Backbone UI模型与Handlebars绑定

时间:2014-08-26 20:20:33

标签: javascript backbone.js handlebars.js

我希望使用把手在Backbone应用程序中实现UI绑定。我已经组织了一个简单的例子来演示设计模式但是我注意到它不能很好地扩展,因为它需要在每次模型值改变时渲染整个模板。

有没有办法更新手柄模板中的单个值,而不需要重新渲染整个模板?

HTML:

<script id="entry-template" type="text/x-handlebars-template">
    <div class="box {{#if active}} active {{/if}}">
        <h1>{{title}}</h1>
        <p>{{description}}</p>
        <button class="btn" data-class="toggleActive">Toggle Active</button>
    </div>
</script>

JS:

var TestModel = Backbone.Model.extend({
    defaults: {
        title: "Test",
        description: "This is a test description!",
        active: false
    }
});

var TestView = Backbone.View.extend({
    template: Handlebars.compile($("#entry-template").html()),
    events: {
        "click [data-class='toggleActive']": "toggleActive"
    },
    initialize: function(){
        this.model = new TestModel();
        this.render();
        this.model.on("change", this.renderUI, this);

    },
    render: function(){
        var self = this;
        $('body').html(self.$el.html(self.template(self.model.toJSON())));
    },
    renderUI: function(){
        this.$el.html(this.template(this.model.toJSON()));
    },
    toggleActive: function(){
        var isActive = this.model.get("active");
        this.model.set("active", !isActive);
    }
});

var testView = new TestView();

2 个答案:

答案 0 :(得分:0)

您可以在模型上侦听特定属性更改,并仅更新相应的html元素。

听取模型标题更改(this.listenTothis.on相同,但它允许在调用this.stopListening时将侦听器解除绑定。

this.listenTo(this.model, 'change:title', this.updateTitle);

然后创建updateTitle处理程序。

updateTitle: function(model, value, options)
{
    // this.$ === this.$el.find
    this.$('h1').text(value);
}

答案 1 :(得分:0)

如果您的视图知道在模板中使用元素的每个地方的选择器,您可以执行以下操作,为每个属性更改创建单独的处理程序,并使用您提供的选择器更新相关的HTML

var TestView = Backbone.View.extend({
    template: Handlebars.compile($("#entry-template").html()),
    events: {
        "click [data-class='toggleActive']": "toggleActive"
    },
    modelBindings: {
      // property name: CSS selector of where to update
      title: 'h1',
      description: 'p'
    },
    initialize: function(){
        this.model = new TestModel();
        this.render();

        var me = this;

        function createHandler(selector) {
            return function(model, value) {
                me.$(selector).html(value);
            }                
        }

        for (var modelProp in this.modelBindings) {
            this.model.on("change:" + modelProp, createHandler(this.modelBindings[modelProp]));
        }

    },
    render: function(){
        var self = this;
        $('body').html(self.$el.html(self.template(self.model.toJSON())));
    },

    toggleActive: function(){
        var isActive = this.model.get("active");
        this.model.set("active", !isActive);
    }
});

这仅适用于您要更新HTML的地方,并且在您希望添加类的情况下无法使用。在这种情况下,您可以使用与向元素添加/删除属性相同的概念