我正在尝试创建一个允许使用MVC创建和编辑实体层次结构的表单。
顶级是项目,可以有1个或多个与之关联的环境。环境是预定义的,例如Dev,Test和Prod。
对于添加的每个环境,可以添加多个接口。
因此用户可以输入项目信息。选择相关的环境,然后为每个环境部分添加几个接口。
我创建了3个视图模型,项目,环境和界面。像这样
public class ProjectViewModel
{
public int Id { get; set; }
public string ProjectTitle { get; set; }
public List<SelectListItem> EnvironmentChoices { get; set; }
public List<EnvironmentViewModel> EnvironmentModel { get; set; }
}
public class EnvironmentViewModel
{
public IList<InterfaceViewModel> Interfaces { get; set; }
public string Environment { get; set; }
}
public class InterfaceViewModel
{
public string InterfaceName { get; set; }
}
然后为环境模型和界面模型创建了1个项目模板和2个编辑器模板。就像这样
<p>
@Html.LabelFor(x => x.ProjectTitle)
@Html.TextBoxFor(x => x.ProjectTitle)
@Html.ValidationMessageFor(x => x.ProjectTitle)
</p>
<p>
@Html.LabelFor(x => x.EnvironmentModel)
@for (int i = 0; i < Model.EnvironmentChoices.Count; i++)
{
@Html.CheckBoxFor(m => m.EnvironmentChoices[i].Selected, new { id = Model.EnvironmentChoices[i].Value })
@Html.HiddenFor(m => m.EnvironmentChoices[i].Value)
@Html.DisplayFor(m => m.EnvironmentChoices[i].Text)
}
</p>
<p>
@Html.EditorFor(x => x.EnvironmentModel)
</p>
用于环境模板
@model EnvironmentViewModel
<fieldset style="margin-left: -10px;">
<legend>@Model.Environment</legend>
@Html.ActionLink("Add Interface", "AddInterface", Model, new { @class = "button icon-file-plus" })
@Html.EditorFor(x => x.Interfaces)
</fieldset>
用于界面模板
@model InterfaceViewModel
<p>
@Html.LabelFor(x => x.InterfaceName)
@Html.TextBoxFor(x => x.InterfaceName)
@Html.ValidationMessageFor(x => x.InterfaceName)
</p>
我发现当我点击环境部分的添加按钮时。控制器只选择环境模型并丢失项目模型上下文,因此无法修改它以添加新的接口模型。
我是以错误的方式解决这个问题吗?如果是这样,是否有最佳实践的例子。如果没有,我做错了什么。
由于
答案 0 :(得分:0)
感谢Stephen Muecke指出我正确的方向。
我发现这个例子非常接近我想要实现的目标
http://jarrettmeyer.com/post/2995732471/nested-collection-models-in-asp-net-mvc-3
基本上它使用MVC来动态呈现JavaScript,这反过来又会将一个详细视图模型添加到符合MVC索引约定的表单中。因此,当主模型和子模型被回发时,整个事物就被绑定到一个大的分层模型。