【问题标题】:Suspend bindings in knockout.js 1.2.1在 knockout.js 1.2.1 中暂停绑定
【发布时间】:2023-03-20 10:31:02
【问题描述】:

是否有任何选项可以在淘汰赛中暂停和恢复绑定?

版本:knockout.js 1.2.1

我们对暂停绑定的需求源于以下原因。在某些操作中,我们必须从服务器加载大量数据,例如,多个选择的整个数据都发生了变化,有些表的行是动态添加的等等。

现在在当前场景中,表单与视图模型完全绑定。当我们清除组合并添加每个项目时,视图会刷新,因此会有很大的延迟。如果我有办法暂停绑定,我可以暂停,然后将所有数据加载到视图模型中,然后再次恢复绑定。

【问题讨论】:

    标签: knockout.js knockout-1.2


    【解决方案1】:

    我认为没有办法在 knockout.js 中暂停绑定。没有看到代码很难说,但速度缓慢可能是由于您通过清除 observableArrays 并逐个添加新项目来刷新 observableArrays 造成的。相反,您可以一次刷新整个数组:

    ...
    self.manyItems = ko.observableArray();
    ...
    function refreshItems(newItems){
        self.manyItems(newItems);
    }
    

    【讨论】:

    • 是的!这是一个很好的建议!..我会尝试一下,一旦我在我的代码上检查它,就把它标记为答案!!
    • 我发现这是最好的方法。谢谢!
    【解决方案2】:

    暂停和恢复是可能的:看看由 Ryan Niemeyer 整理的this demo。有关更多背景信息,请参阅他博客上的 this entry

    【讨论】:

      【解决方案3】:

      如果您仍然真的需要暂停订阅,我找到了一种方法可以在计算的 observables 中使用 pauseableComputed 来暂停订阅(想法来自 this site)。我稍微修改了一下,增加了pauseableComputed的读写功能。

      viewModel.myComputedObservable = ko.pauseableComputed(function() {
          return myResult;
      }, viewModel);
      

      对于暂停,您调用 myComputedObservable.pause();,进行所有修改,然后调用 myComputedObservable.resume(); 进行这些修改以触发计算的 observable 中的订阅。

         //wrapper for a computed observable that can pause its subscriptions
              ko.pauseableComputed = function (evaluatorFunction, evaluatorFunctionTarget) {
                  var _cachedValue = "";
                  var _isPaused = ko.observable(false);
      
                  //the computed observable that we will return
                  var result;
                  if (evaluatorFunction.read) {
                      result = ko.computed({
                          read: function() {
                              if (!_isPaused()) {
                                  //call the actual function that was passed in
                                  return evaluatorFunction.read.call(evaluatorFunctionTarget);
                              }
                              return _cachedValue;
                          },
                          write: function(value) {
                              if (!_isPaused()) {
                                  //call the actual function that was passed in
                                  return evaluatorFunction.write.call(evaluatorFunctionTarget, value);
                              }
                              return _cachedValue;
                          }
                      }, evaluatorFunctionTarget);
                  } else {
                      result = ko.computed(function() {
                          if (!_isPaused()) {
                              //call the actual function that was passed in
                              return evaluatorFunction.call(evaluatorFunctionTarget);
                          }
                          return _cachedValue;
                      }, evaluatorFunctionTarget);
                  }
      

      【讨论】: