0

Hi I am still new to MVC4, I would like to use HTML helper to create a select box that would allow users to select multiple items using CTRL Click and store results using EF. Here is my view

@model AtomicQuestionnaire.Models.Questionnaire

@{
    ViewBag.Title = "Create";
}

@{
    var ListInterest = new List<SelectListItem>()
{
new SelectListItem(){Value="Stamp Collecting",Text="Stamp Collecting"},
new SelectListItem(){Value="Listening to Music",Text="Listening to Music"},
new SelectListItem(){Value="Reading",Text="Reading"}
};




}

<h2>Create</h2>



@using (Html.BeginForm()) {
    @Html.AntiForgeryToken()
    @Html.ValidationSummary(true)

        <div class="editor-label">
            @Html.LabelFor(model => model.Interest)
        </div>
        <div class="editor-field">
            @Html.ListBoxFor(model => model.Interest, ListInterest, new { size = "15", Multiple = "multiple" })
            @Html.ValidationMessageFor(model => model.Interest)
        </div>

        <p>
            <input type="submit" value="Create" />
        </p>
    </fieldset>
}

And here is my model

public class Questionnaire
{
    public int ID { get; set; }
    public string Name { get; set; }
    public string City { get; set; }
    public string VisitorDesc { get; set; }
    public string Interest { get; set; }
    public int SiteRating { get; set; }
}

and my controller for create action

[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Create(Questionnaire questionnaire)
{
    if (ModelState.IsValid)
    {
        db.Questionnaires.Add(questionnaire);
        db.SaveChanges();
        return RedirectToAction("Index");
    }

    return View(questionnaire);
}

I was only able to store the first item of the html selection box to database. Would you be able to tell me what I did wrong? I would like to store all selected items into DB. Thanks

3
  • Shouldn't it be a collection of Questionnaires you handle, and not just a single object? Commented Dec 7, 2013 at 19:04
  • Any recommendation/correction is appreciated as I am still new to .Net world. Thanks. Commented Dec 7, 2013 at 19:07
  • Try checking out this one: stackoverflow.com/questions/18104110/… to see if it sheds some light :) Commented Dec 7, 2013 at 19:13

1 Answer 1

1

Since you want to select multiple listbox values you have to define your model's property as

public virtual ICollection<Interest> Interests { get; set; },

not as

public string Interest { get; set; }

If Interests property is collection, you will need a separate table to store them (separate entity at the EF level).

public class Interest
{
    public int ID { get; set; }
    public string Title { get; set; }
    public virtual ICollection<Questionnaire> Questionnaires { get; set; }
}

For there entities EF will generate Interests table and a junction table to store Questionnaire-Interest associations.

The view:

@{
    var ListInterest = new List<SelectListItem>() //hard-code, better load interests from db
{
new SelectListItem(){ Value = 1, Text="Stamp Collecting" },
new SelectListItem(){ Value=2, Text="Listening to Music" },
new SelectListItem(){ Value=3, Text="Reading"}
}; 

Html.ListBoxFor(c => c.Interests,
                new MultiSelectList(ListInteres, "Value", "Text"))

Notice, that Interest Entities must exist in db (or SaveChanges will raise an exception). You can add them manually for now or write a separate add/edit page.

Sign up to request clarification or add additional context in comments.

6 Comments

Thanks for your help. I tried that but none of the listbox values were stored. I removed the connections and the db file from app-data and rebuilt. And found out that the DB column Interest was not created at all.
My bad, forgot about db. Collection properties cannot be stored in a single column, you need a separate table for them. Please see my update.
Thanks again. How should I update the view appropriately from the following. Sorry for noobish question <div class="editor-field"> @Html.ListBoxFor(model => model.Interest, ListInterest) @Html.ValidationMessageFor(model => model.Interest) </div>
Also for the sake of simplicity, is there any way to just concat all the selected options as one string and store in a string field instead of a collection? Thanks.
Of course, you can do the following: 1) Declare ICollection<string> property in the model. It will not be saved (cause EF does not save collections in single column), but still will be bound. But then you will need one more property to store concatenated values and pass it to db. (Smth like model.InterestsConcatenated = string.Join(",", Model.Interests);) Or, you can separate the domain model from the view model. 2) Grab values directly from Request.Form and concatenate them to a single string.
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.