--- a/devtools/client/shared/widgets/ColorWidget.js
+++ b/devtools/client/shared/widgets/ColorWidget.js
@@ -256,16 +256,132 @@ ColorWidget.prototype = {
return [Math.round(rgb[0]), Math.round(rgb[1]), Math.round(rgb[2]), rgb[3]];
},
get rgbCssString() {
const rgb = this.rgb;
return "rgba(" + rgb[0] + ", " + rgb[1] + ", " + rgb[2] + ", " + rgb[3] + ")";
},
+ buildContrastHelpButton(doc) {
+ this.contrastHelp = doc.createElementNS(XHTML_NS, "button");
+ this.contrastHelp.className = "colorwidget-contrast-help";
+ this.contrastHelp.classList.add("devtools-button");
+
+ const contrastInner = this.element.querySelector(".colorwidget-contrast-inner");
+ contrastInner.appendChild(this.contrastHelp);
+ },
+
+ buildColorSelect(doc) {
+ // Create markup for color widget's select component
+ this.colorWidgetValue = this.element.querySelector(".colorwidget-value");
+ this.colorSelect = doc.createElementNS(XHTML_NS, "select");
+ this.colorSelect.id = "colorwidget-select";
+ const colorWidgetHex = this.element.querySelector(".colorwidget-hex");
+ this.colorWidgetValue.insertBefore(this.colorSelect, colorWidgetHex);
+
+ // Create hex option
+ this.hexOption = doc.createElementNS(XHTML_NS, "option");
+ this.hexOption.value = "hex";
+ this.hexOption.appendChild(doc.createTextNode("Hex"));
+
+ // Create RGBA option
+ this.rgbaOption = doc.createElementNS(XHTML_NS, "option");
+ this.rgbaOption.value = "rgba";
+ this.rgbaOption.appendChild(doc.createTextNode("RGBA"));
+
+ // Create HSLA option
+ this.hslaOption = doc.createElementNS(XHTML_NS, "option");
+ this.hslaOption.value = "hsla";
+ this.hslaOption.appendChild(doc.createTextNode("HSLA"));
+
+ // Append options to the colorSelect element.
+ this.colorSelect.appendChild(this.hexOption);
+ this.colorSelect.appendChild(this.rgbaOption);
+ this.colorSelect.appendChild(this.hslaOption);
+
+ this.colorSelect.addEventListener("change", this.onSelectValueChange);
+ },
+
+ buildHexInput(doc) {
+ // Create markup for color widget's hex input component
+ this.hexValue = this.element.querySelector(".colorwidget-hex");
+ this.hexValueInput = doc.createElementNS(XHTML_NS, "input");
+ this.hexValueInput.className = "colorwidget-hex-input";
+ this.hexValue.appendChild(this.hexValueInput);
+
+ this.hexValueInput.addEventListener("input", this.onHexInputChange);
+ },
+
+ buildRGBAInput(doc) {
+ // Create markup for color widget's rgba's inputs
+ this.rgbaValue = this.element.querySelector(".colorwidget-rgba");
+ this.rgbaR = doc.createElementNS(XHTML_NS, "input");
+ this.rgbaR.className = "colorwidget-rgba-r";
+ this.rgbaR["data-id"] = "r";
+
+ this.rgbaG = doc.createElementNS(XHTML_NS, "input");
+ this.rgbaG.className = "colorwidget-rgba-g";
+ this.rgbaG["data-id"] = "g";
+
+ this.rgbaB = doc.createElementNS(XHTML_NS, "input");
+ this.rgbaB.className = "colorwidget-rgba-b";
+ this.rgbaB["data-id"] = "b";
+
+ this.rgbaA = doc.createElementNS(XHTML_NS, "input");
+ this.rgbaA.className = "colorwidget-rgba-a";
+ this.rgbaA["data-id"] = "a";
+
+ this.rgbaValue.appendChild(this.rgbaR);
+ this.rgbaValue.appendChild(this.rgbaG);
+ this.rgbaValue.appendChild(this.rgbaB);
+ this.rgbaValue.appendChild(this.rgbaA);
+
+ this.rgbaValueInputs = {
+ r: this.rgbaR,
+ g: this.rgbaG,
+ b: this.rgbaB,
+ a: this.rgbaA,
+ };
+ this.rgbaValue.addEventListener("input", this.onRgbaInputChange);
+ },
+
+ buildHSLAInput(doc) {
+ // Create markup for color widget's hsla's inputs
+ this.hslaValue = this.element.querySelector(".colorwidget-hsla");
+ this.hslaH = doc.createElementNS(XHTML_NS, "input");
+ this.hslaH.className = "colorwidget-hsla-h";
+ this.hslaH["data-id"] = "h";
+
+ this.hslaS = doc.createElementNS(XHTML_NS, "input");
+ this.hslaS.className = "colorwidget-hsla-s";
+ this.hslaS["data-id"] = "s";
+
+ this.hslaL = doc.createElementNS(XHTML_NS, "input");
+ this.hslaL.className = "colorwidget-hsla-l";
+ this.hslaL["data-id"] = "l";
+
+ this.hslaA = doc.createElementNS(XHTML_NS, "input");
+ this.hslaA.className = "colorwidget-hsla-a";
+ this.hslaA["data-id"] = "a";
+
+ this.hslaValue.appendChild(this.hslaH);
+ this.hslaValue.appendChild(this.hslaS);
+ this.hslaValue.appendChild(this.hslaL);
+ this.hslaValue.appendChild(this.hslaA);
+
+ this.hslaValueInputs = {
+ h: this.hslaH,
+ s: this.hslaS,
+ l: this.hslaL,
+ a: this.hslaA,
+ };
+ this.hslaValue.addEventListener("input", this.onHslaInputChange);
+ },
+
initializeColorWidget: function() {
const colorNameLabel = L10N.getStr("inspector.colorwidget.colorNameLabel");
this.parentEl.innerHTML = "";
this.element = this.parentEl.ownerDocument.createElementNS(XHTML_NS, "div");
this.element.className = "colorwidget-container";
// eslint-disable-next-line no-unsanitized/property
this.element.innerHTML = `
@@ -285,21 +401,16 @@ ColorWidget.prototype = {
</div>
</div>
<div class="colorwidget-alpha colorwidget-checker colorwidget-box">
<div class="colorwidget-alpha-inner">
<div class="colorwidget-alpha-handle colorwidget-slider-control"></div>
</div>
</div>
<div class="colorwidget-value">
- <select class="colorwidget-select">
- <option value="hex">Hex</option>
- <option value="rgba">RGBA</option>
- <option value="hsla">HSLA</option>
- </select>
<div class="colorwidget-hex">
<input class="colorwidget-hex-input"/>
</div>
<div class="colorwidget-rgba colorwidget-hidden">
<input class="colorwidget-rgba-r" data-id="r" />
<input class="colorwidget-rgba-g" data-id="g" />
<input class="colorwidget-rgba-b" data-id="b" />
<input class="colorwidget-rgba-a" data-id="a" />
@@ -316,21 +427,31 @@ ColorWidget.prototype = {
<span class="colorwidget-colorname-value"></span>
</div>
<div class="colorwidget-contrast">
<div class="colorwidget-contrast-info"></div>
<div class="colorwidget-contrast-inner">
<span class="colorwidget-colorswatch"></span>
<span class="colorwidget-contrast-ratio"></span>
<span class="colorwidget-contrast-grade"></span>
- <button class="colorwidget-contrast-help devtools-button"></button>
</div>
</div>
`;
+ const doc = this.element.ownerDocument;
+
+ // Form elements need to be appended manually after innerHTML is declared.
+ // This must be done due to security issues of having form elements available
+ // in innerHTML.
+ this.buildColorSelect(doc);
+ this.buildHexInput(doc);
+ this.buildRGBAInput(doc);
+ this.buildHSLAInput(doc);
+ this.buildContrastHelpButton(doc);
+
this.element.addEventListener("click", this.onElementClick);
this.parentEl.appendChild(this.element);
this.closestBackgroundColor = "rgba(255, 255, 255, 1)";
this.colorName = this.element.querySelector(".colorwidget-colorname-value");
@@ -356,41 +477,16 @@ ColorWidget.prototype = {
this.dragger = this.element.querySelector(".colorwidget-color");
this.dragHelper = this.element.querySelector(".colorwidget-dragger");
ColorWidget.draggable(this.dragger, this.onDraggerMove);
this.alphaSlider = this.element.querySelector(".colorwidget-alpha");
this.alphaSliderInner = this.element.querySelector(".colorwidget-alpha-inner");
this.alphaSliderHelper = this.element.querySelector(".colorwidget-alpha-handle");
ColorWidget.draggable(this.alphaSliderInner, this.onAlphaSliderMove);
-
- this.colorSelect = this.element.querySelector(".colorwidget-select");
- this.colorSelect.addEventListener("change", this.onSelectValueChange);
-
- this.hexValue = this.element.querySelector(".colorwidget-hex");
- this.hexValueInput = this.element.querySelector(".colorwidget-hex-input");
- this.hexValueInput.addEventListener("input", this.onHexInputChange);
-
- this.rgbaValue = this.element.querySelector(".colorwidget-rgba");
- this.rgbaValueInputs = {
- r: this.element.querySelector(".colorwidget-rgba-r"),
- g: this.element.querySelector(".colorwidget-rgba-g"),
- b: this.element.querySelector(".colorwidget-rgba-b"),
- a: this.element.querySelector(".colorwidget-rgba-a"),
- };
- this.rgbaValue.addEventListener("input", this.onRgbaInputChange);
-
- this.hslaValue = this.element.querySelector(".colorwidget-hsla");
- this.hslaValueInputs = {
- h: this.element.querySelector(".colorwidget-hsla-h"),
- s: this.element.querySelector(".colorwidget-hsla-s"),
- l: this.element.querySelector(".colorwidget-hsla-l"),
- a: this.element.querySelector(".colorwidget-hsla-a"),
- };
- this.hslaValue.addEventListener("input", this.onHslaInputChange);
},
async show() {
this.initializeColorWidget();
this.element.classList.add("colorwidget-show");
this.slideHeight = this.slider.offsetHeight;
this.dragWidth = this.dragger.offsetWidth;