I have a partial view that contains a few <div>s that look the same and every each of them in their turn contain a DropdownList. Now, selected values in the DropdownLists usually different. And initial list of values comes from some external source.
So that would’t work:
public PartialViewResult GetMeals()
{
var meals = DataContext.GetMeals();
ViewBag.Units = new SelectList(DataContext.GetUnits,"Id","Name");
return PartialView("_Meals", meals);
}
@foreach (var m in Meals)
{
<div>
@Html.DropDownList("Units", ViewBag.Units as List<SelectListItem>)
<dig>
I can of course create another partial view for each Meal, but I don’t wanna get into a partial views hierarchy and create Partial inside another Partial (Although Leo DiCaprio would’ve love that)
Can you guys give me an advice?
Here’s what I would do. This first thing is to get rid of ViewBag. Then define a view model:
Inside this view model you put only what your view (partial view in this case) needs.
and then I would have my controller action populate this view model by aggregating data from wherever you want:
and inside the partial
_MealsI would use editor templates:and finally I would define an editor template for a meal: (
~/Views/Shared/EditorTemplates/MealViewModel.cshtml) which will be rendered for each element of the model:Now more loops, casts, wrongly named input controls. You get strongly typed, Intellisense enabled views, yummy 🙂
Now when you look at the controller action there must be something that bothers you: this repetitive mapping code between your domain models and the view models. Enter the world of AutoMapper and you will get really pretty code.