Skip to content

Commit

Permalink
Adding select tool to select an element for a Selenese command by cli…
Browse files Browse the repository at this point in the history
…cking on it in Selenium IDE
  • Loading branch information
samitbadle committed Dec 31, 2013
1 parent b04a82d commit 57a6251
Show file tree
Hide file tree
Showing 5 changed files with 158 additions and 8 deletions.
47 changes: 47 additions & 0 deletions ide/main/src/content/debugger.js
Original file line number Diff line number Diff line change
Expand Up @@ -205,6 +205,53 @@ Debugger.prototype.showElement = function (locator) {
this.runner.showElement(locator);
};

Debugger.prototype.selectElement = function () {
this.init();
var button = document.getElementById("selectElementButton");
var help = document.getElementById("selectElementTip");
if (this.targetSelecter) {
this.targetSelecter.cleanup();
this.targetSelecter = null;
return;
}
var self = this;
var isRecording = this.editor.recordingEnabled;
if (isRecording) {
this.editor.setRecordingEnabled(false);
}
button.label = "Cancel";
help.removeAttribute("style");
this.targetSelecter = new TargetSelecter(function (element, win) {
if (element && win) {
var locatorBuilders = new LocatorBuilders(win);
var target = locatorBuilders.buildAll(element);
locatorBuilders.detach();
if (target != null && target instanceof Array) {
if (target[0]) {
self.editor.treeView.updateCurrentCommand('targetCandidates', target);
} else {
alert("LOCATOR_DETECTION_FAILED");
}
}

}
self.targetSelecter = null;
}, function () {
button.label = "Select";
help.setAttribute("style", "display: none;");
if (isRecording) {
self.editor.setRecordingEnabled(true);
}
});
};

Debugger.prototype.unload = function () {
if (this.targetSelecter) {
this.targetSelecter.cleanup();
this.targetSelecter = null;
}
};

