Show More
@@ -0,0 +1,72 b'' | |||
|
1 | ||
|
2 | //============================================================================ | |
|
3 | // Cell | |
|
4 | //============================================================================ | |
|
5 | ||
|
6 | ||
|
7 | var Cell = function (notebook) { | |
|
8 | this.notebook = notebook; | |
|
9 | this.selected = false; | |
|
10 | this.element; | |
|
11 | this.create_element(); | |
|
12 | if (this.element !== undefined) { | |
|
13 | this.element.data("cell", this); | |
|
14 | this.bind_events(); | |
|
15 | } | |
|
16 | this.cell_id = uuid(); | |
|
17 | }; | |
|
18 | ||
|
19 | ||
|
20 | Cell.prototype.grow = function(element) { | |
|
21 | // Grow the cell by hand. This is used upon reloading from JSON, when the | |
|
22 | // autogrow handler is not called. | |
|
23 | var dom = element.get(0); | |
|
24 | var lines_count = 0; | |
|
25 | // modified split rule from | |
|
26 | // http://stackoverflow.com/questions/2035910/how-to-get-the-number-of-lines-in-a-textarea/2036424#2036424 | |
|
27 | var lines = dom.value.split(/\r|\r\n|\n/); | |
|
28 | lines_count = lines.length; | |
|
29 | if (lines_count >= 1) { | |
|
30 | dom.rows = lines_count; | |
|
31 | } else { | |
|
32 | dom.rows = 1; | |
|
33 | } | |
|
34 | }; | |
|
35 | ||
|
36 | ||
|
37 | Cell.prototype.select = function () { | |
|
38 | this.element.addClass('ui-widget-content ui-corner-all'); | |
|
39 | this.selected = true; | |
|
40 | // TODO: we need t test across browsers to see if both of these are needed. | |
|
41 | // In the meantime, there should not be any harm in having them both. | |
|
42 | this.element.find('textarea').trigger('focusin'); | |
|
43 | this.element.find('textarea').trigger('focus'); | |
|
44 | }; | |
|
45 | ||
|
46 | ||
|
47 | Cell.prototype.unselect = function () { | |
|
48 | this.element.removeClass('ui-widget-content ui-corner-all'); | |
|
49 | this.selected = false; | |
|
50 | }; | |
|
51 | ||
|
52 | ||
|
53 | Cell.prototype.bind_events = function () { | |
|
54 | var that = this; | |
|
55 | var nb = that.notebook | |
|
56 | that.element.click(function (event) { | |
|
57 | if (that.selected === false) { | |
|
58 | nb.select(nb.find_cell_index(that)); | |
|
59 | }; | |
|
60 | }); | |
|
61 | that.element.focusin(function (event) { | |
|
62 | if (that.selected === false) { | |
|
63 | nb.select(nb.find_cell_index(that)); | |
|
64 | }; | |
|
65 | }); | |
|
66 | }; | |
|
67 | ||
|
68 | ||
|
69 | // Subclasses must implement create_element. | |
|
70 | Cell.prototype.create_element = function () {}; | |
|
71 | ||
|
72 |
@@ -0,0 +1,195 b'' | |||
|
1 | ||
|
2 | //============================================================================ | |
|
3 | // CodeCell | |
|
4 | //============================================================================ | |
|
5 | ||
|
6 | ||
|
7 | var CodeCell = function (notebook) { | |
|
8 | this.code_mirror = null; | |
|
9 | this.input_prompt_number = ' '; | |
|
10 | Cell.apply(this, arguments); | |
|
11 | }; | |
|
12 | ||
|
13 | ||
|
14 | CodeCell.prototype = new Cell(); | |
|
15 | ||
|
16 | ||
|
17 | CodeCell.prototype.create_element = function () { | |
|
18 | var cell = $('<div></div>').addClass('cell code_cell vbox border-box-sizing'); | |
|
19 | var input = $('<div></div>').addClass('input hbox border-box-sizing'); | |
|
20 | input.append($('<div/>').addClass('prompt input_prompt monospace-font')); | |
|
21 | var input_area = $('<div/>').addClass('input_area box-flex1 border-box-sizing'); | |
|
22 | this.code_mirror = CodeMirror(input_area.get(0), { | |
|
23 | indentUnit : 4, | |
|
24 | enterMode : 'flat', | |
|
25 | tabMode: 'shift' | |
|
26 | }); | |
|
27 | input.append(input_area); | |
|
28 | var output = $('<div></div>').addClass('output vbox border-box-sizing'); | |
|
29 | cell.append(input).append(output); | |
|
30 | this.element = cell; | |
|
31 | this.collapse() | |
|
32 | }; | |
|
33 | ||
|
34 | ||
|
35 | CodeCell.prototype.select = function () { | |
|
36 | Cell.prototype.select.apply(this); | |
|
37 | this.code_mirror.focus(); | |
|
38 | }; | |
|
39 | ||
|
40 | ||
|
41 | CodeCell.prototype.append_pyout = function (data, n) { | |
|
42 | var toinsert = $("<div/>").addClass("output_area output_pyout hbox monospace-font"); | |
|
43 | toinsert.append($('<div/>'). | |
|
44 | addClass('prompt output_prompt'). | |
|
45 | html('Out[' + n + ']:') | |
|
46 | ); | |
|
47 | this.append_display_data(data, toinsert); | |
|
48 | toinsert.children().last().addClass("box_flex1"); | |
|
49 | this.element.find("div.output").append(toinsert); | |
|
50 | // If we just output latex, typeset it. | |
|
51 | if (data["text/latex"] !== undefined) { | |
|
52 | MathJax.Hub.Queue(["Typeset",MathJax.Hub]); | |
|
53 | }; | |
|
54 | }; | |
|
55 | ||
|
56 | ||
|
57 | CodeCell.prototype.append_pyerr = function (ename, evalue, tb) { | |
|
58 | var s = ''; | |
|
59 | var len = tb.length; | |
|
60 | for (var i=0; i<len; i++) { | |
|
61 | s = s + tb[i] + '\n'; | |
|
62 | } | |
|
63 | s = s + '\n'; | |
|
64 | this.append_stream(s); | |
|
65 | }; | |
|
66 | ||
|
67 | ||
|
68 | CodeCell.prototype.append_display_data = function (data, element) { | |
|
69 | console.log(data); | |
|
70 | if (data["text/latex"] !== undefined) { | |
|
71 | this.append_latex(data["text/latex"], element); | |
|
72 | // If it is undefined, then we just appended to div.output, which | |
|
73 | // makes the latex visible and we can typeset it. The typesetting | |
|
74 | // has to be done after the latex is on the page. | |
|
75 | if (element === undefined) { | |
|
76 | MathJax.Hub.Queue(["Typeset",MathJax.Hub]); | |
|
77 | }; | |
|
78 | } else if (data["image/svg+xml"] !== undefined) { | |
|
79 | this.append_svg(data["image/svg+xml"], element); | |
|
80 | } else if (data["image/png"] !== undefined) { | |
|
81 | this.append_png(data["image/png"], element); | |
|
82 | } else if (data["text/plain"] !== undefined) { | |
|
83 | this.append_stream(data["text/plain"], element); | |
|
84 | }; | |
|
85 | return element; | |
|
86 | }; | |
|
87 | ||
|
88 | ||
|
89 | CodeCell.prototype.append_stream = function (data, element) { | |
|
90 | element = element || this.element.find("div.output"); | |
|
91 | var toinsert = $("<div/>").addClass("output_area output_stream monospace-font"); | |
|
92 | toinsert.append($("<pre/>").addClass("monospace-font").html(fixConsole(data))); | |
|
93 | element.append(toinsert); | |
|
94 | return element; | |
|
95 | }; | |
|
96 | ||
|
97 | ||
|
98 | CodeCell.prototype.append_svg = function (svg, element) { | |
|
99 | element = element || this.element.find("div.output"); | |
|
100 | var toinsert = $("<div/>").addClass("output_area output_svg"); | |
|
101 | toinsert.append(svg); | |
|
102 | element.append(toinsert); | |
|
103 | return element; | |
|
104 | }; | |
|
105 | ||
|
106 | ||
|
107 | CodeCell.prototype.append_png = function (png, element) { | |
|
108 | element = element || this.element.find("div.output"); | |
|
109 | var toinsert = $("<div/>").addClass("output_area output_png"); | |
|
110 | toinsert.append($("<img/>").attr('src','data:image/png;base64,'+png)); | |
|
111 | element.append(toinsert); | |
|
112 | return element; | |
|
113 | }; | |
|
114 | ||
|
115 | ||
|
116 | CodeCell.prototype.append_latex = function (latex, element) { | |
|
117 | // This method cannot do the typesetting because the latex first has to | |
|
118 | // be on the page. | |
|
119 | element = element || this.element.find("div.output"); | |
|
120 | var toinsert = $("<div/>").addClass("output_area output_latex monospace-font"); | |
|
121 | toinsert.append(latex); | |
|
122 | element.append(toinsert); | |
|
123 | return element; | |
|
124 | } | |
|
125 | ||
|
126 | ||
|
127 | CodeCell.prototype.clear_output = function () { | |
|
128 | this.element.find("div.output").html(""); | |
|
129 | }; | |
|
130 | ||
|
131 | ||
|
132 | CodeCell.prototype.collapse = function () { | |
|
133 | this.element.find('div.output').hide(); | |
|
134 | }; | |
|
135 | ||
|
136 | ||
|
137 | CodeCell.prototype.expand = function () { | |
|
138 | this.element.find('div.output').show(); | |
|
139 | }; | |
|
140 | ||
|
141 | ||
|
142 | CodeCell.prototype.set_input_prompt = function (number) { | |
|
143 | var n = number || ' '; | |
|
144 | this.input_prompt_number = n | |
|
145 | this.element.find('div.input_prompt').html('In [' + n + ']:'); | |
|
146 | }; | |
|
147 | ||
|
148 | ||
|
149 | CodeCell.prototype.get_code = function () { | |
|
150 | return this.code_mirror.getValue(); | |
|
151 | }; | |
|
152 | ||
|
153 | ||
|
154 | CodeCell.prototype.set_code = function (code) { | |
|
155 | return this.code_mirror.setValue(code); | |
|
156 | }; | |
|
157 | ||
|
158 | ||
|
159 | CodeCell.prototype.at_top = function () { | |
|
160 | var cursor = this.code_mirror.getCursor(); | |
|
161 | if (cursor.line === 0) { | |
|
162 | return true; | |
|
163 | } else { | |
|
164 | return false; | |
|
165 | } | |
|
166 | }; | |
|
167 | ||
|
168 | ||
|
169 | CodeCell.prototype.at_bottom = function () { | |
|
170 | var cursor = this.code_mirror.getCursor(); | |
|
171 | if (cursor.line === (this.code_mirror.lineCount()-1)) { | |
|
172 | return true; | |
|
173 | } else { | |
|
174 | return false; | |
|
175 | } | |
|
176 | }; | |
|
177 | ||
|
178 | ||
|
179 | CodeCell.prototype.fromJSON = function (data) { | |
|
180 | if (data.cell_type === 'code') { | |
|
181 | this.set_code(data.code); | |
|
182 | this.set_input_prompt(data.prompt_number); | |
|
183 | }; | |
|
184 | }; | |
|
185 | ||
|
186 | ||
|
187 | CodeCell.prototype.toJSON = function () { | |
|
188 | return { | |
|
189 | code : this.get_code(), | |
|
190 | cell_type : 'code', | |
|
191 | prompt_number : this.input_prompt_number | |
|
192 | }; | |
|
193 | }; | |
|
194 | ||
|
195 |
@@ -0,0 +1,107 b'' | |||
|
1 | ||
|
2 | //============================================================================ | |
|
3 | // Kernel | |
|
4 | //============================================================================ | |
|
5 | ||
|
6 | ||
|
7 | var Kernel = function () { | |
|
8 | this.kernel_id = null; | |
|
9 | this.base_url = "/kernels"; | |
|
10 | this.kernel_url = null; | |
|
11 | }; | |
|
12 | ||
|
13 | ||
|
14 | Kernel.prototype.get_msg = function (msg_type, content) { | |
|
15 | var msg = { | |
|
16 | header : { | |
|
17 | msg_id : uuid(), | |
|
18 | username : "bgranger", | |
|
19 | session: this.session_id, | |
|
20 | msg_type : msg_type | |
|
21 | }, | |
|
22 | content : content, | |
|
23 | parent_header : {} | |
|
24 | }; | |
|
25 | return msg; | |
|
26 | } | |
|
27 | ||
|
28 | Kernel.prototype.start_kernel = function (callback, context) { | |
|
29 | var that = this; | |
|
30 | $.post(this.base_url, | |
|
31 | function (kernel_id) { | |
|
32 | that._handle_start_kernel(kernel_id, callback, context); | |
|
33 | }, | |
|
34 | 'json' | |
|
35 | ); | |
|
36 | }; | |
|
37 | ||
|
38 | ||
|
39 | Kernel.prototype._handle_start_kernel = function (kernel_id, callback, context) { | |
|
40 | this.kernel_id = kernel_id; | |
|
41 | this.kernel_url = this.base_url + "/" + this.kernel_id; | |
|
42 | this._start_channels(); | |
|
43 | callback.call(context); | |
|
44 | }; | |
|
45 | ||
|
46 | ||
|
47 | Kernel.prototype._start_channels = function () { | |
|
48 | var ws_url = "ws://127.0.0.1:8888" + this.kernel_url; | |
|
49 | this.shell_channel = new WebSocket(ws_url + "/shell"); | |
|
50 | this.iopub_channel = new WebSocket(ws_url + "/iopub"); | |
|
51 | } | |
|
52 | ||
|
53 | ||
|
54 | Kernel.prototype.execute = function (code) { | |
|
55 | var content = { | |
|
56 | code : code, | |
|
57 | silent : false, | |
|
58 | user_variables : [], | |
|
59 | user_expressions : {} | |
|
60 | }; | |
|
61 | var msg = this.get_msg("execute_request", content); | |
|
62 | this.shell_channel.send(JSON.stringify(msg)); | |
|
63 | return msg.header.msg_id; | |
|
64 | } | |
|
65 | ||
|
66 | ||
|
67 | Kernel.prototype.interrupt = function () { | |
|
68 | $.post(this.kernel_url + "/interrupt"); | |
|
69 | }; | |
|
70 | ||
|
71 | ||
|
72 | Kernel.prototype.restart = function () { | |
|
73 | this.status_restarting(); | |
|
74 | url = this.kernel_url + "/restart" | |
|
75 | var that = this; | |
|
76 | $.post(url, function (kernel_id) { | |
|
77 | console.log("Kernel restarted: " + kernel_id); | |
|
78 | that.kernel_id = kernel_id; | |
|
79 | that.kernel_url = that.base_url + "/" + that.kernel_id; | |
|
80 | that.status_idle(); | |
|
81 | }, 'json'); | |
|
82 | }; | |
|
83 | ||
|
84 | ||
|
85 | Kernel.prototype.status_busy = function () { | |
|
86 | $("#kernel_status").removeClass("status_idle"); | |
|
87 | $("#kernel_status").removeClass("status_restarting"); | |
|
88 | $("#kernel_status").addClass("status_busy"); | |
|
89 | $("#kernel_status").text("Busy"); | |
|
90 | }; | |
|
91 | ||
|
92 | ||
|
93 | Kernel.prototype.status_idle = function () { | |
|
94 | $("#kernel_status").removeClass("status_busy"); | |
|
95 | $("#kernel_status").removeClass("status_restarting"); | |
|
96 | $("#kernel_status").addClass("status_idle"); | |
|
97 | $("#kernel_status").text("Idle"); | |
|
98 | }; | |
|
99 | ||
|
100 | Kernel.prototype.status_restarting = function () { | |
|
101 | $("#kernel_status").removeClass("status_busy"); | |
|
102 | $("#kernel_status").removeClass("status_idle"); | |
|
103 | $("#kernel_status").addClass("status_restarting"); | |
|
104 | $("#kernel_status").text("Restarting"); | |
|
105 | }; | |
|
106 | ||
|
107 |
@@ -0,0 +1,62 b'' | |||
|
1 | ||
|
2 | //============================================================================ | |
|
3 | // On document ready | |
|
4 | //============================================================================ | |
|
5 | ||
|
6 | ||
|
7 | $(document).ready(function () { | |
|
8 | ||
|
9 | $('div#wrapper').addClass('vbox border-box-sizing') | |
|
10 | $('div.notebook').addClass('box-flex1 border-box-sizing') | |
|
11 | ||
|
12 | MathJax.Hub.Config({ | |
|
13 | tex2jax: { | |
|
14 | inlineMath: [ ['$','$'], ["\\(","\\)"] ], | |
|
15 | displayMath: [ ['$$','$$'], ["\\[","\\]"] ], | |
|
16 | }, | |
|
17 | displayAlign: 'left', // Change this to 'center' to center equations. | |
|
18 | "HTML-CSS": { | |
|
19 | styles: {'.MathJax_Display': {"margin": 0}} | |
|
20 | } | |
|
21 | }); | |
|
22 | ||
|
23 | IPYTHON.notebook = new Notebook('div.notebook'); | |
|
24 | IPYTHON.notebook.insert_code_cell_after(); | |
|
25 | ||
|
26 | $("#menu_tabs").tabs(); | |
|
27 | ||
|
28 | $("#help_toolbar").buttonset(); | |
|
29 | ||
|
30 | $("#kernel_toolbar").buttonset(); | |
|
31 | $("#interrupt_kernel").click(function () {IPYTHON.notebook.kernel.interrupt();}); | |
|
32 | $("#restart_kernel").click(function () {IPYTHON.notebook.kernel.restart();}); | |
|
33 | $("#kernel_status").addClass("status_idle"); | |
|
34 | ||
|
35 | $("#move_cell").buttonset(); | |
|
36 | $("#move_up").button("option", "icons", {primary:"ui-icon-arrowthick-1-n"}); | |
|
37 | $("#move_up").button("option", "text", false); | |
|
38 | $("#move_up").click(function () {IPYTHON.notebook.move_cell_up();}); | |
|
39 | $("#move_down").button("option", "icons", {primary:"ui-icon-arrowthick-1-s"}); | |
|
40 | $("#move_down").button("option", "text", false); | |
|
41 | $("#move_down").click(function () {IPYTHON.notebook.move_cell_down();}); | |
|
42 | ||
|
43 | $("#insert_delete").buttonset(); | |
|
44 | $("#insert_cell_before").click(function () {IPYTHON.notebook.insert_code_cell_before();}); | |
|
45 | $("#insert_cell_after").click(function () {IPYTHON.notebook.insert_code_cell_after();}); | |
|
46 | $("#delete_cell").button("option", "icons", {primary:"ui-icon-closethick"}); | |
|
47 | $("#delete_cell").button("option", "text", false); | |
|
48 | $("#delete_cell").click(function () {IPYTHON.notebook.delete_cell();}); | |
|
49 | ||
|
50 | $("#cell_type").buttonset(); | |
|
51 | $("#to_code").click(function () {IPYTHON.notebook.text_to_code();}); | |
|
52 | $("#to_text").click(function () {IPYTHON.notebook.code_to_text();}); | |
|
53 | ||
|
54 | $("#sort").buttonset(); | |
|
55 | $("#sort_cells").click(function () {IPYTHON.notebook.sort_cells();}); | |
|
56 | ||
|
57 | $("#toggle").buttonset(); | |
|
58 | $("#collapse").click(function () {IPYTHON.notebook.collapse();}); | |
|
59 | $("#expand").click(function () {IPYTHON.notebook.expand();}); | |
|
60 | ||
|
61 | }); | |
|
62 |
@@ -0,0 +1,144 b'' | |||
|
1 | ||
|
2 | //============================================================================ | |
|
3 | // TextCell | |
|
4 | //============================================================================ | |
|
5 | ||
|
6 | ||
|
7 | var TextCell = function (notebook) { | |
|
8 | Cell.apply(this, arguments); | |
|
9 | this.placeholder = "Type <strong>HTML</strong> and LaTeX: $\\alpha^2$" | |
|
10 | this.rendered = false; | |
|
11 | }; | |
|
12 | ||
|
13 | ||
|
14 | TextCell.prototype = new Cell(); | |
|
15 | ||
|
16 | ||
|
17 | TextCell.prototype.create_element = function () { | |
|
18 | var cell = $("<div>").addClass('cell text_cell'). | |
|
19 | append( | |
|
20 | $("<textarea>" + this.placeholder + "</textarea>"). | |
|
21 | addClass('text_cell_input monospace-font'). | |
|
22 | attr('rows',1). | |
|
23 | attr('cols',80). | |
|
24 | autogrow() | |
|
25 | ).append( | |
|
26 | // The tabindex=-1 makes this div focusable. | |
|
27 | $('<div></div>').addClass('text_cell_render').attr('tabindex','-1') | |
|
28 | ) | |
|
29 | this.element = cell; | |
|
30 | }; | |
|
31 | ||
|
32 | ||
|
33 | TextCell.prototype.bind_events = function () { | |
|
34 | Cell.prototype.bind_events.apply(this); | |
|
35 | var that = this; | |
|
36 | this.element.keydown(function (event) { | |
|
37 | if (event.which === 13) { | |
|
38 | if (that.rendered) { | |
|
39 | that.edit(); | |
|
40 | event.preventDefault(); | |
|
41 | }; | |
|
42 | }; | |
|
43 | }); | |
|
44 | }; | |
|
45 | ||
|
46 | ||
|
47 | TextCell.prototype.select = function () { | |
|
48 | Cell.prototype.select.apply(this); | |
|
49 | var output = this.element.find("div.text_cell_render"); | |
|
50 | output.trigger('focus'); | |
|
51 | }; | |
|
52 | ||
|
53 | ||
|
54 | TextCell.prototype.edit = function () { | |
|
55 | if (this.rendered === true) { | |
|
56 | var text_cell = this.element; | |
|
57 | var input = text_cell.find("textarea.text_cell_input"); | |
|
58 | var output = text_cell.find("div.text_cell_render"); | |
|
59 | output.hide(); | |
|
60 | input.show().trigger('focus'); | |
|
61 | this.rendered = false; | |
|
62 | }; | |
|
63 | }; | |
|
64 | ||
|
65 | ||
|
66 | TextCell.prototype.render = function () { | |
|
67 | if (this.rendered === false) { | |
|
68 | var text_cell = this.element; | |
|
69 | var input = text_cell.find("textarea.text_cell_input"); | |
|
70 | var output = text_cell.find("div.text_cell_render"); | |
|
71 | var text = input.val(); | |
|
72 | if (text === "") { | |
|
73 | text = this.placeholder; | |
|
74 | input.val(text); | |
|
75 | }; | |
|
76 | output.html(text) | |
|
77 | input.html(text); | |
|
78 | MathJax.Hub.Queue(["Typeset",MathJax.Hub]); | |
|
79 | input.hide(); | |
|
80 | output.show(); | |
|
81 | this.rendered = true; | |
|
82 | }; | |
|
83 | }; | |
|
84 | ||
|
85 | ||
|
86 | TextCell.prototype.config_mathjax = function () { | |
|
87 | var text_cell = this.element; | |
|
88 | var that = this; | |
|
89 | text_cell.click(function () { | |
|
90 | that.edit(); | |
|
91 | }).focusout(function () { | |
|
92 | that.render(); | |
|
93 | }); | |
|
94 | ||
|
95 | text_cell.trigger("focusout"); | |
|
96 | }; | |
|
97 | ||
|
98 | ||
|
99 | TextCell.prototype.get_text = function() { | |
|
100 | return this.element.find("textarea.text_cell_input").val(); | |
|
101 | }; | |
|
102 | ||
|
103 | ||
|
104 | TextCell.prototype.set_text = function(text) { | |
|
105 | this.element.find("textarea.text_cell_input").val(text); | |
|
106 | this.element.find("textarea.text_cell_input").html(text); | |
|
107 | this.element.find("div.text_cell_render").html(text); | |
|
108 | }; | |
|
109 | ||
|
110 | ||
|
111 | TextCell.prototype.at_top = function () { | |
|
112 | if (this.rendered) { | |
|
113 | return true; | |
|
114 | } else { | |
|
115 | return false; | |
|
116 | } | |
|
117 | }; | |
|
118 | ||
|
119 | ||
|
120 | TextCell.prototype.at_bottom = function () { | |
|
121 | if (this.rendered) { | |
|
122 | return true; | |
|
123 | } else { | |
|
124 | return false; | |
|
125 | } | |
|
126 | }; | |
|
127 | ||
|
128 | ||
|
129 | TextCell.prototype.fromJSON = function (data) { | |
|
130 | if (data.cell_type === 'text') { | |
|
131 | this.set_text(data.text); | |
|
132 | this.grow(this.element.find("textarea.text_cell_input")); | |
|
133 | }; | |
|
134 | } | |
|
135 | ||
|
136 | ||
|
137 | TextCell.prototype.toJSON = function () { | |
|
138 | return { | |
|
139 | cell_type : 'text', | |
|
140 | text : this.get_text(), | |
|
141 | }; | |
|
142 | }; | |
|
143 | ||
|
144 |
@@ -0,0 +1,62 b'' | |||
|
1 | ||
|
2 | //============================================================================ | |
|
3 | // Utilities | |
|
4 | //============================================================================ | |
|
5 | ||
|
6 | ||
|
7 | var uuid = function () { | |
|
8 | // http://www.ietf.org/rfc/rfc4122.txt | |
|
9 | var s = []; | |
|
10 | var hexDigits = "0123456789ABCDEF"; | |
|
11 | for (var i = 0; i < 32; i++) { | |
|
12 | s[i] = hexDigits.substr(Math.floor(Math.random() * 0x10), 1); | |
|
13 | } | |
|
14 | s[12] = "4"; // bits 12-15 of the time_hi_and_version field to 0010 | |
|
15 | s[16] = hexDigits.substr((s[16] & 0x3) | 0x8, 1); // bits 6-7 of the clock_seq_hi_and_reserved to 01 | |
|
16 | ||
|
17 | var uuid = s.join(""); | |
|
18 | return uuid; | |
|
19 | }; | |
|
20 | ||
|
21 | ||
|
22 | //Fix raw text to parse correctly in crazy XML | |
|
23 | function xmlencode(string) { | |
|
24 | return string.replace(/\&/g,'&'+'amp;') | |
|
25 | .replace(/</g,'&'+'lt;') | |
|
26 | .replace(/>/g,'&'+'gt;') | |
|
27 | .replace(/\'/g,'&'+'apos;') | |
|
28 | .replace(/\"/g,'&'+'quot;') | |
|
29 | .replace(/`/g,'&'+'#96;') | |
|
30 | } | |
|
31 | ||
|
32 | //Map from terminal commands to CSS classes | |
|
33 | attrib = { | |
|
34 | "30":"cblack", "31":"cred", | |
|
35 | "32":"cgreen", "33":"cyellow", | |
|
36 | "34":"cblue", "36":"ccyan", | |
|
37 | "37":"cwhite", "01":"cbold"} | |
|
38 | ||
|
39 | //Fixes escaped console commands, IE colors. Turns them into HTML | |
|
40 | function fixConsole(txt) { | |
|
41 | txt = xmlencode(txt) | |
|
42 | var re = /\033\[([\d;]*?)m/ | |
|
43 | var opened = false | |
|
44 | var cmds = [] | |
|
45 | var opener = "" | |
|
46 | var closer = "" | |
|
47 | ||
|
48 | while (re.test(txt)) { | |
|
49 | var cmds = txt.match(re)[1].split(";") | |
|
50 | closer = opened?"</span>":"" | |
|
51 | opened = cmds.length > 1 || cmds[0] != 0 | |
|
52 | var rep = [] | |
|
53 | for (var i in cmds) | |
|
54 | if (typeof(attrib[cmds[i]]) != "undefined") | |
|
55 | rep.push(attrib[cmds[i]]) | |
|
56 | opener = rep.length > 0?"<span class=\""+rep.join(" ")+"\">":"" | |
|
57 | txt = txt.replace(re, closer + opener) | |
|
58 | } | |
|
59 | if (opened) txt += "</span>" | |
|
60 | return txt.trim() | |
|
61 | } | |
|
62 |
This diff has been collapsed as it changes many lines, (637 lines changed) Show them Hide them | |||
@@ -1,67 +1,3 b'' | |||
|
1 | var IPYTHON = {}; | |
|
2 | ||
|
3 | ||
|
4 | //============================================================================ | |
|
5 | // Utilities | |
|
6 | //============================================================================ | |
|
7 | ||
|
8 | ||
|
9 | var uuid = function () { | |
|
10 | // http://www.ietf.org/rfc/rfc4122.txt | |
|
11 | var s = []; | |
|
12 | var hexDigits = "0123456789ABCDEF"; | |
|
13 | for (var i = 0; i < 32; i++) { | |
|
14 | s[i] = hexDigits.substr(Math.floor(Math.random() * 0x10), 1); | |
|
15 | } | |
|
16 | s[12] = "4"; // bits 12-15 of the time_hi_and_version field to 0010 | |
|
17 | s[16] = hexDigits.substr((s[16] & 0x3) | 0x8, 1); // bits 6-7 of the clock_seq_hi_and_reserved to 01 | |
|
18 | ||
|
19 | var uuid = s.join(""); | |
|
20 | return uuid; | |
|
21 | }; | |
|
22 | ||
|
23 | ||
|
24 | //Fix raw text to parse correctly in crazy XML | |
|
25 | function xmlencode(string) { | |
|
26 | return string.replace(/\&/g,'&'+'amp;') | |
|
27 | .replace(/</g,'&'+'lt;') | |
|
28 | .replace(/>/g,'&'+'gt;') | |
|
29 | .replace(/\'/g,'&'+'apos;') | |
|
30 | .replace(/\"/g,'&'+'quot;') | |
|
31 | .replace(/`/g,'&'+'#96;') | |
|
32 | } | |
|
33 | ||
|
34 | //Map from terminal commands to CSS classes | |
|
35 | attrib = { | |
|
36 | "30":"cblack", "31":"cred", | |
|
37 | "32":"cgreen", "33":"cyellow", | |
|
38 | "34":"cblue", "36":"ccyan", | |
|
39 | "37":"cwhite", "01":"cbold"} | |
|
40 | ||
|
41 | //Fixes escaped console commands, IE colors. Turns them into HTML | |
|
42 | function fixConsole(txt) { | |
|
43 | txt = xmlencode(txt) | |
|
44 | var re = /\033\[([\d;]*?)m/ | |
|
45 | var opened = false | |
|
46 | var cmds = [] | |
|
47 | var opener = "" | |
|
48 | var closer = "" | |
|
49 | ||
|
50 | while (re.test(txt)) { | |
|
51 | var cmds = txt.match(re)[1].split(";") | |
|
52 | closer = opened?"</span>":"" | |
|
53 | opened = cmds.length > 1 || cmds[0] != 0 | |
|
54 | var rep = [] | |
|
55 | for (var i in cmds) | |
|
56 | if (typeof(attrib[cmds[i]]) != "undefined") | |
|
57 | rep.push(attrib[cmds[i]]) | |
|
58 | opener = rep.length > 0?"<span class=\""+rep.join(" ")+"\">":"" | |
|
59 | txt = txt.replace(re, closer + opener) | |
|
60 | } | |
|
61 | if (opened) txt += "</span>" | |
|
62 | return txt.trim() | |
|
63 | } | |
|
64 | ||
|
65 | 1 | |
|
66 | 2 |
|
|
67 | 3 | // Notebook |
@@ -570,576 +506,3 b' Notebook.prototype.load_notebook = function (filename) {' | |||
|
570 | 506 | $.ajax("/notebooks/" + filename, settings); |
|
571 | 507 | } |
|
572 | 508 | |
|
573 | ||
|
574 | //============================================================================ | |
|
575 | // Cell | |
|
576 | //============================================================================ | |
|
577 | ||
|
578 | ||
|
579 | var Cell = function (notebook) { | |
|
580 | this.notebook = notebook; | |
|
581 | this.selected = false; | |
|
582 | this.element; | |
|
583 | this.create_element(); | |
|
584 | if (this.element !== undefined) { | |
|
585 | this.element.data("cell", this); | |
|
586 | this.bind_events(); | |
|
587 | } | |
|
588 | this.cell_id = uuid(); | |
|
589 | }; | |
|
590 | ||
|
591 | ||
|
592 | Cell.prototype.grow = function(element) { | |
|
593 | // Grow the cell by hand. This is used upon reloading from JSON, when the | |
|
594 | // autogrow handler is not called. | |
|
595 | var dom = element.get(0); | |
|
596 | var lines_count = 0; | |
|
597 | // modified split rule from | |
|
598 | // http://stackoverflow.com/questions/2035910/how-to-get-the-number-of-lines-in-a-textarea/2036424#2036424 | |
|
599 | var lines = dom.value.split(/\r|\r\n|\n/); | |
|
600 | lines_count = lines.length; | |
|
601 | if (lines_count >= 1) { | |
|
602 | dom.rows = lines_count; | |
|
603 | } else { | |
|
604 | dom.rows = 1; | |
|
605 | } | |
|
606 | }; | |
|
607 | ||
|
608 | ||
|
609 | Cell.prototype.select = function () { | |
|
610 | this.element.addClass('ui-widget-content ui-corner-all'); | |
|
611 | this.selected = true; | |
|
612 | // TODO: we need t test across browsers to see if both of these are needed. | |
|
613 | // In the meantime, there should not be any harm in having them both. | |
|
614 | this.element.find('textarea').trigger('focusin'); | |
|
615 | this.element.find('textarea').trigger('focus'); | |
|
616 | }; | |
|
617 | ||
|
618 | ||
|
619 | Cell.prototype.unselect = function () { | |
|
620 | this.element.removeClass('ui-widget-content ui-corner-all'); | |
|
621 | this.selected = false; | |
|
622 | }; | |
|
623 | ||
|
624 | ||
|
625 | Cell.prototype.bind_events = function () { | |
|
626 | var that = this; | |
|
627 | var nb = that.notebook | |
|
628 | that.element.click(function (event) { | |
|
629 | if (that.selected === false) { | |
|
630 | nb.select(nb.find_cell_index(that)); | |
|
631 | }; | |
|
632 | }); | |
|
633 | that.element.focusin(function (event) { | |
|
634 | if (that.selected === false) { | |
|
635 | nb.select(nb.find_cell_index(that)); | |
|
636 | }; | |
|
637 | }); | |
|
638 | }; | |
|
639 | ||
|
640 | ||
|
641 | // Subclasses must implement create_element. | |
|
642 | Cell.prototype.create_element = function () {}; | |
|
643 | ||
|
644 | ||
|
645 | //============================================================================ | |
|
646 | // CodeCell | |
|
647 | //============================================================================ | |
|
648 | ||
|
649 | ||
|
650 | var CodeCell = function (notebook) { | |
|
651 | this.code_mirror = null; | |
|
652 | this.input_prompt_number = ' '; | |
|
653 | Cell.apply(this, arguments); | |
|
654 | }; | |
|
655 | ||
|
656 | ||
|
657 | CodeCell.prototype = new Cell(); | |
|
658 | ||
|
659 | ||
|
660 | CodeCell.prototype.create_element = function () { | |
|
661 | var cell = $('<div></div>').addClass('cell code_cell vbox border-box-sizing'); | |
|
662 | var input = $('<div></div>').addClass('input hbox border-box-sizing'); | |
|
663 | input.append($('<div/>').addClass('prompt input_prompt monospace-font')); | |
|
664 | var input_area = $('<div/>').addClass('input_area box-flex1 border-box-sizing'); | |
|
665 | this.code_mirror = CodeMirror(input_area.get(0), { | |
|
666 | indentUnit : 4, | |
|
667 | enterMode : 'flat', | |
|
668 | tabMode: 'shift' | |
|
669 | }); | |
|
670 | input.append(input_area); | |
|
671 | var output = $('<div></div>').addClass('output vbox border-box-sizing'); | |
|
672 | cell.append(input).append(output); | |
|
673 | this.element = cell; | |
|
674 | this.collapse() | |
|
675 | }; | |
|
676 | ||
|
677 | ||
|
678 | CodeCell.prototype.select = function () { | |
|
679 | Cell.prototype.select.apply(this); | |
|
680 | this.code_mirror.focus(); | |
|
681 | }; | |
|
682 | ||
|
683 | ||
|
684 | CodeCell.prototype.append_pyout = function (data, n) { | |
|
685 | var toinsert = $("<div/>").addClass("output_area output_pyout hbox monospace-font"); | |
|
686 | toinsert.append($('<div/>'). | |
|
687 | addClass('prompt output_prompt'). | |
|
688 | html('Out[' + n + ']:') | |
|
689 | ); | |
|
690 | this.append_display_data(data, toinsert); | |
|
691 | toinsert.children().last().addClass("box_flex1"); | |
|
692 | this.element.find("div.output").append(toinsert); | |
|
693 | // If we just output latex, typeset it. | |
|
694 | if (data["text/latex"] !== undefined) { | |
|
695 | MathJax.Hub.Queue(["Typeset",MathJax.Hub]); | |
|
696 | }; | |
|
697 | }; | |
|
698 | ||
|
699 | ||
|
700 | CodeCell.prototype.append_pyerr = function (ename, evalue, tb) { | |
|
701 | var s = ''; | |
|
702 | var len = tb.length; | |
|
703 | for (var i=0; i<len; i++) { | |
|
704 | s = s + tb[i] + '\n'; | |
|
705 | } | |
|
706 | s = s + '\n'; | |
|
707 | this.append_stream(s); | |
|
708 | }; | |
|
709 | ||
|
710 | ||
|
711 | CodeCell.prototype.append_display_data = function (data, element) { | |
|
712 | console.log(data); | |
|
713 | if (data["text/latex"] !== undefined) { | |
|
714 | this.append_latex(data["text/latex"], element); | |
|
715 | // If it is undefined, then we just appended to div.output, which | |
|
716 | // makes the latex visible and we can typeset it. The typesetting | |
|
717 | // has to be done after the latex is on the page. | |
|
718 | if (element === undefined) { | |
|
719 | MathJax.Hub.Queue(["Typeset",MathJax.Hub]); | |
|
720 | }; | |
|
721 | } else if (data["image/svg+xml"] !== undefined) { | |
|
722 | this.append_svg(data["image/svg+xml"], element); | |
|
723 | } else if (data["image/png"] !== undefined) { | |
|
724 | this.append_png(data["image/png"], element); | |
|
725 | } else if (data["text/plain"] !== undefined) { | |
|
726 | this.append_stream(data["text/plain"], element); | |
|
727 | }; | |
|
728 | return element; | |
|
729 | }; | |
|
730 | ||
|
731 | ||
|
732 | CodeCell.prototype.append_stream = function (data, element) { | |
|
733 | element = element || this.element.find("div.output"); | |
|
734 | var toinsert = $("<div/>").addClass("output_area output_stream monospace-font"); | |
|
735 | toinsert.append($("<pre/>").addClass("monospace-font").html(fixConsole(data))); | |
|
736 | element.append(toinsert); | |
|
737 | return element; | |
|
738 | }; | |
|
739 | ||
|
740 | ||
|
741 | CodeCell.prototype.append_svg = function (svg, element) { | |
|
742 | element = element || this.element.find("div.output"); | |
|
743 | var toinsert = $("<div/>").addClass("output_area output_svg"); | |
|
744 | toinsert.append(svg); | |
|
745 | element.append(toinsert); | |
|
746 | return element; | |
|
747 | }; | |
|
748 | ||
|
749 | ||
|
750 | CodeCell.prototype.append_png = function (png, element) { | |
|
751 | element = element || this.element.find("div.output"); | |
|
752 | var toinsert = $("<div/>").addClass("output_area output_png"); | |
|
753 | toinsert.append($("<img/>").attr('src','data:image/png;base64,'+png)); | |
|
754 | element.append(toinsert); | |
|
755 | return element; | |
|
756 | }; | |
|
757 | ||
|
758 | ||
|
759 | CodeCell.prototype.append_latex = function (latex, element) { | |
|
760 | // This method cannot do the typesetting because the latex first has to | |
|
761 | // be on the page. | |
|
762 | element = element || this.element.find("div.output"); | |
|
763 | var toinsert = $("<div/>").addClass("output_area output_latex monospace-font"); | |
|
764 | toinsert.append(latex); | |
|
765 | element.append(toinsert); | |
|
766 | return element; | |
|
767 | } | |
|
768 | ||
|
769 | ||
|
770 | CodeCell.prototype.clear_output = function () { | |
|
771 | this.element.find("div.output").html(""); | |
|
772 | }; | |
|
773 | ||
|
774 | ||
|
775 | CodeCell.prototype.collapse = function () { | |
|
776 | this.element.find('div.output').hide(); | |
|
777 | }; | |
|
778 | ||
|
779 | ||
|
780 | CodeCell.prototype.expand = function () { | |
|
781 | this.element.find('div.output').show(); | |
|
782 | }; | |
|
783 | ||
|
784 | ||
|
785 | CodeCell.prototype.set_input_prompt = function (number) { | |
|
786 | var n = number || ' '; | |
|
787 | this.input_prompt_number = n | |
|
788 | this.element.find('div.input_prompt').html('In [' + n + ']:'); | |
|
789 | }; | |
|
790 | ||
|
791 | ||
|
792 | CodeCell.prototype.get_code = function () { | |
|
793 | return this.code_mirror.getValue(); | |
|
794 | }; | |
|
795 | ||
|
796 | ||
|
797 | CodeCell.prototype.set_code = function (code) { | |
|
798 | return this.code_mirror.setValue(code); | |
|
799 | }; | |
|
800 | ||
|
801 | ||
|
802 | CodeCell.prototype.at_top = function () { | |
|
803 | var cursor = this.code_mirror.getCursor(); | |
|
804 | if (cursor.line === 0) { | |
|
805 | return true; | |
|
806 | } else { | |
|
807 | return false; | |
|
808 | } | |
|
809 | }; | |
|
810 | ||
|
811 | ||
|
812 | CodeCell.prototype.at_bottom = function () { | |
|
813 | var cursor = this.code_mirror.getCursor(); | |
|
814 | if (cursor.line === (this.code_mirror.lineCount()-1)) { | |
|
815 | return true; | |
|
816 | } else { | |
|
817 | return false; | |
|
818 | } | |
|
819 | }; | |
|
820 | ||
|
821 | ||
|
822 | CodeCell.prototype.fromJSON = function (data) { | |
|
823 | if (data.cell_type === 'code') { | |
|
824 | this.set_code(data.code); | |
|
825 | this.set_input_prompt(data.prompt_number); | |
|
826 | }; | |
|
827 | }; | |
|
828 | ||
|
829 | ||
|
830 | CodeCell.prototype.toJSON = function () { | |
|
831 | return { | |
|
832 | code : this.get_code(), | |
|
833 | cell_type : 'code', | |
|
834 | prompt_number : this.input_prompt_number | |
|
835 | }; | |
|
836 | }; | |
|
837 | ||
|
838 | //============================================================================ | |
|
839 | // TextCell | |
|
840 | //============================================================================ | |
|
841 | ||
|
842 | ||
|
843 | var TextCell = function (notebook) { | |
|
844 | Cell.apply(this, arguments); | |
|
845 | this.placeholder = "Type <strong>HTML</strong> and LaTeX: $\\alpha^2$" | |
|
846 | this.rendered = false; | |
|
847 | }; | |
|
848 | ||
|
849 | ||
|
850 | TextCell.prototype = new Cell(); | |
|
851 | ||
|
852 | ||
|
853 | TextCell.prototype.create_element = function () { | |
|
854 | var cell = $("<div>").addClass('cell text_cell'). | |
|
855 | append( | |
|
856 | $("<textarea>" + this.placeholder + "</textarea>"). | |
|
857 | addClass('text_cell_input monospace-font'). | |
|
858 | attr('rows',1). | |
|
859 | attr('cols',80). | |
|
860 | autogrow() | |
|
861 | ).append( | |
|
862 | // The tabindex=-1 makes this div focusable. | |
|
863 | $('<div></div>').addClass('text_cell_render').attr('tabindex','-1') | |
|
864 | ) | |
|
865 | this.element = cell; | |
|
866 | }; | |
|
867 | ||
|
868 | ||
|
869 | TextCell.prototype.bind_events = function () { | |
|
870 | Cell.prototype.bind_events.apply(this); | |
|
871 | var that = this; | |
|
872 | this.element.keydown(function (event) { | |
|
873 | if (event.which === 13) { | |
|
874 | if (that.rendered) { | |
|
875 | that.edit(); | |
|
876 | event.preventDefault(); | |
|
877 | }; | |
|
878 | }; | |
|
879 | }); | |
|
880 | }; | |
|
881 | ||
|
882 | ||
|
883 | TextCell.prototype.select = function () { | |
|
884 | Cell.prototype.select.apply(this); | |
|
885 | var output = this.element.find("div.text_cell_render"); | |
|
886 | output.trigger('focus'); | |
|
887 | }; | |
|
888 | ||
|
889 | ||
|
890 | TextCell.prototype.edit = function () { | |
|
891 | if (this.rendered === true) { | |
|
892 | var text_cell = this.element; | |
|
893 | var input = text_cell.find("textarea.text_cell_input"); | |
|
894 | var output = text_cell.find("div.text_cell_render"); | |
|
895 | output.hide(); | |
|
896 | input.show().trigger('focus'); | |
|
897 | this.rendered = false; | |
|
898 | }; | |
|
899 | }; | |
|
900 | ||
|
901 | ||
|
902 | TextCell.prototype.render = function () { | |
|
903 | if (this.rendered === false) { | |
|
904 | var text_cell = this.element; | |
|
905 | var input = text_cell.find("textarea.text_cell_input"); | |
|
906 | var output = text_cell.find("div.text_cell_render"); | |
|
907 | var text = input.val(); | |
|
908 | if (text === "") { | |
|
909 | text = this.placeholder; | |
|
910 | input.val(text); | |
|
911 | }; | |
|
912 | output.html(text) | |
|
913 | input.html(text); | |
|
914 | MathJax.Hub.Queue(["Typeset",MathJax.Hub]); | |
|
915 | input.hide(); | |
|
916 | output.show(); | |
|
917 | this.rendered = true; | |
|
918 | }; | |
|
919 | }; | |
|
920 | ||
|
921 | ||
|
922 | TextCell.prototype.config_mathjax = function () { | |
|
923 | var text_cell = this.element; | |
|
924 | var that = this; | |
|
925 | text_cell.click(function () { | |
|
926 | that.edit(); | |
|
927 | }).focusout(function () { | |
|
928 | that.render(); | |
|
929 | }); | |
|
930 | ||
|
931 | text_cell.trigger("focusout"); | |
|
932 | }; | |
|
933 | ||
|
934 | ||
|
935 | TextCell.prototype.get_text = function() { | |
|
936 | return this.element.find("textarea.text_cell_input").val(); | |
|
937 | }; | |
|
938 | ||
|
939 | ||
|
940 | TextCell.prototype.set_text = function(text) { | |
|
941 | this.element.find("textarea.text_cell_input").val(text); | |
|
942 | this.element.find("textarea.text_cell_input").html(text); | |
|
943 | this.element.find("div.text_cell_render").html(text); | |
|
944 | }; | |
|
945 | ||
|
946 | ||
|
947 | TextCell.prototype.at_top = function () { | |
|
948 | if (this.rendered) { | |
|
949 | return true; | |
|
950 | } else { | |
|
951 | return false; | |
|
952 | } | |
|
953 | }; | |
|
954 | ||
|
955 | ||
|
956 | TextCell.prototype.at_bottom = function () { | |
|
957 | if (this.rendered) { | |
|
958 | return true; | |
|
959 | } else { | |
|
960 | return false; | |
|
961 | } | |
|
962 | }; | |
|
963 | ||
|
964 | ||
|
965 | TextCell.prototype.fromJSON = function (data) { | |
|
966 | if (data.cell_type === 'text') { | |
|
967 | this.set_text(data.text); | |
|
968 | this.grow(this.element.find("textarea.text_cell_input")); | |
|
969 | }; | |
|
970 | } | |
|
971 | ||
|
972 | ||
|
973 | TextCell.prototype.toJSON = function () { | |
|
974 | return { | |
|
975 | cell_type : 'text', | |
|
976 | text : this.get_text(), | |
|
977 | }; | |
|
978 | }; | |
|
979 | ||
|
980 | //============================================================================ | |
|
981 | // On document ready | |
|
982 | //============================================================================ | |
|
983 | ||
|
984 | ||
|
985 | var Kernel = function () { | |
|
986 | this.kernel_id = null; | |
|
987 | this.base_url = "/kernels"; | |
|
988 | this.kernel_url = null; | |
|
989 | }; | |
|
990 | ||
|
991 | ||
|
992 | Kernel.prototype.get_msg = function (msg_type, content) { | |
|
993 | var msg = { | |
|
994 | header : { | |
|
995 | msg_id : uuid(), | |
|
996 | username : "bgranger", | |
|
997 | session: this.session_id, | |
|
998 | msg_type : msg_type | |
|
999 | }, | |
|
1000 | content : content, | |
|
1001 | parent_header : {} | |
|
1002 | }; | |
|
1003 | return msg; | |
|
1004 | } | |
|
1005 | ||
|
1006 | Kernel.prototype.start_kernel = function (callback, context) { | |
|
1007 | var that = this; | |
|
1008 | $.post(this.base_url, | |
|
1009 | function (kernel_id) { | |
|
1010 | that._handle_start_kernel(kernel_id, callback, context); | |
|
1011 | }, | |
|
1012 | 'json' | |
|
1013 | ); | |
|
1014 | }; | |
|
1015 | ||
|
1016 | ||
|
1017 | Kernel.prototype._handle_start_kernel = function (kernel_id, callback, context) { | |
|
1018 | this.kernel_id = kernel_id; | |
|
1019 | this.kernel_url = this.base_url + "/" + this.kernel_id; | |
|
1020 | this._start_channels(); | |
|
1021 | callback.call(context); | |
|
1022 | }; | |
|
1023 | ||
|
1024 | ||
|
1025 | Kernel.prototype._start_channels = function () { | |
|
1026 | var ws_url = "ws://127.0.0.1:8888" + this.kernel_url; | |
|
1027 | this.shell_channel = new WebSocket(ws_url + "/shell"); | |
|
1028 | this.iopub_channel = new WebSocket(ws_url + "/iopub"); | |
|
1029 | } | |
|
1030 | ||
|
1031 | ||
|
1032 | Kernel.prototype.execute = function (code) { | |
|
1033 | var content = { | |
|
1034 | code : code, | |
|
1035 | silent : false, | |
|
1036 | user_variables : [], | |
|
1037 | user_expressions : {} | |
|
1038 | }; | |
|
1039 | var msg = this.get_msg("execute_request", content); | |
|
1040 | this.shell_channel.send(JSON.stringify(msg)); | |
|
1041 | return msg.header.msg_id; | |
|
1042 | } | |
|
1043 | ||
|
1044 | ||
|
1045 | Kernel.prototype.interrupt = function () { | |
|
1046 | $.post(this.kernel_url + "/interrupt"); | |
|
1047 | }; | |
|
1048 | ||
|
1049 | ||
|
1050 | Kernel.prototype.restart = function () { | |
|
1051 | this.status_restarting(); | |
|
1052 | url = this.kernel_url + "/restart" | |
|
1053 | var that = this; | |
|
1054 | $.post(url, function (kernel_id) { | |
|
1055 | console.log("Kernel restarted: " + kernel_id); | |
|
1056 | that.kernel_id = kernel_id; | |
|
1057 | that.kernel_url = that.base_url + "/" + that.kernel_id; | |
|
1058 | that.status_idle(); | |
|
1059 | }, 'json'); | |
|
1060 | }; | |
|
1061 | ||
|
1062 | ||
|
1063 | Kernel.prototype.status_busy = function () { | |
|
1064 | $("#kernel_status").removeClass("status_idle"); | |
|
1065 | $("#kernel_status").removeClass("status_restarting"); | |
|
1066 | $("#kernel_status").addClass("status_busy"); | |
|
1067 | $("#kernel_status").text("Busy"); | |
|
1068 | }; | |
|
1069 | ||
|
1070 | ||
|
1071 | Kernel.prototype.status_idle = function () { | |
|
1072 | $("#kernel_status").removeClass("status_busy"); | |
|
1073 | $("#kernel_status").removeClass("status_restarting"); | |
|
1074 | $("#kernel_status").addClass("status_idle"); | |
|
1075 | $("#kernel_status").text("Idle"); | |
|
1076 | }; | |
|
1077 | ||
|
1078 | Kernel.prototype.status_restarting = function () { | |
|
1079 | $("#kernel_status").removeClass("status_busy"); | |
|
1080 | $("#kernel_status").removeClass("status_idle"); | |
|
1081 | $("#kernel_status").addClass("status_restarting"); | |
|
1082 | $("#kernel_status").text("Restarting"); | |
|
1083 | }; | |
|
1084 | ||
|
1085 | //============================================================================ | |
|
1086 | // On document ready | |
|
1087 | //============================================================================ | |
|
1088 | ||
|
1089 | ||
|
1090 | $(document).ready(function () { | |
|
1091 | ||
|
1092 | $('div#wrapper').addClass('vbox border-box-sizing') | |
|
1093 | $('div.notebook').addClass('box-flex1 border-box-sizing') | |
|
1094 | ||
|
1095 | MathJax.Hub.Config({ | |
|
1096 | tex2jax: { | |
|
1097 | inlineMath: [ ['$','$'], ["\\(","\\)"] ], | |
|
1098 | displayMath: [ ['$$','$$'], ["\\[","\\]"] ], | |
|
1099 | }, | |
|
1100 | displayAlign: 'left', // Change this to 'center' to center equations. | |
|
1101 | "HTML-CSS": { | |
|
1102 | styles: {'.MathJax_Display': {"margin": 0}} | |
|
1103 | } | |
|
1104 | }); | |
|
1105 | ||
|
1106 | IPYTHON.notebook = new Notebook('div.notebook'); | |
|
1107 | IPYTHON.notebook.insert_code_cell_after(); | |
|
1108 | ||
|
1109 | $("#menu_tabs").tabs(); | |
|
1110 | ||
|
1111 | $("#help_toolbar").buttonset(); | |
|
1112 | ||
|
1113 | $("#kernel_toolbar").buttonset(); | |
|
1114 | $("#interrupt_kernel").click(function () {IPYTHON.notebook.kernel.interrupt();}); | |
|
1115 | $("#restart_kernel").click(function () {IPYTHON.notebook.kernel.restart();}); | |
|
1116 | $("#kernel_status").addClass("status_idle"); | |
|
1117 | ||
|
1118 | $("#move_cell").buttonset(); | |
|
1119 | $("#move_up").button("option", "icons", {primary:"ui-icon-arrowthick-1-n"}); | |
|
1120 | $("#move_up").button("option", "text", false); | |
|
1121 | $("#move_up").click(function () {IPYTHON.notebook.move_cell_up();}); | |
|
1122 | $("#move_down").button("option", "icons", {primary:"ui-icon-arrowthick-1-s"}); | |
|
1123 | $("#move_down").button("option", "text", false); | |
|
1124 | $("#move_down").click(function () {IPYTHON.notebook.move_cell_down();}); | |
|
1125 | ||
|
1126 | $("#insert_delete").buttonset(); | |
|
1127 | $("#insert_cell_before").click(function () {IPYTHON.notebook.insert_code_cell_before();}); | |
|
1128 | $("#insert_cell_after").click(function () {IPYTHON.notebook.insert_code_cell_after();}); | |
|
1129 | $("#delete_cell").button("option", "icons", {primary:"ui-icon-closethick"}); | |
|
1130 | $("#delete_cell").button("option", "text", false); | |
|
1131 | $("#delete_cell").click(function () {IPYTHON.notebook.delete_cell();}); | |
|
1132 | ||
|
1133 | $("#cell_type").buttonset(); | |
|
1134 | $("#to_code").click(function () {IPYTHON.notebook.text_to_code();}); | |
|
1135 | $("#to_text").click(function () {IPYTHON.notebook.code_to_text();}); | |
|
1136 | ||
|
1137 | $("#sort").buttonset(); | |
|
1138 | $("#sort_cells").click(function () {IPYTHON.notebook.sort_cells();}); | |
|
1139 | ||
|
1140 | $("#toggle").buttonset(); | |
|
1141 | $("#collapse").click(function () {IPYTHON.notebook.collapse();}); | |
|
1142 | $("#expand").click(function () {IPYTHON.notebook.expand();}); | |
|
1143 | ||
|
1144 | }); | |
|
1145 |
General Comments 0
You need to be logged in to leave comments.
Login now