我有一个非常复杂的jquery模板,我ViewModel通过knockout.js框架与基于javascript的数据绑定.其实,我有一个observableArray的ViewModel内的另一对象ViewModel是被绑定到我的模板.
在我的模板中,我有几个DOM元素,当它们的值发生变化时会触发某些事件.例如,我有一个单选按钮设置,当选择一个值时,它会改变选择列表的绑定(以及启用),这反过来通过改变各种可观察的属性来清除文本框的值(以及启用)在我的范围内ViewModel.这些触发器有助于为最终用户指导UX流程,并确保根据需要保存或清除某些值.这一切都很好.
然而...
当我从我的数据库中检索初始数据并填充我的ViewModels,然后将其绑定ViewModels到模板时,触发器就会响应.但是,我不希望由于触发器触发而清除基础可观察值.所以,我设计的是一种初始设置我ViewModel的IsInitialData可观察值的方法true,我的触发器用它来确定是否清除某些值.但是,我希望在false完成模板绑定之后,以及在执行任何用户交互之前将这些属性设置为.
对我来说最有意义的是使用afterRender回调来设置IsInitialData属性false.这样,我的触发器会在绑定初始数据后正常触发.我的afterRender回调函数如下所示:
function resetIsInitialDataAttribute(nodesArray, dataValue) {
alert(dataValue.IsInitialData()); // Displays 'true'
dataValue.IsInitialData(false);
alert(dataValue.IsInitialData()); // Displays 'false'
}
Run Code Online (Sandbox Code Playgroud)
有意思的是,即使设置了值,我也可以在上面的函数中读取该值.
然而...
一旦我在afterRender上面的回调函数中设置了值,我的可观察绑定似乎就会中断.为了测试,我在我的模板中放置了一个div来序列化我的observableArray所以我可以显示我ViewModel的所有值:
<div data-bind="text: ko.toJSON(locationsViewModel.locations)"></div>
Run Code Online (Sandbox Code Playgroud)
如果我没有IsInitialData在afterRender回调中设置属性,那么当我修改已绑定到我ViewModel的可观察属性的DOM元素时,上面的div会立即显示修改后的值.但是,如果我IsInitialData在回调函数中设置我的属性,上面的div不再显示我的任何更改的值ViewModel.
有谁知道为什么ViewModel在afterRender回调函数中设置我的属性会导致问题?IsInitialData ViewModel在初始数据库绑定完成后,是否有其他方法可以设置属性?我查看了jQuery.tmpl文档中的任何类型的回调,我可以使用它在绑定我的数据后发生,但没有发现任何可用的.
您的问题基本上是此问题的一个版本:https://github.com/SteveSanderson/knockout/issues/133.这里也有描述.
在afterRender元素期间实际上还没有在DOM中.在该代码中设置一个可观察的值(或在结合)刚绑定到一个元素将引起dependentObservable在该元素的结合被重新评估使用.它会看到该元素不在DOM中,并认为它应该自行处理.
一个简单的解决方法是设置您的价值afterRender:
setTimeout(function() { dataValue.IsInitialData(false); }, 0);
Run Code Online (Sandbox Code Playgroud)
这将使当前执行完成,此时您的元素将在DOM中.
| 归档时间: |
|
| 查看次数: |
3366 次 |
| 最近记录: |