0

我想在制作同步 ajax 时显示一个等待对话框。我使用智能向导,在一步一步之间进行切换,我必须验证一些数据才能做到这一点,我必须一个接一个地进行 3 个 ajax 调用,完成后我想显示一个等待对话框。这就是我正在做的事情。

if (indexes.fromStep==1) {  
    res=false;  
    var validatorResult = validator.checkAll($("#install_modbus_form"))
    if (validatorResult) {          
        $("#modal_loader").modal()      
        $.ajax({
            type: "post",
            url: url1, 
            async: false,            
            dataType: "json",   
            data:{
                data
            },     
            success: function(response)
            { 
                if (response.success) 
                {
                    $.ajax({
                        type: "post",
                        url: url2, 
                        async: false,            
                        dataType: "json",   
                        data:{
                            data
                        },     
                        success: function(response)
                        { 
                            if (response.success) 
                            {
                                $.ajax({
                                    type: "post",
                                    url: url3, 
                                    async: false,            
                                    dataType: "json",   
                                    data:{
                                        data
                                    },     
                                    success: function(response)
                                    { 
                                        if (response.success) 
                                        {
                                            //make magic here
                                            res=true;
                                        }
                                    },
                                    failure:function() 
                                    {
                                        waitingDialog.hide()
                                        res=false
                                    },
                                    error:function(a,b,c) {
                                        waitingDialog.hide()
                                        res=false
                                    }
                                )
                            }
                        },
                        failure:function() 
                        {
                            waitingDialog.hide()
                            res=false
                        },
                        error:function(a,b,c) {
                            waitingDialog.hide()
                            res=false
                        }
                    )
                }
            },
            failure:function() 
            {
                waitingDialog.hide()
                res=false
            },
            error:function(a,b,c) {
                waitingDialog.hide()
                res=false
            }
        )
        $("#modal_loader").modal('hide')        
        return res;//if true change step 
    }
}

我尝试使用 beforeSend 来显示等待对话框,我也尝试使用 setTimeout 但未显示等待对话框并且智能向导不前进

希望你能提供帮助,我是 jquery 的新手。

抱歉英语不好

4

1 回答 1

0

假设您使用的是jQuery-Smart-Wizard,解决方案在于:

  • onLeaveStep您的事件处理程序的构造,和(或包括)
  • 问题中显示的验证代码的修改版本。

幸运的是,尽管插件本身并不支持异步,但实现起来相当简单。本质上,您需要做的是:

  • falseonLeaveStep回调中返回,
  • 建立一个在成功验证时履行或在失败时拒绝的承诺,
  • .smartWizard('goForward')从 promise 的成功处理程序调用,
  • .smartWizard('showError')从 promise 的错误处理程序中调用。

基于 smartWizard 的 ReadMe.md,这是一个执行同步和异步验证的框架:

$(document).ready(function() {
    var waitingDialog = $('#whatever'); // ???

    // Smart Wizard         
    $('#wizard').smartWizard({
        onLeaveStep: leaveAStepCallback,
        onFinish: onFinishCallback
    });

    function leaveAStepCallback(obj, context) {
        alert("Leaving step " + context.fromStep + " to go to step " + context.toStep);
        var returnValue;
        switch(context.fromStep) {
            case 1: // asynchronous
                if (validator.checkAll($("#install_modbus_form"))) {
                    $("#modal_loader").modal();
                    waitingDialog.show();
                    validateStep1() // validateStep1() returns a promise
                    .then(function() {
                        // You will arrive here only if all three ajax calls were successful and all three responded with a truthy `response.success`.
                        $('#wizard').smartWizard('goForward'); // advance to next step
                    }, function(e) {
                        // You will arrive here on validation failure
                        $('#wizard').smartWizard('showError', e.message); // something went wrong
                    }).always(function() {
                        // You will arrive here on validation success or failure
                        waitingDialog.hide(); // the waiting is over
                        $("#modal_loader").modal('hide'); // ???
                    });
                } else {
                    $('#wizard').smartWizard('showError', 'validator.checkAll() failed');
                }
                returnValue = false; // *must* return false to remain at step 1. If validation is successful, `.smartWizard('goForward')` will be executed later (see above).
            break;
            case 2: // synchronous
                returnValue = validateStep2(); // validateStep2() returns true of false
            break;
            case 3:
                ...
            break;
        }
        return returnValue; // true or false
    }

    // And here's the all-important `validateStep1()` :
    function validateStep1() {
        var sequence = [
            { url: 'url/1', data: {...} },
            { url: 'url/2', data: {...} },
            { url: 'url/3', data: {...} }
        ];

        return sequence.reduce(function(promise, item, i) {
            return promise.then(function() {
                return $.ajax({
                    'type': 'post',
                    'url': item.url,
                    'dataType': 'json',
                    'data': item.data
                }).then(function(response, textStatus, jqXHR) {
                    return response.success ? response : $.Deferred().reject(jqXHR, 'response.success not truthy at validation stage ' + i); // note: need to mimic jQuery.ajax's error signature.
                });
            });
        }, $.when()) // starter promise for the reduction
        .then(null, function(jqXHR, textStatus, errorThrown) {
            return $.Deferred().reject(new Error(textStatus || errorThrown));
        });
    }

    function validateStep2() {
        // if validation here is synchronous, then return true of false
        if(....) {
            return true;
        } else {
            return false;
        }
    }
    function validateStep3() {
        ...
    }
    // etc.

    function onFinishCallback(objs, context) {
        if(validateAllSteps()) {
            $('form').submit();
        }
    }

    function validateAllSteps() {
        var isStepValid = true;
        // all step validation logic     
        return isStepValid;
    }          
});

备注:

  • 分支逻辑在onLeaveStep回调中。
  • validateStep1()使用链式承诺模式对三个 ajax 调用进行排序。
  • 如果validateAllSteps()需要重复第 1 步验证,那么您将需要validateStep1().then(...)再次调用,或者从之前缓存的 Promise 中链接。

正如你所看到的,上面的一些方面是不完整的,所以还有一些工作要做。

于 2017-08-02T09:22:59.667 回答