Canvas+Video打造酷炫播放体验

一.简介
直到现在,仍然不存在一项旨在网页上显示视频的标准。
今天,大多数视频是通过插件(比如 Flash)来显示的。然而,并非所有浏览器都拥有同样的插件。
HTML5 规定了一种通过 video 元素来包含视频的标准方法。如:
| 1 2 | <videosrc="movie.ogg" controls="controls"></video> | 
二.Canvas+Video
HTML5中引入新的元素canvas,其drawImage 方法允许在 canvas 中插入其他图像( img 和 canvas 元素) 。
drawImage函数有三种函数原型:
drawImage(image, dx, dy) 
drawImage(image, dx, dy, dw, dh) 
drawImage(image, sx, sy, sw, sh, dx, dy, dw, dh)
第一个参数image可以用HTMLImageElement,HTMLCanvasElement或者HTMLVideoElement作为参数。
dx和dy是image在canvas中定位的坐标值;dw和dh是image在canvas中即将绘制区域(相对dx和dy坐标的偏移量)的宽度和高度值;
sx和sy是image所要绘制的起始位置,sw和sh是image所要绘制区域(相对image的sx和sy坐标的偏移量)的宽度和高度值。
所以这使酷炫播放体验有了实现的可能。
三.理解canvas.translate和canvas.scale
很多人对于canvas.translate(x,y)的理解有的错误,之前一直以原点(0,0)为基准点,作用就是移动原点,默认的原点(0,0)是在屏幕左上角的,你可以通过translate(x,y)把点(x,y)作为原点,就一直以为这个(x,y)就是新的坐标原点。但看一下API就会知道,这种理解是不对的,
不过API确实容易误导大家:
| 1 2 3 4 5 6 7 | view plainpublicvoidtranslate (floatdx, floatdy)   Since: API Level 1  Preconcat the current matrix with the specified translation  Parameters  dx  The distance to translate in X  dy  The distance to translate in Y | 
其实是原来的原点分别在x轴和y轴偏移多远的距离,然后以偏移后的位置作为坐标原点。也就是说原来在(100,100),然后translate(1,1)新的坐标原点在(101,101)而不是(1,1)
canvas.scale:
canvas.scale提供了放大缩小倒置等功能。比如Y倒置:canvas.scale(1,-1)
四.核心代码
| 1 2 3 4 5 6 7 | canvas.setAttribute('height', Math.floor(video.height));      canvas.setAttribute('width', Math.floor(video.width));      ctx.translate(0, canvas.height );      ctx.scale(1, -1);      ctx.globalAlpha = 0.3;      ctx.drawImage(video, 0, 0, video.width, video.height, 0, -canvas.height/2, canvas.width, canvas.height); | 
五.在线演示
六.代码下载
| 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 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 | <html><head><metacharset="utf-8" /><title></title></head><body>   <div>   <videowidth="640" height="264">   </video> <br/>  <canvasstyle="position:absolute; top:143px;"></canvas></div><divstyle="position:absolute; top:400px;">  <p>    <inputtype="button" id="play" value="play">    <spanid="position">00:00</span> / <spanid="duration"></span>  </p>  </div><script>    var addEvent = (function () {        if (document.addEventListener) {            return function (el, type, fn) {                if (el && el.nodeName || el === window) {                    el.addEventListener(type, fn, false);                } else if (el && el.length) {                    for (var i = 0; i < el.length; i++) {                        addEvent(el[i], type, fn);                    }                }            };        } else {            return function (el, type, fn) {                if (el && el.nodeName || el === window) {                    el.attachEvent('on' + type, function () { return fn.call(el, window.event); });                } else if (el && el.length) {                    for (var i = 0; i < el.length; i++) {                        addEvent(el[i], type, fn);                    }                }            };        }    })();   </script><script>    var video = document.querySelector('video');    var togglePlay = document.querySelector('#play');    var position = document.querySelector('#position');    var canvas = document.querySelector('canvas');    var ctx = canvas.getContext('2d');    addEvent(togglePlay, 'click', function () {        video.playbackRate = 0.5;        if (video.paused) {            if (video.ended) video.currentTime = 0;            video.play();            this.value = "pause";        } else {            video.pause();            this.value = "play";        }    });    setInterval(function () {        position.innerHTML = asTime(video.currentTime);        ctx.drawImage(video, 0, 0, video.width, video.height, 0, -canvas.height / 2, canvas.width, canvas.height);    }, 1000 / 15);    addEvent(video, 'ended', function () {        togglePlay.value = "play";    });    addEvent(video, 'canplay', function () {        video.muted = true;        document.querySelector('#duration').innerHTML = asTime(this.duration);        startCanvas();    });    function startCanvas() {        canvas.setAttribute('height', Math.floor(video.height));        canvas.setAttribute('width', Math.floor(video.width));        ctx.translate(0, canvas.height );        ctx.scale(1, -1);        ctx.globalAlpha = 0.3;        ctx.drawImage(video, 0, 0, video.width, video.height, 0, -canvas.height/2, canvas.width, canvas.height);          }    function asTime(t) {        t = Math.round(t);        var s = t % 60;        var m = Math.round(t / 60);        return two(m) + ':' + two(s);    }    function two(s) {        s += "";        if (s.length < 2) s = "0" + s;        return s;    }</script></body></html> | 
 
                    
                
 
                
            
         浙公网安备 33010602011771号
浙公网安备 33010602011771号