8

I have all most the same question as him ASP.NET MVC partial views: input name prefixes

I am tring to create CRUD operations for this data entities:

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 entity:

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

I also have partial view ZipCode which used UserViewModel.ZipCode:

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

I am going to use ZipCodePartialView in another Page (for example user).

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

When MVC save User ZipCode field Zip is empty.

So question is how I can add model prefix to the patrial View?

4
  • How do you load your object ? Is you ISession opened ? Do you use lazy loading ? Commented Feb 4, 2011 at 13:13
  • 1
    Are you saying that the data from ZipCode never makes it onto the rendered page? Or are you saying that when you post data back the data never gets populated into the model? Commented Feb 4, 2011 at 13:28
  • All data from ZipCode always makes it intro the rendered page. Commented Feb 4, 2011 at 13:39
  • Found a better answer at stackoverflow.com/questions/1488890/… Commented Feb 23, 2012 at 3:29

4 Answers 4

14

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 } }); } 
Sign up to request clarification or add additional context in comments.

Comments

10

Instead of using Html.RenderPartial() put your partial view in Shared/EditorTemplates/ and name it the name of the type (in this case ZipCodeViewModel). Then you can use Html.EditorFor() passing in the expression for the property. EditorFor() prefixes the fields correctly so that the model binder in MVC can put your data in place correctly.

So something like this

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

I'll try to dig up some links and resources but wanted to get the answer out there for you.

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

Anyway, when you use those Html.TextBoxFor() or Html.DropDownFor() extensions, what they do is get the full name of the property from the expression you pass in and set the HTML input element's name and id attributes to that. Example could be:

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

would render

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

Those input names and values are the key/value pairs in the post data. The default ASP.NET MVC model binder tries to match those keys up to the models your controller actions take in. If it can find a match then it sets the value.

So your problem above is probably because the input names in your partial view are from the ZipCodeViewModel down but your action is taking in a UserViewModel. The EditorFor() prefixes the names for you so it can basically render a partial view that will post data back that can be bound for you. Although you could set the name attributes yourself on the input elements (or flatten everything as you suggested in the comments) has these helpers in there to do it for you.

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

4 Comments

I can just add fields from my ZipCode model to User model and all works. But then i have to create the ZipCode view in the View. It isn`t good implementation of the MVC. And I goona get something like UserControl, which I can use in the various places of my program.
I would recommend not cluttering up your User model if you don't need/want to and the EditorFor() helper with the EditorTemplates create a reusable partial view. I believe this is what you are after.
Thank you for anwser, but this soulutions no good for me. EditorFor() helper don`t allow to use controller. My partial view has own logic. I have to do somethink like this - stackoverflow.com/questions/1488890/…
Whammy! This was exactly what I was searching for.
0

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

Simply add ZipCodeViewModel.cshtml to an EditorTemplates folder, which can sit inside Views/Shared if you want. Then use, @Html.EditorFor(m => m.ZipCode). Works like magic.

Comments

-1

You can the following code:

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

So model well be updated twice. Second time for your partial.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.