ASP.MVC 3 Razor Add Model Prefix to the Html.PartialView Extension

I have all the same questions that he has . ASP.NET MVC partial views: name input prefixes

I am trying to create CRUD operations for these data objects:

public class UserViewModel { protected virtual Id {get; set;} public virtual string Login { get; set; } public virtual string Password { get; set; } public virtual ZipCodeViewModel ZipCode { get; set; } } 

Zip Code Object:

 public class ZipCodeViewModel { public virtual string City { get; set; } public virtual string State { get; set; } public virtual string Zip { get; set; } } 

I also have a partial view of ZipCode that used UserViewModel.ZipCode:

 @model ZipCodeViewModel @Html.TextBoxFor(x => x.Zip, new { id = "ZipCode", name = "ZipCode.Zip", maxlength = "5" }) 

I am going to use ZipCodePartialView on another page (e.g. user).

 @model UserViewModel ..... @{Html.RenderPartial("Zipcode", Model.ZipCode);} 

When MVC saves the User ZipCode field, the Zip is empty.

So the question is, how can I add a model prefix to the patriarch?

+6
asp.net-mvc-3 razor
source share
4 answers

Try this extension:

 public static void RenderPartialWithPrefix(this HtmlHelper helper, string partialViewName, object model, string prefix) { helper.RenderPartial(partialViewName, model, new ViewDataDictionary { TemplateInfo = new System.Web.Mvc.TemplateInfo { HtmlFieldPrefix = prefix } }); } 
+11
source share

Instead of using Html.RenderPartial() put your partial view in Shared / EditorTemplates / and name its type name (in this case ZipCodeViewModel ). Then you can use Html.EditorFor() passing in the expression for the property. EditorFor () is the correct field prefix so that the mediator in MVC can correctly place your data.

So something like this

 @model UserViewModel ..... @Html.EditorFor(m => m.ZipCode); 

I will try to dig out some links and resources, but I want to get an answer for you.

EDIT : This blog post seems to cover the basics of the EditorFor () extension and EditorTempaltes: ASP.NET MVC Tips: Tempaltes Editor

In any case, when you use the extensions Html.TextBoxFor() or Html.DropDownFor() , what they do is to get the full name of the property from the expression you are passing into and set the attributes of the name and identifier of the HTML element for it. An example could be:

 @Html.TextBoxFor(m => m.Person.FirstName) 

will display

 <input id="Person_FirstName" name="Person.FirstName" type="text" value="<what ever was in FirstName>" /> 

These input names and values ​​are key / value pairs in the message data. The ASP.NET MVC middleware, by default, attempts to map these keys to models that include the actions of your controller. If he can find a match, he sets the value.

So your problem above is probably because the input names in your partial view are from ZipCodeViewModel down, but your action accepts UserViewModel . EditorFor() a name prefix for you, so it can basically display a partial view that will send data back that can be bound to you. Although you yourself could set the name attributes on the input elements (or flatten everything, as you said in the comments), there are these helpers to do this for you.

I hope this helps explain what is happening and a possible solution for you.

+10
source share

As it turned out, EditorTemplates is the way to go. (first comment on this entry: http://thatextramile.be/blog/2011/01/prefixing-input-elements-of-partial-views-with-asp-net-mvc )

Just add ZipCodeViewModel.cshtml to the EditorTemplates folder, which can be inside Views / Shared if you want. Then use, @ Html.EditorFor (m => m.ZipCode). It works like magic.

0
source share

You can use the following code:

 ActionResult MyAction(UserViewModel model) { TryUpdateModel(model.ZipCode); } 

So, the model updates well twice. Second time for your partial.

-one
source share

All Articles