Skip to content

Commit 4174390

Browse files
committed
keyboard navigation cleanup, closes Leaflet#646 Leaflet#663
1 parent ccd6c29 commit 4174390

9 files changed

+218
-163
lines changed

CHANGELOG.md

+1
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ Leaflet 0.4 contains several API improvements that allow simpler, jQuery-like sy
1818
### Notable new features
1919

2020
* Added configurable **panning inertia** - after a quick pan, the map slows down in the same direction.
21+
* Added **keyboard navigation** for panning/zooming with keyboard arrows and +/- keys (by [@ericmmartinez](https://github.com/ericmmartinez)). [#663](https://github.com/CloudMade/Leaflet/pull/663) [#646](https://github.com/CloudMade/Leaflet/issues/646)
2122
* Added **polyline and polygon editing**. [#174](https://github.com/CloudMade/Leaflet/issues/174)
2223
* Added an unobtrusive **scale control**.
2324
* Added **DivIcon** class that easily allows you to create lightweight div-based markers.

build/deps.js

+1-7
Original file line numberDiff line numberDiff line change
@@ -180,15 +180,9 @@ var deps = {
180180
desc: 'Enables zooming to bounding box by shift-dragging the map.'
181181
},
182182

183-
Focus: {
184-
src: ['map/handler/Map.Focus.js'],
185-
desc: 'Enables map to gain focus.'
186-
},
187-
188183
Keyboard: {
189184
src: ['map/handler/Map.Keyboard.js'],
190-
deps: ['Focus'],
191-
desc: 'Enables keyboard pan/zoom when map is focused.'
185+
desc: 'Enables keyboard pan/zoom when the map is focused.'
192186
},
193187

194188
MarkerDrag: {

debug/leaflet-include.js

+1
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,7 @@
5151
'map/handler/Map.DoubleClickZoom.js',
5252
'map/handler/Map.ScrollWheelZoom.js',
5353
'map/handler/Map.BoxZoom.js',
54+
'map/handler/Map.Keyboard.js',
5455

5556
'layer/LayerGroup.js',
5657
'layer/FeatureGroup.js',

dist/leaflet-src.js

+135
Original file line numberDiff line numberDiff line change
@@ -6000,6 +6000,139 @@ L.Map.BoxZoom = L.Handler.extend({
60006000
L.Map.addInitHook('addHandler', 'boxZoom', L.Map.BoxZoom);
60016001

60026002

6003+
L.Map.mergeOptions({
6004+
keyboard: true,
6005+
keyboardPanOffset: 80,
6006+
keyboardZoomOffset: 1
6007+
});
6008+
6009+
L.Map.Keyboard = L.Handler.extend({
6010+
6011+
// list of e.keyCode values for particular actions
6012+
keyCodes: {
6013+
left: [37],
6014+
right: [39],
6015+
down: [40],
6016+
up: [38],
6017+
zoomIn: [187, 61, 107],
6018+
zoomOut: [189, 109, 0]
6019+
},
6020+
6021+
initialize: function (map) {
6022+
this._map = map;
6023+
6024+
this._setPanOffset(map.options.keyboardPanOffset);
6025+
this._setZoomOffset(map.options.keyboardZoomOffset);
6026+
},
6027+
6028+
addHooks: function () {
6029+
var container = this._map._container;
6030+
6031+
// make the container focusable by tabbing
6032+
if (container.tabIndex === -1) {
6033+
container.tabIndex = "0";
6034+
}
6035+
6036+
L.DomEvent
6037+
.addListener(container, 'focus', this._onFocus, this)
6038+
.addListener(container, 'blur', this._onBlur, this)
6039+
.addListener(container, 'mousedown', this._onMouseDown, this);
6040+
6041+
this._map
6042+
.on('focus', this._addHooks, this)
6043+
.on('blur', this._removeHooks, this);
6044+
},
6045+
6046+
removeHooks: function () {
6047+
this._removeHooks();
6048+
6049+
var container = this._map._container;
6050+
L.DomEvent
6051+
.removeListener(container, 'focus', this._onFocus, this)
6052+
.removeListener(container, 'blur', this._onBlur, this)
6053+
.removeListener(container, 'mousedown', this._onMouseDown, this);
6054+
6055+
this._map
6056+
.off('focus', this._addHooks, this)
6057+
.off('blur', this._removeHooks, this);
6058+
},
6059+
6060+
_onMouseDown: function () {
6061+
if (!this._focused) {
6062+
this._map._container.focus();
6063+
}
6064+
},
6065+
6066+
_onFocus: function () {
6067+
this._focused = true;
6068+
this._map.fire('focus');
6069+
},
6070+
6071+
_onBlur: function () {
6072+
this._focused = false;
6073+
this._map.fire('blur');
6074+
},
6075+
6076+
_setPanOffset: function (pan) {
6077+
var keys = this._panKeys = {},
6078+
codes = this.keyCodes,
6079+
i, len;
6080+
6081+
for (i = 0, len = codes.left.length; i < len; i++) {
6082+
keys[codes.left[i]] = [-1 * pan, 0];
6083+
}
6084+
for (i = 0, len = codes.right.length; i < len; i++) {
6085+
keys[codes.right[i]] = [pan, 0];
6086+
}
6087+
for (i = 0, len = codes.down.length; i < len; i++) {
6088+
keys[codes.down[i]] = [0, pan];
6089+
}
6090+
for (i = 0, len = codes.up.length; i < len; i++) {
6091+
keys[codes.up[i]] = [0, -1 * pan];
6092+
}
6093+
},
6094+
6095+
_setZoomOffset: function (zoom) {
6096+
var keys = this._zoomKeys = {},
6097+
codes = this.keyCodes,
6098+
i, len;
6099+
6100+
for (i = 0, len = codes.zoomIn.length; i < len; i++) {
6101+
keys[codes.zoomIn[i]] = zoom;
6102+
}
6103+
for (i = 0, len = codes.zoomOut.length; i < len; i++) {
6104+
keys[codes.zoomOut[i]] = -zoom;
6105+
}
6106+
},
6107+
6108+
_addHooks: function () {
6109+
L.DomEvent.addListener(document, 'keydown', this._onKeyDown, this);
6110+
},
6111+
6112+
_removeHooks: function () {
6113+
L.DomEvent.removeListener(document, 'keydown', this._onKeyDown, this);
6114+
},
6115+
6116+
_onKeyDown: function (e) {
6117+
var key = e.keyCode;
6118+
6119+
if (this._panKeys.hasOwnProperty(key)) {
6120+
this._map.panBy(this._panKeys[key]);
6121+
6122+
} else if (this._zoomKeys.hasOwnProperty(key)) {
6123+
this._map.setZoom(this._map.getZoom() + this._zoomKeys[key]);
6124+
6125+
} else {
6126+
return;
6127+
}
6128+
6129+
L.DomEvent.stop(e);
6130+
}
6131+
});
6132+
6133+
L.Map.addInitHook('addHandler', 'keyboard', L.Map.Keyboard);
6134+
6135+
60036136
/*
60046137
* L.Handler.MarkerDrag is used internally by L.Marker to make the markers draggable.
60056138
*/
@@ -7102,6 +7235,8 @@ L.Map.include(!(L.Transition && L.Transition.implemented()) ? {} : {
71027235
},
71037236

71047237
panBy: function (offset, options) {
7238+
offset = L.point(offset);
7239+
71057240
if (!(offset.x || offset.y)) {
71067241
return this;
71077242
}

dist/leaflet.css

+1-3
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717
}
1818
.leaflet-container {
1919
overflow: hidden;
20+
outline: 0;
2021
}
2122
.leaflet-tile,
2223
.leaflet-marker-icon,
@@ -340,9 +341,6 @@
340341
.leaflet-container {
341342
background: #ddd;
342343
}
343-
.leaflet-container-nofocus {
344-
outline:0;
345-
}
346344
.leaflet-container a {
347345
color: #0078A8;
348346
}

dist/leaflet.js

+1-1
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/map/anim/Map.PanAnimation.js

+2
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,8 @@ L.Map.include(!(L.Transition && L.Transition.implemented()) ? {} : {
2525
},
2626

2727
panBy: function (offset, options) {
28+
offset = L.point(offset);
29+
2830
if (!(offset.x || offset.y)) {
2931
return this;
3032
}

src/map/handler/Map.Focus.js

-69
This file was deleted.

0 commit comments

Comments
 (0)