Steve Sanderson est BeginCollectionItem aide ne se lient pas correctement
Je suis à l'aide de Steve Sanderson est BeginCollectionItem helper et a couru dans un problème. J'ai un formulaire qui dispose d'une option d'ajouter un nombre illimité de récompenser les champs. Je suis en utilisant son aide car il a résolu ce problème avec la façon de générer les champs et ne pas avoir à vous soucier de la façon de les lier lorsque le formulaire est soumis.
Que j'ai dans ce même formulaire de certaines cases qu'il y a une quantité inconnue. La différence avec celui-ci par rapport à la récompense est le montant inconnu deviendra connu après une base de données d'appel et sera connu par le temps, le code de la vue.
Donc mon code ressemble à ceci
public class FrmVm
{
public Guid Id { get; set; }
public string Name { get; set; }
public bool Active { get; set; }
public IList<WarrantyFeaturesVm> WarrantyFeaturesVm { get; set; } //this is the checkbox ones.
public IList<RewardVms> RewardVms { get; set; } //this is the dyanmic one that I needed the helper for
public CbCreditCardFrmVm()
{
Active = true;
WarrantyFeaturesVm = new List<WarrantyFeaturesVm>();
RewardVms = new List<RewardVms>();
}
}
//view
@foreach (var tier in Model.RewardVms)
{
@Html.Partial("GenerateReward", tier) //in this partial view in the BeginCollectionItem
}
@foreach (var warranties in Model.WarrantyFeaturesVm)
{
using (Html.BeginCollectionItem("WarrantyFeaturesVm"))
{
<span>@warranties.Name:</span>
@Html.TextBoxFor(x => warranties.FeatureId)
@Html.CheckBoxFor(x => warranties.HasFeature)
}
}
J'utilise jquery pour présenter les données à l'aide de serializeArray(). Quand il va sur le serveur il lier toutes les dynamiques correctement et même se lie à la Garantie de la Collection(la collection compte est 1). Pourtant, il se lie jamais rien entrailles de la WarrantyFeaturesVm, tout est à gauche en tant que par défaut.
si je supprimer à l'aide de (Html.BeginCollectionItem("WarrantyFeaturesVm"))
puis il n'a même pas de lier la collection.
Ce que quelqu'un sait pourquoi il n'est pas contraignant quoi que ce soit dans la collection?
Modifier
//for loop (works)
<form method="post" id="" action="" class="ui-formwizard ui-helper-reset ui-widget ui-widget-content ui-corner-all" novalidate="novalidate">
<span id="" class="step ui-formwizard-content ui-helper-reset ui-corner-all" style="display: none;">
<input type="hidden" value="6aa20677-d367-4e2a-84f0-9fbe00deb191" name="WarrantyFeaturesVm[0].FeatureId" id="WarrantyFeaturesVm_0__FeatureId" data-val-required="The FeatureId field is required." data-val="true" class="ui-wizard-content ui-helper-reset ui-state-default"> <span>Purchase</span>
<input type="checkbox" value="true" name="WarrantyFeaturesVm[0].HasFeature" id="WarrantyFeaturesVm_0__HasFeature" data-val-required="The HasFeature field is required." data-val="true" class="ui-wizard-content ui-helper-reset ui-state-default"><input type="hidden" value="false" name="WarrantyFeaturesVm[0].HasFeature" class="ui-wizard-content ui-helper-reset ui-state-default">
</form>
//foreach loop beginItemCollection(does not work)
<form method="post" id="" action="" class="ui-formwizard ui-helper-reset ui-widget ui-widget-content ui-corner-all" novalidate="novalidate">
<span id="" class="step ui-formwizard-content ui-helper-reset ui-corner-all" style="display: inline;">
<input type="hidden" value="68ba9241-c409-4f4b-96da-cce13b127c1e" autocomplete="off" name="WarrantyFeaturesVm.index" class="ui-wizard-content ui-helper-reset ui-state-default">
<input type="hidden" value="6aa20677-d367-4e2a-84f0-9fbe00deb191" name="WarrantyFeaturesVm[68ba9241-c409-4f4b-96da-cce13b127c1e].war.FeatureId" id="WarrantyFeaturesVm_68ba9241-c409-4f4b-96da-cce13b127c1e__war_FeatureId" data-val-required="The FeatureId field is required." data-val="true" class="ui-wizard-content ui-helper-reset ui-state-default"> <span>Purchase</span>
<input type="checkbox" value="true" name="WarrantyFeaturesVm[68ba9241-c409-4f4b-96da-cce13b127c1e].war.HasFeature" id="WarrantyFeaturesVm_68ba9241-c409-4f4b-96da-cce13b127c1e__war_HasFeature" data-val-required="The HasFeature field is required." data-val="true" class="ui-wizard-content ui-helper-reset ui-state-default"><input type="hidden" value="false" name="WarrantyFeaturesVm[68ba9241-c409-4f4b-96da-cce13b127c1e].war.HasFeature" class="ui-wizard-content ui-helper-reset ui-state-default">
</span>
</form>
//for loop beginItemCollection (does not work)
<form method="post" id="" action="" class="ui-formwizard ui-helper-reset ui-widget ui-widget-content ui-corner-all" novalidate="novalidate">
<span id="" class="step ui-formwizard-content ui-helper-reset ui-corner-all" style="display: none;">
<input type="hidden" value="fe3fbc82-a2df-476d-a15a-dacd841df97e" autocomplete="off" name="WarrantyFeaturesVm.index" class="ui-wizard-content ui-helper-reset ui-state-default">
<input type="hidden" value="6aa20677-d367-4e2a-84f0-9fbe00deb191" name="WarrantyFeaturesVm[fe3fbc82-a2df-476d-a15a-dacd841df97e].WarrantyFeaturesVm[0].FeatureId" id="WarrantyFeaturesVm_fe3fbc82-a2df-476d-a15a-dacd841df97e__WarrantyFeaturesVm_0__FeatureId" data-val-required="The FeatureId field is required." data-val="true" class="ui-wizard-content ui-helper-reset ui-state-default"> <span>Purchase</span>
<input type="checkbox" value="true" name="WarrantyFeaturesVm[fe3fbc82-a2df-476d-a15a-dacd841df97e].WarrantyFeaturesVm[0].HasFeature" id="WarrantyFeaturesVm_fe3fbc82-a2df-476d-a15a-dacd841df97e__WarrantyFeaturesVm_0__HasFeature" data-val-required="The HasFeature field is required." data-val="true" class="ui-wizard-content ui-helper-reset ui-state-default"><input type="hidden" value="false" name="WarrantyFeaturesVm[fe3fbc82-a2df-476d-a15a-dacd841df97e].WarrantyFeaturesVm[0].HasFeature" class="ui-wizard-content ui-helper-reset ui-state-default">
</span>
<span id="adminSettings" class="step ui-formwizard-content ui-helper-reset ui-corner-all" style="display: inline;">
</form>
Oui, ils sont dans un format Html.BeginForm. Je pense que j'ai tout compris(partiellement). Si je change la boucle foreach pour un forloop de faire quelque chose comme @Html.TextBoxFor(x => le Modèle.WarrantyFeaturesVm[i].FeatureId), il fonctionne. Je ne sais pas pourquoi le beginCollection ne fonctionne pas bien.
Le modèle de classeur regarde le code HTML. Découvrez les différences dans la façon dont le HTML id sont rendus de manière différente dans les 2 cas différents. Nous utilisons foreach souvent avec BeginCollectionItem, mais, souvent, les BeginCollectionItem est dans une partie ou de l'éditeur de modèle.
J'ai donc fait le test. Quelque chose de bizarre qui se passe avec les noms.
Avez-vous essayé d'utiliser le Html.HiddenFor(guerre => la guerre.FeatureId) au lieu de Html.HiddenFor(m => la guerre.FeatureId)?
OriginalL'auteur chobo2 | 2011-12-19
Vous devez vous connecter pour publier un commentaire.
Ok je crois que je vois ce qui se passe ici.
Dans le deuxième exemple, où vous avez fait le foreach, il ressemble à votre cshtml était quelque chose comme ceci (@ symboles peut être incorrecte):
Parce que BeginCollectionItem utilise son contexte afin de dériver le code HTML des noms et des id, ce est pourquoi vous vous retrouvez avec une "guerre" dans les id et les noms. Le modèle de liaison est à la recherche d'une collection bien nommée "WarrantyFeaturesVm", qu'il trouve. Cependant, il est alors à la recherche pour une propriété nommée "guerre" sur le WarrantyFeaturesVm viewmodel, qu'il ne trouve pas, et donc ne se lie pas.
Dans le 3ème scénario, il est similaire. Il est à la recherche pour le WarranyFeaturesVm collection de propriété, qu'il trouve. Toutefois, elle recherche un autre élément de la collection.
Afin de lier correctement, votre HTML a pour ressembler à votre premier exemple de code HTML:
Comme je l'ai déjà évoqué dans mon commentaire, vous pouvez atteindre cet objectif en mettant l'BeginCollectionItem et tout ce qu'elle enroule en une vue partielle. La vue partielle recevrez ensuite son propre contexte, depuis votre aides-utiliser la vue du @Modèle de la propriété avec l'marqué tapé aides comme:
@Html.WidgetFor(m => m.PropertyName).
D'autre part, si vous avez vraiment besoin de la collection à être rendus à l'extérieur de la vue, je ne vois pas de problème à l'aide de la normale de l'indexation (entier) avec une boucle for et sans BeginCollectionItem.
Mise à jour
J'ai creusé ce vieux post de Phil Haack. Un extrait:
BeginCollectionItem utilise cette méthode d'indexation assurez-vous que le modèle de liaison qui se passe. La seule différence est qu'il utilise le Guid au lieu d'entiers que l'indexeur. Mais vous pouvez définir manuellement les indexeur comme dans le Phil de l'exemple ci-dessus.
BeginCollectionItem pas parfait. C'est la seule chose qui me manque en faisant le php il y a 10 ans. J'aimerais si MVC et vous permet de passer dans les collections simplement à l'aide de input id="CollectionProperty[]". Serait tellement plus facile.
OriginalL'auteur danludwig