0
votes

I am building a web application in ASP.NET Core 1.1 (MVC) using VS.2017 Community. In it I have a view in which I have to display a list of checkboxes and then when the form is submitted the model contains among other things the list of checkboxes that were checked. However, when the POST is done, the other properties are passsed well but the List<> property has the correct length (one for each checkbox, marked or not) but the IsChecked property of all of them is false even when the checkbox was checked.

My View Model that is passed to the view looks like this:

public class UserPermissionsViewModel {
    public string Id { get; set; }
    public string UserName { get; set; }
    public List<CheckboxListItem> PermissionList { get; set; }

    public UserPermissionsViewModel() {
        PermissionList = new List<CheckboxListItem>();
    }
}

public class CheckboxListItem {
    public int ID { get; set; }
    public string Display { get; set; }
    public bool IsChecked { get; set; }
}

And the relevant part of the view where I render the list of checkboxes looks like this:

@model Models.UserPermissionsViewModel

@{   // code block in the middle of the view, not at the top!
     foreach (CheckboxListItem cbitem in Model.PermissionList) {
         <div class="checkbox">
            <div class="form-inline col-md-offset-2">
               <input type="hidden" asp-for="@Model.PermissionList[i].ID" />
               <input type="hidden" asp-for="@Model.PermissionList[i].Display" />
               <input type="checkbox" asp-for="@Model.PermissionList[i].IsChecked" value="@Model.PermissionList[i].IsChecked" />
               <label asp-for="@Model.PermissionList[i].ID">@Model.PermissionList[i].Display</label>
            </div>
         </div>
     }
}

And the Post controller action (simplified):

[HttpPost]
[ValidateAntiForgeryToken]
public IActionResult PermissionAssignToUser(UserPermissionsViewModel model)
{
     if (ModelState.IsValid) {
         // it gets here but the model.PermissionList pty has ZERO length.
     }
}

So how do I actually get the list of values right, thus indicating that for example checkbox with ID = 1 is true and checkbox with ID = 3 is true? So far I get all of them but with value false instead of the actual checkbox state.

UPDATE #3 After much trial I actually got it to work and found out WHY the states of the checkboxes were not being passed to the Post action method.

If you can see above my input tag helper for the checkbox type not only has an asp-for property but also a value property. I thought that with it I would have it display the current value (when the view was rendered). But as it turns out, if you specify a value (or checked) property in addition to the asp=for property then the POST action method will always receive false regardless of the actual state of the checkbox.

If on the other hand for the checkbox type you only specify the asp-for property, then the checkbox state is properly communicated via the model to the POST action method.

So replacing the checkbox input above for this one below actually solves the problem:

<input type="checkbox" asp-for="@Model.PermissionList[i].IsChecked" />
1
There's a number of questions that explain how you could implement a CheckboxList. Here's previous answer of mine that should work in .net core stackoverflow.com/questions/21841428/… The gist is that you need 2 lists, 1 to maintain all the values and 1 to maintain the checked values.Fran
@Fran Actually, with my answer above I got it to work with just one list. On the Post I receive the list of all checkboxes with their actual state (checked/unchecked).Lord of Scripts
The thing is, you don't need to pass all that information. html will pass multiple values as an array if you give all the checkboxes the same name. you know the checked values by the array values passed back in the post. There should be no need for all those extra hidden fields.Fran
Add your own answer and accept it to close this out. Questions should not contain the answer.user3559349
where are you initializing "i" ?Oracular Man

1 Answers

0
votes

After much trial I actually got it to work and found out WHY the states of the checkboxes were not being passed to the Post action method.

If you can see above my input tag helper for the checkbox type not only has an asp-for property but also a value property. I thought that with it I would have it display the current value (when the view was rendered). But as it turns out, if you specify a value (or checked) property in addition to the asp=for property then the POST action method will always receive false regardless of the actual state of the checkbox.

If on the other hand for the checkbox type you only specify the asp-for property, then the checkbox state is properly communicated via the model to the POST action method.

So replacing the checkbox input above for this one below actually solves the problem:

<input type="checkbox" asp-for="@Model.PermissionList[i].IsChecked" />