jQuery1.5.1 animate方法源码阅读


Posted in Javascript onApril 05, 2011
/*7536-7646*/ 
animate: function( prop, speed, easing, callback ) { 
if ( jQuery.isEmptyObject( prop ) ) { 
return this.each( optall.complete ); 
} 
//#7864行this.options.complete.call( this.elem )使得其可以不断的连续执行动画,比如$(‘selector').animate({prop1},speed1).animate({prop2},speed2)这样的动画队列; 
return this[ optall.queue === false ? "each" : "queue" ](function() { 
// XXX 'this' does not always have a nodeName when running the 
// test suite 
var opt = jQuery.extend({}, optall), p, 
isElement = this.nodeType === 1, 
hidden = isElement && jQuery(this).is(":hidden"), 
self = this; 
//要执行动画的prop,prop一般是一个plainObj,形如{key1:value1,key2:value2}; 
for ( p in prop ) { 
//驼峰改写,有些比如magrin-top需要变成驼峰的属性即变成marginTop;见cameCase方法; 
var name = jQuery.camelCase( p ); 
//fix属性;主要是前面camelcase的属性; 
if ( p !== name ) { 
prop[ name ] = prop[ p ]; 
delete prop[ p ]; 
p = name; 
} 
//如果执行$(..).show||$(..).hide;如果这个元素本身是hidden,而动画里面又写hide,直接运行callbacks就可以了; 
if ( prop[p] === "hide" && hidden || prop[p] === "show" && !hidden ) { 
return opt.complete.call(this); 
} 
//如果prop[key]==(height||width)并且是一个dom元素;需要有些特殊的处理; 
if ( isElement && ( p === "height" || p === "width" ) ) { 
// Make sure that nothing sneaks out 
// Record all 3 overflow attributes because IE does not 
// change the overflow attribute when overflowX and 
// overflowY are set to the same value 
opt.overflow = [ this.style.overflow, this.style.overflowX, this.style.overflowY ]; // Set display property to inline-block for height/width 
// animations on inline elements that are having width/height 
// animated 
if ( jQuery.css( this, "display" ) === "inline" && 
jQuery.css( this, "float" ) === "none" ) { 
if ( !jQuery.support.inlineBlockNeedsLayout ) { 
this.style.display = "inline-block"; 
} else { 
var display = defaultDisplay(this.nodeName); 
// inline-level elements accept inline-block; 
// block-level elements need to be inline with layout 
if ( display === "inline" ) { 
this.style.display = "inline-block"; 
} else { 
this.style.display = "inline"; 
this.style.zoom = 1; 
} 
} 
} 
} 
//如果prop[key]是一个数组;只用第一个值prop[p][0]; 
if ( jQuery.isArray( prop[p] ) ) { 
// Create (if needed) and add to specialEasing 
(opt.specialEasing = opt.specialEasing || {})[p] = prop[p][1]; 
prop[p] = prop[p][0]; 
} 
} 
if ( opt.overflow != null ) { 
//如果动画元素的overflow已经被设置的情况下,把它暂时为hidden; 
this.style.overflow = "hidden"; 
} 
//当前动画键值对,其实就是prop; 
opt.curAnim = jQuery.extend({}, prop); 
//这里便是动画的核心了,对每一个prop[key]进行处理; 
jQuery.each( prop, function( name, val ) { 
//获取一个Fx对象;传入的每一个参数都被设置成为这个对象的属性;其中self是指动画元素自身;opt是前面产生的对象; 
var e = new jQuery.fx( self, opt, name ); 
//当执行show||hide操作的时候prop==fxAttrs(参见show||hide方法) 
if ( rfxtypes.test(val) ) { 
e[ val === "toggle" ? hidden ? "show" : "hide" : val ]( prop ); 
} else { 
var parts = rfxnum.exec(val), 
//start保存了初始值,它可能在style,也可能在css中,如果该值==null,undefiend,auto,0等将被设置为0; 
start = e.cur(); 
if ( parts ) { 
//end是指变化量的大小,比如:{left:-=66px},那么end=66; 
var end = parseFloat( parts[2] ), 
//单元运算符,就是px,%;如果是一些不能带单位的,比如z-index,设置为空,否则就设置为px; 
unit = parts[3] || ( jQuery.cssNumber[ name ] ? "" : "px" ); 
// We need to compute starting value 
//如果不是px,比如%,em等等; 
if ( unit !== "px" ) { 
//设置该属性值name为(end || 1) + unit,如果end=0;设置为1;开始值被设置为start = ((end || 1) / e.cur()) * start; 
jQuery.style( self, name, (end || 1) + unit); 
//这里e.cur()和前面的start = e.cur();是不一样的,因为jQuery.style( self, name, (end || 1) + unit)的执行使得start被改变;用于处理end=0的情况;因为e.cur()作为除数,不能为0; 
start = ((end || 1) / e.cur()) * start; 
jQuery.style( self, name, start + unit); 
} 
// If a +=/-= token was provided, we're doing a relative animation 
if ( parts[1] ) { 
//end相应的被设置为运算后的变量值; 
end = ((parts[1] === "-=" ? -1 : 1) * end) + start; 
} 
e.custom( start, end, unit ); 
//如果没有数字化的运算;那么没传入的只能是''; 
} else { 
e.custom( start, val, "" ); 
} 
} 
}); 
// For JS strict compliance 
return true; 
}); 
},
Javascript 相关文章推荐
火狐下table中创建form导致两个table之间出现空白
Sep 02 Javascript
兼容FF和IE的动态table示例自写
Oct 21 Javascript
javascript实现网页屏蔽Backspace事件,输入框不屏蔽
Jul 21 Javascript
JavaScript中this详解
Sep 01 Javascript
JS解决iframe之间通信和自适应高度的问题
Aug 24 Javascript
jQuery事件对象总结
Oct 17 Javascript
关于微信jssdk实现多图片上传的一点心得分享
Dec 13 Javascript
jquery Ajax 全局调用封装实例详解
Jan 16 Javascript
详解webpack 多页面/入口支持&公共组件单独打包
Jun 29 Javascript
Vue 自定义动态组件实例详解
Mar 28 Javascript
浅谈React 服务器端渲染的使用
May 08 Javascript
nvm、nrm、npm 安装和使用详解(小结)
Jan 17 Javascript
jQuery的运行机制和设计理念分析
Apr 05 #Javascript
jQuery JSON的解析方式分享
Apr 05 #Javascript
jQuery 1.5 源码解读 面向中高阶JSER
Apr 05 #Javascript
基于jquery的动态创建表格的插件
Apr 05 #Javascript
基于jquery的合并table相同单元格的插件(精简版)
Apr 05 #Javascript
新鲜出炉的js tips提示效果
Apr 03 #Javascript
使用Firebug对js进行断点调试的图文方法
Apr 02 #Javascript
You might like
php设计模式  Command(命令模式)
2011/06/17 PHP
php设计模式 Decorator(装饰模式)
2011/06/26 PHP
基于php使用memcache存储session的详解
2013/06/25 PHP
php多层数组与对象的转换实例代码
2013/08/05 PHP
老生常谈php 正则中的i,m,s,x,e分别表示什么
2017/03/02 PHP
thinkphp5.0自定义验证规则使用方法
2017/11/16 PHP
超级强大的表单验证
2006/06/26 Javascript
用Jquery.load载入页面后样式没了页面混乱的解决方法
2014/10/20 Javascript
jQuery简单实现日历的方法
2015/05/04 Javascript
JavaScript判断页面加载完之后再执行预定函数的技巧
2016/05/17 Javascript
微信小程序 SocketIO 实例讲解
2016/10/13 Javascript
Angular8基础应用之表单及其验证
2019/08/11 Javascript
微信小程序实现时间进度条功能
2020/11/17 Javascript
js DOM的事件常见操作实例详解
2019/12/16 Javascript
微信小程序实现选择地址省市区三级联动
2020/06/21 Javascript
python encode和decode的妙用
2009/09/02 Python
Python对象的深拷贝和浅拷贝详解
2014/08/25 Python
CentOS 7下安装Python 3.5并与Python2.7兼容并存详解
2017/07/07 Python
python读取与写入csv格式文件的示例代码
2017/12/16 Python
wxpython实现图书管理系统
2018/03/12 Python
Python多继承以及MRO顺序的使用
2019/11/11 Python
在Python中使用MongoEngine操作数据库教程实例
2019/12/03 Python
TensorFlow——Checkpoint为模型添加检查点的实例
2020/01/21 Python
jupyter notebook参数化运行python方式
2020/04/10 Python
python 读取、写入txt文件的示例
2020/09/27 Python
Invicta手表官方商店:百年制表历史的瑞士腕表品牌
2019/09/26 全球购物
大学生自我鉴定
2013/12/08 职场文书
初中三好学生事迹材料
2014/01/13 职场文书
求职信怎么写
2014/05/23 职场文书
学习张林森心得体会
2014/09/10 职场文书
工作证明格式及范本
2014/09/12 职场文书
民事诉讼代理授权委托书范本
2014/10/08 职场文书
介绍信样本
2015/01/31 职场文书
2015年度公共机构节能工作总结
2015/05/26 职场文书
王亚平太空授课观后感
2015/06/12 职场文书
SQL实现LeetCode(177.第N高薪水)
2021/08/04 MySQL