so,到现在用H5技能在移动端做网页直播也是见怪不怪了,但是!
!
!
本日我们的主角是webApp下播放视频
参考文献:
1)HTML5+CSS3+JQuery打造自定义视频播放器
简介
HTML5的<video>标签已经被目前大多数主流浏览器所支持,包括还未正式发布的IE9也声明将支持<video>标签,利用浏览器原生特性嵌入视频有很多好处,以是很多开拓者想尽快用上,但是真正利用前还有些问题要考虑,尤其是 Opera/Firefox 和IE/Safari浏览器所支持的视频编码不同的问题,Google几个月前发布的开源视频编码VP8有望能办理这一问题,其余Google还发布了开放网络媒体项目WebM,旨在帮助开拓者为开放网络制作出世界级媒体格式,Opera, Firefox, Chrome和IE9都将支持VP8,而且Flash Player也将可以播放VP8,这就意味着我们很快就可以只制作一个版本的视频然后在所有主流浏览器上播放了。其余一个紧张的问题便是如何构建自定义的HTML5<video>播放器,这是目前Flash Player的上风所在,利用Flash的IDE所供应的接口可以很方便的构建一个个性化的视频播放器,那HTML5的<video>标签要若何才能实现呢?这个问题便是本文所要办理的!
我们将开拓一个HTML5<video>视频播放器的jQuery插件,并且可以很方便的进行自定义,将分为以下几个部分:
1.视频掌握工具条
2.视频掌握按钮
3.打包成jQuery插件
4.外不雅观和体验
5.自定义皮肤
视频掌握工具条
做为一个专业的web开拓职员,我们创建一个视频播放器时一定希望它的外不雅观在各个浏览器中看起来同等(consistent),但是通过下面的图可以看到目前各个浏览器供应的视频掌握工具条外不雅观各不相同:
那就没办法了,我们得自己从头来创建这个掌握工具条,利用HTML和CSS再加上一些图片实现起来并不算很难,其余通过HTML5多媒体元素供应的API我们可以很方便将创建的任何按钮与播放/停息等事宜进行绑定。
视频掌握按钮
基本的视频掌握工具条要包含一个播放/停息按钮,一个进度条,一个计时器和一个音量掌握按钮,我们将这些按钮放在<video>元素下面,并用一个div作为父容器:
Java代码
<div class=\公众ghinda-video-controls\"大众>
<a class=\公众ghinda-video-play\"大众 title=\"大众Play/Pause\"大众></a>
<div class=\公众ghinda-video-seek\"大众></div>
<div class=\公众ghinda-video-timer\公众>00:00</div>
<div class=\"大众ghinda-volume-box\公众>
<div class=\"大众ghinda-volume-slider\公众></div>
<a class=\"大众ghinda-volume-button\"大众 title=\公众Mute/Unmute\公众></a>
</div>
</div>
复制代码
把稳,我们利用元素的class属性来代替ID属性是为了方便在一个页面上利用多个播放器。
打包成jQuery插件
创建好掌握按钮后我们须要合营多媒体元素的API来实现视频掌握的目的,正如前面提到的一样我们将我们的播放器打包成jQuery插件,这样可以很好的实现复用,代码如下:
Java代码
$.fn.gVideo = function(options) {
// build main options before element iteration
var defaults = {
theme: 'simpledark',
childtheme: ''
};
var options = $.extend(defaults, options);
// iterate and reformat each matched element
return this.each(function() {
var $gVideo = $(this);
//create html structure
//main wrapper
var $video_wrap = $('<div></div>').addClass('ghinda-video-player').addClass(options.theme).addClass(options.childtheme);
//controls wraper
var $video_controls = $('<div class=\"大众ghinda-video-controls\"大众><a class=\"大众ghinda-video-play\公众 title=\"大众Play/Pause\公众></a><div class=\"大众ghinda-video-seek\"大众></div><div class=\公众ghinda-video-timer\公众>00:00</div><div class=\"大众ghinda-volume-box\公众><div class=\公众ghinda-volume-slider\"大众></div><a class=\"大众ghinda-volume-button\"大众 title=\"大众Mute/Unmute\"大众></a></div></div>');
$gVideo.wrap($video_wrap);
$gVideo.after($video_controls);
这里先假设您理解jQuery并知道如何创建一个jQuery插件,由于这个不在本文的谈论范围之内,在上面这段脚本中我们利用jQuery动态创建视频掌握工具条的元素,接下来为了绑定事宜我们须要获取对应的元素:
Java代码
//get newly created elements
var $video_container = $gVideo.parent('.ghinda-video-player');
var $video_controls = $('.ghinda-video-controls', $video_container);
var $ghinda_play_btn = $('.ghinda-video-play', $video_container);
var $ghinda_video_seek = $('.ghinda-video-seek', $video_container);
var $ghinda_video_timer = $('.ghinda-video-timer', $video_container);
var $ghinda_volume = $('.ghinda-volume-slider', $video_container);
var $ghinda_volume_btn = $('.ghinda-volume-button', $video_container);
$video_controls.hide(); // keep the controls hidden
这里我们通过className办法获取,先让工具条隐蔽直到所有资源加载完成,现在来实现播放/停息按钮:
Java代码
var gPlay = function() {
if($gVideo.attr('paused') == false) {
$gVideo[0].pause();
} else {
$gVideo[0].play();
}
};
$ghinda_play_btn.click(gPlay);
$gVideo.click(gPlay);
$gVideo.bind('play', function() {
$ghinda_play_btn.addClass('ghinda-paused-button');
});
$gVideo.bind('pause', function() {
$ghinda_play_btn.removeClass('ghinda-paused-button');
});
$gVideo.bind('ended', function() {
$ghinda_play_btn.removeClass('ghinda-paused-button');
});
大多数浏览器在右键点击视频时会供应一个独立的菜单,它也供应了视频掌握功能,如果用户通过这个右键菜单掌握视频那就会跟我们的自定义控件冲突,所以为了避免这一点我们须要绑定视频播放器自身的“播放”,“停息”和“结束”事宜,在事宜处理函数中处理播放/停息按钮,掌握按钮的样式。
为了创建进度条的拖动块,我们利用了jQuery UI的Slider组件:
Java代码
var createSeek = function() {
if($gVideo.attr('readyState')) {
var video_duration = $gVideo.attr('duration');
$ghinda_video_seek.slider({
value: 0,
step: 0.01,
orientation: \"大众horizontal\公众,
range: \"大众min\公众,
max: video_duration,
animate: true,
slide: function(){
seeksliding = true;
},
stop:function(e,ui){
seeksliding = false;
$gVideo.attr(\"大众currentTime\"大众,ui.value);
}
});
$video_controls.show();
} else {
setTimeout(createSeek, 150);
}
};
createSeek();
正如你所看到的,这里我们写了一个递归函数,通过循环比较video的readyState属性来判断视频是否已经准备好,否则我们就不能得到视频的时长也无法创建滑动块,当视频准备好后我们初始化滑动块并显示掌握工具条,下一步我们通过绑定video元素的timeupdate事宜实现计时器功能:
Java代码
var gTimeFormat=function(seconds){
var m=Math.floor(seconds/60)<10?\"大众0\"大众+Math.floor(seconds/60):Math.floor(seconds/60);
var s=Math.floor(seconds-(m60))<10?\"大众0\"大众+Math.floor(seconds-(m60)):Math.floor(seconds-(m60));
return m+\"大众:\"大众+s;
};
var seekUpdate = function() {
var currenttime = $gVideo.attr('currentTime');
if(!seeksliding) $ghinda_video_seek.slider('value', currenttime);
$ghinda_video_timer.text(gTimeFormat(currenttime));
};
$gVideo.bind('timeupdate', seekUpdate);
这里我们用seekUpdate函数获取video的currentTime属性值然后调用gTimeFormat函数进行格式化后得到当前播放的韶光点。
至于音量掌握控件我们还是利用jQuery UI的Slider组件然后利用自定义函数实现静音和取消静音的功能:
Java代码
$ghinda_volume.slider({
value: 1,
orientation: \"大众vertical\公众,
range: \"大众min\公众,
max: 1,
step: 0.05,
animate: true,
slide:function(e,ui){
$gVideo.attr('muted',false);
video_volume = ui.value;
$gVideo.attr('volume',ui.value);
}
});
var muteVolume = function() {
if($gVideo.attr('muted')==true) {
$gVideo.attr('muted', false);
$ghinda_volume.slider('value', video_volume);
$ghinda_volume_btn.removeClass('ghinda-volume-mute');
} else {
$gVideo.attr('muted', true);
$ghinda_volume.slider('value', '0');
$ghinda_volume_btn.addClass('ghinda-volume-mute');
};
};
$ghinda_volume_btn.click(muteVolume);
末了当我们自己的自定义视频掌握工具条布局完成后须要移除<video>标签的controls属性,这样浏览器默认的工具条就被去掉了。
好了,我们的插件功能已经全部完成了,调用方法:
Java代码
$('video').gVideo();
这会将我们的插件运用到页面上每一个video元素上。
外不雅观和体验
好的,现在到了比较故意思的部分,也便是播放器的外不雅观和体验了。当插件功能已经完成后利用一点CSS就可以很随意马虎地自定义样式了,我们将全部利用CSS3来实现。
首先,我们给播放器主容器加一些样式:
Java代码
.ghinda-video-player {
float: left;
padding: 10px;
border: 5px solid #61625d;
-moz-border-radius: 5px; / FF1+ /
-ms-border-radius: 5px; / IE future proofing /
-webkit-border-radius: 5px; / Saf3+, Chrome /
border-radius: 5px; / Opera 10.5, IE 9 /
background: #000000;
background-image: -moz-linear-gradient(top, #313131, #000000); / FF3.6 /
background-image: -webkit-gradient(linear,left top,left bottombottom,color-stop(0, #313131),color-stop(1, #000000)); / Saf4+, Chrome /
box-shadow: inset 0 15px 35px #535353;
}
下一步,我们设置视频掌握工具条左边浮动使它们水平对齐,利用CSS3的opacity和transitions我们给播放/停息和静音/取消静音按钮添加了非常不错的悬浮效果:
Java代码
.ghinda-video-play {
display: block;
width: 22px;
height: 22px;
margin-right: 15px;
background: url(../images/play-icon.png) no-repeat;
opacity: 0.7;
-moz-transition: all 0.2s ease-in-out; / Firefox /
-ms-transition: all 0.2s ease-in-out; / IE future proofing /
-o-transition: all 0.2s ease-in-out; / Opera /
-webkit-transition: all 0.2s ease-in-out; / Safari and Chrome /
transition: all 0.2s ease-in-out;
}
.ghinda-paused-button {
background: url(../images/pause-icon.png) no-repeat;
}
.ghinda-video-play:hover {
opacity: 1;
}
如果您仔细看了前面那段根据视频播放状态(Playing/Paused)添加和移除播放/停息按钮样式的JavaScript代码,就会明白为什么.ghinda-paused-button为什么要重写.ghinda-video-play的背景属性了。
现在轮到滑动块了,我们进度条和音量掌握的滑动块的实现都是利用了jQuery UI的Slider组件,这个组件它本身自带了样式,定义在jQuery UI对应的css文件中,但是为了使滑动块和播放器其他控件外不雅观保持同等我们全部重写了它的样式:
Java代码
.ghinda-video-seek .ui-slider-handle {
width: 15px;
height: 15px;
border: 1px solid #333;
top: -4px;
-moz-border-radius:10px;
-ms-border-radius:10px;
-webkit-border-radius:10px;
border-radius:10px;
background: #e6e6e6;
background-image: -moz-linear-gradient(top, #e6e6e6, #d5d5d5);
background-image: -webkit-gradient(linear,left top,left bottombottom,color-stop(0, #e6e6e6),color-stop(1, #d5d5d5));
box-shadow: inset 0 -3px 3px #d5d5d5;
}
.ghinda-video-seek .ui-slider-handle.ui-state-hover {
background: #fff;
}
.ghinda-video-seek .ui-slider-range {
-moz-border-radius:15px;
-ms-border-radius:15px;
-webkit-border-radius:15px;
border-radius:15px;
background: #4cbae8;
background-image: -moz-linear-gradient(top, #4cbae8, #39a2ce);
background-image: -webkit-gradient(linear,left top,left bottombottom,color-stop(0, #4cbae8),color-stop(1, #39a2ce));
box-shadow: inset 0 -3px 3px #39a2ce;
}
这时候音量掌握的滑动块一贯显示在音量按钮阁下,我们须要将它改成默认隐蔽,当鼠标悬浮在音量按钮上再动态显示出来,利用transitions来实现这个效果会是个不错的的选择:
Java代码
.ghinda-volume-box {
height: 30px;
-moz-transition: all 0.1s ease-in-out; / Firefox /
-ms-transition: all 0.1s ease-in-out; / IE future proofing /
-o-transition: all 0.2s ease-in-out; / Opera /
-webkit-transition: all 0.1s ease-in-out; / Safari and Chrome /
transition: all 0.1s ease-in-out;
}
.ghinda-volume-box:hover {
height: 135px;
padding-top: 5px;
}
.ghinda-volume-slider {
visibility: hidden;
opacity: 0;
-moz-transition: all 0.1s ease-in-out; / Firefox /
-ms-transition: all 0.1s ease-in-out; / IE future proofing /
-o-transition: all 0.1s ease-in-out; / Opera /
-webkit-transition: all 0.1s ease-in-out; / Safari and Chrome /
transition: all 0.1s ease-in-out;
}
.ghinda-volume-box:hover .ghinda-volume-slider {
position: relative;
visibility: visible;
opacity: 1;
}
利用一些根本的CSS属性以及CSS3供应的新属性我们打造了一个全新的播放器外不雅观,它看起来是这个样子:
自定义皮肤
可能您已经把稳到,我们在编写插件的时候已经定义了一些默认选项,它们是theme和childtheme,可以在调用插件的时候根据须要方便的运用自定义皮肤。
这里阐明下theme便是所有控件的一整套样式定义,childtheme便是在theme根本上重写某些样式,我们在调用插件的时候可以同时指定这两个选项或者个中的一个:
Java代码
$('video').gVideo({
childtheme:'smalldark'
});
我们写了一个示例的皮肤smalldark,它只重写了部分的样式,显示效果是这样的:
总结
利用HTML5 video,JavaScript和CSS3打造自定义的视频播放器真的非常随意马虎,t实现工具条功能用JavaScrip,外不雅观和体验交给CSS3,我们得到了一个功能强大并且易于定制的办理方案!
enjoy!
2)mui Html5 Video 实现方案
序言: 最近项目中须要用到html5 视频播放功能,于是轻微研究理解了下,碰着了很多坑,特此记录下.
一、 Html5 Video
参考来源: http://www.xuanfengge.com/html5-video-play.html
(这篇博文确实帮助很大)
1.1、 目的
将Html5 Video功能运用到实际项目中,针对不同的平台和环境,进行个性化处理。
基本只考虑webkit浏览器兼容问题
1.2、 Html5 Video支持格式
只支持: .mp4后缀(.h264编码格式),和.webm后缀(专用web视频格式),以及.ogg后缀(音频文件)
把稳: Html5 Video 可以添加多个source源来进行兼容适配,这样,当第一个源读取出问题时会自动读取下一个源. 比如可以同时在前面加上.webm和.mp4源,这样一个出错时会自动读取另一个可用源(由于不同浏览器,支持的格式是不一样的)
但是,Hybird模式的 Android 下,有些机型只能读取第一个source来源(测试华为和遐想都是),以是也便是说在这种情形下,要确保第一个source源是精确的
各大浏览器兼容如图所示:
见图1
1.3、 不同平台环境和对应实现方案
解释: 这里分为两大块,普通浏览器环境(pc和手机,紧张是移动端,pc不做特殊处理)和Hybird模式的APP环境(Android和iOS).
注: Html5 video可以播放本地视频或者网络视频
1.3.1、 普通浏览器环境
用Html5 Video 自带的播放栏控件
用 Video 视频统一处理方法处理后,点击图片手动隐蔽图片,设置视比年夜小,手动播放视频.
注: 播放效果则由各大浏览器自行实现
手机端浏览器实现的不同效果,比如:
QQ浏览器(包括QQ客户端内置的浏览器):播放时会自动进入全屏
华为自带浏览器: 正常小窗口播放
1.3.2、 Hybird App环境
解释: 内联播放是指直接在video标签中播放视频,没有必要进入全屏
1.3.2.1、 Android内联播放
用Html5 Video 自带的播放栏控件
用 Video 视频统一处理方法处理后,点击图片手动隐蔽图片,设置视比年夜小,手动播放视频.
Android内联播放须要把稳,必须开启硬件加速,由于有些Android手机 webview是默认关闭硬件加速的,以是必须在创建这个带视频播放的webview时手动添加 硬件加速属性才行.(详情见plus创建webview的style)
style.hardwareAccelerated = true;
1.3.2.2、 iOS内联播放
用Html5 Video 自带的播放栏控件
用 Video 视频统一处理方法处理后,点击图片手动隐蔽图片,设置视比年夜小,手动播放视频.
内联播放把稳要点,由于iOS下默认是全屏播放的,以是须要经由设置才能正常内联播放
第一步:在项目的manifest里面配置许可webview内联播放
\"大众plus\"大众: { \公众splashscreen\"大众: { \"大众autoclose\"大众: true,/是否自动关闭程序启动界面,true表示运用加载运用入口页面后自动关闭;false则需调plus.navigator.closeSplashscreen()关闭/ \公众waiting\"大众: true/是否在程序启动界面显示等待雪花,true表示显示,false表示不显示。/ }, \"大众allowsInlineMediaPlayback\"大众: true,/设置ios下许可内联播放/ \"大众popGesture\公众: \公众close\"大众
第二步: 创建video标签时,手动加上内联播放的属性(iOS不支持preload)
<!-- 让ios支持内联播放,必须添加 webkit-playsinline 标签 --> <video webkit-playsinline id=\"大众videoMedia\"大众 controls=\"大众controls\"大众 preload>
这样iOS手机在播放的时候才会采取内联播放
1.3.2.3、 Android非内联播放
通过NJS利用原生播放器来播放视频,传入的url可以是本地的或网络的地址
用 Video 视频统一处理方法处理后,点击图片之后,图片保持不变(以是没有必要隐蔽图片),直接获取视频的资源地址,传给原生播放器播放
注: 这种模式下,性能要比直接html5自带播放器播放高
1.3.2.4、 iOS非内联播放
用Html5 Video 自带的播放栏控件(非内联播放须要去除特定内联属性”webkit-playsinline”,这样才能全屏播放)
if(!isInlinePlay){ //如果是非内敛,ios须要去除内联样式 mediaTarget.removeAttribute('webkit-playsinline'); }
用 Video 视频统一处理方法处理后,点击图片之后,图片保持不变(以是没有必要隐蔽图片),直接调用video.play()播放视频(这时候会用一个全屏播放器来播放视频)
1.3.3、 把稳要点
如果采取NJS通过Android原生播放器播放视频,目前无法监听到视频的一些自定义事宜.(如下载中,播放完毕,停息,播放韶光等)
而如果采取Html5 Video自带播放,这些是可以通过脚本掌握的.
以是选定方案时须要进行衡量
其余,在Html5 Video播放时,无法监听到规定的结束事宜seeked,只能在timeUpdate里面判断,如果ended为true就代表结束了.
在NJS通过Android原生播放器播放时,可以通过document监听resume和pause事宜判断是否进入播放和退出播放
1.4、 Tips
1.4.1、 关于Video 视频统一处理的方案
解释: 由于将一个<Video>直接显示在页面中,会有各种五花八门的播放器效果,如图:
(这里引用了参考来源的图)
见图2
显然,体验效果并不好,以是现在的做法是用一张仿照播放的图片来替代<Video>所在的地方,而将Video元素设置为11像素大小.然后给图片设置点击监听,监听到点击时,播放视频.
把稳:
这里不要用{display: none}或者{width:0;height:0;}的办法,由于这样视频元素会处于未激活的状态,给后续的处理带来麻烦.
这里没有考虑ios<6和一些低版本的Android的兼容性问题了(这些版本里,无法直接通过video.play()来播放),由于项目环境基本上哀求Android>4.0 iOS 7.0以上的.
关于点击图片播放视频后,如果是内联播放模式下(或者是普通浏览器),就该当将图片隐蔽,然后将视比年夜小设置为本来的大小(一样平常为图片大小);如果是非内联播放模式(全屏模式),就没有必要隐蔽图片了,由于iOS下会自动打开一个全屏播放器来播放视频,Android下考虑到Html5 video较卡,以是也会通过NJS利用原生播放器来全屏播放视频.
1.4.2、 Android NJS播放视屏的实当代码
解释: 这个是Dcloud论坛中有人分享的
//非内联模式下的plus下的android才用到 var Intent = plus.android.importClass(\公众android.content.Intent\"大众); var Uri = plus.android.importClass(\"大众android.net.Uri\公众); var main = plus.android.runtimeMainActivity(); var intent = new Intent(Intent.ACTION_VIEW); var uri = Uri.parse(url); intent.setDataAndType(uri, \"大众video/\公众); main.startActivity(intent);
1.4.3、 如何读取元素的宽高
在获取视频的宽度时,创造用 video.style.width无法获取到宽度.
后来查了资料,创造dom.style.width(height)只能获取在stye直接授予的值.而如果是通过css样式表授予的值是无法直接获取的,只能通过dom.offsetWidth(offsetHeight)获取.
设置元素宽和高是不要直接在style里设置,而是最好通过css样式表授予
读取元素宽和高时,用offsetWidth(offsetHeight)
1.4.4、 关于全屏播放的问题
在PC端webkit浏览器下,全屏代码如下:
进入全屏: videoContainer(对应的dom).webkitRequestFullscreen();
退出全屏: document.webkitCancelFullScreen();
但是经测试,在手机浏览器和Hybird模式下的手机环境中都无法利用,
该当是手机浏览器中video 播放器的全屏模式和pc真个有差异,已经分开了webkit的全屏组件,而是用原生自己实现的.
1.5、 碰着问题及办理方法
1.5.1、 Video.currentTime 设置值时设置无效,或者变为0
缘故原由剖析:
与测试的做事器和端口有关,测试环境是放在hbuild本地浏览器的,没有处理好视频快进问题,以是会导致每次快进后,视频都会重置-在某些测试做事器上,则涌现快进无效,但不会重置
办理方法:
将网页用其它正式做事器打开均可正常,如tomcat,wampserver,乃至直接在本地打开也行.
1.5.2、 无法通过代码Video.src获取资源路径
缘故原由剖析:
本实例中,Video是通过source添加src的,无法直接读取video的src
办理方法:
可以通过读取到第一个source的标签,再获取source的src
注:本来这个方法有一个缺陷便是有可能第一个source的src不可用.但是由于Android中第一个source必须有用才行.否则无法正常播放.以是在确保第一个source精确的情形下能这样用.
1.5.3、 部分Android机型无法退出全屏
描述:
在利用Html5 Video自带播放器播放时,部分Android机型(如遐想K860点击全屏按钮进入全屏后,无法退出全屏-由于进入全屏后,全屏按钮不见了)
缘故原由剖析: 可能是手机厂商擅自挟制了浏览器或者修改了浏览器实现办法
办理方法:
目前无法办理,在这类机型中,建议直接采取非内联模式播放或者是只管即便不要手动进入全屏
3)移动端HTML5<video>视频播放优化实践
碰着的寻衅
移动端HTML5利用原生<video>标签播放视频,要做到两个基本原则,速率快和体验佳,先来剖析一下这两个问题。
下载速率
以一个8s短视频为例,wifi环境下供应的高清视频达到1000kbps,文件大小大约1MB;非wifi环境下供应的低码率视频是500kbps旁边,文件大小大约500KB;参考QzoneTouch多普勒测速,2g网络的均匀速率是14KB/s,那么下载一个低码率视频耗时35s;那么要想流畅播放视频,就须要一个加载等待的过程,这个过程要有明确的反馈,不能让用户有“坏掉了”的觉得。
多普勒测速数据参考
用户体验
视频是否可以自动播放,是否能循环播放,是否能显示下载进度,播放的时候如何隐蔽掌握条,停息的时候又能显示出来呢。这些问题看上去貌似大略,但是由于PC/iOS/Android这些不同平台、不同的浏览器内核、乃至相同内核的不同版本,所实现的<video>属性、方法和事宜差异较大,办理兼容性问题又给开拓造成了很大困扰。
剖析缘故原由
事宜差异
下面是播放一个短视频,在不同平台触发事宜和获取属性的差异表现。
PC
iOS
Android
一些常用且须要重点关注的<video>事宜
属性差异
封面图片
支持,但是加载速率明显比在<img>中要慢;不一定支持(浏览器厂商的实现标准分歧一);preload预加载
iPhone不支持;可能支持;autoplay自动播放
iPhone Safari中不支持,但在webview中可能被开启;iOS开拓文档明确解释蜂窝网络下不许可autoplay;可能支持;loop循环播放
支持可能支持;controls掌握条
支持,但是须要开始播放了才显示基本都支持显示或者不显示width和height一定给出明确的属性设置,切不能为0;如果不设置,仅仅通过CSS样式去掌握视比年夜小,可能会导致标签失落效。其他怪异bug和不友好表现
webview.allowsInlineMediaPlayback = YES;
,可以通过设置webkit-playsinline
属性支持内联播放;支持内联播放,但某些厂商会用自己的播放器挟制原生的视频播放;下载视频时,会先发送一个2字节的要求来获取视频元数据(比如时长),然后再不断的发送分包续传(206)要求来下载视频,抓包显示要求数和要求量至少有一倍的冗余(x2),这个严重的bug在iOS8中有明显的修复,但是分包的206要求仍旧会有冗余数据的下载,摧残浪费蹂躏了流量。比iOS的处理办法好,没有第一个2字节要求,没有流量损耗;–低版本Android(<=4.0.4)中,<video>如果在有相对和决定定位的层中,可能会导致全体页面错位。–某些浏览器厂商会挟制<video>,用其“自己”的播放器来播放视频,“毁坏”了产品本身的播放体验,那么只能case by case的办理了。加载视频时没有进度提示,视觉上看不出是播放完了还是卡住了;加载视频时,大都会显示一个自带的loading UI(菊花)。最佳实践
视频初始化
如果将一个<video>直接显示在页面中,那么就会看到各种五花八门的播放器初始效果;
这显然不是一个好的视觉体验,那么常日的做法是制作一个仿照的视频播放视图,比如一个封面加一个播放按钮。
而真实的<video>视频元素要隐蔽起来,如何隐蔽呢?最好不要用{display: none}
或者{width:0;height:0;}
的办法,由于这样视频元素会处于未激活的状态,给后续的处理带来麻烦。最佳的办法是将视频设置成1×1像素大小,放在视觉边缘的位置。
1
2
3
4
5
<!--iOS-->
<video webkit-playsinline width=\"大众1\"大众height=\"大众1\"大众class=\公众vplayinside notaplink\"大众x-webkit-airplay controls loop=\"大众loop\"大众src=\"大众<%=src%>\公众></video>
<!--Android-->
<video width=\"大众1\"大众height=\公众1\"大众controls loop=\"大众loop\"大众src=\"大众<%=src%>\公众></video>
自动播放
autoplay的支持依赖内核和网络状况,比如iPhone在蜂窝网络下明确禁用了autoplay;
经由试验,在没有明确的用户操作的情形下,直接通过video.play()
也是无法激活播放的;
并且在产品设计上,自动播放也不是一个舒畅的用户体验,以是产品设计上只管即便避免利用自动播放。
点击播放
之条件到,视频最好通过1px大小隐蔽起来,那么这时如何触发播放呢?
经由试验,当在明确的用户操作(touch、click)时,通过这些用户行为事宜的回调函数,用video.play()
是可以触发视频播放的,那么能否在用户操作后,再去同步的创建和播放视频呢?答案是肯定的,这无疑是一个视频元素初始化的最佳实践,但是有些差异须要把稳。
iOS6+
可以在用户的touch韶光中动态创建并播放视频。
iOS < 6
可以在用户的touch韶光中动态创建视频,但不能播放;要再追加一个click事宜来启动播放;也便是说,给假造的视频播放按钮同时绑定tap和click事宜,在tap的时候创建,在之后300毫秒的click中去播放。
Android
大部分高版本Android可以像iOS6+那样去处理,但是低版本的弗成,必须要通过click事宜去通报video.play()
,为了保持兼容,最好是用帮tap和click两个事宜来分别完成视频的初始化和播放。
我们还创造,有些低版本Android中,无法通过video.play()
来播放视频,必须有真实的用户点击视频元素才能播放;这种情形,有一个技巧便是在tap的时候初始化并放大视频覆盖在播放视图中,让300毫秒后的真实点击行为穿透点击在视频元素上来实现播放。
循环播放
如果视频须要循环播放,那么就增加loop
属性,是否能循环播放就看浏览器是否支持了,由于还没有找到hack技巧来逼迫循环播放;
纵然,在不支持循环播放的Android中,通过监听seeked
事宜知道了播放进度到了终点或出发点停息了,此时也无法通过video.play()
来让视频重新播放。
监控下载进度
如何获取视频时长和已经下载的时长?
1
2
3
4
5
6
7
8
9
10
11
12
13
// 视频时长
varduration=video.duration
// 获取视频已经下载的时长
functiongetEnd(video){
varend=0
try{
end=video.buffered.end(0)||0
end=parseInt(end1000+1)/1000
}catch(e){
}
returnend
}
progress事宜表示视频在加载,但是它的触发频率和机遇并不规律,最佳做法是通过一个定时器去实时获取end,当end >= duration时,表示已经下载完毕,再终止定时器。
1
2
3
4
5
6
7
8
9
10
vartimer=setInterval(function(){
varend=getEnd(video),
duration=video.duration
if(end<duration){
return
}
clearInterval(timer)
},1000)
全部下载后再播放
假设播放短视频,如果网络不佳,会造成播放断断续续,在iOS中这种停顿还没有一个明确的等待提示,这不是一个好的体验,那么是否可以将视频全部下载完毕再播放呢?
在iOS中,可以在视频刚开始下载的时候立时停息,此时下载还将连续,可以做一个loading的菊花奉告视频正在加载,然后等到视频全部下载完再开始播放。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
$(video).one('loadeddata',function(){
// 停息,但下载还在连续
video.pause()
// 启动定时器检测视频下载进度
vartimer=setInterval(function(){
varend=getEnd(video),
duration=video.duration
if(end<duration){
return
}
varwidth=$(video).parent().width()
// 下载完了,开始播放吧
$(video).attr{
width:width,
height:width
}
video.play()
clearInterval(timer)
},1000)
})
缓冲播放——边下边播时,选择开始播放的最佳韶光点
当视频越来越长或者网络慢时,等待视频全部下载完再播放也不是好的体验,最好能边下边播,缓冲到流畅状态就开始播放,那什么时候播放才是最佳韶光点呢?
在iOS中,canplaythrough事宜便是这个最佳韶光点,它是通过动态打算缓冲量和下载速率得出的视频可以流畅播放的状态反馈。
canplaythrough event: The user agent estimates that if playback were to be started now, the media resource could be rendered at the current playback rate all the way to its end without having to stop for further buffering.
把稳:下载完再播放和缓冲播放只适用于iOS。
统计播放韶光和播放次数
要统计实际的播放韶光,要累加timeupdate事宜变革的韶光,再减去中间可能停息的韶光。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
$video.on('playing',function(){
// 开始播放是打点
$video.attr('data-updateTime',+newDate())
})
$video.on('pause',function(){
// 停息播放时打消打点
$video.removeAttr('data-updateTime')
})
// 累加播放韶光
$video.on('timeupdate',function(event){
var$video=$(event.target),
updateTime=parseInt($video.attr('data-updateTime')||0),
playingTime=parseInt($video.attr('data-playingTime')||0),
times=parseInt($video.attr('data-times')||0),
newtimes=0,
video=$video.get(0),
duration=parseFloat($video.attr('data-duration')||0),
now=+newDate()
// 播放韶光
playingTime=playingTime+now-updateTime
// 播放次数
newtimes=Math.ceil(playingTime/1000/duration)
$video.attr('data-playingTime',playingTime)
$video.attr('data-updateTime',now)
})
非常处理
对error事宜做详细的上报;
对stalled事宜做统计上报,并提示用户网络慢等。
参考数据
微视触屏版iOS视频测速
韶光点(s)
韶光点(s)
韶光点(s)
搬好凳子看HTML
首先我们在HB下创建一个新的app项目,名称为 欠债
新建一个video.html
webkit-playsinline : 在ios中,加入此属性,可以关闭自动全屏播放
object-fit:fill : 视频充满video容器的大小
详细情由请看参考文献2or3
在此我们向项目里放置一个mp4格式的视频,视频内容不限,可以是小动画,也可以是
ps:要在meta中加上,否则视频会扩充变形哦
<meta name=\公众viewport\"大众 content=\"大众width=device-width,initial-scale=1,minimum-scale=1,maximum-scale=1,user-scalable=no\公众 />
OK,现在布局已经完成,一个视频已经在页面中了
旁白:尼玛,点了没反应,那这怎么播放?
楼主:你们这群家伙看别的小视频等个1小时都行。。。
旁白:一个大略的播放器,至少要有 停息/播放,进度条,视频时长,全屏等控件吧
楼主:来来来,不要急,先来个播放按钮写在video标签后面
<div class=\公众bad-video\"大众> <video class=\"大众\公众 webkit-playsinline style=\"大众object-fit:fill;\公众> <source src='xx.mp4' type=\公众video/mp4\"大众></source> <p>设备不支持</p> <video> <img src=\公众img/play.png\"大众/> </div>
写好样式、
.bad-video { position: relative; overflow: hidden; background-color: #CCCCCC; } .bad-video .vplay{ position: absolute; width: 15%; z-index: 99; top: 50%; left: 50%; -webkit-transform: translate(-50%, -50%); transform: translate(-50%, -50%); }
楼主:当当当
再在后面加一个掌握条
<img src=\"大众img/play.png\"大众 class=\公众vplay\公众 /> <div class=\"大众controls\"大众> <div> <div class=\公众progressBar\"大众> <div class=\"大众timeBar\公众></div> </div> </div> <div><span class=\"大众current\公众>00:00</span>/<span class=\"大众duration\公众>00:00</span></div> <div><span class=\公众fill\"大众>全屏</span></div> </div>
.bad-video .controls { width: 100%; height: 2rem; line-height: 2rem; font-size: 0.8rem; color: white; display: block; position: absolute; bottom: 0; background-color: rgba(0, 0, 0, .55); display: -webkit-flex; display: flex;}.bad-video .controls> { flex: 1;}.bad-video .controls>:nth-child(1) { flex: 6;}.bad-video .controls>:nth-child(2) { flex: 2; text-align: center;}.bad-video .controls .progressBar { margin: .75rem 5%; position: relative; width: 90%; height: .5rem; background-color: rgba(200, 200, 200, .55); border-radius: 10px;}.bad-video .controls .timeBar { position: absolute; top: 0; left: 0; width: 0; height: 100%; background-color: rgba(99, 110, 225, .85); border-radius: 10px;}
总算有个看起来像样的了
旁白:楼主,可是还是不能播放啊
楼主:叫你别急,要不你先去撸一把,我写好了笔墨@你
旁白:好啊,早说嘛,我先走了,记得@我
楼主:你走,省的我精神分裂码两个人的字
好,现在Html元素已经基本上弄好啦,看起来不是那么low了