project/node_modules/zrender/lib/dom/HandlerProxy.js

294 lines
10 KiB
JavaScript

import { __extends } from "tslib";
import { addEventListener, removeEventListener, normalizeEvent, getNativeEvent } from '../core/event.js';
import * as zrUtil from '../core/util.js';
import Eventful from '../core/Eventful.js';
import env from '../core/env.js';
var TOUCH_CLICK_DELAY = 300;
var globalEventSupported = env.domSupported;
var localNativeListenerNames = (function () {
var mouseHandlerNames = [
'click', 'dblclick', 'mousewheel', 'wheel', 'mouseout',
'mouseup', 'mousedown', 'mousemove', 'contextmenu'
];
var touchHandlerNames = [
'touchstart', 'touchend', 'touchmove'
];
var pointerEventNameMap = {
pointerdown: 1, pointerup: 1, pointermove: 1, pointerout: 1
};
var pointerHandlerNames = zrUtil.map(mouseHandlerNames, function (name) {
var nm = name.replace('mouse', 'pointer');
return pointerEventNameMap.hasOwnProperty(nm) ? nm : name;
});
return {
mouse: mouseHandlerNames,
touch: touchHandlerNames,
pointer: pointerHandlerNames
};
})();
var globalNativeListenerNames = {
mouse: ['mousemove', 'mouseup'],
pointer: ['pointermove', 'pointerup']
};
var wheelEventSupported = false;
function isPointerFromTouch(event) {
var pointerType = event.pointerType;
return pointerType === 'pen' || pointerType === 'touch';
}
function setTouchTimer(scope) {
scope.touching = true;
if (scope.touchTimer != null) {
clearTimeout(scope.touchTimer);
scope.touchTimer = null;
}
scope.touchTimer = setTimeout(function () {
scope.touching = false;
scope.touchTimer = null;
}, 700);
}
function markTouch(event) {
event && (event.zrByTouch = true);
}
function normalizeGlobalEvent(instance, event) {
return normalizeEvent(instance.dom, new FakeGlobalEvent(instance, event), true);
}
function isLocalEl(instance, el) {
var elTmp = el;
var isLocal = false;
while (elTmp && elTmp.nodeType !== 9
&& !(isLocal = elTmp.domBelongToZr
|| (elTmp !== el && elTmp === instance.painterRoot))) {
elTmp = elTmp.parentNode;
}
return isLocal;
}
var FakeGlobalEvent = (function () {
function FakeGlobalEvent(instance, event) {
this.stopPropagation = zrUtil.noop;
this.stopImmediatePropagation = zrUtil.noop;
this.preventDefault = zrUtil.noop;
this.type = event.type;
this.target = this.currentTarget = instance.dom;
this.pointerType = event.pointerType;
this.clientX = event.clientX;
this.clientY = event.clientY;
}
return FakeGlobalEvent;
}());
var localDOMHandlers = {
mousedown: function (event) {
event = normalizeEvent(this.dom, event);
this.__mayPointerCapture = [event.zrX, event.zrY];
this.trigger('mousedown', event);
},
mousemove: function (event) {
event = normalizeEvent(this.dom, event);
var downPoint = this.__mayPointerCapture;
if (downPoint && (event.zrX !== downPoint[0] || event.zrY !== downPoint[1])) {
this.__togglePointerCapture(true);
}
this.trigger('mousemove', event);
},
mouseup: function (event) {
event = normalizeEvent(this.dom, event);
this.__togglePointerCapture(false);
this.trigger('mouseup', event);
},
mouseout: function (event) {
event = normalizeEvent(this.dom, event);
var element = event.toElement || event.relatedTarget;
if (!isLocalEl(this, element)) {
if (this.__pointerCapturing) {
event.zrEventControl = 'no_globalout';
}
this.trigger('mouseout', event);
}
},
wheel: function (event) {
wheelEventSupported = true;
event = normalizeEvent(this.dom, event);
this.trigger('mousewheel', event);
},
mousewheel: function (event) {
if (wheelEventSupported) {
return;
}
event = normalizeEvent(this.dom, event);
this.trigger('mousewheel', event);
},
touchstart: function (event) {
event = normalizeEvent(this.dom, event);
markTouch(event);
this.__lastTouchMoment = new Date();
this.handler.processGesture(event, 'start');
localDOMHandlers.mousemove.call(this, event);
localDOMHandlers.mousedown.call(this, event);
},
touchmove: function (event) {
event = normalizeEvent(this.dom, event);
markTouch(event);
this.handler.processGesture(event, 'change');
localDOMHandlers.mousemove.call(this, event);
},
touchend: function (event) {
event = normalizeEvent(this.dom, event);
markTouch(event);
this.handler.processGesture(event, 'end');
localDOMHandlers.mouseup.call(this, event);
if (+new Date() - (+this.__lastTouchMoment) < TOUCH_CLICK_DELAY) {
localDOMHandlers.click.call(this, event);
}
},
pointerdown: function (event) {
localDOMHandlers.mousedown.call(this, event);
},
pointermove: function (event) {
if (!isPointerFromTouch(event)) {
localDOMHandlers.mousemove.call(this, event);
}
},
pointerup: function (event) {
localDOMHandlers.mouseup.call(this, event);
},
pointerout: function (event) {
if (!isPointerFromTouch(event)) {
localDOMHandlers.mouseout.call(this, event);
}
}
};
zrUtil.each(['click', 'dblclick', 'contextmenu'], function (name) {
localDOMHandlers[name] = function (event) {
event = normalizeEvent(this.dom, event);
this.trigger(name, event);
};
});
var globalDOMHandlers = {
pointermove: function (event) {
if (!isPointerFromTouch(event)) {
globalDOMHandlers.mousemove.call(this, event);
}
},
pointerup: function (event) {
globalDOMHandlers.mouseup.call(this, event);
},
mousemove: function (event) {
this.trigger('mousemove', event);
},
mouseup: function (event) {
var pointerCaptureReleasing = this.__pointerCapturing;
this.__togglePointerCapture(false);
this.trigger('mouseup', event);
if (pointerCaptureReleasing) {
event.zrEventControl = 'only_globalout';
this.trigger('mouseout', event);
}
}
};
function mountLocalDOMEventListeners(instance, scope) {
var domHandlers = scope.domHandlers;
if (env.pointerEventsSupported) {
zrUtil.each(localNativeListenerNames.pointer, function (nativeEventName) {
mountSingleDOMEventListener(scope, nativeEventName, function (event) {
domHandlers[nativeEventName].call(instance, event);
});
});
}
else {
if (env.touchEventsSupported) {
zrUtil.each(localNativeListenerNames.touch, function (nativeEventName) {
mountSingleDOMEventListener(scope, nativeEventName, function (event) {
domHandlers[nativeEventName].call(instance, event);
setTouchTimer(scope);
});
});
}
zrUtil.each(localNativeListenerNames.mouse, function (nativeEventName) {
mountSingleDOMEventListener(scope, nativeEventName, function (event) {
event = getNativeEvent(event);
if (!scope.touching) {
domHandlers[nativeEventName].call(instance, event);
}
});
});
}
}
function mountGlobalDOMEventListeners(instance, scope) {
if (env.pointerEventsSupported) {
zrUtil.each(globalNativeListenerNames.pointer, mount);
}
else if (!env.touchEventsSupported) {
zrUtil.each(globalNativeListenerNames.mouse, mount);
}
function mount(nativeEventName) {
function nativeEventListener(event) {
event = getNativeEvent(event);
if (!isLocalEl(instance, event.target)) {
event = normalizeGlobalEvent(instance, event);
scope.domHandlers[nativeEventName].call(instance, event);
}
}
mountSingleDOMEventListener(scope, nativeEventName, nativeEventListener, { capture: true });
}
}
function mountSingleDOMEventListener(scope, nativeEventName, listener, opt) {
scope.mounted[nativeEventName] = listener;
scope.listenerOpts[nativeEventName] = opt;
addEventListener(scope.domTarget, nativeEventName, listener, opt);
}
function unmountDOMEventListeners(scope) {
var mounted = scope.mounted;
for (var nativeEventName in mounted) {
if (mounted.hasOwnProperty(nativeEventName)) {
removeEventListener(scope.domTarget, nativeEventName, mounted[nativeEventName], scope.listenerOpts[nativeEventName]);
}
}
scope.mounted = {};
}
var DOMHandlerScope = (function () {
function DOMHandlerScope(domTarget, domHandlers) {
this.mounted = {};
this.listenerOpts = {};
this.touching = false;
this.domTarget = domTarget;
this.domHandlers = domHandlers;
}
return DOMHandlerScope;
}());
var HandlerDomProxy = (function (_super) {
__extends(HandlerDomProxy, _super);
function HandlerDomProxy(dom, painterRoot) {
var _this = _super.call(this) || this;
_this.__pointerCapturing = false;
_this.dom = dom;
_this.painterRoot = painterRoot;
_this._localHandlerScope = new DOMHandlerScope(dom, localDOMHandlers);
if (globalEventSupported) {
_this._globalHandlerScope = new DOMHandlerScope(document, globalDOMHandlers);
}
mountLocalDOMEventListeners(_this, _this._localHandlerScope);
return _this;
}
HandlerDomProxy.prototype.dispose = function () {
unmountDOMEventListeners(this._localHandlerScope);
if (globalEventSupported) {
unmountDOMEventListeners(this._globalHandlerScope);
}
};
HandlerDomProxy.prototype.setCursor = function (cursorStyle) {
this.dom.style && (this.dom.style.cursor = cursorStyle || 'default');
};
HandlerDomProxy.prototype.__togglePointerCapture = function (isPointerCapturing) {
this.__mayPointerCapture = null;
if (globalEventSupported
&& ((+this.__pointerCapturing) ^ (+isPointerCapturing))) {
this.__pointerCapturing = isPointerCapturing;
var globalHandlerScope = this._globalHandlerScope;
isPointerCapturing
? mountGlobalDOMEventListeners(this, globalHandlerScope)
: unmountDOMEventListeners(globalHandlerScope);
}
};
return HandlerDomProxy;
}(Eventful));
export default HandlerDomProxy;