Bug 1448213 - Merge text-base, text-label, label-control, text-link bindings into the text binding
MozReview-Commit-ID: DiI2fPtkb3m
--- a/toolkit/content/minimal-xul.css
+++ b/toolkit/content/minimal-xul.css
@@ -45,33 +45,24 @@
/* hide the content, but don't destroy the frames */
[collapsed="true"],
[moz-collapsed="true"] {
visibility: collapse;
}
/********** label **********/
-description {
- -moz-binding: url("chrome://global/content/bindings/text.xml#text-base");
-}
-
-label {
- -moz-binding: url("chrome://global/content/bindings/text.xml#text-label");
+label, description {
+ -moz-binding: url("chrome://global/content/bindings/text.xml#text");
}
label.text-link, label[onclick] {
- -moz-binding: url("chrome://global/content/bindings/text.xml#text-link");
-moz-user-focus: normal;
}
-label[control], label.radio-label, label.checkbox-label, label.toolbarbutton-multiline-text {
- -moz-binding: url("chrome://global/content/bindings/text.xml#label-control");
-}
-
html|span.accesskey {
text-decoration: underline;
}
/********** resizer **********/
resizer {
-moz-binding: url("chrome://global/content/bindings/resizer.xml#resizer");
--- a/toolkit/content/widgets/text.xml
+++ b/toolkit/content/widgets/text.xml
@@ -4,32 +4,117 @@
- file, You can obtain one at http://mozilla.org/MPL/2.0/. -->
<bindings id="textBindings"
xmlns="http://www.mozilla.org/xbl"
xmlns:xul="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
xmlns:html="http://www.w3.org/1999/xhtml">
- <!-- bound to <description>s -->
- <binding id="text-base">
- <implementation implements="nsIDOMXULDescriptionElement">
+ <!-- bound to <label>s and <description>s -->
+ <binding id="text">
+ <content>
+ <children/><html:span anonid="accessKeyParens"></html:span>
+ </content>
+ <implementation implements="nsIDOMXULLabelElement, nsIDOMXULDescriptionElement">
+ <constructor>
+ <![CDATA[
+ if (this.tagName !== "label" && this.tagName !== "xul:label") {
+ // Features are not available to <description>s.
+ return;
+ }
+
+ if (this.hasAttribute("control") ||
+ this.classList.contains("radio-label") ||
+ this.classList.contains("checkbox-label") ||
+ this.classList.contains("toolbarbutton-multiline-text")) {
+ this.isControlLabel = true;
+ this.formatAccessKey(true);
+ } else if (this.hasAttribute("onclick") ||
+ this.classList.contains("text-link")) {
+ this.isTextLink = true;
+ }
+
+ this._setupEventListeners();
+ ]]>
+ </constructor>
+
+ <method name="_setupEventListeners">
+ <body>
+ <![CDATA[
+ if (this.isControlLabel) {
+ this.addEventListener("click", this);
+ }
+ if (this.isTextLink) {
+ this.addEventListener("click", this, true);
+ this.addEventListener("keypress", this, true);
+ }
+ ]]>
+ </body>
+ </method>
+
+ <method name="handleEvent">
+ <parameter name="aEvent"/>
+ <body>
+ <![CDATA[
+ switch (aEvent.type) {
+ case "click":
+ if (this.isControlLabel) {
+ if (this.disabled) {
+ break;
+ }
+ var controlElement = this.labeledControlElement;
+ if (controlElement) {
+ controlElement.focus();
+ }
+
+ break;
+ }
+ if (this.isTextLink) {
+ switch (aEvent.button) {
+ case 0:
+ case 1:
+ this.open(aEvent);
+ break;
+ }
+ }
+ break;
+ case "keypress":
+ if (aEvent.keyCode !== aEvent.DOM_VK_RETURN) {
+ break;
+ }
+ this.click();
+ aEvent.preventDefault();
+ break;
+ }
+ ]]>
+ </body>
+ </method>
+
+ <destructor>
+ <![CDATA[
+ this.removeEventListener("click", this);
+ this.removeEventListener("click", this, true);
+ this.removeEventListener("keypress", this, true);
+ ]]>
+ </destructor>
+
+ <!-- common implementations -->
+
<property name="disabled" onset="if (val) this.setAttribute('disabled', 'true');
else this.removeAttribute('disabled');
return val;"
onget="return this.getAttribute('disabled') == 'true';"/>
<property name="value" onget="return this.getAttribute('value');"
onset="this.setAttribute('value', val); return val;"/>
<property name="crop" onget="return this.getAttribute('crop');"
onset="this.setAttribute('crop', val); return val;"/>
- </implementation>
- </binding>
- <binding id="text-label" extends="chrome://global/content/bindings/text.xml#text-base">
- <implementation implements="nsIDOMXULLabelElement">
+ <!-- text label implementations -->
+
<property name="accessKey">
<getter>
<![CDATA[
var accessKey = this.getAttribute("accesskey");
return accessKey ? accessKey[0] : null;
]]>
</getter>
<setter>
@@ -38,35 +123,26 @@
return val;
]]>
</setter>
</property>
<property name="control" onget="return getAttribute('control');">
<setter>
<![CDATA[
- // After this gets set, the label will use the binding #label-control
+ if (this.parentNode) {
+ throw new Error("Cannot mutate the control attribute while attached.");
+ }
this.setAttribute("control", val);
return val;
]]>
</setter>
</property>
- </implementation>
- </binding>
- <binding id="label-control" extends="chrome://global/content/bindings/text.xml#text-label">
- <content>
- <children/><html:span anonid="accessKeyParens"></html:span>
- </content>
- <implementation implements="nsIDOMXULLabelElement">
- <constructor>
- <![CDATA[
- this.formatAccessKey(true);
- ]]>
- </constructor>
+ <!-- control label implementions -->
<method name="formatAccessKey">
<parameter name="firstTime"/>
<body>
<![CDATA[
var control = this.labeledControlElement;
if (!control) {
var bindingParent = document.getBindingParent(this);
@@ -271,29 +347,18 @@
}
this.setAttribute("control", val);
this.formatAccessKey(false);
return val;
]]>
</setter>
</property>
- </implementation>
+ <!-- text link implementations -->
- <handlers>
- <handler event="click" action="if (this.disabled) return;
- var controlElement = this.labeledControlElement;
- if(controlElement)
- controlElement.focus();
- "/>
- </handlers>
- </binding>
-
- <binding id="text-link" extends="chrome://global/content/bindings/text.xml#text-label">
- <implementation>
<property name="href" onget="return this.getAttribute('href');"
onset="this.setAttribute('href', val); return val;" />
<method name="open">
<parameter name="aEvent"/>
<body>
<![CDATA[
var href = this.href;
if (!href || this.disabled || aEvent.defaultPrevented)
@@ -365,18 +430,14 @@
if (window.isChromeWindow) {
while (win.opener && !win.opener.closed)
win = win.opener;
}
win.open(href);
]]>
</body>
</method>
+
</implementation>
- <handlers>
- <handler event="click" phase="capturing" button="0" action="this.open(event)"/>
- <handler event="click" phase="capturing" button="1" action="this.open(event)"/>
- <handler event="keypress" preventdefault="true" keycode="VK_RETURN" action="this.click()" />
- </handlers>
</binding>
</bindings>