我想用 selectedItem 和 Itemsource 构建自己的 listView。
我已经开始了一个 jsFiddle http://jsfiddle.net/andersb79/53xRL/1/
您能否帮助我正确地了解我应该如何构建它。我还没有看到这样做的 bindingHanlder。
我想要的是这样的东西。
data-bind="myListView : { items : comments, selectedItem : selectedComment}"
我想用 selectedItem 和 Itemsource 构建自己的 listView。
我已经开始了一个 jsFiddle http://jsfiddle.net/andersb79/53xRL/1/
您能否帮助我正确地了解我应该如何构建它。我还没有看到这样做的 bindingHanlder。
我想要的是这样的东西。
data-bind="myListView : { items : comments, selectedItem : selectedComment}"
在您的自定义绑定中,您需要:
为了清楚起见,我还突出显示了当前选定的项目。
ko.bindingHandlers.myListView = {
update: function(element, valueAccessor) {
var value = ko.utils.unwrapObservable(valueAccessor()),
//get the list of items
items = value.items(),
//get a reference to the selected item observable
selectedItem = value.selectedItem,
//get a jQuery reference to the element
$element = $(element),
//get the currently selected item
currentSelected = selectedItem();
//clear the parent of any existing children
$element.html("");
for (var index = 0; index < items.length; index++) {
(function() {
//get the list of items
var item = ko.utils.unwrapObservable(items[index]),
//create a child element with a click handler
$childElement = $("<li>")
.text(item.id() + " " + item.text())
.click(function() {
//remove selected class on all siblings
$(this).siblings().removeClass("selected");
//add selected class on this item
$(this).addClass("selected");
//set the observable 'selected item' property on the source view model
selectedItem(item);
});
//add the selected class if this item is the current selected item
if (item == currentSelected) {
$childElement.addClass("selected");
}
//add the child to the parent
$element.append($childElement);
})();
}
}
};
这是一个工作示例
注意:由于我使用的是更新评论列表时将使用的方法update
而不是该方法init
更新
如果要使用原始 DIV 的内容作为每个创建项目的模板,则需要两个额外的步骤:
在将创建的元素添加到 DOM 之前将绑定应用到创建的元素
ko.bindingHandlers.myListView = {
init: function(element) {
var $element = $(element),
originalContent = $element.html();
$element.data("original-content", originalContent);
return { controlsDescendantBindings: true }
},
update: function(element, valueAccessor) {
var value = ko.utils.unwrapObservable(valueAccessor()),
//get the list of items
items = value.items(),
//get a reference to the selected item observable
selectedItem = value.selectedItem,
//get a jQuery reference to the element
$element = $(element),
//get the currently selected item
currentSelected = selectedItem(),
//get the current content of the element
elementContent = $element.data("original-content");
$element.html("");
for (var index = 0; index < items.length; index++) {
(function() {
//get the list of items
var item = ko.utils.unwrapObservable(items[index]),
//create a child element with a click handler
$childElement = $(elementContent)
.click(function() {
//remove selected class on all siblings
$(this).siblings().removeClass("selected");
//add selected class on this item
$(this).addClass("selected");
//set the observable 'selected item' property on the source view model
selectedItem(item);
});
ko.applyBindings(item, $childElement[0]);
//add the selected class if this item is the current selected item
if (item == currentSelected) {
$childElement.addClass("selected");
}
//add the child to the parent
$element.append($childElement);
})();
}
}
};
{ controlsDescendantBindings: true }
请注意,我们必须通过从我们的init
方法返回来防止 div 的内容被敲除处理。
这是一个更新的示例