(重新)在更改事件处理程序中渲染主干视图不起作用
Posted
技术标签:
【中文标题】(重新)在更改事件处理程序中渲染主干视图不起作用【英文标题】:(Re)rendering Backbone view in change event handler does not work 【发布时间】:2016-04-03 00:47:16 【问题描述】:我有两个表单元素,都是通过backbone.stickit 进行双向数据绑定的。 第二个表单元素 (#input) 只是装饰物 - 用于显示它确实有效。
这个想法是,每次下拉菜单 (#select) 中的选项发生更改时,我的视图都会被(重新)渲染。
我试图通过捕捉 #select 的“更改”事件并调用 this.render() 来(重新)渲染视图来实现这一点。
显然这行不通。所选选项没有保存回模型中,我不明白为什么。
我不是在寻找解决方案,而不是解释,为什么下面的代码不起作用。解决方案(如:对我有用)是小提琴的一部分 - 已注释掉。
html:
<script type="text/template" id="tpl">
<h1>Hello <%= select %></h1>
<select id="select">
</select>
<p>Select:
<%= select %>
</p>
<hr>
<input type="text" id="input">
<p>Input:
<%= input %>
</p>
</script>
<div id="ctr"></div>
Foo = Backbone.Model.extend(
defaults:
select: "",
input: "",
);
FooView = Backbone.View.extend(
el: '#ctr',
template: _.template($('#tpl').html()),
initialize()
this.model.bind('change', function()
console.log("model change:");
console.log(this.model.get('select'));
console.log(this.model.get('input'));
, this);
//this.model.bind('change:select', function() this.render(); , this); // <--------------------- WORKS
,
render: function()
this.$el.html(this.template(this.model.toJSON()));
this.stickit();
return this;
,
events:
'change #select': function(ev)
console.log('change event triggered:');
console.log(this.model.get('select'));
console.log(this.model.get('input'));
this.render(); // <--------------------- DOES NOT WORK - WHY?
,
/* 'click #render': function(ev)
console.log('render event triggered:');
console.log(this.model.get('select'));
console.log(this.model.get('input'));
this.render();
*/
,
bindings:
'#input': 'input',
'#select':
observe: 'select',
selectOptions:
collection: function()
return [
value: '1',
label: 'Foo'
,
value: '2',
label: 'Bar'
,
value: '3',
label: 'Blub'
]
,
,
);
new FooView(
model: new Foo()
).render();
https://jsfiddle.net/r7vL9u07/9/
【问题讨论】:
【参考方案1】:从change #select
事件处理程序中调用this.render()
不起作用的原因是因为您正在破坏Backbone.stickit 为您提供的双向数据绑定。流程如下所示:
change #select
处理程序触发并调用this.render()
。
render
使用未选择 option
的新选择菜单重新填充 #ctr
。
Backbone.stickit 响应更改为 #select
。
Backbone.stickit 尝试获取#select
的值,但由于它不包含选定的option
,因此值为undefined
。
Backbone.sticket 将model
的select
属性设置为undefined
。
如果您将this.render()
调用移动到model
的change:select
处理程序中,它起作用的原因是因为Backbone.stickit 能够在不改变DOM 的情况下正确更新模型。
【讨论】:
非常感谢您的解释。那么通过 model.bind('change:select') 这样做是正确的方法吗? 如果您想在选择更改时重新渲染,那么可以。 非常感谢朋友!以上是关于(重新)在更改事件处理程序中渲染主干视图不起作用的主要内容,如果未能解决你的问题,请参考以下文章