diff --git a/IPython/frontend/html/notebook/static/js/cell.js b/IPython/frontend/html/notebook/static/js/cell.js new file mode 100644 index 0000000..3bf37a4 --- /dev/null +++ b/IPython/frontend/html/notebook/static/js/cell.js @@ -0,0 +1,72 @@ + +//============================================================================ +// Cell +//============================================================================ + + +var Cell = function (notebook) { + this.notebook = notebook; + this.selected = false; + this.element; + this.create_element(); + if (this.element !== undefined) { + this.element.data("cell", this); + this.bind_events(); + } + this.cell_id = uuid(); +}; + + +Cell.prototype.grow = function(element) { + // Grow the cell by hand. This is used upon reloading from JSON, when the + // autogrow handler is not called. + var dom = element.get(0); + var lines_count = 0; + // modified split rule from + // http://stackoverflow.com/questions/2035910/how-to-get-the-number-of-lines-in-a-textarea/2036424#2036424 + var lines = dom.value.split(/\r|\r\n|\n/); + lines_count = lines.length; + if (lines_count >= 1) { + dom.rows = lines_count; + } else { + dom.rows = 1; + } +}; + + +Cell.prototype.select = function () { + this.element.addClass('ui-widget-content ui-corner-all'); + this.selected = true; + // TODO: we need t test across browsers to see if both of these are needed. + // In the meantime, there should not be any harm in having them both. + this.element.find('textarea').trigger('focusin'); + this.element.find('textarea').trigger('focus'); +}; + + +Cell.prototype.unselect = function () { + this.element.removeClass('ui-widget-content ui-corner-all'); + this.selected = false; +}; + + +Cell.prototype.bind_events = function () { + var that = this; + var nb = that.notebook + that.element.click(function (event) { + if (that.selected === false) { + nb.select(nb.find_cell_index(that)); + }; + }); + that.element.focusin(function (event) { + if (that.selected === false) { + nb.select(nb.find_cell_index(that)); + }; + }); +}; + + +// Subclasses must implement create_element. +Cell.prototype.create_element = function () {}; + + diff --git a/IPython/frontend/html/notebook/static/js/codecell.js b/IPython/frontend/html/notebook/static/js/codecell.js new file mode 100644 index 0000000..aba9477 --- /dev/null +++ b/IPython/frontend/html/notebook/static/js/codecell.js @@ -0,0 +1,195 @@ + +//============================================================================ +// CodeCell +//============================================================================ + + +var CodeCell = function (notebook) { + this.code_mirror = null; + this.input_prompt_number = ' '; + Cell.apply(this, arguments); +}; + + +CodeCell.prototype = new Cell(); + + +CodeCell.prototype.create_element = function () { + var cell = $('
').addClass('cell code_cell vbox border-box-sizing'); + var input = $('
').addClass('input hbox border-box-sizing'); + input.append($('
').addClass('prompt input_prompt monospace-font')); + var input_area = $('
').addClass('input_area box-flex1 border-box-sizing'); + this.code_mirror = CodeMirror(input_area.get(0), { + indentUnit : 4, + enterMode : 'flat', + tabMode: 'shift' + }); + input.append(input_area); + var output = $('
').addClass('output vbox border-box-sizing'); + cell.append(input).append(output); + this.element = cell; + this.collapse() +}; + + +CodeCell.prototype.select = function () { + Cell.prototype.select.apply(this); + this.code_mirror.focus(); +}; + + +CodeCell.prototype.append_pyout = function (data, n) { + var toinsert = $("
").addClass("output_area output_pyout hbox monospace-font"); + toinsert.append($('
'). + addClass('prompt output_prompt'). + html('Out[' + n + ']:') + ); + this.append_display_data(data, toinsert); + toinsert.children().last().addClass("box_flex1"); + this.element.find("div.output").append(toinsert); + // If we just output latex, typeset it. + if (data["text/latex"] !== undefined) { + MathJax.Hub.Queue(["Typeset",MathJax.Hub]); + }; +}; + + +CodeCell.prototype.append_pyerr = function (ename, evalue, tb) { + var s = ''; + var len = tb.length; + for (var i=0; i").addClass("output_area output_stream monospace-font"); + toinsert.append($("
").addClass("monospace-font").html(fixConsole(data)));
+    element.append(toinsert);
+    return element;
+};
+
+
+CodeCell.prototype.append_svg = function (svg, element) {
+    element = element || this.element.find("div.output");
+    var toinsert = $("
").addClass("output_area output_svg"); + toinsert.append(svg); + element.append(toinsert); + return element; +}; + + +CodeCell.prototype.append_png = function (png, element) { + element = element || this.element.find("div.output"); + var toinsert = $("
").addClass("output_area output_png"); + toinsert.append($("").attr('src','data:image/png;base64,'+png)); + element.append(toinsert); + return element; +}; + + +CodeCell.prototype.append_latex = function (latex, element) { + // This method cannot do the typesetting because the latex first has to + // be on the page. + element = element || this.element.find("div.output"); + var toinsert = $("
").addClass("output_area output_latex monospace-font"); + toinsert.append(latex); + element.append(toinsert); + return element; +} + + +CodeCell.prototype.clear_output = function () { + this.element.find("div.output").html(""); +}; + + +CodeCell.prototype.collapse = function () { + this.element.find('div.output').hide(); +}; + + +CodeCell.prototype.expand = function () { + this.element.find('div.output').show(); +}; + + +CodeCell.prototype.set_input_prompt = function (number) { + var n = number || ' '; + this.input_prompt_number = n + this.element.find('div.input_prompt').html('In [' + n + ']:'); +}; + + +CodeCell.prototype.get_code = function () { + return this.code_mirror.getValue(); +}; + + +CodeCell.prototype.set_code = function (code) { + return this.code_mirror.setValue(code); +}; + + +CodeCell.prototype.at_top = function () { + var cursor = this.code_mirror.getCursor(); + if (cursor.line === 0) { + return true; + } else { + return false; + } +}; + + +CodeCell.prototype.at_bottom = function () { + var cursor = this.code_mirror.getCursor(); + if (cursor.line === (this.code_mirror.lineCount()-1)) { + return true; + } else { + return false; + } +}; + + +CodeCell.prototype.fromJSON = function (data) { + if (data.cell_type === 'code') { + this.set_code(data.code); + this.set_input_prompt(data.prompt_number); + }; +}; + + +CodeCell.prototype.toJSON = function () { + return { + code : this.get_code(), + cell_type : 'code', + prompt_number : this.input_prompt_number + }; +}; + + diff --git a/IPython/frontend/html/notebook/static/js/kernel.js b/IPython/frontend/html/notebook/static/js/kernel.js new file mode 100644 index 0000000..0692045 --- /dev/null +++ b/IPython/frontend/html/notebook/static/js/kernel.js @@ -0,0 +1,107 @@ + +//============================================================================ +// Kernel +//============================================================================ + + +var Kernel = function () { + this.kernel_id = null; + this.base_url = "/kernels"; + this.kernel_url = null; +}; + + +Kernel.prototype.get_msg = function (msg_type, content) { + var msg = { + header : { + msg_id : uuid(), + username : "bgranger", + session: this.session_id, + msg_type : msg_type + }, + content : content, + parent_header : {} + }; + return msg; +} + +Kernel.prototype.start_kernel = function (callback, context) { + var that = this; + $.post(this.base_url, + function (kernel_id) { + that._handle_start_kernel(kernel_id, callback, context); + }, + 'json' + ); +}; + + +Kernel.prototype._handle_start_kernel = function (kernel_id, callback, context) { + this.kernel_id = kernel_id; + this.kernel_url = this.base_url + "/" + this.kernel_id; + this._start_channels(); + callback.call(context); +}; + + +Kernel.prototype._start_channels = function () { + var ws_url = "ws://127.0.0.1:8888" + this.kernel_url; + this.shell_channel = new WebSocket(ws_url + "/shell"); + this.iopub_channel = new WebSocket(ws_url + "/iopub"); +} + + +Kernel.prototype.execute = function (code) { + var content = { + code : code, + silent : false, + user_variables : [], + user_expressions : {} + }; + var msg = this.get_msg("execute_request", content); + this.shell_channel.send(JSON.stringify(msg)); + return msg.header.msg_id; +} + + +Kernel.prototype.interrupt = function () { + $.post(this.kernel_url + "/interrupt"); +}; + + +Kernel.prototype.restart = function () { + this.status_restarting(); + url = this.kernel_url + "/restart" + var that = this; + $.post(url, function (kernel_id) { + console.log("Kernel restarted: " + kernel_id); + that.kernel_id = kernel_id; + that.kernel_url = that.base_url + "/" + that.kernel_id; + that.status_idle(); + }, 'json'); +}; + + +Kernel.prototype.status_busy = function () { + $("#kernel_status").removeClass("status_idle"); + $("#kernel_status").removeClass("status_restarting"); + $("#kernel_status").addClass("status_busy"); + $("#kernel_status").text("Busy"); +}; + + +Kernel.prototype.status_idle = function () { + $("#kernel_status").removeClass("status_busy"); + $("#kernel_status").removeClass("status_restarting"); + $("#kernel_status").addClass("status_idle"); + $("#kernel_status").text("Idle"); +}; + +Kernel.prototype.status_restarting = function () { + $("#kernel_status").removeClass("status_busy"); + $("#kernel_status").removeClass("status_idle"); + $("#kernel_status").addClass("status_restarting"); + $("#kernel_status").text("Restarting"); +}; + + diff --git a/IPython/frontend/html/notebook/static/js/namespace.js b/IPython/frontend/html/notebook/static/js/namespace.js new file mode 100644 index 0000000..d28851e --- /dev/null +++ b/IPython/frontend/html/notebook/static/js/namespace.js @@ -0,0 +1,4 @@ +var IPYTHON = {}; + + + diff --git a/IPython/frontend/html/notebook/static/js/notebook.js b/IPython/frontend/html/notebook/static/js/notebook.js index b93f117..53d92b1 100644 --- a/IPython/frontend/html/notebook/static/js/notebook.js +++ b/IPython/frontend/html/notebook/static/js/notebook.js @@ -1,67 +1,3 @@ -var IPYTHON = {}; - - -//============================================================================ -// Utilities -//============================================================================ - - -var uuid = function () { - // http://www.ietf.org/rfc/rfc4122.txt - var s = []; - var hexDigits = "0123456789ABCDEF"; - for (var i = 0; i < 32; i++) { - s[i] = hexDigits.substr(Math.floor(Math.random() * 0x10), 1); - } - s[12] = "4"; // bits 12-15 of the time_hi_and_version field to 0010 - s[16] = hexDigits.substr((s[16] & 0x3) | 0x8, 1); // bits 6-7 of the clock_seq_hi_and_reserved to 01 - - var uuid = s.join(""); - return uuid; -}; - - -//Fix raw text to parse correctly in crazy XML -function xmlencode(string) { - return string.replace(/\&/g,'&'+'amp;') - .replace(//g,'&'+'gt;') - .replace(/\'/g,'&'+'apos;') - .replace(/\"/g,'&'+'quot;') - .replace(/`/g,'&'+'#96;') -} - -//Map from terminal commands to CSS classes -attrib = { - "30":"cblack", "31":"cred", - "32":"cgreen", "33":"cyellow", - "34":"cblue", "36":"ccyan", - "37":"cwhite", "01":"cbold"} - -//Fixes escaped console commands, IE colors. Turns them into HTML -function fixConsole(txt) { - txt = xmlencode(txt) - var re = /\033\[([\d;]*?)m/ - var opened = false - var cmds = [] - var opener = "" - var closer = "" - - while (re.test(txt)) { - var cmds = txt.match(re)[1].split(";") - closer = opened?"":"" - opened = cmds.length > 1 || cmds[0] != 0 - var rep = [] - for (var i in cmds) - if (typeof(attrib[cmds[i]]) != "undefined") - rep.push(attrib[cmds[i]]) - opener = rep.length > 0?"":"" - txt = txt.replace(re, closer + opener) - } - if (opened) txt += "" - return txt.trim() -} - //============================================================================ // Notebook @@ -570,576 +506,3 @@ Notebook.prototype.load_notebook = function (filename) { $.ajax("/notebooks/" + filename, settings); } - -//============================================================================ -// Cell -//============================================================================ - - -var Cell = function (notebook) { - this.notebook = notebook; - this.selected = false; - this.element; - this.create_element(); - if (this.element !== undefined) { - this.element.data("cell", this); - this.bind_events(); - } - this.cell_id = uuid(); -}; - - -Cell.prototype.grow = function(element) { - // Grow the cell by hand. This is used upon reloading from JSON, when the - // autogrow handler is not called. - var dom = element.get(0); - var lines_count = 0; - // modified split rule from - // http://stackoverflow.com/questions/2035910/how-to-get-the-number-of-lines-in-a-textarea/2036424#2036424 - var lines = dom.value.split(/\r|\r\n|\n/); - lines_count = lines.length; - if (lines_count >= 1) { - dom.rows = lines_count; - } else { - dom.rows = 1; - } -}; - - -Cell.prototype.select = function () { - this.element.addClass('ui-widget-content ui-corner-all'); - this.selected = true; - // TODO: we need t test across browsers to see if both of these are needed. - // In the meantime, there should not be any harm in having them both. - this.element.find('textarea').trigger('focusin'); - this.element.find('textarea').trigger('focus'); -}; - - -Cell.prototype.unselect = function () { - this.element.removeClass('ui-widget-content ui-corner-all'); - this.selected = false; -}; - - -Cell.prototype.bind_events = function () { - var that = this; - var nb = that.notebook - that.element.click(function (event) { - if (that.selected === false) { - nb.select(nb.find_cell_index(that)); - }; - }); - that.element.focusin(function (event) { - if (that.selected === false) { - nb.select(nb.find_cell_index(that)); - }; - }); -}; - - -// Subclasses must implement create_element. -Cell.prototype.create_element = function () {}; - - -//============================================================================ -// CodeCell -//============================================================================ - - -var CodeCell = function (notebook) { - this.code_mirror = null; - this.input_prompt_number = ' '; - Cell.apply(this, arguments); -}; - - -CodeCell.prototype = new Cell(); - - -CodeCell.prototype.create_element = function () { - var cell = $('
').addClass('cell code_cell vbox border-box-sizing'); - var input = $('
').addClass('input hbox border-box-sizing'); - input.append($('
').addClass('prompt input_prompt monospace-font')); - var input_area = $('
').addClass('input_area box-flex1 border-box-sizing'); - this.code_mirror = CodeMirror(input_area.get(0), { - indentUnit : 4, - enterMode : 'flat', - tabMode: 'shift' - }); - input.append(input_area); - var output = $('
').addClass('output vbox border-box-sizing'); - cell.append(input).append(output); - this.element = cell; - this.collapse() -}; - - -CodeCell.prototype.select = function () { - Cell.prototype.select.apply(this); - this.code_mirror.focus(); -}; - - -CodeCell.prototype.append_pyout = function (data, n) { - var toinsert = $("
").addClass("output_area output_pyout hbox monospace-font"); - toinsert.append($('
'). - addClass('prompt output_prompt'). - html('Out[' + n + ']:') - ); - this.append_display_data(data, toinsert); - toinsert.children().last().addClass("box_flex1"); - this.element.find("div.output").append(toinsert); - // If we just output latex, typeset it. - if (data["text/latex"] !== undefined) { - MathJax.Hub.Queue(["Typeset",MathJax.Hub]); - }; -}; - - -CodeCell.prototype.append_pyerr = function (ename, evalue, tb) { - var s = ''; - var len = tb.length; - for (var i=0; i").addClass("output_area output_stream monospace-font"); - toinsert.append($("
").addClass("monospace-font").html(fixConsole(data)));
-    element.append(toinsert);
-    return element;
-};
-
-
-CodeCell.prototype.append_svg = function (svg, element) {
-    element = element || this.element.find("div.output");
-    var toinsert = $("
").addClass("output_area output_svg"); - toinsert.append(svg); - element.append(toinsert); - return element; -}; - - -CodeCell.prototype.append_png = function (png, element) { - element = element || this.element.find("div.output"); - var toinsert = $("
").addClass("output_area output_png"); - toinsert.append($("").attr('src','data:image/png;base64,'+png)); - element.append(toinsert); - return element; -}; - - -CodeCell.prototype.append_latex = function (latex, element) { - // This method cannot do the typesetting because the latex first has to - // be on the page. - element = element || this.element.find("div.output"); - var toinsert = $("
").addClass("output_area output_latex monospace-font"); - toinsert.append(latex); - element.append(toinsert); - return element; -} - - -CodeCell.prototype.clear_output = function () { - this.element.find("div.output").html(""); -}; - - -CodeCell.prototype.collapse = function () { - this.element.find('div.output').hide(); -}; - - -CodeCell.prototype.expand = function () { - this.element.find('div.output').show(); -}; - - -CodeCell.prototype.set_input_prompt = function (number) { - var n = number || ' '; - this.input_prompt_number = n - this.element.find('div.input_prompt').html('In [' + n + ']:'); -}; - - -CodeCell.prototype.get_code = function () { - return this.code_mirror.getValue(); -}; - - -CodeCell.prototype.set_code = function (code) { - return this.code_mirror.setValue(code); -}; - - -CodeCell.prototype.at_top = function () { - var cursor = this.code_mirror.getCursor(); - if (cursor.line === 0) { - return true; - } else { - return false; - } -}; - - -CodeCell.prototype.at_bottom = function () { - var cursor = this.code_mirror.getCursor(); - if (cursor.line === (this.code_mirror.lineCount()-1)) { - return true; - } else { - return false; - } -}; - - -CodeCell.prototype.fromJSON = function (data) { - if (data.cell_type === 'code') { - this.set_code(data.code); - this.set_input_prompt(data.prompt_number); - }; -}; - - -CodeCell.prototype.toJSON = function () { - return { - code : this.get_code(), - cell_type : 'code', - prompt_number : this.input_prompt_number - }; -}; - -//============================================================================ -// TextCell -//============================================================================ - - -var TextCell = function (notebook) { - Cell.apply(this, arguments); - this.placeholder = "Type HTML and LaTeX: $\\alpha^2$" - this.rendered = false; -}; - - -TextCell.prototype = new Cell(); - - -TextCell.prototype.create_element = function () { - var cell = $("
").addClass('cell text_cell'). - append( - $(""). - addClass('text_cell_input monospace-font'). - attr('rows',1). - attr('cols',80). - autogrow() - ).append( - // The tabindex=-1 makes this div focusable. - $('
').addClass('text_cell_render').attr('tabindex','-1') - ) - this.element = cell; -}; - - -TextCell.prototype.bind_events = function () { - Cell.prototype.bind_events.apply(this); - var that = this; - this.element.keydown(function (event) { - if (event.which === 13) { - if (that.rendered) { - that.edit(); - event.preventDefault(); - }; - }; - }); -}; - - -TextCell.prototype.select = function () { - Cell.prototype.select.apply(this); - var output = this.element.find("div.text_cell_render"); - output.trigger('focus'); -}; - - -TextCell.prototype.edit = function () { - if (this.rendered === true) { - var text_cell = this.element; - var input = text_cell.find("textarea.text_cell_input"); - var output = text_cell.find("div.text_cell_render"); - output.hide(); - input.show().trigger('focus'); - this.rendered = false; - }; -}; - - -TextCell.prototype.render = function () { - if (this.rendered === false) { - var text_cell = this.element; - var input = text_cell.find("textarea.text_cell_input"); - var output = text_cell.find("div.text_cell_render"); - var text = input.val(); - if (text === "") { - text = this.placeholder; - input.val(text); - }; - output.html(text) - input.html(text); - MathJax.Hub.Queue(["Typeset",MathJax.Hub]); - input.hide(); - output.show(); - this.rendered = true; - }; -}; - - -TextCell.prototype.config_mathjax = function () { - var text_cell = this.element; - var that = this; - text_cell.click(function () { - that.edit(); - }).focusout(function () { - that.render(); - }); - - text_cell.trigger("focusout"); -}; - - -TextCell.prototype.get_text = function() { - return this.element.find("textarea.text_cell_input").val(); -}; - - -TextCell.prototype.set_text = function(text) { - this.element.find("textarea.text_cell_input").val(text); - this.element.find("textarea.text_cell_input").html(text); - this.element.find("div.text_cell_render").html(text); -}; - - -TextCell.prototype.at_top = function () { - if (this.rendered) { - return true; - } else { - return false; - } -}; - - -TextCell.prototype.at_bottom = function () { - if (this.rendered) { - return true; - } else { - return false; - } -}; - - -TextCell.prototype.fromJSON = function (data) { - if (data.cell_type === 'text') { - this.set_text(data.text); - this.grow(this.element.find("textarea.text_cell_input")); - }; -} - - -TextCell.prototype.toJSON = function () { - return { - cell_type : 'text', - text : this.get_text(), - }; -}; - -//============================================================================ -// On document ready -//============================================================================ - - -var Kernel = function () { - this.kernel_id = null; - this.base_url = "/kernels"; - this.kernel_url = null; -}; - - -Kernel.prototype.get_msg = function (msg_type, content) { - var msg = { - header : { - msg_id : uuid(), - username : "bgranger", - session: this.session_id, - msg_type : msg_type - }, - content : content, - parent_header : {} - }; - return msg; -} - -Kernel.prototype.start_kernel = function (callback, context) { - var that = this; - $.post(this.base_url, - function (kernel_id) { - that._handle_start_kernel(kernel_id, callback, context); - }, - 'json' - ); -}; - - -Kernel.prototype._handle_start_kernel = function (kernel_id, callback, context) { - this.kernel_id = kernel_id; - this.kernel_url = this.base_url + "/" + this.kernel_id; - this._start_channels(); - callback.call(context); -}; - - -Kernel.prototype._start_channels = function () { - var ws_url = "ws://127.0.0.1:8888" + this.kernel_url; - this.shell_channel = new WebSocket(ws_url + "/shell"); - this.iopub_channel = new WebSocket(ws_url + "/iopub"); -} - - -Kernel.prototype.execute = function (code) { - var content = { - code : code, - silent : false, - user_variables : [], - user_expressions : {} - }; - var msg = this.get_msg("execute_request", content); - this.shell_channel.send(JSON.stringify(msg)); - return msg.header.msg_id; -} - - -Kernel.prototype.interrupt = function () { - $.post(this.kernel_url + "/interrupt"); -}; - - -Kernel.prototype.restart = function () { - this.status_restarting(); - url = this.kernel_url + "/restart" - var that = this; - $.post(url, function (kernel_id) { - console.log("Kernel restarted: " + kernel_id); - that.kernel_id = kernel_id; - that.kernel_url = that.base_url + "/" + that.kernel_id; - that.status_idle(); - }, 'json'); -}; - - -Kernel.prototype.status_busy = function () { - $("#kernel_status").removeClass("status_idle"); - $("#kernel_status").removeClass("status_restarting"); - $("#kernel_status").addClass("status_busy"); - $("#kernel_status").text("Busy"); -}; - - -Kernel.prototype.status_idle = function () { - $("#kernel_status").removeClass("status_busy"); - $("#kernel_status").removeClass("status_restarting"); - $("#kernel_status").addClass("status_idle"); - $("#kernel_status").text("Idle"); -}; - -Kernel.prototype.status_restarting = function () { - $("#kernel_status").removeClass("status_busy"); - $("#kernel_status").removeClass("status_idle"); - $("#kernel_status").addClass("status_restarting"); - $("#kernel_status").text("Restarting"); -}; - -//============================================================================ -// On document ready -//============================================================================ - - -$(document).ready(function () { - - $('div#wrapper').addClass('vbox border-box-sizing') - $('div.notebook').addClass('box-flex1 border-box-sizing') - - MathJax.Hub.Config({ - tex2jax: { - inlineMath: [ ['$','$'], ["\\(","\\)"] ], - displayMath: [ ['$$','$$'], ["\\[","\\]"] ], - }, - displayAlign: 'left', // Change this to 'center' to center equations. - "HTML-CSS": { - styles: {'.MathJax_Display': {"margin": 0}} - } - }); - - IPYTHON.notebook = new Notebook('div.notebook'); - IPYTHON.notebook.insert_code_cell_after(); - - $("#menu_tabs").tabs(); - - $("#help_toolbar").buttonset(); - - $("#kernel_toolbar").buttonset(); - $("#interrupt_kernel").click(function () {IPYTHON.notebook.kernel.interrupt();}); - $("#restart_kernel").click(function () {IPYTHON.notebook.kernel.restart();}); - $("#kernel_status").addClass("status_idle"); - - $("#move_cell").buttonset(); - $("#move_up").button("option", "icons", {primary:"ui-icon-arrowthick-1-n"}); - $("#move_up").button("option", "text", false); - $("#move_up").click(function () {IPYTHON.notebook.move_cell_up();}); - $("#move_down").button("option", "icons", {primary:"ui-icon-arrowthick-1-s"}); - $("#move_down").button("option", "text", false); - $("#move_down").click(function () {IPYTHON.notebook.move_cell_down();}); - - $("#insert_delete").buttonset(); - $("#insert_cell_before").click(function () {IPYTHON.notebook.insert_code_cell_before();}); - $("#insert_cell_after").click(function () {IPYTHON.notebook.insert_code_cell_after();}); - $("#delete_cell").button("option", "icons", {primary:"ui-icon-closethick"}); - $("#delete_cell").button("option", "text", false); - $("#delete_cell").click(function () {IPYTHON.notebook.delete_cell();}); - - $("#cell_type").buttonset(); - $("#to_code").click(function () {IPYTHON.notebook.text_to_code();}); - $("#to_text").click(function () {IPYTHON.notebook.code_to_text();}); - - $("#sort").buttonset(); - $("#sort_cells").click(function () {IPYTHON.notebook.sort_cells();}); - - $("#toggle").buttonset(); - $("#collapse").click(function () {IPYTHON.notebook.collapse();}); - $("#expand").click(function () {IPYTHON.notebook.expand();}); - -}); - diff --git a/IPython/frontend/html/notebook/static/js/notebook_main.js b/IPython/frontend/html/notebook/static/js/notebook_main.js new file mode 100644 index 0000000..5f1f1bc --- /dev/null +++ b/IPython/frontend/html/notebook/static/js/notebook_main.js @@ -0,0 +1,62 @@ + +//============================================================================ +// On document ready +//============================================================================ + + +$(document).ready(function () { + + $('div#wrapper').addClass('vbox border-box-sizing') + $('div.notebook').addClass('box-flex1 border-box-sizing') + + MathJax.Hub.Config({ + tex2jax: { + inlineMath: [ ['$','$'], ["\\(","\\)"] ], + displayMath: [ ['$$','$$'], ["\\[","\\]"] ], + }, + displayAlign: 'left', // Change this to 'center' to center equations. + "HTML-CSS": { + styles: {'.MathJax_Display': {"margin": 0}} + } + }); + + IPYTHON.notebook = new Notebook('div.notebook'); + IPYTHON.notebook.insert_code_cell_after(); + + $("#menu_tabs").tabs(); + + $("#help_toolbar").buttonset(); + + $("#kernel_toolbar").buttonset(); + $("#interrupt_kernel").click(function () {IPYTHON.notebook.kernel.interrupt();}); + $("#restart_kernel").click(function () {IPYTHON.notebook.kernel.restart();}); + $("#kernel_status").addClass("status_idle"); + + $("#move_cell").buttonset(); + $("#move_up").button("option", "icons", {primary:"ui-icon-arrowthick-1-n"}); + $("#move_up").button("option", "text", false); + $("#move_up").click(function () {IPYTHON.notebook.move_cell_up();}); + $("#move_down").button("option", "icons", {primary:"ui-icon-arrowthick-1-s"}); + $("#move_down").button("option", "text", false); + $("#move_down").click(function () {IPYTHON.notebook.move_cell_down();}); + + $("#insert_delete").buttonset(); + $("#insert_cell_before").click(function () {IPYTHON.notebook.insert_code_cell_before();}); + $("#insert_cell_after").click(function () {IPYTHON.notebook.insert_code_cell_after();}); + $("#delete_cell").button("option", "icons", {primary:"ui-icon-closethick"}); + $("#delete_cell").button("option", "text", false); + $("#delete_cell").click(function () {IPYTHON.notebook.delete_cell();}); + + $("#cell_type").buttonset(); + $("#to_code").click(function () {IPYTHON.notebook.text_to_code();}); + $("#to_text").click(function () {IPYTHON.notebook.code_to_text();}); + + $("#sort").buttonset(); + $("#sort_cells").click(function () {IPYTHON.notebook.sort_cells();}); + + $("#toggle").buttonset(); + $("#collapse").click(function () {IPYTHON.notebook.collapse();}); + $("#expand").click(function () {IPYTHON.notebook.expand();}); + +}); + diff --git a/IPython/frontend/html/notebook/static/js/textcell.js b/IPython/frontend/html/notebook/static/js/textcell.js new file mode 100644 index 0000000..b181278 --- /dev/null +++ b/IPython/frontend/html/notebook/static/js/textcell.js @@ -0,0 +1,144 @@ + +//============================================================================ +// TextCell +//============================================================================ + + +var TextCell = function (notebook) { + Cell.apply(this, arguments); + this.placeholder = "Type HTML and LaTeX: $\\alpha^2$" + this.rendered = false; +}; + + +TextCell.prototype = new Cell(); + + +TextCell.prototype.create_element = function () { + var cell = $("
").addClass('cell text_cell'). + append( + $(""). + addClass('text_cell_input monospace-font'). + attr('rows',1). + attr('cols',80). + autogrow() + ).append( + // The tabindex=-1 makes this div focusable. + $('
').addClass('text_cell_render').attr('tabindex','-1') + ) + this.element = cell; +}; + + +TextCell.prototype.bind_events = function () { + Cell.prototype.bind_events.apply(this); + var that = this; + this.element.keydown(function (event) { + if (event.which === 13) { + if (that.rendered) { + that.edit(); + event.preventDefault(); + }; + }; + }); +}; + + +TextCell.prototype.select = function () { + Cell.prototype.select.apply(this); + var output = this.element.find("div.text_cell_render"); + output.trigger('focus'); +}; + + +TextCell.prototype.edit = function () { + if (this.rendered === true) { + var text_cell = this.element; + var input = text_cell.find("textarea.text_cell_input"); + var output = text_cell.find("div.text_cell_render"); + output.hide(); + input.show().trigger('focus'); + this.rendered = false; + }; +}; + + +TextCell.prototype.render = function () { + if (this.rendered === false) { + var text_cell = this.element; + var input = text_cell.find("textarea.text_cell_input"); + var output = text_cell.find("div.text_cell_render"); + var text = input.val(); + if (text === "") { + text = this.placeholder; + input.val(text); + }; + output.html(text) + input.html(text); + MathJax.Hub.Queue(["Typeset",MathJax.Hub]); + input.hide(); + output.show(); + this.rendered = true; + }; +}; + + +TextCell.prototype.config_mathjax = function () { + var text_cell = this.element; + var that = this; + text_cell.click(function () { + that.edit(); + }).focusout(function () { + that.render(); + }); + + text_cell.trigger("focusout"); +}; + + +TextCell.prototype.get_text = function() { + return this.element.find("textarea.text_cell_input").val(); +}; + + +TextCell.prototype.set_text = function(text) { + this.element.find("textarea.text_cell_input").val(text); + this.element.find("textarea.text_cell_input").html(text); + this.element.find("div.text_cell_render").html(text); +}; + + +TextCell.prototype.at_top = function () { + if (this.rendered) { + return true; + } else { + return false; + } +}; + + +TextCell.prototype.at_bottom = function () { + if (this.rendered) { + return true; + } else { + return false; + } +}; + + +TextCell.prototype.fromJSON = function (data) { + if (data.cell_type === 'text') { + this.set_text(data.text); + this.grow(this.element.find("textarea.text_cell_input")); + }; +} + + +TextCell.prototype.toJSON = function () { + return { + cell_type : 'text', + text : this.get_text(), + }; +}; + + diff --git a/IPython/frontend/html/notebook/static/js/utils.js b/IPython/frontend/html/notebook/static/js/utils.js new file mode 100644 index 0000000..8aaf55a --- /dev/null +++ b/IPython/frontend/html/notebook/static/js/utils.js @@ -0,0 +1,62 @@ + +//============================================================================ +// Utilities +//============================================================================ + + +var uuid = function () { + // http://www.ietf.org/rfc/rfc4122.txt + var s = []; + var hexDigits = "0123456789ABCDEF"; + for (var i = 0; i < 32; i++) { + s[i] = hexDigits.substr(Math.floor(Math.random() * 0x10), 1); + } + s[12] = "4"; // bits 12-15 of the time_hi_and_version field to 0010 + s[16] = hexDigits.substr((s[16] & 0x3) | 0x8, 1); // bits 6-7 of the clock_seq_hi_and_reserved to 01 + + var uuid = s.join(""); + return uuid; +}; + + +//Fix raw text to parse correctly in crazy XML +function xmlencode(string) { + return string.replace(/\&/g,'&'+'amp;') + .replace(//g,'&'+'gt;') + .replace(/\'/g,'&'+'apos;') + .replace(/\"/g,'&'+'quot;') + .replace(/`/g,'&'+'#96;') +} + +//Map from terminal commands to CSS classes +attrib = { + "30":"cblack", "31":"cred", + "32":"cgreen", "33":"cyellow", + "34":"cblue", "36":"ccyan", + "37":"cwhite", "01":"cbold"} + +//Fixes escaped console commands, IE colors. Turns them into HTML +function fixConsole(txt) { + txt = xmlencode(txt) + var re = /\033\[([\d;]*?)m/ + var opened = false + var cmds = [] + var opener = "" + var closer = "" + + while (re.test(txt)) { + var cmds = txt.match(re)[1].split(";") + closer = opened?"":"" + opened = cmds.length > 1 || cmds[0] != 0 + var rep = [] + for (var i in cmds) + if (typeof(attrib[cmds[i]]) != "undefined") + rep.push(attrib[cmds[i]]) + opener = rep.length > 0?"":"" + txt = txt.replace(re, closer + opener) + } + if (opened) txt += "" + return txt.trim() +} +