Vorwort: Der vorherige Artikel führt die Kapselung von KO -Addition, Löschung, Änderung und Suche vor, die tatsächlich viele JS -Code spart. Der Blogger ist eine Person, die gerne faul ist. Er ist immer der Ansicht, dass diese grundlegenden Ergänzungen, Löschungen, Änderungen und Überprüfungen die Seiteneffekte direkt über ein Tool generieren können und kein Code erforderlich ist. Das wäre so cool. Also habe ich die Grammatik von T4 studiert. Obwohl ich es nicht vollständig gemeistert habe, hatte ich ein allgemeines Verständnis. Der heutige Artikel von heute: Generieren Sie schnell Seiten durch T4 -Vorlagen.
Artikel der Knockoutjs -Serie:
Bootstrappable und KnockoutJs kombinieren die Funktion des Hinzufügens, Löschens, Modifizierens und Überprüfens [1]
Bootstrappable und KnockoutJs kombinieren die Funktion des Hinzufügens, Löschens, Änderns und Überprüfens [2]
Bootstrappable + Knockoutjs kombiniert die Lösung des Hinzufügens, Löschens, Änderns und Überprüfens (3) Zwei ViewModels können das Hinzufügen, das Löschen, Ändern und Überprüfen des Hinzufügens abschließen
1. Einführung in die Verwendung von T4
Wir wissen, dass beim Hinzufügen von Ansichten in MVC der Seiteneffekt des Hinzufügens, Löschens, Änderns und Überprüfens automatisch generiert werden kann. Dies liegt daran, dass MVC grundlegende Vorlagen zum Hinzufügen, Löschen, Ändern und Überprüfen integriert hat. Die Syntax dieser Vorlagen besteht darin, T4 zu verwenden. Wo sind diese Vorlagen? Nach der Suche nach verwandten Artikeln stellte ich fest, dass sich der Ort von MVC4 und unterhalb der Versionsvorlagen stark von der von MVC5 und höher unterscheidet.
• Vorlagespeicherort für MVC4 und die folgenden Versionen: VS Installationsverzeichnis +/itemTemplates/csharp/web/mvc 2/codetemplates. Zum Beispiel die D:/Programmdateien des Bloggers (x86)/Microsoft Visual Studio 12.0/Common7/ide/itemTemplates/CSHARP/Web/MVC 4/Codetemplates.
Suchen Sie die Vorlage, die CSHTML entspricht, und es gibt entsprechende TT -Dateien, die hinzufügen, löschen, ändern und überprüfen
• MVC5 und oben Vorlage Ort: Geben Sie direkt den Vorlagenort der Bloggerin D:/Programmdateien (x86)/Microsoft Visual Studio 12.0/Common7/IDE/Extensions/Microsoft/Web/MVC/Gerüst/Vorlagen an
Sobald Sie dies wissen, besteht der nächste Schritt darin, die Vorlage umzubauen und Ihren eigenen generierten Inhalt hinzuzufügen. Sie können die Liste direkt kopieren und Vorlagen zur Selbsttransformation bearbeiten. Nachdem Sie darüber nachgedacht haben, ist es jedoch besser, das eingebaute MVC nicht zu berühren. Es ist nicht besser, selbst Ihre eigenen Vorlagen zu bauen.
Erstellen Sie einen neuen Ordner im Root -Verzeichnis des aktuellen Webprojekts, nennen Sie es Codetemplates und kopieren Sie dann die beiden Vorlagenordner MVCCONTROLLEREMPTY und MVCVIEW in der MVC -Vorlage in den Ordner codetemplates, entfernen Sie die ursprünglichen Vorlagen darin und erstellen Sie dann mehrere neue Vorlagen, wie in der Abbildung unten gezeigt, mehrere neue Vorlagen erstellen, wie in der Abbildung unten gezeigt.
Wenn wir einen neuen Controller hinzufügen und eine neue Ansicht erstellen, können wir unsere individuelle Vorlage sehen:
2. Einführung von T4 Code
Das obige führt vor, wie Sie Ihre eigene Vorlage erstellen. Nachdem die Vorlage erstellt wurde, sollten Sie den entsprechenden Inhalt in sie einfüllen. Wenn die Grammatik von T4 erweitert wird, ist dieser Artikel endlos. Interessierte Gärtner können im Garten suchen. Es gibt immer noch ziemlich viele Artikel. Schauen wir uns hier ein paar Vorlageninhalte an. Eine andere Sache zu beachten ist, dass nach MVC5 das Suffix von T4 nach MVC5 in T4 geändert wurde und die vorherigen Vorlagen immer mit TT beendet wurden. Ohne die Unterschiede in ihrer Syntax zu betrachten, wird geschätzt, dass es kaum einen Unterschied geben sollte.
1. Controller.cs.t4
Warum diese leere Controller -Vorlage neu schreiben? Der Blogger ist der Ansicht, dass viele Methoden zum Hinzufügen, Löschen, Ändern und Überprüfungen manuell geschrieben werden müssen, und es ist große Probleme, eine Vorlage direkt zu schreiben. Schauen wir uns den Implementierungscode in der Vorlage an:
<#@ Template Language = "C#" hostSpecific = "true"#> <#@ output erweitert = "cs"#> <#@ parameter type = "system.string" name = "Controllername"#> <#@ parameter type = "system.string" name = "controllerRootname"##@@@@@@@@@@ -String "system" system "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name "name" name name = "areaname"#> <#var index = Controllername.lastIndexof ("Controller"); var modelName = Controllername.substring (0, Index);#> Verwenden von System.Collectionss.generic; Verwendung von System.LinQ; Verwendung von System.Web; #>: Controller {public actionResult index () {return view ();} public actionResult edit (< #= modelName #> model) {return view (model);} [httpget] public JsonResult (int limit, int offset) {return json (neu {{}, jonRequestBeSult]; JsonResult add (<#= modelName#> odata) {<#= modelName#> model.add (odata); return JSON (neu {}, jsonRequestBehavior.AllowGet);} // Aktualisierung von Entity [httppost] public JsonResult -Update (<#= modelName#> odata) {#=#=#=#=#=#=#=#=#=#=#=#=#=##> odata#> odata#> odata #> Model.Update (odata); return JSON (neu {}, jsonRequestBehavior.AllowGet);} // Entität löschen [httppost] public JsonResult delete (list << #= modelname #> odata) {< #= modelname #> model. JsonRequestBehavior.AllowGet);}}}Dieser Inhalt ist nicht schwer zu verstehen. Überprüfen Sie einfach den generierten Controller -Code:
Verwenden von System; system.collectionss.generic; Verwendung von System.LinQ; Verwendung von System.web; Verwendung von System.web.mvc; Verwendung testko.models; namespace testko.controller {public class UserController: Controller {Public actionResult Index () {) Return View (); JsonResult get (int limit, int offset) {return JSON (neu {}, jsonRequestBehavior.AllowGet);} // Entität hinzufügen [httppost] public JsonResult add (Benutzer odata) {UsmoDel.Add (Odata); return JSON (neu {}, jsonRequestBehavior.AllowGet);} // Entität aktualisieren [httppost] public JsonResult Update (Benutzer ODATA) {UsModel.update (Odata); return JSON (neu {}, jsonRequestBehavior.AllowGet);} // Entität löschen [httppost] public JsonResult delete (list <Unter> odata) {UsModel.delete (odata); return JSON (neu {}, jsonRequestBehavior.AllowGet);}}}2. Koindex.cs.t4
Diese Vorlage wird hauptsächlich zum Generieren von Listenseiten mit dem allgemeinen Code wie folgt verwendet:
<#@ template Language = "C#" hostSpecific = "true"#> <#@ output erweiterung = ". if (isLayoutPageSelected) {#>@{viewbag.title = "<#= viewName#>"; <#if (! String.IsNullorempy (LayoutPageFile)) {#> layout = "<#= LayoutPageFile#>"; html> <html> <head> <meta name = "viewPort" content = "width = Geräte-Width"/> <title> < #= viewName #> </title> <link href = "~/content/bootstrap/css/bootstrap.min href = "~/content/bootstrap-table/bootstrap-table src = "~/content/bootstrap-table/bootstrap-table.min.js"> </script> <script src = "~/content/bootstrap-table/local/bootstrap-table-zh-cn.js"> </script src="~/scripts/knockout/extensions/knockout.mapping-latest.js"></script><script src="~/scripts/extensions/knockout.index.js"></script><script src="~/scripts/extensions/knockout.index.js"></script><script><script src = "~/scripts/extensions/knockout.index.js"> </script> <script src = "~/scripts/extensions/knockout.bootStrapTable.js"> </script> <script type = "text/javaScript"> $ (Funktion () {var viewModel = {bindid: "dividId:" dividId: "dividId:" dividId: "dividId:" dividId: "dividId:" dividEx ", tableParams" "/<| : {}}; Ko.BindingViewModel (ViewModel);}); </script> </head> <body> <#pushindent ("");}#> <div id = "Symbolleiste"> <button data-bind = "click: addClick" type "type"> <span rot: "klicks". type = "button"> <span aria-hidden = "true"> </span> modifizieren Sie </button> <button data-bind = "klicken: deleteClick" type = "button"> <span aria-hidden = "true"> </span> lösche </button> </div> <table data-bind data-Checkbox = "true"> </th> <#ienumerable <SperticesMetadata> properties = modelMetadata.properties; foreach (PropertyMetadata-Eigenschaft in Eigenschaften) {if (Property.scaffold &&! GetValueExpression (Eigenschaft)#> </th> <#}}#> </tr> </thead> </table> <#// Der folgende Code schließt das im Fall einer Ansicht verwendete Tag mit einer Layout -Seite und der Body- und HTML -Tags im Fall einer regulären Ansicht Seite#> <#! {ClearIndent ();#> </body> </html> <#}#> <#@ include File = "modelMetadatafUNctions.cs.include.t4"#>Fügen Sie einen Ansichtsindex hinzu und wählen Sie diese Vorlage aus
Der Seiteninhalt wurde erhalten
@{Layout = null;} <! DocType html> <html> <kopf> <meta name = "viewPort" content = "width = Gerätebidth"/> <title> Index </title> <link href = "~/content/bootstrap/css/bootstrap.Min.css" rel = " href = "~/content/bootstrap-table/bootstrap-table src = "~/content/bootstrap-table/bootstrap-table.min.js"> </script> <script src = "~/content/bootstrap-table/local/bootstrap-table-zh-cn.js"> </script src = "~/scripts/Knockout/Knockout-3.4.0.min.js"> </script> <script src = "~/scripts/knockout/extensions/knockout src = "~/scripts/extensions/knockout.bootStrapTable.js"> </script> <script type = "text/javaScript"> $ (function () {var viewModel = {bindid: "div_index", tableParams: {url: "/user/user/user/user/deletsize: pagesiz: 2, · | "/User/edit", add: "/user/edit",}, queryCondition: {}}; ko.bindingViewModel (viewModel);}); data-bind = "klicken: editclick" type = "button"> <span aria-hidden = "true"> </span> modifizieren Sie </button> <button data-bind = "klicken: deleteclick" type = "button"> <span aria-hidden = "true"> data-checkbox="true"></th><th data-field="Name">Name</th><th data-field="FullName">FullName</th><th data-field="Age">Age</th><th data-field="Des">Des</th><th data-field="Createtime">Createtime</th><th Data-Field = "StrCreateTime"> StrCreateTime </th> </tr> </thead> </table> </body> </html> index.cshtmlWir haben das im vorherige Artikel erwähnte ViewModel auf die Seite verschoben, damit wir es nicht jedes Mal vom Controller übergeben müssen. Ändern Sie den Spaltennamen der Tabelle geringfügig und die Seite kann ausgeführt werden.
Hier sind einige Punkte zu optimieren:
(1) Die Abfragebedingungen wurden nicht generiert. Wenn Sie die Syntax von T4 ein wenig tiefer untersuchen, können Sie den Feldern Eigenschaften hinzufügen, die abfragt werden müssen, um festzustellen, welche Felder abgefragt werden müssen, und dann automatisch die entsprechenden Abfragebedingungen generieren.
(2) Die Spaltennamen der Tabelle scheinen über die Feldeigenschaften des Attributs generiert zu werden. Dies ähnelt dem ersten Punkt und beide müssen die Grammatik von T4 untersuchen.
3.. Koedit.cs.t4
Die dritte Vorlagenseite ist die bearbeitete Vorlage, und ihr grober Code lautet wie folgt:
<#@ template Language = "C#" hostSpecific = "true"#> <#@ output erweiterung = ". Dies verwendet ein DIV in Bootstrapstraping booltype = "System.boolean"; Version fordert mvcversion = new Version ("5.1.0.0"); bool iscontrolhtmlattributessSupported = mvcversion> = fordereMvcversion; // Die folgende Ketten-Statement-Stadium-Stadium-Stadik-oder-Einstaaten-Stadel-oder-Ein-Stadik-Abholung. view.if (iSpartialView) {#> <#} else if (isLayoutPageSelected) {#>@{viewBag.title = "<#= viewName#>"; <#if (! String.isnullEmpty (LayoutPageFile) {#> Layout =##=#=########> "; ViewName#></h2><#} else {#>@{Layout = null;}<!DOCTYPE html><html><head><meta name="viewport" content="width=device-width" /><title><#= ViewName #></title></head><body><#PushIndent(");}#><#if (ReferenceScriptLibraries) {#><#if (!IsLayoutPageSelected && IsBundleConfigPresent) {#>@Scripts.Render("~/bundles/jquery")@Scripts.Render("~/bundles/jqueryval")<#}#><#else if (!IsLayoutPageSelected) {#><script src="~/Scripts/jquery-<#= JQueryversion#>. Min.js "> </script> <script src =" ~/scripts/jQuery.validat.min.js "> </script> <script src =" ~/scripts/jQuery.validat.unoBusive.min.js "> </script> <####> <##> <##> <Form =" model.id) <Div> <#ienumerable <SperticesMetadata> Eigenschaften = modelmetadata.properties; foreach (PropertyMetadata -Eigentum in Eigenschaften) {if (property.scaffold &&! "<nr. }) </div> </div> <#}}#> </div> <div> <button type = "button" data-dismiss = "modal"> <span aria-hidden = "true"> </span> schließen </button> <button type = "arrang"> <span ark-hidden = "true"> </span> save> save </button </button> </div> </div> </button> </button </div> </</div> </</div> </</div> </button ViewDatatypename.lastIndexof ("."); Var modelName = viewDatatypename.substring (Index+1, ViewDatatypename.length-Index-1); @Html.raw (newtonsoft.json.jsonConvert.SerializeObject (Modell)); var viewModel = {formId: "Formedit", EditModel: modell, URLs: {subine: model.id == 0? {Validatoren: {NotonMpty: {message: 'Der Name kann nicht leer sein!'}}}}}}; Ko.BindingDitViewModel (ViewModel); Oder src = "~/scripts/jQuery.validat.min.js"> </script> <script src = "~/scripts/jQuery.validat.unoBtusiv.min.js"> </script> <script src = "~/scripts/jquery.unobusive. Verwendet im Fall einer Ansicht unter Verwendung einer Layout -Seite und der Körper- und HTML -Tags im Fall einer regulären Ansicht Seite#> <#if (!Generierter Code:
@Model testko.models.user <Form ID = "formEdit">@html.hiddenFor (model => model.id) <div> <div>@html.labelfor (model => model @class = "Form-control", data_bind = "value: editModel.name"}) </div> </div> <div> @html.labelfor (model => model.fullname, "fullname", new {@class = "control-label col-xs-2"}) <divname, @html.texdmodell (modell-modell), {divname @html. @class = "Form-control", data_bind = "value: editModel.fullname"}) </div> </div> <div> @html.labelfor (model => model.age, "age", new {@class = "Control-Label col-xs-2"}) <div> @htmgl.textBox, modell = @ @ @htmgl.tmgl.tmgl. "Form-control", data_bind = "value: editModel.age"}) </div> </div> <div> @html.labelforder (model => model.des, "Des", new {@class = "Control-Label col-XS-2"}) <Div> @html.TeTexS (modell). data_bind = "value: editModel.des"}) </div> </div> <div> @html.labelfor (model => model.createTime, "createTime", new {@class = "control-label col-xs-2"}) <divtmlaStmmmodel (modell). data_bind = "value: editModel.createTime"}) </div> </div> <div> @html.labelfor (model => model "Form-control", data_bind = "value: editModel.strCreateTime"}) </div> </div> <div> <button type src="~/Scripts/extensions/knockout.edit.js"></script><script type="text/javascript">$(function () {var model = @Html.Raw(Newtonsoft.Json.JsonConvert.SerializeObject(Model));var viewModel = {formId: "formEdit",editModel : model,urls :{submit : model.id == 0?Natürlich muss der Code auch geringfügig geändert werden. Durch Hinzufügen einer benutzerdefinierten Vorlagenseite müssen Sie nur zwei neue benutzerdefinierte Ansichten im vorderen Ende erstellen, solange das entsprechende Entitätsmodell erstellt wird, und eine einfache Ergänzung, Löschung, Änderung und Suche können abgeschlossen werden, ohne einen Satz von JS -Code zu schreiben.
3. Bindung der ausgewählten Komponente
Die obige Einführung führt die Syntax von T4 -Verpackungszusatz, Löschung, Modifikation und Suche ein. Alle Komponenten der Seite sind im Grunde Textfelder. In den tatsächlichen Projekten müssen jedoch viele Abfragen und Bearbeitungsseiten Dropdown-Boxen angezeigt werden. Wie sollen wir mit der Dropdown-Box umgehen? Wenn Sie es nicht geheim halten, geben Sie einfach eine Lösung. Zum Beispiel können wir die Datenquelle des Dropdown-Box im Hintergrund in der Bearbeitungsseite platzieren.
Einheit des Benutzers
[DataContract] Public Class User {[DataMember] public int id {get; Satz; } [DataMember] public String Name {get; Satz; } [DataMember] public String fullname {get; Satz; } [Datamember] public int age {get; Satz; } [DataMember] public String des {get; Satz; } [Datamember] public dateTime createTime {get; Satz; } [DataMember] public String StrCreateTime {get; Satz; } [DataMember] public String stababteilung {get; Satz; } [DataMember] öffentliche Objektabteilungen {get; Satz; }}Dann bearbeiten Sie die Seite
public actionResult edit (Benutzermodell) {modell.departments = AbteilungModel.getData (); Rückgabeansicht (Modell);}Binden Sie dann das vordere Ende.
<div> <label for = "txt_des"> Abteilung </Label> <select id = "sel_dept" data-bind = "Optionen: edayModel.Departments, OptionStext: 'Name', optionsValue: 'id', Wert: editModel.DepartmentID"> </select> </div> </div> </div> </div> </div>
Der JS -Code muss nicht geändert werden. Beim Hinzufügen oder Bearbeiten können Abteilungsfelder automatisch zum ViewModel hinzugefügt werden.
Natürlich werden die Dropdown-Boxen, die von vielen unserer Projekte verwendet werden, nicht einfach ausgewählt, da der einfache ausgewählte Stil wirklich hässlich ist, so dass viele ausgewählte Komponenten wie Select2, Multiselect usw. vom Blogger geteilt werden. Wenn Sie diese Komponenten verwenden, um die Auswahl zu initialisieren, werden Sie feststellen, dass das Dropdown-Feld auf der Schnittstelle kein einfaches Auswahl-Tag mehr ist, sondern aus vielen anderen Tags besteht, die von der Komponente angepasst werden. Nehmen wir die Select2 -Komponente als Beispiel, um festzustellen, ob es möglich ist, direkt nach dem oben genannten zu initialisieren.
Wir fügen den letzten Satz hinzu, um den von der Seite initiierten JS -Code zu bearbeiten:
<script type = "text/javaScript"> $ (function () {var model = @html.raw (newtonsoft.json.jsonconvert.SerializeObject (Modell)); var viewModel = {formalId: "formEdit", edioModel: modell, urls: {ordnen: model. "/User/update"}, validator: {fields: {name: {validators: {notEmimpty: {message: 'Der Name kann nicht leer sein!Durch die Ergänzungen und Änderungen ist dies in der Tat machbar! Analyse des Grundes, obwohl sich die Seite HTML nach der Initialisierung der Select2 -Komponente ändert, präsentiert die Komponente schließlich den ausgewählten Wert für das ursprüngliche SELECT -Steuerelement. Ich weiß nicht, ob andere ausgewählte Initialisierungskomponenten mit Ausnahme von Select2 so aussehen, und sie warten darauf, überprüft zu werden. Hier gibt es jedoch eine Sache zu erklären. Vor der Initialisierung von Select2 müssen die Optionen im Dropdown-Feld an den Wert gebunden sein, dh die Initialisierung der Komponente muss nach Ko.Applybinding () platziert werden.
4. Zusammenfassung
Zu diesem Zeitpunkt sind KO in Kombination mit Bootstraptable -Vorlagenerzeugung und Verwendung ausgewählter Steuerelemente im Grunde genommen verfügbar und muss natürlich noch verbessert werden. Wenn Sie Zeit später haben, sortiert der Blogger die Kombination anderer Front-End-Komponenten und KO, wie beispielsweise unsere häufigste Datumsregelung. Wenn Sie Fragen haben, hinterlassen Sie mir bitte eine Nachricht und der Editor wird allen rechtzeitig antworten. Vielen Dank für Ihre Unterstützung auf der Wulin.com -Website!