Главная страница Случайная страница КАТЕГОРИИ: АвтомобилиАстрономияБиологияГеографияДом и садДругие языкиДругоеИнформатикаИсторияКультураЛитератураЛогикаМатематикаМедицинаМеталлургияМеханикаОбразованиеОхрана трудаПедагогикаПолитикаПравоПсихологияРелигияРиторикаСоциологияСпортСтроительствоТехнологияТуризмФизикаФилософияФинансыХимияЧерчениеЭкологияЭкономикаЭлектроника |
Динамические формы
Я уже писал статью на эту тему. Но то был asp.net mvc первый, а сейчас можно сделать все на много проще. Значит, проблема заключается в следующем. Мы на post-action в контроллере принимаем объект, у которого, заранее не известно количество полей. Например, это будет следующая структура: public class Ownership { public string Name { get; set; }
public int Price { get; set; } } public class Customer { public int ID { get; set; }
public string Name { get; set; }
public Dictionary< string, Ownership> Ownerships { get; set; } }
Можно использовать и List вместо Dictionary, но, в будущем, будут проблемы с валидацией для определенного элемента.
Создадим контроллер: public class CustomerController: DefaultController { [HttpGet] public ActionResult Edit(int id) { return View(new Customer() { Ownerships = new Dictionary< string, Ownership> () }); } [HttpPost] public ActionResult Edit(Customer customer) { if (ModelState.IsValid) { } return View(customer); } } В БД мы не будем ничего записывать, поэтому здесь просто заглушка. Добавляем View: @model LessonProject.Models.Info.Customer
@{ ViewBag.Title = " Edit"; Layout = " ~/Areas/Default/Views/Shared/_Layout.cshtml"; } @section scripts { @Scripts.Render(" /Scripts/default/customer-edit.js") }
< h2> Edit< /h2>
@using (Html.BeginForm(" Edit", " Customer", FormMethod.Post, new { @class = " form-horizontal" })) { < fieldset> @Html.Hidden(" ID", Model.ID) < div class=" control-group" > < label class=" control-label" for=" Email" > Name< /label> < div class=" controls" > @Html.TextBox(" Name", Model.Name, new { @class = " input-xlarge" }) @Html.ValidationMessage(" Name") < /div> < /div> < div id=" OwnershipListWrapper" > < div class=" btn" id=" AddOwnership" > Добавить< /div> @foreach (var keyValuePair in Model.Ownerships) { @Html.Partial(" OwnershipItem", keyValuePair) } < /div>
< div class=" form-actions" > < button type=" submit" class=" btn btn-primary" > Ок< /button> < /div> < /fieldset> }
keyValuePair переносим в PartialView (/Areas/Default/Views/Customer/OwnershipItem.cshtml): @model KeyValuePair< string, LessonProject.Models.Info.Ownership>
< div class=" OwnershipWrapper" > < div class=" btn remove-line" > Удалить< /div>
< div class=" control-group" > < label class=" control-label" > Имя < /label> < div class=" controls" > @Html.TextBox(" Ownerships[" + Model.Key + " ].Name", Model.Value.Name, new { @class = " input-xlarge" }) @Html.ValidationMessage(" Ownerships[" + Model.Key + " ].Name") < /div> < /div> < div class=" control-group" > < label class=" control-label" > Цена < /label> < div class=" controls" > @Html.TextBox(" Ownerships[" + Model.Key + " ].Price", Model.Value.Price, new { @class = " input-xlarge" }) @Html.ValidationMessage(" Ownerships[" + Model.Key + " ].Price") < /div> < /div> < /div>
Js-обработчик состоит из обработки кнопок добавления и удаления (/Scripts/default/customer-edit.js): function CustomerEdit() { _this = this;
this.ajaxAddOwnership = " /Customer/AddOwnership";
this.init = function () { $(" #AddOwnership").click(function () { $.ajax({ type: " GET", url: _this.ajaxAddOwnership, success: function (data) { $(" #OwnershipListWrapper").append(data); } }) });
$(document).on(" click", ".remove-line", function () { $(this).closest(".OwnershipWrapper").remove(); }); } }
var customerEdit = null; $().ready(function () { customerEdit = new CustomerEdit(); customerEdit.init(); }); При нажатии на кнопку «добавить», мы получаем по ajax-запросу часть уже сформированный и добавим к списку. При удалении по клику, просто удалим ряд значений, найдя ближайший OwnershipWrapper. Обратите внимание на создание глобального обработчика для remove-line. Это необходимо для того, чтобы динамически созданные кнопки тоже обрабатывали этот клик. Добавим обработчик в CustomerController, используя уже созданный нами View OwnershipItem.cshtml: public ActionResult AddOwnership() { return View(" OwnershipItem", new KeyValuePair< string, Ownership> ( Guid.NewGuid().ToString(" N"), new Ownership())); }
|