用HTML5制作视频拼图的教程


Posted in HTML / CSS onMay 13, 2015

几天前同事给我看了一个特效,是一个拼图游戏,不同的是,拼图里的是动画。他让我看下做个DEMO,于是就自己整了一会,也确实不难。用canvas很容易做。所以这篇博文不适合高手看。。。。就是随便写来玩玩的。
效果图:
用HTML5制作视频拼图的教程

至少我刚看到这个的时候觉得挺新颖的,所以才会想到做出来玩玩,觉得楼主out的哥们请轻喷

不多说,先上DEMO:视频拼图  (或许要等一会才能看到效果,我是直接在w3school那里搞了个视频链接过来的,拖动什么的都做的很简单,或许还有些bug,毕竟就只是做一个DEMO玩玩而已,说说原理就行了),还有一点,直接把视频的当前帧画到canvas中在移动设备上好像还不支持。。。至少我用ipad看了一下,发现画不上去,如果有知道肿么解决这问题的大牛请为小弟解答一下,不甚感激

原理:每一块拼图就是一个canvas,同时还需要一个离屏canvas。先整一个video标签

复制代码
代码如下:
</p> <p><video id="video" src="http://www.w3school.com.cn/example/html5/mov_bbb.mp4" width="600px" height="400px" controls="control" loop="loop" style="display:block;position:absolute;top:-6000px;"></video></p> <p>

并且把video隐藏掉,然后播放视频的时候把每一帧都画到离屏canvas中(离屏canvas就是隐藏了的canvas,用于保存数据),写法很简单:

复制代码
代码如下:
ctx.drawImage(video , 0 , 0 , vw , vh);

,直接用drawImage方法画上去就行了。为何要先用离屏canvas呢,因为如果直接把每一帧数据同时画到所有拼图块的canvas中,浏览器会瞬间崩掉。所以用一个离屏canvas作为缓冲。先把当前帧的数据保存到canvas,然后再将canvas画到作为拼图块的canvas中。将canvas画到canvas中也很简单,也是用drawImage就可以搞定:

ctx2.drawImage(cs , -this.cols*this.w , -this.rows*this.h , vw , vh);

然后。。。。原理就这么简单,之后提醒一点,用requestAnimationFrame循环取帧时,要限一下速,例如下面所写的,我是每30毫秒取一次,推荐30~50毫秒,太低浏览器容易崩溃,太高的话视频出现卡帧现象了:

 

复制代码
代码如下:

function animate(){
var newTime = new Date();
if(newTime - lastTime > 30){
lastTime = newTime;
ctx.drawImage(video , 0 , 0 , vw , vh);
canvases.forEach(function(){
var ctx2 = this.cas.getContext('2d');
ctx2.drawImage(cs , -this.cols*this.w , -this.rows*this.h , vw , vh);
});
}
if("requestAnimationFrame" in window){
requestAnimationFrame(animate);
}
else if("webkitRequestAnimationFrame" in window){
webkitRequestAnimationFrame(animate);
}
else if("msRequestAnimationFrame" in window){
msRequestAnimationFrame(animate);
}
else if("mozRequestAnimationFrame" in window){
mozRequestAnimationFrame(animate);
}
}

最后贴出所有代码: 

复制代码
代码如下:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html;charset=UTF-8">
<style>
body{margin:0;padding:0;}
.allCanvas{
position: relative;
margin:50px auto;
width:600px;
}
.vcanvas{
position: absolute;
display: block;
border: 1px solid;
}
</style>
<title>视频拼图</title>
</head>
<body>
<div class="allCanvas">
<canvas id="liping" width="600" height="400" style="display:none"></canvas>
</div>
<video id="video" src="http://www.w3school.com.cn/example/html5/mov_bbb.mp4" width="600px" height="400px" controls="control" loop="loop" style="display:block;position:absolute;top:-6000px;"></video>
<script>
var video = document.getElementById("video");
var cs = document.getElementById("liping");
var ctx = cs.getContext('2d')
var rows = 3,
cols = 3,
cb = document.querySelector(".allCanvas"),
vw = 600,
vh = 400,
canvases = [];</p> <p> function createCanvas(){
var num = rows*cols;
for(var i=0;i<cols;i++){
for(var j=0;j<rows;j++){
var canvas = new vCanvas(Math.random()*600, Math.random()*600 , vw/rows , vh/cols , j , i);
canvases.push(canvas);
}
}
}</p> <p> var vCanvas = function(x,y,w,h,cols,rows){
this.x = x;
this.y = y;
this.w = w;
this.h = h;
this.cols = cols;
this.rows = rows;
this.creat();
this.behavior();
}
vCanvas.prototype = {
creat:function(){
this.cas = document.createElement("canvas");
cb.appendChild(this.cas);
this.cas.className = "vcanvas";
this.cas.id = "vc_"+(this.cols+1)*(this.rows+1);
this.cas.style.left = this.x+"px";
this.cas.style.top = this.y+"px";
this.cas.width = this.w;
this.cas.height = this.h;
},
behavior:function(){
this.cas.onmousedown = function(e){
e = e || window.event;
var that = this;
var om = {
x:e.clientX,
y:e.clientY
}
window.onmousemove = function(e){
e = e || window.event;
var nm = {
x:e.clientX,
y:e.clientY
}
that.style.left = parseInt(that.style.left.replace("px","")) + (nm.x-om.x) + "px";
that.style.top = parseInt(that.style.top.replace("px","")) + (nm.y-om.y) + "px";
om = nm;
}
window.onmouseup = function(){
this.onmousemove = null;
}
}
}
}</p> <p> Array.prototype.forEach = function(callback){
for(var i=0;i<this.length;i++){
callback.call(this[i]);
}
}</p> <p> var lastTime = 0;
function initAnimate(){
lastTime = new Date();
createCanvas();
animate();
}</p> <p> function animate(){
var newTime = new Date();
if(newTime - lastTime > 30){
lastTime = newTime;
ctx.drawImage(video , 0 , 0 , vw , vh);
canvases.forEach(function(){
var ctx2 = this.cas.getContext('2d');
ctx2.drawImage(cs , -this.cols*this.w , -this.rows*this.h , vw , vh);
});
}
if("requestAnimationFrame" in window){
requestAnimationFrame(animate);
}
else if("webkitRequestAnimationFrame" in window){
webkitRequestAnimationFrame(animate);
}
else if("msRequestAnimationFrame" in window){
msRequestAnimationFrame(animate);
}
else if("mozRequestAnimationFrame" in window){
mozRequestAnimationFrame(animate);
}
}</p> <p> video.play();
initAnimate();
</script>
</body>
</html>

