UNPKG

jodit

Version:

Jodit is an awesome and useful wysiwyg editor with filebrowser

191 lines (190 loc) 5.6 kB
/*! * Jodit Editor (https://xdsoft.net/jodit/) * Released under MIT see LICENSE.txt in the project root for license information. * Copyright (c) 2013-2025 Valeriy Chupurnov. All rights reserved. https://xdsoft.net */ import { Async } from "../async/index.js"; import { STATUSES } from "./statuses.js"; import { uniqueUid } from "../global.js"; import { get, getClassName, isFunction, isVoid, kebabCase } from "../helpers/index.js"; const StatusListHandlers = new Map(); /** * The base class of all Jodit UI components. Provides work with a life cycle. */ export class Component { get componentName() { if (!this.__componentName) { this.__componentName = 'jodit-' + kebabCase((isFunction(this.className) ? this.className() : '') || getClassName(this)); } return this.__componentName; } getFullElName(elementName, mod, modValue) { const result = [this.componentName]; if (elementName) { elementName = elementName.replace(/[^a-z0-9-]/gi, '-'); result.push(`__${elementName}`); } if (mod) { result.push('_', mod); result.push('_', isVoid(modValue) ? 'true' : modValue.toString()); } return result.join(''); } /** * The document in which jodit was created */ get ownerDocument() { return this.ow.document; } /** * Shortcut for `this.ownerDocument` */ get od() { return this.ownerDocument; } get ow() { return this.ownerWindow; } /** * Safe get any field * @example * ```js * private a = { * b: { * c: { * e: { * g: { * color: 'red' * } * } * } * } * } * * this.get('a.b.c.e.g.color'); // Safe access to color * // instead using optionsl chaining * this?.a?.b?.c?.e?.g?.color * ``` * * @param chain - the path to be traversed in the obj object * @param obj - the object in which the value is searched */ get(chain, obj) { return get(chain, obj || this); } /** * Component is ready for work */ get isReady() { return this.componentStatus === STATUSES.ready; } /** * Component was destructed */ get isDestructed() { return this.componentStatus === STATUSES.destructed; } /** * The component is currently undergoing destructuring or has already been destroyed. * Those. you should not the app froze new events on him now or do anything else with him. */ get isInDestruct() { return (STATUSES.beforeDestruct === this.componentStatus || STATUSES.destructed === this.componentStatus); } /** * Bind destructor to some View */ bindDestruct(component) { component.hookStatus(STATUSES.beforeDestruct, () => !this.isInDestruct && this.destruct()); return this; } constructor() { this.async = new Async(); /** * The window in which jodit was created */ this.ownerWindow = window; this.__componentStatus = STATUSES.beforeInit; this.uid = 'jodit-uid-' + uniqueUid(); } /** * Destruct component method */ destruct() { this.setStatus(STATUSES.destructed); if (this.async) { this.async.destruct(); // @ts-ignore this.async = undefined; } if (StatusListHandlers.get(this)) { StatusListHandlers.delete(this); } // @ts-ignore this.ownerWindow = undefined; } /** * Current component status */ get componentStatus() { return this.__componentStatus; } /** * Setter for current component status */ set componentStatus(componentStatus) { this.setStatus(componentStatus); } /** * Set component status * @param componentStatus - component status * @see ComponentStatus */ setStatus(componentStatus) { return this.setStatusComponent(componentStatus, this); } /** * Set status recursively on all parents */ setStatusComponent(componentStatus, component) { if (componentStatus === this.__componentStatus) { return; } if (component === this) { this.__componentStatus = componentStatus; } const proto = Object.getPrototypeOf(this); if (proto && isFunction(proto.setStatusComponent)) { proto.setStatusComponent(componentStatus, component); } const statuses = StatusListHandlers.get(this), list = statuses === null || statuses === void 0 ? void 0 : statuses[componentStatus]; if (list && list.length) { list.forEach(cb => cb(component)); } } /** * Adds a handler for changing the component's status * * @param status - the status at which the callback is triggered * @param callback - a function that will be called when the status is `status` */ hookStatus(status, callback) { let list = StatusListHandlers.get(this); if (!list) { list = {}; StatusListHandlers.set(this, list); } if (!list[status]) { list[status] = []; } list[status].push(callback); } static isInstanceOf(c, constructorFunc) { return c instanceof constructorFunc; } } Component.STATUSES = STATUSES;