EditorTemplate的复杂类型的列表返回null,而EditorTemplate其元素工作正常 [英] EditorTemplate for List of complex type returns null, while EditorTemplate for its elements works fine

查看:207
本文介绍了EditorTemplate的复杂类型的列表返回null,而EditorTemplate其元素工作正常的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个视图中,用户可以通过选择checkboxex选择任意数量的俱乐部。该俱乐部与类型List &LT主模型的属性; ClubModel >。
虽然重构我开始了这一点:

I have a View in which the user can choose any number of Clubs by selecting checkboxex. The Clubs are a property of the main model with type List<ClubModel>. While refactoring I start out with this:

@using (Html.BeginForm())
{
    <fieldset>
        <legend>Voor Select clubs </legend><br />
    <table>
        <tr>
            @for (var i = 0; i < Model.Clubs.Count; i++)
            {
                if (i % 3 == 0)
                {
                    @:</tr><tr> 
                }
                <td>
                    @Html.HiddenFor(model => model.Clubs[i].ClubID)
                    @Html.EditorFor(model => model.Clubs[i].IsAvailable)
                </td> 
                <td>@Html.DisplayFor(model => model.Clubs[i].ClubName)</td>
             }
        </tr>
     </table>
        <input type="submit" value="Submit" />
    </fieldset>
}

这工作正常:该模型是用填充俱乐部属性返回

This works fine: the model is returned with a populated Clubs property.

现在我拿出了&LT; TD >标签,并将其移动到EditorTemplate:

Now I take out the <td> tags and move them to an EditorTemplate:

@using (Html.BeginForm())
{
    <fieldset>
        <legend>Select Clubs </legend><br />
           <table>
        <tr>
            @for (var i = 0; i < Model.Clubs.Count; i++)
            {
                if (i % 3 == 0)
                {
                    @:</tr><tr> 
                }
               @Html.EditorFor(model=>model.Clubs[i])
             }
        </tr>
     </table>
        <input type="submit" value="Submit" />
    </fieldset>
}

这仍然有效(未显示模板)。

This still works (template not shown).

现在我想得动循环的EditorTemplate:

Now I want to move the loop too to an EditorTemplate:

@using (Html.BeginForm())
{
    <fieldset>
        <legend> Select Clubs</legend><br />
        <EditorFor(model=>model.Clubs,"ListOfClubs")
         <input type="submit" value="Submit" />
    </fieldset>
}

我正式创建一个名为EditorTemplate'ListOfClubs

I duly create a EditorTemplate named 'ListOfClubs':

@using InvallersManagementMVC3.ViewModels;
@model List<StandInClubModel>
@{
    Layout = null;
}
<!DOCTYPE html>
<html>
<head>
</head>
<body>
    <table>
        <tr>
            @for (var i = 0; i < Model.Count; i++)
            {
                if (i % 3 == 0)
                {
                    @:</tr><tr> 
                }
                <td>
                    @Html.HiddenFor(model => model[i].ClubID)
                    @Html.EditorFor(model => model[i].IsAvailable)
                </td> 
                <td>@Html.DisplayFor(model => model[i].ClubName)</td>
             }
        </tr>
     </table>
</body>
</html>

此正确显示了复选框的IsAvailable财产的俱乐部,但现在上发布了该模型的俱乐部属性为null!

This correctly shows the clubs with checkboxes for the IsAvailable property, but now on posting the Clubs property of the model is null!

我在哪里去了?

编辑:
我试图实现用异丙基苯的回答是:

I tried to implement Cymen's answer by using:

@Html.EditorFor(model=>model.Clubs,"ClubModel") 

或指定elementtemplate同时使这些元素的列表。不过我迎接一个例外:
System.InvalidOperationException了用户code未处理
  消息=传递到字典的模型项的类型是System.Collections.Generic.List`1 [InvallersManagementMVC3.ViewModels.ClubModel]',但本词典需要类型的InvallersManagementMVC3.ViewModels.ClubModel的典范项目。

or specifying the elementtemplate while passing in a list of these element. However I am greeted by an exception: System.InvalidOperationException was unhandled by user code Message=The model item passed into the dictionary is of type 'System.Collections.Generic.List`1[InvallersManagementMVC3.ViewModels.ClubModel]', but this dictionary requires a model item of type 'InvallersManagementMVC3.ViewModels.ClubModel'.

推荐答案

您似乎在试图通过组3传递到视图的模型列表因此,为了重构code,我会建议由你开始引入适当的视图模型=>一个反映了这种特定视图的要求:

You seem to be trying to group the model list passed to the view by 3. So in order to refactor your code I would recommend you start by introducing a proper view model => one that reflects the requirements of this specific view:

public class GroupedClubs
{
    public IEnumerable<StandInClubModel> Clubs { get; set; }
}

现在控制器动作里面,我们应该简单地域模型转化成这个视图模型的列表:

Now inside the controller action we should simply convert the domain model into a list of this view model:

public ActionResult Index()
{
    // This is our domain model. In a real world application
    // it would come from a service layer. I am hardcoding some
    // values here for simplicity
    var clubs = Enumerable.Range(1, 8).Select(x => new StandInClubModel
    {
        ClubID = x,
        ClubName = "club " + x
    });

    // Now we group the list of clubs by 3 in order to simplify
    // our view code and avoid writing some ugly loops and spaghetti code
    // In a real world application I would recommend externalizing this mapping
    // between the domain model and the view model into a separate mapping layer
    // AutoMapper is great for this job 
    var viewModel = clubs
        .Select((club, index) => new { club, index })
        .GroupBy(g => g.index / 3, i => i.club)
        .Select(x => new GroupedClubs
        {
            Clubs = x
        });

    return View(viewModel);
}

现在,所有剩下的就是写一些看法:

Now all that's left is to write some views:

〜/查看/主页/ Index.cshtml

@model IEnumerable<GroupedClubs>

@using (Html.BeginForm())
{
    <fieldset>
        <legend> Select Clubs</legend>
        <br />

        <table>
            <tbody>
                @Html.EditorForModel()
            </tbody>
        </table>

        <input type="submit" value="Submit" />
    </fieldset>
}

〜/查看/主页/ EditorTemplates / GroupedClubs.cshtml

@model GroupedClubs
<tr>
    @Html.EditorFor(x => x.Clubs)
</tr>

〜/查看/主页/ EditorTemplates / StandInClubModel.cshtml

@model StandInClubModel
<td>
    @Html.HiddenFor(x => x.ClubID)
    @Html.EditorFor(x => x.IsAvailable)
</td>
<td>
    @Html.DisplayFor(x => x.ClubName)
</td>

这就是pretty所有得多。现在,你可以有一个控制器动作这将处理表单提交:

and that's pretty much all. Now you could have a controller action which would handle the form submission:

[HttpPost]
public ActionResult Index(List<GroupedClubs> clubs)
{
    ... map the view model back to some domain model and pass
        to the service layer for processing
}

这篇关于EditorTemplate的复杂类型的列表返回null,而EditorTemplate其元素工作正常的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