как заставить функцию возвращать значение в этой ситуации

0

Я хочу использовать ui.confirm следующим образом:

if(ui.confirm('content')){
    //do something
}else{
    //do something
}

ui:

var ui = {
    confirm:function(content){
        //...            
        $(".btn-success").click(function(){
            //when I click this button , ui.confirm return true
        });
        $(".btn-warning").click(function(){
            //when I click this button , ui.confirm return false
        });
    }
}

Хотя у меня есть еще одно недопустимое решение:

var ui = {
    confirm:function(content,callback1,callback2){
        //...

        $(".btn-success").click(function(){
            //execute callback1
        });
        $(".btn-warning").click(function(){
            //execute callback2
        });
    }
}
  • 1
    Вы не можете: идти с моделью асинхронного программирования, а не против. Я рекомендую использовать Promises / A (достаточно jQuery Deferred Objects ), а не "обратные вызовы".
  • 0
    Ну, вы не можете вернуть результат из функции, запускающей асинхронное действие.
Показать ещё 5 комментариев
Теги:

3 ответа

2
Лучший ответ

Вы не можете вернуть значимое значение из confirm потому что нажатие кнопки является асинхронным. Это означает, что нажатие кнопки (возможно) произойдет "в какой-то момент в будущем", но функция должна "немедленно вернуться".

Решение в JavaScript заключается в том, чтобы использовать асинхронную модель программирования через-и-через, как только эта ситуация встречается. Хотя обратные вызовы являются строительными блоками таких асинхронных операций, я предпочитаю использовать Promises, когда могу.

Таким образом, и потому, что dystroy не думает, что я должен ;-), я представлю подход, используя Promises/A (jQuery 1. 9+ Отложенные объекты работают просто отлично и "бесплатно" с jQuery).

function uiConfirm (msg) {
   var action = $.Deferred();

   // Note: On the button clicks the dialog should be closed as a Promise can only
   // be resolved/rejected once; Promises are really good for execution flow
   // management (see 'then'), but are not as general as simple callbacks.
   $(".btn-success").click(function(){
       action.resolve("okay");
   });
   $(".btn-warning").click(function(){
       // Depending upon semantics, this could 'reject' the Promise, but I think
       // it cleaner to just resolve it with a different discriminator value 
       // in this case.
       action.resolve("cancel");
   });

   // uiConfirm returns immediately (before the clicks),
   // but returns a Promise/Deferred that can be resolved (or rejected) later
   // in response to a button click.
   return action;
}

uiConfirm("Do you like Cheese?")
   .then(function (value) {
      // This code runs when a button has been clicked
      alert("Action: " + value);
   });

// This code runs right after uiConfirm returns (before any clicks)
// because uiConfirm is asynchronous or "non-blocking"
  • 1
    Я не думаю, что вы не должны давать обещания, вы должны, они будут играть все более и более важную роль в мире js, я думаю, что OP следует предупредить, что их использование в браузере сегодня - не простой и не естественный путь.
  • 0
    Разве это не легко и не естественно? Вау, это суровые слова борьбы! При этом я полностью согласен с тем, что ОП должен понимать первоклассные функции и обратные вызовы (и иметь возможность использовать их с / без обещаний).
Показать ещё 4 комментария
2

невозможно использовать асинхронные функции

вам нужно сделать что-то вроде:

ui.confirm('content', function() {
    //do something
}, function() {
    //do something
});
1

Вы не можете сделать это именно так. Вам нужно будет предоставить функцию обратного вызова, чтобы "сделать что-то", когда произойдет одно из событий щелчка. Вы не можете "вернуть" из этих событий в ранее выполненное состояние.

var ui = {
    confirm:function(content,callback1,callback2){
        $(".btn-success").click(function(){
            callback1();
        });
        $(".btn-warning").click(function(){
            callback2();
        });
    }
}

ui.confirm('content', function() {
  //do something
  alert("success");
}, function() {
  //do something else
  alert("WARNING");
})

Пример: http://jsfiddle.net/xvbL5/1/

  • 1
    Обычно следует использовать fn() (вместо fn.call() ), если не fn.call() конкретный контекст.
  • 0
    у меня нет выбора, но я делаю это так. спасибо

Ещё вопросы

Сообщество Overcoder
Наверх
Меню