Knockout.js - Form and list demo
by nitronic
HTML
<script src="https://github.com/downloads/SteveSanderson/knockout/jquery.tmpl.js"></script>
<script src="https://github.com/SteveSanderson/knockout/raw/master/build/output/knockout-latest.js"></script>
<script src="http://knockoutjs.com/examples/resources/knockout.simpleGrid.js"></script>
<div id="booksCollection">
<form data-bind="submit: addItem" id="newEntryForm">
<div class="formArea">
<h1>Add new Entry</h1>
<div class="errorBox" data-bind="visible: currentBook.hasErrors">
ERROR: <span data-bind="text: currentBook.errorMessage"/>
</div>
<div id="row">
<div id="col">
Title
</div>
<div id="col">
<input data-bind="value: currentBook.title" placeholder="Enter new book title"></input>
</div>
</div>
<div id="row">
<div id="col">
Author
</div>
<div id="col">
<input data-bind="value: currentBook.author" placeholder="Enter new author"></input>
</div>
</div>
<div id="row">
<div id="col">
Pages
</div>
<div id="col">
<input data-bind="value: currentBook.pages" placeholder="Enter new pages count"></input>
</div>
</div>
<button type="submit">Add book</button>
</div>
</form>
<div class="collectionArea">
<h1>Books</h1>
<div data-bind='simpleGrid: gridViewModel'></div>
<button data-bind="click: clear">Clear books</button>
</div>
</div>
CSS
body {
margin: 0.5em;
}
.formArea {
display: table;
padding: 15px;
}
.errorBox {
background-color: red;
color: white;
padding: 10px;
border: 1px solid white;
margin: 15px 0px 15px 0px;
}
#booksCollection {
background-color: #ddd;
}
#row {
display: table-row;
height: 30px;
}
#col {
display: table-cell;
}
h1 {
font-size: 130%;
font-weight: bold;
margin-bottom: 0.5em;
margin-top: 1em;
}
.ko-grid { margin-bottom: 1em; width: 25em; border: 1px solid #000; background-color:White; }
.ko-grid th { text-align:left; background-color: #51A2FF; color:White; }
.ko-grid td, th { padding: 0.4em; }
.ko-grid tr.odd { background-color: #DDD; }
.ko-grid-pageLinks { margin-bottom: 1em; }
.ko-grid-pageLinks a { padding: 0.5em; }
.ko-grid-pageLinks a.selected { background-color: #51A2FF; color: White; }
.collectionArea {
padding: 15px;
}
JavaScript
var BookViewModel = function() {
this.title = ko.observable('');
this.author = ko.observable('');
this.pages = ko.observable('');
this.errorMessage = ko.observable('');
this.hasErrors = ko.computed(function() { return (this.errorMessage() != ''); }, this);
this.reset = function() {
this.title('');
this.author('');
this.pages('');
this.errorMessage('');
};
this.validate = function() {
this.errorMessage('');
if (this.title().length === 0 || this.author().length === 0 || this.pages().length === 0) {
this.errorMessage('All fields are required');
}
};
};
var initialData = [{
title: "Windows Presentation Foundation 4.5",
author: "Norbert Eder",
pages: 400}
];
var BooksViewModel = function(items) {
this.items = ko.observableArray(items);
this.currentBook = new BookViewModel();
this.addItem = function(formData) {
this.currentBook.validate();
if (!this.currentBook.hasErrors()) {
this.items.push({
title: formData[0].value,
author: formData[1].value,
pages: formData[2].value
});
this.currentBook.reset();
}
};
this.clear = function() {
this.items.removeAll();
};
this.gridViewModel = new ko.simpleGrid.viewModel({
data: this.items,
columns: [
{
headerText: "Title",
rowText: "title"},
{
headerText: "Author",
rowText: "author"},
{
headerText: "Pages",
rowText: "pages"}
],
pageSize: 5
});
};
var firstViewModel = new BooksViewModel(initialData);
ko.applyBindings(firstViewModel, $('booksCollection').get(0));