UNPKG

c8y-openlayer

Version:

This module is designed to help integrate Openlayer with Cumulocity IoT

323 lines (278 loc) 10.2 kB
import _ol_ from './index.js'; import _ol_has_ from './has.js'; import _ol_MapBrowserEventType_ from './mapbrowsereventtype.js'; import _ol_MapBrowserPointerEvent_ from './mapbrowserpointerevent.js'; import _ol_events_ from './events.js'; import _ol_events_EventTarget_ from './events/eventtarget.js'; import _ol_pointer_EventType_ from './pointer/eventtype.js'; import _ol_pointer_PointerEventHandler_ from './pointer/pointereventhandler.js'; /** * @param {ol.PluggableMap} map The map with the viewport to listen to events on. * @param {number|undefined} moveTolerance The minimal distance the pointer must travel to trigger a move. * @constructor * @extends {ol.events.EventTarget} */ var _ol_MapBrowserEventHandler_ = function(map, moveTolerance) { _ol_events_EventTarget_.call(this); /** * This is the element that we will listen to the real events on. * @type {ol.PluggableMap} * @private */ this.map_ = map; /** * @type {number} * @private */ this.clickTimeoutId_ = 0; /** * @type {boolean} * @private */ this.dragging_ = false; /** * @type {!Array.<ol.EventsKey>} * @private */ this.dragListenerKeys_ = []; /** * @type {number} * @private */ this.moveTolerance_ = moveTolerance ? moveTolerance * _ol_has_.DEVICE_PIXEL_RATIO : _ol_has_.DEVICE_PIXEL_RATIO; /** * The most recent "down" type event (or null if none have occurred). * Set on pointerdown. * @type {ol.pointer.PointerEvent} * @private */ this.down_ = null; var element = this.map_.getViewport(); /** * @type {number} * @private */ this.activePointers_ = 0; /** * @type {!Object.<number, boolean>} * @private */ this.trackedTouches_ = {}; /** * Event handler which generates pointer events for * the viewport element. * * @type {ol.pointer.PointerEventHandler} * @private */ this.pointerEventHandler_ = new _ol_pointer_PointerEventHandler_(element); /** * Event handler which generates pointer events for * the document (used when dragging). * * @type {ol.pointer.PointerEventHandler} * @private */ this.documentPointerEventHandler_ = null; /** * @type {?ol.EventsKey} * @private */ this.pointerdownListenerKey_ = _ol_events_.listen(this.pointerEventHandler_, _ol_pointer_EventType_.POINTERDOWN, this.handlePointerDown_, this); /** * @type {?ol.EventsKey} * @private */ this.relayedListenerKey_ = _ol_events_.listen(this.pointerEventHandler_, _ol_pointer_EventType_.POINTERMOVE, this.relayEvent_, this); }; _ol_.inherits(_ol_MapBrowserEventHandler_, _ol_events_EventTarget_); /** * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. * @private */ _ol_MapBrowserEventHandler_.prototype.emulateClick_ = function(pointerEvent) { var newEvent = new _ol_MapBrowserPointerEvent_( _ol_MapBrowserEventType_.CLICK, this.map_, pointerEvent); this.dispatchEvent(newEvent); if (this.clickTimeoutId_ !== 0) { // double-click clearTimeout(this.clickTimeoutId_); this.clickTimeoutId_ = 0; newEvent = new _ol_MapBrowserPointerEvent_( _ol_MapBrowserEventType_.DBLCLICK, this.map_, pointerEvent); this.dispatchEvent(newEvent); } else { // click this.clickTimeoutId_ = setTimeout(function() { this.clickTimeoutId_ = 0; var newEvent = new _ol_MapBrowserPointerEvent_( _ol_MapBrowserEventType_.SINGLECLICK, this.map_, pointerEvent); this.dispatchEvent(newEvent); }.bind(this), 250); } }; /** * Keeps track on how many pointers are currently active. * * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. * @private */ _ol_MapBrowserEventHandler_.prototype.updateActivePointers_ = function(pointerEvent) { var event = pointerEvent; if (event.type == _ol_MapBrowserEventType_.POINTERUP || event.type == _ol_MapBrowserEventType_.POINTERCANCEL) { delete this.trackedTouches_[event.pointerId]; } else if (event.type == _ol_MapBrowserEventType_.POINTERDOWN) { this.trackedTouches_[event.pointerId] = true; } this.activePointers_ = Object.keys(this.trackedTouches_).length; }; /** * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. * @private */ _ol_MapBrowserEventHandler_.prototype.handlePointerUp_ = function(pointerEvent) { this.updateActivePointers_(pointerEvent); var newEvent = new _ol_MapBrowserPointerEvent_( _ol_MapBrowserEventType_.POINTERUP, this.map_, pointerEvent); this.dispatchEvent(newEvent); // We emulate click events on left mouse button click, touch contact, and pen // contact. isMouseActionButton returns true in these cases (evt.button is set // to 0). // See http://www.w3.org/TR/pointerevents/#button-states // We only fire click, singleclick, and doubleclick if nobody has called // event.stopPropagation() or event.preventDefault(). if (!newEvent.propagationStopped && !this.dragging_ && this.isMouseActionButton_(pointerEvent)) { this.emulateClick_(this.down_); } if (this.activePointers_ === 0) { this.dragListenerKeys_.forEach(_ol_events_.unlistenByKey); this.dragListenerKeys_.length = 0; this.dragging_ = false; this.down_ = null; this.documentPointerEventHandler_.dispose(); this.documentPointerEventHandler_ = null; } }; /** * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. * @return {boolean} If the left mouse button was pressed. * @private */ _ol_MapBrowserEventHandler_.prototype.isMouseActionButton_ = function(pointerEvent) { return pointerEvent.button === 0; }; /** * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. * @private */ _ol_MapBrowserEventHandler_.prototype.handlePointerDown_ = function(pointerEvent) { this.updateActivePointers_(pointerEvent); var newEvent = new _ol_MapBrowserPointerEvent_( _ol_MapBrowserEventType_.POINTERDOWN, this.map_, pointerEvent); this.dispatchEvent(newEvent); this.down_ = pointerEvent; if (this.dragListenerKeys_.length === 0) { /* Set up a pointer event handler on the `document`, * which is required when the pointer is moved outside * the viewport when dragging. */ this.documentPointerEventHandler_ = new _ol_pointer_PointerEventHandler_(document); this.dragListenerKeys_.push( _ol_events_.listen(this.documentPointerEventHandler_, _ol_MapBrowserEventType_.POINTERMOVE, this.handlePointerMove_, this), _ol_events_.listen(this.documentPointerEventHandler_, _ol_MapBrowserEventType_.POINTERUP, this.handlePointerUp_, this), /* Note that the listener for `pointercancel is set up on * `pointerEventHandler_` and not `documentPointerEventHandler_` like * the `pointerup` and `pointermove` listeners. * * The reason for this is the following: `TouchSource.vacuumTouches_()` * issues `pointercancel` events, when there was no `touchend` for a * `touchstart`. Now, let's say a first `touchstart` is registered on * `pointerEventHandler_`. The `documentPointerEventHandler_` is set up. * But `documentPointerEventHandler_` doesn't know about the first * `touchstart`. If there is no `touchend` for the `touchstart`, we can * only receive a `touchcancel` from `pointerEventHandler_`, because it is * only registered there. */ _ol_events_.listen(this.pointerEventHandler_, _ol_MapBrowserEventType_.POINTERCANCEL, this.handlePointerUp_, this) ); } }; /** * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. * @private */ _ol_MapBrowserEventHandler_.prototype.handlePointerMove_ = function(pointerEvent) { // Between pointerdown and pointerup, pointermove events are triggered. // To avoid a 'false' touchmove event to be dispatched, we test if the pointer // moved a significant distance. if (this.isMoving_(pointerEvent)) { this.dragging_ = true; var newEvent = new _ol_MapBrowserPointerEvent_( _ol_MapBrowserEventType_.POINTERDRAG, this.map_, pointerEvent, this.dragging_); this.dispatchEvent(newEvent); } // Some native android browser triggers mousemove events during small period // of time. See: https://code.google.com/p/android/issues/detail?id=5491 or // https://code.google.com/p/android/issues/detail?id=19827 // ex: Galaxy Tab P3110 + Android 4.1.1 pointerEvent.preventDefault(); }; /** * Wrap and relay a pointer event. Note that this requires that the type * string for the MapBrowserPointerEvent matches the PointerEvent type. * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. * @private */ _ol_MapBrowserEventHandler_.prototype.relayEvent_ = function(pointerEvent) { var dragging = !!(this.down_ && this.isMoving_(pointerEvent)); this.dispatchEvent(new _ol_MapBrowserPointerEvent_( pointerEvent.type, this.map_, pointerEvent, dragging)); }; /** * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. * @return {boolean} Is moving. * @private */ _ol_MapBrowserEventHandler_.prototype.isMoving_ = function(pointerEvent) { return Math.abs(pointerEvent.clientX - this.down_.clientX) > this.moveTolerance_ || Math.abs(pointerEvent.clientY - this.down_.clientY) > this.moveTolerance_; }; /** * @inheritDoc */ _ol_MapBrowserEventHandler_.prototype.disposeInternal = function() { if (this.relayedListenerKey_) { _ol_events_.unlistenByKey(this.relayedListenerKey_); this.relayedListenerKey_ = null; } if (this.pointerdownListenerKey_) { _ol_events_.unlistenByKey(this.pointerdownListenerKey_); this.pointerdownListenerKey_ = null; } this.dragListenerKeys_.forEach(_ol_events_.unlistenByKey); this.dragListenerKeys_.length = 0; if (this.documentPointerEventHandler_) { this.documentPointerEventHandler_.dispose(); this.documentPointerEventHandler_ = null; } if (this.pointerEventHandler_) { this.pointerEventHandler_.dispose(); this.pointerEventHandler_ = null; } _ol_events_EventTarget_.prototype.disposeInternal.call(this); }; export default _ol_MapBrowserEventHandler_;