knockout-sortable - seating chart
https://github.com/rniemeyer/knockout-sortable
by pj_js15
HTML
<script src="http://knockoutjs.com/downloads/knockout-2.3.0.js"></script>
<script src="https://rawgithub.com/rniemeyer/knockout-sortable/master/build/knockout-sortable.js"></script>
<div id="main" data-bind="foreach: itemsTable">
<!-- ko if: $index() == 0 -->
<div class="table">
<span data-bind="text: agendaSPItems.Id"></span>
<div class="seats" data-bind="sortable: { data: agendaSPItems, allowDrop: $root.isTableFull }">
<div class="student" data-bind="text: ME"></div>
</div>
</div>
<!-- /ko -->
</div>
<div id="anotherMain" data-bind="foreach: itemsTable">
<!-- ko if: $index() == 1 -->
<div class="table">
<span data-bind="text: agendaSPItems.Id"></span>
<div class="seats" data-bind="sortable: { data: agendaSPItems, allowDrop: $root.isTableFull }">
<div class="student" data-bind="text: ME"></div>
</div>
</div>
<!-- /ko -->
</div>
<div id="extra">
<div>Available</div>
<div class="new" data-bind="sortable: availableStudents">
<div class="student" data-bind="text: name"></div>
</div>
</div>
<div id="message" data-bind="flash: lastAction"></div>
<div id="error" data-bind="flash: lastError"></div>
<div id="master">
<div>Master List</div>
<table>
<tr>
<th></th>
<th>Seat One</th>
<th>Seat Two</th>
<th>Seat Three</th>
<th>Seat Four</th>
</tr>
<tbody data-bind="foreach: itemsTable">
<tr>
<th data-bind="text: agendaSPItems.Id"></th>
<!-- ko foreach: agendaSPItems -->
<td data-bind="text: ME"></td>
<!-- /ko -->
</tr>
</tbody>
<tr>
<th>Available</th>
<!-- ko foreach: availableStudents -->
<td data-bind="text: ME"></td>
...
CSS
body {
font-family: arial;
}
.table {
float: left;
text-align: center;
margin-right: 5px;
}
.table span {
font-size: .75em;
}
.seats {
border: solid 3px #666;
width: 75px;
height: 100px;
background-color: #666;
margin: 5px;
padding: 2px;
border-radius: 5px;
box-shadow: 2px 2px 2px #999;
}
.ko_container {
border: solid 3px green;
}
.student {
background-color: #444;
color: #fff;
border-radius: 3px;
margin: 2px;
padding: 1px;
text-align: center;
width: 70px;
cursor: move;
}
.new {
border: solid 1px #444;
background-color: #ccc;
height: 25px;
width: 500px;
padding: 2px;
border-radius: 5px;
}
.new div {
float: left;
}
.note {
font-style: italic;
font-size: .75em;
color: #888;
margin-bottom: 10px;
}
.count {
color: #666;
}
.ready {
color: green;
}
#extra {
clear: both;
padding-top: 20px;
}
#master {
margin-top: 40px;
}
#master td, th {
font-size: .75em;
text-align: center;
padding: 1px;
border: solid 1px black;
}
#master th {
color: #666;
}
#message, #error {
font-size: .75em;
margin-top: 10px;
background-color: orange;
color: #444;
padding: 2px;
width: 500px;
text-align: center;
border-radius: 5px;
box-shadow: 2px 2px 2px #999;
position: absolute;
}
#error {
background-color: #ff3333;
color: #ddd;
}
JavaScript
ko.bindingHandlers.flash = {
init: function(element) {
//$(element).hide();
},
update: function(element, valueAccessor) {
var value = ko.utils.unwrapObservable(valueAccessor());
/*
if (value) {
$(element).stop().hide().text(value).fadeIn(function() {
clearTimeout($(element).data("timeout"));
$(element).data("timeout", setTimeout(function() {
$(element).fadeOut();
valueAccessor()(null);
}, 3000));
});
}
*/
},
timeout: null
};
/********** MeetingSetup ***************************/
var AgendaSPItem = function(Id, ME) {
this.Id = Id;
this.ME = ME;
}
var ItemsTable = function(Id, agendaSPItems) {
this.agendaSPItems = ko.observableArray(agendaSPItems);
this.agendaSPItems.Id = Id;
}
/********** End of MeetingSetup *******************/
var Student = function(id, name, gender) {
this.id = id;
this.name = ko.observable(name);
this.gender = gender;
};
var Table = function(id, students) {
this.students = ko.observableArray(students);
this.students.id = id;
};
var SeatingChartModel = function(tables, availableStudents) {
var self = this;
/* Meeting Setup */
var testTable2 = [
new ItemsTable("Agenda", [
new AgendaSPItem(1, "Ones"),
new AgendaSPItem(2, "Twos"),
new AgendaSPItem(3, "Threes")
]),
new ItemsTable("Sub Pres", [
new AgendaSPItem(4, "Fours"),
new AgendaSPItem(5, "Fives"),
new AgendaSPItem(6, "Sixs")
])
];
this.itemsTable = ko.observableArray(testTable2);
this.tables = ko.observableArray(tables);
this.availableStudents = ko.observableArray(availableStudents);
this.availableStudents.id = "Available Students";
this.lastAction = ko.observable();
this.lastError = ko.observable();
this.maximumStudents = 4;
this.isTableFull =...