Unobtrusive Validation for Inline Datepicker not working, works fine for non-inline Datepicker
Asked Answered
C

2

5

I didn't use jquery.ui's datepicker because I needed to select an entire week and multiple dates under different conditions, so I am using Keith Wood's datepicker in an EditorTemplate for my Date fields:

    @model Nullable<DateTime>
    @{
        string name = ViewData.TemplateInfo.HtmlFieldPrefix;
        string id = name.Replace(".", "_");
        string dt = Model.HasValue ? String.Format("{0:d}",(string)Model.Value.ToShortDateString()) : string.Empty;
    }        
    @Html.TextBox("", dt, new { @class = "datefield", @type = "date", @id = id })
    <script type="text/javascript">
        $(document).ready(function () {
            $('#@id').datepick({
                renderer: $.datepick.themeRollerRenderer,
                multiSelect: 999
            });
        });    
    </script>

Validation works just fine when using a textbox and having the datepicker "pop-up"; but what I really want is to use an inline datepicker, but I can't get validation to work under these conditions:

    @model Nullable<DateTime>
    @{
        string name = ViewData.TemplateInfo.HtmlFieldPrefix;
        string id = name.Replace(".", "_");
        string dt = Model.HasValue ? String.Format("{0:d}",(string)Model.Value.ToShortDateString()) : string.Empty;
    }

    <div class="kwdp">
    </div>
    @Html.Hidden("", dt, new { @class = "datefield", @id = id })
    <script type="text/javascript">
        $(document).ready(function () {
            $('.kwdp').datepick({
                renderer: $.datepick.themeRollerRenderer,
                multiSelect: 999
            });
        });    
    </script>

Here is a snip-it of my custom client-side validation:

    form.validate({ 
        rules:{
            StartDate: { 
                required: true, 
                dpDate: true 
            }
        },
        messages: {
            StartDate: 'Please enter a valid date (dd-mm-yyyy)'
        }
    });

And here is the definition of the DateTime field in my Data Class:

    [Required]
    [DataType(DataType.Date)]
    [DisplayFormat(ApplyFormatInEditMode = true, DataFormatString = "{0:dd-MM-yyyy}")]
    public Nullable<DateTime> StartDate { get; set; }

I understand that I should add an onSelect for the datepicker to populate the hidden field with date(s), but regardless, I should get an error when the hidden field value is empty, but its not validating. The html markup is rendered as the following:

    <input name="StartDate" class="datefield" id="StartDate" type="hidden" data-val-required="The StartDate field is required." data-val="true" data-val-date="The field StartDate must be a date." value=""/>

I am using the following libraries:

    <script src="@Url.Content("~/Scripts/jquery.validate.min.js")" type="text/javascript"></script>
    <script src="@Url.Content("~/Scripts/jquery.validate.unobtrusive.min.js")" type="text/javascript"></script>
    <script src="@Url.Content("~/Scripts/jquery.unobtrusive-ajax.min.js")" type="text/javascript"></script>    
    <script src="@Url.Content("~/Scripts/datepick/jquery.datepick.min.js")" type="text/javascript"></script>
    <script src="@Url.Content("~/Scripts/datepick/jquery.datepick.ext.min.js")" type="text/javascript"></script>
    <script src="@Url.Content("~/Scripts/datepick/jquery.datepick.validation.min.js")" type="text/javascript"></script>
    <script src="@Url.Content("~/Scripts/jquery.ui.datepicker.validation.min.js")" type="text/javascript"></script>

I found a similar un-answered question that looks the developer is having the same problem, but no posted solution. Any ideas to where I am going wrong?

Czarevitch answered 2/6, 2012 at 1:14 Comment(0)
B
8

Jason is right. By default, jquery validation skips / ignores non-visible input elements. This goes for input type="hidden" elements, or even text boxes that have / inherit display:none; CSS. There is a setting called ignore, and its default value looks like this:

ignore: ':hidden'

You can override this setting on your page with the following script:

$.validator.setDefaults({
    ignore: ''
});

This tells jquery validate not to ignore validation for non-visible elements. If you use this script, jquery validation should automatically, validate the field unobtrusively without you having to manually validate each time the datepicker field value us changed.

Booker answered 2/6, 2012 at 16:55 Comment(2)
That did it! It works for both Html.Hidden(...) & Html.TextBox(... style="display:none"). Note: I did have to load it early on in the page lifecycle, I couldn't just setDefaults() in a function called when dynamically populating a form with elements. Thanks for the help. R/ BrandonCzarevitch
Yes you are right, the default setting override doesn't seem to take effect if you put it in a self-executing anonymous function.Booker
H
0

In MVC3 hidden form fields are not validated by the clientside validation script, from what I understand. Why not just make the text field hidden, if thats all you want to do?

@Html.TextBox("", dt, new { @class = "datefield", @type = "date", @id = id, style="display:none;" })

or if you want to keep it as a @Html.Hidden field you will have to manually call the validate plugin on the form each time the datepicker is changed.

 $("form").validate().form();
Hyperbola answered 2/6, 2012 at 1:28 Comment(2)
It seems that not only are they not validated when type="hidden" but and when display:none as well as it wasn't evaluated either.Czarevitch
I initially tested this in mvc3 before migrating the mvc4 in hopes it would solve the issue, but it didn't, hence the title. But the the fix you posted I've only tested in mvc4, I saw elsewhere that the display:none should have fixed it in mvc3, I'll try migrating back to mvc3 to test your fix.Czarevitch

© 2022 - 2024 — McMap. All rights reserved.