如何创建处理现有数据的编辑器模板

本文关键字:数据 编辑器 处理 何创建 创建 | 更新日期: 2023-09-27 17:56:44

我创建了一个编辑器模板来显示表单中包含的文本框。

    @model WebApplication1.Models.PersonViewModel
<input type="text" class="form-control" name="@ViewData.TemplateInfo.HtmlFieldPrefix" value=""/>

我只想在用于收集此模型数据的所有输入文本框中包含"form-control"类。

public class PersonViewModel
{ 
    [UIHint("_TextFormControl")]
    public string FirstName { get; set; }
    [UIHint("_TextFormControl")]
    public string LastName { get; set; }
    public int Age { get; set; }
}  

当表单开始时为空白时,这非常有用,但是,当我将模板用于预填充了数据的表单时,例如当我想要编辑现有模型时,我收到错误消息:"传递到字典中的模型项类型为'System.String',但此字典需要类型为'WebApplication1.Models.PersonViewModel'的模型项。

这是我的控制器:

 // GET: /Person/Edit/5
    [HttpGet]
    public ActionResult Edit(int? id)
    {
        if (id == null)
        {
            return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
        }
        Person person = db.Persons.Find(id);
        if (person == null)
        {
            return HttpNotFound();
        }
        return View(person);
    }

如何允许此编辑器与现有数据以及新表单一起使用?

如何创建处理现有数据的编辑器模板

您已经为 typeof PersonViewModel 创建了一个EditorTemplate,但您对应用于 typeof string[UIHint("_TextFormControl")]的使用意味着您将string传递给模板,而不是PersonViewModel 。目前还不清楚您在这里想要实现的目标,但根据您当前的模型,他的模板需要

@model String
@Html.TextBox("") // or @Html.TextBoxFor(m => m)

但是,这与在视图中使用@Html.EditorFor(m => m.FirstName)(或TextBoxFor())相同。您可能会做这样的事情的一个原因是生成多个 html 元素,例如

@model String
@Html.Label("")
@Html.TextBox("")
@Html.ValidationMessage("")

以便在主视图中使用 @Html.EditorFor(m => m.FirstName) 将生成验证消息的标签、文本框和占位符。

但是,使用自定义编辑器模板的真正好处之一是,当您将它们用于复杂类型并希望为这些类型提供一致的 UI 时。例如,您可以为类型创建模板 PersonViewModel 。在/Views/Shared/EditorTemplates/PersonViewModel.cshtml中(请注意,模板的名称必须与类型名称匹配)

@model WebApplication1.Models.PersonViewModel
<div>
  @Html.LabelFor(m => m.FirstName)
  @Html.TextBoxFor(m => m.FirstName)
  @Html.ValidationMessageFor(m => m.FirstName)
</div>
<div>
  @Html.LabelFor(m => m.LastName)
  @Html.TextBoxFor(m => m.LastName)
  @Html.ValidationMessageFor(m => m.LastName)
</div>
.... // ditto for other properties of PersonViewModel

然后在主视图中

@model WebApplication1.Models.PersonViewModel
@Html.EditorFor(m => m)

这也适用于PersonViewModel集合,并为集合中的每个PersonViewModel生成一个编辑器模板

@model IEnumerable<WebApplication1.Models.PersonViewModel>
@Html.EditorFor(m => m)

同样,如果您有另一个包含属性public PersonViewModel Person { get; set; }的模型,则可以使用@Html.EditorFor(m => m.Person)

旁注:

  1. 您声称"当表单开始时为空白时,这很好用"表示您没有将新的PersonViewModel实例传递给您的查看"创建"方法,这是不好的做法。您的控制器方法应将实例传递给视图。
  2. 手动构造输入元素的当前模板不起作用,因为您从未设置 value 属性。在此外,您不添加用于客户端的data-val-*属性侧面验证。始终使用强类型的 html 帮助程序来生成您的 HTML,以便您获得正确的 2 向模型绑定并采取MVC 所有内置功能的优势。