Chapter 8 视频
1 <video>元素
<video controls autoplay src="test.webm" width="320" height="180" poster="conver.jpg" id="video" preload="metadata" loop>
</video>
- controls:布尔值,视频控件(播放、暂停、音量、进度条等)
- autoplay:布尔值,自动播放
- src:视频源文件
- width, height:宽高,视频自动缩放并用黑边填充
- poster:播放前显示的图片,若无则选择视频其中一帧
- preload:播放前是否预加载,可选none/auto/metadata
- loop:布尔值,循环播放
- volume:音量,取值范围为0.0-1.0
2 视频格式
- WebM容器
- Vp8视频编码,Vorbis音频编码
- Chrome、Firefox、Android支持
- .webm格式
- MP4容器
- H.264视频编码,AAC音频编码
- Safari、IE9+、iOS支持
- .mp4格式
- Ogg容器
- Theora视频编码,Vorbis音频编码
- Firefox、Chrome支持
- .ogv格式
-
<video>元素处理多种格式:使用<sourece>元素
<video controls autoplay width="320" height="180" poster="cover.jpg" id="video" preload="metadata" loop> <source src="test.mp4"> <!--浏览器从上到小查找直至找到能播放的视频格式--> <source src="test.webm"> <source src="test.ogv"> <object> 可在此处插入Flash,作为Html5的后备 </object> <p> <!--都不支持则显示此文本信息--> Sorry, you should upgrade the browser. </p> </video>
3 <video>元素API
属性 | 方法 | 事件 |
---|---|---|
videoWidth, videoHeight, currentTime, duration, ended, error, loop, muted, paused, readyState, seeking, volume | play, pause, load, canPlayType | play, pause, progress, error, timeupdate, ended, abort, waiting, loadeddata, loadedmetadata, volumechange |
4 addEventListener方法
video.addEventListener(event, handler, false);
5 canPlayType方法
video.canPlayType('video/webm; codes="vp8,vorbis"');
- 返回值""/“maybe”/“probably”
- 不提供codes参数,则只返回""/“maybe”
6 document.querySelectorAll方法
-
选择与一个CSS选择匹配的所有元素,返回元素对象数组
-
举例
document.querySelectorAll("a.control");
7 scratch缓冲区
-
工作原理:
(1) 浏览器将视频解码为一系列帧,每帧都是一个像素构成的矩形
(2) 解码每一帧时,将其复制到scratch缓冲区
(3) 对scratch缓冲区的图像数据进行逐像素迭代处理
(4) 处理完后,将其从scratch缓冲区复制到显示画布
-
实现方法:构建两个<canvas>,scratch缓冲区和显示画布,层叠在视频之上
8 scratch缓冲区代码实现
function processFrame() {
var video = document.getElementById("video");
if(video.paused || video.ended) { //若视频暂停或结束播放,则无需效果处理
return;
}
var bufferCanvas = getElementById("buffer");
var displayCanvas = getElementById("display");
var buffer = bufferCanvas.getContext("2d");
var display = displayCanvas.getContext("2d");
buffer.drawImage(video,0,0,bufferCanvas.width,bufferCanvas.height);
var frame = buffer.getImageData(0,0,bufferCanvas.width,bufferCanvas.height);
var length = frame.data.length / 4;
for(var i = 0; i < length; i++) {
var r = frame.data[i*4];
var g = frame.data[i*4+1];
var b = frame.data[i*4+2];
effectFunction(i,r,g,b,frame); //处理函数,为帧数据添加效果
}
display.putImageData(frame,0,0);
setTimeout(processFrame,0); //马上执行下一帧处理
}
- 画布的context对象的drawImage方法取出视频的一帧
- 画布的context对象的getImageData得到该帧视频的图像数据,存于data属性中
- frame.data数据中,包含RGBA(颜色+透明度)信息
- 画布的context对象的putImageData将处理后的该帧视频,存于显示画布中
9 错误对象error
- video.error.code属性存放错误代码
- 错误代码含义
- =1,请求视频过程被浏览器中止
- =2,网络错误
- =3,解码错误
- =4,不支持视频源,视频损坏等
-
添加错误处理程序
video.addEventListener("error", errorHandler, false);