Creating jQuery plug-ins from MicrosoftAjax components

(c) Bertrand Le Roy We had an interesting discussion recently on the ASP Insiders mailing list and ended up talking about what cool stuff we could build on top of jQuery. Many interesting things were mentioned and it was a very useful discussion but one suggestion in particular struck my curiosity as it was something I had investigated before and that could be improved on with very little code.

I had already written a little plugin to enable instantiation of Microsoft Ajax components on the results of a jQuery selector:

jQuery.fn.create = function(type, properties) {
    return this.each(function() {
        Sys.Component.create(type, properties, {}, {}, this);
    });
};

I have another version that is a little more elaborate and takes a bag of properties and events instead of just properties (get it from the attached sample) but you get the idea. This makes it fairly easy to instantiate components based on a selector:

$(":text.nomorethanfive")
    .create(Bleroy.Sample.CharCount, { maxLength: 5 });

But if this were a native jQuery plugin instead of a Microsoft Ajax component, as Rick Strahl suggested, chances are you’d do something like this instead:

$(":text.nomorethanfive").charCount({ maxLength: 5 });

We can actually get that exact result fairly easily by writing a plugin that is specific to this component, but we can’t expect every Microsoft Ajax component author to also write a jQuery plugin, can we? We can do better than that. Here is a second small piece of code that is still generic but is in the business of creating jQuery plugins:

Sys.Component.exposeTojQuery = function(type, pluginName) {
    return jQuery.fn[pluginName] = function(properties) {
        return this.each(function() {
            Sys.Component.create(type, properties, {}, {}, this);
        });
    }
}

Like above, the version in the sample is better than that in that it supports events in addition to properties but again you get the idea. Thanks to this function, we can create a jQuery plugin for any existing Microsoft Ajax component with a single line of code:

Sys.Component.exposeTojQuery(Bleroy.Sample.CharCount, "charCount");

After this call, we can write exactly the code we wrote before, but without having had to write a specific plugin. We can then use charCount like a native jQuery plugin:

$(":text.nomorethanfive").charCount({ maxLength: 5 });

This is really easy to use, and I quite like it. We could for example add the following line of code to the new MicrosoftAjaxTemplates.js:

if (jQuery)
Sys.Component.exposeTojQuery(Sys.UI.DataView, "dataView");

This would enable us to instantiate DataView controls as simply as this:

<ul class="dv">
    <li>{{ $dataItem }}</li>
</ul>
<script type="text/javascript">
    $(".dv").dataView({ data: ["foo", "bar", "baz"] });
</script>

Get the code from here (you need to include jquery-1.3.2.js to the script folder):
http://weblogs.asp.net/blogs/bleroy/Samples/jQueryCreate.zip

12 Comments

  • Thanks Bertrand, this will make the client web applications easier to design.

  • Hi Sir,

    The article is very nice but the starting is little bit confusing. Thanks for letting us know this.

    Thanks,
    Thani

  • WHY ???WHY ???WHY ???WHY ???WHY ???

  • Globalization, client templates, client data and live bindings, integration with ADO.NET Data Services, client and server-side support for the back button, a client component model on which third parties are building professional & supported components (Telerik, Infragistics, ComponentArt, etc.), etc. What's bloat to you is useful to others. Client library is 24kB gzipped (jQuery is 18kB), and in 4.0 you can reduce it down to 7kB depending on what pieces you need.

  • If the globalization etc is indeed so good, then why not contribute to jquery ?

  • Just nice. Between this and the my previous work on Declarative jQuery (with Microsoft Ajax) we are able to go from one side to the other :-) letting users of either libraries use the components of the other one with less effort.

  • Do you guys set aside a day of the week to justify the work you do? Globalization? Is that how people are dong it these days? Via javascript? Huh...

    Data Services return JSON, why do you need msAjax for that?

    Using jQuery you can build your own plugin quicker than you can download those "professional" third-party components. Or you know, you can just goto plugins.jquery.com

    It isn't about size or bloat, but about continuing to put effort into outdated and inferior solutions (and dragging countless developers down with you). Its about streamlining and adapting.

  • Really great stuff here. Nice work guys but can i know when this will ship or be mature enough to be used in production. I really want to use it in my next project.

  • It's important to bear in mind that not everyone uses jQuery. We started off with the intention to use it, but ended up with ExtJs for our current web app because of its far more mature widgets (check out the grid), which you can find all in one place. No hunting around the plugin-o-sphere.

    ExtJs has 45 localization files, but they mainly contain localized resource strings for the widgets. There's limited support for formatting a date for display, and no support for formatting a floating point number (AFAICS). Compare this with MS AJAX's globalization files, which give you great support for formatting and parsing dates and numbers in 205 different cultures. Most of our formatting for display takes place on the server, but occasionally we need the client-side globalization support (e.g. for formatting numbers that the user enters into the editable ExtJs grid).

    So if Bertrand and team are going to keep globalization (and other useful parts of MS AJAX) separate from jQuery, and applicable to both jQuery and other JavaScript libraries, I can only applaud.

  • #twitcode version of Bertrand's exposeTojQuery function:

    c=Sys.Component;c.$it=function(t,pn){return jQuery.fn[pn]=function(p){return this.each(function(){c.create(t,p,{},{},this);});}}

    ;-)

  • @Oskar: awesome, but you should add var in front of that c to avoid a warning in strict mode.

  • @Bertrand - re Karl Seguin's comments. I totally get where you're coming from on this. With regards to Karl, I'm afraid he's just jumped on the Scott Bellware Not-Invented-By-Microsoft bandwagon that's so vogue in certain cliques. The problem is, whilst he tries to ride the smarter than thou high horse for not using the MS toolchain, he's nowhere near as talented or as interesting as Scott, who's a real pragmatist.

Comments have been disabled for this content.