0

Have a model containing an empty list. I want to add items to the list and post it all in one go.

Main Model

[Required]
public string WillAttend { get; set; }

/// <summary>
/// Guests to accompany the RSVPer
/// </summary>
public List<Guest> Guests { get; set; }

Guest Model

[Required]
[Display(Name = "First Name")]
public string FirstName { get; set; }

[Required]
[Display(Name = "Last Name")]
public string LastName { get; set; }

Inside the form:

<div class="form-group">
    <div>
        Yes @Html.RadioButtonFor(m => m.WillAttend, "yes", new { @class = "" })
        No @Html.RadioButtonFor(m => m.WillAttend, "no", new { @class = "" })
    </div>
</div>
<div class="form-group">
    <div>
        <span>Will you bringing any children or guests?</span>
        <input id="InputAddGuest" type="button" class="form-control" value="Add Guest or Child" />                            
        <ul id="ListGuest">

        </ul>
    </div>
</div>

<div class="form-group">
    <div>
        <button type="submit" class="btn btn-block">Finish</button>
    </div>
</div>

There is one form on the page for submitting the main model above, and I'm using jquery to generate html:

<script type="text/javascript">

    $(document).ready(function () {
        $('#InputAddGuest').click(function () {
            $('#ListGuest').append('<li>HELLO WORLD</li>');
        });
    });

</script>

but what goes in here so that when I post my model contains actual guests?

O.O
  • 11,077
  • 18
  • 94
  • 182
  • Are you using ASP? Razor? – Jace Mar 28 '16 at 19:01
  • Razor is dirt simple way to embed code into your HTML markup http://www.w3schools.com/aspnet/razor_intro.asp – Jace Mar 28 '16 at 19:02
  • Refer the answers [here](http://stackoverflow.com/questions/29161481/post-a-form-array-without-successful/29161796#29161796) and [here](http://stackoverflow.com/questions/28019793/submit-same-partial-view-called-multiple-times-data-to-controller/28081308#28081308) for options –  Mar 28 '16 at 21:15

2 Answers2

1

You basically need to build the html markup with input field names matching to your view model property hierarchy.

Since your main view model has a Guests property which is a collection, your input field's name should be like Guests[0].FirstName, Guests[0].LastName,Guests[1].FirstName etc.

This should work

$(document).ready(function () {
    $('#InputAddGuest').click(function () {
       var index = $(".guestRow").length;
       var row = "<div class='guestRow'>";
       row += "<input type='text' name='Guests[" + index + "].FirstName' />";
       row += "<input type='text' name='Guests[" + index + "].LastName' />";
       row += "</div>";
       $('#ListGuest').append(row);
    });
});

Assuming your HttpPost action method parameter is of MainModel type

[HttpPost]
public ActionResult Register(MainModel model)
{
    //check model.WillAttend
    // iterate through model.Guests
    // to do : return something
}
Elvis Jr
  • 135
  • 6
Shyju
  • 214,206
  • 104
  • 411
  • 497
0

List

I have similar case, at Feature.

What I do is: I make session on controller, so when

$('#InputAddGuest').click(function () {

        });

I call $.ajax like this:

  var valDdlTeamProject = $('#TeamProjectCollection').val();
        var valDdlProject = $('#Project').val();
$.ajax({
                type: 'POST',
                dataType: 'json',
                url: '@Url.Action("AddTfsFeature", "Request")',
                data: {
                    requestNo: '@Model.RequestNo',
                    teamProjectCollection: valDdlTeamProject,
                    project: valDdlProject
                },
                success: function (response) {
                    if (response.Result == 'Success') {
                        var additionalHtml = "";
                        var additionalHtml = '<a class="label label-info" href="#">';
                        additionalHtml += response.TempObject.TeamProjectCollection + ' - ' + response.TempObject.Project;
                        additionalHtml += '<span class="glyphicon glyphicon-remove remove-feature" data-ID="' + response.TempObject.ID + '" onclick="removeFeature(\'' + response.TempObject.ID + '\', this)"></span>';
                        additionalHtml += '</a>';
                        $('.body-add-feature').append(additionalHtml);
                        clearTfsFeatureForm();
                        iCounterFeature = response.TempObjectCount;
                        if (response.TempObjectCount > 0)
                            $('#DialogCreateFeature').modal('hide');
                    }
                    if (response.Result == 'Failed') {
                        alert(response.Message);
                    }
                },
                error: function (response) { }
            })

At code behind:

[HttpPost]
        public JsonResult AddTfsFeature(string requestNo, string teamProjectCollection, string project)
        {
            ResultMessageViewModel result = new ResultMessageViewModel
            {
                Result = "Failed",
                Message = "No data"
            };

            TfsFeature feature = new TfsFeature
            {
                ID = sessTempIndexTfsFeature,
                RequestNo = requestNo,
                TeamProjectCollection = teamProjectCollection,
                Project = project,
                CreatedBy = UserID
            };
            for (int i = 0; i < sessListTfsFeature.Count; i++)
            {
                if (sessListTfsFeature.ElementAt(i).TeamProjectCollection == teamProjectCollection &&
                    sessListTfsFeature.ElementAt(i).Project == project)
                {
                    result.Result = "Failed";
                    result.Message = "Existing feature data has already exist.";
                    return Json(result, JsonRequestBehavior.AllowGet);
                }
            }
            sessListTfsFeature.Add(feature);

        result.Result = "Success";
        result.Message = "Add Success";
        result.TempObject = feature;
        result.TempObjectCount = sessListTfsFeature.Count;
        return Json(result, JsonRequestBehavior.AllowGet);

sessListTfsFeature is List<TfsFeature>

and if there is button to delete Guest, you need new ajax, and new controller to delete object Guest at session.

toha
  • 5,095
  • 4
  • 40
  • 52