Webinar wrap-up: Julian on JavaScript–using jQuery with DevExpress ASP.NET controls

ctodx
29 June 2011

When I originally proposed this webinar I thought the topic was doable in a single session. It turns out I was way too optimistic, not only did I have to draft Mehul in to help (he knows way more about our ASP.NET controls than I do), but we also decided that the subject deserved a couple more to give it justice. So this particular presentation turned into a “basics” webinar; we’ll cover other ideas later on.

Construction Signsphoto © 2008 jphilipg | more info (via: Wylio)You can watch the webinar here. The slidedeck is here.

UPDATE: Mikhail in the ASP.NET team was kind enough to point out a couple of issues and some extra information. Look out for the UPDATE markers in the text below.

Basics

Speaking broadly, jQuery has two main uses: finding elements, and doing something to those elements (for example, changing values, properties, and attributes, and animating them). DevExpress ASP.NET controls have some of the same features, and our recommendation is that it’s best to use the built-in support whenever possible. Don’t fight it just to trumpet that you’re using jQuery, use what we already provide whenever possible.

If you find that jQuery with the DevExpress controls is hard, jQuery UI adds a whole new complexity layer on top. To be blunt: if you don’t pay attention, you’ll find yourself battling between what jQuery UI wants and what the ASP.NET controls want. An example of this is B144365. (UPDATE: we’ve updated this report to make it more readable and understandable. Ditto B142903, referenced within that report.)

Basic issues

1. DevExpress ASP.NET controls don’t use jQuery (whereas our ASP.NET MVC extensions do). That means that you will have to remember to add a script element to load jQuery. Best place for it is in the website’s master page, to ensure jQuery’s loaded for all pages.

<script type="text/javascript" src=http://ajax.microsoft.com/ajax/jQuery/jquery-1.6.1.min.js></script>

Here, I’m using Microsoft’s CDN (Content Delivery Network) to load it, but of course you can use a local copy or Google’s API for loading JavaScript libraries.

2. How do you find the right DOM element? ASP.NET controls have a complex algorithm to name HTML elements. Our controls sometimes (or maybe, often) create a set of HTML elements in a container hierarchy for a single ASP.NET controls. My advice here is to not try and guess the id of an element (or the classes to which it belongs), but to look at the source code for the page. Find the HTML rendering for the control and use that to understand the relationship between the container(s) and the input control(s) and other elements. Mehul also pointed out you can use the developer tools for your favorite browser to determine the same information.

I’ll note that sometimes it’s possible to use the client-side ClientInstanceName() function at run-time to determine the id of the element. (UPDATE: ClientInstanceName is a property not a function.) We’ll see an example of this later.

3. When should you set up bindings? Normally in website programming with jQuery you use the document ready function to set up bindings to event handlers and the like, since you know all the elements have been created. So you write a function to be executed with jQuery(document).ready(myFunction) function or the simpler $(myFunction). Easy enough, but it must be emphasized that DevExpress controls have some special initialization that may not be complete at document ready time or that executes after your document ready function (remember the ASP.NET controls don’t use jQuery, so their special “document ready” code may execute before or after jQuery’s).

(Aside: in essence there are several parts to a DevExpress control at run-time. There’s the HTML DOM element (or elements). There’s also the client-side JavaScript object that takes care of communication between client-side and server-side. And there’s the server-side object defining the control’s behavior. It is the JavaScript object that may not be fully initialized at document ready time.)

In certain cases, it may make sense to catch the Init event of the controls’ ClientSideEvents object to set up your bindings to jQuery.

4. Unobtrusive vs. obtrusive JavaScript. The modern style of using JavaScript on a web page is to use it unobtrusively. All event handlers and special JS functionality are attached at run-time by JavaScript code. This is the ideal, but of course ASP.NET apps don’t follow this at all: they all embed code in the middle of the HTML, mixing content with behavior. If you like, this is old-style JavaScript. Be aware that our controls will use obtrusive JavaScript and plan/test accordingly when you add other handlers via jQuery.

5. Losing jQuery bindings after callbacks. Be aware that DevExpress controls will rebuild parts of the DOM after a callback (for example, paging down in the grid). Your carefully crafted bindings will be lost since the DOM elements they were attached to have gone away, even though the control “looks” the same after the callback. We recommend you peruse this sample: E3324.

Simple example 1

  • Drop a textbox, label, and button on form
  • Clicking the button will post the entered text to the label and refresh the page
  • Using jQuery:
    • If textbox is empty, show “Enter data” in it
    • If textbox gains focus & is empty, remove that text
    • If textbox has value, just show value

