在 jsfiddle 上查看问题:http: //jsfiddle.net/6bFsY/3/
当您单击“添加用户”,然后再次单击“添加用户”时,扩展下拉字段中的所有数据都会消失。这发生在我添加了一个电子邮件列之后。电子邮件字段会预先填充扩展下拉列表中选择的任何内容(电子邮件是其对象的一部分)。
此外,扩展下拉列表是每行唯一的,部分脚本告诉它如果它存在于前一行中,则将其从数组中删除。
JS
window.usrViewModel = new function () {
var self = this;
window.viewModel = self;
self.list = ko.observableArray();
self.pageSize = ko.observable(10);
self.pageIndex = ko.observable(0);
self.selectedItem = ko.observable();
self.extData = ko.observableArray();
self.validAccess = [{
'name': 'No Access',
'id': 'none'
}, {
'name': 'System Settings',
'id': 'pbx'
}, {
'name': 'Accounting',
'id': 'billing'
}, {
'name': 'Full Administrator',
'id': 'full'
}];
self.availableExtData = ko.computed(function () {
var inUse = [];
if (!self.selectedItem()) return inUse;
ko.utils.arrayForEach(self.list(), function (item) {
if (inUse.indexOf(item.usrExtVal().extension) == -1 && self.selectedItem() != item) inUse.push(item.usrExtVal().extension);
self.selectedItem().usrEmail(self.selectedItem().usrExtVal().email);
});
return ko.utils.arrayFilter(self.extData(), function (item) {
return inUse.indexOf(item.extension) == -1;
});
});
self.edit = function (item) {
if (self.selectedItem()) self.save();
self.selectedItem(item);
};
self.cancel = function () {
self.selectedItem(null);
};
self.add = function () {
if (self.selectedItem()) self.save();
var newItem = new Users();
self.selectedItem(newItem);
self.list.push(newItem);
self.moveToPage(self.maxPageIndex());
};
self.remove = function (item) {
if (confirm('Are you sure you wish to delete this item?')) {
self.list.remove(item);
if (self.pageIndex() > self.maxPageIndex()) {
self.moveToPage(self.maxPageIndex());
}
}
$('.error').hide();
};
self.save = function () {
self.selectedItem(null);
};
self.templateToUse = function (item) {
return self.selectedItem() === item ? 'editUsrs' : 'usrItems';
};
self.pagedList = ko.dependentObservable(function () {
var size = self.pageSize();
var start = self.pageIndex() * size;
return self.list.slice(start, start + size);
});
self.maxPageIndex = ko.dependentObservable(function () {
return Math.ceil(self.list().length / self.pageSize()) - 1;
});
self.previousPage = function () {
if (self.pageIndex() > 0) {
self.pageIndex(self.pageIndex() - 1);
}
};
self.nextPage = function () {
if (self.pageIndex() < self.maxPageIndex()) {
self.pageIndex(self.pageIndex() + 1);
}
};
self.allPages = ko.dependentObservable(function () {
var pages = [];
for (i = 0; i <= self.maxPageIndex(); i++) {
pages.push({
pageNumber: (i + 1)
});
}
return pages;
});
self.moveToPage = function (index) {
self.pageIndex(index);
};
};
ko.applyBindings(usrViewModel, document.getElementById('usrForm'));
function Users(fname, lname, email, phone, access, usrExtVal, usrEmail) {
this.fname = ko.observable(fname);
this.lname = ko.observable(lname);
this.email = ko.observable(email);
this.phone = ko.observable(phone);
this.access = ko.observable(access);
this.usrExtVal = ko.observable(usrExtVal);
this.usrEmail = ko.observable(usrEmail);
}
var ajaxResultExt = [{
'extension': '123',
'name': 'Stephen',
'email': 'test@test.com'
}, {
'extension': '123',
'name': 'Stephen',
'email': 'stephen@test.com'
}];
usrViewModel.extData(ajaxResultExt);
HTML
<fieldset title="Users">
<legend>2</legend>
<div>
<div class="cbp-content">
<form id="usrForm">
<h2>Users</h2>
<table class="table table-striped table-bordered" data-bind='visible: pagedList().length > 0'>
<thead>
<tr>
<th>First Name</th>
<th>Last Name</th>
<th>Phone Number</th>
<th>Access</th>
<th>Extension</th>
<th>Email</th>
<th style="width: 100px; text-align:right;" />
</tr>
</thead>
<tbody data-bind=" template:{name:templateToUse, foreach: pagedList }"></tbody>
</table>
<!-- ko if: 2 > pagedList().length -->
<p class="pull-right"><a class="btn btn-primary" data-bind="click: $root.add" href="#" title="edit"><i class="icon-plus"></i> Add Users</a></p>
<!-- /ko -->
<div class="supOneUsr" style="display:none;"><i class="icon-warning-sign"></i> <span style="color:red;">Please supply at least 1 User with Administrator Rights</span></div>
<div class="pagination pull-left" data-bind='visible: pagedList().length > 0'>
<ul><li data-bind="css: { disabled: pageIndex() === 0 }"><a href="#" data-bind="click: previousPage">Previous</a></li></ul>
<ul data-bind="foreach: allPages">
<li data-bind="css: { active: $data.pageNumber === ($root.pageIndex() + 1) }"><a href="#" data-bind="text: $data.pageNumber, click: function() { $root.moveToPage($data.pageNumber-1); }"></a></li>
</ul>
<ul><li data-bind="css: { disabled: pageIndex() === maxPageIndex() }"><a href="#" data-bind="click: nextPage">Next</a></li></ul>
</div>
<br clear="all" />
<script id="usrItems" type="text/html">
<tr>
<td data-bind="text: fname"></td>
<td data-bind="text: lname"></td>
<td data-bind="text: phone"></td>
<td data-bind="text: access.asObject && access.asObject() && access.asObject().name"></td>
<td data-bind="text: usrExtVal().extension"></td>
<td data-bind="text: usrEmail"></td>
<td class="buttons">
<a class="btn" data-bind="click: $root.edit" href="#" title="edit"><i class="icon-edit"></i></a>
<a class="btn" data-bind="click: $root.remove" href="#" title="remove"><i class="icon-remove"></i></a>
</td>
</tr>
</script>
<script id="editUsrs" type="text/html">
<tr>
<td><input data-errorposition="b" class="required" name="fname" data-bind="value: fname" /></td>
<td><input data-errorposition="b" class="required" name="lname" data-bind="value: lname" /></td>
<td><input data-errorposition="b" class="required" name="phone" data-bind="value: phone" /></td>
<td><select class="accessSelect" data-bind="options: $root.validAccess, optionsText: 'name', optionsValue: 'id', value: access, valueAsObject: 'asObject'"></select></td>
<td><select id="extData" data-bind="options: $root.availableExtData, optionsText: 'extension', value: usrExtVal"></select></td>
<td><input id="extEmail" data-errorposition="b" class="required" name="email" data-bind="value: usrEmail" /></td>
<td class="buttons">
<a class="btn btn-success" data-bind="click: $root.save" href="#" title="save"><i class="icon-ok"></i></a>
<a class="btn" data-bind="click: $root.remove" href="#" title="remove"><i class="icon-remove"></i></a>
</td>
</tr>
</script>
</form>
</div>
</div>
</fieldset>