JS运动中的封装的部分实用函数(框架)总结

JS运动中的封装的部分实用函数(框架)总结

前段时间学习JS运动时做的很实用的几个函数,应该可以称之为小的框架了,现在总结一下。为什么不当时就总结呢?我认为所谓总结不是趁着大脑中还残留着对新知识印象的时候将其写下来,而是过了一段时间之后再回头去看,将其重新拾起,这个时候一般会有对这些新东西的新看法和新的体会,我把这个过程称为“知识的发酵"。对于我来说经过 “发酵”之后的带有自己的见解和体会东西才可以称之为总结。

下面分为几个版本来说,也反映了他们的进化过程,这几个函数功能都是设置元素的属性,而且都是以渐变的,带有缓冲效果的形式来做的,也就是说在变化过程中每次的变化量不是均匀的,而是随着距离目标值的距离而逐渐改变的。

附上封装的getStyle()函数,可以获取元素的非行间样式,由于ie获取非行间元素的方法和其他浏览器不一样,为了避免每次都判断当前浏览器类型,所以封装成一个函数:

function getStyle(obj, attr)//参数:要获取属性的元素,要获取的属性
{
	if(obj.currentStyle)//ie浏览器的获取方法
	{
		return obj.currentStyle[attr];
	}
	else//非ie用的方法
	{
		return getComputedStyle(obj, false)[attr];
	}
}

 

 

 

第一版:

----功能:实现单个特定元素的特定属性值的设置。

----思路:在由现在的值到目标值的过程中要实现带有缓冲渐变效果变化过程应该要设置一个变量来控制每一次的变化量,命名为speed,这个变量的大小应该在定时器每次调用时重新定值,而这个值由当前值和目标值的差来决定(由于当前值在没有到达目标值之前和目标值的差始终是在变化的,所以这个值也是在变化的)。在计算出speed之后将其加到当前值上然后将“新的”当前值赋给目标元素。可以在大脑中模拟一下这个过程,就很好理解了。

对于带有长度属性的元素(比如元素高度height、宽度width、距离left、right、top、bottom等)可以在用parseInt()方法来将元素的值转为数值类型,在设置的时候加上’px’转为字符串就可以了。但是有个比较特殊但是常用的属性—透明度,他是不带有单位的,所以对透明度要特殊处理:获取的透明度的当前值为默认为小数,由于函数第三个参数为整数值,所以将其转换为0~100的整数值进行处理比较方便(取出其值后*100)。在将“新的”当前值赋给目标元素的时候以透明度的方式来做就可以了。最后,若到达了目标值,就关闭定时器。其他细节在代码注释中说:

function changeTo(obj,attr,target) {
	clearInterval(obj.timer);//先将以前的定时器关闭,否则每调用一次这个函数就会增加一个定时器,元素的动画效果变化越来越快
	var nowValue = 0 ;
	var speed = 0 ;
	obj.timer = setInterval(function(){
		//处理不透明度的方法中要四舍五入,便于后面使用
		nowValue = (attr == 'opacity')?Math.round(parseFloat(getStyle(obj,'opacity'))*100):parseInt(getStyle(obj,attr));
		speed = (target>nowValue)?Math.ceil((target-nowValue)/10):Math.floor((target-nowValue)/10);//speed值为负时注意向下取整
		nowValue+=speed;
		if (attr == 'opacity') {//
			obj.style.filter = 'alpha(opacity:'+ nowValue +')';
			obj.style.opacity = nowValue/100;//非ie设置透明度方法
		}else{
			obj.style[attr] = nowValue + 'px';//变量做参数用方括号括起来,点号“.”调用不生效
		}
		if (nowValue == target) {//判断是否到目标值,若到了关闭定时器
			clearInterval(obj.timer);
		}
	},30);
}<span style="font-family: Arial, Helvetica, sans-serif; background-color: rgb(255, 255, 255);"> </span>

第二版:

----功能:实现多个元素的特定属性值的设置。

----思路:上面的函数每次只能实现一个元素的一个属性的设置,有些时候够用了,但是在其他很多时候的需求是要求这个元素的多个属性同时发生变化的,比如元素的位置和大小同时发生变化,大小和透明度同时发生变化等等。这个时候该怎么处理呢?总体思路是在这个函数中每一次定时器调用时改变所有属性,这就需要用到循环了,但是函数参数怎么写呢?这个时候就需要用到Json了,使用Json之后参数的问题解决了,循环的问题也解决了。

