Token Ids are one of the better productive parts in the Ext.Net’s (a.k.a Coolite’s) server-side framework. As we know, ASP.NET translates server-side control Ids to client-side Ids that would be almost always different from their server-ids, especially if your controls are inside a Template Control, or an INamingContainer.

Ext.Net provides convenient Tokens for server control Ids (of the form #{ControlId}), that you can use inside the Handler/Fn for Listeners, and at some other places (e.g. Html/Text for labels, buttons etc), and the Ext.Net framework translates them to the control’s corresponding client-side id generated by ASP.NET.

However, I recently noticed one interesting aspect of this Id translation. You know, 2 controls inside the same TemplateControl (Page and WebUserControl etc.) cannot have same ID, but IDs can be same across 2 controls in different TemplateControls, and ASP.NET generates unique client-side Ids for them. In addition, controls inside a TemplateControl can only access other controls inside the same TemplateControl directly by using the ID property.

And I thought the same would hold for Ext.Net. That is, when you use #{ControlId} tokens, it always refers to the control with the specified Id from the same Template control.

However, while working recently, I observed one exception to this. Suppose a Page registers & uses 2 UserControls UC1 & UC2 on it. Further, both UC1 & UC2 have a control with Id “Control1”, but only UC1 has a control with Id “Control2”.

In the above scenario, using #{Control1} from UC1 would refer to the control inside UC1, and ditto for UC2. No surprises here. Similarly, using #{Control2} from UC1 would again refer to the local control in UC1.

But if you use #{Control2} from UC2 (which remember does not have any control with this server Id), Ext.Net makes it reference to the control with that Id from UC1.

Confused, well let me put this in words. When using Token Id inside a Template Control, Ext.Net first tries to reference it from the local Template Control itself. However, if this fails (meaning there is no control with the specified Id in the same Template Control), Ext.Net tries to bind it to a control from another Template Control registered on the same page (or from the Page itself), with the same Id as that inside the Token.

Cool, you have to agree… But simultaneously undocumented and I am not sure whether this is an intentional feature, or a unknown side-effect.

The attached code demonstrates what I am trying to say in this blog post.

UPDATE:

  • (Apr 12, 2010) – The same concept applies to cross-referenced Control Ids. e.g. In data controls like GridPanel, Combobox etc., you specify the source Store for data using StoreID. Ext.Net searches for a store with the specified ID first in the same Template control, and if it does not find one, continues with the search in the Parent or sibling Template controls.
  • As specified by vlad below, you can use the IDMode property to control how server Ids are translated into client Ids. The better part of it is that the Tokens automatically adjust to the specified IDMode for the control. Thus, if Control1 has IDMode as Static, #{Control1} translates to “Control1”, but if IDMode for the Control1 is Legacy, it would translate into “ctlxx_Control1” or something like that depending upon the INamingContainer hierarchy the control is in.