jQuery191源码分析系列(十五)之动画处理_jquery_第1页
jQuery191源码分析系列(十五)之动画处理_jquery_第2页
jQuery191源码分析系列(十五)之动画处理_jquery_第3页
jQuery191源码分析系列(十五)之动画处理_jquery_第4页
jQuery191源码分析系列(十五)之动画处理_jquery_第5页
已阅读5页,还剩5页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、jquery 1. 9. 1源码分析系列(十五)之 动画处理首先需要有队列(queue)的基本知识。见上一章。相关教程:jquery卜的动画处理总结:http:/www. jb51. net/article/42000.htmjquery 1. 9. 1源码分析系列(十五)动画处理之缓动动画核心tween :http:/www. jb51. net/article/75821. htma.动画入口 jquery. fn. animate函数执彳亍流程详解先根据参数调用jquery. speed获取动画相关参数,得到一个类似如下的对 象;并且生成动uui执行函数doanimationoptail

2、 = complete: fnction() .,/动画执行完成的回调duration: 400, /动画执行时长 easing: "swing",/动厕效果 queue: "fx", /动画队列 old: false/fnction() ,var empty 二 jquery. isemptyobject( prop ),optal 1 二 jquery.speed( speed, easing, callback ),doanimation 二 function() 在特征的副本上操作,保证每个特征效果不会被丢失var anim = animatio

3、n( this, jquery. extend( , prop ), optail ); doanimation. finish 二 function() anim. stop( true );;/空动画或完成需要立马解决if ( empty | jquery. _data( this, "finish" ) ) anim. stop( true );;doanimationfinish = doanimation;没有动画正在执行则马上执行动画,否则将动画压入动画队列等待执行/没有动画在执行则马上执行动画,否则将动画压入动画队列等待执行 return empty | op

4、tail.queue 二二二 false ?this. each( doanimation ):this.queue( optail, queue, doanimation );可以看出,真正执行动画的地方是animation( this, jquery. extend( , prop ), optail )函数b. jquery内部函数animation详解animation ( clem, properties, options ) propertics 是要进行动画的 css 特征,options 是动画相关选项complete: function () , duration: 400,

