UNPKG

@visactor/vrender

Version:

```typescript import { xxx } from '@visactor/vrender'; ```

1,255 lines (1,182 loc) 3.17 MB
(function (global, factory) { typeof exports === 'object' && typeof module !== 'undefined' ? factory(exports) : typeof define === 'function' && define.amd ? define(['exports'], factory) : (global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory(global.VRender = {})); })(this, (function (exports) { 'use strict'; class Hook { constructor(args, name) { this._args = args, this.name = name, this.taps = []; } tap(options, fn) { this._tap("sync", options, fn); } unTap(options, fn) { const name = "string" == typeof options ? options.trim() : options.name; name && (this.taps = this.taps.filter(tap => !(tap.name === name && (!fn || tap.fn === fn)))); } _parseOptions(type, options, fn) { let _options; if ("string" == typeof options) _options = { name: options.trim() };else if ("object" != typeof options || null === options) throw new Error("Invalid tap options"); if ("string" != typeof _options.name || "" === _options.name) throw new Error("Missing name for tap"); return _options = Object.assign({ type: type, fn: fn }, _options), _options; } _tap(type, options, fn) { this._insert(this._parseOptions(type, options, fn)); } _insert(item) { let before; "string" == typeof item.before ? before = new Set([item.before]) : Array.isArray(item.before) && (before = new Set(item.before)); let stage = 0; "number" == typeof item.stage && (stage = item.stage); let i = this.taps.length; for (; i > 0;) { i--; const x = this.taps[i]; this.taps[i + 1] = x; const xStage = x.stage || 0; if (before) { if (before.has(x.name)) { before.delete(x.name); continue; } if (before.size > 0) continue; } if (!(xStage > stage)) { i++; break; } } this.taps[i] = item; } } class SyncHook extends Hook { call(...args) { this.taps.map(t => t.fn).forEach(cb => cb(...args)); } } class Generator { static GenAutoIncrementId() { return Generator.auto_increment_id++; } } Generator.auto_increment_id = 0; class Application {} const APPLICATION_STATE_SYMBOL = Symbol.for("@visactor/vrender-core/application-state"); function createApplicationState() { return { application: new Application() }; } function getApplicationState() { const scope = globalThis; return scope[APPLICATION_STATE_SYMBOL] || (scope[APPLICATION_STATE_SYMBOL] = createApplicationState()), scope[APPLICATION_STATE_SYMBOL]; } const application = getApplicationState().application; let idx = 0; class PerformanceRAF { constructor() { this.nextAnimationFrameCbs = new Map(), this._rafHandle = null, this.runAnimationFrame = time => { this._rafHandle = null; const cbs = this.nextAnimationFrameCbs; this.nextAnimationFrameCbs = new Map(), cbs.forEach(cb => cb(time)); }, this.tryRunAnimationFrameNextFrame = () => { null === this._rafHandle && 0 !== this.nextAnimationFrameCbs.size && (this._rafHandle = application.global.getRequestAnimationFrame()(this.runAnimationFrame)); }; } addAnimationFrameCb(callback) { return this.nextAnimationFrameCbs.set(++idx, callback), this.tryRunAnimationFrameNextFrame(), idx; } removeAnimationFrameCb(index) { return !!this.nextAnimationFrameCbs.has(index) && (this.nextAnimationFrameCbs.delete(index), !0); } wait() { return new Promise(resolve => { this.addAnimationFrameCb(() => resolve()); }); } } class EventListenerManager { constructor() { this._listenerMap = new Map(), this._eventListenerTransformer = event => event; } setEventListenerTransformer(transformer) { this._eventListenerTransformer = transformer || (event => event); } addEventListener(type, listener, options) { if (!listener) return; const capture = this._resolveCapture(options), once = this._resolveOnce(options), listenerTypeMap = this._getOrCreateListenerTypeMap(type), wrappedMap = this._getOrCreateWrappedMap(listenerTypeMap, listener); if (wrappedMap.has(capture)) return; const wrappedListener = event => { const transformedEvent = this._eventListenerTransformer(event); "function" == typeof listener ? listener(transformedEvent) : listener.handleEvent && listener.handleEvent(transformedEvent), once && this._deleteListenerRecord(type, listener, capture); }; wrappedMap.set(capture, { wrappedListener: wrappedListener, options: options }), this._nativeAddEventListener(type, wrappedListener, options); } removeEventListener(type, listener, options) { var _a, _b; if (!listener) return; const capture = this._resolveCapture(options), wrappedRecord = null === (_b = null === (_a = this._listenerMap.get(type)) || void 0 === _a ? void 0 : _a.get(listener)) || void 0 === _b ? void 0 : _b.get(capture); wrappedRecord && (this._nativeRemoveEventListener(type, wrappedRecord.wrappedListener, capture), this._deleteListenerRecord(type, listener, capture)); } dispatchEvent(event) { return this._nativeDispatchEvent(event); } clearAllEventListeners() { this._listenerMap.forEach((listenerMap, type) => { listenerMap.forEach(wrappedMap => { wrappedMap.forEach((wrappedRecord, capture) => { this._nativeRemoveEventListener(type, wrappedRecord.wrappedListener, capture); }); }); }), this._listenerMap.clear(); } _resolveCapture(options) { return "boolean" == typeof options ? options : !!(null == options ? void 0 : options.capture); } _resolveOnce(options) { return "object" == typeof options && !!(null == options ? void 0 : options.once); } _getOrCreateListenerTypeMap(type) { let listenerTypeMap = this._listenerMap.get(type); return listenerTypeMap || (listenerTypeMap = new Map(), this._listenerMap.set(type, listenerTypeMap)), listenerTypeMap; } _getOrCreateWrappedMap(listenerTypeMap, listener) { let wrappedMap = listenerTypeMap.get(listener); return wrappedMap || (wrappedMap = new Map(), listenerTypeMap.set(listener, wrappedMap)), wrappedMap; } _deleteListenerRecord(type, listener, capture) { const listenerTypeMap = this._listenerMap.get(type); if (!listenerTypeMap) return; const wrappedMap = listenerTypeMap.get(listener); wrappedMap && (wrappedMap.delete(capture), 0 === wrappedMap.size && listenerTypeMap.delete(listener), 0 === listenerTypeMap.size && this._listenerMap.delete(type)); } _nativeAddEventListener(type, listener, options) { throw new Error("_nativeAddEventListener must be implemented by derived classes"); } _nativeRemoveEventListener(type, listener, options) { throw new Error("_nativeRemoveEventListener must be implemented by derived classes"); } _nativeDispatchEvent(event) { throw new Error("_nativeDispatchEvent must be implemented by derived classes"); } } var __awaiter$7 = undefined && undefined.__awaiter || function (thisArg, _arguments, P, generator) { return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator.throw(value)); } catch (e) { reject(e); } } function step(result) { var value; result.done ? resolve(result.value) : (value = result.value, value instanceof P ? value : new P(function (resolve) { resolve(value); })).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); }); }; class DefaultGlobal extends EventListenerManager { get env() { return this._env; } get isImageAnonymous() { return this._isImageAnonymous; } set isImageAnonymous(isImageAnonymous) { this._isImageAnonymous = isImageAnonymous; } get devicePixelRatio() { return this._env || this.setEnv("browser"), this.envContribution.getDevicePixelRatio(); } get supportEvent() { return this._env || this.setEnv("browser"), this.envContribution.supportEvent; } set supportEvent(support) { this._env || this.setEnv("browser"), this.envContribution.supportEvent = support; } get supportsTouchEvents() { return this._env || this.setEnv("browser"), this.envContribution.supportsTouchEvents; } set supportsTouchEvents(support) { this._env || this.setEnv("browser"), this.envContribution.supportsTouchEvents = support; } get supportsPointerEvents() { return this._env || this.setEnv("browser"), this.envContribution.supportsPointerEvents; } set supportsPointerEvents(support) { this._env || this.setEnv("browser"), this.envContribution.supportsPointerEvents = support; } get supportsMouseEvents() { return this._env || this.setEnv("browser"), this.envContribution.supportsMouseEvents; } set supportsMouseEvents(support) { this._env || this.setEnv("browser"), this.envContribution.supportsMouseEvents = support; } get applyStyles() { return this._env || this.setEnv("browser"), this.envContribution.applyStyles; } set applyStyles(support) { this._env || this.setEnv("browser"), this.envContribution.applyStyles = support; } constructor(contributions) { super(), this.contributions = contributions, this._isImageAnonymous = !0, this._performanceRAFList = [], this.eventListenerTransformer = event => event, this.id = Generator.GenAutoIncrementId(), this.hooks = { onSetEnv: new SyncHook(["lastEnv", "env", "global"]) }, this.measureTextMethod = "native", this.optimizeVisible = !1; } _nativeAddEventListener(type, listener, options) { return this._env || this.setEnv("browser"), this.envContribution.addEventListener(type, listener, options); } _nativeRemoveEventListener(type, listener, options) { return this._env || this.setEnv("browser"), this.envContribution.removeEventListener(type, listener, options); } _nativeDispatchEvent(event) { return this._env || this.setEnv("browser"), this.envContribution.dispatchEvent(event); } bindContribution(params) { const promiseArr = []; if (this.contributions.getContributions().forEach(contribution => { const data = contribution.configure(this, params); data && data.then && promiseArr.push(data); }), promiseArr.length) return Promise.all(promiseArr); } getDynamicCanvasCount() { return this._env || this.setEnv("browser"), this.envContribution.getDynamicCanvasCount(); } getStaticCanvasCount() { return this._env || this.setEnv("browser"), this.envContribution.getStaticCanvasCount(); } setEnv(env, params) { if (params && !0 === params.force || this._env !== env) return this.deactiveCurrentEnv(), this.activeEnv(env, params); } deactiveCurrentEnv() { this.envContribution && this.envContribution.release(); } activeEnv(env, params) { const lastEnv = this._env; this._env = env; const data = this.bindContribution(params); if (data && data.then) return data.then(() => { this.envParams = params, this.hooks.onSetEnv.call(lastEnv, env, this); }); this.envParams = params, this.hooks.onSetEnv.call(lastEnv, env, this); } setActiveEnvContribution(contribution) { this.envContribution = contribution; } createCanvas(params) { return this._env || this.setEnv("browser"), this.envContribution.createCanvas(params); } createOffscreenCanvas(params) { return this._env || this.setEnv("browser"), this.envContribution.createOffscreenCanvas(params); } releaseCanvas(canvas) { return this._env || this.setEnv("browser"), this.envContribution.releaseCanvas(canvas); } getRequestAnimationFrame() { return this._env || this.setEnv("browser"), this.envContribution.getRequestAnimationFrame(); } getSpecifiedRequestAnimationFrame(id) { this._env || this.setEnv("browser"), this._performanceRAFList[id] || (this._performanceRAFList[id] = new PerformanceRAF()); const performanceRAF = this._performanceRAFList[id]; return callback => performanceRAF.addAnimationFrameCb(callback); } getSpecifiedPerformanceRAF(id) { return this._env || this.setEnv("browser"), this._performanceRAFList[id] || (this._performanceRAFList[id] = new PerformanceRAF()), this._performanceRAFList[id]; } getSpecifiedCancelAnimationFrame(id) { if (this._env || this.setEnv("browser"), !this._performanceRAFList[id]) return () => !1; const performanceRAF = this._performanceRAFList[id]; return handle => performanceRAF.removeAnimationFrameCb(handle); } getCancelAnimationFrame() { return this._env || this.setEnv("browser"), this.envContribution.getCancelAnimationFrame(); } getElementById(str) { return this._env || this.setEnv("browser"), this.envContribution.getElementById ? this.envContribution.getElementById(str) : null; } getRootElement() { return this._env || this.setEnv("browser"), this.envContribution.getRootElement ? this.envContribution.getRootElement() : null; } getDocument() { return this._env || this.setEnv("browser"), this.envContribution.getDocument ? this.envContribution.getDocument() : null; } mapToCanvasPoint(event, domElement) { return this._env || this.setEnv("browser"), this.envContribution.mapToCanvasPoint ? this.envContribution.mapToCanvasPoint(event, domElement) : null; } loadImage(url) { return this._env || this.setEnv("browser"), this.envContribution.loadImage(url); } loadSvg(str) { return this._env || this.setEnv("browser"), this.envContribution.loadSvg(str); } loadJson(url) { return this._env || this.setEnv("browser"), this.envContribution.loadJson(url); } loadArrayBuffer(url) { return this._env || this.setEnv("browser"), this.envContribution.loadArrayBuffer(url); } loadBlob(url) { return this._env || this.setEnv("browser"), this.envContribution.loadBlob(url); } loadFont(name, source, descriptors) { return __awaiter$7(this, void 0, void 0, function* () { return this._env || this.setEnv("browser"), this.envContribution.loadFont(name, source, descriptors); }); } isChrome() { return null != this._isChrome || (this._env || this.setEnv("browser"), this._isChrome = "browser" === this._env && navigator.userAgent.indexOf("Chrome") > -1), this._isChrome; } isSafari() { return null != this._isSafari || (this._env || this.setEnv("browser"), this._isSafari = "browser" === this._env && /Safari/.test(navigator.userAgent) && !/Chrome/.test(navigator.userAgent)), this._isSafari; } getNativeAABBBounds(dom) { return this._env || this.setEnv("browser"), this.envContribution.getNativeAABBBounds(dom); } removeDom(dom) { return this._env || this.setEnv("browser"), this.envContribution.removeDom(dom); } createDom(params) { return this._env || this.setEnv("browser"), this.envContribution.createDom(params); } updateDom(dom, params) { return this._env || this.setEnv("browser"), this.envContribution.updateDom(dom, params); } getElementTop(dom, baseWindow = !1) { return this._env || this.setEnv("browser"), this.envContribution.getElementTop(dom, baseWindow); } getElementLeft(dom, baseWindow = !1) { return this._env || this.setEnv("browser"), this.envContribution.getElementLeft(dom, baseWindow); } getElementTopLeft(dom, baseWindow = !1) { return this._env || this.setEnv("browser"), this.envContribution.getElementTopLeft(dom, baseWindow); } isMacOS() { return this._env || this.setEnv("browser"), this.envContribution.isMacOS(); } copyToClipBoard(text) { return this._env || this.setEnv("browser"), this.envContribution.copyToClipBoard(text); } } var commonjsGlobal = typeof globalThis !== 'undefined' ? globalThis : typeof window !== 'undefined' ? window : typeof global !== 'undefined' ? global : typeof self !== 'undefined' ? self : {}; function getDefaultExportFromCjs (x) { return x && x.__esModule && Object.prototype.hasOwnProperty.call(x, 'default') ? x['default'] : x; } var eventemitter3 = {exports: {}}; (function (module) { var has = Object.prototype.hasOwnProperty, prefix = '~'; /** * Constructor to create a storage for our `EE` objects. * An `Events` instance is a plain object whose properties are event names. * * @constructor * @private */ function Events() {} // // We try to not inherit from `Object.prototype`. In some engines creating an // instance in this way is faster than calling `Object.create(null)` directly. // If `Object.create(null)` is not supported we prefix the event names with a // character to make sure that the built-in object properties are not // overridden or used as an attack vector. // if (Object.create) { Events.prototype = Object.create(null); // // This hack is needed because the `__proto__` property is still inherited in // some old browsers like Android 4, iPhone 5.1, Opera 11 and Safari 5. // if (!new Events().__proto__) prefix = false; } /** * Representation of a single event listener. * * @param {Function} fn The listener function. * @param {*} context The context to invoke the listener with. * @param {Boolean} [once=false] Specify if the listener is a one-time listener. * @constructor * @private */ function EE(fn, context, once) { this.fn = fn; this.context = context; this.once = once || false; } /** * Add a listener for a given event. * * @param {EventEmitter} emitter Reference to the `EventEmitter` instance. * @param {(String|Symbol)} event The event name. * @param {Function} fn The listener function. * @param {*} context The context to invoke the listener with. * @param {Boolean} once Specify if the listener is a one-time listener. * @returns {EventEmitter} * @private */ function addListener(emitter, event, fn, context, once) { if (typeof fn !== 'function') { throw new TypeError('The listener must be a function'); } var listener = new EE(fn, context || emitter, once), evt = prefix ? prefix + event : event; if (!emitter._events[evt]) emitter._events[evt] = listener, emitter._eventsCount++;else if (!emitter._events[evt].fn) emitter._events[evt].push(listener);else emitter._events[evt] = [emitter._events[evt], listener]; return emitter; } /** * Clear event by name. * * @param {EventEmitter} emitter Reference to the `EventEmitter` instance. * @param {(String|Symbol)} evt The Event name. * @private */ function clearEvent(emitter, evt) { if (--emitter._eventsCount === 0) emitter._events = new Events();else delete emitter._events[evt]; } /** * Minimal `EventEmitter` interface that is molded against the Node.js * `EventEmitter` interface. * * @constructor * @public */ function EventEmitter() { this._events = new Events(); this._eventsCount = 0; } /** * Return an array listing the events for which the emitter has registered * listeners. * * @returns {Array} * @public */ EventEmitter.prototype.eventNames = function eventNames() { var names = [], events, name; if (this._eventsCount === 0) return names; for (name in events = this._events) { if (has.call(events, name)) names.push(prefix ? name.slice(1) : name); } if (Object.getOwnPropertySymbols) { return names.concat(Object.getOwnPropertySymbols(events)); } return names; }; /** * Return the listeners registered for a given event. * * @param {(String|Symbol)} event The event name. * @returns {Array} The registered listeners. * @public */ EventEmitter.prototype.listeners = function listeners(event) { var evt = prefix ? prefix + event : event, handlers = this._events[evt]; if (!handlers) return []; if (handlers.fn) return [handlers.fn]; for (var i = 0, l = handlers.length, ee = new Array(l); i < l; i++) { ee[i] = handlers[i].fn; } return ee; }; /** * Return the number of listeners listening to a given event. * * @param {(String|Symbol)} event The event name. * @returns {Number} The number of listeners. * @public */ EventEmitter.prototype.listenerCount = function listenerCount(event) { var evt = prefix ? prefix + event : event, listeners = this._events[evt]; if (!listeners) return 0; if (listeners.fn) return 1; return listeners.length; }; /** * Calls each of the listeners registered for a given event. * * @param {(String|Symbol)} event The event name. * @returns {Boolean} `true` if the event had listeners, else `false`. * @public */ EventEmitter.prototype.emit = function emit(event, a1, a2, a3, a4, a5) { var evt = prefix ? prefix + event : event; if (!this._events[evt]) return false; var listeners = this._events[evt], len = arguments.length, args, i; if (listeners.fn) { if (listeners.once) this.removeListener(event, listeners.fn, undefined, true); switch (len) { case 1: return listeners.fn.call(listeners.context), true; case 2: return listeners.fn.call(listeners.context, a1), true; case 3: return listeners.fn.call(listeners.context, a1, a2), true; case 4: return listeners.fn.call(listeners.context, a1, a2, a3), true; case 5: return listeners.fn.call(listeners.context, a1, a2, a3, a4), true; case 6: return listeners.fn.call(listeners.context, a1, a2, a3, a4, a5), true; } for (i = 1, args = new Array(len - 1); i < len; i++) { args[i - 1] = arguments[i]; } listeners.fn.apply(listeners.context, args); } else { var length = listeners.length, j; for (i = 0; i < length; i++) { if (listeners[i].once) this.removeListener(event, listeners[i].fn, undefined, true); switch (len) { case 1: listeners[i].fn.call(listeners[i].context); break; case 2: listeners[i].fn.call(listeners[i].context, a1); break; case 3: listeners[i].fn.call(listeners[i].context, a1, a2); break; case 4: listeners[i].fn.call(listeners[i].context, a1, a2, a3); break; default: if (!args) for (j = 1, args = new Array(len - 1); j < len; j++) { args[j - 1] = arguments[j]; } listeners[i].fn.apply(listeners[i].context, args); } } } return true; }; /** * Add a listener for a given event. * * @param {(String|Symbol)} event The event name. * @param {Function} fn The listener function. * @param {*} [context=this] The context to invoke the listener with. * @returns {EventEmitter} `this`. * @public */ EventEmitter.prototype.on = function on(event, fn, context) { return addListener(this, event, fn, context, false); }; /** * Add a one-time listener for a given event. * * @param {(String|Symbol)} event The event name. * @param {Function} fn The listener function. * @param {*} [context=this] The context to invoke the listener with. * @returns {EventEmitter} `this`. * @public */ EventEmitter.prototype.once = function once(event, fn, context) { return addListener(this, event, fn, context, true); }; /** * Remove the listeners of a given event. * * @param {(String|Symbol)} event The event name. * @param {Function} fn Only remove the listeners that match this function. * @param {*} context Only remove the listeners that have this context. * @param {Boolean} once Only remove one-time listeners. * @returns {EventEmitter} `this`. * @public */ EventEmitter.prototype.removeListener = function removeListener(event, fn, context, once) { var evt = prefix ? prefix + event : event; if (!this._events[evt]) return this; if (!fn) { clearEvent(this, evt); return this; } var listeners = this._events[evt]; if (listeners.fn) { if (listeners.fn === fn && (!once || listeners.once) && (!context || listeners.context === context)) { clearEvent(this, evt); } } else { for (var i = 0, events = [], length = listeners.length; i < length; i++) { if (listeners[i].fn !== fn || once && !listeners[i].once || context && listeners[i].context !== context) { events.push(listeners[i]); } } // // Reset the array, or remove it completely if we have no more listeners. // if (events.length) this._events[evt] = events.length === 1 ? events[0] : events;else clearEvent(this, evt); } return this; }; /** * Remove all listeners, or those of the specified event. * * @param {(String|Symbol)} [event] The event name. * @returns {EventEmitter} `this`. * @public */ EventEmitter.prototype.removeAllListeners = function removeAllListeners(event) { var evt; if (event) { evt = prefix ? prefix + event : event; if (this._events[evt]) clearEvent(this, evt); } else { this._events = new Events(); this._eventsCount = 0; } return this; }; // // Alias methods names because people roll like that. // EventEmitter.prototype.off = EventEmitter.prototype.removeListener; EventEmitter.prototype.addListener = EventEmitter.prototype.on; // // Expose the prefix. // EventEmitter.prefixed = prefix; // // Allow `EventEmitter` to be imported as module namespace. // EventEmitter.EventEmitter = EventEmitter; // // Expose the module. // { module.exports = EventEmitter; } })(eventemitter3); var eventemitter3Exports = eventemitter3.exports; var EventEmitter = /*@__PURE__*/getDefaultExportFromCjs(eventemitter3Exports); const isType = (value, type) => Object.prototype.toString.call(value) === `[object ${type}]`; var isType$1 = isType; const isBoolean = (value, fuzzy = !1) => fuzzy ? "boolean" == typeof value : !0 === value || !1 === value || isType$1(value, "Boolean"); var isBoolean$1 = isBoolean; const isFunction = value => "function" == typeof value; var isFunction$1 = isFunction; const isNil = value => null == value; var isNil$1 = isNil; const isValid = value => null != value; var isValid$1 = isValid; const isObject = value => { const type = typeof value; return null !== value && "object" === type || "function" === type; }; var isObject$1 = isObject; const isObjectLike = value => "object" == typeof value && null !== value; var isObjectLike$1 = isObjectLike; const isPlainObject$2 = function (value) { if (!isObjectLike$1(value) || !isType$1(value, "Object")) return !1; if (null === Object.getPrototypeOf(value)) return !0; let proto = value; for (; null !== Object.getPrototypeOf(proto);) proto = Object.getPrototypeOf(proto); return Object.getPrototypeOf(value) === proto; }; var isPlainObject$3 = isPlainObject$2; const isUndefined = value => void 0 === value; var isUndefined$1 = isUndefined; const isString = (value, fuzzy = !1) => { const type = typeof value; return fuzzy ? "string" === type : "string" === type || isType$1(value, "String"); }; var isString$1 = isString; const isArray = value => Array.isArray ? Array.isArray(value) : isType$1(value, "Array"); var isArray$1 = isArray; const isArrayLike = function (value) { return null !== value && "function" != typeof value && Number.isFinite(value.length); }; var isArrayLike$1 = isArrayLike; const isDate = value => isType$1(value, "Date"); var isDate$1 = isDate; const isNumber$1 = (value, fuzzy = !1) => { const type = typeof value; return fuzzy ? "number" === type : "number" === type || isType$1(value, "Number"); }; var isNumber$2 = isNumber$1; const isValidNumber = value => isNumber$2(value) && Number.isFinite(value); var isValidNumber$1 = isValidNumber; const isValidUrl = value => new RegExp(/^(http(s)?:\/\/)\w+[^\s]+(\.[^\s]+){1,}$/).test(value); var isValidUrl$1 = isValidUrl; const isBase64 = value => new RegExp(/^data:image\/(?:gif|png|jpeg|bmp|webp|svg\+xml)(?:;charset=utf-8)?;base64,(?:[A-Za-z0-9]|[+/])+={0,2}/g).test(value); var isBase64$1 = isBase64; const getType = value => ({}).toString.call(value).replace(/^\[object /, "").replace(/]$/, ""); var getType$1 = getType; const objectProto = Object.prototype, isPrototype = function (value) { const Ctor = value && value.constructor; return value === ("function" == typeof Ctor && Ctor.prototype || objectProto); }; var isPrototype$1 = isPrototype; const hasOwnProperty$1 = Object.prototype.hasOwnProperty; function isEmpty(value) { if (isNil$1(value)) return !0; if (isArrayLike$1(value)) return !value.length; const type = getType$1(value); if ("Map" === type || "Set" === type) return !value.size; if (isPrototype$1(value)) return !Object.keys(value).length; for (const key in value) if (hasOwnProperty$1.call(value, key)) return !1; return !0; } const get = (obj, path, defaultValue) => { const paths = isString$1(path) ? path.split(".") : path; for (let p = 0; p < paths.length; p++) obj = obj ? obj[paths[p]] : void 0; return void 0 === obj ? defaultValue : obj; }; var get$1 = get; const hasOwnProperty = Object.prototype.hasOwnProperty, has = (object, key) => null != object && hasOwnProperty.call(object, key); var has$1 = has; function cloneDeep(value, ignoreWhen, excludeKeys) { let result; if (!isValid$1(value) || "object" != typeof value || ignoreWhen && ignoreWhen(value)) return value; const isArr = isArray$1(value), length = value.length; result = isArr ? new Array(length) : "object" == typeof value ? {} : isBoolean$1(value) || isNumber$2(value) || isString$1(value) ? value : isDate$1(value) ? new Date(+value) : void 0; const props = isArr ? void 0 : Object.keys(Object(value)); let index = -1; if (result) for (; ++index < (props || value).length;) { const key = props ? props[index] : index, subValue = value[key]; excludeKeys && excludeKeys.includes(key.toString()) ? result[key] = subValue : result[key] = cloneDeep(subValue, ignoreWhen, excludeKeys); } return result; } function baseMerge(target, source, shallowArray = !1, skipTargetArray = !1) { if (source) { if (target === source) return; if (isValid$1(source) && "object" == typeof source) { const iterable = Object(source), props = []; for (const key in iterable) props.push(key); let { length: length } = props, propIndex = -1; for (; length--;) { const key = props[++propIndex]; !isValid$1(iterable[key]) || "object" != typeof iterable[key] || skipTargetArray && isArray$1(target[key]) ? assignMergeValue(target, key, iterable[key]) : baseMergeDeep(target, source, key, shallowArray, skipTargetArray); } } } } function baseMergeDeep(target, source, key, shallowArray = !1, skipTargetArray = !1) { const objValue = target[key], srcValue = source[key]; let newValue = source[key], isCommon = !0; if (isArray$1(srcValue)) { if (shallowArray) newValue = [];else if (isArray$1(objValue)) newValue = objValue;else if (isArrayLike$1(objValue)) { newValue = new Array(objValue.length); let index = -1; const length = objValue.length; for (; ++index < length;) newValue[index] = objValue[index]; } } else isPlainObject$3(srcValue) ? (newValue = null != objValue ? objValue : {}, "function" != typeof objValue && "object" == typeof objValue || (newValue = {})) : isCommon = !1; isCommon && baseMerge(newValue, srcValue, shallowArray, skipTargetArray), assignMergeValue(target, key, newValue); } function assignMergeValue(target, key, value) { (void 0 !== value && !eq(target[key], value) || void 0 === value && !(key in target)) && (target[key] = value); } function eq(value, other) { return value === other || Number.isNaN(value) && Number.isNaN(other); } function merge(target, ...sources) { let sourceIndex = -1; const length = sources.length; for (; ++sourceIndex < length;) { baseMerge(target, sources[sourceIndex], !0); } return target; } function objToString(obj) { return Object.prototype.toString.call(obj); } function objectKeys(obj) { return Object.keys(obj); } function isEqual(a, b, options) { if (a === b) return !0; if (typeof a != typeof b) return !1; if (null == a || null == b) return !1; if (Number.isNaN(a) && Number.isNaN(b)) return !0; if (objToString(a) !== objToString(b)) return !1; if (isFunction$1(a)) return !!(null == options ? void 0 : options.skipFunction); if ("object" != typeof a) return !1; if (isArray$1(a)) { if (a.length !== b.length) return !1; for (let i = a.length - 1; i >= 0; i--) if (!isEqual(a[i], b[i], options)) return !1; return !0; } if (!isPlainObject$3(a)) return !1; const ka = objectKeys(a), kb = objectKeys(b); if (ka.length !== kb.length) return !1; ka.sort(), kb.sort(); for (let i = ka.length - 1; i >= 0; i--) if (ka[i] != kb[i]) return !1; for (let i = ka.length - 1; i >= 0; i--) { const key = ka[i]; if (!isEqual(a[key], b[key], options)) return !1; } return !0; } function keys(obj) { if (!obj) return []; if (Object.keys) return Object.keys(obj); const keyList = []; for (const key in obj) obj.hasOwnProperty(key) && keyList.push(key); return keyList; } function defaults(target, source, overlay) { const keysArr = keys(source); for (let i = 0; i < keysArr.length; i++) { const key = keysArr[i]; (overlay ? null != source[key] : null == target[key]) && (target[key] = source[key]); } return target; } function mixin(target, source, override = !0) { if (target = "prototype" in target ? target.prototype : target, source = "prototype" in source ? source.prototype : source, Object.getOwnPropertyNames) { const keyList = Object.getOwnPropertyNames(source); for (let i = 0; i < keyList.length; i++) { const key = keyList[i]; "constructor" !== key && (override ? null != source[key] : null == target[key]) && (target[key] = source[key]); } } else defaults(target, source, override); } function array(arr) { return isValid$1(arr) ? isArray$1(arr) ? arr : [arr] : []; } function last(val) { if (isArrayLike$1(val)) { return val[val.length - 1]; } } const maxInArray = (arr, compareFn) => { var _a; if (0 === arr.length) return; let max = arr[0]; for (let i = 1; i < arr.length; i++) { const value = arr[i]; (null !== (_a = null == compareFn ? void 0 : compareFn(value, max)) && void 0 !== _a ? _a : value - max) > 0 && (max = value); } return max; }; const minInArray = (arr, compareFn) => { var _a; if (0 === arr.length) return; let min = arr[0]; for (let i = 1; i < arr.length; i++) { const value = arr[i]; (null !== (_a = null == compareFn ? void 0 : compareFn(value, min)) && void 0 !== _a ? _a : value - min) < 0 && (min = value); } return min; }; function arrayEqual(a, b) { if (!isArray$1(a) || !isArray$1(b)) return !1; if (a.length !== b.length) return !1; for (let i = 0; i < a.length; i++) if (a[i] !== b[i]) return !1; return !0; } function flattenArray(arr) { if (!isArray$1(arr)) return [arr]; const result = []; for (const value of arr) result.push(...flattenArray(value)); return result; } function range(start, stop, step) { isValid$1(stop) || (stop = start, start = 0), isValid$1(step) || (step = 1); let i = -1; const n = 0 | Math.max(0, Math.ceil((stop - start) / step)), range = new Array(n); for (; ++i < n;) range[i] = start + i * step; return range; } function ascending(a, b) { return a < b ? -1 : a > b ? 1 : a >= b ? 0 : NaN; } function toNumber(a) { return Number(a); } const hasConsole = "undefined" != typeof console; function log(method, level, input) { const args = [level].concat([].slice.call(input)); hasConsole && console[method].apply(console, args); } var LoggerLevel; !function (LoggerLevel) { LoggerLevel[LoggerLevel.None = 0] = "None", LoggerLevel[LoggerLevel.Error = 1] = "Error", LoggerLevel[LoggerLevel.Warn = 2] = "Warn", LoggerLevel[LoggerLevel.Info = 3] = "Info", LoggerLevel[LoggerLevel.Debug = 4] = "Debug"; }(LoggerLevel || (LoggerLevel = {})); class Logger { static getInstance(level, method) { return Logger._instance && isNumber$2(level) ? Logger._instance.level(level) : Logger._instance || (Logger._instance = new Logger(level, method)), Logger._instance; } static setInstance(logger) { return Logger._instance = logger; } static setInstanceLevel(level) { Logger._instance ? Logger._instance.level(level) : Logger._instance = new Logger(level); } static clearInstance() { Logger._instance = null; } constructor(level = LoggerLevel.None, method) { this._onErrorHandler = [], this._level = level, this._method = method; } addErrorHandler(handler) { this._onErrorHandler.find(h => h === handler) || this._onErrorHandler.push(handler); } removeErrorHandler(handler) { const index = this._onErrorHandler.findIndex(h => h === handler); index < 0 || this._onErrorHandler.splice(index, 1); } callErrorHandler(...args) { this._onErrorHandler.forEach(h => h(...args)); } canLogInfo() { return this._level >= LoggerLevel.Info; } canLogDebug() { return this._level >= LoggerLevel.Debug; } canLogError() { return this._level >= LoggerLevel.Error; } canLogWarn() { return this._level >= LoggerLevel.Warn; } level(levelValue) { return arguments.length ? (this._level = +levelValue, this) : this._level; } error(...args) { var _a; return this._level >= LoggerLevel.Error && (this._onErrorHandler.length ? this.callErrorHandler(...args) : log(null !== (_a = this._method) && void 0 !== _a ? _a : "error", "ERROR", args)), this; } warn(...args) { return this._level >= LoggerLevel.Warn && log(this._method || "warn", "WARN", args), this; } info(...args) { return this._level >= LoggerLevel.Info && log(this._method || "log", "INFO", args), this; } debug(...args) { return this._level >= LoggerLevel.Debug && log(this._method || "log", "DEBUG", args), this; } } Logger._instance = null; function bisect(a, x, lo = 0, hi) { for (isNil$1(hi) && (hi = a.length); lo < hi;) { const mid = lo + hi >>> 1; ascending(a[mid], x) > 0 ? hi = mid : lo = mid + 1; } return lo; } const binaryFuzzySearchInNumberRange = (x1, x2, compareFn) => { let left = x1, right = x2; for (; left < right;) { const mid = Math.floor((left + right) / 2); compareFn(mid) >= 0 ? right = mid : left = mid + 1; } return left; }; const DEFAULT_ABSOLUTE_TOLERATE = 1e-10, DEFAULT_RELATIVE_TOLERATE = 1e-10; function isNumberClose(a, b, relTol = DEFAULT_RELATIVE_TOLERATE, absTol = DEFAULT_ABSOLUTE_TOLERATE) { const abs = absTol, rel = relTol * Math.max(a, b); return Math.abs(a - b) <= Math.max(abs, rel); } function isGreater(a, b, relTol, absTol) { return a > b && !isNumberClose(a, b, relTol, absTol); } function isLess(a, b, relTol, absTol) { return a < b && !isNumberClose(a, b, relTol, absTol); } const memoize = func => { let lastArgs = null, lastResult = null; return (...args) => (lastArgs && args.every((val, i) => val === lastArgs[i]) || (lastArgs = args, lastResult = func(...args)), lastResult); }; const clamp = function (input, min, max) { return input < min ? min : input > max ? max : input; }; var clamp$1 = clamp; const clampRange = (range, min, max) => { let [lowValue, highValue] = range; highValue < lowValue && (lowValue = range[1], highValue = range[0]); const span = highValue - lowValue; return span >= max - min ? [min, max] : (lowValue = Math.min(Math.max(lowValue, min), max - span), [lowValue, lowValue + span]); }; var clampRange$1 = clampRange; function clamper(a, b) { let t; return a > b && (t = a, a = b, b = t), x => Math.max(a, Math.min(b, x)); } let hasRaf = !1; try { hasRaf = "function" == typeof requestAnimationFrame && "function" == typeof cancelAnimationFrame; } catch (err) { hasRaf = !1; } function debounce(func, wait, options) { let lastArgs, lastThis, maxWait, result, timerId, lastCallTime, lastInvokeTime = 0, leading = !1, maxing = !1, trailing = !0; const useRAF = !wait && 0 !== wait && hasRaf; if ("function" != typeof func) throw new TypeError("Expected a function"); function invokeFunc(time) { const args = lastArgs, thisArg = lastThis; return lastArgs = lastThis = void 0, lastInvokeTime = time, result = func.apply(thisArg, args), result; } function startTimer(pendingFunc, wait) { return useRAF ? (cancelAnimationFrame(timerId), requestAnimationFrame(pendingFunc)) : setTimeout(pendingFunc, wait); } function shouldInvoke(time) { const timeSinceLastCall = time - lastCallTime; return void 0 === lastCallTime || timeSinceLastCall >= wait || timeSinceLastCall < 0 || maxing && time - lastInvokeTime >= maxWait; } function timerExpired() { const time = Date.now(); if (shouldInvoke(time)) return trailingEdge(time); timerId = startTimer(timerExpired, function (time) { const timeSinceLastInvoke = time - lastInvokeTime, timeWaiting = wait - (time - lastCallTime); return maxing ? Math.min(timeWaiting, maxWait - timeSinceLastInvoke) : timeWaiting; }(time)); } function trailingEdge(time) { return timerId = void 0, trailing && lastArgs ? invokeFunc(time) : (lastArgs = lastThis = void 0, result); } function debounced(...args) { const time = Date.now(), isInvoking = shouldInvoke(time); if (lastArgs = args, lastThis = this, lastCallTime = time, isInvoking) { if (void 0 === timerId) return function (time) { return lastInvokeTime = time, timerId = startTimer(timerExpired, wait), leading ? invokeFunc(time) : result; }(lastCallTime); if (maxing) return timerId = startTimer(timerExpired, wait), invokeFunc(lastCallTime); } return void 0 === timerId && (timerId = startTimer(timerExpired, wait)), result; } return wait = +wait || 0, isObject$1(options) && (leading = !!options.leading, maxing = "maxWait" in options, maxing && (maxWait = Math.max(isValidNumber$1(options.maxWait) ? options.maxWait : 0, wait)), trailing = "trailing" in options ? !!options.trailing : trailing), debounced.cancel = function () { void 0 !== timerId && function (id) { if (useRAF) return cancelAnimationFrame(id); clearTimeout(id); }(timerId), lastInvokeTime = 0, lastArgs = lastCallTime = lastThis = timerId = void 0; }, debounced.flush = function () { return void 0 === timerId ? result : trailingEdge(Date.now()); }, debounced.pending = function () { return void 0 !== timerId; }, debounced; } hasRaf = !1; function throttle(func, wait, options) { let leading = !0, trailing = !0; if ("function" != typeof func) throw new TypeError("Expected a function"); return isObject$1(options) && (leading = "leading" in options ? !!options.leading : leading, trailing = "trailing" in options ? !!options.trailing : trailing), debounce(func, wait, { leading: leading, trailing: trailing, maxWait: wait }); } function interpolateNumber$1(a, b) { return t => a * (1 - t) + b * t; } function interpolateNumberRound(a, b) { return function (t) { return Math.round(a * (1 - t) + b * t); }; } function interpolateDate(a, b) { const aVal = a.valueOf(), bVal = b.valueOf(), d = new Date(); return t => (d.setTime(aVal * (1 - t) + bVal * t), d); } const reA = /[-+]?(?:\d+\.?\d*|\.?\d+)(?:[eE][-+]?\d+)?/g, reB = new RegExp(reA.source, "g"); function zero(b) { return function () { return b; }; } function one(b) { return function (t) { return b(t) + ""; }; } function interpolateString(a, b) { let am, bm, bs, bi = reA.lastIndex = reB.lastIndex = 0, i = -1; const s = [], q = []; for (a += "", b += ""; (am = reA.exec(a)) && (bm = reB.exec(b));) (bs = bm.index) > bi && (bs = b.slice(bi, bs), s[i] ? s[i] += bs : s[++i] = bs), (am = am[0]) === (bm = bm[0]) ? s[i] ? s[i] += bm : s[++i] = bm : (s[++i] = null, q.push({ i: i, x: interpolateNumber$1(am, bm) })), bi = reB.lastIndex; return bi < b.length && (bs = b.slice(bi), s[i] ? s[i] += bs : s[++i] = bs), s.length < 2 ? q[0] ? one(q[0].x) : zero(b) : (b = q.length, function (t) { for (let o, i = 0; i < b; ++i) s[(o = q[i]).i] = o.x(t); return s.join(""); }); } const epsilon = 1e-12; const pi = Math.PI; const halfPi$1 = pi / 2; const tau = 2 * pi; const pi2 = 2 * Math.PI; const abs = Math.abs; const atan2 = Math.atan2; const cos = Math.cos; const max = Math.max; const min = Math.min; const sin = Math.sin; const sqrt = Math.sqrt; const pow = Math.pow; function acos(x) { return x > 1 ? 0 : x < -1 ? pi : Math.acos(x); } function asin(x) { return x >= 1 ? halfPi$1 : x <= -1 ? -halfPi$1 : Math.asin(x); } function pointAt(x1, y1, x2, y2, t) { let x