MVC2 model binding w/ many-to-many: at the cusp

ぐ巨炮叔叔 提交于 2019-12-08 09:16:45

问题


I'm an inch away from getting my Create form working. My problem is that some data passed into the form in the view model isn't being sent back in the postback.

Models:

Game:
    GameID - int (primary key, auto-incr)
    GameTitle - nvarchar(100)
    ReviewText - text
    ReviewScore - smallint
    Pros - text
    Cons - text
    LastModified - Datetime
    GenreID - int (foreign key from Genres)

Platform:
    PlatformID - int (primary key, auto-incr)
    Name - nvarchar(50)

GamePlatform (not visible as an EF 4 entity):
    GameID - int (foreign key from Games)
    PlatformID - int (foreign key from Platforms)

The view models I'm using:

public class PlatformListing
{
    public Platform Platform { get; set; }
    public bool IsSelected { get; set; }
}

public class AdminGameReviewViewModel
{
    public Game GameData { get; set; }
    public List<Genre> AllGenres { get; set; }
    public List<PlatformListing> AllPlatforms { get; set; }
}

And the form itself:

<%@ Control Language="C#" Inherits="System.Web.Mvc.ViewUserControl<HandiGamer.WebUI.ViewModels.AdminGameReviewViewModel>" %>

<p>
    <%: Html.Label("Game Title") %>
    <%: Html.TextBoxFor(model => Model.GameData.GameTitle) %>
    <%: Html.ValidationMessageFor(model => Model.GameData.GameTitle) %>
</p>
<p>
    <%: Html.LabelFor(model => Model.GameData.GenreID) %>
    <%: Html.DropDownListFor(m => Model.GameData.GenreID, new SelectList(Model.AllGenres, "GenreID", "Name", Model.GameData.GenreID)) %>
</p>
<p>
    <%: Html.Label("Platforms") %><br />
    <% for(var i = 0; i < Model.AllPlatforms.Count; ++i)
       { %>
           <%: Model.AllPlatforms[i].Platform.Name %> <%: Html.CheckBoxFor(p => Model.AllPlatforms[i].IsSelected) %>
    <% } %>
</p>
<p>
    <%: Html.Label("Review") %>
    <%: Html.TextAreaFor(model => Model.GameData.ReviewText) %>
</p>
<p>
    <%: Html.Label("Review Score") %>
    <%: Html.DropDownListFor(m => Model.GameData.ReviewScore,  new SelectList(new int[] {1, 2, 3, 4, 5}))%>
</p>
<p>
    <%: Html.LabelFor(model => model.GameData.Pros) %><br />
    <%: Html.TextAreaFor(model => model.GameData.Pros) %>
</p>
<p>
    <%: Html.LabelFor(model => model.GameData.Cons) %><br />
    <%: Html.TextAreaFor(model => model.GameData.Cons) %>
</p>

And, finally, my Create method (barebones as I'm trying to get this to work):

    [HttpPost]
    public ActionResult CreateReview([Bind(Prefix = "GameData")]Game newGame, [Bind(Prefix = "AllPlatforms")]List<PlatformListing> PlatformList)
    {
        try
        {
            foreach(var plat in PlatformList)
            {
                if (plat.IsSelected == true)
                {
                    newGame.Platforms.Add(plat.Platform);
                }
            }

            newGame.LastModified = DateTime.Now;

            _siteDB.Games.AddObject(newGame);
            _siteDB.SaveChanges();

            // add form data to entities, then save
            return RedirectToAction("Index");
        }
        catch
        {
            return View();
        }
    }

The problem is, of course, with my checkboxes. The boolean isSelected is being set fine, but when the data is being posted, the corresponding Platform object is missing. I thought they would automatically be passed back. So, any suggestions on how to pass back the actual Platform part of a PlatformListing?


回答1:


Regarding getting the checkbox values, how about using the strategy described here?

Regarding passing around entity objects as arguments, I'd say you're letting your data layer get mixed into your view layer, and you should use a dedicated ViewModel.



来源:https://stackoverflow.com/questions/4196247/mvc2-model-binding-w-many-to-many-at-the-cusp

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!