Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 1a1b82d

Browse files
committed
Merge pull request matplotlib#3965 from tacaswell/js_fixes
Js fixes for key events + ipython notebooks
2 parents b4ec20f + fd4d913 commit 1a1b82d

File tree

3 files changed

+105
-21
lines changed

3 files changed

+105
-21
lines changed

lib/matplotlib/backends/web_backend/mpl.js

Lines changed: 40 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -40,11 +40,12 @@ mpl.figure = function(figure_id, websocket, ondownload, parent_element) {
4040
this.rubberband_context = undefined;
4141
this.format_dropdown = undefined;
4242

43-
this.focus_on_mousover = false;
4443
this.image_mode = 'full';
4544

4645
this.root = $('<div/>');
46+
this._root_extra_style(this.root)
4747
this.root.attr('style', 'display: inline-block');
48+
4849
$(parent_element).append(this.root);
4950

5051
this._init_header(this);
@@ -93,6 +94,15 @@ mpl.figure.prototype._init_header = function() {
9394
this.header = titletext[0];
9495
}
9596

97+
mpl.figure.prototype._canvas_extra_style = function(canvas_div) {
98+
99+
}
100+
101+
102+
mpl.figure.prototype._root_extra_style = function(canvas_div) {
103+
104+
}
105+
96106
mpl.figure.prototype._init_canvas = function() {
97107
var fig = this;
98108

@@ -101,17 +111,22 @@ mpl.figure.prototype._init_canvas = function() {
101111
function(event, ui) { fig.request_resize(ui.size.width, ui.size.height); }
102112
, 50)});
103113

104-
canvas_div.attr('style', 'position: relative; clear: both;');
105-
this.root.append(canvas_div);
106-
107-
var canvas = $('<canvas/>');
108-
canvas.addClass('mpl-canvas');
109-
canvas.attr('style', "left: 0; top: 0; z-index: 0;")
114+
canvas_div.attr('style', 'position: relative; clear: both; outline: 0');
110115

111116
function canvas_keyboard_event(event) {
112117
return fig.key_event(event, event['data']);
113118
}
114119

120+
canvas_div.keydown('key_press', canvas_keyboard_event);
121+
canvas_div.keydown('key_release', canvas_keyboard_event);
122+
this.canvas_div = canvas_div
123+
this._canvas_extra_style(canvas_div)
124+
this.root.append(canvas_div);
125+
126+
var canvas = $('<canvas/>');
127+
canvas.addClass('mpl-canvas');
128+
canvas.attr('style', "left: 0; top: 0; z-index: 0; outline: 0")
129+
115130
this.canvas = canvas[0];
116131
this.context = canvas[0].getContext("2d");
117132

