Let me try… The t:id parameter defines the component id, i.e. the "name" of the component in your template, which you can use for injecting the component to your component class:
tml: > <t:zone t:id="myzone"></t:zone> class: > @InjectComponent > private Zone myzone; Mostly it's enough for you to specify just t:id. Each zone with a t:id gets a generated, unique "id" attribute. If your zone "myzone" is rendered only once the id attribute will be identical to the t:id attribute that it has been generated from. I'll illustrate the render process and what gets initialized vie JavaScript. In the first example I'll show when and why you don't need to specify the additional id attribute to t:zone. In the second example I'll show when you absolutely need to specify both. Example #1: page tml: > <t:zone t:id="myzone"></t:zone> > <t:actionLink t:id="myLink" t:zone="myzone>update zone</t:actionLink> > > <t:block id="lazyContent"><p>updated content</p></t:block> page class: > @Inject > private AjaxResponseRenderer ajax; > > @Inject > private Block lazyContent; > > void onActionFromMyLink() { > > ajax.addRenderer("myzone", lazyContent); > } 1. The page is called for the first time 2. The zone "myzone" is rendered, its id attribute will be also "myzone". 3. The actionLink is rendered and a Tapestry JavaScript init-method will be prepared with the following configuration JSON: { "inits": [ { "linkZone": { "linkId": "myLink", "zoneId": "myzone" } } ] } --> See the Tapestry source of ClientBehaviorSupportImpl.java "linkZone" method for more details. 4. The client-side JS code will look for an element with the exact id of "myzone" to trigger the zone update as soon as the link is clicked. 5. User clicks on the link, onActionFromMyLink is called and a zone refresh for the zone with the id "myzone" will be sent to the client. The id ("myzone") must still be equal to the id in the DOM. Example #2: page tml: > <t:zone t:id="wrapperZone"> > <t:zone t:id="myzone" id="myzone"></t:zone> > <t:actionLink t:id="myLink" t:zone="myzone>update inner > zone</t:actionLink> > </t:zone> > <t:actionLink t:id="wrapperUpdate" t:zone="wrapperZone >update > wrapper</t:actionLink> > <t:block id="lazyContent"><p>updated content</p></t:block> page class: > @Inject > private AjaxResponseRenderer ajax; > > @Inject > private Block lazyContent; > > @InjectComponent > private Zone wrapperZone; > > void onActionFromMyLink() { > > ajax.addRenderer("myzone", lazyContent); > > void onActionFromWrapperUpdate() { > > ajax.addRenderer("wrapperZone", wrapperZone); > } This time "myzone" is inside another zone. And as I said earlier the id attribute of a zone is only equal to the t:id attribute if the zone is only rendered once. After you click the "update wrapper" action link the inner zone "myzone" will render again and its id will not be equal to "myzone" (it's going to be something like myzone_012312abc) unless you specify the parameter yourself. This way it's also your responsibility to make sure this id is only existing once in your DOM. The 5 steps from the first example stay the same for the rendering of the wrapper zone's body. Your actionlink (or whatever component you're using, e.g jquery.slider) will always bind on the same client-side zoneId, which is "myzone", because that's what you've specified as its t:zone parameter. So there are multiple solutions to this problem: 1. You add id="myzone" to your inner zones to make sure the client side id attribute is always what you expect. 2. You make the t:zone parameter value a property that is evaluated during rendering. So instead of t:zone="myzone" (which is a literal binding) you specify t:zone="prop:currentZoneId" and add a corresponding getter in the java code: > @InjectComponent > private Zone myzone; > > public String getCurrentZoneId() { > myzone.getClientId(); > } Solution #2 brings another caveat: If the actionLink from my example would be specified in the template before the zone this wouldn't work. The zone's clientId would be "null" because the zone hasn't been rendered, yet… You could add some more advanced tricks with Heartbeats and @HeartbeatDeferred but… I guess you'll just stick with solution #1 :-) I'm sure the upcoming refactorings (an euphemism?) in tapestry.js will make it better and easier! tl;dr Use t:id AND id on zones if it's a nested zone, since the client-side id would not be predictable and watch out you have no duplicate ids in you DOM, otherwise use only t:id Cheers, Christian Am 10.08.2012 um 00:34 schrieb bhorvat: > Well like it says in the subject, why should we specify both normal id and > the t:id. I know that the latter is for the tapestry where the first one is > for the client, but why is not that set by default in tapestry if it is that > important, and I take it that it is because some of my code wont work > without. For example > > <t:form> > <t:jquery.slider t:id="percentageSlider" t:value="percentage" > t:zone="zonePercentage" > t:params="sliderParams" /> > </t:form> > <t:zone t:id="zonePercentage" id="zonePercentage" t:update="show"> > <div class="itcTxt">${percentage}%</div> > </t:zone> > > without id="zonePercentage" the event wont be triggered. > > thanks all > cheers > > > > -- > View this message in context: > http://tapestry.1045711.n5.nabble.com/Why-should-we-specify-t-id-and-id-for-the-zone-tp5715208.html > Sent from the Tapestry - User mailing list archive at Nabble.com. > > --------------------------------------------------------------------- > To unsubscribe, e-mail: users-unsubscr...@tapestry.apache.org > For additional commands, e-mail: users-h...@tapestry.apache.org > --------------------------------------------------------------------- To unsubscribe, e-mail: users-unsubscr...@tapestry.apache.org For additional commands, e-mail: users-h...@tapestry.apache.org