Let’s take it step by step. This is the first time we'll be discussing what is being rendered.

UPDATE: We already have this feature built into our ASPxEditors. It’s known as NullText or Watermark.

Set the button's Click handler to

    protected void ASPxButton1_Click(object sender, EventArgs e) {
      ASPxLabel1.Text = ASPxTextBox1.Text;
      ASPxTextBox1.Text = "";
    }
You can run the app, and see that it works. Whatever you type into the textbox is reflected in the label when the button is clicked. It uses a postback. View the HTML source for the running web page. Note that the actual HTML input field is in a <table> container and the container has the id we’d expect, whereas the input field has a different id.

Add the jQuery script element above to the master page. Write the document ready script at the bottom of the ASP.NET body content container:

<script type="text/javascript">
  $(function () {

  });
</script>

Now for the first line of code:

    var textBoxId = "<%= ASPxTextBox1.ClientID %>";
    alert(textBoxId);

What's happening here is that we're using ASP.NET to fill in the actual id for the textbox. We don't want to "calculate" it in the script; let ASP.NET do it for us. Run the app to see the alert. We're getting there.

Now to get the container (delete the alert – it was just to show what the id looks like).

    var textBoxContainer = $("#" + textBoxId);

Now to get the HTML input field:

    var textBox = textBoxContainer.find("input");

Now for the (fairly simple) code:

    var isEmpty = true;

    var setValueWhenEmpty = function () {
      if (textBox.val()) {
        isEmpty = false;
      }
      else {
        isEmpty = true;
        textBox.val("Enter data")
      }
    }

    textBox.bind("focus", function () {
      if (isEmpty) {
        textBox.val("");
      }
    });

    textBox.bind("blur", function () {
      setValueWhenEmpty();
    });

    setValueWhenEmpty();

Run to show it in action: when the textbox doesn't have focus and is empty, "Enter data" is shown. Focus it and it becomes blank. If it has a value, it’s always displayed.

If you give the textbox control a ClientInstanceName (say, myTextBox), you can change the initial code as follows:

    var textBox = $(window.myTextBox.GetInputElement());

That is, the code for the control will create a JavaScript object called myTextBox, and you can use the GetInputElement() function to return the DOM element for the input field. After that, just call jQuery on the DOM element to return the jQuery object for the input element. After that, we can use the same code to bind focus and blur (the blur event is the DOM’s name for the unfocus event).

Summary: we've seen how to identify elements in an ASPX page created with DevExpress controls and how to add event handlers to the required elements, all using jQuery.

Simple example 2

We’ll build on the example we just made by getting the label to flash when it is initially shown.

Show the source for the running app and note how the label gets rendered. This time there's no container to worry about.

Color animation is done through jQuery UI: it extends the basic jQuery animations to include color. So we need to add the jQuery UI JavaScript file to the project's Scripts folder (or you can use a CDN), and then add it as a script tag to the master page using drag/drop.

Add the following code:

      var labelId = "<%= ASPxLabel1.ClientID %>";
      var label = $("#" + labelId);
      var origBackColor = label.css("backgroundColor");
      var origColor = label.css("color");

      if (label.html()) {
        label.animate({
          backgroundColor: "#DC574E",
          color: "white"
        }, 2000, function () {
          label.animate({
            backgroundColor: origBackColor,
            color: origColor
          }, 500);
        });
      }
In other words: get the id of the label, get the jQuery object for that id, save the current fore and back colors. If the label has some text, animate the colors to something more visible and, on completion of that animation, animate them back to the original colors.

Summary: jQuery UI needs us to add the custom JS file to our Scripts folder. Again we reinforce the plan of attack: look at what's originally rendered to understand the structure, use that knowledge to get at the right DOM elements and manipulate them using jQuery.

Complex example

Mehul presented a great example using jQuery with the ASPxGridView: highlighting the just-edited-and-updated row. You can read about it here.

Interesting jQuery-with-DevExpress examples

The support team are adding jQuery examples regularly. Here are some of the more interesting ones:

  • E3324 – binding jQuery to data cells
  • E3325 – Attach jQuery UI AutoComplete to ASPxTextBox
  • E1810 – drag/drop from one ASPxGridView to another using jQuery UI library

Free DevExpress Products - Get Your Copy Today

The following free DevExpress product offers remain available. Should you have any questions about the free offers below, please submit a ticket via the DevExpress Support Center at your convenience. We'll be happy to follow-up.
No Comments

Please login or register to post comments.