@@ -131,9 +146,6 @@ mpl.figure.prototype._init_canvas = function() {
131146
canvas_div.append(canvas);
132147
canvas_div.append(rubberband);
133148

134-
canvas_div.keydown('key_press', canvas_keyboard_event);
135-
canvas_div.keydown('key_release', canvas_keyboard_event);
136-
137149
this.rubberband = rubberband;
138150
this.rubberband_canvas = rubberband[0];
139151
this.rubberband_context = rubberband[0].getContext("2d");
@@ -155,6 +167,13 @@ mpl.figure.prototype._init_canvas = function() {
155167
// Set the figure to an initial 600x600px, this will subsequently be updated
156168
// upon first draw.
157169
this._resize_canvas(600, 600);
170+
171+
function set_focus () {
172+
canvas.focus();
173+
canvas_div.focus();
174+
}
175+
176+
window.setTimeout(set_focus, 100);
158177
}
159178

160179
mpl.figure.prototype._init_toolbar = function() {
@@ -172,7 +191,7 @@ mpl.figure.prototype._init_toolbar = function() {
172191
return fig.toolbar_button_onmouseover(event['data']);
173192
}
174193

175-
for(var toolbar_ind in mpl.toolbar_items){
194+
for(var toolbar_ind in mpl.toolbar_items) {
176195
var name = mpl.toolbar_items[toolbar_ind][0];
177196
var tooltip = mpl.toolbar_items[toolbar_ind][1];
178197
var image = mpl.toolbar_items[toolbar_ind][2];
@@ -397,9 +416,10 @@ mpl.findpos = function(e) {
397416
mpl.figure.prototype.mouse_event = function(event, name) {
398417
var canvas_pos = mpl.findpos(event)
399418

400-
if (this.focus_on_mouseover && name === 'motion_notify')
419+
if (name === 'button_press')
401420
{
402421
this.canvas.focus();
422+
this.canvas_div.focus();
403423
}
404424

405425
var x = canvas_pos.x;
@@ -422,7 +442,7 @@ mpl.figure.prototype.key_event = function(event, name) {
422442
return;
423443
}
424444

425-
value = '';
445+
var value = '';
426446
if (event.ctrlKey) {
427447
value += "ctrl+";
428448
}
@@ -432,6 +452,7 @@ mpl.figure.prototype.key_event = function(event, name) {
432452
value += String.fromCharCode(event.keyCode).toLowerCase();
433453

434454
this.send_message(name, {key: value});
455+
return false;
435456
}
436457

437458
mpl.figure.prototype.toolbar_button_onclick = function(name) {
@@ -448,18 +469,18 @@ mpl.figure.prototype.toolbar_button_onmouseover = function(tooltip) {
448469
this.message.textContent = tooltip;
449470
};
450471

451-
mpl.debounce_event = function(func, time){
472+
mpl.debounce_event = function(func, time) {
452473
var timer;
453-
return function(event){
474+
return function(event) {
454475
clearTimeout(timer);
455-
timer = setTimeout(function(){ func(event); }, time);
476+
timer = setTimeout(function() { func(event); }, time);
456477
};
457478
}
458479

459-
mpl.debounce_resize = function(func, time){
480+
mpl.debounce_resize = function(func, time) {
460481
var timer;
461-
return function(event, ui){
482+
return function(event, ui) {
462483
clearTimeout(timer);
463-
timer = setTimeout(function(){ func(event, ui); }, time);
484+
timer = setTimeout(function() { func(event, ui); }, time);
464485
};
465486
}

lib/matplotlib/backends/web_backend/nbagg_mpl.js

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -123,6 +123,25 @@ mpl.figure.prototype._init_toolbar = function() {
123123
titlebar.prepend(buttongrp);
124124
}
125125

126+
127+
mpl.figure.prototype._canvas_extra_style = function(el){
128+
// this is important to make the div 'focusable
129+
el.attr('tabindex', 0)
130+
// reach out to IPython and tell the keyboard manager to turn it's self
131+
// off when our div gets focus
132+
133+
// location in version 3
134+
if (IPython.notebook.keyboard_manager) {
135+
IPython.notebook.keyboard_manager.register_events(el);
136+
}
137+
else {
138+
// location in version 2
139+
IPython.keyboard_manager.register_events(el);
140+
}
141+
142+
}
143+
144+
126145
mpl.find_output_cell = function(html_output) {
127146
// Return the cell and output element which can be found *uniquely* in the notebook.
128147
// Note - this is a bit hacky, but it is done because the "notebook_saving.Notebook"

lib/matplotlib/backends/web_backend/nbagg_uat.ipynb

Lines changed: 46 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,24 @@
11
{
22
"metadata": {
33
"name": "",
4-
"signature": "sha256:1d491e506b54b126f6971897d3249a9e6f96f9d50bf4e4ba8d179c6b7b1aefa8"
4+
"signature": "sha256:43daeaae8ae9fd496fc33d7a64639194bc009b755d28c23cd6329f225628197c"
55
},
66
"nbformat": 3,
77
"nbformat_minor": 0,
88
"worksheets": [
99
{
1010
"cells": [
11+
{
12+
"cell_type": "code",
13+
"collapsed": false,
14+
"input": [
15+
"from __future__ import print_function\n",
16+
"from imp import reload"
17+
],
18+
"language": "python",
19+
"metadata": {},
20+
"outputs": []
21+
},
1122
{
1223
"cell_type": "markdown",
1324
"metadata": {},
@@ -152,7 +163,7 @@
152163
"cell_type": "code",
153164
"collapsed": false,
154165
"input": [
155-
"print matplotlib.backends.backend_nbagg.connection_info()"
166+
"print(matplotlib.backends.backend_nbagg.connection_info())"
156167
],
157168
"language": "python",
158169
"metadata": {},
@@ -384,6 +395,39 @@
384395
"language": "python",
385396
"metadata": {},
386397
"outputs": []
398+
},
399+
{
400+
"cell_type": "markdown",
401+
"metadata": {},
402+
"source": [
403+
"### UAT 16 - key events\n",
404+
"\n",
405+
"Pressing any keyboard key or mouse button should cycle the line line while the figure has focus. The figure should have focus by default when it is created and re-gain it by clicking on the canvas. Clicking anywhere outside of the figure should release focus, but moving the mouse out of the figure should not release focus."
406+
]
407+
},
408+
{
409+
"cell_type": "code",
410+
"collapsed": false,
411+
"input": [
412+
"import itertools\n",
413+
"fig, ax = plt.subplots()\n",
414+
"x = np.linspace(0,10,10000)\n",
415+
"y = np.sin(x)\n",
416+
"ln, = ax.plot(x,y)\n",
417+
"evt = []\n",
418+
"colors = iter(itertools.cycle(['r', 'g', 'b', 'k', 'c']))\n",
419+
"def on_event(event):\n",
420+
" evt.append(event)\n",
421+
" ln.set_color(next(colors))\n",
422+
" fig.canvas.draw()\n",
423+
" fig.canvas.draw_idle()\n",
424+
"fig.canvas.mpl_connect('button_press_event', on_event)\n",
425+
"fig.canvas.mpl_connect('key_press_event', on_event)\n",
426+
"plt.show()"
427+
],
428+
"language": "python",
429+
"metadata": {},
430+
"outputs": []
387431
}
388432
],
389433
"metadata": {}

0 commit comments

Comments
 (0)