Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.
Comment: Mentioned ajaxResponseRenderer and added links to JumpStart, rearranged a bit

...

Tapestry provides easy-to-use support for Ajax, the technique of using JavaScript to dynamically updating parts of a web page with content from the server without redrawing the whole page. But with With Tapestry, you don't have can do simple Ajax updates without having to write any JavaScript code at all.

Ajax support is included in many built-in components and component mixins via the zone parameter.

Zones

Zones are Tapestry's approach to performing partial page updates. A Zone component renders as an HTML element, typically a <div>, with the "t-zone" CSS class. (It also adds some JavaScript to the page to "wire up" a Tapestry.ZoneManager object to control updating that element.)

A Zone can be updated via an EventLink, ActionLink or Select component, or by a Form. All of these components support a zone parameter, which provides the id of the Zone's <div>. Clicking such a link will invoke an event handler method on the server as normal ... except that the return value of the event handler method is used to send a partial page response to the client, and the content of that response is used to update the Zone's <div> in place.

An Update div within a Zone div

Deprecated

This feature is removed starting with Tapestry 5.4

In many situations, a Zone is a kind of "wrapper" or "container" for dynamic content; one that provides a look and feel ... a bit of wrapping markup to create a border. In that situation, the Zone <div> may contain an update <div>.

An Update <div> is specifically a <div> element marked with the CSS class "t-zone-update", inside the Zone's <div>.

If an Update div exists within a Zone div, then when Tapestry updates a zone only the update <div>'s content will be changed, rather than the entire Zone <div>.

The show and update functions (see Zone Functions, below) apply to the Zone <div>, not just the update <div>.

Event Handler Return Types

Code Block
xml
xml

<t:actionlink t:id="someLink" zone="myzone">update</t:actionlink>
...
<t:zone t:id="myZone" id="myzone">
    The current time is ${currentTime}
</t:zone>

Event Handler Return Types

