admin管理员组

文章数量:1394180

As a beginner MVC programmer I am constantly searching the web for help. I am trying to dynamically add a row to a HTML table using javascript. The below code works great, it adds the rows. The problem is when I return to the controller, the new rows are not there. If I start with 3 rows of data and add 1 or 2 rows, when I click the submit button it returns with only the original 3 records. Not sure why the below is not returning the new rows I added. Below is a reduced portion of the code.

Any help will be greatly appreciated.

Here is my View.

@model List<ACES.Models.ENTITY_CONTACTS>

@using (Html.BeginForm("Edit", "Contacts", FormMethod.Post))
{
    @Html.AntiForgeryToken()
    @Html.ValidationSummary(true)

    <div class="form-horizontal">
        <table id="dataTable" class="list-Contacts table-condensed table-striped  table-responsive test">
            <tr>
                <th class="danger text-center">
                    <label>Last Name</label>
                </th>
                <th class="text-center">
                    <label>First Name</label>
                </th>
                <th class="text-center">
                    <label>Title</label>
                </th>
                <th class="text-center">
                    <label>EMail Address</label>
                </th>

            </tr>

            @if (Model != null && Model.Count > 0)
            {
                int j = 0;
                foreach (var i in Model)
                {
                    if (j == 1)
                    {
                        <tr class="contacts-record-template" style="display:none">

                            <td>
                                @Html.TextBoxFor(a => a[j].LASTNAME)
                            </td>
                            <td>
                                @Html.TextBoxFor(a => a[j].FIRSTNAME)
                            </td>
                            <td>
                                @Html.TextBoxFor(a => a[j].TITLE)
                            </td>
                            <td>
                                @Html.TextBoxFor(a => a[j].EMAIL, new { @style = "width: 200px;" })
                            </td>

                        </tr>
                    }

                    <tr class="contacts-record">
                        <td>
                            @Html.TextBoxFor(a => a[j].LASTNAME)
                        </td>
                        <td>
                            @Html.TextBoxFor(a => a[j].FIRSTNAME)
                        </td>
                        <td>
                            @Html.TextBoxFor(a => a[j].TITLE)
                        </td>
                        <td>
                            @Html.TextBoxFor(a => a[j].EMAIL, new { @style = "width: 200px;" })
                        </td>

                    </tr>
                    j++;
                }
            }
        </table>


        @*Display buttons*@
        <input type="button" class="add-button" name="add" value="Add" />

        <div style="text-align:right"><a href="#" id="addNew">Add Contact</a></div>
        <input type="submit" name="submitAction" value="Submit" class="btn btn-primary" onclick="return confirm('Please double check all information before submitting.   Submit Notification?')" />
    </div>


}
@section Scripts {
    @Scripts.Render("~/bundles/jqueryval")
}
<script src="~/Scripts/jquery-1.10.2.min.js"></script>
<script src="~/Scripts/jquery.validate.min.js"></script>
<script src="~/Scripts/jquery.validate.unobtrusive.min.js"></script>
<script src="~/Scripts/jquery.maskedinput.min.js"></script>
<script type="text/javascript">
    $('.phone2').mask('999-999-9999');
    $('.phone').mask('?999-999-9999');


    $(document).ready(function () {
        var count = 0;
        $('.add-button').click(function () {
            count++;
            var template = $('.contacts-record-template').clone()
            template.find('input[type=text]').val(null);
            template.find('input[type=checkbox]').prop('checked', false);
            $.each(template.find('input[type=text]'), function () {
                var name = $(this).attr('name');
                name = name.replace('0', count - 1);
                $(this).attr('name', name);
            });

            $('.list-Contacts').append(template);
            template.removeClass('contacts-record-template').addClass('contacts-record').show();
        })
    });

</script>