但是问题又出现了--可能有的属性值会先到达目标,有些属性值后到达目标,总不能在一个属性到达目标值后就关闭定时器吧,定时器应该在所有属性值都设置完成之后再关闭。怎么解决这个问题呢?---设置一个变量就可以了:在循环开始之前设置一个布尔类型的变量isFinished,初始值设置为true,然后在循环中判断每个属性是否到达目标值,若没有到达则将isFinished设置为false,这样一来,只要有一个属性没有到达目标值,那么isFinished就是false;如果所有属性都到达了目标值,那isFinished值就不会被更改,则依然为true。最后在循环结束时,如果isFinished为true,则关闭定时器。这个方法经常被采用,怎么理解并且记住这个方法呢?可以想象有一个队列,给队列中每个人都布置不同的任务,每个任务需要的时间不同,所以队列里的人肯定不会同时完成,那么怎么判断所有人都完成了呢?那就设置一个定时器,定时器开始工作时定义一个初始值为true的布尔型变量,之后就挨个问队列中的人是否完成了任务,完成任务的人什么也不做,而没有完成任务的人,就让他大喊一声“Oh,
no!!!”然后把这个变量狠狠的置为false,等到定时器这次的工作结束之前再看看这个布尔类型的变量,如果值还是true,那么就说明没人没有完成,也就是所有人都完成了,就可以解散(关闭定时器)了。

其他细节在代码注释中说:

 

function changeNow(obj,json) {//参数:目标元素,Json
	clearInterval(obj.timer);//先将以前的定时器关闭,否则每调用一次这个函数就会增加一个定时器,元素的动画效果变化越来越快
	var nowValue = 0;
	var speed = 0;

	obj.timer = setInterval(function(){
		for(var i in json){
			var attr = i;
			var target = json[i];
			//处理不透明度的方法中要四舍五入,便于后面使用
			nowValue = (attr == 'opacity')?Math.round(parseFloat(getStyle(obj,'opacity'))*100):parseInt(getStyle(obj,attr));
			//speed值为负时注意向下取整
			speed = (target - nowValue) > 0 ? Math.ceil((target - nowValue)/10) : Math.floor((target - nowValue)/10);
			nowValue += speed;//累加现在当前值,下面赋值给元素的属性
			if (nowValue != target) {//有一个元素没有到目标就将isFinished置为false
				isFinished = false;
			}

			if (attr == 'opacity') {
				obj.style.filter = 'alpha(opacity:'+ nowValue +')';
				obj.style.opacity = nowValue / 100;//非ie设置透明度为小数
			}
			else{
				obj.style[attr] = nowValue + 'px';//变量做参数用方括号括起来,点号“.”调用不生效
			}
		}
		if (isFinished) {//如果所有属性值都已经设置为了目标值
			clearInterval(obj.timer);
		}
	},30);
}

第三版:链式调用

----功能:所谓的链式函数,就是在一个函数完成之后开始另一个函数。

----思路:在函数中调用下一个函数就可以,关键在于何时调用,就上面的第二版的函数来说应该是在所有动作完成之后再调用。只需要在第二版函数中增加一个参数,如果isFinished==true,则调用这个函数。为了增加灵活性,增加一个判断—--如果这个函数存在,则调用。说的有点多,直接上关键代码把。

function changeNow(obj,json,fn) {

     ……//这里的代码和第二版函数的相同

if (flag) {

              clearInterval(obj.timer);

              if(fn) {fn();}//增加的代码,如果这个函数存在,则调用

         }

}

 完整代码:

function changeNow(obj,json,fn) {//参数:目标元素,Json,接下来要执行的函数
	clearInterval(obj.timer);//先将以前的定时器关闭,否则每调用一次这个函数就会增加一个定时器,元素的动画效果变化越来越快
	var nowValue = 0;
	var speed = 0;

	obj.timer = setInterval(function(){
		var isFinished = true;//每次循环开始前设置标记,用来判断是否已经设置完成全部属性
		for(var i in json){
			var attr = i;
			var target = json[i];
			//处理不透明度的方法中要四舍五入,便于后面使用
			nowValue = (attr == 'opacity')?Math.round(parseFloat(getStyle(obj,'opacity'))*100):parseInt(getStyle(obj,attr));
			//speed值为负时注意向下取整
			speed = (target - nowValue) > 0 ? Math.ceil((target - nowValue)/10) : Math.floor((target - nowValue)/10);
			nowValue += speed;//累加现在当前值,下面赋值给元素的属性
			if (nowValue != target) {//有一个元素没有到目标就将isFinished置为false
				isFinished = false;
			}

			if (attr == 'opacity') {
				obj.style.filter = 'alpha(opacity:'+ nowValue +')';
				obj.style.opacity = nowValue / 100;//非ie设置透明度为小数
			}
			else{
				obj.style[attr] = nowValue + 'px';//变量做参数用方括号括起来,点号“.”调用不生效
			}
		}
		if (isFinished) {//如果所有属性值都设置为了目标值
			clearInterval(obj.timer);
<span style="white-space:pre">			</span>/*
<span style="white-space:pre">				</span>增加的代码
<span style="white-space:pre">			</span>*/
			if (fn) {fn();}//fn函数是不一定存在的,只有存在时才调用
		}
	},30);
}

