项目选择使用KnockoutJS的MVC视图
我正在尝试实现一个通用的ASP.net MVC视图。 UI应显示从服务器加载数据(基本上是字符串列表)的可用和选定项目的列表。 用户可以对列表进行更改,即可以从可用项目列表中选择新项目,也可以从选定列表中删除项目。
我想使用KnockoutJS来利用绑定。
我设法完成所有工作,除了在可用列表中初始化视图时将所选项目显示为已选中。 例如,如此处所示
我尝试了各种选项( 使用模板(最接近我想要实现的) , Checked attr , 可能的选项 ),问题是如果我设法显示项目检查了一些其他function中断。 尝试定义一个模板,但无法让它在我的情况下工作。
HTML:
JS:
var initialData = [ { availableItems: [ { title: "US", isSelected: true }, { title: "Canada", isSelected: false }, { title: "India", isSelected: false }] }, { selectedItems: [ { "title": "US" }, { "title": "Canada" } ] } ]; function Item(titleText, isSelected) { this.title = ko.observable(titleText); this.isSelected = ko.observable(isSelected); } var SelectableItemViewModel = function (items) { // Data var self = this; self.availableItems = ko.observableArray(ko.utils.arrayMap(items[0].availableItems, function (item) { return new Item(item.title, item.isSelected); })); self.selectedItems = ko.observableArray(ko.utils.arrayMap(items[1].selectedItems, function (item) { return new Item(item.title, item.isSelected); })); // Operations self.selectItem = function (item) { self.selectedItems.push(item); item.isSelected(!item.isSelected()); }; self.removeItem = function (removedItem) { self.selectedItems.remove(removedItem); $.each(self.availableItems, function (item) { if (item.title === removedItem.title) { item.isSelected = false; } }); }; } var vm = new SelectableItemViewModel(initialData); $(document).ready(function () { ko.applyBindings(vm); });
你能帮忙吗,看下面的jsfiddle:
http://jsfiddle.net/sbirthare/KR4a6/6/
**更新:以下问题**
其后续问题:
我需要在同一个UI上添加一个combobox,例如美国州。 可用的项目是县,根据用户选择状态组合我需要过滤县。 我使用AJAX从服务器获取数据并且所有成功但是显示的列表没有刷新。 我期待正确的绑定设置,如果我们在viewmodel中更改observable数组,UI应该更改。 我尝试强制更改为availableItems,但它只显示所有项目。 请查看您是否可以在下面的代码中发现我正在更新ViewModel observable数组的问题。
function multiselect_change() { console.log("event: openmultiselect_change"); var selectedState = $("#stateDropdownSelect").val(); var propertyName = $("#PropertyName").val(); var searchId = @Model.SearchId; var items; var model = { propertyName: propertyName, searchId: searchId, stateName: selectedState }; $.ajax({ url: '@Url.Action("GetFilterValues", "Search")', contentType: 'application/json; charset=utf-8', type: 'POST', dataType: 'html', data: JSON.stringify(model) }) .success(function(result) { debugger; items = JSON.parse(result); vm.availableItems(items.AvailableItems); //vm.availableItems.valueHasMutated(); //var item = document.getElementById('availableItemId'); //ko.cleanNode(item); //ko.applyBindings(vm, item); vm.filter(selectedState); }) .error(function(xhr, status) { alert(status); }); }
正如user3426870所提到的,您需要将传递给检查绑定的值更改为boolean。
另外,我认为您不需要在初始数据中使用selectedItems。
而在viewModel中,您可以执行以下操作:
self.selectedItems = ko.computed(function() { return ko.utils.arrayFilter(self.availableItems(), function (item) { return item.isSelected(); }); });
这是因为你给一个checked
的绑定数组,而它应该是一个可与true
或false
相比的值(如undefind
或空字符串)。 我会使用函数检查$data
是否在您的数组中并返回一个布尔值到您的绑定。
像这样的东西!