Hinweis
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, sich anzumelden oder das Verzeichnis zu wechseln.
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, das Verzeichnis zu wechseln.
von Rick Anderson
Abgeschlossenes Projekt herunterladen
Erstellen einer dynamischen Benutzeroberfläche mit Knockout.js
In diesem Abschnitt verwenden wir Knockout.js, um der Administratoransicht Funktionen hinzuzufügen.
Knockout.js ist eine Javascript-Bibliothek, die das Binden von HTML-Steuerelementen an Daten erleichtert. Knockout.js verwendet das Model-View-ViewModel (MVVM)-Muster.
- Das Modell ist die serverseitige Darstellung der Daten in der Geschäftsdomäne (in unserem Fall Produkte und Bestellungen).
- Die Ansicht ist die Präsentationsebene (HTML).
- Das Ansichtsmodell ist ein Javascript-Objekt , das die Modelldaten enthält. Das Ansichtsmodell ist eine Codestraktion der Benutzeroberfläche. Sie hat keine Kenntnisse über die HTML-Darstellung. Stattdessen stellt sie abstrakte Features der Ansicht dar, z. B. "eine Liste von Elementen".
Die Ansicht ist datengebunden an das Ansichtsmodell. Aktualisierungen des Ansichtsmodells werden automatisch in der Ansicht widergespiegelt. Das Ansichtsmodell ruft auch Ereignisse aus der Ansicht ab, z. B. Schaltflächenklicks, und führt Vorgänge für das Modell aus, z. B. das Erstellen einer Bestellung.
Diagramm, das die Interaktion zwischen H T M L-Daten, dem Ansichtsmodell, j Son und dem Web A P I-Controller zeigt. Das H T M L Datenfeld ist mit "view" beschriftet. Ein doppelpfeilbeschriftetes Datenbindungsfeld verbindet das Datenfeld HTML mit dem Ansichtsmodellfeld. Mit einem Doppelpfeil beschriftete HTTP-Anfragen und ein JSON-Modell vom Server verknüpfen das Ansichtsmodell mit dem Web-API-Controller.
Zunächst definieren wir das Ansichtsmodell. Danach binden wir das HTML-Markup an das Ansichtsmodell.
Fügen Sie den folgenden Razor-Abschnitt zu Admin.cshtml hinzu:
@section Scripts {
@Scripts.Render("~/bundles/jqueryval")
<script type="text/javascript" src="@Url.Content("~/Scripts/knockout-2.1.0.js")"></script>
<script type="text/javascript">
// View-model will go here
</script>
}
Sie können diesen Abschnitt an einer beliebigen Stelle in der Datei hinzufügen. Wenn die Ansicht gerendert wird, wird der Abschnitt am unteren Rand der HTML-Seite direkt vor dem schließenden </body-Tag> angezeigt.
Das gesamte Skript für diese Seite wird innerhalb des Skripttags eingefügt, das durch den Kommentar gekennzeichnet ist:
<script type="text/javascript">
// View-model will go here
</script>
Definieren Sie zunächst eine Ansichtsmodellklasse:
function ProductsViewModel() {
var self = this;
self.products = ko.observableArray();
}
ko.observableArray ist eine besondere Art von Objekt in Knockout, das als observable bezeichnet wird. Aus der Knockout.js Dokumentation: Ein feststellbares Objekt ist ein "JavaScript-Objekt, das Abonnenten über Änderungen benachrichtigen kann.". Wenn der Inhalt einer feststellbaren Änderung geändert wird, wird die Ansicht automatisch entsprechend aktualisiert.
Um das products Array aufzufüllen, erstellen Sie eine AJAX-Anforderung an die Web-API. Erinnern Sie sich daran, dass wir den Basis-URI für die API im Ansichtsbehälter gespeichert haben (siehe Teil 4 des Lernprogramms).
function ProductsViewModel() {
var self = this;
self.products = ko.observableArray();
// New code
var baseUri = '@ViewBag.ApiUrl';
$.getJSON(baseUri, self.products);
}
Als Nächstes fügen Sie dem Ansichtsmodell Funktionen hinzu, um Produkte zu erstellen, zu aktualisieren und zu löschen. Diese Funktionen übermitteln AJAX-Aufrufe an die Web-API und verwenden die Ergebnisse zum Aktualisieren des Ansichtsmodells.
function ProductsViewModel() {
var self = this;
self.products = ko.observableArray();
var baseUri = '@ViewBag.ApiUrl';
// New code
self.create = function (formElement) {
// If the form data is valid, post the serialized form data to the web API.
$(formElement).validate();
if ($(formElement).valid()) {
$.post(baseUri, $(formElement).serialize(), null, "json")
.done(function (o) {
// Add the new product to the view-model.
self.products.push(o);
});
}
}
self.update = function (product) {
$.ajax({ type: "PUT", url: baseUri + '/' + product.Id, data: product });
}
self.remove = function (product) {
// First remove from the server, then from the view-model.
$.ajax({ type: "DELETE", url: baseUri + '/' + product.Id })
.done(function () { self.products.remove(product); });
}
$.getJSON(baseUri, self.products);
}
Jetzt ist der wichtigste Teil: Wenn das DOM vollständig geladen wird, rufen Sie die ko.applyBindings Funktion auf, und übergeben Sie eine neue Instanz der ProductsViewModel:
$(document).ready(function () {
ko.applyBindings(new ProductsViewModel());
})
Die ko.applyBindings-Methode aktiviert Knockout und verkabelt das Ansichtsmodell mit der Ansicht.
Da wir nun über ein Ansichtsmodell verfügen, können wir die Bindungen erstellen. In Knockout.jsfügen Sie dazu Attribute zu HTML-Elementen hinzu data-bind . Um beispielsweise eine HTML-Liste an ein Array zu binden, verwenden Sie die foreach Bindung:
<ul id="update-products" data-bind="foreach: products">
Die foreach Bindung durchläuft das Array und erstellt untergeordnete Elemente für jedes Objekt im Array. Bindungen für die untergeordneten Elemente können auf Eigenschaften der Arrayobjekte verweisen.
Fügen Sie der Liste "Updateprodukte" die folgenden Bindungen hinzu:
<ul id="update-products" data-bind="foreach: products">
<li>
<div>
<div class="item">Product ID</div> <span data-bind="text: $data.Id"></span>
</div>
<div>
<div class="item">Name</div>
<input type="text" data-bind="value: $data.Name"/>
</div>
<div>
<div class="item">Price ($)</div>
<input type="text" data-bind="value: $data.Price"/>
</div>
<div>
<div class="item">Actual Cost ($)</div>
<input type="text" data-bind="value: $data.ActualCost"/>
</div>
<div>
<input type="button" value="Update" data-bind="click: $root.update"/>
<input type="button" value="Delete Item" data-bind="click: $root.remove"/>
</div>
</li>
</ul>
Das <li> Element tritt innerhalb des Bereichs der Foreachbindung auf. Das bedeutet, dass Knockout das Element einmal für jedes Produkt im products Array rendert. Alle Bindungen innerhalb des <li> Elements beziehen sich auf diese Produktinstanz. Verweist beispielsweise $data.Name auf die Name Eigenschaft des Produkts.
Verwenden Sie die value Bindung, um die Werte der Texteingaben festzulegen. Die Schaltflächen sind mithilfe der click Bindung an Funktionen in der Modellansicht gebunden. Die Produktinstanz wird als Parameter an jede Funktion übergeben. Für weitere Informationen enthält die Knockout.js Dokumentation gute Beschreibungen der verschiedenen Bindungen.
Fügen Sie als Nächstes eine Bindung für das Sendeereignis im Formular "Produkt hinzufügen" hinzu:
<form id="addProduct" data-bind="submit: create">
Diese Bindung ruft die create Funktion im Ansichtsmodell auf, um ein neues Produkt zu erstellen.
Hier sehen Sie den vollständigen Code für die Administratoransicht:
@model ProductStore.Models.Product
@{
ViewBag.Title = "Admin";
}
@section Scripts {
@Scripts.Render("~/bundles/jqueryval")
<script type="text/javascript" src="@Url.Content("~/Scripts/knockout-2.0.0.js")"></script>
<script type="text/javascript">
function ProductsViewModel() {
var self = this;
self.products = ko.observableArray();
var baseUri = '@ViewBag.ApiUrl';
self.create = function (formElement) {
// If valid, post the serialized form data to the web api
$(formElement).validate();
if ($(formElement).valid()) {
$.post(baseUri, $(formElement).serialize(), null, "json")
.done(function (o) { self.products.push(o); });
}
}
self.update = function (product) {
$.ajax({ type: "PUT", url: baseUri + '/' + product.Id, data: product });
}
self.remove = function (product) {
// First remove from the server, then from the UI
$.ajax({ type: "DELETE", url: baseUri + '/' + product.Id })
.done(function () { self.products.remove(product); });
}
$.getJSON(baseUri, self.products);
}
$(document).ready(function () {
ko.applyBindings(new ProductsViewModel());
})
</script>
}
<h2>Admin</h2>
<div class="content">
<div class="float-left">
<ul id="update-products" data-bind="foreach: products">
<li>
<div>
<div class="item">Product ID</div> <span data-bind="text: $data.Id"></span>
</div>
<div>
<div class="item">Name</div>
<input type="text" data-bind="value: $data.Name"/>
</div>
<div>
<div class="item">Price ($)</div>
<input type="text" data-bind="value: $data.Price"/>
</div>
<div>
<div class="item">Actual Cost ($)</div>
<input type="text" data-bind="value: $data.ActualCost"/>
</div>
<div>
<input type="button" value="Update" data-bind="click: $root.update"/>
<input type="button" value="Delete Item" data-bind="click: $root.remove"/>
</div>
</li>
</ul>
</div>
<div class="float-right">
<h2>Add New Product</h2>
<form id="addProduct" data-bind="submit: create">
@Html.ValidationSummary(true)
<fieldset>
<legend>Contact</legend>
@Html.EditorForModel()
<p>
<input type="submit" value="Save" />
</p>
</fieldset>
</form>
</div>
</div>
Führen Sie die Anwendung aus, melden Sie sich mit dem Administratorkonto an, und klicken Sie auf den Link "Administrator". Sie sollten die Liste der Produkte anzeigen und in der Lage sein, Produkte zu erstellen, zu aktualisieren oder zu löschen.