是否有一种更简单的方法可以为不同的选择器链接不同的jQuery操作然后嵌套$ .when?

时间:2014-11-29 20:37:13

标签: javascript jquery jquery-ui

在jQuery中,您可以非常轻松地对同一个选择器执行chain操作,但如果您想为每个操作使用不同的选择器,则需要嵌套$.when,其中包含两个以上很难阅读的操作,维护。

HTML:

<span id='a'>Hello</span>
<span id='b'>world</span>
<span id='c'>!!!</span>

CSS:

span {
    display: none;
}

JS:基于此:how to hide multiple items but only call the handler once?

var d = 500; // duration

// Execute in parallel.
//$('#a').show(d).hide(d);
//$('#b').show(d).hide(d);
//$('#c').show(d).hide(d);


$.when($('#a').fadeIn(d).fadeOut(d)).done(function () {
    $.when($('#b').show(d).hide(d)).done(function () {
        $('#c').slideDown(d).slideUp(d);
    });
});

jsfiddle(旧)

jsfiddle-2

我认为我可以使用queue,但它似乎只适用于同一个选择器。

有没有办法以更易于维护的方式编写它:

伪代码

var myActions = [];
myActions.push(function(){...});
myActions.push(function(){...});
myActions.push(function(){...});
something.executeSequentially(myActions);

编辑:

我对演示进行了更新,使其更难一点。

2 个答案:

答案 0 :(得分:4)

如果你真的不必遇到失败(而且我认为动画几乎不可能),你可以使用以下方法(对@Esailija的称赞,因为这个解决方案基本上是简化的版本his answer):

var chainOfActions = [
    function() { return $('#a').fadeIn(d).fadeOut(d); },
    function() { return $('#b').fadeIn(d).fadeOut(d); },
    function() { return $('#c').fadeIn(d).fadeOut(d); },
];
chainOfActions.reduce(function(curr, next) {
    return curr.then(next);
}, $().promise());

Demo。这里有三个关键点:

  • 操作链中的每个功能都已经返回一个承诺(如果没有,您可以通过返回.promise()调用的结果来宣传它
  • reduce的每个步骤创建一个链,因为提供给then()的每个回调都会创建一个新的承诺
  • 通过提供空承诺作为reduce累加器的初始值来启动整个链。

答案 1 :(得分:1)

修改,更新

var d = 500
, something = {}
, myActions = [];

myActions.push(
function (next) {
    $('#a').fadeIn(d).fadeOut(d, next)
});
myActions.push(
function (next) {
    return $('#b').show(d).hide(d, next)
});
myActions.push(
function () {
    return $('#c').slideDown(d).slideUp(d)
});

something.executeSequentially = function (arr) {
    return $(this).queue("fx", arr);
};
something.executeSequentially(myActions);

jsfiddle http://jsfiddle.net/guest271314/2oawa1zn/