【问题标题】:Knockout.js 2.2.1 can't find observable arrayKnockout.js 2.2.1 找不到可观察数组
【发布时间】:2013-02-03 13:15:11
【问题描述】:

不确定这里出了什么问题,但 KnockoutJS 在查找我的 MasterViewModel 中的可观察数组时遇到了一些问题。使用 2.2.1 和 jQuery 1.8.x 以及不是我的第一个 KJS 应用程序。这里是:

初始化

$(function() {
  window.vm = new MasterViewModel();
  ko.applyBindings(vm);
});

视图模型

function MasterViewModel(data) {
  var self = this;
  self.currentAppView = ko.observable();

  // Users
  self.userList = ko.observableArray([]);
  self.templateListGetter = ko.computed(function() {
    $.getJSON("/user/list"), function(data) {
      var mapped = $.map(data, function(item) { return new userModel(item) });
      self.userList(mapped);
    };
  });

  self.goToAppView = function(appView) { 
    location.hash = '!/' + appView;
  };    
  Sammy(function() {
      this.get('#!/:appView', function() {
        self.currentAppView(this.params.appView);
        $('.appview').hide();
        ko.applyBindings(new window[this.params.appView+'VM']());
      });
      this.notFound = function(){
        location.hash = "!/dashboard";
      }
      //this.raise_errors = true;
  }).run();
}

观点

  <table class="table table-bordered table-striped">
    <tbody data-bind="foreach: userList">
      <tr>
        <td data-bind="text: guid"></td>
        <td data-bind="text: firstName"></td>
        <td data-bind="text: lastName"></td>
        <td data-bind="text: email"></td>
        <td data-bind="text: updated"></td>
        <td data-bind="text: suspended"></td>
      </tr>
    </tbody>
  </table> 

我正在加载一个简单的表格

即使在仔细检查了几件事(例如将defer="defer" 添加到我的 JS 标记并确保 userList 存在之后,它也无法找到 observableArray。它给出了错误:

Message: ReferenceError: userList is not defined;
Bindings value: foreach: userList Error {} 

有人知道发生了什么吗?

更新

对于那些想知道每次哈希更改时调用什么的人:

function usersVM() {
    // Data
    var self = this;
    // Behaviours
    $('#users').show();
}

【问题讨论】:

    标签: javascript mvvm knockout.js knockout-2.0


    【解决方案1】:

    您似乎正在使用未定义的视图模型初始化剔除?

    ko.applyBindings(new window[this.params.appView+'VM']());,但您的实际视图模型是window.vm。区分大小写ftw。此外,窗口上的视图模型已经创建/初始化。所以你不需要new 运算符。

    因此,将 applyBindings 行更改为

    ko.applyBindings(window[this.params.appView+'vm']());

    更新答案:通过海报

    没有必要在每次路由更改时都继续运行ko.applyBindings,因为它已经在页面加载时应用了绑定。于是 Sammy.js 改成了:

      Sammy(function() {
          this.get('#!/:appView', function() {
            self.currentAppView(this.params.appView);
            $('.appview').hide();
            window[this.params.appView+'Route']();
          });
          this.notFound = function(){
            location.hash = "!/dashboard";
          }
          //this.raise_errors = true;
      }).run();
    

    看起来ko.computed 或对window.vm.getUserList() 的常规函数​​调用没有正常运行,但这将被保存用于其他问题。

    function usersRoute() {
        // Data
        var self = this;
        // Behaviours
        $('#users').show();
        window.vm.getUserList();
    }
    

    【讨论】:

    • 嗯,遗憾的是没有解决问题。抱歉,我为 VM 参数选择了一个糟糕的名称。它实际上引用了“页面”更改时要执行的不同功能。更新问题。
    • 好吧,你说的有一部分是对的,但看起来有两个问题。我将用更改的内容编辑您的答案;)
    • 好的。我刚刚注意到的另一件事是您可能正在用子 VM 覆盖 MasterVM。我很高兴看到实际问题是什么!
    猜你喜欢
    • 2019-12-16
    • 2018-11-26
    • 1970-01-01
    • 1970-01-01
    • 2013-07-28
    • 1970-01-01
    • 2012-06-30
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多