HTML / CSS 相关文章推荐
CSS+jQuery+PHP+MySQL实现的在线答题功能
Apr 25 HTML / CSS
CSS3中新增的对文本和字体的设置
Feb 03 HTML / CSS
canvas学习笔记之2d画布基础的实现
Feb 21 HTML / CSS
HTML5边玩边学(2)基础绘图实现方法
Sep 21 HTML / CSS
html5中canvas学习笔记1-画板的尺寸与实际显示尺寸
Jan 06 HTML / CSS
html5指南-4.使用Geolocation实现定位功能
Jan 07 HTML / CSS
HTML5+CSS3实现拖放(Drag and Drop)示例
Jul 07 HTML / CSS
HTML5 Canvas中使用路径描画二阶、三阶贝塞尔曲线
Jan 01 HTML / CSS
调用HTML5的Canvas API绘制图形的快速入门指南
Jun 17 HTML / CSS
h5使用canvas画布实现手势解锁
Jan 04 HTML / CSS
HTML5自定义视频播放器源码
Jan 06 HTML / CSS
css filter和getUserMedia的联合使用
Feb 24 HTML / CSS
用HTML5制作一个简单的弹力球游戏
May 12 #HTML / CSS
用HTML5制作一个简单的桌球游戏的教程
May 12 #HTML / CSS
利用HTML5绘制点线面组成的3D图形的示例
May 12 #HTML / CSS
用HTML5制作烟火效果的教程
May 12 #HTML / CSS
浅谈利用缓存来优化HTML5 Canvas程序的性能
May 12 #HTML / CSS
利用HTML5 Canvas制作一个简单的打飞机游戏
May 11 #HTML / CSS
用HTML5制作数字时钟的教程
May 11 #HTML / CSS
You might like
php实现无限级分类实现代码(递归方法)
2011/01/01 PHP
浅析php中如何在有限的内存中读取大文件
2013/07/02 PHP
PHP生成唯一ID之SnowFlake算法
2016/12/17 PHP
详解PHP中的外观模式facade pattern
2018/02/05 PHP
php适配器模式简单应用示例
2019/10/23 PHP
PHP使用递归按层级查找数据的方法
2019/11/10 PHP
JavaScript 替换Html标签实现代码
2009/10/14 Javascript
js模拟类继承小例子
2010/07/17 Javascript
ASP.NET jQuery 实例18 通过使用jQuery validation插件校验DropDownList
2012/02/03 Javascript
JavaScript 基础篇之对象、数组使用介绍(三)
2012/04/07 Javascript
jquery写个checkbox——类似邮箱全选功能
2013/03/19 Javascript
使用jquery中height()方法获取各种高度大全
2014/04/02 Javascript
简单实现Vue的observer和watcher
2016/12/21 Javascript
JS在浏览器中解析Base64编码图像
2017/02/09 Javascript
jQuery EasyUI 折叠面板accordion的使用实例(分享)
2017/12/25 jQuery
JavaScript设计模式之单例模式简单实例教程
2018/07/02 Javascript
Vue.js 父子组件通信的十种方式
2018/10/30 Javascript
python中查看变量内存地址的方法
2015/05/05 Python
Python处理字符串之isspace()方法的使用
2015/05/19 Python
Python实现列表转换成字典数据结构的方法
2016/03/11 Python
python3批量删除豆瓣分组下的好友的实现代码
2016/06/07 Python
python实现批量监控网站
2016/09/09 Python
Django中的静态文件管理过程解析
2019/08/01 Python
python 追踪except信息方式
2020/04/25 Python
关于PyCharm安装后修改路径名称使其可重新打开的问题
2020/10/20 Python
pycharm激活码2020最新分享适用pycharm2020最新版亲测可用
2020/11/22 Python
可以随进度显示不同颜色的css3进度条分享
2014/04/11 HTML / CSS
canvas实现图片马赛克的示例代码
2018/03/26 HTML / CSS
Draper James官网:知名演员瑞茜·威瑟斯彭所创品牌
2017/10/25 全球购物
韩国江南富人区高端时尚百货商场:Galleria(格乐丽雅)
2018/03/27 全球购物
C#里面可以避免一个类被其他类继承么?如何?
2013/09/26 面试题
教师辞职报告范文
2014/01/20 职场文书
服装设计专业求职信
2014/06/16 职场文书
工作迟到检讨书范文
2015/05/06 职场文书
2016年毕业实习心得体会范文
2015/10/09 职场文书
win10蓝屏0xc0000001安全模式进不了怎么办?win10出现0xc0000001的解决方法
2022/08/05 数码科技