jQuery技术

jQuery Deferred模块详解

字号+ 作者:H5之家 来源:H5之家 2017-10-28 11:41 我要评论( )

jQuer 1.5版本引入Deferred功能, 为处理事件回调提供了更加强大而灵活的编程模型.本文章向码农们介绍jQuery Deferred模块,感兴趣的码农可以参考一下。

jQuery Deferred模块详解

标签: jqueryDeferred   时间:2016-04-14

jQuer 1.5版本引入Deferred功能, 为处理事件回调提供了更加强大而灵活的编程模型.本文章向码农们介绍jQuery Deferred模块,感兴趣的码农可以参考一下。

什么Deferred 

根据jQuery的官方api文档的描述: jQuery.Deferred()是可链式调用的工具对象, 它能够注册回调函数到一个队列中, 依次调用该队列中的回调函数,并且能够将调链中上一个函数(同步或者异步)的返回状态传递到下一个回调函数中. 

jQuery.Deferred()背后的设计理念来自CommonJS Promises/A , jQuery.Deferred()基于这个理念实现,但并没有完全遵循其设计。其它语言或者框架,例如python和dojo中都有类似的实现。 

下面简单介绍一下 “Promises”的设计思想,目的在于下文介绍jQuery.Deferred()的API时,让大家能有一个理论上的了解。 

Promise, 中文可以理解为愿望,代表单个操作完成的最终结果。一个Promise拥有三种状态:分别是unfulfilled(未满足的)、fulfilled(满足的)、failed(失败的),fulfilled状态和failed状态都可以被监听。一个愿望可以从未满足状态变为满足或者失败状态,一旦一个愿望处于满足或者失败状态,其状态将不可再变化。这种“不可改变”的特性对于一个Promise来说非常的重要,它可以避免Promise的状态监听器修改一个Promise的状态导致别的监听器的行为异常。例如:一个监听fulfilled状态的监听器把Promise的状态修改为failed,那么将触发failed状态的监听器,而如果一个failed状态监听器又把Promise的状态设置为fulfilled,那么又将触发fulfilled状态的监听器,这样将导致死循环。另外一种理解Promise这种特性的方式是把Promise看成是javascript中的primative类型的变量,这种变量可以被传入被调用的函数中,但是不可以被调用函数所改变。 

每一个Promise对象都有一个方法:then(fulfilledHandler, errorHandler, progressHandler),用于监听一个Promise的不同状态。fulfilledHandler用于监听fulfilled事件,errorHandler用于监听failed事件,progressHandler用于监听progress事件。一个Promise不强制实现progress状态的事件监听(jQuery的Deferred就是一个Promise的实现,但没有实现对progress状态事件的处理)。 

then(...)函数中的fulfilledHandler和errorHandler的返回值是一个新的Promise对象, 以便能够链式调用then(...)函数。每一个回调函数在正常情况下返回的是处于fulfilled状态的Promise,如果该回调函数返回错误值,那么返回的Promise状态将会变为failed。 

【疑惑:】以上对于Promise的介绍基本由英文原文翻译而来。感觉英文原文中的描述有点矛盾。例如前面说一个Promise的状态只能从unfulfilled变为fulfilled或者failed,可是又在后面说一个回调函数如果失败,将会把一个Promise从fulfilled状态变为failed状态。还请读者阅读原文 自行甄别。 

幸好jQuery的Promise实现, Deferred,要清晰的多。下面将详细介绍jQuery.Deferred()的API。 
 

Deferred API介绍 

1. 构造函数 

//方式一: var deferred = $.Deferred(); //方式二:使用new操作符号,一般不这样做,显得冗余 var deferred = new $.Deferred(); //方式三:传入一个函数作为回调函数,这个函数会在构造的Deferred对象返回前执行。该函数被传入要返回的Deferred对象作为参数 //在函数内部this指向要返回的Deferred对象。 var dfd = new $.Deferred(function(newDeferred){ this.then(function(){console.log("new deferred");}); });

 

2. deferred.promise() 和 .promise() 

这两个API语法几乎一样,但是有着很大的差别。deferred.promise()是Deferred实例的一个方法,他返回一个Deferred.Promise实例。一个Deferred.Promise对象可以理解为是deferred对象的一个视图,它只包含deferred对象的一组方法,包括:done(),then(),fail(),isResolved(), isRejected(), always(),这些方法只能观察一个deferred的状态,而无法更改deferred对象的内在状态。这非常适合于API的封装。例如一个deferred对象的持有者可以根据自己的需要控制deferred状态的状态(resolved或者rejected),但是可以把这个deferred对象的Promise对象返回给其它的观察者,观察者只能观察状态的变化绑定相应的回调函数,但是无法更改deferred对象的内在状态,从而起到很好的隔离保护作用。 

$(function(){ // var deferred = $.Deferred(); var promise = deferred.promise(); var doSomething = function(promise) { promise.done(function(){ alert('deferred resolved.'); }); }; deferred.resolve(); doSomething(promise); })

deferred.promise()也可以接受一个object参数,此时传入的object将被赋予Promise的方法,并作为结果返回。 

// Existing object var obj = { hello: function( name ) { alert( "Hello " + name ); } }, // Create a Deferred defer = $.Deferred(); // Set object as a promise defer.promise( obj ); // Resolve the deferred defer.resolve( "John" ); // Use the object as a Promise obj.done(function( name ) { this.hello( name ); // will alert "Hello John" }).hello( "Karl" ); // will alert "Hello Karl"

 

接下来介绍.promise()方法。 

首先这不是Deferred实例的方法!该方法是jQuery实例的方法。该方法用于一组类型的动作(例如动画)全部完成后返回一个Promise对象,供事件监听器监听其状态并执行相应的处理函数。 

该方法接受两个可选参数:.promise( [type,] [target] ) 

type:队列的类型,默认值是fx,fx即jQuery对象的动画. 
targetObject :要赋予Promise行为的对象, 

这两个参数是可选的。其中第一个参数(我)目前除了fx还没有找到其他的值类型。因此一般都是用于动画的监控,在动画完成后做一些操作。 

例子:没有动画效果直接返回一个resolved状态的promise对象 

var div = $( "<div />" ); div.promise().done(function( arg1 ) { // 将会被马上触发 alert( this === div && arg1 === div ); });

 

1.本站遵循行业规范,任何转载的稿件都会明确标注作者和来源;2.本站的原创文章,请转载时务必注明文章作者和来源,不尊重原创的行为我们将追究责任;3.作者投稿可能会经我们编辑修改或补充。

相关文章
  • jQuery学习心得总结(必看篇)

    jQuery学习心得总结(必看篇)

    2017-10-28 08:12

  • JQuery 的几个有用的技巧,JQuery有用技巧

    JQuery 的几个有用的技巧,JQuery有用技巧

    2017-10-26 12:28

  • 关于jQuery Mobile学习笔记之列表视图

    关于jQuery Mobile学习笔记之列表视图

    2017-10-26 12:12

  • js与jQuery 获取父窗、子窗的iframe

    js与jQuery 获取父窗、子窗的iframe

    2017-10-25 14:47

网友点评