Handling jMaki Widget Events Using the Publish and Subscribe Mechanism



This document uses the jMaki Dojo fisheye widget to show you how to use the publish and subscribe mechanism to respond to jMaki widget events from your application.

Motivation for the Publish and Subscribe Mechanism

One of the many widgets that jMaki offers is the Dojo fisheye widget:



A page author adds this widget to an application by including the following ajax tag in a page:

 <a:widget

name="dojo.fisheye"

args="{items:[
{iconSrc:'images/icon_browser.png',caption:'You are here!'},
{iconSrc:'images/icon_calendar.png',caption:'test3'},
{iconSrc:'images/icon_update.png',caption:'Update'}

]}">
</a:widget>

In the preceding tag, each item in the items array represents the properties for the icon in the widget.

This widget resizes the image icons as the user moves the mouse over them. But, what if you want something to happen when the user clicks on an image? One way to do this is to register an event handler onto the widget by hand, as explained in Sang Shin's excellent jMaki lab.

Now there's a much easier way, which is to use the new publish and subscribe mechanism in jMaki.  This guide shows how we modified the example fisheye widget that is part of jMaki so that it publishes itself as a topic to which individual applications can subscribe.  You'll also see how to subscribe to the topic from your application.

Publishing to a Topic

The first step to use the publish and subscribe mechanism is to modify the widget's component.js file to publish the appropriate content to a topic.  In the case of the fisheye widget, we need to know which icon the user selected so that the application can respond appropriately to the event of the user clicking on the icon.  What we did to the fisheye widget's component.js file is we replaced the alert message inside the onClick function with a publish statement:


dojo.require("dojo.widget.FisheyeList");


// create the top level widget
var fishEye = dojo.widget.createWidget(widget.uuid);


// programtically add FisheyeListItem children to the widget
var counter = 0;

while (true) {

var i = widget.args.items[counter++];

if (i == null) break;

var icon = dojo.widget.createWidget("FisheyeListItem", i);


    icon.onClick = function (){

 jmaki.publish("/fisheye", this);
 }

   fishEye.addChild(icon);
}

As shown in the preceding code, for each image in the fisheye, the script creates a new icon widget. The i variable in the call to create the icon widget is the set of properties that is passed from the widget's tag.  (Recall the items array in the ajax tag.)

Inside the onclick function, the script calls the publish method, passing the topic, which is "/fisheye", and the icon widget corresponding to the icon that was clicked.  The icon, which includes all the properties passed from the tag is what is published.

At this point, an application can subscribe to the topic. The next section describes how to do this.

Subscribing to a Topic

To subscribe to a topic, an application needs to do two things: add a listener to listen for the widget event and subscribe to the topic by invoking the subscribe method supplied by jMaki.

The application using the fisheye widget needs to do the following:

To do this, we modified the fisheye.jsp page in the dojo-test application included in jMaki, as shown in the following code.  What the application does now is it displays images of some of Sun's engineers. When the user clicks on an image, the bio matching the image displays on the same page. 

    <a:widget type="dojo" name="dojo.fisheye"
args="{items:[
{iconSrc:'images/JayashriVisvanathan.jpg',caption:'Jayashri', index:1},
{iconSrc:'images/chinnici.jpg',caption:'Roberto',index:2},
{iconSrc:'images/blog_murray.jpg',caption:'Greg',index:3}
]}"/>


<script>
function fisheyeListener(item) {
var targetDiv = document.getElementById("newpage");
var responseText = "";
var index = Number(item.index);
switch(index){
case 1: // Set responseText equal to Jayashri's bio
break;
case 2: // Set responseText equal to Roberto's bio
break;
case 3: // Set responseText equal to Greg's bio
break;
default: responseText += 'Click on one of the photos above';
break;
}
targetDiv.innerHTML = responseText;
}
jmaki.subscribe("/fisheye", fisheyeListener);
</script>

<p>

<h3><div id="newpage"></div></h3>

Notice that there is a function that subscribes to the "/fisheye" topic. This function passes the reference to the topic into the JavaScript function, fisheyeListener, which is called if a message is published to the topic.

Let's go through what happens when this application runs. First, the fisheye widget renders itself. When the user clicks an icon in the fisheye widget, all the properties for that clicked icon are published to the topic. The JSP page then checks the icon's index property to see which icon was clicked and then replaces the div tag with the appropriate bio:






Next Steps

To see the new fisheye application in action, you need to check out a new jMaki workspace or update your current workspace and then build it. Alternatively, you can browse the code.

To see an example of two jMaki widgets interacting using the publish and subscribe mechanism, download the latest jMaki application and take a look at the Yahoo Map with Geocoder example. With this example, you can enter a location into the GeoCoder widget and a tooltip that points to the location is added on top of the map widget.  In this case, the GeoCoder publishes the coordinates that the user enters into the GeoCoder widget.  An application using the GeoCoder and Map together provides a listener that takes the coordinates, creates a tooltip, and overlays the tooltip on the map in the location specified by the coordinates.

One of the great things about the publish and subscribe mechanism is that once you publish a topic for a widget, you can subscribe to the topic from any application and respond to a widget event however you like. You don't need to hardcode specific behavior into the widget.