在我正在编写的ASP.Net MVC 5应用程序中,一个Material
可以有多个名称(MaterialName
s)。我已经构建了一个Web界面,用于在材料的Edit
和Create
页面上添加,编辑和删除材料的名称。为实现此目的,我在名为text
的网页上有多个input
- Material.MaterialNames
。可以使用javascript添加和删除客户端以更改名称的数量。我不需要name
的{{1}} s中的索引,因为用户应该看到和编辑的数据只是一个扁平的字符串列表。
这些是我模特的相关部分:
input
如果public class MaterialVM
{
public Material Material { get; set; }
// ...
}
public class Material
{
public int Id { get; set; }
public List<MaterialName> MaterialNames { get; set; }
// ...
}
public class MaterialName
{
public int Id { get; set; }
public string Name { get; set; }
public int MaterialId { get; set; }
}
类型为Material.MaterialNames
,那么现在一切都会好起来的。在我的情况下,模型绑定器不能从作为表单数据传递的多个字符串值创建List<string>
。我相信修复此问题的默认方法是
编写自定义模型绑定器
像in this answer一样(=覆盖MaterialName
并只更改一个PropertyType的行为)是不是一个好主意?我会将globally registering the binder与BindProperty
类型结合起来。
我是否想念一个更简单的选项?
是不是可以只提供默认绑定器一种方法来转换/转换/序列化/ ...简单类型到复杂类型?我的方法是如何正确编写自定义模型绑定器的?我还缺少哪些其他选项会让这更直观吗?
答案 0 :(得分:2)
您可以使用默认模型绑定器绑定复杂类型,但需要向重复控件的模板添加.Index
属性。
这是我能想到的最简单的例子:
@model WebApplication25.Models.MaterialVM
@using (Html.BeginForm())
{
@Html.HiddenFor(model => model.Material.Id)
<table id="output">
<tr>
<th>Name</th>
<th>MaterialId</th>
<th>Id</th>
</tr>
</table>
<button id="add-more" type="button">Add Another</button>
<button type="submit">Submit</button>
}
@section scripts{
<script>
(function (window) {
"use strict";
var index = 0;
$("#add-more").on("click", function () {
$("#output").append(
"<tr><td>" +
"<input type='hidden' name='Material.MaterialNames.Index' value='" + index + "' />" + // add in the index
"<input type='text' name='Material.MaterialNames[" + index + "].Name' /></td>" +
"<td><input type='number' name='Material.MaterialNames[" + index + "].MaterialId' /></td>" +
"<td><input type='number' name='Material.MaterialNames[" + index + "].Id' />" +
"</td></tr>");
index++;
});
}(window));
</script>
}
答案 1 :(得分:1)
视图模型应该适应视图,因此应该有一个
List<string> materialNames
MVC绑定将绑定到视图模型。
然后在控制器或您处理映射的任何层中,您可以将 MaterialVM 映射到材料。
答案 2 :(得分:0)
如果您将MaterialVM
缓存在会话变量中,或Id
和MaterialNames
缓存Dictionary<int, List<string>>
,那么您可以回复id
的操作和List<string>
名称。使用id
,您可以查找材料,然后更新模型。
或者,在JS中,您可以JSON.stringify
表单数据,然后在服务器端解析它。