/*
* Use to reload the Selenium Core API
* and its overrides and extensions (user-extensions file)
Expand Down
1 change: 1 addition & 0 deletions ide/main/src/content/editor.js
Original file line number Diff line number Diff line change
Expand Up @@ -501,6 +501,7 @@ Editor.prototype.log = Editor.log = new Log("Editor");
Editor.prototype.unload = function () {
this.app.saveState();

this.selDebugger.unload();
this.deregisterRecorder();
top.controllers.removeController(Editor.controller);

Expand Down
11 changes: 9 additions & 2 deletions ide/main/src/content/selenium-ide.xul
Original file line number Diff line number Diff line change
Expand Up @@ -132,12 +132,19 @@ limitations under the License.
<label control="commandTarget" value="&target.label;"/>
<hbox flex="1">
<textbox flex="1" disabled="true" id="commandTarget" oninput="window.editor.treeView.updateCurrentCommand('target', window.editor.treeView.decodeText(this.value))" autocompletesearch="selenium-ide-generic" enablehistory="true" forcecomplete="true" tabscrolling="true" type="autocomplete" showcommentcolumn="true" />
<button label="&findTarget.label;"
<button label="Select" disabled="true"
oncommand="window.editor.selDebugger.selectElement()"
id="selectElementButton" />
<button label="&findTarget.label;" disabled="true"
oncommand="window.editor.selDebugger.showElement(document.getElementById('commandTarget').value)"
id="findElementButton" />
</hbox>
</row>
<row align="center">
<row align="right" id="selectElementTip" style="display: none">
<label></label>
<description>Select an element by clicking on it in the browser or click Cancel to cancel.</description>
</row>
<row align="center">
<label control="commandValue" value="&value.label;"/>
<textbox disabled="true" id="commandValue" oninput="window.editor.treeView.updateCurrentCommand('value', window.editor.treeView.decodeText(this.value))"/>
</row>
Expand Down
80 changes: 80 additions & 0 deletions ide/main/src/content/tools.js
Original file line number Diff line number Diff line change
Expand Up @@ -316,3 +316,83 @@ function defineEnum(clazz, names) {
function $(id) {
return document.getElementById(id);
}

function TargetSelecter(callback, cleanupCallback) {
this.callback = callback;
this.cleanupCallback = cleanupCallback;
var wm = Components.classes["@mozilla.org/appshell/window-mediator;1"].getService(Components.interfaces.nsIWindowMediator);
this.win = wm.getMostRecentWindow('navigator:browser').getBrowser().contentWindow;
var doc = this.win.document;
var div = doc.createElement("div");
div.setAttribute("style", "display: none;");
doc.body.insertBefore(div, doc.body.firstChild);
this.div = div;
this.e = null;
this.r = null;
doc.addEventListener("mousemove", this, true);
doc.addEventListener("click", this, true);
}

TargetSelecter.prototype.cleanup = function () {
if (this.div) {
if (this.div.parentNode) {
this.div.parentNode.removeChild(this.div);
}
this.div = null;
}
if (this.win) {
var doc = this.win.document;
doc.removeEventListener("mousemove", this, true);
doc.removeEventListener("click", this, true);
this.win = null;
}
if (this.cleanupCallback) {
this.cleanupCallback();
}
};

TargetSelecter.prototype.handleEvent = function (evt) {
switch (evt.type) {
case "mousemove":
this.highlight(evt.target.ownerDocument, evt.clientX, evt.clientY);
break;
case "click":
if (evt.button == 0 && this.e && this.callback) {
this.callback(this.e, this.win);
} //Right click would cancel the select
evt.preventDefault();
evt.stopPropagation();
this.cleanup();
break;
}
};

TargetSelecter.prototype.highlight = function (doc, x, y) {
if (doc) {
var e = doc.elementFromPoint(x, y);
if (e && e != this.e) {
this.highlightElement(e);
}
}
}

TargetSelecter.prototype.highlightElement = function (element) {
if (element && element != this.e) {
this.e = element;
} else {
return;
}
var r = element.getBoundingClientRect();
var or = this.r;
if (r.left >= 0 && r.top >= 0 && r.width > 0 && r.height > 0) {
if (or && r.top == or.top && r.left == or.left && r.width == or.width && r.height == or.height) {
return;
}
this.r = r;
var style = "pointer-events: none; position: absolute; box-shadow: 0 0 0 1px black; outline: 1px dashed white; outline-offset: -1px; background-color: rgba(250,250,128,0.4); z-index: 100;";
var pos = "top:" + (r.top + this.win.scrollY) + "px; left:" + (r.left + this.win.scrollX) + "px; width:" + r.width + "px; height:" + r.height + "px;";
this.div.setAttribute("style", style + pos);
} else if (or) {
this.div.setAttribute("style", "display: none;");
}
};
27 changes: 21 additions & 6 deletions ide/main/src/content/treeView.js
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,12 @@ objectExtend(TreeView.prototype, {
this.document.getElementById(id).disabled = disabled;
},

updateTarget: function(value, disabled) {
this.setTextBox("commandTarget", value, disabled);
this.document.getElementById('selectElementButton').disabled = disabled;
this.document.getElementById('findElementButton').disabled = disabled;
},

getCommand: function(row) {
if (row < this.testCase.commands.length) {
return this.testCase.commands[row];
Expand Down Expand Up @@ -225,11 +231,11 @@ objectExtend(TreeView.prototype, {
Editor.GENERIC_AUTOCOMPLETE.setCandidatesWithComments(XulUtils.toXPCOMString(this.editor.getAutoCompleteSearchParam("commandTarget")),
XulUtils.toXPCOMArray(locators),
XulUtils.toXPCOMArray(types));
this.setTextBox("commandTarget", this.encodeText(command.target), false);
this.updateTarget(this.encodeText(command.target), false);
} else {
targetBox.setAttribute("enablehistory", "false");
targetBox.disableAutoComplete = true;
this.setTextBox("commandTarget", this.encodeText(command.target), false);
this.updateTarget(this.encodeText(command.target), false);
}
},

Expand Down Expand Up @@ -325,7 +331,7 @@ objectExtend(TreeView.prototype, {
this.setTextBox("commandValue", this.encodeText(command.value), false);
} else if (command.type == 'comment') {
this.setTextBox("commandAction", command.comment, false);
this.setTextBox("commandTarget", '', true);
this.updateTarget('', true);
this.setTextBox("commandValue", '', true);
}

Expand All @@ -335,7 +341,7 @@ objectExtend(TreeView.prototype, {
this.editor.showRollupReference(command);
} else {
this.setTextBox("commandAction", '', true);
this.setTextBox("commandTarget", '', true);
this.updateTarget('', true);
this.setTextBox("commandValue", '', true);
this.currentCommand = null;
}
Expand All @@ -355,6 +361,13 @@ objectExtend(TreeView.prototype, {
this.updateSeleniumTargets();
this.editor.showReference(this.currentCommand);
}
else if (key == 'targetCandidates') {
this.updateSeleniumTargets();
if (value != null && value instanceof Array && value[0]) {
this.updateCurrentCommand('target', value[0][0]);
this.selectCommand();
}
}
else if (key == 'target') {
this.updateSeleniumValues();
this.editor.showUIReference(value);
Expand All @@ -367,7 +380,7 @@ objectExtend(TreeView.prototype, {
},
onHide: function() {
this.setTextBox("commandAction", '', true);
this.setTextBox("commandTarget", '', true);
this.updateTarget('', true);
this.setTextBox("commandValue", '', true);
this.currentCommand = null;
},
Expand Down Expand Up @@ -672,7 +685,9 @@ TreeView.UpdateCommandAction.prototype = {
this.treeView.treebox.rowCountChanged(this.treeView.rowCount - 1, -1);
this.treeView.rowCount--;
this.treeView.log.debug("removed new command");
}
} else if (this.index == this.treeView.tree.currentIndex) {
this.treeView.selectCommand();
}
}
}

Expand Down

0 comments on commit 57a6251

Please sign in to comment.