Controller.

    [HttpPost]
    [ValidateAntiForgeryToken]
    public ActionResult Edit(string submitAction, List<ENTITY_CONTACTS> entity_Contacts)
    {
        if (ModelState.IsValid)
        {
            foreach (var i in entity_Contacts)
            {
                ViewBag.temp = i.LASTNAME;
            }
            db.SaveChanges();
        }
        return View(entity_Contacts);

As a beginner MVC programmer I am constantly searching the web for help. I am trying to dynamically add a row to a HTML table using javascript. The below code works great, it adds the rows. The problem is when I return to the controller, the new rows are not there. If I start with 3 rows of data and add 1 or 2 rows, when I click the submit button it returns with only the original 3 records. Not sure why the below is not returning the new rows I added. Below is a reduced portion of the code.

Any help will be greatly appreciated.

Here is my View.

@model List<ACES.Models.ENTITY_CONTACTS>

@using (Html.BeginForm("Edit", "Contacts", FormMethod.Post))
{
    @Html.AntiForgeryToken()
    @Html.ValidationSummary(true)

    <div class="form-horizontal">
        <table id="dataTable" class="list-Contacts table-condensed table-striped  table-responsive test">
            <tr>
                <th class="danger text-center">
                    <label>Last Name</label>
                </th>
                <th class="text-center">
                    <label>First Name</label>
                </th>
                <th class="text-center">
                    <label>Title</label>
                </th>
                <th class="text-center">
                    <label>EMail Address</label>
                </th>

            </tr>

            @if (Model != null && Model.Count > 0)
            {
                int j = 0;
                foreach (var i in Model)
                {
                    if (j == 1)
                    {
                        <tr class="contacts-record-template" style="display:none">

                            <td>
                                @Html.TextBoxFor(a => a[j].LASTNAME)
                            </td>
                            <td>
                                @Html.TextBoxFor(a => a[j].FIRSTNAME)
                            </td>
                            <td>
                                @Html.TextBoxFor(a => a[j].TITLE)
                            </td>
                            <td>
                                @Html.TextBoxFor(a => a[j].EMAIL, new { @style = "width: 200px;" })
                            </td>

                        </tr>
                    }

                    <tr class="contacts-record">
                        <td>
                            @Html.TextBoxFor(a => a[j].LASTNAME)
                        </td>
                        <td>
                            @Html.TextBoxFor(a => a[j].FIRSTNAME)
                        </td>
                        <td>
                            @Html.TextBoxFor(a => a[j].TITLE)
                        </td>
                        <td>
                            @Html.TextBoxFor(a => a[j].EMAIL, new { @style = "width: 200px;" })
                        </td>

                    </tr>
                    j++;
                }
            }
        </table>


        @*Display buttons*@
        <input type="button" class="add-button" name="add" value="Add" />

        <div style="text-align:right"><a href="#" id="addNew">Add Contact</a></div>
        <input type="submit" name="submitAction" value="Submit" class="btn btn-primary" onclick="return confirm('Please double check all information before submitting.   Submit Notification?')" />
    </div>


}
@section Scripts {
    @Scripts.Render("~/bundles/jqueryval")
}
<script src="~/Scripts/jquery-1.10.2.min.js"></script>
<script src="~/Scripts/jquery.validate.min.js"></script>
<script src="~/Scripts/jquery.validate.unobtrusive.min.js"></script>
<script src="~/Scripts/jquery.maskedinput.min.js"></script>
<script type="text/javascript">
    $('.phone2').mask('999-999-9999');
    $('.phone').mask('?999-999-9999');


    $(document).ready(function () {
        var count = 0;
        $('.add-button').click(function () {
            count++;
            var template = $('.contacts-record-template').clone()
            template.find('input[type=text]').val(null);
            template.find('input[type=checkbox]').prop('checked', false);
            $.each(template.find('input[type=text]'), function () {
                var name = $(this).attr('name');
                name = name.replace('0', count - 1);
                $(this).attr('name', name);
            });

            $('.list-Contacts').append(template);
            template.removeClass('contacts-record-template').addClass('contacts-record').show();
        })
    });

</script>

Controller.

    [HttpPost]
    [ValidateAntiForgeryToken]
    public ActionResult Edit(string submitAction, List<ENTITY_CONTACTS> entity_Contacts)
    {
        if (ModelState.IsValid)
        {
            foreach (var i in entity_Contacts)
            {
                ViewBag.temp = i.LASTNAME;
            }
            db.SaveChanges();
        }
        return View(entity_Contacts);
Share Improve this question asked Mar 10, 2016 at 14:40 JBrozJBroz 691 gold badge1 silver badge5 bronze badges 3
  • While Shyju's answer may have resolved one issue, you have multiple others that will cause binding to fail. Your 'template' is withing the form tags, so it will post back its values which are the initial values of the 2nd row and any edits you make in the second row will be ignored. You cannot implement a 'delete' row feature without significant extra javascript code. Your script refer to an input[type=checkbox] which does not exist, but if it did the it would fail because you have not renamed the indexer (and there are least 3 others). – user3559349 Commented Mar 11, 2016 at 2:51
  • 1 I remend you look at the answers here and here for the correct way to implement this. – user3559349 Commented Mar 11, 2016 at 2:54
  • Thank you for the above and you are right, I am having issues on creating a row I did not want. You state above that the "template is within the form tags so it will post back its initial values". Where should the template be stored? Outside the table? In a partial view? tried several things and still not getting it to work properly. When I put the template outside the form tags, my java script is not recognizing the template. How do I reference a template outside the form tags? Thanks again for all your help. – JBroz Commented Mar 16, 2016 at 12:32
Add a ment  | 

2 Answers 2

Reset to default 3

The problem is, your template input field has name like [1].LASTNAME. But in your code you are doing a replace on 0, instead of 1.

Change your code to replace 1 instead of 0 when you try to generate the name value for the dynamically generated input fields.

The below code should work fine.

$(document).ready(function () {

    $('.add-button').click(function() {

        var count = $("tr.contacts-record").length;
        var template = $('.contacts-record-template').clone();
        template.find('input[type=text]').val(null);
        template.find('input[type=checkbox]').prop('checked', false);
        $.each(template.find('input[type=text]'), function() {
            var name = $(this).attr('name');             
            name = name.replace('1', count);             
            $(this).attr('name', name);
        });

        $('.list-Contacts').append(template);
        template.removeClass('contacts-record-template')
                                           .addClass('contacts-record').show();
    });
});

Your javascript runs on document ready.

please try:

<input type="button" class="add-button" name="add" value="Add" />

switched to:

<button type="button" class="add-button" onclick="doIt();" name="add">Add</button>

also main function:

function doIt() {
        var count = 0;
            count++;
            var template = $('.contacts-record-template').clone()
            template.find('input[type=text]').val(null);
            template.find('input[type=checkbox]').prop('checked', false);
            $.each(template.find('input[type=text]'), function () {
                var name = $(this).attr('name');
                name = name.replace('0', count - 1);
                $(this).attr('name', name);
            });

            $('.list-Contacts').append(template);
            template.removeClass('contacts-record-template').addClass('contacts-record').show();
    }

i hope its works.

本文标签: aspnet mvcDynamically adding rows to an html tableusing JavaScriptStack Overflow