2015-06-27 54 views
2

我正在循环AngularJS中的一些项目,并使用AngularUI模式询问用户对每个项目的输入。我的问题是,循环完成,所有的模块一次渲染,而无需等待用户。在AngularUI模态打开时暂停执行

如何才能让执行等到模态关闭?

我的代码示例:

var listofitems = somelist; 
// loop through each item 
for (var i in listofitems){ 
    if (listofitems[i].id == presetId){ 
     // ask user confirmation in a modal 
     $scope.selections = {'doThis': doThis, 
          'doThat': doThat} 
     var openModal = function() { 
      var modalInstance = $modal.open({ 
       templateUrl: 'confirmationModal.html', 
       controller: confirmationController, 
       resolve: { 
        selections: function() { 
          return $scope.selections; 
        } 
       } 
      }); 

      modalInstance.result.then(function (selections) { 
       doThis = selections.doThis; 
       if (selections.doThat){ 
        doThis = selections.doThis; 
       } 
      }); 
     } 
     // open the modal 
     openModal();             
     } 
    } 
} 


var confirmationController = function ($scope, $modalInstance, selections) { 

    $scope.selections = selections; 

    $scope.doThis = function() { 
     $scope.selections.doThis = true; 
     $modalInstance.close($scope.selections); 
    }; 

    $scope.doThat = function() { 
     $scope.selections.doThat = true; 
     $modalInstance.close($scope.selections); 
    }; 
}; 

结合@dsfg这里回答是一个Plunkr example。 UI模块不能很好地工作,但您可以在用户提交任何输入之前看到执行完成。

回答

2

你不能只是暂停循环(你可以可以与ES6发电机)。但是你可以改变你迭代数组/对象键的方式。你可以做的是使用函数逐个检查项目,并且只有当前一个完成时才执行下一个“迭代”。承诺很容易。

首先,使openModal返回承诺,然后创建帮助函数checkItems,该函数将为键数组中的每个项目调用。

var openModal = function() { 
    var modalInstance = $modal.open({ 
     templateUrl: 'confirmationModal.html', 
     controller: confirmationController, 
     resolve: { 
      selections: function() { 
       return $scope.selections; 
      } 
     } 
    }); 

    return modalInstance.result.then(function(selections) { 
     doThis = selections.doThis; 
     if (selections.doThat) { 
      doThis = selections.doThis; 
     } 
    }); 
}; 

var listofitems = somelist; 
var keys = Object.keys(listofitems); 

(function checkItems() { 

    // get the first key and remove it from array 
    var key = keys.shift(); 

    if (listofitems[key].id == presetId) { 
     // ask user confirmation in a modal 
     $scope.selections = { 
      'doThis': doThis, 
      'doThat': doThat 
     } 
     // open the modal 
     openModal().then(function() { 
      if (keys.length) { 
       checkItems(); 
      } 
     }); 
    }  
})(); 

在上例中,项目将被检查,直到第一个承诺被拒绝。如果你想检查所有项目,无论承诺状态如何,然后使用

openModal().finally(function() { 
    if (keys.length) { 
     checkItems(); 
    } 
}); 
+0

这真是令我困惑。我确信我正确地遵循了你的例子,而且看起来好像连续打开而不是一次打开的模式。但执行仍然像往常一样继续。日志记录显示'then()'没有被执行,但不知何故'checkItems()'被调用,直到没有更多的键。我会看看我能否得到小提琴。 – Niel

+0

我编辑了我的代码,所以'即使id不匹配,也会调用(keys.length){checkItems();}'。 – Niel

+0

那么,你把你的代码放在不会暂停的循环中。相反,尝试将代码重构为承诺数组,并在所有承诺解决时设置完成标志。 http://plnkr.co/edit/1Eq5kNLOun9kn6PXsXhT?p=preview – dfsq