views:

524

answers:

3

I have this action:

public ActionResult Add([Bind(Include = "Title,Description")] product product2Add){ --SNIP-- }

I'm using a view model pattern where I've created a special "AddProduct_ViewModel" class that contains my product class and anything else I need in my view. That includes 2 dropdownlists; one that does a DB lookup of all the various product catagories, and another that lists the product suppliers.

When I do validation on my product that fails I cannot see how to easily save the state of my dropdownlists (without doing some lengthy db code). Is there a better way?

A: 

Well.. in MVC there is no viewstate, so controls can't save state, although you can use some tricks with storing it in a cookie using javascript - preferably jquery, or saving this information to the server side in onChange event.

Michal Rogozinski
+1  A: 

in the controller you can call:

Request.Form.Get("MyDropDownListId");

To get the selected option's value attribute.

While building up the dropdownlist again after postback, you can use this value to re-set the selected item.

Example of setting the selected item in the view when you have a property "PageSize" in your Model:

Response.Write(Html.DropDownList("pageSize",
            Model.PageSizes.ToSelectList(p => p.ToString(), p => p.ToString(), p => p.Equals(Model.PageSize))));

With extension method ToSelectList():

public static List<SelectListItem> ToSelectList<T>(this IEnumerable<T> enumerable, Func<T, string> text, Func<T, string> value, Func<T, bool> selected)
{
    var items = enumerable.Select(f => new SelectListItem() { Text = text(f), Value = value(f) }).ToList();
    return items;
}
Thomas Stock
In short - controller action should accept ddl data through parameters and pass them back. Right?
Arnis L.
yes you can use a parameter "string MyDropDownListId" or you can use the Request.Form NameValueCollection if you don't want to bother with parameters
Thomas Stock
And indeed, you need to pass the selected value back to your view after postback.You can avoid this using AJAX.
Thomas Stock
A: 

The best way i have found is like this.

viewmodel:

public class ViewModel
{
    public int? DropdownValue { get; set; }
}

view:

<%@ Page Language="C#" Inherits="System.Web.Mvc.ViewPage<ViewModel>" %>
<%= Html.DropDownList("DropdownValue") %>

controller:

public ActionResult Edit()
{
    ViewData["DropdownValue"] = CreateListOfSelectListItem();
    View(GetViewModelFromDb());
}

[AcceptVerbs(HttpVerbs.Post)]
public ActionResult Edit(ViewModel postedData)
{
    ViewData["DropdownValue"] = CreateListOfSelectListItem();
    UpdateDb(postedData);
    View();
}

This method keeps your viewmodel clean of the select options, and uses the model state so you can easily add validation. If you an option without a value, you can just validate on not null.

Hope it helps.

AndreasN