Bug 1168246 - part3: ES lint fixes for inplace-editor and autocomplete-popup;r=pbrosset

MozReview-Commit-ID: GbEGN3aNhxz

--HG--
extra : rebase_source : f358ef6b795fe61eebdaee10095e1ec90411ac0c
This commit is contained in:
Julian Descottes 2016-03-29 16:01:48 +02:00
Родитель a360bcdbef
Коммит f795754b01
2 изменённых файлов: 112 добавлений и 136 удалений

Просмотреть файл

@ -5,19 +5,18 @@
"use strict";
const {Cc, Ci, Cu} = require("chrome");
const XUL_NS = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul";
const Services = require("Services");
const {gDevTools} = require("devtools/client/framework/devtools");
const events = require("devtools/shared/event-emitter");
const events = require("devtools/shared/event-emitter");
/**
* Autocomplete popup UI implementation.
*
* @constructor
* @param nsIDOMDocument aDocument
* @param {nsIDOMDocument} document
* The document you want the popup attached to.
* @param Object aOptions
* @param {Object} options
* An object consiting any of the following options:
* - panelId {String} The id for the popup panel.
* - listBoxId {String} The id for the richlistbox inside the panel.
@ -25,25 +24,24 @@ const events = require("devtools/shared/event-emitter");
* - theme {String} String related to the theme of the popup.
* - autoSelect {Boolean} Boolean to allow the first entry of the popup
* panel to be automatically selected when the popup shows.
* - direction {String} The direction of the text in the panel. rtl or ltr
* - direction {String} The direction of the text in the panel. rtl / ltr
* - onSelect {String} The select event handler for the richlistbox
* - onClick {String} The click event handler for the richlistbox.
* - onKeypress {String} The keypress event handler for the richlistitems.
* - onKeypress {String} The keypress event handler for richlistitems.
*/
function AutocompletePopup(aDocument, aOptions = {})
{
this._document = aDocument;
function AutocompletePopup(document, options = {}) {
this._document = document;
this.autoSelect = aOptions.autoSelect || false;
this.position = aOptions.position || "after_start";
this.direction = aOptions.direction || "ltr";
this.autoSelect = options.autoSelect || false;
this.position = options.position || "after_start";
this.direction = options.direction || "ltr";
this.onSelect = aOptions.onSelect;
this.onClick = aOptions.onClick;
this.onKeypress = aOptions.onKeypress;
this.onSelect = options.onSelect;
this.onClick = options.onClick;
this.onKeypress = options.onKeypress;
let id = aOptions.panelId || "devtools_autoCompletePopup";
let theme = aOptions.theme || "dark";
let id = options.panelId || "devtools_autoCompletePopup";
let theme = options.theme || "dark";
// If theme is auto, use the devtools.theme pref
if (theme == "auto") {
theme = Services.prefs.getCharPref("devtools.theme");
@ -62,7 +60,7 @@ function AutocompletePopup(aDocument, aOptions = {})
this._panel.setAttribute("noautofocus", "true");
this._panel.setAttribute("level", "top");
if (!aOptions.onKeypress) {
if (!options.onKeypress) {
this._panel.setAttribute("ignorekeys", "true");
}
// Stop this appearing as an alert to accessibility.
@ -71,12 +69,10 @@ function AutocompletePopup(aDocument, aOptions = {})
let mainPopupSet = this._document.getElementById("mainPopupSet");
if (mainPopupSet) {
mainPopupSet.appendChild(this._panel);
}
else {
} else {
this._document.documentElement.appendChild(this._panel);
}
}
else {
} else {
this._list = this._panel.firstChild;
}
@ -92,8 +88,8 @@ function AutocompletePopup(aDocument, aOptions = {})
this._list.setAttribute("flex", "1");
this._list.setAttribute("seltype", "single");
if (aOptions.listBoxId) {
this._list.setAttribute("id", aOptions.listBoxId);
if (options.listBoxId) {
this._list.setAttribute("id", options.listBoxId);
}
this._list.className = "devtools-autocomplete-listbox " + theme + "-theme";
@ -128,22 +124,21 @@ AutocompletePopup.prototype = {
/**
* Open the autocomplete popup panel.
*
* @param nsIDOMNode aAnchor
* @param {nsIDOMNode} anchor
* Optional node to anchor the panel to.
* @param Number aXOffset
* @param {Number} xOffset
* Horizontal offset in pixels from the left of the node to the left
* of the popup.
* @param Number aYOffset
* @param {Number} yOffset
* Vertical offset in pixels from the top of the node to the starting
* of the popup.
* @param integer index
* @param {Number} index
* The position of item to select.
*/
openPopup: function AP_openPopup(aAnchor, aXOffset = 0, aYOffset = 0, index)
{
openPopup: function(anchor, xOffset = 0, yOffset = 0, index) {
this.__maxLabelLength = -1;
this._updateSize();
this._panel.openPopup(aAnchor, this.position, aXOffset, aYOffset);
this._panel.openPopup(anchor, this.position, xOffset, yOffset);
if (this.autoSelect) {
this.selectItemAtIndex(index);
@ -158,8 +153,7 @@ AutocompletePopup.prototype = {
* @param {Number} index
* The position of the item to select.
*/
selectItemAtIndex: function AP_selectItemAtIndex(index)
{
selectItemAtIndex: function(index) {
if (typeof index != "number") {
// If no index was provided, select the item closest to the input.
let isAboveInput = this.position.includes("before");
@ -172,8 +166,7 @@ AutocompletePopup.prototype = {
/**
* Hide the autocomplete popup panel.
*/
hidePopup: function AP_hidePopup()
{
hidePopup: function() {
// Return accessibility focus to the input.
this._document.activeElement.removeAttribute("aria-activedescendant");
this._panel.hidePopup();
@ -193,8 +186,7 @@ AutocompletePopup.prototype = {
* same code. It is the responsability of the client code to perform DOM
* cleanup.
*/
destroy: function AP_destroy()
{
destroy: function() {
if (this.isOpen) {
this.hidePopup();
}
@ -225,27 +217,25 @@ AutocompletePopup.prototype = {
/**
* Get the autocomplete items array.
*
* @param Number aIndex The index of the item what is wanted.
* @param {Number} index
* The index of the item what is wanted.
*
* @return The autocomplete item at index aIndex.
* @return {Object} The autocomplete item at index index.
*/
getItemAtIndex: function AP_getItemAtIndex(aIndex)
{
return this._list.getItemAtIndex(aIndex)._autocompleteItem;
getItemAtIndex: function(index) {
return this._list.getItemAtIndex(index)._autocompleteItem;
},
/**
* Get the autocomplete items array.
*
* @return array
* The array of autocomplete items.
* @return {Array} The array of autocomplete items.
*/
getItems: function AP_getItems()
{
getItems: function() {
let items = [];
Array.forEach(this._list.childNodes, function(aItem) {
items.push(aItem._autocompleteItem);
Array.forEach(this._list.childNodes, function(item) {
items.push(item._autocompleteItem);
});
return items;
@ -254,15 +244,14 @@ AutocompletePopup.prototype = {
/**
* Set the autocomplete items list, in one go.
*
* @param array aItems
* @param {Array} items
* The list of items you want displayed in the popup list.
* @param integer index
* @param {Number} index
* The position of the item to select.
*/
setItems: function AP_setItems(aItems, index)
{
setItems: function(items, index) {
this.clearItems();
aItems.forEach(this.appendItem, this);
items.forEach(this.appendItem, this);
// Make sure that the new content is properly fitted by the XUL richlistbox.
if (this.isOpen) {
@ -296,26 +285,20 @@ AutocompletePopup.prototype = {
/**
* Update the panel size to fit the content.
*
* @private
*/
_updateSize: function AP__updateSize()
{
_updateSize: function() {
if (!this._panel) {
return;
}
this._list.style.width = (this._maxLabelLength + 3) +"ch";
this._list.style.width = (this._maxLabelLength + 3) + "ch";
this._list.ensureIndexIsVisible(this._list.selectedIndex);
},
/**
* Update accessibility appropriately when the selected item is changed.
*
* @private
*/
_updateAriaActiveDescendant: function AP__updateAriaActiveDescendant()
{
_updateAriaActiveDescendant: function() {
if (!this._list.selectedItem) {
// Return accessibility focus to the input.
this._document.activeElement.removeAttribute("aria-activedescendant");
@ -329,8 +312,7 @@ AutocompletePopup.prototype = {
/**
* Clear all the items from the autocomplete list.
*/
clearItems: function AP_clearItems()
{
clearItems: function() {
// Reset the selectedIndex to -1 before clearing the list
this.selectedIndex = -1;
@ -354,7 +336,7 @@ AutocompletePopup.prototype = {
/**
* Getter for the index of the selected item.
*
* @type number
* @type {Number}
*/
get selectedIndex() {
return this._list.selectedIndex;
@ -363,11 +345,11 @@ AutocompletePopup.prototype = {
/**
* Setter for the selected index.
*
* @param number aIndex
* @param {Number} index
* The number (index) of the item you want to select in the list.
*/
set selectedIndex(aIndex) {
this._list.selectedIndex = aIndex;
set selectedIndex(index) {
this._list.selectedIndex = index;
if (this.isOpen && this._list.ensureIndexIsVisible) {
this._list.ensureIndexIsVisible(this._list.selectedIndex);
}
@ -376,7 +358,7 @@ AutocompletePopup.prototype = {
/**
* Getter for the selected item.
* @type object
* @type Object
*/
get selectedItem() {
return this._list.selectedItem ?
@ -386,11 +368,11 @@ AutocompletePopup.prototype = {
/**
* Setter for the selected item.
*
* @param object aItem
* @param {Object} item
* The object you want selected in the list.
*/
set selectedItem(aItem) {
this._list.selectedItem = this._findListItem(aItem);
set selectedItem(item) {
this._list.selectedItem = this._findListItem(item);
if (this.isOpen) {
this._list.ensureIndexIsVisible(this._list.selectedIndex);
}
@ -400,7 +382,7 @@ AutocompletePopup.prototype = {
/**
* Append an item into the autocomplete list.
*
* @param object aItem
* @param {Object} item
* The item you want appended to the list.
* The item object can have the following properties:
* - label {String} Property which is used as the displayed value.
@ -413,8 +395,7 @@ AutocompletePopup.prototype = {
* - count {Number} [Optional] The number to represent the count of
* autocompleted label.
*/
appendItem: function AP_appendItem(aItem)
{
appendItem: function(item) {
let listItem = this._document.createElementNS(XUL_NS, "richlistitem");
// Items must have an id for accessibility.
listItem.id = this._panel.id + "_item_" + this._itemIdCounter++;
@ -422,24 +403,24 @@ AutocompletePopup.prototype = {
listItem.setAttribute("dir", this.direction);
}
let label = this._document.createElementNS(XUL_NS, "label");
label.setAttribute("value", aItem.label);
label.setAttribute("value", item.label);
label.setAttribute("class", "autocomplete-value");
if (aItem.preLabel) {
if (item.preLabel) {
let preDesc = this._document.createElementNS(XUL_NS, "label");
preDesc.setAttribute("value", aItem.preLabel);
preDesc.setAttribute("value", item.preLabel);
preDesc.setAttribute("class", "initial-value");
listItem.appendChild(preDesc);
label.setAttribute("value", aItem.label.slice(aItem.preLabel.length));
label.setAttribute("value", item.label.slice(item.preLabel.length));
}
listItem.appendChild(label);
if (aItem.count && aItem.count > 1) {
if (item.count && item.count > 1) {
let countDesc = this._document.createElementNS(XUL_NS, "label");
countDesc.setAttribute("value", aItem.count);
countDesc.setAttribute("value", item.count);
countDesc.setAttribute("flex", "1");
countDesc.setAttribute("class", "autocomplete-count");
listItem.appendChild(countDesc);
}
listItem._autocompleteItem = aItem;
listItem._autocompleteItem = item;
this._list.appendChild(listItem);
},
@ -449,18 +430,16 @@ AutocompletePopup.prototype = {
*
* @private
*
* @param object aItem
* @param {Object} item
* The object you want found in the list.
*
* @return nsIDOMNode|null
* The nsIDOMNode that belongs to the given item object. This node is
* the richlistitem element.
* @return {nsIDOMNode} The nsIDOMNode that belongs to the given item object.
* This node is the richlistitem element. Can be null.
*/
_findListItem: function AP__findListItem(aItem)
{
_findListItem: function(item) {
for (let i = 0; i < this._list.childNodes.length; i++) {
let child = this._list.childNodes[i];
if (child._autocompleteItem == aItem) {
if (child._autocompleteItem == item) {
return child;
}
}
@ -470,21 +449,20 @@ AutocompletePopup.prototype = {
/**
* Remove an item from the popup list.
*
* @param object aItem
* @param {Object} item
* The item you want removed.
*/
removeItem: function AP_removeItem(aItem)
{
let item = this._findListItem(aItem);
if (!item) {
removeItem: function(item) {
let listItem = this._findListItem(item);
if (!listItem) {
throw new Error("Item not found!");
}
this._list.removeChild(item);
this._list.removeChild(listItem);
},
/**
* Getter for the number of items in the popup.
* @type number
* @type {Number}
*/
get itemCount() {
return this._list.childNodes.length;
@ -493,9 +471,7 @@ AutocompletePopup.prototype = {
/**
* Getter for the height of each item in the list.
*
* @private
*
* @type number
* @type {Number}
*/
get _itemHeight() {
return this._list.selectedItem.clientHeight;
@ -504,15 +480,13 @@ AutocompletePopup.prototype = {
/**
* Select the next item in the list.
*
* @return object
* @return {Object}
* The newly selected item object.
*/
selectNextItem: function AP_selectNextItem()
{
selectNextItem: function() {
if (this.selectedIndex < (this.itemCount - 1)) {
this.selectedIndex++;
}
else {
} else {
this.selectedIndex = 0;
}
@ -522,15 +496,13 @@ AutocompletePopup.prototype = {
/**
* Select the previous item in the list.
*
* @return object
* @return {Object}
* The newly-selected item object.
*/
selectPreviousItem: function AP_selectPreviousItem()
{
selectPreviousItem: function() {
if (this.selectedIndex > 0) {
this.selectedIndex--;
}
else {
} else {
this.selectedIndex = this.itemCount - 1;
}
@ -541,11 +513,10 @@ AutocompletePopup.prototype = {
* Select the top-most item in the next page of items or
* the last item in the list.
*
* @return object
* @return {Object}
* The newly-selected item object.
*/
selectNextPageItem: function AP_selectNextPageItem()
{
selectNextPageItem: function() {
let itemsPerPane = Math.floor(this._list.scrollHeight / this._itemHeight);
let nextPageIndex = this.selectedIndex + itemsPerPane + 1;
this.selectedIndex = nextPageIndex > this.itemCount - 1 ?
@ -558,11 +529,10 @@ AutocompletePopup.prototype = {
* Select the bottom-most item in the previous page of items,
* or the first item in the list.
*
* @return object
* @return {Object}
* The newly-selected item object.
*/
selectPreviousPageItem: function AP_selectPreviousPageItem()
{
selectPreviousPageItem: function() {
let itemsPerPane = Math.floor(this._list.scrollHeight / this._itemHeight);
let prevPageIndex = this.selectedIndex - itemsPerPane - 1;
this.selectedIndex = prevPageIndex < 0 ? 0 : prevPageIndex;
@ -573,8 +543,7 @@ AutocompletePopup.prototype = {
/**
* Focuses the richlistbox.
*/
focus: function AP_focus()
{
focus: function() {
this._list.focus();
},
@ -583,22 +552,21 @@ AutocompletePopup.prototype = {
*
* @private
*
* @param String aEvent
* @param {String} event
* The name of the event. In this case, "pref-changed".
* @param Object aData
* @param {Object} data
* An object passed by the emitter of the event. In this case, the
* object consists of three properties:
* - pref {String} The name of the preference that was modified.
* - newValue {Object} The new value of the preference.
* - oldValue {Object} The old value of the preference.
*/
_handleThemeChange: function AP__handleThemeChange(aEvent, aData)
{
if (aData.pref == "devtools.theme") {
this._panel.classList.toggle(aData.oldValue + "-theme", false);
this._panel.classList.toggle(aData.newValue + "-theme", true);
this._list.classList.toggle(aData.oldValue + "-theme", false);
this._list.classList.toggle(aData.newValue + "-theme", true);
_handleThemeChange: function(event, data) {
if (data.pref == "devtools.theme") {
this._panel.classList.toggle(data.oldValue + "-theme", false);
this._panel.classList.toggle(data.newValue + "-theme", true);
this._list.classList.toggle(data.oldValue + "-theme", false);
this._list.classList.toggle(data.newValue + "-theme", true);
}
},
};

Просмотреть файл

@ -231,7 +231,7 @@ function InplaceEditor(options, event) {
for (let i = 0; i < advanceChars.length; i++) {
advanceCharcodes[advanceChars.charCodeAt(i)] = true;
}
this._advanceChars = aCharCode => aCharCode in advanceCharcodes;
this._advanceChars = charCode => charCode in advanceCharcodes;
}
// Hide the provided element and add our editor.
@ -306,9 +306,11 @@ InplaceEditor.prototype = {
this.input.removeEventListener("keypress", this._onKeyPress, false);
this.input.removeEventListener("keyup", this._onKeyup, false);
this.input.removeEventListener("input", this._onInput, false);
this.input.removeEventListener("dblclick", this._stopEventPropagation, false);
this.input.removeEventListener("dblclick", this._stopEventPropagation,
false);
this.input.removeEventListener("click", this._stopEventPropagation, false);
this.input.removeEventListener("mousedown", this._stopEventPropagation, false);
this.input.removeEventListener("mousedown", this._stopEventPropagation,
false);
this._stopAutosize();
@ -481,13 +483,15 @@ InplaceEditor.prototype = {
if (type === "rgb" || type === "hsl") {
info = {};
let part = value.substring(range.start, selStart).split(",").length - 1;
if (part === 3) { // alpha
if (part === 3) {
// alpha
info.minValue = 0;
info.maxValue = 1;
} else if (type === "rgb") {
info.minValue = 0;
info.maxValue = 255;
} else if (part !== 0) { // hsl percentage
} else if (part !== 0) {
// hsl percentage
info.minValue = 0;
info.maxValue = 100;
@ -552,7 +556,7 @@ InplaceEditor.prototype = {
* @return {Object} object with properties 'value', 'start', 'end', and
* 'type'.
*/
_parseCSSValue: function(value, offset) {
_parseCSSValue: function(value, offset) {
const reSplitCSS = /(url\("?[^"\)]+"?\)?)|(rgba?\([^)]*\)?)|(hsla?\([^)]*\)?)|(#[\dA-Fa-f]+)|(-?\d*\.?\d+(%|[a-z]{1,4})?)|"([^"]*)"?|'([^']*)'?|([^,\s\/!\(\)]+)|(!(.*)?)/;
let start = 0;
let m;
@ -621,8 +625,10 @@ InplaceEditor.prototype = {
// Parse periods as belonging to the number only if we are in a known
// number context. (This makes incrementing the 1 in 'image1.gif' work.)
let pattern = "[" + (info ? "0-9." : "0-9") + "]*";
let before = new RegExp(pattern + "$").exec(value.substr(0, offset))[0].length;
let after = new RegExp("^" + pattern).exec(value.substr(offset))[0].length;
let before = new RegExp(pattern + "$")
.exec(value.substr(0, offset))[0].length;
let after = new RegExp("^" + pattern)
.exec(value.substr(offset))[0].length;
start = offset - before;
end = offset + after;
@ -1204,7 +1210,8 @@ InplaceEditor.prototype = {
// Detecting if cursor is at property or value;
let match = query.match(/([:;"'=]?)\s*([^"';:=]+)?$/);
if (match && match.length >= 2) {
if (match[1] == ":") { // We are in CSS value completion
if (match[1] == ":") {
// We are in CSS value completion
let propertyName =
query.match(/[;"'=]\s*([^"';:= ]+)\s*:\s*[^"';:=]*$/)[1];
list =
@ -1220,7 +1227,8 @@ InplaceEditor.prototype = {
// Don't suggest '!important' without any manually typed character
list.splice(0, 1);
}
} else if (match[1]) { // We are in CSS property name completion
} else if (match[1]) {
// We are in CSS property name completion
list = CSSPropertyList;
startCheckQuery = match[2];
}