Wiki Markup
{float:right|background=#eee|padding=0 1em}
    *JumpStart Demo:*
    [AJAX ActionLink|http://jumpstart.doublenegative.com.au/jumpstart/examples/ajax/actionlink]
{float}

In a traditional request, the return value of an event handler method is used to determine which page will render a complete response, and a redirect is sent to the client to render the new page (as a new request).

In contrast, with a Zone update, the return value is used to render a partial response within the same request.

This return value is typically often just the zone's own body (as below), but it can also be an injected component or block. The value will be rendered, and that markup will be used on the client side to update the Zone's <div>.

Code Block
java
java

@Inject
private Request request;

@InjectComponent
private Zone myZone;
...
Object onClickFromSomeLink()
{
   return myZone.getBody(); // AJAX request, return zone's own body
} 

Alternatively, an event handler may return a Link and the client will be redirected to that link. Similarly, returning a page name (as a String), or a page class, or a page instance will send a redirect to the indicated page.

Graceful Degradation

Users who do not have JavaScript enabled may click EventLinks (or ActionLinks, or Forms) that are configured to update a Zone. When that occurs, the request will still be sent to the server, but Tapestry will handle it as a traditional request.

To support graceful degradation, you should detect that case in your event handler method and return a traditional response: a page, page name or page class. This is accomplished by injecting the Request object, and invoking the isXHR() method. This value will be true for Ajax requests, and false for traditional request.

Code Block
java
java

@Inject
private Request request;

@InjectComponent
private Zone myZone;
...
Object onClickFromSomeLink()
{
    // return either the zone body (ajax) or whole page (non-ajax)
    return request.isXHR() ? myZone.getBody() : null;
} 

Multiple Zone Updates

Wiki Markup
{float:right|background=#eee|padding=0 1em}
    *JumpStart Demo:*
    [AJAX Multiple Zone Update|http://jumpstart.doublenegative.com.au/jumpstart/examples/ajax/multiplezoneupdate]
{float}

An event handler may cause often needs to update multiple zones to be updated on the client side. To accomplish this, use an AjaxResponseRenderer (or, for Tapestry 5.2 and earlier, return a MultiZoneUpdate object configured with ), indicating the zones to update. You must know the client-side id for each zone to update (the best way for this is to lock down the zone's id using the id parameter of the Zone component).

The renderer for each zone can be a block or component, or a Renderable or RenderCommand ... or an object, such as String, that can be coerced to either of these. Typically, you will inject a Block or Component and return that:

Section
Column
Code Block
java
java
titleFor Tapestry 5.3 and later

@InjectComponent
private Zone userInput;

@InjectComponent
private Zone helpPanel;

@Inject
private AjaxResponseRenderer ajaxResponseRenderer;

void onActionFromRegister()
{
    ajaxResponseRenderer.addRender("userInput", userInput)
                .addRender("helpPanel", helpPanel);
}
Column
Code Block
java
java
titleFor Tapestry 5.1, 5.2 and 5.3

@Inject
private Form registrationForm;

@Inject Block registrationHelp;

Object onActionFromRegister()
{
    return new MultiZoneUpdate("userInput", registrationForm)
                .add("helpPanel", registrationHelp);
}

    Note that MultiZoneUpdate is deprecated starting with Tapestry 5.3.

These examples assume This implies that there are two zones, "userInput" and "helpPanel", somewhere in the rendered page, waiting to receive the updated content.

Graceful Degradation

Users who do not have JavaScript enabled may click EventLinks (or ActionLinks, or Forms) that are configured to update a Zone. When that occurs, the request will still be sent to the server, but Tapestry will handle it as a traditional request.

To support graceful degradation, you should detect that case in your event handler method and return a traditional response: a page, page name or page class. This is accomplished by injecting the Request object, and invoking the isXHR() method. This value will be true for Ajax requests, and false for traditional request.

...

An Update div within a Zone div

Deprecated

This feature is removed starting with Tapestry 5.4

In many situations, a Zone is a kind of "wrapper" or "container" for dynamic content; one that provides a look and feel ... a bit of wrapping markup to create a border. In that situation, the Zone <div> may contain an update <div>.

An Update <div> is specifically a <div> element marked with the CSS class "t-zone-update", inside the Zone's <div>.

If an Update div exists within a Zone div, then when Tapestry updates a zone only the update <div>'s content will be changed, rather than the entire Zone <div>.

The show and update functions (see Zone Functions, below) apply to the Zone <div>, not just the update <div>.

Zone Effect Functions

A Zone may be initially visible or invisible. When a Zone is updated, it is made visible if not currently so. This is accomplished via a function on the Tapestry.ElementEffect client-side object. By default, the show() function is used for this purpose. If you want Tapestry to call a different Tapestry.ElementEffect function when updates occur, specify its name with the zone's show parameter.

...

Code Block
JavaScript
JavaScript
Tapestry.ElementEffect.myeffectname = function(element){ YourJavascriptCodeGoesHere; };

Zone Component Id vs. Zone Element Id

Like all Tapestry components, Zones have a component id, specified using the t:id attribute. If you do not assign a component id, a unique id is assigned by Tapestry.

...

The show and update function names are converted to lower case; all the methods of Tapestry.ElementEffect should have all lower-case names. Because client-side JavaScript is so fluid (new methods may be added to existing objects), Tapestry makes no attempt to validate the function names ... however, if the names are not valid, then the default show and highlight methods will be used.

...

More Information

For examples of extending a Form with a Zone and updating multiple zones at once, see the Ajax Components FAQ.

Anchor
autocomplete
autocomplete

Autocomplete Mixin

Wiki Markup
{float:right|background=#eee|padding=0 1em}
    *JumpStart Demo:*
    [Autocomplete Mixin|http://jumpstart.doublenegative.com.au/jumpstart/examples/ajax/autocompletemixin]
{float}

The Autocomplete mixin exists to allow a text field to query the server for completions for a partially entered phrase. It is often used in situations where the field exists to select a single value from a large set, too large to successfully download to the client as a drop down list; for example, when the number of values to select from is numbered in the thousands.

...