Si vous avez besoin de lier un dictionnaire, de sorte que chaque valeur possède une boîte texbox pour l'éditer, voici une façon de le faire fonctionner. Les parties les plus importantes qui affectent la génération de l'attribut name dans le code HTML sont l'expression du modèle, qui garantit que la liaison du modèle se produit lors de la publication. Cet exemple ne fonctionne que pour le dictionnaire.
L'article lié explique la syntaxe HTML qui fait fonctionner la liaison, mais il laisse la syntaxe Razor pour accomplir cela un mystère. En outre, l'article est assez différent en ce sens qu'il autorise l'édition des clés et des valeurs et utilise un index entier même si la clé du dictionnaire est une chaîne et non un nombre entier. Donc, si vous essayez de lier un dictionnaire, vous devrez d'abord évaluer si vous voulez simplement que les valeurs soient modifiables, ou les clés et les valeurs, avant de décider de l'approche à adopter, car ces scénarios sont très différents.
Si jamais vous avez besoin de lier un objet complexe, c'est-à-dire Dictionnaire, vous devriez juste avoir une zone de texte pour chaque propriété avec l'expression d'exploration dans la propriété, similaire à l'article.
http://www.hanselman.com/blog/ASPNETWireFormatForModelBindingToArraysListsCollectionsDictionaries.aspx
public class SomeVM
{
public Dictionary<string, string> Fields { get; set; }
}
public class HomeController : Controller
{
[HttpGet]
public ViewResult Edit()
{
SomeVM vm = new SomeVM
{
Fields = new Dictionary<string, string>() {
{ "Name1", "Value1"},
{ "Name2", "Value2"}
}
};
return View(vm);
}
[HttpPost]
public ViewResult Edit(SomeVM vm) //Posted values in vm.Fields
{
return View();
}
}
CSHTML:
rédacteurs en chef pour les valeurs que (de vous pourriez bien sûr ajouter LabelFor pour générer des étiquettes basées sur la clé):
@model MvcApplication2.Controllers.SomeVM
@using (Html.BeginForm()) {
@Html.ValidationSummary(true)
<fieldset>
<legend>SomeVM</legend>
@foreach(var kvpair in Model.Fields)
{
@Html.EditorFor(m => m.Fields[kvpair.Key]) //html: <input name="Fields[Name1]" …this is how the model binder knows during the post that this textbox value gets stuffed in a dictionary named “Fields”, either a parameter named Fields or a property of a parameter(in this example vm.Fields).
}
<p>
<input type="submit" value="Save" />
</p>
</fieldset>
}
Modification des deux clés/valeurs : @ {var fields = Model.Fields.ToList(); }
@for (int i = 0; i < fields.Count; ++i)
{
//It is important that the variable is named fields, to match the property name in the Post method's viewmodel.
@Html.TextBoxFor(m => fields[i].Key)
@Html.TextBoxFor(m => fields[i].Value)
//generates using integers, even though the dictionary doesn't use integer keys,
//it allows model binder to correlate the textbox for the key with the value textbox:
//<input name="fields[0].Key" ...
//<input name="fields[0].Value" ...
//You could even use javascript to allow user to add additional pairs on the fly, so long as the [0] index is incremented properly
}
Veuillez décrire ce que «cela ne fonctionne pas». –
Exactement ce qui ne fonctionne pas? Pourriez-vous élaborer un peu? – Jimmeh
J'essaye de traiter les données qui ont été mises à jour sur la vue, ainsi dans le contrôleur je reçois le modèle mis à jour correct, mais cette propriété particulière n'a pas de valeur. Dans mon cas, c'est [null, null]. –