标签:
一、目录
1. 入门案例——实现匀速运动
2. 入门案例——实现缓冲运动
3. 实现任意值的运动框架v.1
4. 改进任意值的运动框架v.2
5. 改进任意值的运动框架v.3
6. 实现链式运动框架
7. 实现完美运动框架
二、内容
1. 入门案例——实现匀速运动
①. 要求:只要简单的实现传入的对象和运动的最终目标,便能操作该对象的left属性的大小匀速的变化到目标大小。
②. 具体代码:
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="UTF-8"> 5 <title></title> 6 <style> 7 #div1 { 8 width: 100px; 9 height: 100px; 10 background: red; 11 margin: 10px; 12 position:absolute; 13 } 14 </style> 15 <script> 16 var timer = null; //定时器 17 var speed = 10; //运动速度 18 function uniformMotion(obj,iTarget) { 19 if (obj.offsetLeft > iTarget) { //判断当前left属性的值与最终目标的值之间的位置 20 speed = -10; //说明当前对象的位置在目标值的右边 21 } else { 22 speed = 10; 23 } 24 clearInterval(timer); //先关闭之前的定时器 25 timer = setInterval(function () { //开启定时器,并保存返回的定时器对象 26 if (obj.offsetLeft == iTarget) { 27 clearInterval(timer); //运动到目标后关闭定时器 28 } else if (Math.abs(obj.offsetLeft - iTarget) < Math.abs(speed)) { 29 obj.style.left = iTarget + ‘px‘; //如果当前位置与目标的位置不足10,那么就让它直接跳到目标位置上 30 clearInterval(timer); //关闭定时器 31 } else { 32 obj.style.left = obj.offsetLeft + speed + ‘px‘; //让当前位置向目标位置移动 33 } 34 }, 30); 35 } 36 window.onload = function () { 37 var btn = document.getElementsByTagName("input")[0]; 38 var oDiv = document.getElementById("div1"); 39 btn.onclick = function(){ 40 uniformMotion(oDiv,300); 41 } 42 } 43 </script> 44 </head> 45 <body> 46 <input type="button" value="匀速运动"/> 47 <div id="div1"></div> 48 </body> 49 </html>
2. 入门案例——实现缓冲运动
①. 要求:只要简单的实现传入的对象和运动的最终目标,便能操作该对象的left属性的大小由大到小的变化到目标大小。
②. 具体代码:
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="UTF-8"> 5 <title></title> 6 7 <style> 8 div { 9 width: 100px; 10 height: 100px; 11 position: absolute; 12 background: red; 13 margin: 10px; 14 left: 100px; 15 } 16 17 #div2{ 18 width: 1px; 19 height:300px; 20 background-color: black; 21 position: absolute; 22 left:600px; 23 } 24 </style> 25 <script> 26 /*缓冲运动*/ 27 var timer = null; 28 var speed = 0; 29 function UnUniformModition(obj,iTarget) { 30 clearInterval(timer); 31 timer = setInterval(function () { 32 if (parseInt(getStyle(obj, "left")) == iTarget) { 33 clearInterval(timer); 34 } else { 35 speed = (iTarget - parseInt(getStyle(obj, "left"))) / 10; 36 speed = speed > 0 ? Math.ceil(speed) : Math.floor(speed); 37 obj.style.left = parseInt(getStyle(obj, "left")) + speed + "px"; 38 } 39 }, 30); 40 } 41 /* 用来获取样式的值 obj-对象,name-样式名*/ 42 function getStyle(obj, name) { 43 if (obj.currentStyle) { 44 return obj.currentStyle[name]; 45 } else { 46 return getComputedStyle(obj, false)[name]; 47 } 48 } 49 window.onload = function () { 50 var btn = document.getElementsByTagName("input")[0]; 51 var oDiv = document.getElementsByTagName("div")[0]; 52 btn.onclick = function () { 53 UnUniformModition(oDiv,600); 54 } 55 } 56 </script> 57 </head> 58 <body> 59 <input type="button" value="缓冲运动"> 60 <div></div> 61 <div id="div2"></div> 62 </body> 63 </html>
3. 实现任意值的运动框架v.1
①. 要求:只要简单的实现传入的对象、要变化的属性名和运动的最终目标,便能操作该对象的传入要变花属性的值由大到小的变化到目标大小。(基于缓冲运动)
②. 具体代码:
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="UTF-8"> 5 <title>任意值运动框架version 1.0</title> 6 <style> 7 div { 8 width: 100px; 9 height: 100px; 10 background: green; 11 margin: 10px; 12 } 13 #div2 { 14 border: 1px solid black; 15 } 16 #div3{ 17 -ms-filter: progid:DXImageTransform.Microsoft.Alpha(Opacity=30); 18 filter: progid:DXImageTransform.Microsoft.Alpha(Opacity=30); 19 opacity: 0.3; 20 } 21 </style> 22 <script> 23 /** 24 * 25 * @param obj 操作对象 26 * @param attr 属性名 27 * @param iTarget 目标值 28 */ 29 var timer = null; 30 function startMove(obj, attr, iTarget) { 31 clearInterval(timer); 32 timer = setInterval(function () { 33 var cur = 0; 34 if (attr == ‘opacity‘) { //单独处理透明度问题,因为只有透明度一定要小数 35 cur = parseFloat(getStyle(obj, attr)) * 100;//乘以100是让透明度的0~1之间的度数扩大,方便后面的使用 36 } else { 37 cur = parseInt(getStyle(obj, attr)); 38 } 39 var speed = (iTarget - cur) / 6; //让速度与当前位置离ITarget的距离成正比。除数越大那么缓冲就越大 40 speed = speed > 0 ? Math.ceil(speed) : Math.floor(speed); 41 if (cur == iTarget) { 42 clearInterval(timer); 43 } else { 44 if (attr == ‘opacity‘) { 45 obj.style.filter = ‘alpha(opacity:‘ + (cur + speed) + ‘)‘; 46 obj.style.opacity = (cur + speed) / 100;//把范围重新缩小为0~1之间 47 } else { 48 obj.style[attr] = cur + speed + ‘px‘; 49 } 50 } 51 }, 30); 52 } 53 /** 54 * 获取样式属性的值。代替offset。 55 * @param obj 操作对象 56 * @param name 属性名 57 * @returns {*} 58 */ 59 function getStyle(obj, name) { 60 if (obj.currentStyle) { 61 return obj.currentStyle[name]; 62 } else { 63 return getComputedStyle(obj, false)[name]; 64 } 65 } 66 67 /** 68 * 测试: 69 * 下面的例子只能一个一个进行测试,因为在这里没有设置多对象动作, 70 * 也就是说定时器此时是共有的,如果同时使用这个定时器,会出错。 71 */ 72 window.onload = function () { 73 //测试width的变化(未设置border等其他影响width的属性) 74 var oDiv1 = document.getElementById("div1"); 75 oDiv1.onmouseover = function () { 76 startMove(this, "width", 500); 77 } 78 oDiv1.onmouseout = function () { 79 startMove(this, "width", 100); 80 } 81 //测试width的变化(设置了影响width值得元素) 82 /* 83 var oDiv2 = document.getElementById("div2"); 84 oDiv2.onmouseover = function () { 85 startMove(this, "width", 500); 86 } 87 oDiv2.onmouseout = function () { 88 startMove(this, "width", 100); 89 } 90 */ 91 92 //测试width的变化(设置了影响width值得元素) 93 /* 94 var oDiv3 = document.getElementById("div3"); 95 oDiv3.onmouseover = function () { 96 startMove(this, "opacity", 100); 97 } 98 oDiv3.onmouseout = function () { 99 startMove(this, "opacity", 30); 100 } 101 */ 102 } 103 </script> 104 </head> 105 <body> 106 <div id="div1"></div> 107 <div id="div2"></div> 108 <div id="div3"></div> 109 </body> 110 </html>
4. 改进任意值的运动框架v.2
①. 要求:在ie低版本测试下,透明度的值因为是小数,会出现一些特殊的情况,所以对此进行改进。
②. 具体代码:
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <!-- 2.o版本对透明度的算法进行了改进,加进了round方法 具体内容在39行--> 5 <meta charset="UTF-8"> 6 <title>任意值运动框架version 2.0</title> 7 <style> 8 div { 9 width: 100px; 10 height: 100px; 11 background: green; 12 margin: 10px; 13 } 14 15 #div2 { 16 border: 1px solid black; 17 } 18 #div3{ 19 -ms-filter: progid:DXImageTransform.Microsoft.Alpha(Opacity=30); 20 filter: progid:DXImageTransform.Microsoft.Alpha(Opacity=30); 21 opacity: 0.3; 22 } 23 </style> 24 <script> 25 /** 26 * 27 * @param obj 操作对象 28 * @param attr 属性名 29 * @param iTarget 目标值 30 */ 31 var timer = null; 32 function startMove(obj, attr, iTarget) { 33 clearInterval(timer); 34 timer = setInterval(function () { 35 var cur = 0; 36 if (attr == ‘opacity‘) { //单独处理透明度问题,因为只有透明度一定要小数 37 //因为parseFloat会得到一个带小数的值,因为计算机会有误差,所以会得到一些奇怪的数值。 38 //因此在这里使用round()方法对其值进行四舍五入,去除掉小数 39 cur = Math.round(parseFloat(getStyle(obj, attr)) * 100); 40 } else { 41 cur = parseInt(getStyle(obj, attr)); 42 } 43 var speed = (iTarget - cur) / 6; //让速度与当前位置离ITarget的距离成正比。除数越大那么缓冲就越大 44 //如果attr的值是0~1之间的话,下面这句代码将不可用,如果是0~100之间的话,那么就没问题 45 speed = speed > 0 ? Math.ceil(speed) : Math.floor(speed); 46 if (cur == iTarget) { 47 clearInterval(timer); 48 } else { 49 if (attr == ‘opacity‘) { 50 obj.style.filter = ‘alpha(opacity:‘ + (cur + speed) + ‘)‘; 51 obj.style.opacity = (cur + speed) / 100;//把范围重新缩小为0~1之间 52 } else { 53 obj.style[attr] = cur + speed + ‘px‘; 54 } 55 } 56 }, 30); 57 } 58 /** 59 * 获取样式属性的值。代替offset。 60 * @param obj 操作对象 61 * @param name 属性名 62 * @returns {*} 63 */ 64 function getStyle(obj, name) { 65 if (obj.currentStyle) { 66 return obj.currentStyle[name]; 67 } else { 68 return getComputedStyle(obj, false)[name]; 69 } 70 } 71 72 /** 73 * 测试: 74 * 下面的例子只能一个一个进行测试,因为在这里没有设置多对象动作, 75 * 也就是说定时器此时是共有的,如果同时使用这个定时器,会出错。 76 */ 77 window.onload = function () { 78 //测试width的变化(未设置border等其他影响width的属性) 79 var oDiv1 = document.getElementById("div1"); 80 oDiv1.onmouseover = function () { 81 startMove(this, "width", 500); 82 } 83 oDiv1.onmouseout = function () { 84 startMove(this, "width", 100); 85 } 86 //测试width的变化(设置了影响width值得元素) 87 /* 88 var oDiv2 = document.getElementById("div2"); 89 oDiv2.onmouseover = function () { 90 startMove(this, "width", 500); 91 } 92 oDiv2.onmouseout = function () { 93 startMove(this, "width", 100); 94 } 95 */ 96 97 //测试width的变化(设置了影响width值得元素) 98 /* 99 var oDiv3 = document.getElementById("div3"); 100 oDiv3.onmouseover = function () { 101 startMove(this, "opacity", 100); 102 } 103 oDiv3.onmouseout = function () { 104 startMove(this, "opacity", 30); 105 } 106 */ 107 } 108 </script> 109 </head> 110 <body> 111 <div id="div1"></div> 112 <div id="div2"></div> 113 <div id="div3"></div> 114 </body> 115 </html>
5. 改进任意值的运动框架v.3
①. 要求:在任意值的运动框架的1/2版本中,都没有实现多物体运动,也就是同时多个物体进行运动,在第三版本中加入了多物体运动的功能。
②. 具体代码:
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <!-- 3.o版本 支持多物体运动 下面的三个例子可以同时测试--> 5 <meta charset="UTF-8"> 6 <title>任意值运动框架version 2.0</title> 7 <style> 8 div { 9 width: 100px; 10 height: 100px; 11 background: green; 12 margin: 10px; 13 } 14 15 #div2 { 16 border: 1px solid black; 17 } 18 #div3{ 19 -ms-filter: progid:DXImageTransform.Microsoft.Alpha(Opacity=30); 20 filter: progid:DXImageTransform.Microsoft.Alpha(Opacity=30); 21 opacity: 0.3; 22 } 23 </style> 24 <script> 25 26 27 /** 28 * 29 * @param obj 操作对象 30 * @param attr 属性名 31 * @param iTarget 目标值 32 */ 33 function startMove(obj, attr, iTarget) { 34 clearInterval(obj.timer); 35 obj.timer = setInterval(function () { 36 var cur = 0; 37 if (attr == ‘opacity‘) { //单独处理透明度问题,因为只有透明度一定要小数 38 //因为parseFloat会得到一个带小数的值,因为计算机会有误差,所以会得到一些奇怪的数值。 39 //因此在这里使用round()方法对其值进行四舍五入,去除掉小数 40 cur = Math.round(parseFloat(getStyle(obj, attr)) * 100); 41 } else { 42 cur = parseInt(getStyle(obj, attr)); 43 } 44 var speed = (iTarget - cur) / 6; //让速度与当前位置离ITarget的距离成正比。除数越大那么缓冲就越大 45 //如果attr的值是0~1之间的话,下面这句代码将不可用,如果是0~100之间的话,那么就没问题 46 speed = speed > 0 ? Math.ceil(speed) : Math.floor(speed); 47 if (cur == iTarget) { 48 clearInterval(obj.timer); 49 } else { 50 if (attr == ‘opacity‘) { 51 obj.style.filter = ‘alpha(opacity:‘ + (cur + speed) + ‘)‘; 52 obj.style.opacity = (cur + speed) / 100;//把范围重新缩小为0~1之间 53 } else { 54 obj.style[attr] = cur + speed + ‘px‘; 55 } 56 } 57 }, 30); 58 } 59 60 61 /** 62 * 获取样式属性的值。代替offset。 63 * @param obj 操作对象 64 * @param name 属性名 65 * @returns {*} 66 */ 67 function getStyle(obj, name) { 68 if (obj.currentStyle) { 69 return obj.currentStyle[name]; 70 } else { 71 return getComputedStyle(obj, false)[name]; 72 } 73 } 74 75 /** 76 * 测试: 77 * 下面的例子只能一个一个进行测试,因为在这里没有设置多对象动作, 78 * 也就是说定时器此时是共有的,如果同时使用这个定时器,会出错。 79 */ 80 window.onload = function () { 81 //测试width的变化(未设置border等其他影响width的属性) 82 var oDiv1 = document.getElementById("div1"); 83 oDiv1.timer = null; 84 oDiv1.onmouseover = function () { 85 startMove(this, "width", 500); 86 } 87 oDiv1.onmouseout = function () { 88 startMove(this, "width", 100); 89 } 90 //测试width的变化(设置了影响width值得元素) 91 var oDiv2 = document.getElementById("div2"); 92 oDiv2.timer = null; 93 oDiv2.onmouseover = function () { 94 startMove(this, "width", 500); 95 } 96 oDiv2.onmouseout = function () { 97 startMove(this, "width", 100); 98 } 99 100 //测试opacity的变化 101 var oDiv3 = document.getElementById("div3"); 102 oDiv3.timer = null; 103 oDiv3.onmouseover = function () { 104 startMove(this, "opacity", 100); 105 } 106 oDiv3.onmouseout = function () { 107 startMove(this, "opacity", 30); 108 } 109 } 110 </script> 111 </head> 112 <body> 113 <div id="div1"></div> 114 <div id="div2"></div> 115 <div id="div3"></div> 116 </body> 117 </html>
6. 实现链式运动框架
①. 要求:让其运动可以一个接一个的运行,也就是链式运动。具体效果看测试代码
②. 具体代码:
html代码部分:
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="UTF-8"> 5 <title></title> 6 <style> 7 #div1{ 8 width:100px; 9 height:100px; 10 background: green; 11 } 12 13 </style> 14 15 <script src="链式运动框架.js"></script> 16 <script> 17 window.onload=function(){ 18 var oBtn = document.getElementsByTagName(‘input‘)[0]; 19 var oDiv = document.getElementById(‘div1‘); 20 oBtn.onclick = function(){ 21 startMove(oDiv,‘width‘,500,function(){ 22 startMove(oDiv,‘height‘,500); 23 }); 24 } 25 } 26 </script> 27 </head> 28 <body> 29 <input type="button" value="运动"> 30 31 <div id="div1"></div> 32 </body> 33 </html>
链式运动框架.js代码:
1 /** 2 * 获取计算后的样式 3 * @param obj 对象 4 * @param name 样式名称:width/height等 5 * @returns {*} 6 */ 7 function getStyle(obj, name) { 8 if (obj.currentStyle) { 9 return obj.currentStyle[name]; 10 } else { 11 return getComputedStyle(obj, false)[name]; 12 } 13 } 14 15 function startMove(obj, attr, iTarget, fun) { 16 clearInterval(obj.timer); 17 obj.timer = setInterval(function () { 18 var cur; 19 if (attr == ‘opacity‘) { 20 cur = Math.round(parseFloat(getStyle(obj, attr)) * 100); 21 } else { 22 cur = parseInt(getStyle(obj, attr)); 23 } 24 var speed = (iTarget - cur) / 6; 25 speed = speed > 0 ? Math.ceil(speed) : Math.floor(speed); 26 if (cur == iTarget) { 27 clearInterval(obj.timer); 28 if (fun) { 29 fun(); 30 } 31 } else { 32 if (attr == ‘opacity‘) { 33 obj.style.filter = ‘alpha(opacity:‘ + (cur + speed) + ‘)‘; 34 obj.style.opacity = (cur + speed) / 100;//把范围重新缩小为0~1之间 35 } else { 36 obj.style[attr] = cur + speed + ‘px‘; 37 } 38 } 39 }, 30); 40 }
7. 实现完美运动框架
①. 要求:改进链式运动框架,链式框架没办法实现多个“属性”同时运动!比如width、height同时变化。链式运动框架是没法实现的,所以对此进行改进,也就是最终的运动框架!
②. 具体代码:
html代码部分:
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="UTF-8"> 5 <title></title> 6 <style> 7 #div1{ 8 width:100px; 9 height:100px; 10 background: black; 11 } 12 </style> 13 <script src="完美运动框架.js"></script> 14 <script> 15 window.onload = function(){ 16 var oBtn = document.getElementById(‘btn1‘); 17 var oDiv = document.getElementById(‘div1‘); 18 oBtn.onclick = function(){ 19 startMove(oDiv,{width:500,height:500},function(){ 20 startMove(oDiv,{width:100,height:100}); 21 }); 22 } 23 } 24 25 </script> 26 </head> 27 <body> 28 <input id="btn1" type="button" value="运动"> 29 <div id="div1"></div> 30 </body> 31 </html>
完美运动框架.js代码部分:
1 /** 2 * 获取对象的样式 3 * @param obj 对象 4 * @param name 样式名称 5 */ 6 function getStyle(obj, name) { 7 if (obj.currentStyle) { 8 return obj.currentStyle[name]; 9 } else { 10 return getComputedStyle(obj, false)[name]; 11 } 12 } 13 /** 14 * 完美运动框架实现了链式运动框架无法实现多属性同时运动的情况。如:width/height同时运动 15 * @param obj 16 * @param json 把要运动的属性通过json方式传入。如:{width:500,height:500} 17 * @param fun 执行完动作后,需要调用的方法 18 */ 19 function startMove(obj, json, fun) { 20 clearTimeout(obj.timer); 21 obj.timer = setInterval(function () { 22 var stop = true; //用来判断是否可以关闭定时器 23 for (var item in json) { 24 var cur; 25 if (item == ‘opacity‘) { 26 cur = Math.round(parseFloat(getStyle(obj, item)) * 100); 27 } else { 28 cur = parseInt(getStyle(obj, item)); 29 } 30 var speed = (json[item] - cur) / 6; 31 speed = speed > 0 ? Math.ceil(speed) : Math.floor(speed); 32 if (cur != json[item]) { //判断当前对象的值是否已经达到目标值 33 stop = false; //未达到目标值时,让stop为false。 34 } 35 if (item == ‘opacity‘) { 36 obj.style.filter = ‘alpha(opacity:‘ + (cur + speed) + ‘)‘; 37 obj.style.opacity = (cur + speed) / 100;//把范围重新缩小为0~1之间 38 } else { 39 obj.style[item] = cur + speed + ‘px‘; 40 } 41 if(stop){ 42 clearInterval(obj.timer); 43 if(fun){fun();} 44 } 45 } 46 }, 30); 47 }
声明:这些知识点都来自智能社的视频所得~~
标签:
原文地址:http://www.cnblogs.com/JamKong/p/4996285.html