5、easing: undefined, old: false, queue:。首先,初始化一个延时对象,这个延时对象用来处理动画队列。deferred 二 jqucr). deferred(). always ( function() / don't match elem in the :animated selector delete tick, elem;),然后,生成一个每一个时间点(相邻两个时间点的事件间隔默认为13毫秒) 上都会执行的函数tick,这个tick函数会保存在jquery. timers中,然后每次 执行jquery. fx. tick的时候会取出来执行。tick

6、二 function() if ( stopped ) return false;var currenttime = fxnow | createfxnowo,remaining 二 math, max ( 0, animation. starttime + animation, duration - currenttime ),/ archaic crash bug won' t allow us to use 1 - ( 0. 5 | | 0 ) (#12497) temp = remaining / animation, duration | 0,percent = 1 - te

7、mp,index = 0,length = animation. tweens. length;/执行动画效果for ( ; index < length ; index+ ) animation, tweens index .run( percent );/生成进度报告deferred, notifywith( elem, animation, percent, remaining );if ( percent < 1 && length ) return rcmaining; else 动画执行完毕,执行所有延时队列中的函数(包描清除动画相关的数据) defer

8、red, resolvewith( elem, animation );return false;我们看到jquery对动画进度的处理:remaining = math, max( 0, animation. starttime + animation.duration - currcnttimc ) temp 二 rcmaining / animation. duration | 0, percent 二 1 - temp,进度百分比二1 -剩余时间百分比。平常我们是这么处理:假设时间13毫秒执行一次动冊i,当前是第n此执行, 总的动画时长为t。那么进度百分比=(n*13)/t实际上这种算法

9、得到的时间n*13是不准确的,因为epu不只是你一个程序 在执行,时间片分给你的时候往往都比n*13大。而且是一个很不准确的值,导 致动画感觉吋快吋慢,不连贯。而jquery这种方式保证当前的事件点上动画执 行结果的准确性,毕竟事件是最新计算结果。第三,生成动画用的所有特征组成的对象animation (这个对象结构如源码 所示),animation, props中保存的是用户传入的特征(动画最终目标)。animation 二 deferred, promise(elem: elem,props: jquery.extend( , propertics ),opts: jquery. exte

10、nd( true, specialeasing: , options ), originalproperties: properties,originaloptions: options,starttime: fxnow | | createfxnowo,duration: options, duration,tweens:,createtween: function( prop, end ) var tween = jquery. tween( e1em, animation, opts, prop, end,animation. opts. specialeasing prop anima

11、tion, opts, easing );animation, tweens, push( tween );return twocn;,stop: function( gotoend ) var index = 0,/ if we are going to the end, we want to run all the twee ns/ otherwise we skip this partlength 二 gotoend ? emimat ion. twocns. 1cngth : 0;if ( stopped ) return this;stopped = true;for ( ; ind

12、ex < length ; indcx+ ) animation, tweens index .run( 1 );/ resolve when we played the last frame/ otherwise, rejectif ( gotoend ) deferred. resolvewith( elem, animation, gotoend ); else deferred. rejectwith( elem, animation, gotoend );return this;)第四,调用propfilter修正css特征名称以便能被浏览器识别,其中需要 注意的是border

13、width/padding/margin指的不是一个css特征,而是四个(上 下左右)/经过 propfilter, animation, opts. specialeasing 添加了相应的特征 propfilter ( props, animation, opts. specialeasing );举例说明propfilter修正成果。例1, css特征 height: 200 的修正后结果为:props = height: 200 animation. opts. specialeasing 二height: undefined例2:, css特征margin:200的修正结果为: pr

14、ops = marginbottom: 200, marg inleft: 200, marg inright: 200, margintop: 200 animation. opts. specialeasing = marginbottom: undefined, marginleft: undefined, marginright: undefined,margintop: undefined 第五,调用defaultpref订ter做适配处理:比如对height/width的动画要 求display和overflow为特定的值才能有效果;比如对show/hide动画需要对 一大堆css

15、特征值进行动画,并且在函数里就调用createtweens生成缓动动画。/ amimationprefilters0 = defaultprefiltcrfor ( ; index < length ; index+ ) result = animationprefiiters index . call( animation, e1em, props, animation. opts );if ( result ) rcturn result;其中 animat ionpref i 1 ters index 值得函数就是 defaul tpref i 1 ter, defaultpref

16、订ter函数处理有几个比较重要的地方dcfaultprcfiltcr重点1:内联元素中height/width相关动画需要设置 display特征值为 inline-block/ height/width overflow passif ( elem. nodetype 二二二 1 && ( "height" in props | | "width" in props ) /确保没冇什么偷偷岀来/记录3个overflow相关特征,因为ie不能改变overflow特征值,/当overflowx和overflowy设置了相同的值opts, o

17、verflow = style, overflow, style. overflowx, style.overflowy ; /内联元素中height/width相关动画需要设置display特征值为iniine-blockif ( jquery. css( elem, "display" ) = "inline" && jquery. css ( elem, "float")二二二"none" ) /内联元素接受ini ine-block;/块级元素必须内欧在布局上if ( !jquery. su

18、pport inlineblockneedslayout | css defaultdisplay ( elem. nodename ) = "inline" ) style, display 二"inline-block,z; else style. zoom = 1;defaultprefiltcr 重点 2:对于 height/width 动画 overflow 都要设置为 "hidden",动画完成后恢复。这个有利于提高渲染速度。/对于height/width动lulj overflow都要设置为"hidden",动

19、iwj完成后恢复 if ( optsoverflow ) stylc. ovcrflow = "hidden"收缩包装块if ( !jquery. supportshrinkwippblocks ) anim. always (function () style, overflow 二 optsoverflow 0 ; styleovcrflowx 二 optsoverflow 1 ; styleoverflowy = opts.overflow 2 ;);defaultprefiltcr 重点 3: show/hide 动画的特殊处理:show/hide 动画调 用gen

20、fx得到形如props 二height: "hide" marginbottom: "hide" marginleft: "hide" marginright: "hide" margin i op: hide opacity: "hide" paddingbottom: "hide" paddingleft: "hide" paddingright: "hide" paddingtop: h ide width: "hide

21、"需要进行动画处理的特征压入handled列表,并将相应的特征删除,后面会 生成相应的缓动动画。for ( index in props ) value = props index ;/rfxtypes 二 /* (?: toggle! show|hide)$/o 口j 以看到最终只有和 show/hide 的动画才会被饶茹handled中if ( rfxtypes. exec ( value ) ) delete props index ;toggle = toggle | value 二二二"toggle"如果当前节点的状态和指定的状态相同则不需要处理直接进行

22、下一个状 态判断if ( value = ( hidden ? "hide" : "show" ) ) continue;handied, push( index );冇需要执行的动涮处理则进入分支,里而会对各个特征动涮生成缓动动涮 length = handled, length;if ( length ) datashow = jquery. _data( elem, fxshow ) | | jquery. _data( elem, "fxshow", );if ( "hiddert in datashow ) hid

23、den 二 datashow. hidden;/ toggle 需要保存状态-enables . stop(). toggle() to "reverse" if ( toggle ) datashow. hidden = hidden;if ( hidden ) jquery ( elem ). show(); else anim. done (function () jquery ( elem ).hide (););emini. done (function() var prop;jquery. _removedata( e1em, fxshow );for ( pr

24、op in orig ) jquery. style( elem, prop, orig prop ););for ( index = 0 ; index < length ; index+ ) prop 二 handled index ;/生成缓动动训tween = anim. createtween( prop, hidden ? datashow prop : 0 ); orig prop 二 datashow prop | | jquery. style( elem, prop );if ( ! ( prop in datashow ) ) datashow prop = two

25、cn. start;if ( hidden ) tween end = tween start;tween, start = prop = "width" | prop = "height" ? 1 : 0; 第六,生成缓动动画,show/hide在defaultpref订ter函数里面已经处理 (上面的源码)。crcatctwccns( amimation, props );我们来看一看createtweens中具体做了什么,先看一下createtweens之前 的animation对象animation object elem: divmydivj

26、props: objectopts: objectj originalpropert alv/ays : function () createtween: function ( prop, end ) done: function () duration: 400 elem: div#mydiv fail: function () opts: object complete: function () duration: 400old: false queue: "fx" specialeasing: object marginbottom: undefined margin

27、left: undefined marginright: undefined margintop: undefined _proto_: object proto : object originaloptions: object complete: function () duration: 400easing: undefined old: false queue: "fx" _proto_: object originalproperties: objectmargin: 200 proto : object pipe: function ( /* fndone fnf

28、ail fnprogress */ ) progress: function () promise: function ( obj ) props: objectmarginbottom: 200marginleft: 200marginright: 200margintop: 200 oroto : obiectstarttime: 1443512615851 state: function () stop: function ( gotoend ) fndone, fnfail, fnprogress */ ) 然后看一下经过createtweens之后的animation对象的tween

29、s数组变成了 tweens: array4 0: tweeninit easing: r,swing" elem: div#mydiv end: 200 now: 0 options: object complete: function () duration: 400 old: falsequeue: "fx"呼厂gin topprop: specialeasing: object rotounit: mpxfi _proto_: tween 1: tween.init easing: r,swin/ elem: div#mydiv end: 200 now:

30、0 options: object prtjmarfiinkightl unit: "px11 _proto_: tween 2: tween.init easing: "swing" elem: div#mydiv end: 200 now: 0 options: obctc prop: '"marginbottomldflt 0unit: "px" _proto_: tween 3: tween.init easi ng: 11 sw ing" elem: div#mydiv end: 200now: 0 opt

31、ions: object zprop: ° ma r g in left11sthtt-s0unit: "px" _proto_: tween1 ana1"h a将margin分解成了四个属性(margintop/right/bottom/left)并且每个属 性都有口己的动画特征。第七,启动动画计时,定时执行tick /启动动画计时 jquery. fx. timer(jquery. extend( tick, elem: elem,anim: animation,queue: animat ion. opts, queue);最后,将传入的动画结束冋调加入延时队列/从options屮获取冋调函数添加到延吋队列屮 return animation progress( animation. opts, progress ).done( emimation. opts, done, animatio

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论