【问题标题】:Backbone.js - Uncaught reference errorBackbone.js - 未捕获的引用错误
【发布时间】:2014-06-07 01:40:03
【问题描述】:

不久前,我在 Stackoverflow 上发布了this 问题。基本上,这是我第一次尝试在自己的项目中尝试 Backbone.js,上一篇文章的问题已经解决。

但是现在,当加载此页面时,我可以在 Chrome 控制台窗口中看到以下 javascript 错误。

Uncaught ReferenceError: completed is not defined VM46:6
(anonymous function) VM46:6
_.template.template underscore.js:1308
Backbone.View.extend.render example_addbutton.html:69
Backbone.View.extend.initialize example_addbutton.html:65
Backbone.View backbone.js:1031
child backbone.js:1658
(anonymous function)

花了一个小时排除故障后,我将问题追溯到这部分代码。

<script id="taskTemplate" type="text/template">
    <span class="<%=completed ? 'completed' : 'incomplete' %>"><%= text %></span>
    <button class="complete"></button>
    <button class="delete"></button>
</script>

提示下划线的模板引擎无法理解“完成”变量。

我已经在这里声明了怎么可能呢?

var Tasks = Backbone.Collection.extend({
            model: Task,

            completed: function(){
                return _.filter(this.models, function(model){
                    return model.get('completed');
                });
            },
        });

我做错了什么??

【问题讨论】:

  • 该错误与template方法有关,调用模板函数时应传递completed属性。您发布的代码与抛出的错误无关。
  • 谢谢!再次重读代码后,我意识到在将变量传递给模板引擎进行渲染时,我的主干模型声明与完成属性有问题。我现在正在调查。干杯!
  • 提示:您可以缩短Tasks 集合:由于Backbone 集合中的所有Underscore 集合方法都可用,您可以将completed 减少为return this.filter(...); ;)

标签: javascript jquery backbone.js


【解决方案1】:

终于找到解决办法了。

在网上搜索快速解决方案后,我不得不重构所谓的“教程”代码以使应用程序正常工作。

原来它的 Backbone View 逻辑写得不好,因为它试图渲染主应用程序屏幕以及在代码的一部分中添加的新项目。所以我不得不将它取出并放置在另一个带有适当事件侦听器的 Backbone View Logic 中。

var TasksView = Backbone.View.extend({
    tagName: 'li',

    template: _.template($('#taskTemplate').html()),

    events: { 
         'click .delete': 'delete',
         'click .complete': 'updateStatus',
         'dblclick span': 'edit'
    },

initialize: function(){
          this.model.on('change', this.render, this);
          this.model.on('remove', this.unrender, this);
          this.render();
    },

    render: function(){
          var markup = this.template(this.model.toJSON());
          this.$el.html(markup);
          return this; 
    },

    unrender: function(){
          this.$el.remove();
    },

    delete: function(){
          this.model.destroy();
          this.$el.remove();
    },

    updateStatus: function(){
          this.model.set('completed', !this.model.get('completed'));
    },

    edit: function(){
          var text = prompt('What should we change your task to?', this.model.get('text'))
          this.model.set('text',text);
    },

});

var AppView = Backbone.View.extend({
    el:'#tasks',

    events: {
        'click .add': 'add',
        'click .clear': 'clearCompleted'
    },

    initialize: function(){
        this.collection = new Tasks();
        this.collection.on('add', this.addOneTask, this);
        this.items = this.$el.children('ul');

    },

    add: function(){
        var text = prompt('What do you need to do?');
        var task = new Task({text: text});
        this.collection.add(task);
    },

    render: function(){

    },

    addOneTask: function(task){
        var view = new TasksView({model:task});
        this.items.append(view.render().el);
    },

    clearCompleted: function(){
        var completedTasks = this.collection.completed();
        this.collection.remove(completedTasks);
    }

});

瞧!有效!

【讨论】:

  • 提示:考虑实现TasksView 并在其中封装list 呈现(在集合上监听addremove)。现在称为TasksView,绑定到模型,然后会渲染一个Task(仅在模型上侦听change)。
  • 对不起...不确定我是否完全关注你。在我按照上面的方法修复之前,它不会和它的原始代码一样吗?您能否演示如何简单地为您的代码建模?
猜你喜欢
  • 2015-09-15
  • 1970-01-01
  • 2013-04-05
  • 1970-01-01
  • 2013-10-27
  • 2014-10-11
  • 2018-02-07
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多