Sudarshan's Blog

My Thoughts, Findings & Experiences

ASP.NET AJAX async call doesn't fire jQuery's 'document.ready()' event: Solution

October 6, 2010 00:56

On our current project we were using following technologies:

  1. ASP.NET
  2. jQuery: for DOM manipulation at client side
  3. jQuery plugins like validator plugin, cleditor plugin, msked input plugin etc.
  4. ASP.NET AJAX: For doing asynchronous calls

Before introducing AJAX functionality on the page, all the jQuery plugins were working fine.But, as we implement AJAX functionality on the page, all the plugins stopped working.

BIG QUESTION, why?

Lets examine working on any jQuery plugin. We need to perform some operations inside the jQuery's 'document.ready()' event.

Here is the example for masked input plugin:

$(document).ready(function() {
// Attaches masks to page controls
$('#<%= txtSsn.ClientID %>').mask("999-99-9999");
$('#<%= txtBirthDate.ClientID %>').mask("99-99-9999");
});

This code get executed every time page is loaded.

Now, when we do asynchronous call using ASP.NET AJAX, only update panel's content get refreshed and not the whole page. This is why jQuery's 'document.ready()' event doesn't get fired. Because of this the masking associated with page controls gets removed.

But, this is so common situation and what to do?

Solution:

There are 2 different ways that I know:

  1. Make use of async call end event which is provided by ASP.NET AJAX. I don't prefer this way because we need to explicitly register and handle async event.
  2. Implement jQuery 'AjaxReady' event . (Thanks to unknown person who posted this solution on some forum, but he missed out to mention how exactly we should use it).

So, we will prefer 2nd way.

This solutions involves following steps:

Register event into jQuery like this

jQuery.fn.extend({
AjaxReady: function (fn) {
if (fn) {
return jQuery.event.add(this[0], "AjaxReady", fn, null);
} else {
var ret = jQuery.event.trigger("AjaxReady", null, this[0], false, null);
// if there was no return value then the even validated correctly
if (ret === undefined)
ret = true;
return ret;
}
}
});

This code should present into your *.js file or inside '<script language="javascript">' tag

Add following script within update panel's 'ContentTemplate'

<asp:UpdatePanel ID="upnlInsuranceCarrier" runat="server">
<ContentTemplate>
// Below script is very important
<script type="text/javascript">
prm = Sys.WebForms.PageRequestManager.getInstance();
prm.add_endRequest(EndRequest);
function EndRequest(sender, args) {
$(document).AjaxReady();
}
</script>

Define your $(document).AjaxReady() event like this

$(document).AjaxReady(function () {
// Add code which needs to be executed after async call
});

Finally your code will look like

$(document).ready(function () {
setup();
});

$(document).AjaxReady(function () {
setup();
});

function setup() {
$('#<%= txtSsn.ClientID %>').mask("999-99-9999");
$('#<%= txtBirthDate.ClientID %>').mask("99-99-9999");
}

// Now, masked input plugin will work fine in async call as well

 

Happy Programming!