有一个包含嵌套HTML select语句的页面。如何在KnockoutJS中绑定选择的示例假设选项值在视图模型中。这里的选项以HTML格式存在。
将使用哪些语法/函数将第二个选择绑定到第一个选择选项的类名,以便它们仅在选择相应的类时出现在第二个列表中?换句话说,什么会取代空间持有者“whenStartAppGroupNSelected。”
加价:
<div class="apps">
<select id="startapp" name="startapp" data-bind="value: startapp">
<option value="value1" class="groupA">Some Val 1</option>
<option value="value2" class="groupB">Some Val 2</option>
<option value="value3" class="groupC">Some Val 3</option>
</select>
</div>
<div class="pages">
<select id="startpage" name="startpage" data-bind="value: startpage">
<option data-bind="visible: whenStartAppGroupASelected" value="path1" class="groupA">Page 1</option>
<option data-bind="visible: whenStartAppGroupBSelected" value="path2" class="groupB">Page 2</option>
<option data-bind="visible: whenStartAppGroupCSelected" value="path3" class="groupC">Page 3</option>
<option data-bind="visible: whenStartAppGroupCSelected" value="path4" class="groupC">Page 4</option>
</select>
</div>
型号:
myModel = function() {
var self = this;
self.startapp = ko.observable("").extend({required: true});
self.startpage = ko.observable("");
self.selectedApp = ko.computed(function() {
return self.startapp();
});
};
答案 0 :(得分:2)
我认为你所拥有的东西通常是针对knockout.js的。您的视图模型的构建方式应能够准确表示您的数据。
相反,我会创建一个单独的StartOption
视图模型对象来充当两个下拉列表的“值”。每个StartOption
都有一个子选项的可观察数组,然后你的主视图模型将有一个StartOption
列表用于第一级对象,每个对象都有一个列表二级项目。
这样的事情:
<div class="apps">
<select id="startapp" name="startapp"
data-bind="options: startApps, optionsText: 'text', value: selectedStartApp, optionsCaption: 'Choose...'">
</select>
</div>
<div class="pages" data-bind="with: selectedStartApp">
<select id="startpage" name="startpage"
data-bind="options: subOptions, optionsText: 'text', value: $root.selectedStartPage">
</select>
</div>
然后是JS:
var StartOption = function(value, text, options) {
var self = this;
self.value = ko.observable(value);
self.text = ko.observable(text);
self.subOptions = ko.observableArray(options || []);
};
var ViewModel = function() {
var self = this;
self.startApps = ko.observableArray([
new StartOption('value1', 'Some Val 1', [
new StartOption('path1', 'Page 1')
]),
new StartOption('value2', 'Some Val 2', [
new StartOption('path2', 'Page 2')
]),
new StartOption('value3', 'Some Val 3', [
new StartOption('path3', 'Page 3'),
new StartOption('path4', 'Page 4')
])
]);
self.selectedStartApp = ko.observable();
self.selectedStartPage = ko.observable();
};
ko.applyBindings(new ViewModel());
或许你想通过AJAX从服务器加载选项,你的JSON响应如下:
var sampleData = [
{
value: 'value1',
text: 'Some Val 1',
subOptions: [
{ value: 'path1', text: 'Page 1' }
]
},
{
value: 'value2',
text: 'Some Val 2',
subOptions: [
{ value: 'path2', text: 'Page 2' }
]
},
{
value: 'value3',
text: 'Some Val 3',
subOptions: [
{ value: 'path3', text: 'Page 3' },
{ value: 'path4', text: 'Page 4' }
]
}
];
你可以使用knockout-mapping
插件为你做一些繁重的工作,这样你就可以简化视图模型:
var StartOption = function(data) {
var self = this;
// map the properties of the data object as observables
// on this object; if we encounter "subOptions", make them
// instances of this object as well
ko.mapping.fromJS(data || {}, {
'subOptions': {
create: function(options) {
return new StartOption(options.data);
}
}
}, self);
};
var ViewModel = function() {
var self = this;
self.startApps = ko.observableArray();
self.load = function(data) {
self.startApps(ko.utils.arrayMap(data || [], function(option) {
return new StartOption(option);
}));
};
self.selectedStartApp = ko.observable();
self.selectedStartPage = ko.observable();
};
var viewModel = new ViewModel();
viewModel.load(sampleData);
ko.applyBindings(viewModel);