views:

3715

answers:

6

I have seen lots of questions relating to this topic.

I am using asp.net MVC 1.0

Problem area

If I use

<%= Html.CheckBox("Status", true) %>

Then why It renders like

<input checked="checked" id="Status" name="Status" type="checkbox" value="true" /><input name="Status" type="hidden" value="false" />

I put this in foreach loop and I have 5 rows.

when I submit form with true,true,true,false,false then I get true,false,true,false,true,false,false,false

i.e. for false => false.

for true => true,false

If I use

<input type="checkbox" value="true" name="Status" checked="checked" />

Then I don't get unchecked one's.

so how do I overcome form this problem?

Please don't post answer with using loop in formcollection object and checking each key!

A: 

It renders so because default binder requires the FormCollection to have a value for nonnullable parameters. Using this technique we are sure that the value will be sent even the checkbox is not checked (by default the value sent only when it's checked). If you use this controller method with just one html input you'll get error on form post with unchecked checkbox (value of checkbox will not be posted and binder will not know what to use for value of isItemSelected):

public ActionResult SomeActionMethod(bool isItemSelected)

You can try use something like this with just one html input:

public ActionResult SomeActionMethod(bool? isItemSelected)

But in this case isItemSelected will be null or will be true. And it will never become false.

zihotki
+1  A: 

In your example, when you submit form with true,true,true,false,false and you get

true,false,true,false,true,false,false,false
it is interesting to note that you are not actually getting eight values back, but five arrays that merely looks like this is the case because all of the values are joined.

I know you asked to not get a loop for your answer, but I can use one to demonstrate what is really happening here:
foreach (string key in postedForm.AllKeys) {
    // "value" will contain a joined/comma-separated list of ALL values,
    // including something like "true,false" for a checked checkbox.
    string value = postedForm[key].GetValue;
    // "values" will be an array, where you can access its first element,
    // e.g., values[0], to get the actual intended value.
    string[] values = postedForm.GetValues(key);
}

So, for your checked boxes, you'll get a values array with two elements, and for unchecked boxes, you'll get just a single-element array.

Thus, to answer your question how do you overcome this problem, the answer lies in using GetValues rather than GetValue, and thinking of your posted fields as arrays rather than strings.

Best of luck!

Funka
A: 

Well there are couple of ways you can do based on your requirement.

I use this method.

<input type="checkbox" value="<%= item.ID %>" name="check" checked="checked")" />

This is may checkboxes.

On server side I will also have array of ID's of item in the model. So I check it whether it is in array

var strArray = form["checkbox"]; //Request.form["checkbox"] or "FormCollection form" in action parameter;  array of ID's in comma separated string.

Different people have different tests.

Vikas
A: 

I know this isn't the elegant one but this is what I did:

collection["response"].Replace("true,false", "true").Split(',').ToList();

RailRhoad
A: 

<%= Html.CheckBox("Status", true) %>

this was intended to use for just just simple CheckBox, what you want is checkboxList, which is not yet cover in the API of ASP.net MVC

If you looking for some thing like checkboxlist, maybe you should write your own helper, provide you understand HTML well..

That's it! :)

DucDigital
A: 

Easier just to check whether AttemptedValue.Contains("true") - it will, if it's checked, not if it's unchecked....

mansachs