2009-09-25 24 views
4

J'ai une classe personnalisée:en utilisant Html.EditorFor avec un IEnumerable <T>

public class Person 
{ 
    public String Name { get; set; } 
    public Int32 Age { get; set; } 
    public List<String> FavoriteFoods { get; set; } 

    public Person() 
    { 
     this.FavoriteFoods = new List<String>(); 
     this.FavoriteFoods.Add("Jambalya"); 
    } 
} 

Je passe cette classe à mon avis fortement typé:

<%@ Page Title="" Language="C#" MasterPageFile="~/Views/Shared/Site.Master" Inherits="System.Web.Mvc.ViewPage<MvcLearner.Models.Person>" %> 

<asp:Content ID="Content1" ContentPlaceHolderID="TitleContent" runat="server"> 
Create 
</asp:Content> 

<asp:Content ID="Content2" ContentPlaceHolderID="MainContent" runat="server"> 

    <h2>Create</h2> 

    <% using (Html.BeginForm()) { %> 
     <%= Html.LabelFor(person => person.Name) %><br /> 
     <%= Html.EditorFor(person => person.Name) %><br /> 
     <%= Html.LabelFor(person => person.Age) %><br /> 
     <%= Html.EditorFor(person => person.Age) %><br /> 
     <%= Html.LabelFor(person => person.FavoriteFoods[0]) %><br /> 
     <%= Html.EditorFor(person => person.FavoriteFoods[0]) %> 
    <% } %> 

</asp:Content> 

Et quand je passe en revue à la page, je finir avec le message d'erreur: Les modèles peuvent être utilisés uniquement avec les expressions d'accesseur de champ et de propriété. Après un peu de googling, j'ai compris que cela arrivait parce que les fonctions EditorFor et LabelFor ne peuvent accepter que les propriétés immédiates de l'objet Model, et FavoriteFoods [0] n'est pas une propriété immédiate. Est-ce que quelqu'un a un travail autour qui ferait fonctionner le code sans utiliser une chaîne pour spécifier le nom du contrôle? Est-ce que c'est possible? Idéalement, je voudrais utiliser une expression du modèle à l'élément qui a besoin d'un éditeur, qui détermine à lui seul le nom du contrôle pour l'entrée.

Essayer quelques autres choses, j'ai pu obtenir ce travail en utilisant les modifications suivantes à la vue:

<% using (Html.BeginForm()) { %> 
    <%= Html.LabelFor(person => person.Name) %><br /> 
    <%= Html.EditorFor(person => person.Name) %><br /> 
    <%= Html.LabelFor(person => person.Age) %><br /> 
    <%= Html.EditorFor(person => person.Age) %><br /> 
    <% foreach (String FavoriteFoods in Model.FavoriteFoods) { %> 
     <%= Html.LabelFor(food => FavoriteFoods) %><br /> 
     <%= Html.EditorFor(food => FavoriteFoods)%><br /> 
    <% } %> 
    <input type="submit" value="Submit" /> 
<% } %> 

Il est important de noter cependant que côté droit de l'expression dans EditorFor et LabelFor doit être nom exact de la liste que vous tentez de remplir et la liste doit être de type basique (ex: String, Int32, etc.). Lorsque j'essaie d'utiliser des types complexes cependant, il échoue toujours. J'ai essayé d'afficher une liste de cette classe de personne avec des entrées pour chaque propriété et il les affiche tous très bien dans le navigateur, mais elle renvoie ensuite une action null List to my post. Comment faire apparaître l'index au nom des entrées pour les éléments d'une liste?

This was a giant help in figuring out what was going on.

Répondre

6

Je suppose que cela est pour la liste des FavoriteFoods. Comment cela a été fait dans ASP.NET MVC v1 avait quelque chose comme ceci:

<input type="hidden" name="FavouriteFoods.Index" value="0" /> 
+0

Auriez-vous à reconstruire les classes dans le contrôleur dans MVC 1? Je voudrais que la classe soit construite par le framework si possible et fournisse simplement à mon contrôleur une classe up packagée avec laquelle travailler. –

+0

Il le fait pour vous. Je pense que cette solution annonce le post de Phil Haack - http://haacked.com/archive/2008/10/23/model-binding-to-a-list.aspx –

+0

Merci beaucoup pour ce lien. Il semble qu'il soit temps pour moi d'écrire des méthodes d'aide dans ma bibliothèque. –