使用淘汰赛下拉
Posted
技术标签:
【中文标题】使用淘汰赛下拉【英文标题】:Drop down using knockout 【发布时间】:2015-06-11 12:11:34 【问题描述】:目前我正在制作一个非常基本的时间表。 所以我目前拥有的是一个点击添加员工的按钮,它会为他们生成一周的时间。我希望发生的是员工姓名输入是一个下拉列表,但我不知道如何继续,这是我到目前为止所拥有的 小提琴 http://jsfiddle.net/grahamwalsh/1p3nnkyg/
<div class='timesheet'>
<form action='/someServerSideHandler'>
<p>You have asked for <span data-bind='text: employees().length'> </span> employee(s)</p>
<table data-bind='visible: employees().length > 0'>
<thead>
<tr>
<th>Employee Name</th>
<th>Monday</th>
<th>Tuesday</th>
<th>Wednesday</th>
<th>Thursday</th>
<th>Friday</th>
<th>Saturday</th>
<th>Sunday</th>
<th />
</tr>
</thead>
<tbody data-bind='foreach: employees'>
<tr>
<td><input class='required' data-bind='value: name, uniqueName: true' /></td>
<td><input class='required number' data-bind='value: hours, uniqueName: true' /></td>
删除
<button data-bind='click: addEmployee'>Add Employee</button>
<button data-bind='enable: employees().length > 0' type='submit'>Submit</button>
</form>
淘汰赛
var EmployeeModel = function(employees)
var self = this;
self.employees = ko.observableArray(employees);
self.addEmployee = function()
self.employees.push(
Name: "",
Monday: "",
Tuesday:"",
Wednesday:"",
Thursday:"",
Friday:"",
Saturday:"",
Sunday:""
);
;
self.removeEmployee = function(employee)
self.employees.remove(employee);
;
self.save = function(form)
alert("Could now transmit to server: " + ko.utils.stringifyJson(self.employees));
;
;
var viewModel = new EmployeeModel([
]);
ko.applyBindings(viewModel);
$("form").validate( submitHandler: viewModel.save );
body font-family: arial; font-size: 14px;
.timesheet padding: 1em; background-color: #EEEEDD; border: 1px solid #CCC; max-width: 655px;
.timesheet input font-family: Arial;
.timesheet b font-weight: bold;
.timesheet p margin-top: 0.9em; margin-bottom: 0.9em;
.timesheet select[multiple] width: 100%; height: 8em;
.timesheet h2 margin-top: 0.4em; font-weight: bold; font-size: 1.2em;
.timesheet table, .liveExample td, .liveExample th padding: 0.2em; border-width: 0;
.timesheet td input width: 13em;
tr vertical-align: top;
.timesheet input.error border: 1px solid red; background-color: #FDC;
.timesheet label.error display: block; color: Red; font-size: 0.8em;
.timesheet th font-weight: bold;
li list-style-type: disc; margin-left: 20px;
【问题讨论】:
类似 jsfiddle.net/1p3nnkyg/6 的东西。欢呼 @Liz 顺便说一句 - 我只是注意到到目前为止您还没有接受任何问题的答案。 It would be great if you could do so,这样您的问题就不会再显示为“未回答”;它使其他人更容易区分谁仍然需要帮助,谁不需要。谢谢! 嗨,对不起,我一定会这样做,我该如何接受? 谢谢!单击您希望接受的答案分数下方的小复选标记。 Here is a screenshot。此外,当您编写 cmets 时,您可以将某人的姓名包含在 @ 符号中,例如@janfoeh。然后,该人会收到您已回复他们的通知 - 否则他们可能会错过您的回复。干杯! 【参考方案1】:如果我正确理解您的问题,您希望您的用户从员工列表中选择一个或多个人。您的方法有几个问题,我正在努力纠正这些问题。
您将视图模型命名为 EmployeeModel
,但您基本上还有另一个针对员工的临时数据模型:
self.employees.push(
Name: "",
Monday: "",
Tuesday:"",
Wednesday:"",
Thursday:"",
Friday:"",
Saturday:"",
Sunday:""
);
顺便说一句,这是行不通的,因为您忘记将属性设置为可观察的。如果将Name
绑定到输入字段值,例如<input data-bind="value: Name">
,它只会将输入设置为Name
的初始内容一次。之后,无论您更改可观察到的 Name
还是 <input>
值,都不会再发生任何事情。
所以让我们将您的视图模型重命名为ViewModel
并为Employee
创建一个专用数据模型:
var Employee = function Employee(name)
this.name = ko.observable(name);
this.monday = ko.observable();
this.tuesday = ko.observable();
this.wednesday = ko.observable();
this.thursday = ko.observable();
this.friday = ko.observable();
this.saturday = ko.observable();
this.sunday = ko.observable();
;
出于本演示的目的,我会将它们直接输入到视图模型中:
var viewModel = new ViewModel([
new Employee('Jane'),
new Employee('John'),
new Employee('Alice'),
new Employee('Bob')
]);
我们基本上有两个列表——
-
用户可以从中选择的员工列表,以及
用户选择的员工
所以我们需要两个 observableArrays:
var ViewModel = function ViewModel(employees)
this.availableEmployees = ko.observableArray(employees);
this.selectedEmployees = ko.observableArray([]);
;
我会改变用户界面,让用户首先选择员工:
这样,我们可以使用只包含尚未添加的员工的动态选择,从而可以防止员工被添加两次。
这是我们的<select>
:
<!-- ko if: availableEmployees().length > 0 -->
<select data-bind="value: employeeToBeAdded,
options: availableEmployees,
optionsText: 'name'">
</select>
<button data-bind='click: addEmployee'>Add Employee</button>
<!-- /ko -->
我们从所有availableEmployees
创建选项,并使用每个Employee
的name
属性作为选项标签文本。如果没有可用的,我们将隐藏所有内容。
employeeToBeAdded
是另一个 observable,持有当前在<select>
中选择的员工,单击“添加员工”时将添加该员工。
发生这种情况时,我们会从列表中获取选定的员工,将其添加到 selectedEmployees
并从 availableEmployees
中删除。对于removeEmployee
,我们反其道而行之:
var ViewModel = function ViewModel(employees)
var self = this;
this.availableEmployees = ko.observableArray(employees);
this.selectedEmployees = ko.observableArray([]);
this.employeeToBeAdded = ko.observable();
this.addEmployee = function addEmployee()
var employee = self.employeeToBeAdded();
self.employeeToBeAdded(null);
self.selectedEmployees.push( employee );
self.availableEmployees.remove( employee );
;
this.removeEmployee = function removeEmployee(employee)
self.availableEmployees.push(employee);
self.selectedEmployees.remove(employee);
;
;
这是完整的、可运行的示例:
var Employee = function Employee(name)
this.name = ko.observable(name);
this.monday = ko.observable();
this.tuesday = ko.observable();
this.wednesday = ko.observable();
this.thursday = ko.observable();
this.friday = ko.observable();
this.saturday = ko.observable();
this.sunday = ko.observable();
;
var ViewModel = function ViewModel(employees)
var self = this;
this.availableEmployees = ko.observableArray(employees);
this.selectedEmployees = ko.observableArray([]);
this.employeeToBeAdded = ko.observable();
this.addEmployee = function()
var employee = self.employeeToBeAdded();
self.employeeToBeAdded(null);
self.selectedEmployees.push(employee);
self.availableEmployees.remove(employee);
;
self.removeEmployee = function(employee)
self.availableEmployees.push(employee);
self.selectedEmployees.remove(employee);
;
self.save = function(form)
alert("Could now transmit to server: " + ko.utils.stringifyJson(self.employees));
;
;
var viewModel = new ViewModel([
new Employee('Jane'),
new Employee('John'),
new Employee('Alice'),
new Employee('Bob')
]);
ko.applyBindings(viewModel);
body font-family: arial; font-size: 14px;
.timesheet padding: 1em; background-color: #EEEEDD; border: 1px solid #CCC; max-width: 655px;
.timesheet input font-family: Arial;
.timesheet b font-weight: bold;
.timesheet p margin-top: 0.9em; margin-bottom: 0.9em;
.timesheet select[multiple] width: 100%; height: 8em;
.timesheet h2 margin-top: 0.4em; font-weight: bold; font-size: 1.2em;
.timesheet table, .liveExample td, .liveExample th padding: 0.2em; border-width: 0;
.timesheet td input width: 5em;
tr vertical-align: top;
.timesheet input.error border: 1px solid red; background-color: #FDC;
.timesheet label.error display: block; color: Red; font-size: 0.8em;
.timesheet th font-weight: bold;
li list-style-type: disc; margin-left: 20px;
.debugging-output padding: 2rem;
<script src="https://cdnjs.cloudflare.com/ajax/libs/knockout/3.2.0/knockout-min.js"></script>
<div class='timesheet'>
<form action='/someServerSideHandler'>
<p>You have asked for <span data-bind='text: selectedEmployees().length'> </span> employee(s)</p>
<table data-bind='visible: selectedEmployees().length > 0'>
<thead>
<tr>
<th>Employee Name</th>
<th>Monday</th>
<th>Tuesday</th>
<th>Wednesday</th>
<th>Thursday</th>
<th>Friday</th>
<th>Saturday</th>
<th>Sunday</th>
<th />
</tr>
</thead>
<tbody data-bind='foreach: selectedEmployees'>
<tr>
<td data-bind="text: name"></td>
<td><input class='required number' data-bind='value: monday, uniqueName: true' /></td>
<td><input class='required number' data-bind='value: tuesday, uniqueName: true' /></td>
<td><input class='required number' data-bind='value: wednesday, uniqueName: true' /></td>
<td><input class='required number' data-bind='value: thursday, uniqueName: true' /></td>
<td><input class='required number' data-bind='value: friday, uniqueName: true' /></td>
<td><input class='required number' data-bind='value: saturday, uniqueName: true' /></td>
<td><input class='required number' data-bind='value: sunday, uniqueName: true' /></td>
<td><button data-bind='click: $parent.removeEmployee'>Delete</button></td>
</tr>
</tbody>
</table>
<!-- ko if: availableEmployees().length > 0 -->
<select data-bind="value: employeeToBeAdded, options: availableEmployees, optionsText: 'name'"></select>
<button data-bind='click: addEmployee'>Add Employee</button>
<!-- /ko -->
<button data-bind='enable: selectedEmployees().length > 0' type='submit'>Submit</button>
</form>
</div>
<ul class="debugging-output" data-bind="foreach: selectedEmployees">
<li data-bind="text: ko.toJSON($data)"></li>
</ul>
【讨论】:
以上是关于使用淘汰赛下拉的主要内容,如果未能解决你的问题,请参考以下文章