My model has a boolean that has to be nullable
public bool? Foo
{
get;
set;
}
so in my Razor cshtml I have
@Html.CheckBoxFor(m => m.Foo)
except that doesn't work. Neither does casting it with (bool). If I do
@Html.CheckBoxFor(m => m.Foo.Value)
that doesn't create an error, but it doesn't bind to my model when posted and foo is set to null. Whats the best way to display Foo on the page and make it bind to my model on a post?
For me the solution was to change the view model. Consider you are searching for invoices. These invoices can be paid or not. So your search has three options: Paid, Unpaid, or "I don't Care".
I had this originally set as a bool? field:
This made me stumble onto this question. I ended up created an Enum type and I handled this as follows:
Of course I had them wrapped in labels and had text specified, I just mean here's another option to consider.
All the answers above came with it's own issues. Easiest/cleanest way IMO is to create a helper
MVC5 Razor
App_Code/Helpers.cshtml
Usage
In my scenario, a nullable checkbox means that a staff member had not yet asked the question to the client, so it's wrapped in a
.checkbox-nullable
so that you may style appropriately and help the end-user identify that it is neithertrue
norfalse
CSS
Why? This doesn't make sense. A checkbox has two states: checked/unchecked, or True/False if you will. There is no third state.
Or wait you are using your domain models in your views instead of view models? That's your problem. So the solution for me is to use a view model in which you will define a simple boolean property:
and now you will have your controller action pass this view model to the view and generate the proper checkbox.
I would actually create a template for it and use that template with an EditorFor().
Here is how I did it:
Create My template, which is basically a partial view I created in the EditorTemplates directory, under Shared, under Views name it as (for example):
CheckboxTemplate
:Use it like this (in any view):
@Html.EditorFor(x => x.MyNullableBooleanCheckboxToBe, "CheckboxTemplate")
Thats all.
Templates are so powerful in MVC, use them.. You can create an entire page as a template, which you would use with the
@Html.EditorFor()
; provided that you pass its view model in the lambda expression..Just check for the null value and return false to it:
When making an EditorTemplate for a model which contains a nullable bool...
Split the nullable bool into 2 booleans:
Within the editor template:
Do not postback the original property Foo, because that is now calculated from FooIsNull and FooCheckbox.