JSViews 可观察数组不刷新
JSViews observable array not refreshing
关于 JSViews 的另一个问题,我们深表歉意。我真的很喜欢这个系统,但我偶尔会挣扎。
我有一个简单的模板,它只需要更新数组中的哪些项目以在 select 框更改时显示:
但是,当我更改数据时 "isSelected" 模板未更新为以下内容:
即:
function someClickFunction(sel) {
value = sel.value;
....
la_configure_list[0].isSelected = false;
$.observable(la_configure_list).refresh(
la_configure_list.slice(0)
);
}
如果我把它改成
$.observable(la_configure_list).refresh(
JSON.parse(JSON.stringify(la_configure_list))
);
它更新得很好。
谁能告诉我我做错了什么:
<script id="la-config-overview-list-template" type="text/x-jsrender">
{^{if isSelected}}
<div class="col s12 la_review_list_item" data-index="{{:#index}}">
<div class="card">
<div class="card-content" style="padding: 10px;">
<div class="col s12 m6 l5 xl5">
<h6 style="font-weight: 700;" class="">{{:title}}</h6>
<div>Categories:</div>
<div>
{{for categories}}
<span class="chip">{{:#data}}</span>
{{/for}}
</div>
</div>
<div class="clearfix"></div>
</div>
</div>
</div>
</div>
{{/if}}
我的 html 是
<div id="teacher_la_review_overview_main_wrapper" class="container body-content">
<div class="row" style="margin-bottom: 0;"></div>
</div>
数组是:
la_configure_list = [
{
isSelected:true,
title: "Title",
categories: ["1", "2"....]
},
....
]
我设置了模板:
$.templates("#la-config-overview-list-template").link("#la_review_list_overview_list_wrapper .row", la_configure_list);
我尝试使用 $.view(elem).refresh(),但是由于我更新 isSelected 的点击动作在模板之外,我找不到正确的 "elem" 来使用。
编辑 - 添加实际更新代码:
function CategoryUpdate(sel) {
var catSelected = sel.value;
var catText = sel.options[sel.selectedIndex].text;
if (catSelected !== "-1") {
for (var cs = 0; cs < la_configure_list.length; cs++) {
if (la_configure_list[cs].categories == null) {
la_configure_list[cs].isSelected = false;
continue;
}
var categories = la_configure_list[cs].categories;
var isFound = false;
for (var c = 0; c < categories.length; c++) {
var category = categories[c];
if (category === catText) {
la_configure_list[cs].isSelected = true;
isFound = true;
}
}
if (!isFound) {
la_configure_list[cs].isSelected = false;
}
}
} else {
for (var x = 0; x < la_configure_list.length; x++) {
la_configure_list[x].isSelected = true;
}
}
$.observable(la_configure_list).refresh(
JSON.parse(JSON.stringify(la_configure_list))
);
}
您的数组 la_configure_list.slice(0)
是 la_configure_list
的浅表副本。可观察数组 refresh()
方法用于数组更新——排序、删除或添加项目。它经过优化以避免不必要的更新。事实上,它会分析数组并针对它检测到的任何更改触发移动、插入和删除事件。
你的情况虽然复制了数组,但是是浅拷贝,所以数组项相同,顺序不变。因此,不会触发可观察到的数组更改事件。当您使用 JSON.parse
等时,您正在用克隆副本替换对象,所以现在 refresh()
认为所有项目都已删除,然后添加了新项目。
但是为什么不对 isSelected
可观察属性进行任何更改,如下所示:
function someClickFunction(sel) {
value = sel.value;
...
$.observable(la_configure_list[index]).propertyChange("isSelected", false);
...
}
因为你有可观察的数据链接{^{if isSelected}}
你应该不需要对数组或视图做任何额外的刷新…
关于 JSViews 的另一个问题,我们深表歉意。我真的很喜欢这个系统,但我偶尔会挣扎。
我有一个简单的模板,它只需要更新数组中的哪些项目以在 select 框更改时显示:
但是,当我更改数据时 "isSelected" 模板未更新为以下内容:
即:
function someClickFunction(sel) {
value = sel.value;
....
la_configure_list[0].isSelected = false;
$.observable(la_configure_list).refresh(
la_configure_list.slice(0)
);
}
如果我把它改成
$.observable(la_configure_list).refresh(
JSON.parse(JSON.stringify(la_configure_list))
);
它更新得很好。
谁能告诉我我做错了什么:
<script id="la-config-overview-list-template" type="text/x-jsrender">
{^{if isSelected}}
<div class="col s12 la_review_list_item" data-index="{{:#index}}">
<div class="card">
<div class="card-content" style="padding: 10px;">
<div class="col s12 m6 l5 xl5">
<h6 style="font-weight: 700;" class="">{{:title}}</h6>
<div>Categories:</div>
<div>
{{for categories}}
<span class="chip">{{:#data}}</span>
{{/for}}
</div>
</div>
<div class="clearfix"></div>
</div>
</div>
</div>
</div>
{{/if}}
我的 html 是
<div id="teacher_la_review_overview_main_wrapper" class="container body-content">
<div class="row" style="margin-bottom: 0;"></div>
</div>
数组是:
la_configure_list = [
{
isSelected:true,
title: "Title",
categories: ["1", "2"....]
},
....
]
我设置了模板:
$.templates("#la-config-overview-list-template").link("#la_review_list_overview_list_wrapper .row", la_configure_list);
我尝试使用 $.view(elem).refresh(),但是由于我更新 isSelected 的点击动作在模板之外,我找不到正确的 "elem" 来使用。
编辑 - 添加实际更新代码:
function CategoryUpdate(sel) {
var catSelected = sel.value;
var catText = sel.options[sel.selectedIndex].text;
if (catSelected !== "-1") {
for (var cs = 0; cs < la_configure_list.length; cs++) {
if (la_configure_list[cs].categories == null) {
la_configure_list[cs].isSelected = false;
continue;
}
var categories = la_configure_list[cs].categories;
var isFound = false;
for (var c = 0; c < categories.length; c++) {
var category = categories[c];
if (category === catText) {
la_configure_list[cs].isSelected = true;
isFound = true;
}
}
if (!isFound) {
la_configure_list[cs].isSelected = false;
}
}
} else {
for (var x = 0; x < la_configure_list.length; x++) {
la_configure_list[x].isSelected = true;
}
}
$.observable(la_configure_list).refresh(
JSON.parse(JSON.stringify(la_configure_list))
);
}
您的数组 la_configure_list.slice(0)
是 la_configure_list
的浅表副本。可观察数组 refresh()
方法用于数组更新——排序、删除或添加项目。它经过优化以避免不必要的更新。事实上,它会分析数组并针对它检测到的任何更改触发移动、插入和删除事件。
你的情况虽然复制了数组,但是是浅拷贝,所以数组项相同,顺序不变。因此,不会触发可观察到的数组更改事件。当您使用 JSON.parse
等时,您正在用克隆副本替换对象,所以现在 refresh()
认为所有项目都已删除,然后添加了新项目。
但是为什么不对 isSelected
可观察属性进行任何更改,如下所示:
function someClickFunction(sel) {
value = sel.value;
...
$.observable(la_configure_list[index]).propertyChange("isSelected", false);
...
}
因为你有可观察的数据链接{^{if isSelected}}
你应该不需要对数组或视图做任何额外的刷新…