以上。写出这些函数是用来做东西的,后面就有用这些函数做出的效果。

时间: 2024-10-01 06:18:36

JS运动中的封装的部分实用函数(框架)总结的相关文章

JS运动缓冲的封装函数

之前经常写运动函数,要写好多好多,后来想办法封装起来.(运动缓冲). 1 /* 2 物体多属性同时运动的函数 3 obj:运动的物体 4 oTarget:对象,属性名为运动的样式名,属性值为样式运动的终点值 5 ratio:速度的系数 6 */ 7 function bufferMove(obj, oTarget, fn,ratio = 8) { 8 clearInterval(obj.iTimer); 9 obj.iTimer = setInterval(function () { 10 //

对于js运动中产生的问题

1.不同的对象调用同一个定时器情况,则需要将定时器的名称定为该对象的一个属性来进行运用. 例: <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> <style> #div1{ width: 100px; height: 200px; background-color:

js学习中,写的一些小函数

/* my js的库 */ //随机产生n个从x-y中不重复的整数 function check(n,x,y){ var num=[]; for(var i=0;i<n;i++){ num[i]=Math.ceil(Math.random()*(y-x)+x); for(var j=0;j<num.length-1;j++){ if(num[j]===num[++j]){ num.splice(j,1); n++; } } } //alert(num.length); return num;

简单的JS运动封装实例---侧栏分享到

1 <!DOCTYPE HTML> 2 <html> 3 <head> 4 <meta http-equiv="Content-Type" content="text/html; charset=utf-8"> 5 <title>无标题文档</title> 6 <style> 7 #div1 {width: 100px; height: 200px; background: red;

JS运动从入门到兴奋1

hello,我是沐晴,一个充满了才华,却靠了照骗走江湖的前端妹子.在这个充满PS的年代,这你们都信,哈哈,废话不多说,今天要分享的是关注JS运动的知识.楼主一直认为,不管学习什么,核心思想才是王道,掌握了思想,不管需求怎么改变,我们都能把它玩弄于股掌之中...下面我们就由浅入深走进运动的世界吧. 首先来看最基础的运动:单个物体向右匀速运动到某一点停止      例子:一个按钮,一个div,点击按钮,让div向右运动到某一个位置暂停 // 原理: 1 获取物体当前的位置 oDiv.offsetle

JS运动1 (转)

JS运动从入门到兴奋1 http://www.cnblogs.com/moqing/p/5666476.html hello,我是沐晴,一个充满了才华,却靠了照骗走江湖的前端妹子.在这个充满PS的年代,这你们都信,哈哈,废话不多说,今天要分享的是关注JS运动 的知识.楼主一直认为,不管学习什么,核心思想才是王道,掌握了思想,不管需求怎么改变,我们都能把它玩弄于股掌之中...下面我们就进入运动的世界吧. 首先来看最基础的运动:单个物体向右匀速运动到某一点停止      例子:一个按钮,一个div,

JS运动从入门到精髓!哈哈

首先来看最基础的运动:单个物体向右匀速运动到某一点停止      例子:一个按钮,一个div,点击按钮,让div向右运动到某一个位置暂停 // 原理: 1 获取物体当前的位置 oDiv.offsetleft // 2 利用定时器,每隔一定的时间,让物体位置增加相同的距离(10px). // 3 判断物体是否移动到指定位置(500px),如果到达,就清除定时器 var oBtn = document.getElementById('btn'); var oDiv = document.getEle

我自己的Javascript 库,封装了一些常用函数 Kingwell.js

我自己的Javascript 库,封装了一些常用函数 Kingwell.js 博客分类: Javascript javascript 库javascript库 现在Javascript库海量,流行的也多,比如jQuery,YUI等,虽然功能强大,但也是不万能的,功能不可能涉及方方面面,自己写一个的JS库是对这些的补充,很多也比较实用,把应用到项目中中去也比较方面,这也是对工作的一些积累,也加深对知识的理解. 2012-6-20更新,添加设置Cookie,获取Cookie,删除Cookie方法.很

js运动动画

今天简单的学了一下js运动动画,再此感谢慕课网的这位老师http://www.imooc.com/view/167,讲的很不错. 下面是我整理出来的结果. 知识点一:速度动画. 1.首先第一步实现速度运动动画,封装一个函数,用到的知识是setInterval(function(){ oDiv.style.left=oDiv.offsetLeft+10+"px"; },30). 对于这里为什么要用到offsetLeft,我特意百度了一下,http://www.cnblogs.com/wo