ASP.Net

ASP.NET MVC: Add a Select All Checkbox to a Checklist Table Using JQuery


Often, we find we need to present our users with a list of items in a table or list, with checkboxes such that the user can select one or more items from the list for additional processing. Most of the time, the user will either be selecting a few items from the list but leaving most unchecked, or selecting all or most of the items from the list and leaving very few items unchecked.

In these cases, it is handy to offer the user a means to “Select All” or “Select None” which then toggles the checked state of the entire list. The common means to do this is with one more checkbox, global to the list itself, which performs the toggling action.

One way to do this is to use JQuery.

The Example Project

We will use an existing example project I created to demonstrate how to display a table with checkboxes for each row, which allows submission to the server for processing the selected items. Here, we will focus on the selection toggling portion of the Index View.

You can find the source code for the example project on my Github repo.

If you clone or download the source from Github, you will need to Enable Nuget Package Restore in order that VS can automatically download and update Nuget packages when the project builds.

The Index View, with Selectable Items in a Table

For our purposes, we will only need to look at the Index view, which presents a table where each row features a checkbox on the leftmost side allowing the user to select one or more individual row items from the list.

The original code for the View looks like this:

Index View with a Table and Checkboxes:
@model AspNetCheckedListExample.Models.PeopleSelectionViewModel
  
@{
    ViewBag.Title = "People";
}
  
<h2>People</h2>
  
@using (Html.BeginForm("SubmitSelected", "People", FormMethod.Post, new { encType = "multipart/form-data", name = "myform" }))
{
    <table class="table">
        <tr>
            <th>
                Select
            </th>
            <th>
                Name
            </th>
            <th></th>
        </tr>
        @Html.EditorFor(model => model.People)
    </table>
    <hr />
    <br />
    <input type="submit" name="operation" id="submit" value="Submit Selected" />
}

In the above, we set up a table, and use a custom Editor Template to render each row item, allowing for the selectable textbox on each row, the status of which will be reflected in the model data passed back to the controller in an Http POST request on form submit.

We want to add a checkbox above the table, selection of which toggles the checked status of all the checkboxes in the table at once.

Add the Select All Checkbox

To do this, we will modify the form on our Index page by adding a <div> element containing our global checkbox, which we will name “checkall”, and then also wrap our Html table in a div named “checkboxes” that we can then manipulate using JQuery:

Add Div Elements to HTML Form on the Index Page:
@using (Html.BeginForm("SubmitSelected", "People", FormMethod.Post, new { encType = "multipart/form-data", name = "myform" }))
{
    // Add a new checkbox in its own div element:
    <div>
        <input type="checkbox" id="checkall" /><span>Check All</span>
    </div>
  
    // Wrap the table element in a div named "checkboxes":
    <div id="checkboxes">
        <table class="table">
            <tr>
                <th>
                    Select
                </th>
                <th>
                    Name
                </th>
                <th></th>
            </tr>
            @Html.EditorFor(model => model.People)
        </table>
    @*Close the "checkboxes" div element:*@
    </div>
    <hr />
    <br />
    <input type="submit" name="operation" id="submit" value="Submit Selected" />
}

JQuery Code to Manipulate the Checkboxes

Now we will add some JQuery to perform the manipulation when we want to toggle the checkbox status. For simplicity, we are going to add this code right on our page. Note that there are myriad ways to do this, and you may see some methods out on the internet which are slightly different.

Under our view code, we will add a <scripts> section, and add the following JQuery:

Add JQuery to Toggle the Checkbox Status for the Table Row Items:
@section Scripts {
    @Scripts.Render("~/bundles/jqueryval")
  
    <script type="text/javascript">
  
        function toggleChecked(status) {
            $("#checkboxes input").each(function () {
                // Set the checked status of each to match the 
                // checked status of the check all checkbox:
                $(this).prop("checked", status);
            });
        }
  
        $(document).ready(function () {
  
            //Set the default value of the global checkbox to true:
            $("#checkall").prop('checked', true);
  
            // Attach the call to toggleChecked to the
            // click event of the global checkbox:
            $("#checkall").click(function () {
                var status = $("#checkall").prop('checked');
                toggleChecked(status);
            });
        });
    </script>

In the above code, We define a function, toggleChecked() , which sets the checked status of each checkbox in the table to match that of the global “checkall” checkbox. Then, in the JQuery (document).ready() function, we the default value of the global “checkall” checkbox to true, and attach a call to the toggleChecked() function to the click event of the global “checkall” checkbox.

As we can see, it is not a complex matter to do this, but it may not be intuitive to those newer to Jquery.

As I mentioned, there are myriad ways to do this out there on the web. if you have seen a better way, or noticed something I have done above that it just plain stupid, please do let me know in the comments, or drop me an email at the address in the About the Author section.

Additional Resources and Items of Interest

ASP.Net
ASP.NET Web Api: Understanding OWIN/Katana Authentication/Authorization Part II: Models and Persistence
CodeProject
Java: Checked Exceptions, Revisited (or, a closer examination of a flawed mechanism)
CodeProject
A More Useful Port of the Chinook Database to Postgresql
  • michael shen

    $(“#checkboxes input”).each(function () how to find the all checkboxes inside the table, if we have other type of input elements besides the checkboxes (as we know the table row has 3 elements: a checkbox a displayFor text and hiddenFor element, does the @Html.hidderFor render element into input html tag?)