Added in cancel on distance
MODIFY
src/mapInteractor.js
src/mapInteractor.js
@@ -24,8 +24,9 @@ var Mousetrap = require('mousetrap');
* @property {number} [click.duration=0] If a positive number, the mouse up
* event must occur within this time in milliseconds of the mouse down
* event for it to be considered a click.
- * @property {boolean} [click.cancelOnMove=true] If truthy, don't generate
- * click events if the mouse moved at all.
+ * @property {boolean|number} [click.cancelOnMove=true] If truthy, don't generate
+ * click events if the mouse moved at all. If a positive number, the distance
+ * at which to cancel click events when the mouse moves.
* @property {object} [keyboard] An object describing which keyboard events are
* handled.
* @property {object} [keyboard.actions] An object with different actions that
@@ -1229,10 +1230,19 @@ var mapInteractor = function (args) {
m_this._getMouseModifiers(evt);
/* Only cancel possible clicks on move if we actually moved */
- if (m_options.click.cancelOnMove && (m_clickMaybe.x === undefined ||
- m_mouse.page.x !== m_clickMaybe.x ||
+ if (m_options.click.cancelOnMove) {
+ if (m_clickMaybe.x === undefined || m_clickMaybe.y === undefined) {
+ m_this._setClickMaybe(false);
+ } else if (m_options.click.cancelOnMove === true &&
+ (m_mouse.page.x !== m_clickMaybe.x ||
m_mouse.page.y !== m_clickMaybe.y)) {
m_this._setClickMaybe(false);
+ } else {
+ const dist = Math.sqrt((m_mouse.page.x - m_clickMaybe.x) ** 2 + (m_mouse.page.y - m_clickMaybe.y) ** 2);
+ if (dist >= m_options.click.cancelOnMove) {
+ m_this._setClickMaybe(false);
+ }
+ }
}
if (m_clickMaybe) {
return;

MODIFY
tests/cases/mapInteractor.js
tests/cases/mapInteractor.js
@@ -972,6 +972,93 @@ describe('mapInteractor', function () {
});
expect(triggered).toBe(1);
});
+ it('not triggered by move distance greater than cancelOnMove then click', function () {
+ var map = mockedMap('#mapNode1'),
+ interactor = geo.mapInteractor({
+ map: map,
+ click: {
+ enabled: true,
+ cancelOnMove: 10,
+ duration: 0
+ },
+ throttle: false
+ }), triggered = 0;
+
+ map.geoOn(geo.event.mouseclick, function () {
+ triggered += 1;
+ });
+ interactor.simulateEvent('mousedown', {
+ map: {x: 20, y: 20},
+ button: 'left'
+ });
+ interactor.simulateEvent('mousemove', {
+ map: {x: 30, y: 30},
+ button: 'left'
+ });
+ interactor.simulateEvent('mouseup', {
+ map: {x: 30, y: 30},
+ button: 'left'
+ });
+ expect(triggered).toBe(0);
+ });
+ it('triggered by move distance less than cancelOnMove then click', function () {
+ var map = mockedMap('#mapNode1'),
+ interactor = geo.mapInteractor({
+ map: map,
+ click: {
+ enabled: true,
+ cancelOnMove: 20,
+ duration: 0
+ },
+ throttle: false
+ }), triggered = 0;
+
+ map.geoOn(geo.event.mouseclick, function () {
+ triggered += 1;
+ });
+ interactor.simulateEvent('mousedown', {
+ map: {x: 20, y: 20},
+ button: 'left'
+ });
+ interactor.simulateEvent('mousemove', {
+ map: {x: 30, y: 30},
+ button: 'left'
+ });
+ interactor.simulateEvent('mouseup', {
+ map: {x: 30, y: 30},
+ button: 'left'
+ });
+ expect(triggered).toBe(1);
+ });
+ it('triggered by move distance less than cancelOnMove then click with subpixel movements', function () {
+ var map = mockedMap('#mapNode1'),
+ interactor = geo.mapInteractor({
+ map: map,
+ click: {
+ enabled: true,
+ cancelOnMove: 0.5,
+ duration: 0
+ },
+ throttle: false
+ }), triggered = 0;
+
+ map.geoOn(geo.event.mouseclick, function () {
+ triggered += 1;
+ });
+ interactor.simulateEvent('mousedown', {
+ map: {x: 20, y: 20},
+ button: 'left'
+ });
+ interactor.simulateEvent('mousemove', {
+ map: {x: 20.25, y: 20.25},
+ button: 'left'
+ });
+ interactor.simulateEvent('mouseup', {
+ map: {x: 20.25, y: 20.25},
+ button: 'left'
+ });
+ expect(triggered).toBe(1);
+ });
it('not triggered by disabled button', function () {
var map = mockedMap('#mapNode1'),
interactor = geo.mapInteractor({

Added in cancel on distance