I've got a web form with a start date field. I've tied a jquery datepicker to the txt field. Now when I choose a date in FF, the selected date is populated in the text box and the calendar popup closes. However when I do the same thing in IE8, the selected date is populated in the text box but the popup remains open. I've also noticed that a script error is generated as soon as I select a date in the popup calendar.
I'm using jquery 1.3.2, jquery-ui 1.7.2, and .NET 3.5. Here's an example of my code:
<script type="text/javascript">
$(document).ready(function() {
$("#<%=txtStartDate.ClientID%>").datepicker({
changeMonth: true,
changeYear: true,
showButtonPanel: true,
showOn: 'button',
buttonImage: '/_layouts/images/CALENDAR.GIF',
buttonImageOnly: true
});
});
</script>
<div id="stylized">
<asp:ValidationSummary ID="vs" runat="server" CssClass="messages-error" HeaderText=" Action required before the form can be submitted." ForeColor="" ValidationGroup="sh" />
<div class="formrow">
<div class="ms-formlabel formlabel">
<asp:Label ID="lblStartDate" runat="server" CssClass="ms-standardheader" AssociatedControlID="txtStartDate">Start Date:</asp:Label>
</div>
<div class="ms-formbody formfield">
<asp:RequiredFieldValidator ID="reqStartDate" runat="server" ControlToValidate="txtStartDate" ErrorMessage="Start Date is a required field." Text="*" Display="Dynamic" ValidationGroup="sh"></asp:RequiredFieldValidator>
<asp:CompareValidator ID="cvStartDate" runat="server" ControlToValidate="txtStartDate" ErrorMessage="Date must be in the format MM/DD/YYYY" Text="*" Display="Dynamic" ValidationGroup="sh" Operator="DataTypeCheck" Type="Date"></asp:CompareValidator>
<asp:TextBox ID="txtStartDate" runat="server"></asp:TextBox>
<span class="formMessage">ex. MM/DD/YYYY</span>
</div>
</div>
<div id="buttonrow">
<asp:Button ID="btnSubmit" runat="server" Text="Submit" CssClass="ms-ButtonHeightWidth" OnClick="Submit_Click" ValidationGroup="sh" />
<asp:Button ID="btnCancel" runat="server" Text="Cancel" CssClass="ms-ButtonHeightWidth" OnClick="Cancel_Click" CausesValidation="false" />
</div>
</div>
Here's the script error I get in IE when I select the date:
'length' is null or not an object
WebResource.axd
Here's the code where the error is being thrown from:
function ValidatorOnChange(event) {
if (!event) {
event = window.event;
}
Page_InvalidControlToBeFocused = null;
var targetedControl;
if ((typeof(event.srcElement) != "undefined") && (event.srcElement != null)) {
targetedControl = event.srcElement;
}
else {
targetedControl = event.target;
}
var vals;
if (typeof(targetedControl.Validators) != "undefined") {
vals = targetedControl.Validators;
}
else {
if (targetedControl.tagName.toLowerCase() == "label") {
targetedControl = document.getElementById(targetedControl.htmlFor);
vals = targetedControl.Validators;
}
}
var i;
for (i = 0; i < vals.length; i++) {
ValidatorValidate(vals[i], null, event);
}
ValidatorUpdateIsValid();
}
It happens on the .length in the for loop at the end. Vals is null and isn't found in the previous if/else. I've stepped through the javascript and if (typeof(targetedControl.Validators) != "undefined") returns false and then if (targetedControl.tagName.toLowerCase() == "label") returns false too. Thus the length is null or not an object error.
Now I'm not sure if the datepicker popup not closing in IE and the script error in the WebResources.axd file are related errors, but I'm leaning that way. Can anyone tell me why the popup isn't closing?
As a date is selected, the datepicker triggers the change event on the INPUT
element, but the ASP.Net validator picks up the click event instead, with the source an A
element, and tries to find the validators on that A
element, instead of the INPUT
. This can be observed by inspecting event.srcElement
inside the validator's ValidatorOnChange
function. In browsers other than IE, event.type is 'change' and event.target is correctly the INPUT
.
While the no-op function onSelect: function() { }
prevents the error, by overriding the .change()
built-in to the datepicker's default onSelect
, it also prevents the validators from triggering. Here's a work-around for both:
onSelect: function() {
this.fireEvent && this.fireEvent('onchange') || $(this).change();
}
This uses the normal .change()
trigger except on IE, where it's required to use .fireEvent
to get the event object to be associated with the change and not the click.
It seems to be a bug of sorts, but adding this line in the datepicker declaration should solve it:
onSelect: function() {}
The solutions provided above only prevents the error from occurring.
On the datepicker:
onSelect : function(dateText, inst){ inst.input.trigger('cValidate')
and bind the event to the calendar input element.
.bind('cValidate', function (event) { window.ValidatorOnChange(event); });
this will fire the validatorchanged event with the correct event args (input field).
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With