0

i want to add dynamic fields into a list of items that are contained in a IEnumerable in a model class.

I followed this tutorial where they say that you can put

$("#addItem").click(function() {
    $.ajax({
       url: this.href,
       cache: false,
       success: function(html) {$("#PuntosMaestrosItems").append(html); }
   });
    return false;
});

But when i post the form , the new added rows are not considered as part of the model. I am sure is because the names of the fields has their own id and name attributes , so they have to follow a pattern like the original ones(not added by js). Can you suggest a way to do that? Any tutorial? Any help? I am lost.

The code called in jquery

    [HttpGet]
    public PartialViewResult BlankFormModelConfigurarAreaItem()
    {
        return PartialView("FormModelConfigurarAreaItem", new FormModelConfigurarAreaItem { Agrupaciones = db.AgrupacionChequeos.ToList(), Seleccionado = true });
    }

The model class containing the IEnumerable

public class FormModelCongifurarArea
{
    public int AreaId { get; set; }
    public IEnumerable<FormModelConfigurarAreaItem> PuntoMaestroItem{ get; set; } 
}

Thw view of FormModelConfigurarArea

@using Inspecciona.Helpers
@model Inspecciona.Models.FormModelCongifurarArea

<h2>ConfigurarInformeAreaNuevo</h2>

@using (Html.BeginForm()) {
    @Html.ValidationSummary(true)

<fieldset>
    <legend>FormModelCongifurarArea</legend>


    <div class="editor-field">
        @Html.HiddenFor(model => model.AreaId)
        @Html.ValidationMessageFor(model => model.AreaId)
    </div>
    <table>
    <thead>
        <tr>
            <th></th>
            <th>AspectoAControlarPuntoChequeo</th>
            <th>DescPuntoChequeo</th>
            <th>Agrupacion Chequeo</th>
            <th>Seleccionado</th>
        </tr>
    </thead>
     </table>
    <div id="PuntosMaestrosItems">
         @Html.EditorFor(model => model.PuntoMaestroItem)


    </div>

    <p>
        @Html.ActionLink("Add Punto chequeo", "BlankFormModelConfigurarAreaItem", null, new { id = "addItem" });
    </p>
    <p>
        <input type="submit" value="Guardar" />
    </p>
</fieldset>

}

And the Action of the Post in the controller

    [HttpPost]
    public ActionResult ConfigurarInformeArea(FormModelCongifurarArea formModelConfigurarArea ){
    }

REMEMBER: the problem is that when i add a new row of type FormModelConfigurarAreaItem the [HttpPost] is not getting the fields in formModelConfigurarArea.PuntoMaestroItem by some names/ids generated in javascript are not fitting the expeted ones. Many thanks!! I will mark as answer the best answer

X.Otano
  • 2,079
  • 1
  • 22
  • 40
  • What is sample value of 'html' in function(html)? – Yogee Sep 17 '14 at 21:04
  • I asked it as if value of 'html' is a formatted html, you could use : $("#PuntosMaestrosItems").html(html); instead of 'append' – Yogee Sep 17 '14 at 21:28
  • Add to your action method a parameter named `FormCollection form`, which will contain all of the form keys and values for debugging purposes. – Brian Mains Sep 17 '14 at 21:29
  • @Yogee it is a formattted html ,but i want to append a new row, i don´t want to replace anything..the problem is that when i Post to save the new Items addes by javascrit , they are not binded to the Model of the view – X.Otano Sep 17 '14 at 21:39
  • @BrianMains this is ok for debugging, but what about for a production solution? – X.Otano Sep 17 '14 at 21:40
  • 1
    You need to ensure your inputs are correctly named with indexers. Inspect the html and (if your `EditorTemplate` is correct) you should see inputs like `PuntoMaestroItem[0].SomeProperty`, `PuntoMaestroItem[1].SomeProperty` etc. so any new item also need to follow this convention to post back correctly. For example if there a 2 existing and you add a 3rd, it would be `PuntoMaestroItem[2].SomeProperty`. [This answer](http://stackoverflow.com/questions/24026374/adding-another-pet-to-a-model-form/24027152#24027152) gives one possible solution to dynamically creating new objects –  Sep 17 '14 at 22:39
  • As Stephen suggested, even in production look at the view source; as long as it's in PuntoMaestroItem[index].SomneProperty for the "name" attribute of the element, and none of the indexes overlap, that should work. It's hard to tell because I don't know what content your AJAX request is actually posting back.. is it doing complete screen wipes (get rid of all the old and load all the new) or just adding items one by one? You can open up firefox with firebug, and put breakpoints in the AJAX calls to verify the markup coming back. – Brian Mains Sep 18 '14 at 01:22
  • @BrianMains it is getting only one item but as you suposse with a not useful id for posting the form as a model(it gets ignored) – X.Otano Sep 18 '14 at 06:11
  • Only if the html your returning contains the `[#]` and `[%]` placeholders for the indexer. Since your partial view appears to be always returning identical html, I don't see why you cant include that html on the page and clone it (saves another call to the server). And please remove your 'answer' (its not and answer) and edit your question instead. –  Sep 18 '14 at 06:48
  • @StephenMuecke recheck the question, i changed the regexp replace – X.Otano Sep 18 '14 at 07:00
  • Does it work? If so great (although I think it should be `...'name="PuntoMaestroItem[' + index ...` since that the name of the property) –  Sep 18 '14 at 07:08
  • @StephenMuecke mark as answer the answer please, to provide help to other people in the same situation :) – X.Otano Sep 18 '14 at 07:19
  • Sorry, I don't understand you last comment –  Sep 18 '14 at 07:23
  • @StephenMuecke yes,if you can check as answer my answer to my own question(i just created it), clicking the green tick. I added it as answer since it works :) – X.Otano Sep 18 '14 at 07:24
  • I cant 'tick it' - its your question - only you can mark it as accepted. –  Sep 18 '14 at 07:26

1 Answers1

0

A suggested Solution:

Notice that in the action which returns the new row i am initializating the element with some customized parameters, this is the part which doesn´t allow me to use clone as the solution proposed in Adding another "Pet" to a Model Form

[HttpGet]
public PartialViewResult BlankFormModelConfigurarAreaItem()
{
    return PartialView("FormModelConfigurarAreaItem", new FormModelConfigurarAreaItem { Agrupaciones = db.AgrupacionChequeos.ToList(), Seleccionado = true });
}

It would be ok,if I continue generating the new row as mentioned in the question but with the following modifications

$("#addItem").click(function() {
   $.ajax({
      url: this.href,
      cache: false,
      success: function(html) {
         var index = $('#PuntosMaestrosItems tr').length; // assumes rows wont be deleted
         html=html.replace(/name=".*\[\d\]/g, 'name="FormModelConfigurarAreaItem[' + index + ']');
         html=html.replace(/id="%"/g, 'id="' + index  + '"');
         $("#PuntosMaestrosItems").append(html); }
    });
   return false;
});
Community
  • 1
  • 1
X.Otano
  • 2,079
  • 1
  • 22
  • 40