define(function(require, exports, module) {
main.consumes = ["Evaluator", "ui"];
main.provides = ["immediate.browserjs"];
return main;
/*
Test Cases:
1
"1"
new Error()
window
console.log("1");
throw new Error("1");
Missing:
get/set in object
__proto__
*/
function main(options, imports, register) {
var Evaluator = imports.Evaluator;
var ui = imports.ui;
var escapeHTML = require("ace/lib/lang").escapeHTML;
/***** Initialization *****/
var plugin = new Evaluator("Ajax.org", main.consumes, {
caption: "Javascript (browser)",
id: "jsbrowser",
mode: "ace/mode/javascript",
message: "Welcome to the Javascript REPL. This REPL allows you to "
+ "test any single or multi line code in\na browser based "
+ "javascript environment (iframe). It operates similar to "
+ "your browser console."
});
// var emit = plugin.getEmitter();
var iframe;
var win;
function createIframe() {
if (iframe) return;
iframe = document.body.appendChild(document.createElement("iframe"));
iframe.setAttribute("nwdisable", "nwdisable");
iframe.style.width = "1px";
iframe.style.height = "1px";
iframe.style.position = "absolute";
iframe.style.left = "-100px";
iframe.style.top = "-100px";
win = iframe.contentWindow;
}
/***** Evaluator *****/
var counter = 0;
function Console(cell) {
this.name = "output_section" + (++counter);
this.cell = cell;
this.html = document.createElement("div");
this.cell.addWidget({ el: this.html, coverLine: true, fixedWidth: true });
}
Console.prototype = {
write: function () {
var html = this.html.appendChild(document.createElement("div"));
var type = arguments[arguments.length - 1];
html.className = type;
for (var i = 0; i < arguments.length - 1; i++) {
renderType(arguments[i], html, type != "return");
}
insert(html, "
");
html.updateWidget = this.$update.bind(this);
html.updateWidget();
this.$scrollIntoView();
},
log: function(output) {
var args = Array.prototype.slice.apply(arguments);
args.push("log");
return this.write.apply(this, args);
},
error: function(output) {
var args = Array.prototype.slice.apply(arguments);
args.push("error");
return this.write.apply(this, args);
},
warn: function(output) {
var args = Array.prototype.slice.apply(arguments);
args.push("warning");
return this.write.apply(this, args);
},
$update: function() {
this.cell.session.repl.onWidgetChanged(this.cell);
},
$scrollIntoView: function() {
var editor = this.cell.session.repl.editor;
if (!editor) // tab isn't active
return;
var renderer = editor.renderer;
// TODO add a better way to scroll ace cursor into view when rendered
setTimeout(function() {
renderer.scrollCursorIntoView();
});
}
};
function insert(div, markup, name) {
if (name !== undefined)
insert(div, "" + escapeHTML(name) + ": ");
markup = markup.replace(/([a-z]\w{1,4}:\/\/[\w:_\-\?&\/\.\#]*)/gi, "$1");
div.insertAdjacentHTML("beforeend", markup);
if (div.lastChild && div.lastChild.nodeType == 1) {
var nodes = div.lastChild.querySelectorAll("a");
for (var i = 0; i < nodes.length; i++) {
nodes[i].addEventListener("click", function(e) {
//@todo
alert(this.firstChild.nodeValue);
e.stopPropagation();
});
}
}
}
function insertTree(div, caption, object, drawChildren) {
// caption can be a string or an html element
var treeitem = div.appendChild(document.createElement("span"));
var arrow = treeitem.appendChild(document.createElement("span"));
treeitem.className = "treeitem";
arrow.className = "arrow";
treeitem.appendChild(caption);
var container;
treeitem.addEventListener("click", function(e) {
if (container && ui.isChildOf(container, e.target, true))
return;
e.stopPropagation();
if (!container) {
container = treeitem.appendChild(document.createElement("div"));
container.className = "treecontainer";
container.style.display = "none";
drawChildren(object, container);
}
var collapsed = container.style.display == "none";
arrow.className = "arrow " + (collapsed ? "expanded" : "");
container.style.display = collapsed ? "block" : "none";
// hack!
var target = e.currentTarget;
while (target) {
if (target.updateWidget) {
target.updateWidget();
break;
}
target = target.parentNode;
}
});
}
function parseChildren(object, html) {
if (object instanceof win.Array) {
if (object.length < 101) {
// object.forEach(function(item, i) {
// renderType(item, html, 2, false, i);
// insert(html, "
");
// });
}
else {
}
}
else if (object.$arrayWalker) {
}
else if (object instanceof win.Error) {
var stack = object.stack.split("\n");
stack.shift();
stack = stack.join("
");
insert(html, "