我有一个基类,一组子类和一个集合容器,我用它来使用部分视图动态创建和填充控件。
// base class
public class SQControl
{
[Key]
public int ID { get; set; }
public string Type { get; set; }
public string Question { get; set; }
public string Previous { get; set; }
public virtual string Current { get; set; }
}
// subclass
public class SQTextBox : SQControl
{
public SQTextBox()
{
this.Type = typeof(SQTextBox).Name;
}
}
//subclass
public class SQDropDown : SQControl
{
public SQDropDown()
{
this.Type = typeof(SQDropDown).Name;
}
[UIHint("DropDown")]
public override string Current { get; set; }
}
// collection container used as the Model for a view
public class SQControlsCollection
{
public List<SQControl> Collection { get; set; }
public SQControlsCollection()
{
Collection = new List<SQControl>();
}
}
我在运行时根据需要用不同的SQControl子类填充Collection控件,而在EditorTemplates中,我为每个子类都有一个单独的视图。在集合项上使用Html.EditorFor,我可以使用适当的控件动态生成表单。
一切正常。
我遇到的问题是,当我保存表单时,MVC绑定无法分辨创建Collection中每个项目的子类,而是将它们绑定到基类SQControl的实例。
这会混淆View引擎,因为它无法确定要加载的正确视图,只是加载默认值。
我目前的解决方法是将子类的“Type”保存为模型中的字段,并在回发时,我将集合复制到一个新容器中,使用适当的子类重新创建每个对象。 “类型”字段中的信息。
public static SQControlsCollection Copy(SQControlsCollection target)
{
SQControlsCollection newCol = new SQControlsCollection();
foreach (SQControl control in target.Collection)
{
if (control.Type == "SQTextBox")
{
newCol.Collection.Add(new SQTextBox { Current = control.Current, Previous = control.Previous, ID = control.ID, Question = control.Question });
}
else if (control.Type == "SQDropDown")
{
newCol.Collection.Add(new SQDropDown { Current = control.Current, Previous = control.Previous, ID = control.ID, Question = control.Question });
}
...
}
return newCol;
}
所以我的问题是,有没有更好的方法来维护回发之间的基类型集合中的项目类型?我理解在MVC中为每个模型创建一个类型视图,但我希望能够使用可重用的部分视图基于XML文档动态构建视图。