Using JQuery UI to Add Effects to a Drupal Site (Part I)

Subject: 
Difficulty: 

The JQuery UI JavaScript library makes it easy to add all sorts of interactive animations to your website with just a few lines of code. Because there are a lot more moving parts, though, it can be a little tricky to integrate these scripts into a CMS like Drupal. In a recent project, I used JQuery UI's .dialog method to script a modal message.

If you want to see the finished file (including the additions from Part II), you can download it here: modal.js.

What the Client Wanted

The client for this project was the board of a non-profit organization that promotes the use of meditation in psychotherapy. I had already built them a directory of clinical members using the powerful views module. The view displays data and user pictures drawn from the profiles of those users possessing the "clinical member" role.

The directory is publicly accessible, and the board decided that they wanted to display a "terms of service" that the user must agree to before proceeding to search the directory and view therapist profiles.

I determined that the best tool for the job was probably JQuery UI. The site was built in Drupal 6, however, which does not come with JQuery UI already installed. I had some work to do before I could take advantage of that script library.

Setting up JQuery UI on the Site

There are a few steps to setting up JQuery UI on a Drupal 6 site. (Drupal 6 already supports the JQuery library, on which JQuery UI depends, so at least that's out of the way.) 

  1. Install the module. Install and activate the JQuery UI Module. (I won't go into how to install a module here; there's plenty of documentation on the drupal site and elsewhere if you'd like help with that). Unlike most other modules, this one doesn't do anything on its own. It was designed solely to make it easier for developers to make use of JQuery UI in their projects.
  2. Install the library. Follow the instructions in the JQuery UI Module README.txt file and download and enable the appropriate version of the JQuery UI library, installing it in your sites/all/libraries folder.
  3. Enable the method. You're not there yet. Installing the module and the library still doesn't make JQuery UI methods available. You need to go into the folder of the theme in which you want to use JQuery UI (e.g., Garland), and then go into that theme's template.php file. For each method from the JQuery UI library that you want to access, you'll need to add a line of code to the template.php like the following. (I only needed one method, "ui.dialog", so that's all I added.) 
    jquery_ui_add("ui.dialog");
  4. Reload the Theme. In my experience, changes to theme files don't take effect right away. You have to go back to the theme administration page and save the theme choices again (even if you are not making any changes) for the changes you made to the files to take effect. If the changes still don't show up, I recommend flushing the caches of your drupal site.

Scripting the Modal Message 

Now that we have the ability to use JQuery UI, we can create a new file within which to write our script. I called mine modal.js and saved it in the same directory as my theme. The theme, however, doesn't know anything about this file or where to find it.  To make sure that the theme calls this script on every page, I need to to edit the [nameofyourtheme].info file, adding the following line of code:

scripts[] = "modal.js"

You'll probably have to reload the theme again for this change to take effect (see #4, above).

Now, I'm finally ready to get scripting. I plan to put the text of the terms of service in the footer of my view. It will be nestled in a DIV with the id of "dialog." That way I can select that block of text in JQuery like this: 

$("#dialog")

Once I've called it, I can apply the .dialog method made available in JQuery UI. I'll modify this later, but for now, this is the code that will call my dialog box:

 (document).ready(function(){
     $("#dialog").dialog ({
     autoOpen: true,
     position: "top",
     draggable: false,
     closeOnEscape: false,
     title: "Terms of Service",
     show: "fold",
     hide: "fade",
     modal: true,
     resizable: false,
     width: 750,
     height: 750,
     buttons: { "I accept the terms": function() {
          $(this).dialog("close");} //end empty function
          } //end buttons
     }); //end .dialog
}); //end ready event

About the Code

You'll notice that the code that actually generates the dialog box is wrapped inside another function:

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

The document ready function ensures that the code nested inside of it launches immediately when the page loads (not waiting on other elements to load).

The rest of the code is very simple. Using the documentation of the .dialog method, you simply indicate the properties you want the dialog to have: how wide, modal or not (i.e., effectively disabling the rest of the page while the box is active), whether it opens automatically, and so on. (I often have trouble keeping track of functions within functions, so I've added some comments to the code to make this a little easier.)

Adding the Terms of Service to the View

The page element that this function is calling, a DIV with the ID of "dialog," doesn't exist yet. If, like me, you were applying this modal message to a Drupal view, you'd need to add it to that view somewhere. In my case, I edited the view and put the terms of use as HTML text in the footer of the page view. I enclosed that HTML in the DIV, like so:

<div id="dialog">The HTML and text of my terms of service</div>

Now, when you save the view and visit the page, you'll find that the script runs and the terms of service appear as a modal dialogue box that the user must click "I agree" to get rid off. This is just what the client wanted . . . well, sort of.

Complications

Basic Modal DialogWe have a working dialog box that shows up every time the user visits the page view--in this case, the directory of clinical members. There are still some problems though:

JQuery UI has put a little "X" in the corner of the dialog box. The user can just click "X" to close the window instead of "I agree." This isn't a binding legal document, but it is very important to the client that the user directly click "I agree" before getting to the directory. We'll have to get rid of that "X."

The dialog box appears every time the page loads. Every time. This seemed like the desired behavior at first, but it's not. The page refreshes whenever the user sorts the table, or advances to the next page in the list of therapists, and--you guessed it--each time the window pops up to annoy the user all over again. We really only want the user to have to agree to the terms of service only once per visit to the site (or maybe once every year or something like that, or only when the terms change).

Solving these problems will require writing some additional code and passing a cookie to the user's browser when they click the "I Agree" button. I'll cover that in Part II.

To learn how to use JQuery and JQuery UI in your own projects, check out lynda.com's JQuery Essential Training. You can learn how to modify Drupal themes and how to create your own with the Creating and Editing Custom Themes course.