MVC3 Model Lifecycle
I'm hoping someone can clarify how a model should progress through postbacks given the following example:
MyModel
public class MyModel
{
public string Text { get; set; }
public List<RadioButtonListItem> Options { get; set; }
public MyModel()
{
//Initialize the options.
this.Options = new List<RadioButtonListItem>()
{
//Setting Text, Value and Group Name. 3rd is selected by default.
new RadioButtonListItem("Item 1", "1", "Options"),
new RadioButtonListItem("Item 2", "2", "Options"),
new RadioButtonListItem("Item 3", "3", "Options", true)
};
}
}
RadioButtonListItem
public class RadioButtonListItem
{
[HiddenInput]
public string Value { get; set; }
[HiddenInput]
public string Text { get; set; }
[HiddenInput]
public string GroupName { get; set; }
[HiddenI开发者_如何学编程nput]
public string SelectedValue { get; set; }
[TemplateVisibility(ShowForEdit = false)]
public override bool Selected { get { return string.Equals(this.Value, this.SelectedValue); } set { this.SelectedValue = (value ? this.Value : null); } }
public RadioButtonListItem() { }
public RadioButtonListItem(string value, string text, string groupName) : this(value, text, groupName, false) { }
public RadioButtonListItem(string value, string text, string groupName, bool selected)
{
//...
}
}
- Controller fires Index view, passing a new model. Options are defaulted, third option is selected by default.
- Now, the form fields that are rendered include basically the entire model, including the value, text and group name of each RadioButtonListItem.
- User fills in the form and clicks Submit button.
- HttpPost controller receives the model. The model is repopulated from the posted data, including the RadioButtonListItems and all of their properties.
- Some form entry is incorrect so the same model instance is sent back to the view, that way the user's entries and selections are preserved.
- The user fixes the error, re-submits the form, all is good.
Summary
This seems weird to me because I don't really think you should have to send back the original metadata so that the model state can be persisted. But if you don't send it back, what do you do? I can think of only one other option: during the post-back create a second model instance and copy the user's selections to the new instance and feed that back to the view.
But that doesn't seem right to me. Can someone clarify how this is supposed to work?
I wasn't thinking clearly when I asked this question. The items in the list, of course, don't need to be sent back with the post data. You simply keep a separate list in the model which you initialize in the constructor and then have an int
field which is the ID or key of the item that was selected from the list.
The model looks like this:
[Required]
[DataType("RadioButtonList")]
[Display(Name = "Format", Order = 2)]
[AdditionalMetadata("Style", "Wide")]
[AdditionalMetadata("List", "Items")]
public int? SelectedItem { get; set; }
[TemplateVisibility(ShowForDisplay = false, ShowForEdit = false)]
public List<ListItem> Items { get; set; }
It points to it's own list with the AdditionalMetaData
attribute. So you can easily have the RadioButtonList EditorTemplate
load up the list and just send back which item was selected. That value will be populated in the SelectedItem
property.
精彩评论