Chris F Carroll
Chris F Carroll

Reputation: 12370

HtmlHelper.Display() & DisplayFor() not working as expected for a model

I have a view for editing a client with the line:

@Html.DisplayFor(x=>x.Orders)

in it. But it only outputs a display for the Id property, ignoring the other properties:

public class Order
{
    public int Id { get; set; }

    [DisplayName("Order Header")]
    public string Header { get; set; }

    // ... etc...

}

whereas I expect the behaviour to be:

If the object contains multiple properties, for each property the method generates a string that consists of markup for the property name and markup for the property value. MSDN

What have I missed?

the view:

@model Models.Client

@{
    ViewBag.Title = "Client Details";
}
<h2>@ViewBag.Title</h2>

<fieldset>
  @Html.DisplayFor(x => x.Notes, "ListOfNotes")
</fieldset>
<fieldset>
  @{ Html.RenderPartial("NewNoteForm", Model); }
</fieldset>

<fieldset>
  @using(@Html.BeginForm())
  {
    @Html.EditorForModel()
    <input type="submit" value="Save"/>
  }
</fieldset>

<fieldset>
  @Html.DisplayFor(x => x.Orders) @* The errant bit *@
</fieldset>

<fieldset>
  @{ Html.RenderPartial("NewOrderForm", Model); }
</fieldset>

The Client Model:

public class Client
{
    public Client(int PId, string title, string forename, string surname)
        : this()
    {
        PId = pId;
        Title = title;
        Forename = forename;
        Surname = surname;
    }

    public Client()
    {
        Notes = new List<Note>();
        Orders= new List<Order>();
    }

    public int PId { get; set; }

    public string Title { get; set; }
    public string Forename { get; set; }
    public string Surname { get; set; }
    public List<Note> Notes { get; private set; }
    public List<Order> Orders { get; private set; }
}

Btw, The list of notes displays as expected.

Upvotes: 2

Views: 4354

Answers (2)

Mladen B.
Mladen B.

Reputation: 2996

Since Orders is a list, you need a loop to display all the items in that list, like this:

<table>
    <thead>
        <tr>
            <th>@Html.DisplayName(m => m.Title)</th>
            <th>@Html.DisplayName(m => m.Orders)</th>
        </tr>
    </thead>
    <tbody>
        <tr>
            <td>@Html.DisplayFor(m => m.Title)</td>
            <td>
                @foreach (var order in Model.Orders)
                {
                    <div>
                        @Html.DisplayFor(_ => order)
                    </div>
                }
            </td>
        </tr>
    </tbody>
</table>

The quote:

If the object contains multiple properties...

refers to the fact the order object's properties (Id and Header) should be displayed all at once, using that single @Html.DisplayFor(_ => order) line.

Upvotes: 0

Parv Sharma
Parv Sharma

Reputation: 12705

Either Use Html.DisplayForModel(o=>o)
or call Html.DisplayFor()
for each property of your current model. Something like this.

@Html.DisplayFor(model=>model.Id)
@Html.DisplayFor(model=>model.Header)

Upvotes: 1

Related Questions