tulih-editor 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +331 -0
- package/dist/tulih-editor.css +1 -0
- package/dist/tulih-editor.es.js +3051 -0
- package/dist/tulih-editor.es.js.map +1 -0
- package/dist/tulih-editor.umd.js +8 -0
- package/dist/tulih-editor.umd.js.map +1 -0
- package/dist/types/core/Editor.d.ts +20 -0
- package/dist/types/core/PluginManager.d.ts +22 -0
- package/dist/types/core/helpers.d.ts +22 -0
- package/dist/types/index.d.ts +5 -0
- package/dist/types/plugins/align.d.ts +3 -0
- package/dist/types/plugins/autoLinkify.d.ts +3 -0
- package/dist/types/plugins/autosave.d.ts +3 -0
- package/dist/types/plugins/block.d.ts +3 -0
- package/dist/types/plugins/caseTransform.d.ts +3 -0
- package/dist/types/plugins/codeBlock.d.ts +3 -0
- package/dist/types/plugins/colors.d.ts +3 -0
- package/dist/types/plugins/darkMode.d.ts +3 -0
- package/dist/types/plugins/direction.d.ts +3 -0
- package/dist/types/plugins/dragDrop.d.ts +3 -0
- package/dist/types/plugins/emoji.d.ts +3 -0
- package/dist/types/plugins/emojiAutocomplete.d.ts +3 -0
- package/dist/types/plugins/findReplace.d.ts +3 -0
- package/dist/types/plugins/floatingToolbar.d.ts +3 -0
- package/dist/types/plugins/fontFamily.d.ts +3 -0
- package/dist/types/plugins/fontSize.d.ts +3 -0
- package/dist/types/plugins/fullscreen.d.ts +3 -0
- package/dist/types/plugins/history.d.ts +3 -0
- package/dist/types/plugins/hr.d.ts +3 -0
- package/dist/types/plugins/iframe.d.ts +3 -0
- package/dist/types/plugins/image.d.ts +3 -0
- package/dist/types/plugins/imageProps.d.ts +3 -0
- package/dist/types/plugins/imageTools.d.ts +3 -0
- package/dist/types/plugins/indent.d.ts +3 -0
- package/dist/types/plugins/index.d.ts +2 -0
- package/dist/types/plugins/inline.d.ts +3 -0
- package/dist/types/plugins/inlineCode.d.ts +3 -0
- package/dist/types/plugins/keyboardShortcuts.d.ts +3 -0
- package/dist/types/plugins/lineHeight.d.ts +3 -0
- package/dist/types/plugins/link.d.ts +3 -0
- package/dist/types/plugins/linkTooltip.d.ts +3 -0
- package/dist/types/plugins/list.d.ts +3 -0
- package/dist/types/plugins/markdown.d.ts +3 -0
- package/dist/types/plugins/mediaEmbed.d.ts +3 -0
- package/dist/types/plugins/pasteImage.d.ts +3 -0
- package/dist/types/plugins/pastePlain.d.ts +3 -0
- package/dist/types/plugins/pre.d.ts +3 -0
- package/dist/types/plugins/readOnly.d.ts +3 -0
- package/dist/types/plugins/shortcutCustomizer.d.ts +3 -0
- package/dist/types/plugins/shortcutsHelp.d.ts +3 -0
- package/dist/types/plugins/source.d.ts +3 -0
- package/dist/types/plugins/specialChars.d.ts +3 -0
- package/dist/types/plugins/statusBar.d.ts +3 -0
- package/dist/types/plugins/subSuper.d.ts +3 -0
- package/dist/types/plugins/table.d.ts +3 -0
- package/dist/types/plugins/tableBg.d.ts +3 -0
- package/dist/types/plugins/tableTools.d.ts +3 -0
- package/dist/types/plugins/toolbarCollapse.d.ts +3 -0
- package/dist/types/plugins/unlink.d.ts +3 -0
- package/dist/types/plugins/wordCount.d.ts +3 -0
- package/dist/types/types.d.ts +226 -0
- package/package.json +66 -0
- package/src/core/Editor.ts +460 -0
- package/src/core/PluginManager.ts +140 -0
- package/src/core/helpers.ts +209 -0
- package/src/css.d.ts +2 -0
- package/src/index.ts +87 -0
- package/src/plugins/align.ts +72 -0
- package/src/plugins/autoLinkify.ts +34 -0
- package/src/plugins/autosave.ts +69 -0
- package/src/plugins/block.ts +32 -0
- package/src/plugins/caseTransform.ts +54 -0
- package/src/plugins/codeBlock.ts +93 -0
- package/src/plugins/colors.ts +68 -0
- package/src/plugins/darkMode.ts +123 -0
- package/src/plugins/direction.ts +30 -0
- package/src/plugins/dragDrop.ts +68 -0
- package/src/plugins/emoji.ts +188 -0
- package/src/plugins/emojiAutocomplete.ts +183 -0
- package/src/plugins/findReplace.ts +229 -0
- package/src/plugins/floatingToolbar.ts +258 -0
- package/src/plugins/fontFamily.ts +41 -0
- package/src/plugins/fontSize.ts +32 -0
- package/src/plugins/fullscreen.ts +36 -0
- package/src/plugins/history.ts +14 -0
- package/src/plugins/hr.ts +118 -0
- package/src/plugins/iframe.ts +88 -0
- package/src/plugins/image.ts +107 -0
- package/src/plugins/imageProps.ts +119 -0
- package/src/plugins/imageTools.ts +344 -0
- package/src/plugins/indent.ts +29 -0
- package/src/plugins/index.ts +101 -0
- package/src/plugins/inline.ts +17 -0
- package/src/plugins/inlineCode.ts +21 -0
- package/src/plugins/keyboardShortcuts.ts +92 -0
- package/src/plugins/lineHeight.ts +40 -0
- package/src/plugins/link.ts +344 -0
- package/src/plugins/linkTooltip.ts +63 -0
- package/src/plugins/list.ts +141 -0
- package/src/plugins/markdown.ts +61 -0
- package/src/plugins/mediaEmbed.ts +44 -0
- package/src/plugins/pasteImage.ts +61 -0
- package/src/plugins/pastePlain.ts +43 -0
- package/src/plugins/pre.ts +11 -0
- package/src/plugins/readOnly.ts +46 -0
- package/src/plugins/shortcutCustomizer.ts +125 -0
- package/src/plugins/shortcutsHelp.ts +51 -0
- package/src/plugins/source.ts +77 -0
- package/src/plugins/specialChars.ts +64 -0
- package/src/plugins/statusBar.ts +85 -0
- package/src/plugins/subSuper.ts +20 -0
- package/src/plugins/table.ts +166 -0
- package/src/plugins/tableBg.ts +11 -0
- package/src/plugins/tableTools.ts +475 -0
- package/src/plugins/toolbarCollapse.ts +14 -0
- package/src/plugins/unlink.ts +29 -0
- package/src/plugins/wordCount.ts +34 -0
- package/src/styles/base.css +258 -0
- package/src/styles/editor.css +309 -0
- package/src/styles/index.css +6 -0
- package/src/types.ts +278 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tulih-editor.es.js","sources":["../src/core/PluginManager.ts","../src/core/helpers.ts","../src/core/Editor.ts","../src/plugins/block.ts","../src/plugins/inline.ts","../src/plugins/pre.ts","../src/plugins/inlineCode.ts","../src/plugins/subSuper.ts","../src/plugins/keyboardShortcuts.ts","../src/plugins/readOnly.ts","../src/plugins/linkTooltip.ts","../src/plugins/emojiAutocomplete.ts","../src/plugins/statusBar.ts","../src/plugins/codeBlock.ts","../src/plugins/mediaEmbed.ts","../src/plugins/dragDrop.ts","../src/plugins/pastePlain.ts","../src/plugins/findReplace.ts","../src/plugins/indent.ts","../src/plugins/list.ts","../src/plugins/lineHeight.ts","../src/plugins/fontSize.ts","../src/plugins/fontFamily.ts","../src/plugins/specialChars.ts","../src/plugins/colors.ts","../src/plugins/tableBg.ts","../src/plugins/align.ts","../src/plugins/markdown.ts","../src/plugins/link.ts","../src/plugins/image.ts","../src/plugins/imageProps.ts","../src/plugins/imageTools.ts","../src/plugins/iframe.ts","../src/plugins/table.ts","../src/plugins/tableTools.ts","../src/plugins/hr.ts","../src/plugins/unlink.ts","../src/plugins/emoji.ts","../src/plugins/direction.ts","../src/plugins/source.ts","../src/plugins/history.ts","../src/plugins/fullscreen.ts","../src/plugins/toolbarCollapse.ts","../src/plugins/autosave.ts","../src/plugins/autoLinkify.ts","../src/plugins/caseTransform.ts","../src/plugins/shortcutsHelp.ts","../src/plugins/floatingToolbar.ts","../src/plugins/darkMode.ts","../src/plugins/shortcutCustomizer.ts","../src/plugins/index.ts","../src/index.ts"],"sourcesContent":["import type { Plugin, PluginContext, Features, PluginManagerInstance } from '../types';\n\n/**\n * Registry and lifecycle manager for plugins. Resolves toolbar order,\n * dependency order, and one-time CSS injection.\n */\nexport default class PluginManager implements PluginManagerInstance {\n private _plugins: Plugin[] = [];\n private _map: Record<string, Plugin> = {};\n private _injectedCSS = new Set<string>();\n private _cssInjected = false;\n\n register(name: string, plugin: Plugin): this {\n if (this._map[name]) {\n throw new Error('Plugin \"' + name + '\" is already registered');\n }\n plugin.name = name;\n plugin.deps = plugin.deps || [];\n plugin.order = plugin.order || 100;\n this._plugins.push(plugin);\n this._map[name] = plugin;\n return this;\n }\n\n unregister(name: string): void {\n const plugin = this._map[name];\n if (!plugin) return;\n if (plugin.destroy) plugin.destroy(undefined as unknown as PluginContext);\n const idx = this._plugins.indexOf(plugin);\n if (idx !== -1) this._plugins.splice(idx, 1);\n delete this._map[name];\n }\n\n get(name: string): Plugin | null {\n return this._map[name] || null;\n }\n\n has(name: string): boolean {\n return !!this._map[name];\n }\n\n getNames(): string[] {\n return Object.keys(this._map);\n }\n\n private _resolveOrder(): Plugin[] {\n const sorted: Plugin[] = [];\n const visited: Record<string, boolean> = {};\n const visiting: Record<string, boolean> = {};\n const map = this._map;\n\n function visit(name: string): void {\n if (visited[name]) return;\n if (visiting[name]) throw new Error('Circular dependency: ' + name);\n visiting[name] = true;\n const p = map[name];\n if (p && p.deps) {\n p.deps.forEach((dep) => {\n if (!map[dep]) throw new Error('Plugin \"' + name + '\" depends on \"' + dep + '\" but not registered');\n visit(dep);\n });\n }\n visiting[name] = false;\n visited[name] = true;\n sorted.push(map[name]);\n }\n\n const ordered = this._plugins.slice().sort((a, b) => (a.order || 0) - (b.order || 0));\n ordered.forEach((p) => visit(p.name));\n\n return sorted;\n }\n\n initAll(ctx: PluginContext): void {\n this._resolveOrder().forEach((plugin) => {\n if (plugin.init) plugin.init(ctx);\n });\n }\n\n destroyAll(ctx: PluginContext): void {\n const reversed = this._plugins.slice().reverse();\n reversed.forEach((plugin) => {\n if (plugin.destroy) plugin.destroy(ctx);\n });\n }\n\n getToolbarHTML(features: Features, toolbar?: string[][]): string {\n if (toolbar && Array.isArray(toolbar)) {\n const parts: string[] = [];\n toolbar.forEach((group, i) => {\n if (i > 0) parts.push('<div class=\"te-divider\"></div>');\n group.forEach((name) => {\n const p = this._map[name];\n if (!p || features[name] === false) return;\n const html = typeof p.toolbarHTML === 'function' ? p.toolbarHTML(features) : p.toolbarHTML;\n if (html) parts.push(html);\n });\n });\n return parts.join('\\n');\n }\n\n const plugins = this._resolveOrder().filter((p) => features[p.name] !== false && p.toolbarHTML);\n const parts: string[] = [];\n let lastGroup = -1;\n plugins.forEach((p) => {\n const html = typeof p.toolbarHTML === 'function' ? p.toolbarHTML(features) : p.toolbarHTML;\n if (!html) return;\n const group = Math.floor((p.order || 0) / 10);\n if (lastGroup !== -1 && group !== lastGroup) {\n parts.push('<div class=\"te-divider\"></div>');\n }\n parts.push(html);\n lastGroup = group;\n });\n return parts.join('\\n');\n }\n\n getModalHTML(features: Features): string {\n const plugins = this._resolveOrder().filter((p) => features[p.name] !== false && p.modalHTML);\n return plugins\n .map((p) => (typeof p.modalHTML === 'function' ? p.modalHTML(features) : p.modalHTML))\n .filter(Boolean)\n .join('\\n');\n }\n\n injectAllCSS(): void {\n if (this._cssInjected) return;\n this._cssInjected = true;\n this._resolveOrder().forEach((p) => {\n if (!p.css || this._injectedCSS.has(p.name)) return;\n this._injectedCSS.add(p.name);\n const cssText = typeof p.css === 'function' ? p.css({}) : p.css;\n if (!cssText) return;\n const style = document.createElement('style');\n style.setAttribute('data-te-css', p.name);\n style.textContent = cssText;\n document.head.appendChild(style);\n });\n }\n}\n","/**\n * Shared DOM utilities used by the editor core and plugins.\n */\n\nconst blockSelector = 'p,h1,h2,h3,blockquote,pre,ul,ol,li,table,hr,iframe,.te-embed';\nconst inlineTags = ['A', 'B', 'I', 'U', 'S', 'STRONG', 'EM', 'SPAN', 'SMALL', 'MARK', 'CODE', 'KBD', 'SUB', 'SUP'];\n\nfunction qs(selector: string, root?: Document | Element | null): Element | null {\n return (root || document).querySelector(selector);\n}\n\nfunction qsa(selector: string, root?: Document | Element | null): Element[] {\n return Array.prototype.slice.call((root || document).querySelectorAll(selector));\n}\n\nfunction exec(command: string, value?: string): void {\n document.execCommand(command, false, value);\n}\n\nfunction getSelectionHtml(): string {\n const selection = window.getSelection();\n if (!selection || selection.rangeCount === 0) return '';\n const range = selection.getRangeAt(0).cloneRange();\n const div = document.createElement('div');\n div.appendChild(range.cloneContents());\n return div.innerHTML;\n}\n\nfunction hasBlockDescendant(el: Element): boolean {\n return !!el.querySelector(blockSelector);\n}\n\nfunction isInlineElement(el: Node): boolean {\n if (el.nodeType !== 1) return false;\n const tag = (el as Element).tagName;\n if (tag === 'IMG' || tag === 'BR' || tag === 'IFRAME') return true;\n return inlineTags.indexOf(tag) !== -1;\n}\n\nfunction wrapNodeInP(node: Node): HTMLParagraphElement {\n const p = document.createElement('p');\n node.parentNode!.insertBefore(p, node);\n p.appendChild(node);\n return p;\n}\n\nfunction wrapIframe(node: Element | null): HTMLDivElement | undefined {\n if (!node || node.tagName !== 'IFRAME') return;\n const wrapper = document.createElement('div');\n wrapper.className = 'te-embed';\n wrapper.setAttribute('contenteditable', 'false');\n node.setAttribute('contenteditable', 'false');\n node.setAttribute('draggable', 'false');\n node.setAttribute('tabindex', '-1');\n node.parentNode!.insertBefore(wrapper, node);\n wrapper.appendChild(node);\n return wrapper;\n}\n\nfunction normalizeParagraphs(root: Element | null): void {\n if (!root) return;\n let child = root.firstChild;\n while (child) {\n const next = child.nextSibling;\n if (child.nodeType === 3) {\n if ((child.textContent || '').trim() === '') {\n root.removeChild(child);\n } else {\n wrapNodeInP(child);\n }\n } else if (child.nodeType === 1) {\n const el = child as Element;\n const tag = el.tagName;\n if (tag === 'DIV') {\n if (el.classList.contains('te-embed') || el.querySelector('iframe,video,audio,.te-embed')) {\n // keep embed wrappers intact\n } else if (!hasBlockDescendant(el)) {\n const p = document.createElement('p');\n while (el.firstChild) {\n p.appendChild(el.firstChild);\n }\n root.replaceChild(p, el);\n }\n } else if (tag === 'IFRAME') {\n wrapIframe(el);\n } else if (isInlineElement(el)) {\n wrapNodeInP(el);\n }\n }\n child = next;\n }\n}\n\nfunction ensureInitialParagraph(root: Element | null): void {\n if (!root) return;\n if (root.querySelector(blockSelector)) return;\n if (!root.firstChild) {\n const p0 = document.createElement('p');\n p0.innerHTML = '<br>';\n root.appendChild(p0);\n return;\n }\n const p = document.createElement('p');\n while (root.firstChild) {\n p.appendChild(root.firstChild);\n }\n root.appendChild(p);\n}\n\nfunction isInsideEditor(editor: Element, node: Node | null): boolean {\n if (!node) return false;\n if (node === editor) return true;\n return editor.contains(node);\n}\n\nfunction getBlockElement(editor: Element): Element | null {\n const sel = window.getSelection();\n if (!sel || sel.rangeCount === 0) return null;\n let node: Node | null = sel.anchorNode;\n if (node && node.nodeType === 3) node = node.parentNode;\n if (!isInsideEditor(editor, node)) return null;\n if (node && (node as Element).closest) {\n return (node as Element).closest('p,h1,h2,h3,blockquote,pre,li,div');\n }\n return null;\n}\n\nfunction setBtnActive(toolbar: Element | null, selector: string, active: boolean): void {\n if (!toolbar) return;\n const btn = toolbar.querySelector(selector);\n if (!btn) return;\n if (active) btn.classList.add('active');\n else btn.classList.remove('active');\n}\n\nfunction updateToolbarState(\n editor: HTMLElement,\n blockSelect: HTMLSelectElement | null,\n alignSelect: HTMLSelectElement | null,\n toolbar: HTMLElement | null,\n): void {\n const blockEl = getBlockElement(editor);\n if (blockSelect) {\n let tag = '';\n if (blockEl) {\n let t = blockEl.tagName.toLowerCase();\n if (t === 'div' || t === 'li') t = 'p';\n if (['p', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'blockquote', 'pre'].indexOf(t) !== -1) {\n tag = t;\n }\n }\n blockSelect.value = tag || 'p';\n }\n if (alignSelect) {\n let align = '';\n if (blockEl) {\n try {\n const cs = window.getComputedStyle(blockEl);\n let ta = cs && cs.textAlign ? cs.textAlign.toLowerCase() : '';\n if (ta === 'start') ta = 'left';\n if (ta === 'left' || ta === 'center' || ta === 'right' || ta === 'justify') {\n align = ta;\n }\n } catch (_) { /* ignore */ }\n }\n alignSelect.value = align || '';\n }\n try {\n setBtnActive(toolbar, '[data-cmd=\"bold\"]', document.queryCommandState('bold'));\n setBtnActive(toolbar, '[data-cmd=\"italic\"]', document.queryCommandState('italic'));\n setBtnActive(toolbar, '[data-cmd=\"underline\"]', document.queryCommandState('underline'));\n setBtnActive(toolbar, '[data-cmd=\"strikeThrough\"]', document.queryCommandState('strikeThrough'));\n } catch (_) { /* ignore */ }\n let inOL = false;\n let inUL = false;\n if (blockEl && blockEl.closest) {\n inOL = !!blockEl.closest('ol');\n inUL = !!blockEl.closest('ul');\n }\n setBtnActive(toolbar, '[data-cmd=\"insertOrderedList\"]', inOL);\n setBtnActive(toolbar, '[data-cmd=\"insertUnorderedList\"]', inUL);\n const isQuote = blockEl && blockEl.tagName === 'BLOCKQUOTE';\n const isPre = blockEl && blockEl.tagName === 'PRE';\n setBtnActive(toolbar, '[data-cmd=\"formatBlock\"][data-val=\"blockquote\"]', !!isQuote);\n setBtnActive(toolbar, '[data-cmd=\"formatBlock\"][data-val=\"pre\"]', !!isPre);\n}\n\nfunction escapeHtml(str: string): string {\n return String(str)\n .replace(/&/g, '&')\n .replace(/</g, '<')\n .replace(/>/g, '>')\n .replace(/\"/g, '"')\n .replace(/'/g, ''');\n}\n\nfunction removeNode(node: Node | null): void {\n if (node && node.parentNode) {\n node.parentNode.removeChild(node);\n }\n}\n\nexport {\n qs, qsa, exec, getSelectionHtml,\n blockSelector, inlineTags, hasBlockDescendant, isInlineElement,\n wrapNodeInP, wrapIframe, normalizeParagraphs, ensureInitialParagraph,\n isInsideEditor, getBlockElement, setBtnActive, updateToolbarState,\n escapeHtml, removeNode,\n};\n","import * as H from './helpers';\nimport type {\n EditorOptions,\n ResolvedOptions,\n Features,\n EditorUtils,\n PluginContext,\n SanitizeOptions,\n TulihEditorStatic,\n EditorInstance,\n TeEditorElement,\n TeWrapperElement,\n} from '../types';\n\nfunction buildEditorHTML(toolbarHTML: string, modalHTML: string): string {\n return '' +\n '<div class=\"te-container\">' +\n ' <div class=\"te-toolbar mb-0\">' +\n toolbarHTML +\n ' </div>' +\n ' <div class=\"te-editor\" contenteditable=\"true\" placeholder=\"Start typing...\"></div>' +\n modalHTML +\n '</div>';\n}\n\nconst DEFAULT_FEATURES: Features = {\n block: false, inline: false, inlineCode: false, subSuper: false, removeFormat: false,\n codeBlock: false, mediaEmbed: false, dragDrop: false,\n readOnly: false, linkTooltip: false, emojiAutocomplete: false, statusBar: false,\n pastePlain: false, findReplace: false, indent: false, list: false, autoLinkify: false, caseTransform: false, shortcutsHelp: false,\n lineHeight: false, fontSize: false, fontFamily: false, specialChars: false,\n colors: false, tableBg: false, align: false, markdown: false,\n link: false, image: false, imageProps: false, imageTools: false,\n iframe: false, table: false, tableTools: false, hr: false,\n unlink: false, emoji: false, direction: false,\n source: false, history: false, fullscreen: false,\n toolbarCollapse: false, autosave: false, floatingToolbar: false,\n darkMode: false, shortcutCustomizer: false, minimal: false,\n};\n\nconst DEFAULT_SANITIZE: SanitizeOptions = {\n allowedTags: ['p', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'blockquote', 'pre', 'code', 'strong', 'em', 'u', 's', 'span', 'a', 'img', 'iframe', 'ul', 'ol', 'li', 'table', 'thead', 'tbody', 'tfoot', 'tr', 'th', 'td', 'br', 'hr'],\n allowedAttributes: ['href', 'src', 'alt', 'title', 'width', 'height', 'class', 'id', 'style', 'target', 'rel', 'allow', 'allowfullscreen', 'frameborder'],\n};\nconst DEFAULT_URL_SCHEMES = ['http', 'https', 'mailto', 'tel'];\nconst DEFAULT_IMAGE_SCHEMES = ['http', 'https', 'data'];\nconst DEFAULT_IFRAME_ALLOWLIST = ['youtube.com', 'www.youtube.com', 'youtu.be', 'player.vimeo.com', 'vimeo.com'];\nconst DEFAULT_IFRAME_SANDBOX = 'allow-scripts allow-same-origin allow-presentation';\nconst DEFAULT_IFRAME_ALLOW = 'accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share';\n\nexport default class Editor implements EditorInstance {\n features!: Features;\n options!: ResolvedOptions;\n utils!: EditorUtils;\n container: HTMLElement | null = null;\n editor: HTMLElement | null = null;\n toolbar: HTMLElement | null = null;\n textarea!: HTMLTextAreaElement;\n private _ctx: PluginContext | null = null;\n\n constructor(target: string | Element, options: EditorOptions | undefined, TulihEditor: TulihEditorStatic) {\n const el = (typeof target === 'string' ? document.querySelector(target) : target) as HTMLElement | null;\n if (!el) return;\n const isTextarea = String(el.tagName).toUpperCase() === 'TEXTAREA';\n const hasAttr = el.matches && el.matches('textarea[data-tulih-editor]');\n if (!isTextarea && !hasAttr) return;\n const sibling = el.nextElementSibling;\n if (sibling && sibling.querySelector && sibling.querySelector('.te-editor')) return;\n\n const opts: EditorOptions = options || {};\n const textarea = el as HTMLTextAreaElement;\n\n const isMinimal = opts.minimal || (opts.features && opts.features.minimal);\n if (isMinimal) {\n this.features = Object.assign({}, DEFAULT_FEATURES, { floatingToolbar: true, link: true, linkTooltip: true }, opts.features || {});\n } else {\n const allOn: Features = {};\n Object.keys(DEFAULT_FEATURES).forEach((k) => {\n if (k !== 'minimal') allOn[k] = true;\n });\n this.features = Object.assign({}, allOn, opts.features || {});\n }\n this.options = {\n sanitize: Object.assign({}, DEFAULT_SANITIZE, opts.sanitize || {}),\n urlSchemes: Array.isArray(opts.allowedUrlSchemes) ? opts.allowedUrlSchemes : DEFAULT_URL_SCHEMES,\n imageSchemes: Array.isArray(opts.allowedImageSchemes) ? opts.allowedImageSchemes : DEFAULT_IMAGE_SCHEMES,\n iframeAllowlist: Array.isArray(opts.iframeAllowlist) ? opts.iframeAllowlist : DEFAULT_IFRAME_ALLOWLIST,\n iframeSandbox: typeof opts.iframeSandbox === 'string' ? opts.iframeSandbox : DEFAULT_IFRAME_SANDBOX,\n iframeAllow: typeof opts.iframeAllow === 'string' ? opts.iframeAllow : DEFAULT_IFRAME_ALLOW,\n readOnly: !!opts.readOnly,\n };\n\n const self = this;\n\n function sanitizeHTML(html: string, sanOpts?: Partial<SanitizeOptions>): string {\n const allowedTags = new Set((sanOpts && sanOpts.allowedTags) || []);\n const allowedAttrs = new Set((sanOpts && sanOpts.allowedAttributes) || []);\n const container = document.createElement('div');\n container.innerHTML = String(html || '');\n const walker = document.createTreeWalker(container, NodeFilter.SHOW_ELEMENT | NodeFilter.SHOW_COMMENT, null);\n const toUnwrap: Element[] = [];\n const comments: Node[] = [];\n while (walker.nextNode()) {\n const node = walker.currentNode as Element;\n if (node.nodeType === 8) { comments.push(node); continue; }\n const tag = node.tagName ? node.tagName.toLowerCase() : '';\n if (tag && !allowedTags.has(tag)) {\n toUnwrap.push(node);\n continue;\n }\n if (node.attributes) {\n const attrs = Array.prototype.slice.call(node.attributes) as Attr[];\n attrs.forEach((attr) => {\n const aname = attr.name.toLowerCase();\n if (aname.startsWith('on')) { node.removeAttribute(attr.name); return; }\n if (!allowedAttrs.has(aname)) { node.removeAttribute(attr.name); return; }\n if (aname === 'href' && attr.value) { if (!isSafeUrl(attr.value, self.options.urlSchemes)) { node.removeAttribute(attr.name); } }\n if (aname === 'src' && attr.value && tag === 'img') { if (!isSafeUrl(attr.value, self.options.imageSchemes)) { node.removeAttribute(attr.name); } }\n });\n }\n if (tag === 'iframe') {\n const src = node.getAttribute('src') || '';\n if (!isAllowedIframeUrl(src)) {\n toUnwrap.push(node);\n } else {\n if (self.options.iframeSandbox) node.setAttribute('sandbox', self.options.iframeSandbox);\n if (self.options.iframeAllow) node.setAttribute('allow', self.options.iframeAllow);\n node.setAttribute('frameborder', '0');\n (node as HTMLElement).style.maxWidth = '100%';\n (node as HTMLElement).style.border = '0';\n }\n }\n }\n comments.forEach((c) => { if (c.parentNode) c.parentNode.removeChild(c); });\n toUnwrap.forEach((node) => {\n if (!node.parentNode) return;\n while (node.firstChild) { node.parentNode.insertBefore(node.firstChild, node); }\n node.parentNode.removeChild(node);\n });\n return container.innerHTML;\n }\n\n function isSafeUrl(url: string, schemes: string[]): boolean {\n try {\n const u = new URL(url, window.location.origin);\n return schemes.indexOf(u.protocol.replace(':', '')) !== -1;\n } catch (_) { return false; }\n }\n\n function isAllowedIframeUrl(url: string): boolean {\n try {\n const u = new URL(url, window.location.origin);\n const host = u.hostname.toLowerCase();\n return self.options.iframeAllowlist.some((allowed) => host === allowed || host.endsWith('.' + allowed));\n } catch (_) { return false; }\n }\n\n this.utils = { sanitizeHTML, isSafeUrl, isAllowedIframeUrl };\n\n const toolbarHTML = TulihEditor.pluginManager.getToolbarHTML(self.features, opts.toolbar);\n const modalHTML = TulihEditor.pluginManager.getModalHTML(self.features);\n const wrapper = document.createElement('div') as TeWrapperElement;\n wrapper.innerHTML = buildEditorHTML(toolbarHTML, modalHTML);\n el.style.display = 'none';\n el.parentNode!.insertBefore(wrapper, el.nextSibling);\n\n const editorEl = wrapper.querySelector('.te-editor') as TeEditorElement;\n const toolbarEl = wrapper.querySelector('.te-toolbar') as HTMLElement;\n\n try { const raw = textarea.value || ''; const safeInit = sanitizeHTML(raw, self.options.sanitize); editorEl.innerHTML = safeInit; } catch (_) { /* ignore */ }\n try { H.normalizeParagraphs(editorEl); H.ensureInitialParagraph(editorEl); } catch (_) { /* ignore */ }\n try { H.ensureInitialParagraph(editorEl); } catch (_) { /* ignore */ }\n\n if (opts.height) {\n editorEl.style.height = typeof opts.height === 'number' ? opts.height + 'px' : String(opts.height);\n editorEl.style.overflow = 'auto';\n }\n\n this.container = wrapper;\n this.editor = editorEl;\n this.toolbar = toolbarEl;\n this.textarea = textarea;\n\n try { document.execCommand('defaultParagraphSeparator', false, 'p'); } catch (_) { /* ignore */ }\n\n function updateActiveStates(): void {\n try {\n ['bold', 'italic', 'underline', 'strikeThrough'].forEach((cmd) => {\n const btn = toolbarEl.querySelector('[data-cmd=\"' + cmd + '\"]');\n if (!btn) return;\n if (document.queryCommandState(cmd)) btn.classList.add('active');\n else btn.classList.remove('active');\n });\n const undoBtn = toolbarEl.querySelector('[data-cmd=\"undo\"]') as HTMLButtonElement | null;\n const redoBtn = toolbarEl.querySelector('[data-cmd=\"redo\"]') as HTMLButtonElement | null;\n const h = editorEl._tableHist;\n if (undoBtn) {\n const canUndo = document.queryCommandEnabled('undo') || (h && h.undo.length > 0);\n undoBtn.toggleAttribute('disabled', !canUndo);\n }\n if (redoBtn) {\n const canRedo = document.queryCommandEnabled('redo') || (h && h.redo.length > 0);\n redoBtn.toggleAttribute('disabled', !canRedo);\n }\n const sel = window.getSelection();\n let node: Node | null = sel && sel.anchorNode;\n if (node && node.nodeType === 3) node = node.parentNode;\n const elNode = node as Element | null;\n const inOL = elNode && elNode.closest && elNode.closest('ol');\n const inUL = elNode && elNode.closest && elNode.closest('ul');\n const olBtn = toolbarEl.querySelector('[data-cmd=\"insertOrderedList\"]');\n const ulBtn = toolbarEl.querySelector('[data-cmd=\"insertUnorderedList\"]');\n if (olBtn) olBtn.classList.toggle('active', !!inOL);\n if (ulBtn) ulBtn.classList.toggle('active', !!inUL);\n } catch (_) { /* ignore */ }\n }\n\n document.addEventListener('selectionchange', () => {\n if (wrapper.contains(document.activeElement)) { updateActiveStates(); }\n });\n\n toolbarEl.querySelectorAll('[data-cmd]').forEach((btn) => {\n btn.addEventListener('click', () => {\n const cmd = btn.getAttribute('data-cmd');\n const val = btn.getAttribute('data-val') || undefined;\n if (cmd === 'createLink' || cmd === 'insertImage' || cmd === 'insertIframe' || cmd === 'insertTable' || cmd === 'editSource' || cmd === 'indent' || cmd === 'outdent' || cmd === 'findReplace' || cmd === 'togglePastePlain' || cmd === 'specialChars' || cmd === 'fullscreen' || cmd === 'emoji' || cmd === 'codeBlock' || cmd === 'toggleReadOnly' || cmd === 'shortcutsHelp' || cmd === 'alignLeft' || cmd === 'alignCenter' || cmd === 'alignRight' || cmd === 'alignJustify' || cmd === 'toggleDark' || cmd === 'customizeShortcuts') {\n return;\n }\n function clearFrHighlights(): void {\n editorEl.querySelectorAll('.te-fr-match, .te-fr-active').forEach((m) => {\n const parent = m.parentNode;\n if (!parent) return;\n while (m.firstChild) parent.insertBefore(m.firstChild, m);\n parent.removeChild(m);\n });\n }\n if (cmd === 'undo') {\n const h = editorEl._tableHist;\n if (h && h.undo.length) {\n clearFrHighlights();\n h.redo.push(editorEl.innerHTML);\n editorEl.contentEditable = 'false';\n editorEl.innerHTML = h.undo.pop() as string;\n editorEl.contentEditable = 'true';\n clearFrHighlights();\n editorEl.focus();\n updateActiveStates();\n return;\n }\n }\n if (cmd === 'redo') {\n const h = editorEl._tableHist;\n if (h && h.redo.length) {\n clearFrHighlights();\n h.undo.push(editorEl.innerHTML);\n editorEl.contentEditable = 'false';\n editorEl.innerHTML = h.redo.pop() as string;\n editorEl.contentEditable = 'true';\n clearFrHighlights();\n editorEl.focus();\n updateActiveStates();\n return;\n }\n }\n document.execCommand(cmd as string, false, val);\n editorEl.focus();\n updateActiveStates();\n });\n });\n\n wrapper.querySelectorAll('[data-te-close]').forEach((x) => {\n x.addEventListener('click', () => {\n const modal = (x as Element).closest('.te-modal');\n if (modal) modal.classList.remove('is-open');\n });\n });\n\n try { H.ensureInitialParagraph(editorEl); } catch (_) { /* ignore */ }\n\n function saveSel(): void {\n const s = window.getSelection();\n if (s && s.rangeCount > 0) { wrapper.__savedRange = s.getRangeAt(0).cloneRange(); }\n }\n function restoreSel(): void {\n const r = wrapper.__savedRange;\n if (!r) return;\n const s = window.getSelection();\n if (!s) return;\n s.removeAllRanges();\n s.addRange(r);\n }\n\n function insertImageFile(file: File | Blob): void {\n const handler = TulihEditor.onUploadImage || function (f: File | Blob, cb: (url: string) => void): void {\n const r = new FileReader();\n r.onload = () => { cb(r.result as string); };\n r.readAsDataURL(f);\n };\n handler(file, (url) => {\n if (!url) return;\n const name = (file as File).name || '';\n const html = '<img src=\"' + url.replace(/\"/g, '"') + '\" alt=\"' + name.replace(/\"/g, '"') + '\" style=\"max-width:100%;\" />';\n document.execCommand('insertHTML', false, html);\n });\n }\n\n function cleanWordHtml(html: string): string {\n if (!html) return '';\n let out = String(html);\n if (out.indexOf('mso-') === -1 && out.indexOf('xmlns:o') === -1 && out.indexOf('google-docs') === -1) return out;\n out = out.replace(/<!--[\\s\\S]*?-->/g, '');\n out = out.replace(/<meta[^>]*>/gi, '');\n out = out.replace(/<link[^>]*>/gi, '');\n out = out.replace(/<o:[^>]*>[\\s\\S]*?<\\/o:[^>]*>/gi, '');\n out = out.replace(/<w:[^>]*>[\\s\\S]*?<\\/w:[^>]*>/gi, '');\n out = out.replace(/<style[^>]*>[\\s\\S]*?<\\/style>/gi, '');\n out = out.replace(/ class=\"[^\"]*Mso[^\"]*\"/gi, '');\n out = out.replace(/ class=\"[^\"]*\" style=\"\"/gi, '');\n out = out.replace(/ style=\"[^\"]*mso-[^;]*[^\"]*\"/gi, '');\n out = out.replace(/<span[^>]*style=\"[^\"]*mso-[^\"]*\"[^>]*>/gi, '<span>');\n out = out.replace(/<span[^>]*><\\/span>/gi, '');\n out = out.replace(/(<(p|h[1-6]|div|span|b|i|u|strong|em))[^>]*>/gi, '$1>');\n return out;\n }\n\n editorEl.addEventListener('paste', (e: ClipboardEvent) => {\n try {\n const files = e.clipboardData && e.clipboardData.files;\n if (files && files.length > 0) {\n let pasted = false;\n for (let fi = 0; fi < files.length; fi++) {\n if (/^image\\//i.test(files[fi].type)) {\n if (!pasted) { e.preventDefault(); pasted = true; }\n insertImageFile(files[fi]);\n }\n }\n if (pasted) return;\n }\n const items = e.clipboardData && e.clipboardData.items;\n if (items && items.length > 0) {\n for (let ii = 0; ii < items.length; ii++) {\n if (items[ii].kind === 'file' && /^image\\//i.test(items[ii].type)) {\n e.preventDefault();\n const imgFile = items[ii].getAsFile();\n if (imgFile) { insertImageFile(imgFile); }\n return;\n }\n }\n }\n if (window.navigator && window.navigator.clipboard && typeof window.navigator.clipboard.read === 'function') {\n window.navigator.clipboard.read().then((clipItems) => {\n for (let ci = 0; ci < clipItems.length; ci++) {\n const ciTypes = clipItems[ci].types || [];\n for (let ct = 0; ct < ciTypes.length; ct++) {\n if (/^image\\//i.test(ciTypes[ct])) {\n clipItems[ci].getType(ciTypes[ct]).then((blob) => {\n insertImageFile(blob);\n });\n break;\n }\n }\n }\n }).catch(() => { /* ignore */ });\n }\n e.preventDefault();\n const rawHtml = (e.clipboardData && e.clipboardData.getData('text/html')) || '';\n const text = (e.clipboardData && e.clipboardData.getData('text/plain')) || '';\n const toInsert = cleanWordHtml(rawHtml) || (text ? '<p>' + text.replace(/\\n/g, '<br>') + '</p>' : '');\n const safe = sanitizeHTML(toInsert, self.options.sanitize);\n document.execCommand('insertHTML', false, safe);\n setTimeout(() => { try { H.ensureInitialParagraph(editorEl); H.normalizeParagraphs(editorEl); } catch (_) { /* ignore */ } }, 0);\n } catch (_) { setTimeout(() => { H.normalizeParagraphs(editorEl); }, 0); }\n });\n\n editorEl.addEventListener('focus', () => { try { H.ensureInitialParagraph(editorEl); } catch (_) { /* ignore */ } });\n editorEl.addEventListener('input', () => {\n setTimeout(() => { try { H.ensureInitialParagraph(editorEl); H.normalizeParagraphs(editorEl); } catch (_) { /* ignore */ } }, 0);\n });\n\n const ctx: PluginContext = {\n wrapper,\n editor: editorEl,\n toolbar: toolbarEl,\n textarea,\n features: self.features,\n options: self.options,\n utils: self.utils,\n TulihEditor,\n saveSel,\n restoreSel,\n updateActiveStates,\n };\n\n if (isMinimal) {\n wrapper.classList.add('te-minimal');\n }\n\n self._ctx = ctx;\n\n TulihEditor.pluginManager.initAll(ctx);\n\n TulihEditor.instances.push(this);\n }\n\n getContent(): string {\n return this.editor ? this.editor.innerHTML : '';\n }\n\n setContent(html: string): void {\n if (!this.editor) return;\n const safe = this.utils.sanitizeHTML(html, this.options.sanitize);\n this.editor.innerHTML = safe;\n try { H.ensureInitialParagraph(this.editor); H.normalizeParagraphs(this.editor); } catch (_) { /* ignore */ }\n }\n\n getText(): string {\n return this.editor ? this.editor.textContent || '' : '';\n }\n\n getWordCount(): number {\n const text = this.getText().trim();\n if (!text) return 0;\n return text.split(/\\s+/).length;\n }\n\n getCharCount(): number {\n return this.getText().length;\n }\n\n setReadOnly(ro: boolean): void {\n if (!this._ctx) return;\n const ctx = this._ctx;\n const isRo = ctx.editor.contentEditable === 'false';\n if (ro === isRo) return;\n const btn = ctx.wrapper.querySelector('[data-cmd=\"toggleReadOnly\"]') as HTMLElement | null;\n if (btn) btn.click();\n }\n\n isReadOnly(): boolean {\n return !!(this._ctx && this._ctx.editor && this._ctx.editor.contentEditable === 'false');\n }\n\n destroy(): void {\n if (!this.container || !this.container.parentNode) return;\n const instances = this._ctx ? this._ctx.TulihEditor.instances : [];\n const myIdx = instances.indexOf(this);\n if (myIdx !== -1) instances.splice(myIdx, 1);\n if (this._ctx) this._ctx.TulihEditor.pluginManager.destroyAll(this._ctx);\n const textarea = this.textarea;\n if (textarea && this.editor) {\n textarea.value = this.editor.innerHTML;\n textarea.style.display = '';\n }\n this.container.parentNode.removeChild(this.container);\n this.editor = null;\n this.container = null;\n this.toolbar = null;\n this._ctx = null;\n }\n}\n","import type { Plugin, PluginContext } from '../types';\n\nconst block: Plugin = {\n name: 'block',\n order: 10,\n toolbarHTML: '' +\n '<select class=\"te-block form-select form-select-sm\">' +\n ' <option value=\"p\">Paragraph</option>' +\n ' <option value=\"h1\">Heading 1</option>' +\n ' <option value=\"h2\">Heading 2</option>' +\n ' <option value=\"h3\">Heading 3</option>' +\n ' <option value=\"h4\">Heading 4</option>' +\n ' <option value=\"h5\">Heading 5</option>' +\n ' <option value=\"h6\">Heading 6</option>' +\n ' <option value=\"blockquote\">Quote</option>' +\n ' <option value=\"pre\">Code</option>' +\n '</select>',\n init(ctx: PluginContext): void {\n if (!ctx.features.block) return;\n const sel = ctx.wrapper.querySelector('.te-block') as HTMLSelectElement | null;\n if (!sel) return;\n sel.addEventListener('change', () => {\n const v = sel.value;\n if (!v) return;\n document.execCommand('formatBlock', false, v);\n ctx.editor.focus();\n ctx.updateActiveStates();\n });\n },\n};\n\nexport default block;\n","import type { Plugin, PluginContext } from '../types';\n\nconst inline: Plugin = {\n name: 'inline',\n order: 20,\n toolbarHTML: '' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Bold\" data-cmd=\"bold\"><i class=\"ti ti-bold\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Italic\" data-cmd=\"italic\"><i class=\"ti ti-italic\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Underline\" data-cmd=\"underline\"><i class=\"ti ti-underline\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Strikethrough\" data-cmd=\"strikeThrough\"><s>S</s></button>' +\n '<div class=\"te-divider\"></div>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Quote\" data-cmd=\"formatBlock\" data-val=\"blockquote\"><strong>\"</strong></button>',\n init(ctx: PluginContext): void {\n }\n};\n\nexport default inline;\n","import type { Plugin, PluginContext } from '../types';\n\nconst pre: Plugin = {\n name: 'pre',\n order: 21,\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Preformatted\" data-cmd=\"formatBlock\" data-val=\"pre\"><i class=\"ti ti-code\"></i></button>',\n init(ctx: PluginContext): void {\n }\n};\n\nexport default pre;\n","import type { Plugin, PluginContext } from '../types';\nimport * as H from '../core/helpers';\n\nconst inlineCode: Plugin = {\n name: 'inlineCode',\n order: 22,\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Inline code\" data-cmd=\"inlineCode\"><i class=\"ti ti-code-circle\"></i></button>',\n init(ctx: PluginContext): void {\n if (!ctx.features.inlineCode) return;\n var btn = ctx.wrapper.querySelector('[data-cmd=\"inlineCode\"]') as HTMLElement | null;\n if (!btn) return;\n btn.addEventListener('click', function () {\n var txt = H.escapeHtml(window.getSelection()!.toString() || 'code');\n var html = '<code>' + txt + '</code>';\n document.execCommand('insertHTML', false, html);\n ctx.editor.focus();\n });\n }\n};\n\nexport default inlineCode;\n","import type { Plugin, PluginContext } from '../types';\n\nconst subSuper: Plugin = {\n name: 'subSuper',\n order: 26,\n toolbarHTML: '' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Subscript\" data-cmd=\"subscript\">x₂</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Superscript\" data-cmd=\"superscript\">x²</button>',\n init(ctx: PluginContext): void {\n if (!ctx.features.subSuper) return;\n ctx.wrapper.querySelectorAll('[data-cmd=\"subscript\"],[data-cmd=\"superscript\"]').forEach(function (btn) {\n btn.addEventListener('click', function () {\n document.execCommand(btn.getAttribute('data-cmd')!, false, undefined);\n ctx.editor.focus();\n });\n });\n }\n};\n\nexport default subSuper;\n","import type { Plugin, PluginContext, TeEditorElement } from '../types';\n\nvar STORAGE_KEY = 'te-shortcut-map';\nvar DEFAULT_MAP = {\n 'Bold': {key:'b', ctrl:true, shift:false},\n 'Italic': {key:'i', ctrl:true, shift:false},\n 'Underline': {key:'u', ctrl:true, shift:false},\n 'Strike': {key:'s', ctrl:true, shift:false},\n 'Undo': {key:'z', ctrl:true, shift:false},\n 'Redo': {key:'z', ctrl:true, shift:true},\n 'RedoAlt': {key:'y', ctrl:true, shift:false},\n 'Link': {key:'k', ctrl:true, shift:false}\n};\n\nfunction loadMap(){\n try {\n var raw = localStorage.getItem(STORAGE_KEY);\n if(raw) return JSON.parse(raw);\n } catch(_){}\n return JSON.parse(JSON.stringify(DEFAULT_MAP));\n}\n\nconst keyboardShortcuts: Plugin = {\n name: 'keyboardShortcuts',\n order: 5,\n init(ctx: PluginContext): void {\n if(ctx.features.keyboardShortcuts === false) return;\n var editor = ctx.editor as TeEditorElement;\n var map = loadMap();\n\n editor.addEventListener('keydown', function(e: KeyboardEvent){\n if(!e.ctrlKey && !e.metaKey) return;\n for(var name in map){\n var s = map[name];\n if(e.key.toLowerCase() === s.key && e.ctrlKey === s.ctrl && e.shiftKey === s.shift){\n e.preventDefault();\n if(name === 'Bold'){ document.execCommand('bold'); }\n else if(name === 'Italic'){ document.execCommand('italic'); }\n else if(name === 'Underline'){ document.execCommand('underline'); }\n else if(name === 'Strike'){ document.execCommand('strikeThrough'); }\n else if(name === 'Undo'){\n var h = editor._tableHist;\n if(h && h.undo.length){\n editor.querySelectorAll('.te-fr-match, .te-fr-active').forEach(function(el){\n var p = el.parentNode; if(!p) return;\n while(el.firstChild) p.insertBefore(el.firstChild, el);\n p.removeChild(el);\n });\n h.redo.push(editor.innerHTML);\n editor.contentEditable = 'false';\n editor.innerHTML = h.undo.pop()!;\n editor.contentEditable = 'true';\n editor.querySelectorAll('.te-fr-match, .te-fr-active').forEach(function(el){\n var p = el.parentNode; if(!p) return;\n while(el.firstChild) p.insertBefore(el.firstChild, el);\n p.removeChild(el);\n });\n editor.focus();\n } else { document.execCommand('undo'); editor.focus(); }\n }\n else if(name === 'Redo' || name === 'RedoAlt'){\n var h = editor._tableHist;\n if(h && h.redo.length){\n editor.querySelectorAll('.te-fr-match, .te-fr-active').forEach(function(el){\n var p = el.parentNode; if(!p) return;\n while(el.firstChild) p.insertBefore(el.firstChild, el);\n p.removeChild(el);\n });\n h.undo.push(editor.innerHTML);\n editor.contentEditable = 'false';\n editor.innerHTML = h.redo.pop()!;\n editor.contentEditable = 'true';\n editor.querySelectorAll('.te-fr-match, .te-fr-active').forEach(function(el){\n var p = el.parentNode; if(!p) return;\n while(el.firstChild) p.insertBefore(el.firstChild, el);\n p.removeChild(el);\n });\n editor.focus();\n } else { document.execCommand('redo'); editor.focus(); }\n }\n else if(name === 'Link'){\n var linkBtn = ctx.wrapper.querySelector('[data-cmd=\"createLink\"]') as HTMLButtonElement | null;\n if(linkBtn) linkBtn.click();\n }\n return;\n }\n }\n });\n }\n};\n\nexport default keyboardShortcuts;\n","import type { Plugin, PluginContext } from '../types';\n\nfunction applyReadOnly(ctx: PluginContext, ro: boolean): void {\n var btn = ctx.wrapper.querySelector('[data-cmd=\"toggleReadOnly\"]');\n if(ro){\n ctx.editor.contentEditable = 'false';\n ctx.wrapper.classList.add('te-readonly');\n if(btn) btn.innerHTML = '<i class=\"ti ti-lock-open\"></i>';\n } else {\n ctx.editor.contentEditable = 'true';\n ctx.wrapper.classList.remove('te-readonly');\n if(btn) btn.innerHTML = '<i class=\"ti ti-lock\"></i>';\n }\n if(btn) btn.classList.toggle('active', ro);\n}\n\nconst readOnly: Plugin = {\n name: 'readOnly',\n order: 75,\n css: '' +\n '.te-readonly-btn.active { background: #fff3cd; border-color: #ffecb5; }' +\n '.te-readonly .te-toolbar select,' +\n '.te-readonly .te-toolbar input,' +\n '.te-readonly .te-toolbar .btn {' +\n ' opacity: .5; pointer-events: none;' +\n '}' +\n '.te-readonly .te-editor { background: #f8f9fa; cursor: default; }',\n toolbarHTML: '',\n init(ctx: PluginContext): void {\n if(ctx.features.readOnly === false) return;\n\n if(ctx.options.readOnly) {\n applyReadOnly(ctx, true);\n }\n\n var btn = ctx.wrapper.querySelector('[data-cmd=\"toggleReadOnly\"]');\n if(!btn) return;\n\n btn.addEventListener('click', function(){\n var isRo = ctx.editor.contentEditable !== 'false';\n applyReadOnly(ctx, !isRo);\n });\n }\n};\n\nexport default readOnly;\n","import type { Plugin, PluginContext } from '../types';\n\nconst linkTooltip: Plugin = {\n name: 'linkTooltip',\n order: 4,\n css: '' +\n '.te-link-tooltip {' +\n ' position: fixed; z-index: 9999;' +\n ' background: #333; color: #fff;' +\n ' padding: 4px 8px; border-radius: 4px;' +\n ' font-size: .75rem; line-height: 1.4;' +\n ' max-width: 300px; overflow: hidden;' +\n ' text-overflow: ellipsis; white-space: nowrap;' +\n ' pointer-events: none; opacity: 0;' +\n ' transition: opacity .15s;' +\n '}' +\n '.te-link-tooltip.show { opacity: 1; }',\n init(ctx: PluginContext): void {\n if(ctx.features.linkTooltip === false) return;\n var editor = ctx.editor;\n\n var tooltip = document.createElement('div');\n tooltip.className = 'te-link-tooltip';\n document.body.appendChild(tooltip);\n var hideTimer: ReturnType<typeof setTimeout> | null = null;\n\n editor.addEventListener('mouseover', function(e: MouseEvent){\n var a = (e.target as HTMLElement) && (e.target as HTMLElement).closest && (e.target as HTMLElement).closest('a') as HTMLAnchorElement | null;\n if(!a || !editor.contains(a)){ hide(); return; }\n clearTimeout(hideTimer!);\n var href = a.getAttribute('href') || '';\n tooltip.textContent = href;\n position(e);\n tooltip.classList.add('show');\n });\n\n editor.addEventListener('mousemove', function(e: MouseEvent){\n if(!tooltip.classList.contains('show')) return;\n position(e);\n });\n\n editor.addEventListener('mouseout', function(e: MouseEvent){\n var a = (e.target as HTMLElement) && (e.target as HTMLElement).closest && (e.target as HTMLElement).closest('a');\n if(!a) return;\n hideTimer = setTimeout(hide, 200);\n });\n\n function position(e: MouseEvent): void {\n var x = e.clientX + 12;\n var y = e.clientY + 12;\n if(x + 310 > window.innerWidth) x = window.innerWidth - 310;\n if(y + 30 > window.innerHeight) y = e.clientY - 30;\n tooltip.style.left = x + 'px';\n tooltip.style.top = y + 'px';\n }\n\n function hide(): void {\n tooltip.classList.remove('show');\n }\n }\n};\n\nexport default linkTooltip;\n","import type { Plugin, PluginContext } from '../types';\nimport * as H from '../core/helpers';\n\nvar EMOJIS = '😀😃😄😁😆😅🤣😂🙂🙃😉😊😇🥰😍🤩😘😗😚😋😛😜🤪😝🤑🤗🤭🤫🤔🤐🤨😐😑😶😏😒🙄😬🤥😌😔😪🤤😴😷🤒🤕🤢🤮🤧🥵🥶🥴😵🤯🤠🥳🥸😎🤓🧐😕😟🙁😮😯😲😳🥺😦😧😨😰😥😢😭😱😖😣😞😓😩😫🥱😤😡😠🤬😈👿💀☠💩🤡👹👺👻👽👾🤖'.match(/.{1,2}/g) || [];\n\nvar EMOJI_NAMES: Record<string, string> = {\n '😀':'grinning laugh happy','😃':'grinning smile','😄':'smile happy','😁':'beaming grin','😆':'laughing grinning',\n '🤣':'rolling floor laugh','😂':'tears joy cry',\n '🙂':'slight smile','🙃':'upside down','😉':'winking wink','😊':'blush smile','😇':'innocent angel',\n '🥰':'love heart','😍':'heart eyes','🤩':'star struck','😘':'kiss blowing','😗':'kissing','😚':'kiss closed',\n '😋':'savor yum','😛':'tongue','😜':'wink tongue silly','🤪':'crazy wild','😝':'squint tongue',\n '🤑':'money tongue','🤗':'hug','🤭':'hand over mouth secret','🤫':'shush quiet silent',\n '🤔':'thinking think','🤐':'zipper mouth secret','🤨':'raised eyebrow suspicious',\n '😐':'neutral straight','😑':'expressionless blank','😶':'no mouth silent',\n '😏':'smirk smug','😒':'unamified','🙄':'eye roll',\n '😬':'grimace awkward','🤥':'lying liar nose',\n '😌':'relieved','😔':'pensive sad','😪':'sleepy tired','🤤':'drooling','😴':'sleeping zzz',\n '😷':'mask sick','🤒':'fever','🤕':'hurt bandage','🤢':'nauseous sick','🤮':'vomiting','🤧':'sneeze',\n '🥵':'hot sweat','🥶':'cold freeze','🥴':'dizzy','😵':'dizzy confused','🤯':'mind blown exploding',\n '🤠':'cowboy','🥳':'party celebration','🥸':'disguise','😎':'sunglasses cool','🤓':'nerd geek','🧐':'monocle',\n '😕':'confused','😟':'worried','🙁':'frown sad','😮':'surprised shock','😯':'hushed','😲':'astonished',\n '😳':'flushed embarrassed','🥺':'pleading puppy eyes',\n '😦':'frown','😧':'anguish','😨':'fearful afraid','😰':'anxious worry','😥':'disappointed',\n '😢':'cry sad tear','😭':'sobbing cry','😱':'scream horror','😖':'confounded','😣':'struggle',\n '😞':'disappointed','😓':'sweat','😩':'weary','😫':'tired exhausted','🥱':'yawn sleepy',\n '😤':'frustrated','😡':'angry rage','😠':'angry mad','🤬':'cursing swear',\n '😈':'devil evil grin','👿':'devil evil angry','💀':'skull death','☠':'skull crossbones danger',\n '💩':'poop','🤡':'clown','👹':'ogre monster','👺':'goblin',\n '👻':'ghost halloween','👽':'alien ufo','👾':'alien monster','🤖':'robot',\n '💋':'kiss lips',\n '👋':'wave hello bye','✋':'raised hand stop','👌':'ok perfect',\n '🤏':'pinching small','🤞':'crossed fingers luck','🤟':'love gesture','🤘':'horns rock','🤙':'call me',\n '👈':'point left','👉':'point right','👆':'point up','🖕':'middle finger',\n '👍':'thumbs up like','👎':'thumbs down dislike',\n '✊':'fist raised power','👊':'fist punch','🤛':'fist left','🤜':'fist right',\n '👏':'clap applause','🙌':'celebration','👐':'open hands','🤲':'palms together pray',\n '🤝':'handshake deal','🙏':'pray please thank',\n '✍':'writing','💅':'nail polish',\n '👂':'ear listen','👃':'nose smell','👣':'footsteps','👀':'eyes','👅':'tongue','👄':'mouth lips'\n};\n\nconst emojiAutocomplete: Plugin = {\n name: 'emojiAutocomplete',\n order: 6,\n css: '' +\n '.te-emoji-ac {' +\n ' position: fixed; z-index: 9999;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .375rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .25rem; display: none;' +\n ' max-height: 160px; overflow-y: auto;' +\n ' min-width: 120px;' +\n '}' +\n '.te-emoji-ac-item {' +\n ' display: flex; align-items: center; gap: 6px;' +\n ' padding: 4px 8px; cursor: pointer;' +\n ' border-radius: .25rem; font-size: 1rem;' +\n '}' +\n '.te-emoji-ac-item:hover, .te-emoji-ac-item.active {' +\n ' background: #e7f1ff;' +\n '}',\n init(ctx: PluginContext): void {\n if(ctx.features.emojiAutocomplete === false) return;\n var editor = ctx.editor;\n\n var popup = document.createElement('div');\n popup.className = 'te-emoji-ac';\n document.body.appendChild(popup);\n\n var query = '';\n var activeIdx = 0;\n var items: Element[] = [];\n\n function buildItems(filter: string){\n filter = filter || '';\n popup.innerHTML = '';\n items = [];\n activeIdx = 0;\n var f = filter.toLowerCase();\n EMOJIS.forEach(function(e){\n var name = (EMOJI_NAMES[e] || '').toLowerCase();\n if(f && name.indexOf(f) === -1) return;\n var div = document.createElement('div');\n div.className = 'te-emoji-ac-item';\n div.textContent = e;\n div.setAttribute('data-emoji', e);\n popup.appendChild(div);\n });\n items = Array.prototype.slice.call(popup.children);\n if(items.length === 0){ popup.style.display = 'none'; return; }\n items[0].classList.add('active');\n popup.style.display = 'block';\n position();\n }\n\n function position(){\n var sel = window.getSelection();\n if(!sel || !sel.rangeCount) return;\n var r = sel.getRangeAt(0);\n var rect = r.getBoundingClientRect();\n popup.style.left = Math.max(4, rect.left) + 'px';\n popup.style.top = (rect.bottom + 4) + 'px';\n var pr = popup.getBoundingClientRect();\n if(pr.right > window.innerWidth - 4){\n popup.style.left = (window.innerWidth - pr.width - 4) + 'px';\n }\n if(pr.bottom > window.innerHeight - 4){\n popup.style.top = (rect.top - pr.height - 4) + 'px';\n }\n }\n\n function insertEmoji(emoji: string){\n editor.focus();\n var sel = window.getSelection();\n if(sel && sel.rangeCount > 0 && query){\n var range = sel.getRangeAt(0);\n var len = query.length + 1;\n if(range.startOffset >= len && range.startContainer.nodeType === 3){\n range.setStart(range.startContainer, range.startOffset - len);\n range.deleteContents();\n }\n }\n document.execCommand('insertText', false, emoji);\n popup.style.display = 'none';\n query = '';\n }\n\n function move(dir: number){\n if(items.length === 0) return;\n items[activeIdx].classList.remove('active');\n activeIdx = (activeIdx + dir + items.length) % items.length;\n items[activeIdx].classList.add('active');\n (items[activeIdx] as HTMLElement).scrollIntoView({ block: 'nearest' });\n }\n\n editor.addEventListener('keydown', function(e: KeyboardEvent){\n if(popup.style.display === 'none') return;\n if(e.key === 'ArrowDown'){ e.preventDefault(); move(1); return; }\n if(e.key === 'ArrowUp'){ e.preventDefault(); move(-1); return; }\n if(e.key === 'Enter' || e.key === 'Tab'){\n e.preventDefault();\n var active = popup.querySelector('.active');\n if(active){\n var emoji = active.getAttribute('data-emoji');\n if(emoji) insertEmoji(emoji);\n }\n return;\n }\n if(e.key === 'Escape'){ popup.style.display = 'none'; query = ''; return; }\n });\n\n editor.addEventListener('input', function(){\n var sel = window.getSelection();\n if(!sel || !sel.rangeCount || !sel.anchorNode) return;\n var node = sel.anchorNode;\n var text = node.textContent || '';\n var offset = sel.anchorOffset;\n var before = text.slice(0, offset);\n var colon = before.lastIndexOf(':');\n if(colon !== -1 && before.indexOf(' ', colon) === -1 && colon !== offset - 1){\n query = before.slice(colon + 1);\n if(query.indexOf(':') !== -1){ popup.style.display = 'none'; return; }\n buildItems(query);\n } else if(colon !== -1 && colon === offset - 1){\n query = '';\n buildItems('');\n } else {\n popup.style.display = 'none';\n query = '';\n }\n });\n\n popup.addEventListener('mousedown', function(e: MouseEvent){\n var item = (e.target as HTMLElement) && (e.target as HTMLElement).closest && (e.target as HTMLElement).closest('.te-emoji-ac-item');\n if(!item) return;\n e.preventDefault();\n var emoji = (item as HTMLElement).getAttribute('data-emoji');\n if(emoji) insertEmoji(emoji);\n });\n }\n};\n\nexport default emojiAutocomplete;\n","import type { Plugin, PluginContext } from '../types';\n\nconst statusBar: Plugin = {\n name: 'statusBar',\n order: 100,\n css: '' +\n '.te-statusbar {' +\n ' display: flex; justify-content: space-between; gap: 1rem;' +\n ' padding: 4px 8px; font-size: .75rem; color: #6c757d;' +\n ' background: #f8f9fa; border: 1px solid #dee2e6;' +\n ' border-top: none; border-radius: 0 0 .375rem .375rem;' +\n '}' +\n '.te-statusbar .te-status-tag {' +\n ' font-weight: 600;' +\n ' font-family: monospace;' +\n '}',\n init(ctx: PluginContext): void {\n if(ctx.features.statusBar === false) return;\n var editor = ctx.editor;\n\n var bar = document.createElement('div');\n bar.className = 'te-statusbar';\n bar.innerHTML = '<span class=\"te-status-tag\"></span><span class=\"te-status-right\"><span class=\"te-status-words\">0 words</span><span class=\"te-status-chars\">0 characters</span></span>';\n editor.parentNode!.insertBefore(bar, editor.nextSibling);\n\n function getActiveTag(): string {\n var sel = window.getSelection();\n if(!sel || sel.rangeCount === 0) return '';\n var n: Node | null = sel.anchorNode;\n if(n && n.nodeType === 3) n = n.parentNode;\n if(!n || !editor.contains(n)) return '';\n var tag = '';\n var el: HTMLElement | null = n as HTMLElement;\n while(el && el !== editor){\n var t = el.tagName ? el.tagName.toLowerCase() : '';\n if(['p','h1','h2','h3','h4','h5','h6','div','blockquote','pre','li','td','th','ol','ul','table','thead','tbody','tfoot','tr'].indexOf(t) !== -1){\n tag = t;\n break;\n }\n el = el.parentElement;\n }\n return tag;\n }\n\n function update(): void {\n var sel = window.getSelection();\n var hasSel = sel && !sel.isCollapsed && editor.contains(sel.anchorNode) && editor.contains(sel.focusNode);\n var text = editor.textContent || '';\n var words = text.trim() ? text.trim().split(/\\s+/).length : 0;\n var chars = text.length;\n var tagEl = bar.querySelector('.te-status-tag') as HTMLElement | null;\n var rightEl = bar.querySelector('.te-status-right') as HTMLElement | null;\n if(tagEl) tagEl.textContent = getActiveTag();\n if(rightEl){\n var wEl = rightEl.querySelector('.te-status-words') as HTMLElement | null;\n var cEl = rightEl.querySelector('.te-status-chars') as HTMLElement | null;\n if(!wEl || !cEl){\n rightEl.innerHTML = '<span class=\"te-status-words\"></span><span class=\"te-status-chars\"></span>';\n wEl = rightEl.querySelector('.te-status-words') as HTMLElement | null;\n cEl = rightEl.querySelector('.te-status-chars') as HTMLElement | null;\n }\n if(wEl) wEl.textContent = words + ' word' + (words !== 1 ? 's' : '');\n if(cEl) cEl.textContent = chars + ' character' + (chars !== 1 ? 's' : '');\n if(hasSel){\n var selText = sel!.toString();\n var selWords = selText.trim() ? selText.trim().split(/\\s+/).length : 0;\n var txt = selWords + ' word' + (selWords !== 1 ? 's' : '') + ', ' + selText.length + ' char selected | ' + words + ' word' + (words !== 1 ? 's' : '') + ', ' + chars + ' characters';\n if(wEl) wEl.style.display = 'none';\n if(cEl) cEl.textContent = txt;\n } else {\n if(wEl) wEl.style.display = '';\n }\n }\n }\n\n editor.addEventListener('input', update);\n editor.addEventListener('paste', function(){ setTimeout(update, 100); });\n document.addEventListener('selectionchange', function(){\n if(document.activeElement === editor || editor.contains(document.activeElement)) update();\n });\n update();\n }\n};\n\nexport default statusBar;\n","import type { Plugin, PluginContext } from '../types';\n\nvar LANGUAGES = [\n { id: 'none', label: 'Plain text' },\n { id: 'markup', label: 'HTML' },\n { id: 'css', label: 'CSS' },\n { id: 'javascript', label: 'JavaScript' },\n { id: 'php', label: 'PHP' },\n { id: 'python', label: 'Python' },\n { id: 'java', label: 'Java' },\n { id: 'c', label: 'C' },\n { id: 'cpp', label: 'C++' },\n { id: 'sql', label: 'SQL' },\n { id: 'bash', label: 'Bash' },\n { id: 'json', label: 'JSON' },\n { id: 'typescript', label: 'TypeScript' },\n { id: 'go', label: 'Go' },\n { id: 'rust', label: 'Rust' },\n { id: 'ruby', label: 'Ruby' }\n];\n\nconst codeBlock: Plugin = {\n name: 'codeBlock',\n order: 23,\n css: '' +\n '.te-codeblock-popup {' +\n ' position: absolute; z-index: 3000;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .375rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .5rem; min-width: 160px;' +\n '}' +\n '.te-codeblock-popup select {' +\n ' width: 100%; margin-bottom: .5rem;' +\n '}' +\n '.te-codeblock-popup .btn { width: 100%; }' +\n '.te-editor pre {' +\n ' background: #1e1e2e; border: 1px solid #45475a;' +\n ' border-left: 4px solid #89b4fa;' +\n ' border-radius: .375rem; padding: .75rem;' +\n ' overflow-x: auto; margin: .5rem 0;' +\n ' font-family: \"JetBrains Mono\", \"Fira Code\", \"Cascadia Code\", Consolas, monospace;' +\n ' font-size: .875rem; line-height: 1.6;' +\n ' color: #cdd6f4;' +\n '}' +\n '.te-editor pre code {' +\n ' background: none; padding: 0; font-size: inherit;' +\n ' line-height: inherit; color: inherit;' +\n '}',\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Code block\" data-cmd=\"codeBlock\"><i class=\"ti ti-codeblock\"></i></button>',\n init(ctx: PluginContext): void {\n if(ctx.features.codeBlock === false) return;\n var btn = ctx.wrapper.querySelector('[data-cmd=\"codeBlock\"]') as HTMLButtonElement | null;\n if(!btn) return;\n\n var popup = document.createElement('div');\n popup.className = 'te-codeblock-popup';\n popup.style.display = 'none';\n popup.innerHTML = '' +\n '<select class=\"te-codeblock-lang form-select form-select-sm\">' +\n LANGUAGES.map(function(l){ return '<option value=\"' + l.id + '\">' + l.label + '</option>'; }).join('') +\n '</select>' +\n '<button type=\"button\" class=\"btn btn-sm btn-primary te-codeblock-insert\">Insert</button>';\n document.body.appendChild(popup);\n\n btn.addEventListener('click', function(e: MouseEvent){\n var rect = btn!.getBoundingClientRect();\n popup.style.left = (window.scrollX + rect.left) + 'px';\n popup.style.top = (window.scrollY + rect.bottom + 4) + 'px';\n popup.style.display = popup.style.display === 'none' ? 'block' : 'none';\n });\n\n (popup.querySelector('.te-codeblock-insert') as HTMLButtonElement).addEventListener('click', function(){\n var lang = (popup.querySelector('.te-codeblock-lang') as HTMLSelectElement).value;\n var sel = window.getSelection();\n var text = sel ? sel.toString() : '';\n if(!text) text = 'code';\n var cls = lang && lang !== 'none' ? ' class=\"language-' + lang + '\"' : '';\n var html = '<pre><code' + cls + '>' + text.replace(/</g,'<').replace(/>/g,'>') + '</code></pre>';\n document.execCommand('insertHTML', false, html);\n popup.style.display = 'none';\n ctx.editor.focus();\n });\n\n document.addEventListener('click', function(e: MouseEvent){\n if(popup.style.display === 'none') return;\n if(!popup.contains(e.target as Node) && e.target !== btn){\n popup.style.display = 'none';\n }\n });\n }\n};\n\nexport default codeBlock;\n","import type { Plugin, PluginContext } from '../types';\nimport * as H from '../core/helpers';\n\nvar EMBED_PROVIDERS: { match: RegExp; embed: (id: string) => string }[] = [\n {\n match: /(?:https?:\\/\\/)?(?:www\\.)?(?:youtube\\.com\\/(?:watch\\?v=|embed\\/|shorts\\/)|youtu\\.be\\/)([a-zA-Z0-9_-]{11})/,\n embed: function(id){ return '<iframe src=\"https://www.youtube.com/embed/' + id + '\" style=\"max-width:100%;border:0;aspect-ratio:16/9;\" allowfullscreen></iframe>'; }\n },\n {\n match: /(?:https?:\\/\\/)?(?:www\\.)?vimeo\\.com\\/(\\d+)/,\n embed: function(id){ return '<iframe src=\"https://player.vimeo.com/video/' + id + '\" style=\"max-width:100%;border:0;aspect-ratio:16/9;\" allowfullscreen></iframe>'; }\n }\n];\n\nconst mediaEmbed: Plugin = {\n name: 'mediaEmbed',\n order: 2,\n init(ctx: PluginContext): void {\n if(ctx.features.mediaEmbed === false) return;\n var editor = ctx.editor;\n\n editor.addEventListener('paste', function(e: ClipboardEvent){\n var text = (e.clipboardData && e.clipboardData.getData('text/plain')) || '';\n if(!text) return;\n text = text.trim();\n\n for(var i = 0; i < EMBED_PROVIDERS.length; i++){\n var m = text.match(EMBED_PROVIDERS[i].match);\n if(m && m[1]){\n e.preventDefault();\n e.stopImmediatePropagation();\n var html = EMBED_PROVIDERS[i].embed(m[1]);\n document.execCommand('insertHTML', false, html);\n setTimeout(function(){\n try { H.normalizeParagraphs(editor); H.ensureInitialParagraph(editor); } catch(_){ }\n }, 0);\n return;\n }\n }\n }, true);\n }\n};\n\nexport default mediaEmbed;\n","import type { Plugin, PluginContext } from '../types';\n\nconst dragDrop: Plugin = {\n name: 'dragDrop',\n order: 3,\n css: '' +\n '.te-editor.te-dragover {' +\n ' outline: 3px dashed rgba(13,110,253,.5);' +\n ' outline-offset: -6px;' +\n ' background: rgba(13,110,253,.03);' +\n '}',\n init(ctx: PluginContext): void {\n if(ctx.features.dragDrop === false) return;\n var editor = ctx.editor;\n\n function isImageFile(file: File): boolean {\n return file && /^image\\/(png|jpe?g|gif|webp|svg\\+xml|bmp)$/i.test(file.type);\n }\n\n function readFile(file: File | Blob, cb: (url: string) => void): void {\n var reader = new FileReader();\n reader.onload = function(){ cb(reader.result as string); };\n reader.readAsDataURL(file);\n }\n\n editor.addEventListener('dragenter', function(e: DragEvent){\n e.preventDefault();\n e.stopPropagation();\n editor.classList.add('te-dragover');\n });\n\n editor.addEventListener('dragover', function(e: DragEvent){\n e.preventDefault();\n e.stopPropagation();\n });\n\n editor.addEventListener('dragleave', function(e: DragEvent){\n e.preventDefault();\n e.stopPropagation();\n if(!editor.contains(e.relatedTarget as Node)){\n editor.classList.remove('te-dragover');\n }\n });\n\n editor.addEventListener('drop', function(e: DragEvent){\n e.preventDefault();\n e.stopPropagation();\n editor.classList.remove('te-dragover');\n\n var files = e.dataTransfer && e.dataTransfer.files;\n if(!files || files.length === 0) return;\n\n for(var i = 0; i < files.length; i++){\n var file = files[i];\n if(!isImageFile(file)) continue;\n\n var handler = (ctx.TulihEditor && ctx.TulihEditor.onUploadImage) || readFile;\n handler(file, function(url: string){\n if(!url) return;\n var html = '<img src=\"' + url.replace(/\"/g,'"') + '\" alt=\"' + (file.name || '').replace(/\"/g,'"') + '\" style=\"max-width:100%;\" />';\n document.execCommand('insertHTML', false, html);\n });\n }\n });\n }\n};\n\nexport default dragDrop;\n","import type { Plugin, PluginContext } from '../types';\nimport * as H from '../core/helpers';\n\nconst pastePlain: Plugin = {\n name: 'pastePlain',\n order: 24,\n css: '' +\n '.te-pasteplain-btn.active { background: #e7f1ff; border-color: #b6d4fe; }',\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light te-pasteplain-btn\" title=\"Paste as plain text\" data-cmd=\"togglePastePlain\"><i class=\"ti ti-clipboard\"></i></button>',\n init(ctx: PluginContext): void {\n if(!ctx.features.pastePlain) return;\n var editor = ctx.editor;\n ctx._pastePlain = false;\n\n var btn = ctx.wrapper.querySelector('[data-cmd=\"togglePastePlain\"]');\n if(btn){\n btn.addEventListener('click', function(){\n ctx._pastePlain = !ctx._pastePlain;\n (btn as HTMLElement).classList.toggle('active', ctx._pastePlain as boolean);\n });\n }\n\n editor.addEventListener('paste', function(e: ClipboardEvent){\n if(!ctx._pastePlain) return;\n e.stopImmediatePropagation();\n e.preventDefault();\n var text = (e.clipboardData && e.clipboardData.getData('text/plain')) || '';\n if(text){\n var safe = H.escapeHtml(text);\n var html = '<p>' + safe.replace(/\\n{2,}/g, '</p><p>').replace(/\\n/g, '<br>') + '</p>';\n document.execCommand('insertHTML', false, html);\n }\n setTimeout(function(){\n try {\n H.normalizeParagraphs(editor);\n H.ensureInitialParagraph(editor);\n } catch(_){}\n }, 0);\n }, true);\n }\n};\n\nexport default pastePlain;\n","import type { Plugin, PluginContext, TeEditorElement } from '../types';\n\nconst findReplace: Plugin = {\n name: 'findReplace',\n order: 31,\n css: '' +\n '.te-fr-popup {' +\n ' position: absolute; z-index: 3000;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .5rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .75rem; width: 320px;' +\n '}' +\n '.te-fr-popup .te-fr-row { display: flex; gap: .5rem; margin-bottom: .5rem; }' +\n '.te-fr-popup .te-fr-row:last-child { margin-bottom: 0; }' +\n '.te-fr-popup input { flex: 1; }' +\n '.te-fr-popup .btn { white-space: nowrap; }' +\n '.te-fr-count { font-size: .8rem; color: #6c757d; padding: .25rem .5rem; }' +\n '.te-fr-match { background: #fff3cd; outline: 2px solid #ffc107; }' +\n '.te-fr-active { background: #f0ad4e; outline: 2px solid #e68600; }',\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Find & Replace\" data-cmd=\"findReplace\"><i class=\"ti ti-search\"></i></button>',\n init(ctx: PluginContext): void {\n if(!ctx.features.findReplace) return;\n var editor = ctx.editor as TeEditorElement;\n var popup = document.createElement('div');\n popup.className = 'te-fr-popup';\n popup.style.display = 'none';\n popup.innerHTML = '' +\n '<div class=\"te-fr-row\">' +\n '<input type=\"text\" class=\"form-control form-control-sm te-fr-find\" placeholder=\"Find...\" />' +\n '<button type=\"button\" class=\"btn btn-sm btn-outline-primary te-fr-prev\" title=\"Previous\">↑</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-primary te-fr-next\" title=\"Next\">↓</button>' +\n '</div>' +\n '<div class=\"te-fr-row\">' +\n '<input type=\"text\" class=\"form-control form-control-sm te-fr-replace\" placeholder=\"Replace...\" />' +\n '<button type=\"button\" class=\"btn btn-sm btn-outline-secondary te-fr-replace-btn\">Replace</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-outline-secondary te-fr-replace-all\">All</button>' +\n '</div>' +\n '<div class=\"te-fr-row\">' +\n '<span class=\"te-fr-count\"></span>' +\n '<button type=\"button\" class=\"btn btn-sm btn-outline-secondary te-fr-close ms-auto\" title=\"Close\">×</button>' +\n '</div>';\n document.body.appendChild(popup);\n\n var findInp = popup.querySelector('.te-fr-find') as HTMLInputElement;\n var replaceInp = popup.querySelector('.te-fr-replace') as HTMLInputElement;\n var countEl = popup.querySelector('.te-fr-count') as HTMLElement;\n\n function escapeRe(s: string){\n return s.replace(/[.*+?^${}()|[\\]\\\\]/g, '\\\\$&');\n }\n\n function clearHighlights(){\n editor.querySelectorAll('.te-fr-match, .te-fr-active').forEach(function(el){\n var parent = el.parentNode;\n if(!parent) return;\n while(el.firstChild) parent.insertBefore(el.firstChild, el);\n parent.removeChild(el);\n });\n editor.normalize();\n }\n\n function selectMatch(el: Element | null){\n editor.querySelectorAll('.te-fr-active').forEach(function(a){ a.classList.remove('te-fr-active'); a.classList.add('te-fr-match'); });\n if(!el) return;\n el.classList.remove('te-fr-match');\n el.classList.add('te-fr-active');\n (el as HTMLElement).scrollIntoView({ block: 'nearest' });\n var range = document.createRange();\n range.selectNodeContents(el);\n var sel = window.getSelection()!;\n sel.removeAllRanges();\n sel.addRange(range);\n }\n\n var highlights: Element[] = [];\n var currentIdx = -1;\n\n function doFind(){\n clearHighlights();\n var text = findInp.value.trim();\n if(!text) return;\n var nodes: Node[] = [];\n var walker = document.createTreeWalker(editor, NodeFilter.SHOW_TEXT, null);\n while(walker.nextNode()) nodes.push(walker.currentNode);\n highlights = [];\n nodes.forEach(function(node){\n var nodeText = node.textContent!;\n var re2 = new RegExp(escapeRe(text), 'gi');\n var matches: { idx: number; len: number }[] = [];\n var match: RegExpExecArray | null;\n while((match = re2.exec(nodeText)) !== null){\n matches.push({ idx: match.index, len: match[0].length });\n }\n // Process matches in reverse order to avoid index drift\n for(var i = matches.length - 1; i >= 0; i--){\n var m = matches[i];\n var span = document.createElement('span');\n span.className = 'te-fr-match';\n span.textContent = nodeText.substring(m.idx, m.idx + m.len);\n var after = (node as Text).splitText(m.idx + m.len);\n var mid = (node as Text).splitText(m.idx);\n mid.parentNode!.replaceChild(span, mid);\n highlights.push(span);\n }\n });\n countEl.textContent = highlights.length + ' matches';\n }\n\n function goNext(){\n if(!highlights.length){ doFind(); if(!highlights.length) return; currentIdx = 0; }\n else currentIdx = (currentIdx + 1) % highlights.length;\n selectMatch(highlights[currentIdx]);\n }\n function goPrev(){\n if(!highlights.length){ doFind(); if(!highlights.length) return; currentIdx = highlights.length - 1; }\n else currentIdx = (currentIdx - 1 + highlights.length) % highlights.length;\n selectMatch(highlights[currentIdx]);\n }\n function doFindAndSelect(dir: number){\n doFind();\n if(!highlights.length) return;\n currentIdx = dir === 1 ? 0 : highlights.length - 1;\n selectMatch(highlights[currentIdx]);\n }\n\n popup.querySelector('.te-fr-next')!.addEventListener('click', goNext);\n popup.querySelector('.te-fr-prev')!.addEventListener('click', goPrev);\n function closePopup(){\n popup.style.display = 'none';\n clearHighlights();\n editor.focus();\n }\n\n findInp.addEventListener('input', function(){ doFind(); });\n findInp.addEventListener('keydown', function(e: KeyboardEvent){\n if(e.key === 'Enter') { e.preventDefault(); doFindAndSelect(1); }\n if(e.key === 'Escape') { e.preventDefault(); closePopup(); }\n });\n replaceInp.addEventListener('keydown', function(e: KeyboardEvent){\n if(e.key === 'Enter') { e.preventDefault(); (popup.querySelector('.te-fr-replace-btn') as HTMLButtonElement).click(); }\n if(e.key === 'Escape') { e.preventDefault(); closePopup(); }\n });\n function saveUndoState(){\n clearHighlights();\n if(!editor._tableHist) editor._tableHist = {undo:[], redo:[]};\n editor._tableHist.undo.push(editor.innerHTML);\n if(editor._tableHist.undo.length > 50) editor._tableHist.undo.shift();\n editor._tableHist.redo = [];\n }\n\n function updateUndoRedoBtns(){\n var btn = ctx.wrapper.querySelector('[data-cmd=\"undo\"]') as HTMLButtonElement | null;\n var rbtn = ctx.wrapper.querySelector('[data-cmd=\"redo\"]') as HTMLButtonElement | null;\n var h = editor._tableHist;\n if(btn) btn.toggleAttribute('disabled', !h || !h.undo.length);\n if(rbtn) rbtn.toggleAttribute('disabled', !h || !h.redo.length);\n }\n\n popup.querySelector('.te-fr-replace-btn')!.addEventListener('click', function(){\n if(!highlights.length) return;\n var active = editor.querySelector('.te-fr-active');\n if(!active) return;\n saveUndoState();\n var text = replaceInp.value;\n var parent = active.parentNode;\n if(parent) parent.replaceChild(document.createTextNode(text), active);\n // Update highlights\n highlights.splice(currentIdx, 1);\n countEl.textContent = highlights.length + ' matches';\n if(highlights.length){\n currentIdx = Math.min(currentIdx, highlights.length - 1);\n selectMatch(highlights[currentIdx]);\n } else {\n countEl.textContent = '0 matches';\n }\n updateUndoRedoBtns();\n });\n popup.querySelector('.te-fr-replace-all')!.addEventListener('click', function(){\n var findText = findInp.value.trim();\n var replaceText = replaceInp.value;\n if(!findText) return;\n saveUndoState();\n clearHighlights();\n var re = new RegExp(escapeRe(findText), 'gi');\n var walker = document.createTreeWalker(editor, NodeFilter.SHOW_TEXT, null);\n var nodes: Node[] = [];\n while(walker.nextNode()) nodes.push(walker.currentNode);\n var count = 0;\n nodes.forEach(function(node){\n var text = node.textContent!;\n if(!re.test(text)) return;\n re.lastIndex = 0;\n node.textContent = text.replace(re, function(){ count++; return replaceText; });\n });\n countEl.textContent = count + ' replaced';\n highlights = [];\n currentIdx = -1;\n updateUndoRedoBtns();\n });\n popup.querySelector('.te-fr-close')!.addEventListener('click', closePopup);\n\n var btn = ctx.wrapper.querySelector('[data-cmd=\"findReplace\"]') as HTMLButtonElement | null;\n if(!btn) return;\n btn.addEventListener('click', function(e: MouseEvent){\n var rect = (btn as HTMLButtonElement).getBoundingClientRect();\n popup.style.left = (window.scrollX + rect.left) + 'px';\n popup.style.top = (window.scrollY + rect.bottom + 4) + 'px';\n popup.style.display = popup.style.display === 'none' ? 'block' : 'none';\n if(popup.style.display !== 'none'){\n findInp.value = '';\n replaceInp.value = '';\n countEl.textContent = '';\n clearHighlights();\n highlights = [];\n currentIdx = -1;\n findInp.focus();\n }\n });\n document.addEventListener('click', function(e: MouseEvent){\n if(popup.style.display === 'none') return;\n if(!popup.contains(e.target as Node) && e.target !== btn){\n popup.style.display = 'none';\n clearHighlights();\n }\n });\n }\n};\n\nexport default findReplace;\n","import type { Plugin, PluginContext } from '../types';\n\nconst indent: Plugin = {\n name: 'indent',\n order: 25,\n toolbarHTML: '' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Indent\" data-cmd=\"indent\"><i class=\"ti ti-indent-increase\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Outdent\" data-cmd=\"outdent\"><i class=\"ti ti-indent-decrease\"></i></button>',\n init(ctx: PluginContext): void {\n if (!ctx.features.indent) return;\n // Buttons may be absent when a custom `toolbar` layout omits this group.\n const indentBtn = ctx.wrapper.querySelector('[data-cmd=\"indent\"]');\n if (indentBtn) {\n indentBtn.addEventListener('click', function () {\n document.execCommand('indent', false, undefined);\n ctx.editor.focus();\n });\n }\n const outdentBtn = ctx.wrapper.querySelector('[data-cmd=\"outdent\"]');\n if (outdentBtn) {\n outdentBtn.addEventListener('click', function () {\n document.execCommand('outdent', false, undefined);\n ctx.editor.focus();\n });\n }\n }\n};\n\nexport default indent;\n","import type { Plugin, PluginContext } from '../types';\n\nvar CLS_RE = /\\bte-list-\\S+/g;\n\nvar OL_STYLES = [\n { val: 'decimal', label: '1.', cls: '' },\n { val: 'upper-alpha', label: 'A.', cls: 'te-list-upper-alpha' },\n { val: 'lower-alpha', label: 'a.', cls: 'te-list-lower-alpha' },\n { val: 'upper-roman', label: 'I.', cls: 'te-list-upper-roman' },\n { val: 'lower-roman', label: 'i.', cls: 'te-list-lower-roman' }\n];\n\nvar UL_STYLES = [\n { val: 'disc', label: '•', cls: '' },\n { val: 'circle', label: '○', cls: 'te-list-circle' },\n { val: 'square', label: '■', cls: 'te-list-square' }\n];\n\nfunction setListStyle(list: HTMLElement | null, val: string, cls: string){\n if(!list) return;\n list.className = (list.className || '').replace(CLS_RE, '').trim();\n if(cls) list.classList.add(cls);\n list.style.listStyleType = val || '';\n}\n\nfunction findAncestorList(node: Node | null): HTMLElement | null {\n while(node && (node as Element).nodeType === 1){\n if((node as Element).tagName === 'OL' || (node as Element).tagName === 'UL') return node as HTMLElement;\n node = (node as Element).parentElement;\n }\n return null;\n}\n\nfunction buildOptions(styles: { val: string; label: string; cls: string }[]){\n var html = '<option value=\"\">—</option>';\n for(var i = 0; i < styles.length; i++){\n html += '<option value=\"' + styles[i].val + '\">' + styles[i].label + '</option>';\n }\n return html;\n}\n\nfunction handleSelect(ctx: PluginContext, select: HTMLSelectElement, tag: string, styles: { val: string; label: string; cls: string }[]){\n var val = select.value;\n select.value = '';\n\n var sel = window.getSelection();\n if(!sel || !sel.anchorNode) return;\n var node: Node | null = sel.anchorNode;\n if(node.nodeType === 3) node = node.parentNode;\n\n var list = findAncestorList(node);\n var execCmd = tag === 'OL' ? 'insertOrderedList' : 'insertUnorderedList';\n\n if(!val){\n if(list && list.tagName === tag){\n document.execCommand(execCmd, false, undefined);\n }\n ctx.editor.focus();\n return;\n }\n\n var matched: { val: string; label: string; cls: string } | null = null;\n for(var i = 0; i < styles.length; i++){\n if(styles[i].val === val){ matched = styles[i]; break; }\n }\n if(!matched) return;\n\n if(list){\n if(list.tagName === tag){\n setListStyle(list, val, matched.cls);\n } else {\n document.execCommand(execCmd, false, undefined);\n var afterNode: Node | null = sel.focusNode;\n if(afterNode && afterNode.nodeType === 3) afterNode = afterNode.parentNode;\n var newList = findAncestorList(afterNode);\n if(newList && newList.tagName === tag) setListStyle(newList, val, matched.cls);\n }\n } else {\n document.execCommand(execCmd, false, undefined);\n var afterNode: Node | null = sel.focusNode;\n if(afterNode && afterNode.nodeType === 3) afterNode = afterNode.parentNode;\n var newList = findAncestorList(afterNode);\n if(newList) setListStyle(newList, val, matched.cls);\n }\n ctx.editor.focus();\n}\n\nconst list: Plugin = {\n name: 'list',\n order: 25,\n css: '' +\n '.te-list-select { width: auto; }' +\n '.te-editor ol.te-list-upper-alpha { list-style-type: upper-alpha; }' +\n '.te-editor ol.te-list-lower-alpha { list-style-type: lower-alpha; }' +\n '.te-editor ol.te-list-upper-roman { list-style-type: upper-roman; }' +\n '.te-editor ol.te-list-lower-roman { list-style-type: lower-roman; }' +\n '.te-editor ul.te-list-circle { list-style-type: circle; }' +\n '.te-editor ul.te-list-square { list-style-type: square; }',\n toolbarHTML: '' +\n '<select class=\"te-list-ol form-select form-select-sm te-list-select\" title=\"Ordered list style\">' +\n buildOptions(OL_STYLES) +\n '</select>' +\n '<select class=\"te-list-ul form-select form-select-sm te-list-select\" title=\"Unordered list style\">' +\n buildOptions(UL_STYLES) +\n '</select>',\n init(ctx: PluginContext): void {\n if(ctx.features.list === false) return;\n\n var olSel = ctx.wrapper.querySelector('.te-list-ol') as HTMLSelectElement | null;\n var ulSel = ctx.wrapper.querySelector('.te-list-ul') as HTMLSelectElement | null;\n\n if(olSel){\n olSel.addEventListener('change', function(){\n handleSelect(ctx, olSel!, 'OL', OL_STYLES);\n });\n }\n\n if(ulSel){\n ulSel.addEventListener('change', function(){\n handleSelect(ctx, ulSel!, 'UL', UL_STYLES);\n });\n }\n\n ctx.editor.addEventListener('keydown', function(e: KeyboardEvent){\n if(e.key === 'Tab'){\n var sel = window.getSelection();\n if(!sel || !sel.anchorNode) return;\n var node: Node | null = sel.anchorNode;\n if(node.nodeType === 3) node = node.parentNode;\n var list = findAncestorList(node);\n if(list){\n e.preventDefault();\n document.execCommand(e.shiftKey ? 'outdent' : 'indent', false, undefined);\n ctx.editor.focus();\n }\n }\n });\n }\n};\n\nexport default list;\n","import type { Plugin, PluginContext } from '../types';\n\nconst lineHeight: Plugin = {\n name: 'lineHeight',\n order: 26,\n css: '' +\n '.te-lh-select { width: auto; }',\n toolbarHTML: '' +\n '<select class=\"te-lh form-select form-select-sm te-lh-select\" title=\"Line height\">' +\n ' <option value=\"\" disabled selected>Line Height</option>' +\n ' <option value=\"1\">1</option>' +\n ' <option value=\"1.15\">1.15</option>' +\n ' <option value=\"1.5\">1.5</option>' +\n ' <option value=\"1.8\">1.8</option>' +\n ' <option value=\"2\">2</option>' +\n ' <option value=\"2.5\">2.5</option>' +\n ' <option value=\"3\">3</option>' +\n '</select>',\n init(ctx: PluginContext): void {\n if(!ctx.features.lineHeight) return;\n var sel = ctx.wrapper.querySelector('.te-lh') as HTMLSelectElement | null;\n if(!sel) return;\n sel.addEventListener('change', function(){\n var v = sel!.value;\n if(!v) return;\n document.execCommand('formatBlock', false, 'p');\n var s = window.getSelection();\n if(!s || !s.rangeCount) return;\n var node: Node | null = s.anchorNode;\n if(node && node.nodeType === 3) node = node.parentNode;\n var block = node && (node as Element).closest && (node as Element).closest('p,h1,h2,h3,h4,h5,h6,div,li,blockquote');\n if(block && ctx.wrapper.contains(block)){\n (block as HTMLElement).style.lineHeight = v;\n }\n ctx.editor.focus();\n });\n }\n};\n\nexport default lineHeight;\n","import type { Plugin, PluginContext } from '../types';\nimport * as H from '../core/helpers';\n\nvar FONT_SIZES = ['8', '9', '10', '11', '12', '13', '14', '16', '18', '20', '22', '24', '26', '28', '36', '48', '72'];\n\nconst fontSize: Plugin = {\n name: 'fontSize',\n order: 27,\n css: '' +\n '.te-fontsize-select { width: auto; }',\n toolbarHTML: '' +\n '<span class=\"te-dropdown-icon te-dropdown-icon-text\">Aa</span>' +\n '<select class=\"te-fontsize form-select form-select-sm te-fontsize-select\" title=\"Font size\">' +\n ' <option value=\"\">Normal</option>' +\n FONT_SIZES.map(function (s) { return '<option value=\"' + s + '\">' + s + '</option>'; }).join('') +\n '</select>',\n init(ctx: PluginContext): void {\n if (!ctx.features.fontSize) return;\n var sel = ctx.wrapper.querySelector('.te-fontsize') as HTMLSelectElement | null;\n if (!sel) return;\n sel.addEventListener('change', function () {\n var v = sel!.value;\n if (!v) return;\n var txt = H.escapeHtml(window.getSelection()!.toString() || 'text');\n var html = '<span style=\"font-size:' + v + 'px\">' + txt + '</span>';\n document.execCommand('insertHTML', false, html);\n ctx.editor.focus();\n });\n }\n};\n\nexport default fontSize;\n","import type { Plugin, PluginContext } from '../types';\n\nvar FONTS = [\n 'Arial',\n 'Arial Black',\n 'Comic Sans MS',\n 'Courier New',\n 'Georgia',\n 'Impact',\n 'Lucida Console',\n 'Tahoma',\n 'Times New Roman',\n 'Trebuchet MS',\n 'Verdana'\n];\n\nconst fontFamily: Plugin = {\n name: 'fontFamily',\n order: 28,\n css: '' +\n '.te-fontfamily-select { width: auto; }',\n toolbarHTML: '' +\n '<span class=\"te-dropdown-icon\"><i class=\"ti ti-typography\"></i></span>' +\n '<select class=\"te-fontfamily form-select form-select-sm te-fontfamily-select\" title=\"Font family\">' +\n ' <option value=\"\">Normal</option>' +\n FONTS.map(function(f){ return '<option value=\"' + f + '\">' + f + '</option>'; }).join('') +\n '</select>',\n init(ctx: PluginContext): void {\n if(!ctx.features.fontFamily) return;\n var sel = ctx.wrapper.querySelector('.te-fontfamily') as HTMLSelectElement | null;\n if(!sel) return;\n sel.addEventListener('change', function(){\n var v = sel!.value;\n if(!v) return;\n document.execCommand('fontName', false, v);\n ctx.editor.focus();\n });\n }\n};\n\nexport default fontFamily;\n","import type { Plugin, PluginContext } from '../types';\n\nvar CHARS = '©®™§±•·†‡•¶′″←↑→↓↔↕⇒⇔∞≈≠≤≥√∛∜÷×∑∏∫∂∇∅∈∉∋∧∨∩∪⊂⊃⊆⊇¬∧∨⇒⇔∀∃∄∵∴∷∠∟∡∥∦∼≅≜≛≝≟≠≡≢≤≥≦≧≨≩≪≫≬≭≮≯≰≱≲≳≴≵≶≷≸≹≺≻≼≽≾≿⊀⊁⊂⊃⊄⊅⊆⊇⊈⊉⊊⊋⊌⊍⊎⊏⊐⊑⊒⊓⊔⊕⊖⊗⊘⊙⊚⊛⊜⊝⊞⊟⊠⊡⊢⊣⊤⊥⊦⊧⊨⊩⊪⊫⊬⊭⊮⊯⊰⊱⊲⊳⊴⊵⊶⊷⊸⊹⊺⊻⊼⊽⊾⊿⋀⋁⋂⋃⋄⋅⋆⋇⋈⋉⋊⋋⋌⋍⋎⋏⋐⋑⋒⋓⋔⋕⋖⋗⋘⋙⋚⋛⋜⋝⋞⋟€£¥₩₽₨₪₫₭₮₰₱₲₳₴₵₶₷₸₹₺₻₼₽₾₿'.split('');\n\nconst specialChars: Plugin = {\n name: 'specialChars',\n order: 29,\n css: '' +\n '.te-sc-popup {' +\n ' position: absolute; z-index: 3000;' +\n ' display: grid; grid-template-columns: repeat(10, 1fr); gap: 2px;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .5rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .5rem; max-width: 320px; max-height: 200px; overflow-y: auto;' +\n '}' +\n '.te-sc-popup button {' +\n ' background: none; border: none; font-size: 1rem;' +\n ' padding: .25rem; cursor: pointer; border-radius: .25rem; text-align: center;' +\n '}' +\n '.te-sc-popup button:hover { background: #f0f0f0; }',\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Special characters\" data-cmd=\"specialChars\"><i class=\"ti ti-hash\"></i></button>',\n init(ctx: PluginContext): void {\n if(!ctx.features.specialChars) return;\n\n var popup = document.createElement('div');\n popup.className = 'te-sc-popup';\n popup.style.display = 'none';\n CHARS.forEach(function(ch){\n var btn = document.createElement('button');\n btn.type = 'button';\n btn.textContent = ch;\n btn.setAttribute('data-sc', ch);\n popup.appendChild(btn);\n });\n document.body.appendChild(popup);\n\n var btn = ctx.wrapper.querySelector('[data-cmd=\"specialChars\"]') as HTMLElement | null;\n if(btn){\n btn.addEventListener('click', function(e: MouseEvent){\n var rect = (btn as HTMLElement).getBoundingClientRect();\n popup.style.left = (window.scrollX + rect.left) + 'px';\n popup.style.top = (window.scrollY + rect.bottom + 4) + 'px';\n popup.style.display = popup.style.display === 'none' ? 'grid' : 'none';\n });\n }\n\n popup.addEventListener('click', function(e: MouseEvent){\n var ch = (e.target as HTMLElement) && (e.target as HTMLElement).getAttribute('data-sc');\n if(!ch) return;\n document.execCommand('insertHTML', false, ch);\n popup.style.display = 'none';\n ctx.editor.focus();\n });\n\n document.addEventListener('click', function(e: MouseEvent){\n if(popup.style.display === 'none') return;\n if(!popup.contains(e.target as Node) && e.target !== btn){\n popup.style.display = 'none';\n }\n });\n }\n};\n\nexport default specialChars;\n","import type { Plugin, PluginContext } from '../types';\n\nconst colors: Plugin = {\n name: 'colors',\n order: 30,\n css: '' +\n '.te-color-btn {' +\n ' position: relative; padding: .15rem .35rem !important;' +\n ' min-width: 28px; text-align: center;' +\n '}' +\n '.te-color-preview {' +\n ' display: block; font-size: 1rem; line-height: 1;' +\n '}' +\n '.te-color-preview::after {' +\n ' content: \"\"; display: block;' +\n ' height: 3px; border-radius: 1px;' +\n ' margin-top: 2px;' +\n '}' +\n '.te-fore-btn .te-color-preview::after {' +\n ' background: currentColor;' +\n '}' +\n '.te-back-btn .te-color-preview::after {' +\n ' background: var(--te-back-color, #ffff00);' +\n '}' +\n '.te-color-input {' +\n ' position: absolute; top: 0; left: 0;' +\n ' width: 100%; height: 100%;' +\n ' opacity: 0; cursor: pointer;' +\n ' border: none; padding: 0;' +\n '}',\n toolbarHTML: '' +\n '<button type=\"button\" class=\"btn btn-sm btn-light te-color-btn te-fore-btn\" title=\"Text color\">' +\n '<span class=\"te-color-preview\" style=\"color:#000000\">A</span>' +\n '<input type=\"color\" class=\"te-color-input te-fore-color\" value=\"#000000\">' +\n '</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light te-color-btn te-back-btn\" title=\"Background color\">' +\n '<span class=\"te-color-preview\" style=\"--te-back-color:#ffff00;color:#000\">A</span>' +\n '<input type=\"color\" class=\"te-color-input te-back-color\" value=\"#ffff00\">' +\n '</button>',\n init(ctx: PluginContext): void {\n if(!ctx.features.colors) return;\n\n var foreInput = ctx.wrapper.querySelector('.te-fore-color') as HTMLInputElement | null;\n var foreBtn = ctx.wrapper.querySelector('.te-fore-btn') as HTMLElement | null;\n if(foreBtn && foreInput){\n foreInput.addEventListener('change', function(){\n var preview = foreBtn!.querySelector('.te-color-preview') as HTMLElement;\n preview.style.color = foreInput!.value;\n document.execCommand('foreColor', false, foreInput!.value);\n ctx.editor.focus();\n });\n }\n\n var backInput = ctx.wrapper.querySelector('.te-back-color') as HTMLInputElement | null;\n var backBtn = ctx.wrapper.querySelector('.te-back-btn') as HTMLElement | null;\n if(backBtn && backInput){\n backInput.addEventListener('change', function(){\n var preview = backBtn!.querySelector('.te-color-preview') as HTMLElement;\n preview.style.setProperty('--te-back-color', backInput!.value);\n try{ document.execCommand('hiliteColor', false, backInput!.value); }\n catch(_){ document.execCommand('backColor', false, backInput!.value); }\n ctx.editor.focus();\n });\n }\n }\n};\n\nexport default colors;\n","import type { Plugin, PluginContext } from '../types';\n\nconst tableBg: Plugin = {\n name: 'tableBg',\n order: 56,\n init(ctx: PluginContext): void {\n // tableBg moved to tableTools floating bar\n },\n};\n\nexport default tableBg;\n","import type { Plugin, PluginContext } from '../types';\n\nvar ALIGN_CMDS: Record<string, { exec: string; match: string }> = {\n alignLeft: { exec: 'justifyLeft', match: 'left' },\n alignCenter: { exec: 'justifyCenter', match: 'center' },\n alignRight: { exec: 'justifyRight', match: 'right' },\n alignJustify: { exec: 'justifyFull', match: 'justify' }\n};\n\nfunction getBlockAlignment(node: Node | null): string {\n if(!node || node.nodeType === 3) node = node ? node.parentNode : null;\n if(!node) return '';\n var el = (node as Element).closest ? (node as Element).closest('p,h1,h2,h3,h4,h5,h6,li,div,blockquote') : null;\n if(!el) return '';\n try {\n var cs = window.getComputedStyle(el);\n var ta = cs.textAlign.toLowerCase();\n if(ta === 'start') return 'left';\n return ta;\n } catch(_){ return ''; }\n}\n\nconst align: Plugin = {\n name: 'align',\n order: 40,\n css: '',\n toolbarHTML: '' +\n '<button type=\"button\" class=\"btn btn-sm btn-light te-align-btn\" title=\"Align left\" data-cmd=\"alignLeft\"><i class=\"ti ti-align-left\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light te-align-btn\" title=\"Align center\" data-cmd=\"alignCenter\"><i class=\"ti ti-align-center\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light te-align-btn\" title=\"Align right\" data-cmd=\"alignRight\"><i class=\"ti ti-align-right\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light te-align-btn\" title=\"Justify\" data-cmd=\"alignJustify\"><i class=\"ti ti-align-justified\"></i></button>',\n init(ctx: PluginContext): void {\n if(!ctx.features.align) return;\n var names = Object.keys(ALIGN_CMDS);\n\n names.forEach(function(name){\n var btn = ctx.wrapper.querySelector('[data-cmd=\"' + name + '\"]') as HTMLElement | null;\n if(!btn) return;\n var cmd = ALIGN_CMDS[name];\n btn.addEventListener('click', function(){\n var align = getBlockAlignment(window.getSelection()!.anchorNode);\n\n if(align === cmd.match){\n document.execCommand('justifyLeft', false, undefined);\n } else {\n document.execCommand(cmd.exec, false, undefined);\n }\n ctx.editor.focus();\n updateActive();\n });\n });\n\n function updateActive(): void {\n var node = window.getSelection()!.anchorNode;\n if(!node || !ctx.wrapper.contains(node)) return;\n var align = getBlockAlignment(node);\n names.forEach(function(name){\n var btn = ctx.wrapper.querySelector('[data-cmd=\"' + name + '\"]') as HTMLElement | null;\n if(!btn) return;\n btn.classList.toggle('active', align === ALIGN_CMDS[name].match);\n });\n }\n\n document.addEventListener('selectionchange', function(){\n if(document.activeElement === ctx.editor || ctx.editor.contains(document.activeElement)){\n updateActive();\n }\n });\n }\n};\n\nexport default align;\n","import type { Plugin, PluginContext } from '../types';\n\nvar RULES: Array<{ re: RegExp; cmd: string; val: string | null }> = [\n { re: /^#{6}\\s$/, cmd: 'formatBlock', val: 'h6' },\n { re: /^#{5}\\s$/, cmd: 'formatBlock', val: 'h5' },\n { re: /^#{4}\\s$/, cmd: 'formatBlock', val: 'h4' },\n { re: /^#{3}\\s$/, cmd: 'formatBlock', val: 'h3' },\n { re: /^#{2}\\s$/, cmd: 'formatBlock', val: 'h2' },\n { re: /^#{1}\\s$/, cmd: 'formatBlock', val: 'h1' },\n { re: /^>\\s$/, cmd: 'formatBlock', val: 'blockquote' },\n { re: /^[-*]\\s$/, cmd: 'insertUnorderedList', val: null },\n { re: /^1[.)]\\s$/, cmd: 'insertOrderedList', val: null },\n];\n\nconst markdown: Plugin = {\n name: 'markdown',\n order: 5,\n init(ctx: PluginContext): void {\n if(!ctx.features.markdown) return;\n\n ctx.editor.addEventListener('keydown', function(e: KeyboardEvent){\n if(e.key !== ' ' && e.key !== 'Enter') return;\n\n var sel = window.getSelection();\n if(!sel || sel.rangeCount === 0 || !sel.isCollapsed) return;\n var node = sel.anchorNode;\n if(!node || node.nodeType !== 3) return;\n var text = node.textContent || '';\n\n for(var i = 0; i < RULES.length; i++){\n var rule = RULES[i];\n if(!rule.re.test(text)) continue;\n\n e.preventDefault();\n\n if(e.key === 'Enter'){\n node.textContent = text.slice(0, -1);\n setTimeout(function(){\n document.execCommand(rule.cmd, false, rule.val || undefined);\n }, 0);\n return;\n }\n\n node.textContent = '';\n document.execCommand(rule.cmd, false, rule.val || undefined);\n ctx.editor.focus();\n return;\n }\n\n if(e.key === 'Enter' && text.trim() === ''){\n var parent = node.parentNode as HTMLElement | null;\n if(parent && (parent.tagName === 'BLOCKQUOTE' || parent.tagName === 'PRE')){\n e.preventDefault();\n document.execCommand('formatBlock', false, 'p');\n }\n }\n });\n }\n};\n\nexport default markdown;\n","import type { Plugin, PluginContext } from '../types';\n\nconst link: Plugin = {\n name: 'link',\n order: 50,\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Link\" data-cmd=\"createLink\"><i class=\"ti ti-link\"></i></button>',\n css: '' +\n '.te-link-tools {' +\n ' position: fixed; display: none; z-index: 3000;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .375rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .25rem .35rem; gap: .2rem; align-items: center;' +\n ' white-space: nowrap;' +\n '}' +\n '.te-link-tools .btn {' +\n ' padding: .2rem .45rem !important; font-size: .75rem !important; line-height: 1 !important;' +\n '}' +\n '.te-link-tools .btn i,' +\n '.te-link-tools .btn svg {' +\n ' width: 12px !important; height: 12px !important;' +\n ' pointer-events: none;' +\n '}' +\n '.te-link-tools .te-divider-v {' +\n ' display: inline-block; width: 1px; height: 14px;' +\n ' background: #dee2e6; margin: 0 .15rem; vertical-align: middle;' +\n '}' +\n '.te-link-edit-popup {' +\n ' position: fixed; display: none; z-index: 3001;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .375rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .35rem; gap: .25rem; align-items: center;' +\n ' white-space: nowrap;' +\n '}' +\n '.te-link-edit-popup input {' +\n ' width: 220px; padding: .2rem .4rem; font-size: .8rem;' +\n ' border: 1px solid #dee2e6; border-radius: .25rem; outline: none;' +\n '}' +\n '.te-link-edit-popup input:focus {' +\n ' border-color: #86b7fe; box-shadow: 0 0 0 2px rgba(13,110,253,.15);' +\n '}' +\n '.te-link-edit-popup .btn {' +\n ' padding: .2rem .5rem !important; font-size: .75rem !important; line-height: 1 !important;' +\n '}',\n modalHTML: '' +\n '<div class=\"te-link-modal te-modal\" aria-hidden=\"true\">' +\n ' <div class=\"te-modal-backdrop\" data-te-close></div>' +\n ' <div class=\"te-modal-dialog\">' +\n ' <div class=\"te-modal-header\">' +\n ' <h5 class=\"te-modal-title m-0\">Insert Link</h5>' +\n ' <button type=\"button\" class=\"btn-close\" data-te-close aria-label=\"Close\"></button>' +\n ' </div>' +\n ' <form class=\"te-link-form\">' +\n ' <div class=\"te-modal-body\">' +\n ' <div class=\"mb-3\">' +\n ' <label class=\"form-label\">URL</label>' +\n ' <input type=\"url\" class=\"te-link-url form-control\" placeholder=\"https://example.com\" required>' +\n ' </div>' +\n ' <div class=\"mb-3\">' +\n ' <label class=\"form-label\">Text (optional)</label>' +\n ' <input type=\"text\" class=\"te-link-text form-control\" placeholder=\"Link text\">' +\n ' </div>' +\n ' <div class=\"mb-3\">' +\n ' <label class=\"form-label\">Rel (optional)</label>' +\n ' <input type=\"text\" class=\"te-link-rel form-control\" placeholder=\"noopener noreferrer, nofollow, ugc, sponsored\">' +\n ' </div>' +\n ' <div class=\"form-check\">' +\n ' <input class=\"te-link-blank form-check-input\" type=\"checkbox\" checked>' +\n ' <label class=\"form-check-label\">Open in new tab</label>' +\n ' </div>' +\n ' </div>' +\n ' <div class=\"te-modal-footer\">' +\n ' <button type=\"button\" class=\"btn btn-outline-secondary\" data-te-close>Cancel</button>' +\n ' <button type=\"submit\" class=\"btn btn-primary\">Insert</button>' +\n ' </div>' +\n ' </form>' +\n ' </div>' +\n '</div>',\n init(ctx: PluginContext): void {\n if(!ctx.features.link) return;\n var editingLink: HTMLAnchorElement | null = null;\n\n var linkTools = document.createElement('div');\n linkTools.className = 'te-link-tools';\n linkTools.innerHTML = '' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-link=\"edit\" title=\"Edit link\"><i class=\"ti ti-edit\"></i> Edit</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-link=\"remove\" title=\"Remove link\"><i class=\"ti ti-link-off\"></i> Remove</button>';\n document.body.appendChild(linkTools);\n\n var linkEditPopup = document.createElement('div');\n linkEditPopup.className = 'te-link-edit-popup';\n linkEditPopup.innerHTML = '' +\n '<input type=\"url\" class=\"te-link-edit-url\" placeholder=\"https://example.com\" />' +\n '<button type=\"button\" class=\"btn btn-sm btn-primary\" data-te-link-edit=\"apply\">Apply</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-link-edit=\"cancel\">Cancel</button>';\n document.body.appendChild(linkEditPopup);\n\n function posLinkTools(a: HTMLAnchorElement): void {\n var rect = a.getBoundingClientRect();\n var er = ctx.editor.getBoundingClientRect();\n linkTools.style.display = 'flex';\n linkTools.style.visibility = 'hidden';\n var tw = linkTools.offsetWidth;\n var th = linkTools.offsetHeight;\n var left = rect.left + rect.width / 2 - tw / 2;\n if(left < er.left) left = er.left;\n if(left + tw > er.right) left = er.right - tw;\n linkTools.style.left = left + 'px';\n var spaceBelow = window.innerHeight - rect.bottom;\n var top = (spaceBelow >= th + 6) ? (rect.bottom + 6) : (rect.top - th - 6);\n if(top < er.top) top = rect.bottom + 6;\n linkTools.style.top = top + 'px';\n linkTools.style.visibility = '';\n }\n\n function hideLinkTools(): void {\n linkTools.style.display = 'none';\n editingLink = null;\n }\n\n var _editPopupTime = 0;\n\n function hideEditPopup(_from?: string): void {\n if(Date.now() - _editPopupTime < 200) return;\n linkEditPopup.style.display = 'none';\n }\n\n function showEditPopup(link: HTMLAnchorElement): void {\n _editPopupTime = Date.now();\n var rect = link.getBoundingClientRect();\n var er = ctx.editor.getBoundingClientRect();\n linkEditPopup.style.display = 'flex';\n linkEditPopup.style.visibility = 'hidden';\n var pw = linkEditPopup.offsetWidth || 350;\n var ph = linkEditPopup.offsetHeight || 32;\n var left = rect.left + rect.width / 2 - pw / 2;\n if(left < er.left) left = er.left;\n if(left + pw > er.right) left = er.right - pw;\n linkEditPopup.style.left = left + 'px';\n var spaceBelow = window.innerHeight - rect.bottom;\n linkEditPopup.style.top = ((spaceBelow >= ph + 6) ? (rect.bottom + 6) : (rect.top - ph - 6)) + 'px';\n linkEditPopup.style.visibility = '';\n (linkEditPopup.querySelector('.te-link-edit-url') as HTMLInputElement).value = link.getAttribute('href') || '';\n setTimeout(function(){ (linkEditPopup.querySelector('.te-link-edit-url') as HTMLInputElement).focus(); }, 0);\n }\n\n function openLinkModal(): void {\n ctx.saveSel();\n var m = ctx.wrapper.querySelector('.te-link-modal');\n if(m) m.classList.add('is-open');\n }\n\n function closeLinkModal(): void {\n var m = ctx.wrapper.querySelector('.te-link-modal');\n if(m) m.classList.remove('is-open');\n }\n\n function fillModal(a: HTMLAnchorElement): void {\n var u = ctx.wrapper.querySelector('.te-link-url') as HTMLInputElement | null;\n var t = ctx.wrapper.querySelector('.te-link-text') as HTMLInputElement | null;\n var r = ctx.wrapper.querySelector('.te-link-rel') as HTMLInputElement | null;\n var b = ctx.wrapper.querySelector('.te-link-blank') as HTMLInputElement | null;\n var sub = ctx.wrapper.querySelector('.te-link-form button[type=\"submit\"]') as HTMLButtonElement | null;\n if(u) u.value = a.getAttribute('href') || '';\n if(t) t.value = a.textContent || '';\n if(r) r.value = a.getAttribute('rel') || '';\n if(b) b.checked = a.getAttribute('target') === '_blank';\n if(sub) sub.textContent = 'Update';\n }\n\n function getSelectedText(): string {\n var sel = window.getSelection();\n return (sel && sel.toString().trim()) || '';\n }\n\n var btn = ctx.wrapper.querySelector('[data-cmd=\"createLink\"]');\n if(btn){\n btn.addEventListener('click', function(){\n editingLink = null;\n hideLinkTools();\n hideEditPopup();\n var u = ctx.wrapper.querySelector('.te-link-url') as HTMLInputElement | null;\n var t = ctx.wrapper.querySelector('.te-link-text') as HTMLInputElement | null;\n var r = ctx.wrapper.querySelector('.te-link-rel') as HTMLInputElement | null;\n var b = ctx.wrapper.querySelector('.te-link-blank') as HTMLInputElement | null;\n var sub = ctx.wrapper.querySelector('.te-link-form button[type=\"submit\"]') as HTMLButtonElement | null;\n if(u) u.value = '';\n if(t) t.value = getSelectedText() || '';\n if(r) r.value = '';\n if(b) b.checked = true;\n if(sub) sub.textContent = 'Insert';\n openLinkModal();\n });\n }\n\n ctx.editor.addEventListener('click', function(e: MouseEvent){\n var a = (e.target as HTMLElement).closest && (e.target as HTMLElement).closest('a') as HTMLAnchorElement | null;\n if(!a || !ctx.editor.contains(a)) return;\n if(!ctx.wrapper.contains(a)) return;\n if(e.ctrlKey || e.metaKey) e.preventDefault();\n e.stopPropagation();\n hideEditPopup('editor.click');\n editingLink = a;\n fillModal(a);\n posLinkTools(a);\n });\n\n linkTools.addEventListener('mousedown', function(e: MouseEvent){\n e.preventDefault();\n e.stopPropagation();\n var actionBtn = (e.target as HTMLElement).closest && (e.target as HTMLElement).closest('[data-te-link]') as HTMLElement | null;\n if(!actionBtn) return;\n var action = actionBtn.getAttribute('data-te-link');\n var link = editingLink;\n\n if(action === 'edit'){\n if(link && ctx.editor.contains(link)){\n editingLink = link;\n showEditPopup(link);\n setTimeout(function(){ linkTools.style.display = 'none'; }, 0);\n }\n }\n else if(action === 'remove'){\n hideLinkTools();\n if(link && ctx.editor.contains(link)){\n var parent = link.parentNode!;\n while(link.firstChild){\n parent.insertBefore(link.firstChild, link);\n }\n parent.removeChild(link);\n ctx.editor.focus();\n }\n }\n });\n\n function updateLink(url: string): void {\n if(!editingLink || !ctx.editor.contains(editingLink)) return;\n if(!/^https?:\\/\\//i.test(url) && !/^mailto:/i.test(url) && !/^tel:/i.test(url)) url = 'https://' + url;\n editingLink.setAttribute('href', url);\n hideEditPopup('updateLink');\n editingLink = null;\n ctx.editor.focus();\n }\n\n linkEditPopup.addEventListener('click', function(e: MouseEvent){ e.stopPropagation(); });\n\n linkEditPopup.addEventListener('mousedown', function(e: MouseEvent){\n e.preventDefault();\n e.stopPropagation();\n var actionBtn = (e.target as HTMLElement).closest && (e.target as HTMLElement).closest('[data-te-link-edit]') as HTMLElement | null;\n if(!actionBtn) return;\n var action = actionBtn.getAttribute('data-te-link-edit');\n\n if(action === 'cancel'){\n hideEditPopup();\n editingLink = null;\n ctx.editor.focus();\n return;\n }\n\n if(action === 'apply'){\n var url = (linkEditPopup.querySelector('.te-link-edit-url') as HTMLInputElement).value.trim();\n if(!url) return;\n updateLink(url);\n }\n });\n\n linkEditPopup.addEventListener('keydown', function(e: KeyboardEvent){\n if(e.key === 'Enter'){\n e.preventDefault();\n var url = (linkEditPopup.querySelector('.te-link-edit-url') as HTMLInputElement).value.trim();\n if(!url) return;\n updateLink(url);\n }\n if(e.key === 'Escape'){\n hideEditPopup();\n editingLink = null;\n ctx.editor.focus();\n }\n });\n\n linkTools.addEventListener('click', function(e: MouseEvent){ e.stopPropagation(); });\n\n document.addEventListener('click', function(e: MouseEvent){\n if(linkTools.style.display !== 'none' && !linkTools.contains(e.target as Node)){\n hideLinkTools();\n }\n if(linkEditPopup.style.display !== 'none' && !linkEditPopup.contains(e.target as Node)){\n var fromTools = (e.target as HTMLElement).closest && (e.target as HTMLElement).closest('.te-link-tools');\n if(!fromTools){\n if(Date.now() - _editPopupTime < 200){\n // too soon after showing edit popup, don't close\n } else {\n hideEditPopup('doc.click');\n editingLink = null;\n }\n }\n }\n });\n\n var form = ctx.wrapper.querySelector('.te-link-form');\n if(form){\n form.addEventListener('submit', function(e: Event){\n e.preventDefault();\n var url = ((ctx.wrapper.querySelector('.te-link-url') as HTMLInputElement).value || '').trim();\n var text = ((ctx.wrapper.querySelector('.te-link-text') as HTMLInputElement).value || '').trim();\n var blank = (ctx.wrapper.querySelector('.te-link-blank') as HTMLInputElement).checked;\n var rel = ((ctx.wrapper.querySelector('.te-link-rel') as HTMLInputElement).value || '').trim();\n if(!url) return;\n var isOk = ctx.utils.isSafeUrl ? ctx.utils.isSafeUrl(url, (ctx.options as any).urlSchemes || ['http','https']) : true;\n if(!isOk) return;\n\n if(editingLink && ctx.editor.contains(editingLink)){\n editingLink.setAttribute('href', url);\n if(blank) editingLink.setAttribute('target', '_blank');\n else editingLink.removeAttribute('target');\n if(rel) editingLink.setAttribute('rel', rel);\n else editingLink.removeAttribute('rel');\n if(text) editingLink.textContent = text;\n closeLinkModal();\n ctx.editor.focus();\n return;\n }\n\n ctx.restoreSel();\n var relFinal = rel || (blank ? 'noopener noreferrer' : '');\n var displayText = (text || url).replace(/&/g,'&').replace(/</g,'<').replace(/>/g,'>').replace(/\"/g,'"');\n var a = '<a href=\"' + url.replace(/\"/g,'"') + '\"' +\n (blank ? ' target=\"_blank\"' : '') +\n (relFinal ? ' rel=\"' + relFinal.replace(/\"/g,'"') + '\"' : '') +\n '>' + displayText + '</a>';\n document.execCommand('insertHTML', false, a);\n closeLinkModal();\n ctx.editor.focus();\n });\n }\n\n var closeBtns = ctx.wrapper.querySelectorAll('[data-te-close]');\n for(var i = 0; i < closeBtns.length; i++){\n closeBtns[i].addEventListener('click', function(){ editingLink = null; });\n }\n }\n};\n\nexport default link;\n","import type { Plugin, PluginContext } from '../types';\n\nconst image: Plugin = {\n name: 'image',\n order: 51,\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Image\" data-cmd=\"insertImage\"><i class=\"ti ti-photo\"></i></button>',\n modalHTML: '' +\n '<div class=\"te-image-modal te-modal\" aria-hidden=\"true\">' +\n ' <div class=\"te-modal-backdrop\" data-te-close></div>' +\n ' <div class=\"te-modal-dialog\">' +\n ' <div class=\"te-modal-header\">' +\n ' <h5 class=\"te-modal-title m-0\">Insert Image</h5>' +\n ' <button type=\"button\" class=\"btn-close\" data-te-close aria-label=\"Close\"></button>' +\n ' </div>' +\n ' <form class=\"te-image-form\">' +\n ' <div class=\"te-modal-body\">' +\n ' <div class=\"mb-3\">' +\n ' <label class=\"form-label\">Image URL</label>' +\n ' <input type=\"text\" class=\"te-image-url form-control\" placeholder=\"/path/to/image.jpg or https://...\" required>' +\n ' <div class=\"mt-2\"><button type=\"button\" class=\"te-image-browse btn btn-sm btn-outline-secondary\"><i class=\"ti ti-folder\"></i> Browse...</button></div>' +\n ' </div>' +\n ' <div class=\"mb-3\">' +\n ' <label class=\"form-label\">Alt text (optional)</label>' +\n ' <input type=\"text\" class=\"te-image-alt form-control\" placeholder=\"Description\">' +\n ' </div>' +\n ' </div>' +\n ' <div class=\"te-modal-footer\">' +\n ' <button type=\"button\" class=\"btn btn-outline-secondary\" data-te-close>Cancel</button>' +\n ' <button type=\"submit\" class=\"btn btn-primary\">Insert</button>' +\n ' </div>' +\n ' </form>' +\n ' </div>' +\n '</div>',\n init(ctx: PluginContext): void {\n if(!ctx.features.image) return;\n var btn = ctx.wrapper.querySelector('[data-cmd=\"insertImage\"]');\n if(btn){\n btn.addEventListener('click', function(){\n ctx.saveSel();\n var m = ctx.wrapper.querySelector('.te-image-modal');\n if(m) m.classList.add('is-open');\n });\n }\n var inputUrl = ctx.wrapper.querySelector('.te-image-url') as HTMLInputElement | null;\n\n var browseBtn = ctx.wrapper.querySelector('.te-image-browse');\n if(browseBtn){\n browseBtn.addEventListener('click', function(e: Event){\n e.preventDefault();\n if(ctx.TulihEditor && typeof ctx.TulihEditor.onBrowseImage === 'function'){\n ctx.TulihEditor.onBrowseImage({ container: ctx.wrapper, editor: ctx.editor }, function(url: string){\n if(url && inputUrl){ inputUrl.value = url; inputUrl.focus(); }\n });\n return;\n }\n var fi = document.createElement('input');\n fi.type = 'file';\n fi.accept = 'image/*';\n fi.style.display = 'none';\n document.body.appendChild(fi);\n fi.addEventListener('change', function(){\n var file = fi.files && fi.files[0];\n if(!file){ document.body.removeChild(fi); return; }\n var r = new FileReader();\n r.onload = function(){\n if(inputUrl){\n inputUrl.value = r.result as string;\n inputUrl.focus();\n }\n document.body.removeChild(fi);\n };\n r.readAsDataURL(file);\n });\n fi.click();\n });\n }\n var form = ctx.wrapper.querySelector('.te-image-form') as HTMLFormElement | null;\n if(form){\n form.addEventListener('submit', function(e: Event){\n e.preventDefault();\n var src = ((ctx.wrapper.querySelector('.te-image-url') as HTMLInputElement).value || '').trim();\n var alt = ((ctx.wrapper.querySelector('.te-image-alt') as HTMLInputElement).value || '').trim();\n if(!src) return;\n var ok = ctx.utils.isSafeUrl ? ctx.utils.isSafeUrl(src, (ctx.options as any).imageSchemes || ['http','https','data']) : true;\n if(!ok) return;\n ctx.restoreSel();\n ctx.editor.focus();\n var img = document.createElement('img');\n img.src = src;\n if(alt) img.alt = alt;\n var sel = window.getSelection();\n if(sel && sel.rangeCount > 0){\n var range = sel.getRangeAt(0);\n range.deleteContents();\n range.insertNode(img);\n range.setStartAfter(img);\n range.collapse(true);\n sel.removeAllRanges();\n sel.addRange(range);\n }\n form!.closest('.te-modal')!.classList.remove('is-open');\n });\n }\n }\n};\n\nexport default image;\n","import type { Plugin, PluginContext } from '../types';\n\nconst imageProps: Plugin = {\n name: 'imageProps',\n order: 52,\n deps: ['image'],\n modalHTML: '' +\n '<div class=\"te-image-props-modal te-modal\" aria-hidden=\"true\">' +\n ' <div class=\"te-modal-backdrop\" data-te-close></div>' +\n ' <div class=\"te-modal-dialog\">' +\n ' <div class=\"te-modal-header\">' +\n ' <h5 class=\"te-modal-title m-0\">Image Properties</h5>' +\n ' <button type=\"button\" class=\"btn-close\" data-te-close aria-label=\"Close\"></button>' +\n ' </div>' +\n ' <form class=\"te-image-props-form\">' +\n ' <div class=\"te-modal-body\">' +\n ' <div class=\"row g-2 mb-3\">' +\n ' <div class=\"col\">' +\n ' <label class=\"form-label\">Width</label>' +\n ' <input type=\"number\" min=\"0\" class=\"te-image-props-width form-control\" placeholder=\"e.g. 800\">' +\n ' </div>' +\n ' <div class=\"col\">' +\n ' <label class=\"form-label\">Height</label>' +\n ' <input type=\"number\" min=\"0\" class=\"te-image-props-height form-control\" placeholder=\"e.g. 600\">' +\n ' </div>' +\n ' </div>' +\n ' <div class=\"mb-3\">' +\n ' <label class=\"form-label\">Alt</label>' +\n ' <input type=\"text\" class=\"te-image-props-alt form-control\" placeholder=\"Alternative text\">' +\n ' </div>' +\n ' <div class=\"row g-2\">' +\n ' <div class=\"col\">' +\n ' <label class=\"form-label\">Class</label>' +\n ' <input type=\"text\" class=\"te-image-props-class form-control\" placeholder=\"class-1 class-2\">' +\n ' </div>' +\n ' <div class=\"col\">' +\n ' <label class=\"form-label\">ID</label>' +\n ' <input type=\"text\" class=\"te-image-props-id form-control\" placeholder=\"optional-id\">' +\n ' </div>' +\n ' </div>' +\n ' <div class=\"mb-3 mt-3\">' +\n ' <label class=\"form-label\">Style (inline CSS)</label>' +\n ' <input type=\"text\" class=\"te-image-props-style form-control\" placeholder=\"max-width:100%; height:auto;\">' +\n ' </div>' +\n ' </div>' +\n ' <div class=\"te-modal-footer\">' +\n ' <button type=\"button\" class=\"btn btn-outline-secondary\" data-te-close>Cancel</button>' +\n ' <button type=\"submit\" class=\"btn btn-primary\">Apply</button>' +\n ' </div>' +\n ' </form>' +\n ' </div>' +\n '</div>',\n init(ctx: PluginContext): void {\n if(!ctx.features.image || !ctx.features.imageProps) return;\n var modal = ctx.wrapper.querySelector('.te-image-props-modal') as HTMLElement | null;\n var form = ctx.wrapper.querySelector('.te-image-props-form') as HTMLFormElement | null;\n var altInp = ctx.wrapper.querySelector('.te-image-props-alt') as HTMLInputElement | null;\n var wInp = ctx.wrapper.querySelector('.te-image-props-width') as HTMLInputElement | null;\n var hInp = ctx.wrapper.querySelector('.te-image-props-height') as HTMLInputElement | null;\n var clsInp = ctx.wrapper.querySelector('.te-image-props-class') as HTMLInputElement | null;\n var idInp = ctx.wrapper.querySelector('.te-image-props-id') as HTMLInputElement | null;\n var styleInp = ctx.wrapper.querySelector('.te-image-props-style') as HTMLInputElement | null;\n var currentImg: HTMLImageElement | null = null;\n\n ctx.editor.addEventListener('dblclick', function(e: MouseEvent){\n var img = e.target && ((e.target as Element).closest && (e.target as Element).closest('img')) as HTMLImageElement | null;\n if(img && ctx.wrapper.contains(img) && modal){\n currentImg = img;\n if(altInp) altInp.value = img.getAttribute('alt') || '';\n if(wInp) wInp.value = img.getAttribute('width') || '';\n if(hInp) hInp.value = img.getAttribute('height') || '';\n if(clsInp) clsInp.value = img.getAttribute('class') || '';\n if(idInp) idInp.value = img.getAttribute('id') || '';\n if(styleInp) styleInp.value = img.getAttribute('style') || '';\n modal.classList.add('is-open');\n }\n });\n\n if(form){\n form.addEventListener('submit', function(e: Event){\n e.preventDefault();\n if(!currentImg){\n if(modal) modal.classList.remove('is-open');\n return;\n }\n var alt = (altInp && altInp.value) || '';\n var w = (wInp && wInp.value) || '';\n var h = (hInp && hInp.value) || '';\n var cls = (clsInp && clsInp.value) || '';\n var idv = (idInp && idInp.value) || '';\n var style = (styleInp && styleInp.value) || '';\n if(style){\n var safeCss: string[] = [];\n style.split(';').forEach(function(decl){\n var idx = decl.indexOf(':');\n if(idx === -1) return;\n var prop = decl.slice(0, idx).trim().toLowerCase();\n var val = decl.slice(idx + 1).trim();\n var SAFE = ['color','background-color','font-family','font-size','font-style','font-weight','text-align','text-decoration','line-height','letter-spacing','word-spacing','margin','margin-top','margin-right','margin-bottom','margin-left','padding','padding-top','padding-right','padding-bottom','padding-left','border','border-collapse','border-color','border-style','border-width','border-radius','width','height','max-width','max-height','min-width','min-height','float','clear','vertical-align','direction','white-space'];\n if(SAFE.indexOf(prop) !== -1) safeCss.push(prop + ':' + val);\n });\n style = safeCss.join(';');\n }\n\n if(alt) currentImg.setAttribute('alt', alt); else currentImg.removeAttribute('alt');\n if(w) currentImg.setAttribute('width', w); else currentImg.removeAttribute('width');\n if(h) currentImg.setAttribute('height', h); else currentImg.removeAttribute('height');\n if(cls) currentImg.setAttribute('class', cls); else currentImg.removeAttribute('class');\n if(idv) currentImg.setAttribute('id', idv); else currentImg.removeAttribute('id');\n if(style) currentImg.setAttribute('style', style); else currentImg.removeAttribute('style');\n\n if(modal) modal.classList.remove('is-open');\n currentImg = null;\n });\n }\n }\n};\n\nexport default imageProps;\n","import type { Plugin, PluginContext } from '../types';\n\nconst imageTools: Plugin = {\n name: 'imageTools',\n order: 56,\n deps: ['image', 'imageProps'],\n css: '' +\n '.te-image-tools {' +\n ' position: absolute; display: none; z-index: 2000;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .375rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .375rem; gap: .25rem; align-items: center;' +\n '}' +\n '.te-image-tools .btn { padding: .2rem .4rem; font-size: .8rem; }' +\n '.te-image-tools svg, .te-image-tools i { pointer-events: none; }' +\n '.te-image-tools .te-image-tools-alt {' +\n ' width: 130px; height: 26px; font-size: .8rem;' +\n ' padding: 0 .35rem; border: 1px solid #dee2e6; border-radius: .25rem;' +\n '}' +\n '.te-image-tools .te-image-tools-alt:focus { outline: none; border-color: #86b7fe; box-shadow: 0 0 0 2px rgba(13,110,253,.25); }' +\n '.te-image-tools .te-divider-v {' +\n ' width: 1px; height: 20px; background: #dee2e6;' +\n '}' +\n '.te-image-tools .active { background: #e7f1ff; border-color: #b6d4fe; }' +\n '.te-editor img.te-focused {' +\n ' outline: 3px solid rgba(13,110,253,.4);' +\n ' outline-offset: 1px;' +\n '}' +\n '.te-image-resize {' +\n ' position: absolute; display: none; z-index: 2001;' +\n ' width: 10px; height: 10px;' +\n ' background: #0d6efd; border: 2px solid #fff;' +\n ' border-radius: 50%; cursor: nwse-resize;' +\n ' box-shadow: 0 1px 4px rgba(0,0,0,.3);' +\n '}' +\n '.te-image-resize:hover { transform: scale(1.2); }' +\n '.te-figure {' +\n ' display: inline-block; margin: .5rem 0;' +\n ' text-align: center; max-width: 100%;' +\n '}' +\n '.te-figure figcaption {' +\n ' font-size: .85rem; color: #6c757d;' +\n ' padding: .25rem .5rem; font-style: italic;' +\n '}',\n init(ctx: PluginContext): void {\n if(!ctx.features.image || !ctx.features.imageTools) return;\n\n var wrapper = ctx.wrapper;\n var editor = ctx.editor;\n var currentImage: HTMLImageElement | null = null;\n\n var tools = document.createElement('div');\n tools.className = 'te-image-tools';\n tools.innerHTML = '' +\n '<input type=\"text\" class=\"te-image-tools-alt\" placeholder=\"Alt text\" title=\"Alt text (Enter to apply)\" />' +\n '<div class=\"te-divider-v\"></div>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-image=\"align-default\" title=\"Inline\"><i class=\"ti ti-align-left\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-image=\"align-left\" title=\"Float left\"><i class=\"ti ti-align-left\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-image=\"align-center\" title=\"Center\"><i class=\"ti ti-align-center\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-image=\"align-right\" title=\"Float right\"><i class=\"ti ti-align-right\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-image=\"caption\" title=\"Caption (toggle)\"><i class=\"ti ti-typography\"></i></button>' +\n '<div class=\"te-divider-v\"></div>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-image=\"width-100\" title=\"Width 100%\">100%</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-image=\"width-75\" title=\"Width 75%\">75%</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-image=\"width-50\" title=\"Width 50%\">50%</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-image=\"width-orig\" title=\"Original size\">Orig</button>' +\n '<div class=\"te-divider-v\"></div>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-image=\"border\" title=\"Toggle border\">Brdr</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-image=\"rounded\" title=\"Toggle rounded corners\">Rnd</button>' +\n '<div class=\"te-divider-v\"></div>' +\n '<button type=\"button\" class=\"btn btn-sm btn-outline-secondary\" data-te-image=\"props\" title=\"Image Properties\"><i class=\"ti ti-settings\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-outline-danger\" data-te-image=\"delete\" title=\"Delete image\"><i class=\"ti ti-x\"></i></button>';\n document.body.appendChild(tools);\n\n var resizeHandle = document.createElement('div');\n resizeHandle.className = 'te-image-resize';\n document.body.appendChild(resizeHandle);\n\n function getAlign(img: HTMLImageElement): string {\n var st = img.style;\n if(st.float === 'left') return 'left';\n if(st.float === 'right') return 'right';\n if(st.display === 'block' && st.marginLeft === 'auto' && st.marginRight === 'auto') return 'center';\n return 'default';\n }\n\n function setAlign(img: HTMLImageElement, align: string): void {\n if(align === 'default'){\n img.style.float = '';\n img.style.display = '';\n img.style.marginLeft = '';\n img.style.marginRight = '';\n } else if(align === 'left'){\n img.style.float = 'left';\n img.style.display = '';\n img.style.marginLeft = '0';\n img.style.marginRight = '1em';\n } else if(align === 'right'){\n img.style.float = 'right';\n img.style.display = '';\n img.style.marginLeft = '1em';\n img.style.marginRight = '0';\n } else if(align === 'center'){\n img.style.float = '';\n img.style.display = 'block';\n img.style.marginLeft = 'auto';\n img.style.marginRight = 'auto';\n }\n }\n\n function clearImageFocus(): void {\n if(!editor) return;\n var prev = editor.querySelector('.te-focused') as HTMLElement | null;\n if(prev) prev.classList.remove('te-focused');\n }\n\n function showResizeHandle(img: HTMLImageElement): void {\n var rect = img.getBoundingClientRect();\n resizeHandle.style.left = (window.scrollX + rect.right - 5) + 'px';\n resizeHandle.style.top = (window.scrollY + rect.bottom - 5) + 'px';\n resizeHandle.style.display = 'block';\n }\n\n function updateAlignBtns(img: HTMLImageElement): void {\n var align = getAlign(img);\n tools.querySelectorAll('[data-te-image^=\"align-\"]').forEach(function(b){\n b.classList.toggle('active', b.getAttribute('data-te-image') === 'align-' + align);\n });\n }\n\n function posTools(img: HTMLImageElement): void {\n var rect = img.getBoundingClientRect();\n var altInp = tools.querySelector('.te-image-tools-alt') as HTMLInputElement | null;\n if(altInp) altInp.value = img.getAttribute('alt') || '';\n tools.style.display = 'flex';\n tools.style.left = (window.scrollX + rect.left) + 'px';\n tools.style.visibility = 'hidden';\n var toolsH = tools.offsetHeight;\n var editorRect = wrapper.getBoundingClientRect();\n var below = rect.bottom + 6 + toolsH;\n var above = rect.top - 6 - toolsH;\n if(below > editorRect.bottom && above > editorRect.top){\n tools.style.top = (window.scrollY + rect.top - 6 - toolsH) + 'px';\n } else {\n tools.style.top = (window.scrollY + rect.bottom + 6) + 'px';\n }\n tools.style.visibility = '';\n showResizeHandle(img);\n updateAlignBtns(img);\n var capBtn = tools.querySelector('[data-te-image=\"caption\"]');\n if(capBtn) capBtn.classList.toggle('active', !!(img.parentNode && (img.parentNode as Element).tagName === 'FIGURE'));\n var brdrBtn = tools.querySelector('[data-te-image=\"border\"]');\n if(brdrBtn){\n var b = img.style.border || '';\n brdrBtn.classList.toggle('active', !!(b && b !== 'none'));\n }\n var rndBtn = tools.querySelector('[data-te-image=\"rounded\"]');\n if(rndBtn){\n var r = img.style.borderRadius || '';\n rndBtn.classList.toggle('active', !!(r && r !== '0px' && r !== ''));\n }\n }\n\n function hideTools(): void {\n tools.style.display = 'none';\n resizeHandle.style.display = 'none';\n clearImageFocus();\n currentImage = null;\n }\n\n editor.addEventListener('click', function(e: MouseEvent){\n var img = e.target && ((e.target as Element).closest ? (e.target as Element).closest('img') : null) as HTMLImageElement | null;\n if(img && wrapper.contains(img)){\n e.stopPropagation();\n currentImage = img;\n clearImageFocus();\n img.classList.add('te-focused');\n img.setAttribute('tabindex', '-1');\n try { img.focus({preventScroll: true}); } catch(_){ }\n posTools(img);\n } else {\n if(!tools.contains(e.target as Node) && e.target !== resizeHandle){\n hideTools();\n }\n }\n });\n\n editor.addEventListener('dblclick', function(){\n hideTools();\n });\n\n document.addEventListener('selectionchange', function(){\n if(!currentImage) return;\n if(document.activeElement !== currentImage &&\n !tools.contains(document.activeElement)){\n var sel = window.getSelection();\n if(!sel || sel.isCollapsed){\n hideTools();\n }\n }\n });\n\n tools.addEventListener('click', function(e: MouseEvent){\n var actionBtn = e.target && (e.target as Element).closest('[data-te-image]') as HTMLElement | null;\n var action = actionBtn && actionBtn.getAttribute('data-te-image');\n if(!action || !currentImage) return;\n e.preventDefault();\n e.stopPropagation();\n\n if(action === 'width-100'){\n currentImage.setAttribute('width', '100%');\n if(currentImage.style) currentImage.style.maxWidth = '100%';\n posTools(currentImage);\n }\n else if(action === 'width-75'){\n currentImage.setAttribute('width', '75%');\n posTools(currentImage);\n }\n else if(action === 'width-50'){\n currentImage.setAttribute('width', '50%');\n posTools(currentImage);\n }\n else if(action === 'width-orig'){\n currentImage.removeAttribute('width');\n currentImage.removeAttribute('height');\n if(currentImage.style) currentImage.style.maxWidth = '';\n posTools(currentImage);\n }\n else if(action === 'delete'){\n var parent = currentImage.parentNode;\n if(parent) parent.removeChild(currentImage);\n hideTools();\n }\n else if(action === 'props'){\n var dblClick = new MouseEvent('dblclick', { bubbles: true });\n currentImage.dispatchEvent(dblClick);\n hideTools();\n }\n else if(action.indexOf('align-') === 0){\n var a = action.replace('align-', '');\n setAlign(currentImage, a);\n updateAlignBtns(currentImage);\n posTools(currentImage);\n }\n else if(action === 'border'){\n var curBorder = currentImage.style.border || '';\n if(curBorder && curBorder !== 'none'){\n currentImage.style.border = '';\n currentImage.removeAttribute('border');\n } else {\n currentImage.style.border = '2px solid #dee2e6';\n }\n posTools(currentImage);\n }\n else if(action === 'rounded'){\n var curRadius = currentImage.style.borderRadius || '';\n if(curRadius && curRadius !== '0px'){\n currentImage.style.borderRadius = '';\n } else {\n currentImage.style.borderRadius = '8px';\n }\n posTools(currentImage);\n }\n else if(action === 'caption'){\n var fig = currentImage.parentNode as Element | null;\n if(fig && fig.tagName === 'FIGURE' && fig.classList.contains('te-figure')){\n var parent = fig.parentNode;\n var img = fig.querySelector('img') || fig.querySelector('figcaption');\n if(img){\n parent!.insertBefore(img, fig);\n parent!.removeChild(fig);\n }\n } else {\n var figure = document.createElement('figure');\n figure.className = 'te-figure';\n var caption = document.createElement('figcaption');\n caption.textContent = 'Caption';\n currentImage.parentNode!.insertBefore(figure, currentImage);\n figure.appendChild(currentImage);\n figure.appendChild(caption);\n caption.contentEditable = 'true';\n }\n posTools(currentImage);\n }\n });\n\n tools.addEventListener('keydown', function(e: KeyboardEvent){\n if(e.key === 'Enter' && currentImage){\n var altInp = tools.querySelector('.te-image-tools-alt') as HTMLInputElement | null;\n if(altInp){\n var val = altInp.value.trim();\n if(val) currentImage.setAttribute('alt', val);\n else currentImage.removeAttribute('alt');\n }\n }\n });\n\n var resizeData: { startX: number; parentW: number; startPct: number; startH: number } | null = null;\n resizeHandle.addEventListener('mousedown', function(e: MouseEvent){\n e.preventDefault();\n e.stopPropagation();\n if(!currentImage) return;\n var parentW = currentImage.parentNode ? (currentImage.parentNode as HTMLElement).clientWidth : currentImage.clientWidth;\n var currentPct = ((currentImage.clientWidth / parentW) * 100);\n var rect = currentImage.getBoundingClientRect();\n resizeData = {\n startX: e.clientX,\n parentW: parentW,\n startPct: currentPct,\n startH: rect.height\n };\n document.addEventListener('mousemove', onResize);\n document.addEventListener('mouseup', onResizeEnd);\n });\n\n function onResize(e: MouseEvent): void {\n if(!resizeData || !currentImage) return;\n var dx = e.clientX - resizeData.startX;\n var pctDelta = (dx / resizeData.parentW) * 100;\n var newPct = Math.max(5, resizeData.startPct + pctDelta);\n currentImage.style.width = newPct + '%';\n currentImage.style.height = 'auto';\n currentImage.removeAttribute('width');\n currentImage.removeAttribute('height');\n showResizeHandle(currentImage);\n }\n\n function onResizeEnd(): void {\n document.removeEventListener('mousemove', onResize);\n document.removeEventListener('mouseup', onResizeEnd);\n resizeData = null;\n if(currentImage) posTools(currentImage);\n }\n\n window.addEventListener('scroll', function(){\n if(currentImage && tools.style.display !== 'none') posTools(currentImage);\n });\n window.addEventListener('resize', function(){\n if(currentImage && tools.style.display !== 'none') posTools(currentImage);\n });\n }\n};\n\nexport default imageTools;\n","import type { Plugin, PluginContext } from '../types';\nimport * as H from '../core/helpers';\n\nconst iframe: Plugin = {\n name: 'iframe',\n order: 53,\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Iframe\" data-cmd=\"insertIframe\"><i class=\"ti ti-video\"></i></button>',\n modalHTML: '' +\n '<div class=\"te-iframe-modal te-modal\" aria-hidden=\"true\">' +\n ' <div class=\"te-modal-backdrop\" data-te-close></div>' +\n ' <div class=\"te-modal-dialog\">' +\n ' <div class=\"te-modal-header\">' +\n ' <h5 class=\"te-modal-title m-0\">Insert Iframe</h5>' +\n ' <button type=\"button\" class=\"btn-close\" data-te-close aria-label=\"Close\"></button>' +\n ' </div>' +\n ' <form class=\"te-iframe-form\">' +\n ' <div class=\"te-modal-body\">' +\n ' <div class=\"mb-3\">' +\n ' <label class=\"form-label\">Src URL</label>' +\n ' <input type=\"url\" class=\"te-iframe-src form-control\" placeholder=\"https://...\" required>' +\n ' </div>' +\n ' <div class=\"row g-2 mb-3\">' +\n ' <div class=\"col\">' +\n ' <label class=\"form-label\">Width (px)</label>' +\n ' <input type=\"number\" min=\"0\" class=\"te-iframe-width form-control\" placeholder=\"640\">' +\n ' </div>' +\n ' <div class=\"col\">' +\n ' <label class=\"form-label\">Height (px)</label>' +\n ' <input type=\"number\" min=\"0\" class=\"te-iframe-height form-control\" placeholder=\"360\">' +\n ' </div>' +\n ' </div>' +\n ' <div class=\"mb-3\">' +\n ' <label class=\"form-label\">Allow (optional)</label>' +\n ' <input type=\"text\" class=\"te-iframe-allow form-control\" placeholder=\"accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share\">' +\n ' </div>' +\n ' <div class=\"form-check mb-2\">' +\n ' <input class=\"te-iframe-allowfullscreen form-check-input\" type=\"checkbox\" checked>' +\n ' <label class=\"form-check-label\">Allow Fullscreen</label>' +\n ' </div>' +\n ' <div class=\"mb-2\">' +\n ' <label class=\"form-label\">Title (accessibility, optional)</label>' +\n ' <input type=\"text\" class=\"te-iframe-title form-control\" placeholder=\"Embedded content description\">' +\n ' </div>' +\n ' </div>' +\n ' <div class=\"te-modal-footer\">' +\n ' <button type=\"button\" class=\"btn btn-outline-secondary\" data-te-close>Cancel</button>' +\n ' <button type=\"submit\" class=\"btn btn-primary\">Insert</button>' +\n ' </div>' +\n ' </form>' +\n ' </div>' +\n '</div>',\n init(ctx: PluginContext): void {\n if(!ctx.features.iframe) return;\n var btn = ctx.wrapper.querySelector('[data-cmd=\"insertIframe\"]') as HTMLButtonElement | null;\n if(btn){\n btn.addEventListener('click', function(){\n ctx.saveSel();\n var m = ctx.wrapper.querySelector('.te-iframe-modal') as HTMLElement | null;\n if(m) m.classList.add('is-open');\n });\n }\n var form = ctx.wrapper.querySelector('.te-iframe-form') as HTMLFormElement | null;\n if(form){\n form.addEventListener('submit', function(e: Event){\n e.preventDefault();\n ctx.restoreSel();\n var src = ((ctx.wrapper.querySelector('.te-iframe-src') as HTMLInputElement).value || '').trim();\n var w = ((ctx.wrapper.querySelector('.te-iframe-width') as HTMLInputElement).value || '').trim();\n var h = ((ctx.wrapper.querySelector('.te-iframe-height') as HTMLInputElement).value || '').trim();\n if(!src) return;\n var allowOk = ctx.utils.isAllowedIframeUrl ? ctx.utils.isAllowedIframeUrl(src) : true;\n if(!allowOk) return;\n var attrs = ' src=\"' + src.replace(/\"/g,'"') + '\"';\n if(w) attrs += ' width=\"' + w.replace(/\"/g,'"') + '\"';\n if(h) attrs += ' height=\"' + h.replace(/\"/g,'"') + '\"';\n var sandbox = (ctx.options && ctx.options.iframeSandbox) || '';\n var allow = (ctx.options && ctx.options.iframeAllow) || '';\n if(sandbox) attrs += ' sandbox=\"' + sandbox.replace(/\"/g,'"') + '\"';\n if(allow) attrs += ' allow=\"' + allow.replace(/\"/g,'"') + '\"';\n var html = '<iframe' + attrs + ' style=\"max-width:100%;border:0;\"></iframe>';\n document.execCommand('insertHTML', false, html);\n (form!.closest('.te-modal') as HTMLElement).classList.remove('is-open');\n });\n }\n }\n};\n\nexport default iframe;\n","import type { Plugin, PluginContext } from '../types';\n\nvar MAX_COLS = 10;\nvar MAX_ROWS = 10;\n\nconst table: Plugin = {\n name: 'table',\n order: 54,\n css: '' +\n '.te-table-grid {' +\n ' position: absolute; z-index: 3000;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .5rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .75rem;' +\n '}' +\n '.te-table-grid .te-tg-label {' +\n ' font-size: .8rem; color: #6c757d; text-align: center;' +\n ' margin-bottom: .5rem;' +\n '}' +\n '.te-table-grid .te-tg-cells {' +\n ' display: grid; gap: 2px;' +\n '}' +\n '.te-table-grid .te-tg-cell {' +\n ' width: 18px; height: 18px;' +\n ' background: #f0f0f0; border: 1px solid #dee2e6;' +\n ' border-radius: 2px; cursor: pointer;' +\n '}' +\n '.te-table-grid .te-tg-cell.active {' +\n ' background: #86b7fe; border-color: #0d6efd;' +\n '}' +\n '.te-tg-header {' +\n ' display: flex; justify-content: space-between; align-items: center;' +\n ' margin-bottom: .5rem;' +\n '}' +\n '.te-toolbar [data-cmd=\"insertTable\"] svg { pointer-events: none; }',\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Table\" data-cmd=\"insertTable\"><i class=\"ti ti-table-plus\"></i></button>',\n modalHTML: '' +\n '<div class=\"te-table-props-modal te-modal\" aria-hidden=\"true\">' +\n ' <div class=\"te-modal-backdrop\" data-te-close></div>' +\n ' <div class=\"te-modal-dialog\">' +\n ' <div class=\"te-modal-header\">' +\n ' <h5 class=\"te-modal-title m-0\">Table Properties</h5>' +\n ' <button type=\"button\" class=\"btn-close\" data-te-close aria-label=\"Close\"></button>' +\n ' </div>' +\n ' <form class=\"te-table-props-form\">' +\n ' <div class=\"te-modal-body\">' +\n ' <div class=\"mb-3\">' +\n ' <label class=\"form-label\">Width (e.g. 100% or 800px)</label>' +\n ' <input type=\"text\" class=\"te-table-props-width form-control\" placeholder=\"100%\">' +\n ' </div>' +\n ' <div class=\"mb-3\">' +\n ' <label class=\"form-label\">Caption</label>' +\n ' <input type=\"text\" class=\"te-table-props-caption form-control\" placeholder=\"Optional caption\">' +\n ' </div>' +\n ' </div>' +\n ' <div class=\"te-modal-footer\">' +\n ' <button type=\"button\" class=\"btn btn-outline-secondary\" data-te-close>Cancel</button>' +\n ' <button type=\"submit\" class=\"btn btn-primary\">Apply</button>' +\n ' </div>' +\n ' </form>' +\n ' </div>' +\n '</div>',\n init(ctx: PluginContext): void {\n if(!ctx.features.table) return;\n\n var popup = document.createElement('div');\n popup.className = 'te-table-grid';\n popup.style.display = 'none';\n popup.innerHTML = '' +\n '<div class=\"te-tg-header\">' +\n '<span class=\"te-tg-label\">0 × 0</span>' +\n '<button type=\"button\" class=\"btn-close te-tg-close\" aria-label=\"Close\"></button>' +\n '</div>' +\n '<div class=\"te-tg-cells\" style=\"grid-template-columns: repeat(' + MAX_COLS + ', 18px);\"></div>';\n var cellsContainer = popup.querySelector('.te-tg-cells') as HTMLElement;\n var label = popup.querySelector('.te-tg-label') as HTMLElement;\n\n for(var r = 0; r < MAX_ROWS; r++){\n for(var c = 0; c < MAX_COLS; c++){\n var cell = document.createElement('div');\n cell.className = 'te-tg-cell';\n cell.setAttribute('data-r', r.toString());\n cell.setAttribute('data-c', c.toString());\n cellsContainer.appendChild(cell);\n }\n }\n\n function clearActive(){\n popup.querySelectorAll('.te-tg-cell.active').forEach(function(el){ el.classList.remove('active'); });\n }\n\n function highlight(r: number, c: number){\n clearActive();\n popup.querySelectorAll('.te-tg-cell').forEach(function(el){\n var er = parseInt(el.getAttribute('data-r')!, 10);\n var ec = parseInt(el.getAttribute('data-c')!, 10);\n if(er <= r && ec <= c) el.classList.add('active');\n });\n label.textContent = (c + 1) + ' × ' + (r + 1);\n }\n\n cellsContainer.addEventListener('mouseover', function(e: MouseEvent){\n var cell = (e.target as HTMLElement).closest('.te-tg-cell');\n if(!cell) return;\n var r = parseInt(cell.getAttribute('data-r')!, 10);\n var c = parseInt(cell.getAttribute('data-c')!, 10);\n highlight(r, c);\n });\n\n cellsContainer.addEventListener('mouseleave', function(){\n clearActive();\n label.textContent = '0 × 0';\n });\n\n function insertTable(cols: number, rows: number){\n ctx.restoreSel();\n var html = '<table class=\"te-table\"><tbody>';\n for(var rr = 0; rr < rows; rr++){\n html += '<tr>';\n for(var cc = 0; cc < cols; cc++){\n html += '<td><br></td>';\n }\n html += '</tr>';\n }\n html += '</tbody></table>';\n document.execCommand('insertHTML', false, html);\n }\n\n cellsContainer.addEventListener('click', function(e: MouseEvent){\n var cell = (e.target as HTMLElement).closest('.te-tg-cell');\n if(!cell) return;\n var cols = parseInt(cell.getAttribute('data-c')!, 10) + 1;\n var rows = parseInt(cell.getAttribute('data-r')!, 10) + 1;\n popup.style.display = 'none';\n insertTable(cols, rows);\n ctx.editor.focus();\n });\n\n document.body.appendChild(popup);\n\n (popup.querySelector('.te-tg-close') as HTMLElement).addEventListener('click', function(){\n popup.style.display = 'none';\n });\n\n var btn = ctx.wrapper.querySelector('[data-cmd=\"insertTable\"]') as HTMLElement | null;\n if(btn){\n btn.addEventListener('click', function(e: MouseEvent){\n e.stopPropagation();\n ctx.saveSel();\n var rect = btn!.getBoundingClientRect();\n popup.style.left = (window.scrollX + rect.left) + 'px';\n popup.style.top = (window.scrollY + rect.bottom + 4) + 'px';\n popup.style.display = popup.style.display === 'none' ? 'block' : 'none';\n });\n }\n\n document.addEventListener('click', function(e: MouseEvent){\n if(popup.style.display === 'none') return;\n if(!popup.contains(e.target as Node) && e.target !== btn){\n popup.style.display = 'none';\n }\n });\n }\n};\n\nexport default table;\n","import type { Plugin, PluginContext, TeEditorElement } from '../types';\n\nconst tableTools: Plugin = {\n name: 'tableTools',\n order: 55,\n deps: ['table'],\n css: '' +\n '.te-table-tools {' +\n ' position: absolute; display: none; z-index: 2000;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .375rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .2rem .3rem; gap: .1rem; align-items: center;' +\n ' white-space: nowrap;' +\n '}' +\n '.te-table-tools .btn {' +\n ' padding: .15rem .35rem !important; font-size: .7rem !important; line-height: 1 !important;' +\n '}' +\n '.te-table-tools .btn svg {' +\n ' width: 12px !important; height: 12px !important;' +\n ' margin-right: 2px; vertical-align: middle;' +\n '}' +\n '.te-table-tools .te-divider-v {' +\n ' display: inline-block; width: 1px; height: 16px;' +\n ' background: #dee2e6; margin: 0 .2rem;' +\n '}' +\n '.te-table-tools .tt-label {' +\n ' font-size: .6rem; color: #6c757d; text-transform: uppercase;' +\n ' letter-spacing: .5px; margin: 0 .15rem;' +\n '}' +\n '.te-table-tools .te-bg-input {' +\n ' width: 26px !important; height: 20px !important;' +\n ' padding: 1px !important; border: 1px solid #dee2e6;' +\n ' border-radius: 3px; cursor: pointer;' +\n '}' +\n '.te-cell-selected {' +\n ' outline: 2px solid #0d6efd !important;' +\n ' outline-offset: -1px;' +\n '}',\n init(ctx: PluginContext): void {\n if(!ctx.features.table || !ctx.features.tableTools) return;\n\n var wrapper = ctx.wrapper;\n var editor = ctx.editor;\n var ed = ctx.editor as TeEditorElement;\n var tools = document.createElement('div');\n tools.className = 'te-table-tools';\n tools.style.display = 'none';\n tools.innerHTML = '' +\n '<span class=\"tt-label\">Add</span>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-table=\"row-before\" title=\"Row above\"><i class=\"ti ti-chevron-up\"></i> Row</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-table=\"row-after\" title=\"Row below\"><i class=\"ti ti-chevron-down\"></i> Row</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-table=\"col-before\" title=\"Column before\"><i class=\"ti ti-chevron-left\"></i> Col</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-table=\"col-after\" title=\"Column after\"><i class=\"ti ti-chevron-right\"></i> Col</button>' +\n '<span class=\"te-divider-v\"></span>' +\n '<span class=\"tt-label\">Del</span>' +\n '<button type=\"button\" class=\"btn btn-sm btn-outline-danger\" data-te-table=\"del-row\" title=\"Delete row\"><i class=\"ti ti-x\"></i> Row</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-outline-danger\" data-te-table=\"del-col\" title=\"Delete column\"><i class=\"ti ti-x\"></i> Col</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-outline-danger\" data-te-table=\"del-table\" title=\"Delete table\"><i class=\"ti ti-trash\"></i> Tbl</button>' +\n '<span class=\"te-divider-v\"></span>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-table=\"merge\" title=\"Merge selected cells\"><i class=\"ti ti-maximize\"></i> Merge</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-table=\"unmerge\" title=\"Unmerge cells\" style=\"display:none\"><i class=\"ti ti-minimize\"></i> Unmerge</button>' +\n '<span class=\"te-divider-v\"></span>' +\n '<button type=\"button\" class=\"btn btn-sm btn-outline-secondary\" data-te-table=\"toggle-header\" title=\"Toggle header\"><i class=\"ti ti-typography\"></i> Hdr</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-outline-secondary\" data-te-table=\"toggle-caption\" title=\"Toggle caption\"><i class=\"ti ti-align-left\"></i> Cap</button>' +\n '<span class=\"te-divider-v\"></span>' +\n '<span class=\"tt-label\">BG</span>' +\n '<input type=\"color\" class=\"te-bg-input form-control form-control-color\" value=\"#ffffff\" title=\"Cell background color\" />' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-table=\"bg-apply\" title=\"Apply background color\">Apply</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-table=\"bg-clear\" title=\"Remove background color\">Clear</button>' +\n '<span class=\"te-divider-v\"></span>' +\n '<span class=\"tt-label\">V</span>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-table=\"valign-top\" title=\"Align top\">Top</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-table=\"valign-middle\" title=\"Align middle\">Mid</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-table=\"valign-bottom\" title=\"Align bottom\">Bot</button>';\n document.body.appendChild(tools);\n\n var currentCell: HTMLElement | null = null, currentTable: HTMLElement | null = null;\n var lastCell: HTMLElement | null = null, lastTable: HTMLElement | null = null;\n var selectedCells: HTMLElement[] = [];\n\n function saveHist(){\n if(!ed._tableHist) ed._tableHist = {undo:[], redo:[]};\n ed._tableHist.undo.push(editor.innerHTML);\n ed._tableHist.redo = [];\n if(ed._tableHist.undo.length > 50) ed._tableHist.undo.shift();\n }\n\n function updateMergeBtn(){\n var btn = tools.querySelector('[data-te-table=\"merge\"]') as HTMLElement | null;\n if(!btn) return;\n btn.style.display = (selectedCells.length >= 2) ? '' : 'none';\n }\n\n function clearHighlights(){\n selectedCells.forEach(function(c){ c.classList.remove('te-cell-selected'); });\n selectedCells = [];\n updateMergeBtn();\n }\n\n function toggleHighlight(cell: HTMLElement){\n var idx = selectedCells.indexOf(cell);\n if(idx !== -1){\n selectedCells.splice(idx, 1);\n cell.classList.remove('te-cell-selected');\n } else {\n selectedCells.push(cell);\n cell.classList.add('te-cell-selected');\n }\n updateMergeBtn();\n }\n\n editor.addEventListener('click', function(e: MouseEvent){\n var cell = (e.target as HTMLElement).closest && (e.target as HTMLElement).closest('td,th') as HTMLElement | null;\n if(!cell || !editor.contains(cell)) return;\n if(e.ctrlKey || e.metaKey){\n e.preventDefault();\n toggleHighlight(cell);\n } else if(!e.shiftKey){\n clearHighlights();\n }\n });\n\n function updateUnmergeBtn(cell: HTMLElement){\n var btn = tools.querySelector('[data-te-table=\"unmerge\"]') as HTMLElement | null;\n if(!btn) return;\n var cs = parseInt(cell.getAttribute('colspan')!, 10) || 1;\n var rs = parseInt(cell.getAttribute('rowspan')!, 10) || 1;\n btn.style.display = (cs > 1 || rs > 1) ? '' : 'none';\n }\n\n function updateValignBtns(cell: HTMLElement){\n tools.querySelectorAll('[data-te-table^=\"valign-\"]').forEach(function(b){\n var align = b.getAttribute('data-te-table')!.replace('valign-', '');\n var cellAlign = ((cell as HTMLElement).style.verticalAlign || '').toLowerCase();\n b.classList.toggle('active', cellAlign === align);\n });\n }\n\n function posTools(cell: HTMLElement){\n var rect = cell.getBoundingClientRect();\n tools.style.display = 'flex';\n tools.style.visibility = 'hidden';\n var toolsW = tools.offsetWidth;\n var toolsH = tools.offsetHeight;\n var editorRect = editor.getBoundingClientRect();\n var sx = window.scrollX, sy = window.scrollY;\n\n var leftPos = rect.left + sx;\n var minLeft = editorRect.left + sx + 2;\n var maxLeft = editorRect.right + sx - toolsW - 2;\n if(leftPos < minLeft) leftPos = minLeft;\n if(leftPos > maxLeft) leftPos = maxLeft;\n tools.style.left = leftPos + 'px';\n\n var spaceBelow = editorRect.bottom - (rect.bottom + 6);\n var spaceAbove = rect.top - 6 - editorRect.top;\n var topPos;\n if(spaceBelow >= toolsH || spaceBelow >= spaceAbove){\n topPos = rect.bottom + 6 + sy;\n } else {\n topPos = rect.top - 6 - toolsH + sy;\n }\n var minTop = editorRect.top + sy + 2;\n var maxTop = editorRect.bottom + sy - toolsH - 2;\n if(topPos < minTop) topPos = minTop;\n if(topPos > maxTop) topPos = maxTop;\n tools.style.top = topPos + 'px';\n\n tools.style.visibility = '';\n updateMergeBtn();\n updateUnmergeBtn(cell);\n updateValignBtns(cell);\n var capBtn = tools.querySelector('[data-te-table=\"toggle-caption\"]') as HTMLElement | null;\n if(capBtn && currentTable) capBtn.classList.toggle('active', !!currentTable.querySelector('caption'));\n }\n function hideTools(){\n tools.style.display = 'none';\n currentCell = null;\n currentTable = null;\n }\n function updateFromSelection(){\n var sel = window.getSelection();\n if(!sel || sel.rangeCount === 0){ hideTools(); return; }\n var n: Node | null = sel.anchorNode;\n if(n && n.nodeType === 3) n = n.parentNode;\n if(!n || !wrapper.contains(n)){ hideTools(); return; }\n var cell = (n as HTMLElement).closest && (n as HTMLElement).closest('td,th') as HTMLElement | null;\n if(cell && editor.contains(cell)){\n currentCell = cell;\n currentTable = cell.closest('table') as HTMLElement | null;\n lastCell = currentCell;\n lastTable = currentTable;\n posTools(cell);\n } else {\n hideTools();\n }\n }\n\n function getSelectedCellsForTools(): HTMLElement[] | null {\n var h = tools.querySelectorAll('.te-cell-selected');\n if(h.length) return Array.prototype.slice.call(h);\n var s = window.getSelection();\n if(!s || s.rangeCount === 0) return null;\n var r = s.getRangeAt(0);\n var tbl = currentTable || lastTable;\n if(!tbl) return null;\n var cells: HTMLElement[] = [];\n tbl.querySelectorAll('td,th').forEach(function(c){\n if(r.intersectsNode(c)) cells.push(c as HTMLElement);\n });\n return cells.length ? cells : null;\n }\n\n function applyBgColor(value: string){\n var cells = getSelectedCellsForTools();\n if(!cells) return;\n for(var i = 0; i < cells.length; i++){\n cells[i].style.backgroundColor = value;\n }\n }\n\n function clearBgColor(){\n var cells = getSelectedCellsForTools();\n if(!cells) return;\n for(var i = 0; i < cells.length; i++){\n cells[i].style.backgroundColor = '';\n }\n }\n\n var bgInput = tools.querySelector('.te-bg-input') as HTMLInputElement | null;\n if(bgInput){\n bgInput.addEventListener('change', function(){\n if(currentCell || lastCell) applyBgColor(bgInput!.value);\n });\n }\n\n document.addEventListener('selectionchange', updateFromSelection);\n window.addEventListener('scroll', function(){ if(currentCell) posTools(currentCell!); });\n window.addEventListener('resize', function(){ if(currentCell) posTools(currentCell!); });\n\n function getCellIndex(cell: HTMLElement){\n var idx = 0, node: HTMLElement | null = cell;\n while(node && node.previousElementSibling){ idx++; node = node.previousElementSibling as HTMLElement; }\n return idx;\n }\n function forEachRow(table: HTMLElement, cb: (row: HTMLTableRowElement, sec: string) => void){\n ['thead','tbody'].forEach(function(sec){\n var s = table.querySelector(sec);\n if(s){\n Array.prototype.forEach.call((s as HTMLTableSectionElement).rows, function(row){ cb(row, sec); });\n }\n });\n }\n\n var refocus: ReturnType<typeof setTimeout> | null;\n\n function scheduleRefocus(){\n if(refocus) clearTimeout(refocus);\n refocus = setTimeout(function(){\n ctx.editor.focus();\n updateFromSelection();\n refocus = null;\n }, 0);\n }\n\n function mergeCells(){\n var table = currentTable || lastTable;\n if(!table) return;\n var rows = Array.prototype.slice.call(table.querySelectorAll('tr')) as HTMLTableRowElement[];\n if(!rows.length) return;\n\n var cells: HTMLElement[];\n if(selectedCells.length > 1){\n cells = selectedCells.slice();\n } else {\n var sel = window.getSelection();\n if(!sel || sel.rangeCount === 0) return;\n var range = sel.getRangeAt(0);\n cells = [];\n table.querySelectorAll('td,th').forEach(function(cell){\n if(range.intersectsNode(cell)) cells.push(cell as HTMLElement);\n });\n }\n if(cells.length < 2) return;\n saveHist();\n\n var positions = cells.map(function(cell){\n return {\n cell: cell,\n row: rows.indexOf(cell.parentElement as HTMLTableRowElement),\n col: getCellIndex(cell)\n };\n });\n\n var minRow = Math.min.apply(null, positions.map(function(p){ return p.row; }));\n var maxRow = Math.max.apply(null, positions.map(function(p){ return p.row; }));\n var minCol = Math.min.apply(null, positions.map(function(p){ return p.col; }));\n var maxCol = Math.max.apply(null, positions.map(function(p){ return p.col; }));\n\n if(minRow !== maxRow && minCol !== maxCol){\n var mergeBtn = tools.querySelector('[data-te-table=\"merge\"]') as HTMLElement | null;\n if(mergeBtn){\n mergeBtn.style.outline = '2px solid #dc3545';\n mergeBtn.style.outlineOffset = '1px';\n setTimeout(function(){ mergeBtn!.style.outline = ''; mergeBtn!.style.outlineOffset = ''; }, 600);\n }\n return;\n }\n\n var contents = cells.map(function(c){ return c.innerHTML; });\n var kept = positions.filter(function(p){ return p.row === minRow && p.col === minCol; })[0];\n if(!kept) kept = positions[0];\n\n cells.forEach(function(cell){\n if(cell !== kept.cell) cell.parentNode!.removeChild(cell);\n });\n\n kept.cell.setAttribute('colspan', String(maxCol - minCol + 1));\n kept.cell.setAttribute('rowspan', String(maxRow - minRow + 1));\n kept.cell.innerHTML = contents.join('');\n clearHighlights();\n }\n\n function unmergeCell(cell: HTMLElement){\n var colspan = parseInt(cell.getAttribute('colspan')!, 10) || 1;\n var rowspan = parseInt(cell.getAttribute('rowspan')!, 10) || 1;\n if(colspan === 1 && rowspan === 1) return;\n\n var tag = cell.tagName;\n var table = cell.closest('table') as HTMLElement;\n var rows = Array.prototype.slice.call(table.querySelectorAll('tr')) as HTMLTableRowElement[];\n var row = cell.parentElement as HTMLTableRowElement;\n var rowIdx = rows.indexOf(row);\n var colIdx = getCellIndex(cell);\n\n cell.removeAttribute('colspan');\n cell.removeAttribute('rowspan');\n cell.innerHTML = '<br>';\n\n var ref = cell.nextSibling;\n for(var c = 1; c < colspan; c++){\n var nc = document.createElement(tag);\n nc.innerHTML = '<br>';\n row.insertBefore(nc, ref);\n }\n\n for(var r = 1; r < rowspan; r++){\n var tr = rows[rowIdx + r];\n if(!tr) break;\n var insBefore = tr.cells[colIdx] || null;\n for(var c = 0; c < colspan; c++){\n var nc = document.createElement(tag);\n nc.innerHTML = '<br>';\n tr.insertBefore(nc, insBefore);\n }\n }\n }\n\n tools.addEventListener('mousedown', function(e: MouseEvent){\n var actionBtn = e.target && (e.target as HTMLElement).closest('[data-te-table]');\n var action = actionBtn && (actionBtn as HTMLElement).getAttribute('data-te-table');\n if(!action) return;\n e.preventDefault();\n var cell = currentCell || lastCell;\n var table = currentTable || lastTable;\n if(!cell || !table) return;\n saveHist();\n var row = cell.parentElement as HTMLTableRowElement;\n var colIdx = getCellIndex(cell);\n\n if(action === 'row-before' || action === 'row-after'){\n var newRow = row.cloneNode(true) as HTMLTableRowElement;\n Array.prototype.forEach.call(newRow.cells, function(td: HTMLTableCellElement){\n td.innerHTML = '<br>';\n td.removeAttribute('colspan');\n td.removeAttribute('rowspan');\n });\n if(action === 'row-before'){ row.parentNode!.insertBefore(newRow, row); }\n else { row.parentNode!.insertBefore(newRow, row.nextSibling); }\n scheduleRefocus();\n }\n else if(action === 'col-before' || action === 'col-after'){\n var after = (action === 'col-after');\n forEachRow(table, function(r, sec){\n var ref = r.cells[colIdx];\n var newCell = document.createElement((sec === 'thead') ? 'th' : 'td');\n newCell.innerHTML = '<br>';\n if(after && ref && ref.nextSibling){ r.insertBefore(newCell, ref.nextSibling); }\n else if(ref){ r.insertBefore(newCell, ref); }\n else { r.appendChild(newCell); }\n });\n scheduleRefocus();\n }\n else if(action === 'del-row'){\n row.parentNode!.removeChild(row);\n if(!table.querySelector('tr')){ table.parentNode!.removeChild(table); hideTools(); }\n else { scheduleRefocus(); }\n }\n else if(action === 'del-col'){\n forEachRow(table, function(r){ if(r.cells[colIdx]) r.deleteCell(colIdx); });\n var any = table.querySelector('tr') as HTMLTableRowElement | null;\n if(any && any.cells.length === 0){ table.parentNode!.removeChild(table); hideTools(); }\n else { scheduleRefocus(); }\n }\n else if(action === 'del-table'){ table.parentNode!.removeChild(table); hideTools(); }\n else if(action === 'bg-apply'){ applyBgColor(bgInput ? bgInput.value : '#ffffff'); scheduleRefocus(); }\n else if(action === 'bg-clear'){ clearBgColor(); scheduleRefocus(); }\n else if(action === 'valign-top' || action === 'valign-middle' || action === 'valign-bottom'){\n var cells = getSelectedCellsForTools();\n if(!cells || !cells.length) cells = [cell];\n var vAlign = action.replace('valign-', '');\n for(var vi = 0; vi < cells.length; vi++){ cells[vi].style.verticalAlign = vAlign; }\n scheduleRefocus();\n }\n else if(action === 'merge'){ mergeCells(); scheduleRefocus(); }\n else if(action === 'unmerge'){ unmergeCell(cell); scheduleRefocus(); }\n else if(action === 'toggle-header'){\n var thead = table.querySelector('thead') as HTMLTableSectionElement | null;\n if(thead){\n var tbody = table.querySelector('tbody') as HTMLTableSectionElement | null || (function(){\n var tb = document.createElement('tbody');\n table.appendChild(tb);\n return tb;\n })();\n Array.prototype.slice.call(thead.rows).forEach(function(hr: HTMLTableRowElement){\n var tr = document.createElement('tr');\n Array.prototype.forEach.call(hr.cells, function(hc: HTMLTableCellElement){\n var td = document.createElement('td');\n td.innerHTML = hc.innerHTML || '<br>';\n tr.appendChild(td);\n });\n tbody.insertBefore(tr, tbody.firstChild);\n });\n thead.parentNode!.removeChild(thead);\n } else {\n var tb = table.querySelector('tbody') as HTMLTableSectionElement | null;\n if(tb && tb.rows.length){\n var first = tb.rows[0];\n var newHead = document.createElement('thead');\n var trh = document.createElement('tr');\n Array.prototype.forEach.call(first.cells, function(td: HTMLTableCellElement){\n var th = document.createElement('th');\n th.innerHTML = td.innerHTML || '<br>';\n trh.appendChild(th);\n });\n newHead.appendChild(trh);\n table.insertBefore(newHead, tb);\n tb.removeChild(first);\n }\n }\n scheduleRefocus();\n }\n else if(action === 'toggle-caption'){\n var cap = table.querySelector('caption');\n if(cap){\n cap.parentNode!.removeChild(cap);\n } else {\n var caption = document.createElement('caption');\n caption.innerHTML = '<br>';\n caption.contentEditable = 'true';\n caption.style.captionSide = 'bottom';\n caption.style.textAlign = 'left';\n caption.style.padding = '4px 6px';\n caption.style.fontStyle = 'italic';\n caption.style.color = '#6c757d';\n table.insertBefore(caption, table.firstChild);\n setTimeout(function(){ caption.focus(); }, 0);\n }\n scheduleRefocus();\n }\n });\n },\n};\n\nexport default tableTools;\n","import type { Plugin, PluginContext } from '../types';\n\nconst hr: Plugin = {\n name: 'hr',\n order: 55,\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Horizontal rule\" data-cmd=\"insertHR\"><i class=\"ti ti-minus\"></i></button>',\n css: '' +\n '.te-hr-popup {' +\n ' position: fixed; display: none; z-index: 3000;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .375rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .5rem; white-space: nowrap;' +\n '}' +\n '.te-hr-popup .btn {' +\n ' padding: .15rem .4rem !important; font-size: 1rem !important; line-height: 1 !important;' +\n ' margin-right: 2px;' +\n '}' +\n '.te-hr-popup .btn.active { background: #e7f1ff; border-color: #b6d4fe; }' +\n '.te-hr-popup input[type=\"color\"] {' +\n ' width: 26px; height: 22px; padding: 1px; border: 1px solid #dee2e6;' +\n ' border-radius: 3px; cursor: pointer; vertical-align: middle;' +\n '}',\n init(ctx: PluginContext): void {\n if(!ctx.features.hr) return;\n var btn = ctx.wrapper.querySelector('[data-cmd=\"insertHR\"]');\n if(!btn) return;\n\n var popup = document.createElement('div');\n popup.className = 'te-hr-popup';\n popup.innerHTML = '' +\n '<button type=\"button\" class=\"btn btn-sm btn-light active\" data-te-hr=\"solid\" title=\"Solid\">━</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-hr=\"dashed\" title=\"Dashed\">┅</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-hr=\"dotted\" title=\"Dotted\">┈</button>' +\n '<input type=\"color\" class=\"te-hr-color\" value=\"#cccccc\" title=\"HR color\" />';\n document.body.appendChild(popup);\n\n var currentStyle = 'solid';\n var currentColor = '#cccccc';\n var savedRange: Range | null = null;\n\n function saveEditorRange(): void{\n var sel = window.getSelection();\n if(sel && sel.rangeCount > 0) savedRange = sel.getRangeAt(0).cloneRange();\n else savedRange = null;\n }\n\n function restoreEditorRange(): void{\n if(!savedRange) return;\n var sel = window.getSelection();\n sel!.removeAllRanges();\n sel!.addRange(savedRange);\n }\n\n function posPopup(): void{\n var br = (btn as HTMLElement).getBoundingClientRect();\n var pw = popup.offsetWidth || 200;\n var left = br.left + (br.width / 2) - (pw / 2);\n if(left < 4) left = 4;\n if(left + pw > window.innerWidth - 4) left = window.innerWidth - pw - 4;\n popup.style.left = left + 'px';\n popup.style.top = (br.bottom + 4) + 'px';\n }\n\n function insertHR(): void{\n ctx.editor.focus();\n restoreEditorRange();\n var style = 'border: none; border-top: 2px ' + currentStyle + ' ' + currentColor + '; margin: 1em 0;';\n document.execCommand('insertHTML', false, '<hr style=\"' + style + '\">');\n hidePopup();\n }\n\n function hidePopup(): void{ popup.style.display = 'none'; }\n function showPopup(): void{\n saveEditorRange();\n popup.style.display = 'block';\n posPopup();\n }\n\n btn.addEventListener('click', function(e: Event){\n (e as MouseEvent).preventDefault();\n (e as MouseEvent).stopPropagation();\n if(popup.style.display === 'block'){ hidePopup(); return; }\n showPopup();\n });\n\n popup.addEventListener('mousedown', function(e: MouseEvent){\n var opt = (e.target as HTMLElement).closest('[data-te-hr]');\n if(opt){\n e.preventDefault();\n currentStyle = opt.getAttribute('data-te-hr')!;\n popup.querySelectorAll('[data-te-hr]').forEach(function(b){ b.classList.remove('active'); });\n opt.classList.add('active');\n insertHR();\n return;\n }\n });\n\n popup.addEventListener('change', function(e: Event){\n var inp = (e.target as HTMLElement).closest('.te-hr-color');\n if(inp){\n currentColor = (inp as HTMLInputElement).value;\n insertHR();\n }\n });\n\n document.addEventListener('click', function(e: MouseEvent){\n if(popup.style.display !== 'block') return;\n if(!popup.contains(e.target as Node) && e.target !== btn && !(btn as HTMLElement).contains(e.target as Node)){\n hidePopup();\n }\n });\n\n window.addEventListener('scroll', function(){ if(popup.style.display === 'block') posPopup(); });\n window.addEventListener('resize', function(){ if(popup.style.display === 'block') posPopup(); });\n }\n};\n\nexport default hr;\n","import type { Plugin, PluginContext } from '../types';\n\nconst unlink: Plugin = {\n name: 'unlink',\n order: 58,\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Remove link\" data-cmd=\"unlink\"><i class=\"ti ti-x\"></i></button>',\n init(ctx: PluginContext): void {\n if(!ctx.features.unlink) return;\n var btn = ctx.wrapper.querySelector('[data-cmd=\"unlink\"]');\n if(!btn) return;\n btn.addEventListener('click', function(){\n var sel = window.getSelection();\n if(!sel || sel.rangeCount === 0) return;\n var node: Node | null = sel.anchorNode;\n if(node && node.nodeType === 3) node = node.parentNode;\n var link = node && (node as HTMLElement).closest && (node as HTMLElement).closest('a') as HTMLAnchorElement | null;\n if(link){\n var parent = link.parentNode!;\n while(link.firstChild){ parent.insertBefore(link.firstChild, link); }\n parent.removeChild(link);\n } else {\n document.execCommand('unlink', false, undefined);\n }\n ctx.editor.focus();\n });\n }\n};\n\nexport default unlink;\n","import type { Plugin, PluginContext } from '../types';\n\nvar EMOJIS = '😀😃😄😁😆😅🤣😂🙂🙃😉😊😇🥰😍🤩😘😗😚😋😛😜🤪😝🤑🤗🤭🤫🤔🤐🤨😐😑😶😏😒🙄😬🤥😌😔😪🤤😴😷🤒🤕🤢🤮🤧🥵🥶🥴😵🤯🤠🥳🥸😎🤓🧐😕😟🙁😮😯😲😳🥺😦😧😨😰😥😢😭😱😖😣😞😓😩😫🥱😤😡😠🤬😈👿💀☠💩🤡👹👺👻👽👾🤖💋👋✋👌🤏🤞🤟🤘🤙👈👉👆🖕👍👎✊👊🤛🤜👏🙌👐🤲🤝🙏✍💅👂👃👣👀👅👄'.match(/.{1,2}/g) || [];\n\nvar EMOJI_NAMES: Record<string, string> = {\n '😀':'grinning laugh happy','😃':'grinning smile happy','😄':'grinning smile happy','😁':'beaming grin happy',\n '😆':'laughing grinning','🤣':'rolling floor laughing','😂':'tears joy laughing cry',\n '🙂':'slight smile','🙃':'upside down','😉':'winking wink',\n '😊':'blush smile happy','😇':'innocent halo angel',\n '🥰':'love heart smile','😍':'heart eyes love','🤩':'star struck',\n '😘':'kiss blowing heart','😗':'kissing kiss','😚':'kiss closed eyes',\n '😋':'savor tongue yum','😛':'tongue playful','😜':'wink tongue silly','🤪':'crazy wild','😝':'squint tongue',\n '🤑':'money tongue rich',\n '🤗':'hug open hands','🤭':'hand over mouth secret','🤫':'shush quiet silent',\n '🤔':'thinking think','🤐':'zipper mouth secret','🤨':'raised eyebrow suspicious',\n '😐':'neutral straight face','😑':'expressionless blank','😶':'no mouth silent',\n '😏':'smirk smug','😒':'unamified roll','🙄':'eye roll',\n '😬':'grimace awkward','🤥':'lying liar nose',\n '😌':'relieved relief','😔':'pensive sad','😪':'sleepy tired','🤤':'drooling drool','😴':'sleeping sleep zzz',\n '😷':'medical mask sick','🤒':'thermometer sick fever','🤕':'head bandage hurt',\n '🤢':'nauseous sick vomit','🤮':'vomiting sick','🤧':'sneeze sick',\n '🥵':'hot fever sweat','🥶':'cold freeze ice','🥴':'dizzy tipsy',\n '😵':'dizzy confused','🤯':'exploding head mind blown',\n '🤠':'cowboy hat','🥳':'party celebration','🥸':'disguise mask',\n '😎':'sunglasses cool','🤓':'nerd geek glasses','🧐':'monocle detective',\n '😕':'confused unsure','😟':'worried concern','🙁':'slight frown sad',\n '😮':'surprised shock','😯':'hushed surprise','😲':'astonished amazed','😳':'flushed embarrassed',\n '🥺':'pleading puppy eyes',\n '😦':'frown sad','😧':'anguish distressed','😨':'fearful afraid','😰':'anxious sweat worry',\n '😥':'disappointed sad','😢':'cry sad tear','😭':'sobbing cry tears',\n '😱':'scream fear horror','😖':'confounded frustrated','😣':'persevere struggle',\n '😞':'disappointed sad','😓':'downcast sweat','😩':'weary tired','😫':'tired exhausted','🥱':'yawn sleepy',\n '😤':'triumph frustrated steam','😡':'angry rage','😠':'angry mad','🤬':'cursing swear',\n '😈':'devil evil grin','👿':'devil evil angry','💀':'skull death','☠':'skull crossbones danger',\n '💩':'poop poo','🤡':'clown circus','👹':'ogre monster','👺':'goblin monster',\n '👻':'ghost halloween','👽':'alien ufo','👾':'alien monster space','🤖':'robot ai',\n '💋':'kiss lips',\n '👋':'wave hand hello bye','✋':'raised hand stop high five','👌':'ok perfect',\n '🤏':'pinching small little','🤞':'crossed fingers luck','🤟':'love gesture',\n '🤘':'horns rock metal','🤙':'call me phone',\n '👈':'point left','👉':'point right','👆':'point up','🖕':'middle finger fuck',\n '👍':'thumbs up like','👎':'thumbs down dislike',\n '✊':'fist raised power','👊':'fist punch','🤛':'fist left','🤜':'fist right',\n '👏':'clap applause','🙌':'raised hands celebration','👐':'open hands',\n '🤲':'palms together pray','🤝':'handshake deal agree','🙏':'folded hands pray please thank',\n '✍':'writing hand','💅':'nail polish care',\n '👂':'ear listen','👃':'nose smell','👣':'footsteps feet','👀':'eyes look','👅':'tongue taste','👄':'mouth lips'\n};\n\nconst emoji: Plugin = {\n name: 'emoji',\n order: 60,\n css: '' +\n '.te-emoji-popup {' +\n ' position: absolute; z-index: 3000;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .5rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .4rem; max-width: 290px;' +\n '}' +\n '.te-emoji-popup .te-emoji-search {' +\n ' width: 100%; box-sizing: border-box;' +\n ' padding: .3rem .5rem; margin-bottom: .4rem;' +\n ' border: 1px solid #dee2e6; border-radius: .375rem;' +\n ' font-size: .8rem; outline: none;' +\n '}' +\n '.te-emoji-popup .te-emoji-search:focus {' +\n ' border-color: #86b7fe; box-shadow: 0 0 0 2px rgba(13,110,253,.15);' +\n '}' +\n '.te-emoji-popup .te-emoji-no-result {' +\n ' padding: 1rem; text-align: center; color: #6c757d; font-size: .8rem;' +\n '}' +\n '.te-emoji-popup .te-emoji-grid {' +\n ' display: grid; grid-template-columns: repeat(8, 1fr); gap: 2px;' +\n ' max-height: 220px; overflow-y: auto;' +\n '}' +\n '.te-emoji-popup .te-emoji-grid button {' +\n ' background: none; border: none; font-size: 1.3rem;' +\n ' padding: .25rem; cursor: pointer; border-radius: .25rem; text-align: center;' +\n '}' +\n '.te-emoji-popup .te-emoji-grid button:hover { background: #f0f0f0; }' +\n '.te-emoji-popup .te-emoji-grid button.hidden { display: none; }',\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Emoji\" data-cmd=\"emoji\"><i class=\"ti ti-mood-smile\"></i></button>',\n init(ctx: PluginContext): void {\n if(!ctx.features.emoji) return;\n\n var popup = document.createElement('div');\n popup.className = 'te-emoji-popup';\n popup.style.display = 'none';\n popup.innerHTML = '<input type=\"text\" class=\"te-emoji-search\" placeholder=\"Search emoji...\" /><div class=\"te-emoji-grid\"></div><div class=\"te-emoji-no-result\" style=\"display:none\">No emoji found</div>';\n var grid = popup.querySelector('.te-emoji-grid') as HTMLElement;\n var search = popup.querySelector('.te-emoji-search') as HTMLInputElement;\n var noResult = popup.querySelector('.te-emoji-no-result') as HTMLElement;\n\n EMOJIS.forEach(function(emoji){\n var btn = document.createElement('button');\n btn.type = 'button';\n btn.textContent = emoji;\n btn.setAttribute('data-emoji', emoji);\n btn.title = EMOJI_NAMES[emoji] || '';\n grid.appendChild(btn);\n });\n document.body.appendChild(popup);\n\n var toolbarBtn = ctx.wrapper.querySelector('[data-cmd=\"emoji\"]') as HTMLElement | null;\n var savedRange: Range | null = null;\n\n function saveEditorRange(){\n var sel = window.getSelection();\n if(sel && sel.rangeCount > 0) savedRange = sel.getRangeAt(0).cloneRange();\n else savedRange = null;\n }\n\n function restoreEditorRange(){\n if(!savedRange) return;\n var sel = window.getSelection();\n sel!.removeAllRanges();\n sel!.addRange(savedRange);\n }\n\n function showPopup(){\n saveEditorRange();\n var rect = toolbarBtn!.getBoundingClientRect();\n popup.style.display = 'block';\n popup.style.visibility = 'hidden';\n var pw = popup.offsetWidth, ph = popup.offsetHeight;\n var sx = window.scrollX, sy = window.scrollY;\n var vw = window.innerWidth, vh = window.innerHeight;\n\n var left = rect.left + sx;\n if(left + pw > sx + vw - 8) left = sx + vw - pw - 8;\n if(left < sx + 4) left = sx + 4;\n popup.style.left = left + 'px';\n\n var top = rect.bottom + 4 + sy;\n if(top + ph > sy + vh - 8) top = rect.top - ph - 4 + sy;\n if(top < sy + 4) top = sy + 4;\n popup.style.top = top + 'px';\n\n popup.style.visibility = '';\n search.value = '';\n grid.querySelectorAll('button').forEach(function(b){ b.classList.remove('hidden'); });\n noResult.style.display = 'none';\n search.focus();\n }\n\n if(toolbarBtn){\n toolbarBtn.addEventListener('click', function(e: MouseEvent){\n if(popup.style.display !== 'none'){ popup.style.display = 'none'; return; }\n showPopup();\n });\n }\n\n search.addEventListener('input', function(){\n var q = search.value.trim().toLowerCase();\n var visible = 0;\n grid.querySelectorAll('button').forEach(function(b){\n var name = (EMOJI_NAMES[(b as HTMLButtonElement).textContent!] || '').toLowerCase();\n var match = !q || name.indexOf(q) !== -1;\n b.classList.toggle('hidden', !match);\n if(match) visible++;\n });\n noResult.style.display = visible ? 'none' : 'block';\n });\n\n search.addEventListener('keydown', function(e: KeyboardEvent){\n if(e.key === 'Escape'){ popup.style.display = 'none'; ctx.editor.focus(); }\n });\n\n popup.addEventListener('mousedown', function(e: MouseEvent){\n var btn = (e.target as HTMLElement).closest && (e.target as HTMLElement).closest('[data-emoji]');\n if(!btn) return;\n e.preventDefault();\n ctx.editor.focus();\n restoreEditorRange();\n document.execCommand('insertHTML', false, (btn as HTMLElement).textContent!);\n popup.style.display = 'none';\n });\n\n document.addEventListener('click', function(e: MouseEvent){\n if(popup.style.display === 'none') return;\n if(!popup.contains(e.target as Node) && e.target !== toolbarBtn){\n popup.style.display = 'none';\n }\n });\n }\n};\n\nexport default emoji;\n","import type { Plugin, PluginContext } from '../types';\n\nconst direction: Plugin = {\n name: 'direction',\n order: 61,\n toolbarHTML: '' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Left to Right\" data-cmd=\"ltr\"><i class=\"ti ti-arrow-left\"></i> LTR</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Right to Left\" data-cmd=\"rtl\">RTL <i class=\"ti ti-arrow-right\"></i></button>',\n init(ctx: PluginContext): void {\n if (!ctx.features.direction) return;\n ctx.wrapper.querySelectorAll('[data-cmd=\"ltr\"],[data-cmd=\"rtl\"]').forEach(function (btn) {\n btn.addEventListener('click', function () {\n var dir = btn.getAttribute('data-cmd');\n document.execCommand('formatBlock', false, 'p');\n var sel = window.getSelection();\n if (sel && sel.rangeCount > 0) {\n var node: Node | null = sel.anchorNode;\n if (node && node.nodeType === 3) node = node.parentNode;\n var block = node && (node as Element).closest && (node as Element).closest('p,h1,h2,h3,h4,h5,h6,div');\n if (block && ctx.wrapper.contains(block)) {\n block.setAttribute('dir', dir!);\n }\n }\n ctx.editor.focus();\n });\n });\n }\n};\n\nexport default direction;\n","import type { Plugin, PluginContext } from '../types';\n\nconst source: Plugin = {\n name: 'source',\n order: 65,\n css: '' +\n '.te-source-toggle.active { background: #e7f1ff; border-color: #b6d4fe; }' +\n '.te-editor.te-source-mode { display: none; }' +\n '.te-source-textarea {' +\n ' width: 100%; min-height: 200px; border: 1px solid #dee2e6;' +\n ' border-radius: .375rem; padding: .75rem; resize: vertical;' +\n ' font-family: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, monospace;' +\n ' font-size: .85rem; line-height: 1.6; display: none;' +\n '}',\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-outline-secondary\" title=\"Toggle source\" data-cmd=\"editSource\"><i class=\"ti ti-source-code\"></i></button>',\n init(ctx: PluginContext): void {\n if(!ctx.features.source) return;\n\n var btn = ctx.wrapper.querySelector('[data-cmd=\"editSource\"]') as HTMLButtonElement | null;\n if(!btn) return;\n\n var ta = document.createElement('textarea');\n ta.className = 'te-source-textarea';\n ta.spellcheck = false;\n ctx.editor.parentNode!.insertBefore(ta, ctx.editor);\n\n var sourceMode = false;\n\n function formatSource(html: string): string {\n if(!html) return '';\n var out = String(html);\n var blockTags = ['p','h1','h2','h3','h4','h5','h6','blockquote','pre','li','tr','thead','tbody','tfoot','table','ul','ol'];\n blockTags.forEach(function(tag){\n var openRe = new RegExp('<' + tag + '(\\\\s[^>]*)?>', 'gi');\n var closeRe = new RegExp('</' + tag + '>', 'gi');\n out = out.replace(openRe, function(m){ return '\\n' + m; });\n out = out.replace(closeRe, function(m){ return m + '\\n'; });\n });\n out = out.replace(/\\n{2,}/g, '\\n');\n return out.trim();\n }\n\n function toggleSource(){\n sourceMode = !sourceMode;\n if(sourceMode){\n ta.value = formatSource(ctx.editor.innerHTML);\n ctx.editor.classList.add('te-source-mode');\n ta.style.display = 'block';\n ta.focus();\n } else {\n var safe = ctx.utils.sanitizeHTML ? ctx.utils.sanitizeHTML(ta.value, ctx.options.sanitize || {}) : ta.value;\n ctx.editor.innerHTML = safe;\n ctx.editor.classList.remove('te-source-mode');\n ta.style.display = 'none';\n ctx.editor.focus();\n }\n btn!.classList.toggle('active', sourceMode);\n var allControls = ctx.toolbar.querySelectorAll('[data-cmd], select, input');\n for(var i = 0; i < allControls.length; i++){\n if(allControls[i] === btn) continue;\n if(sourceMode){\n (allControls[i] as HTMLElement).setAttribute('disabled', 'disabled');\n (allControls[i] as HTMLElement).style.opacity = '.4';\n (allControls[i] as HTMLElement).style.pointerEvents = 'none';\n } else {\n (allControls[i] as HTMLElement).removeAttribute('disabled');\n (allControls[i] as HTMLElement).style.opacity = '';\n (allControls[i] as HTMLElement).style.pointerEvents = '';\n }\n }\n }\n\n btn.addEventListener('click', toggleSource);\n }\n};\n\nexport default source;\n","import type { Plugin, PluginContext } from '../types';\n\nconst history: Plugin = {\n name: 'history',\n order: 70,\n toolbarHTML: '' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Undo\" data-cmd=\"undo\"><i class=\"ti ti-arrow-back-up\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Redo\" data-cmd=\"redo\"><i class=\"ti ti-arrow-forward-up\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Clear formatting\" data-cmd=\"removeFormat\"><i class=\"ti ti-trash\"></i></button>',\n init(ctx: PluginContext): void {\n },\n};\n\nexport default history;\n","import type { Plugin, PluginContext } from '../types';\n\nconst fullscreen: Plugin = {\n name: 'fullscreen',\n order: 75,\n css: '' +\n '.te-fullscreen {' +\n ' position: fixed; inset: 0; z-index: 9999;' +\n '}' +\n '.te-fullscreen .te-container {' +\n ' max-width: none; display: flex; flex-direction: column; height: 100%;' +\n '}' +\n '.te-fullscreen .te-container .te-editor {' +\n ' flex: 1; height: auto !important; min-height: 300px;' +\n '}' +\n '.te-fullscreen .te-container .te-toolbar {' +\n ' border-radius: 0;' +\n '}' +\n '.te-fullscreen .te-btn-fullscreen {' +\n ' background: #e7f1ff; border-color: #b6d4fe;' +\n '}',\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light te-btn-fullscreen\" title=\"Fullscreen\" data-cmd=\"fullscreen\"><i class=\"ti ti-maximize\"></i></button>',\n init(ctx: PluginContext): void {\n if (!ctx.features.fullscreen) return;\n var btn = ctx.wrapper.querySelector('[data-cmd=\"fullscreen\"]') as HTMLElement | null;\n if (!btn) return;\n btn.addEventListener('click', function () {\n var isFull = ctx.wrapper.classList.toggle('te-fullscreen');\n btn!.innerHTML = isFull ? '<i class=\"ti ti-minimize\"></i>' : '<i class=\"ti ti-maximize\"></i>';\n\n ctx.editor.focus();\n });\n }\n};\n\nexport default fullscreen;\n","import type { Plugin, PluginContext } from '../types';\n\nconst toolbarCollapse: Plugin = {\n name: 'toolbarCollapse',\n order: 1000,\n css: '' +\n '.te-toolbar .btn svg, .te-toolbar .btn i {' +\n ' width: 14px !important; height: 14px !important;' +\n ' vertical-align: middle;' +\n '}',\n init(ctx: PluginContext): void {}\n};\n\nexport default toolbarCollapse;\n","import type { Plugin, PluginContext } from '../types';\n\nvar STORAGE_PREFIX = 'te-autosave-';\n\nfunction getStorageKey(textarea: HTMLTextAreaElement): string {\n var id = textarea.id || textarea.name || textarea.className || '';\n return STORAGE_PREFIX + (id || Math.random().toString(36).slice(2, 8));\n}\n\nconst autosave: Plugin = {\n name: 'autosave',\n order: 210,\n css: '' +\n '.te-autosave-badge {' +\n ' font-size: .7rem; padding: 1px 6px; border-radius: 8px;' +\n ' line-height: 1.4; opacity: .6; margin-left: auto;' +\n '}' +\n '.te-autosave-badge.saved { background: #d1e7dd; color: #0f5132; }' +\n '.te-autosave-badge.unsaved { background: #fff3cd; color: #664d03; }',\n init(ctx: PluginContext): void {\n if(!ctx.features.autosave) return;\n\n var key = getStorageKey(ctx.textarea);\n\n try {\n var saved = localStorage.getItem(key);\n if(saved && saved !== ctx.editor.innerHTML){\n ctx.editor.innerHTML = saved;\n }\n } catch(_){}\n\n var badge = document.createElement('span');\n badge.className = 'te-autosave-badge saved';\n badge.textContent = 'Saved';\n var rightEl = ctx.wrapper.querySelector('.te-status-right') as HTMLElement | null;\n if(rightEl){\n rightEl.style.display = 'inline-flex';\n rightEl.style.alignItems = 'center';\n rightEl.style.gap = '8px';\n rightEl.appendChild(badge);\n }\n\n function setStatus(saved: boolean): void {\n badge.textContent = saved ? 'Saved' : 'Unsaved';\n badge.className = 'te-autosave-badge ' + (saved ? 'saved' : 'unsaved');\n }\n\n var saveTimer: ReturnType<typeof setTimeout> | null = null;\n function save(): void {\n setStatus(false);\n if(saveTimer) clearTimeout(saveTimer);\n saveTimer = setTimeout(function(){\n try {\n localStorage.setItem(key, ctx.editor.innerHTML);\n setStatus(true);\n } catch(_){}\n }, 500);\n }\n\n ctx.editor.addEventListener('input', save);\n ctx.editor.addEventListener('paste', save);\n\n ctx.editor.addEventListener('blur', function(){\n try { localStorage.removeItem(key); } catch(_){}\n });\n }\n};\n\nexport default autosave;\n","import type { Plugin, PluginContext } from '../types';\n\nvar URL_RE = /(?:https?:\\/\\/|www\\.)[^\\s<>\"'()]+(?:\\.[^\\s<>\"'()]+)*/gi;\n\nconst autoLinkify: Plugin = {\n name: 'autoLinkify',\n order: 1,\n init(ctx: PluginContext): void {\n if (ctx.features.autoLinkify === false) return;\n var editor = ctx.editor;\n\n editor.addEventListener('paste', function (e: ClipboardEvent) {\n var text = (e.clipboardData && e.clipboardData.getData('text/plain')) || '';\n if (!text) return;\n\n text = text.trim();\n\n if (URL_RE.test(text)) {\n URL_RE.lastIndex = 0;\n var url = text.match(URL_RE)![0];\n var fullUrl = url.indexOf('://') === -1 ? 'https://' + url : url;\n var isOk = ctx.utils.isSafeUrl ? ctx.utils.isSafeUrl(fullUrl, ctx.options.urlSchemes || ['http', 'https', 'mailto', 'tel']) : true;\n if (isOk) {\n e.preventDefault();\n e.stopImmediatePropagation();\n var html = '<p><a href=\"' + fullUrl.replace(/\"/g, '"') + '\" target=\"_blank\" rel=\"noopener noreferrer\">' + url.replace(/</g, '<').replace(/>/g, '>') + '</a></p>';\n document.execCommand('insertHTML', false, html);\n }\n }\n }, true);\n }\n};\n\nexport default autoLinkify;\n","import type { Plugin, PluginContext } from '../types';\n\nconst caseTransform: Plugin = {\n name: 'caseTransform',\n order: 31,\n toolbarHTML: '' +\n '<select class=\"te-case form-select form-select-sm\" title=\"Change case\">' +\n ' <option value=\"\">Case</option>' +\n ' <option value=\"upper\">UPPERCASE</option>' +\n ' <option value=\"lower\">lowercase</option>' +\n ' <option value=\"title\">Title Case</option>' +\n ' <option value=\"sentence\">Sentence case</option>' +\n '</select>',\n init(ctx: PluginContext): void {\n if(ctx.features.caseTransform === false) return;\n var sel = ctx.wrapper.querySelector('.te-case') as HTMLSelectElement | null;\n if(!sel) return;\n\n sel.addEventListener('mousedown', function(){\n ctx.saveSel();\n });\n\n sel.addEventListener('change', function(){\n var v = sel!.value;\n sel!.value = '';\n if(!v) return;\n\n ctx.restoreSel();\n\n var s = window.getSelection();\n if(!s || s.isCollapsed || !s.rangeCount) return;\n var text = s.toString();\n if(!text) return;\n\n var transformed: string;\n switch(v){\n case 'upper': transformed = text.toUpperCase(); break;\n case 'lower': transformed = text.toLowerCase(); break;\n case 'title':\n transformed = text.toLowerCase().replace(/\\b\\w/g, function(m){ return m.toUpperCase(); });\n break;\n case 'sentence':\n transformed = text.charAt(0).toUpperCase() + text.slice(1).toLowerCase().replace(/([.!?]\\s+)(\\w)/g, function(m){ return m.toUpperCase(); });\n break;\n default: return;\n }\n\n document.execCommand('insertText', false, transformed);\n ctx.editor.focus();\n });\n }\n};\n\nexport default caseTransform;\n","import type { Plugin, PluginContext } from '../types';\n\nconst shortcutsHelp: Plugin = {\n name: 'shortcutsHelp',\n order: 90,\n css: '' +\n '.te-shortcuts-table { width: 100%; border-collapse: collapse; font-size: .875rem; }' +\n '.te-shortcuts-table th, .te-shortcuts-table td { padding: .4rem .75rem; border-bottom: 1px solid #e9ecef; text-align: left; color: #000; }' +\n '.te-shortcuts-table th { background: #f8f9fa; font-weight: 600; }' +\n '.te-shortcuts-table kbd { display: inline-block; padding: 2px 6px; font-size: .75rem; font-family: monospace; background: #f0f0f0; border: 1px solid #d0d0d0; border-radius: 3px; color: #000; }',\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Keyboard shortcuts\" data-cmd=\"shortcutsHelp\"><i class=\"ti ti-help-circle\"></i></button>',\n modalHTML: '' +\n '<div class=\"te-shortcuts-modal te-modal\" aria-hidden=\"true\">' +\n ' <div class=\"te-modal-backdrop\" data-te-close></div>' +\n ' <div class=\"te-modal-dialog\">' +\n ' <div class=\"te-modal-header\">' +\n ' <h5 class=\"te-modal-title m-0\">Keyboard Shortcuts</h5>' +\n ' <button type=\"button\" class=\"btn-close\" data-te-close aria-label=\"Close\"></button>' +\n ' </div>' +\n ' <div class=\"te-modal-body\">' +\n ' <table class=\"te-shortcuts-table\">' +\n ' <thead><tr><th>Shortcut</th><th>Action</th></tr></thead>' +\n ' <tbody>' +\n ' <tr><td><kbd>Ctrl</kbd> + <kbd>B</kbd></td><td>Bold</td></tr>' +\n ' <tr><td><kbd>Ctrl</kbd> + <kbd>I</kbd></td><td>Italic</td></tr>' +\n ' <tr><td><kbd>Ctrl</kbd> + <kbd>U</kbd></td><td>Underline</td></tr>' +\n ' <tr><td><kbd>Ctrl</kbd> + <kbd>S</kbd></td><td>Strikethrough</td></tr>' +\n ' <tr><td><kbd>Ctrl</kbd> + <kbd>Z</kbd></td><td>Undo</td></tr>' +\n ' <tr><td><kbd>Ctrl</kbd> + <kbd>Shift</kbd> + <kbd>Z</kbd></td><td>Redo</td></tr>' +\n ' <tr><td><kbd>Ctrl</kbd> + <kbd>Y</kbd></td><td>Redo</td></tr>' +\n ' <tr><td><kbd>Ctrl</kbd> + <kbd>K</kbd></td><td>Insert link</td></tr>' +\n ' <tr><td><kbd>Tab</kbd></td><td>Indent list item</td></tr>' +\n ' <tr><td><kbd>Shift</kbd> + <kbd>Tab</kbd></td><td>Outdent list item</td></tr>' +\n ' </tbody>' +\n ' </table>' +\n ' </div>' +\n ' </div>' +\n '</div>',\n init(ctx: PluginContext): void {\n if(ctx.features.shortcutsHelp === false) return;\n var btn = ctx.wrapper.querySelector('[data-cmd=\"shortcutsHelp\"]');\n if(btn){\n btn.addEventListener('click', function(){\n var m = ctx.wrapper.querySelector('.te-shortcuts-modal');\n if(m) m.classList.add('is-open');\n });\n }\n }\n};\n\nexport default shortcutsHelp;\n","import type { Plugin, PluginContext } from '../types';\n\nconst floatingToolbar: Plugin = {\n name: 'floatingToolbar',\n order: 58,\n css: '' +\n '.te-float-toolbar {' +\n ' position: fixed; display: none; z-index: 3100;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .375rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .2rem; gap: 2px; align-items: center;' +\n ' white-space: nowrap;' +\n '}' +\n '.te-float-toolbar .btn {' +\n ' padding: .2rem .4rem !important; font-size: .75rem !important; line-height: 1 !important;' +\n '}' +\n '.te-float-toolbar .btn i,' +\n '.te-float-toolbar .btn svg {' +\n ' width: 13px !important; height: 13px !important;' +\n ' pointer-events: none;' +\n '}' +\n '.te-float-link-input {' +\n ' position: fixed; display: none; z-index: 3101;' +\n ' background: #fff; border: 1px solid #dee2e6;' +\n ' border-radius: .375rem; box-shadow: 0 6px 20px rgba(0,0,0,.15);' +\n ' padding: .35rem; gap: .25rem; align-items: center;' +\n ' white-space: nowrap;' +\n '}' +\n '.te-float-link-input input {' +\n ' width: 220px; padding: .2rem .4rem; font-size: .8rem;' +\n ' border: 1px solid #dee2e6; border-radius: .25rem; outline: none;' +\n '}' +\n '.te-float-link-input input:focus {' +\n ' border-color: #86b7fe; box-shadow: 0 0 0 2px rgba(13,110,253,.15);' +\n '}' +\n '.te-float-link-input .btn {' +\n ' padding: .2rem .5rem !important; font-size: .75rem !important; line-height: 1 !important;' +\n '}',\n init(ctx: PluginContext): void {\n if(!ctx.features.floatingToolbar) return;\n\n var editor = ctx.editor;\n var tools = document.createElement('div');\n tools.className = 'te-float-toolbar';\n tools.innerHTML = '' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-float=\"bold\" title=\"Bold\"><i class=\"ti ti-bold\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-float=\"italic\" title=\"Italic\"><i class=\"ti ti-italic\"></i></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-float=\"underline\" title=\"Underline\"><i class=\"ti ti-underline\"></i></button>' +\n '<span class=\"te-divider-v\" style=\"display:inline-block;width:1px;height:14px;background:#dee2e6;margin:0 2px;vertical-align:middle\"></span>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light te-float-fore\" title=\"Text color\" style=\"position:relative;padding:.15rem .35rem!important;min-width:22px;text-align:center\"><span class=\"te-float-cp\" style=\"display:block;font-size:.8rem;line-height:1\">A<span style=\"display:block;height:2px;border-radius:1px;margin-top:1px;background:#000\"></span></span><input type=\"color\" class=\"te-float-fore-input\" value=\"#000000\" style=\"position:absolute;top:0;left:0;width:100%;height:100%;opacity:0;cursor:pointer;border:none;padding:0\"></button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light te-float-back\" title=\"Background color\" style=\"position:relative;padding:.15rem .35rem!important;min-width:22px;text-align:center\"><span class=\"te-float-cp\" style=\"display:block;font-size:.8rem;line-height:1\">A<span style=\"display:block;height:2px;border-radius:1px;margin-top:1px;background:#ffff00\"></span></span><input type=\"color\" class=\"te-float-back-input\" value=\"#ffff00\" style=\"position:absolute;top:0;left:0;width:100%;height:100%;opacity:0;cursor:pointer;border:none;padding:0\"></button>' +\n '<span class=\"te-divider-v\" style=\"display:inline-block;width:1px;height:14px;background:#dee2e6;margin:0 2px;vertical-align:middle\"></span>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-float=\"link\" title=\"Insert link\"><i class=\"ti ti-link\"></i></button>' +\n '<span class=\"te-divider-v\" style=\"display:inline-block;width:1px;height:14px;background:#dee2e6;margin:0 2px;vertical-align:middle\"></span>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-float=\"removeFormat\" title=\"Clear formatting\"><i class=\"ti ti-clear-formatting\"></i></button>';\n document.body.appendChild(tools);\n\n var linkInput = document.createElement('div');\n linkInput.className = 'te-float-link-input';\n linkInput.innerHTML = '' +\n '<input type=\"url\" class=\"te-float-link-url\" placeholder=\"https://example.com\" />' +\n '<button type=\"button\" class=\"btn btn-sm btn-primary\" data-te-float-link=\"apply\">Apply</button>' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\" data-te-float-link=\"cancel\">Cancel</button>';\n document.body.appendChild(linkInput);\n\n var foreInput = tools.querySelector('.te-float-fore-input') as HTMLInputElement | null;\n var backInput = tools.querySelector('.te-float-back-input') as HTMLInputElement | null;\n\n if(foreInput){\n foreInput.addEventListener('change', function(){\n editor.focus();\n restoreRange();\n document.execCommand('foreColor', false, (foreInput as HTMLInputElement).value);\n var preview = tools.querySelector('.te-float-fore .te-float-cp') as HTMLElement | null;\n if(preview) preview.style.color = (foreInput as HTMLInputElement).value;\n hideTools();\n });\n }\n\n if(backInput){\n backInput.addEventListener('change', function(){\n editor.focus();\n restoreRange();\n try{ document.execCommand('hiliteColor', false, (backInput as HTMLInputElement).value); }\n catch(e){ document.execCommand('backColor', false, (backInput as HTMLInputElement).value); }\n var bar = tools.querySelector('.te-float-back .te-float-cp span:last-child') as HTMLElement | null;\n if(bar) bar.style.background = (backInput as HTMLInputElement).value;\n hideTools();\n });\n }\n\n var hideTimer: ReturnType<typeof setTimeout> | null = null;\n var isVisible = false;\n var savedRange: Range | null = null;\n\n function saveRange(){\n var sel = window.getSelection();\n if(sel && sel.rangeCount > 0) savedRange = sel.getRangeAt(0).cloneRange();\n else savedRange = null;\n }\n\n function restoreRange(){\n if(!savedRange) return;\n var sel = window.getSelection()!;\n sel.removeAllRanges();\n sel.addRange(savedRange);\n }\n\n function posTools(x: number, y: number, rect: DOMRect | null){\n var tw = tools.offsetWidth || 100;\n var th = tools.offsetHeight || 30;\n var er = editor.getBoundingClientRect();\n var left = x - tw / 2;\n if(left < er.left) left = er.left;\n if(left + tw > er.right) left = er.right - tw;\n var spaceAbove = rect ? rect.top - er.top : y - er.top;\n var spaceBelow = rect ? er.bottom - rect.bottom : er.bottom - y;\n var top;\n if(spaceAbove >= th + 8){\n top = (rect ? rect.top : y) - th - 8;\n } else if(spaceBelow >= th + 8){\n top = (rect ? rect.bottom : y) + 8;\n } else {\n top = spaceAbove > spaceBelow ? er.top + 2 : er.bottom - th - 2;\n }\n tools.style.left = left + 'px';\n tools.style.top = top + 'px';\n }\n\n function hideTools(){\n isVisible = false;\n linkInput.style.display = 'none';\n tools.style.display = 'none';\n }\n\n function showTools(x: number, y: number, rect: DOMRect | null){\n isVisible = true;\n tools.style.display = 'flex';\n posTools(x, y, rect);\n saveRange();\n }\n\n function showLinkInput(){\n saveRange();\n var er = editor.getBoundingClientRect();\n var toolsRect = tools.getBoundingClientRect();\n linkInput.style.display = 'flex';\n linkInput.style.visibility = 'hidden';\n var liw = linkInput.offsetWidth || 320;\n var lih = linkInput.offsetHeight || 32;\n var left = toolsRect.left + toolsRect.width / 2 - liw / 2;\n if(left < er.left) left = er.left;\n if(left + liw > er.right) left = er.right - liw;\n linkInput.style.left = left + 'px';\n var spaceBelow = window.innerHeight - toolsRect.bottom;\n linkInput.style.top = ((spaceBelow >= lih + 4) ? (toolsRect.bottom + 4) : (toolsRect.top - lih - 4)) + 'px';\n linkInput.style.visibility = '';\n (linkInput.querySelector('.te-float-link-url') as HTMLInputElement).value = '';\n (linkInput.querySelector('.te-float-link-url') as HTMLInputElement).focus();\n }\n\n editor.addEventListener('mouseup', function(e: MouseEvent){\n if(editor.contentEditable !== 'true') return;\n if(hideTimer) clearTimeout(hideTimer);\n var sel = window.getSelection();\n if(!sel || sel.isCollapsed || !sel.toString().trim()){\n hideTools();\n return;\n }\n if(!editor.contains(sel.anchorNode) || !editor.contains(sel.focusNode)){\n hideTools();\n return;\n }\n var range = sel.getRangeAt(0);\n var rect = range.getBoundingClientRect();\n var x = rect.left + rect.width / 2;\n showTools(x, 0, rect);\n });\n\n editor.addEventListener('mousedown', function(){\n if(hideTimer) clearTimeout(hideTimer);\n hideTimer = setTimeout(function(){ hideTools(); }, 200);\n });\n\n editor.addEventListener('keydown', function(){\n hideTools();\n });\n\n editor.addEventListener('scroll', function(){\n if(isVisible) hideTools();\n });\n\n tools.addEventListener('mousedown', function(e: MouseEvent){\n e.preventDefault();\n var actionBtn = (e.target as HTMLElement).closest('[data-te-float]');\n if(!actionBtn) return;\n var action = actionBtn.getAttribute('data-te-float');\n if(!action) return;\n\n if(action === 'link'){\n showLinkInput();\n return;\n }\n\n editor.focus();\n var sel = window.getSelection();\n if(!sel || sel.rangeCount === 0) return;\n document.execCommand(action, false, undefined);\n hideTools();\n });\n\n linkInput.addEventListener('mousedown', function(e: MouseEvent){\n e.preventDefault();\n var actionBtn = (e.target as HTMLElement).closest('[data-te-float-link]');\n if(!actionBtn) return;\n var action = actionBtn.getAttribute('data-te-float-link');\n\n if(action === 'cancel'){\n hideTools();\n return;\n }\n\n if(action === 'apply'){\n var url = (linkInput.querySelector('.te-float-link-url') as HTMLInputElement).value.trim();\n if(!url) return;\n editor.focus();\n restoreRange();\n if (!/^https?:\\/\\//i.test(url) && !/^mailto:/i.test(url) && !/^tel:/i.test(url)) url = 'https://' + url;\n document.execCommand('createLink', false, url);\n hideTools();\n }\n });\n\n linkInput.addEventListener('keydown', function(e: KeyboardEvent){\n if(e.key === 'Enter'){\n e.preventDefault();\n var url = (linkInput.querySelector('.te-float-link-url') as HTMLInputElement).value.trim();\n if(!url) return;\n editor.focus();\n restoreRange();\n if (!/^https?:\\/\\//i.test(url) && !/^mailto:/i.test(url) && !/^tel:/i.test(url)) url = 'https://' + url;\n document.execCommand('createLink', false, url);\n hideTools();\n }\n if(e.key === 'Escape'){\n hideTools();\n }\n });\n\n document.addEventListener('mousedown', function(e: MouseEvent){\n if(isVisible && !tools.contains(e.target as Node) && !linkInput.contains(e.target as Node) && e.target !== editor && !editor.contains(e.target as Node)){\n hideTools();\n }\n });\n }\n};\n\nexport default floatingToolbar;\n","import type { Plugin, PluginContext } from '../types';\n\nconst darkMode: Plugin = {\n name: 'darkMode',\n order: 59,\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Toggle dark mode\" data-cmd=\"toggleDark\"><i class=\"ti ti-moon\"></i></button>',\n css: '' +\n '.te-container.te-dark {' +\n ' color-scheme: dark;' +\n '}' +\n '.te-container.te-dark .te-toolbar {' +\n ' background: #1e1e1e; border-color: #444;' +\n '}' +\n '.te-container.te-dark .te-toolbar .btn {' +\n ' color: #ccc; border-color: #555; background: #2a2a2a;' +\n '}' +\n '.te-container.te-dark .te-toolbar .btn:hover {' +\n ' background: #333; color: #fff;' +\n '}' +\n '.te-container.te-dark .te-toolbar .btn.active {' +\n ' background: #0d6efd; color: #fff; border-color: #0d6efd;' +\n '}' +\n '.te-container.te-dark .te-editor {' +\n ' background: #121212; border-color: #444; color: #e0e0e0;' +\n '}' +\n '.te-container.te-dark .te-editor:focus {' +\n ' box-shadow: inset 0 0 0 2px rgba(13,110,253,.5);' +\n '}' +\n '.te-container.te-dark .te-editor[placeholder]:empty:before {' +\n ' color: #666;' +\n '}' +\n '.te-container.te-dark .te-divider {' +\n ' background: #444;' +\n '}' +\n '.te-container.te-dark .te-status {' +\n ' color: #999;' +\n '}' +\n '.te-container.te-dark .te-modal-dialog {' +\n ' background: #1e1e1e; color: #e0e0e0; box-shadow: 0 20px 60px rgba(0,0,0,.5);' +\n '}' +\n '.te-container.te-dark .te-modal-header,' +\n '.te-container.te-dark .te-modal-footer {' +\n ' background: #2a2a2a; border-color: #444;' +\n '}' +\n '.te-container.te-dark .te-modal-header .te-modal-title {' +\n ' color: #e0e0e0;' +\n '}' +\n '.te-container.te-dark .te-modal-body {' +\n ' color: #e0e0e0;' +\n '}' +\n '.te-container.te-dark .btn-close {' +\n ' filter: invert(1);' +\n '}' +\n '.te-container.te-dark .te-modal .btn-primary {' +\n ' background: #555; border-color: #555; color: #fff;' +\n '}' +\n '.te-container.te-dark .te-modal .btn-primary:hover {' +\n ' background: #777; border-color: #777;' +\n '}' +\n '.te-container.te-dark .te-modal .btn-outline-secondary {' +\n ' color: #ccc; border-color: #555;' +\n '}' +\n '.te-container.te-dark .te-modal .btn-outline-secondary:hover {' +\n ' background: #333; border-color: #777;' +\n '}' +\n '.te-container.te-dark .te-modal .btn-outline-danger {' +\n ' color: #e57373; border-color: #e57373;' +\n '}' +\n '.te-container.te-dark .te-modal .btn-outline-danger:hover {' +\n ' background: #C1272D; border-color: #C1272D; color: #fff;' +\n '}' +\n '.te-container.te-dark .form-control {' +\n ' background: #2a2a2a; border-color: #555; color: #e0e0e0;' +\n '}' +\n '.te-container.te-dark .form-select {' +\n ' background: #2a2a2a; border-color: #555; color: #e0e0e0;' +\n '}' +\n '.te-container.te-dark .te-table-tools {' +\n ' background: #1e1e1e; border-color: #444;' +\n '}' +\n '.te-container.te-dark .te-table-tools .btn {' +\n ' color: #ccc; border-color: #555; background: #2a2a2a;' +\n '}' +\n '.te-container.te-dark .te-table-tools .tt-label {' +\n ' color: #999;' +\n '}' +\n '.te-container.te-dark .te-image-tools {' +\n ' background: #1e1e1e; border-color: #444;' +\n '}' +\n '.te-container.te-dark .te-image-tools .btn {' +\n ' color: #ccc; border-color: #555; background: #2a2a2a;' +\n '}' +\n '.te-container.te-dark .te-float-toolbar {' +\n ' background: #1e1e1e; border-color: #444;' +\n '}' +\n '.te-container.te-dark .te-float-toolbar .btn {' +\n ' color: #ccc; border-color: #555; background: #2a2a2a;' +\n '}' +\n '.te-container.te-dark .te-hr-popup {' +\n ' background: #1e1e1e; border-color: #444;' +\n '}' +\n '.te-container.te-dark .te-hr-popup .btn {' +\n ' color: #ccc; border-color: #555; background: #2a2a2a;' +\n '}',\n init(ctx: PluginContext): void {\n if(!ctx.features.darkMode) return;\n var btn = ctx.wrapper.querySelector('[data-cmd=\"toggleDark\"]');\n if(!btn) return;\n\n btn.addEventListener('click', function(){\n var container = ctx.wrapper.querySelector('.te-container');\n if(!container) return;\n var isDark = container.classList.toggle('te-dark');\n var icon = btn!.querySelector('.ti');\n if(icon){\n icon.className = 'ti ' + (isDark ? 'ti-sun' : 'ti-moon');\n }\n (btn as HTMLElement).classList.toggle('active', isDark);\n });\n }\n};\n\nexport default darkMode;\n","import type { Plugin, PluginContext } from '../types';\n\nvar STORAGE_KEY = 'te-shortcut-map';\n\nvar DEFAULT_MAP: Record<string, {key: string; ctrl: boolean; shift: boolean}> = {\n 'Bold': {key:'b', ctrl:true, shift:false},\n 'Italic': {key:'i', ctrl:true, shift:false},\n 'Underline': {key:'u', ctrl:true, shift:false},\n 'Strike': {key:'s', ctrl:true, shift:false},\n 'Undo': {key:'z', ctrl:true, shift:false},\n 'Redo': {key:'z', ctrl:true, shift:true},\n 'RedoAlt': {key:'y', ctrl:true, shift:false},\n 'Link': {key:'k', ctrl:true, shift:false}\n};\n\nfunction loadMap(): Record<string, {key: string; ctrl: boolean; shift: boolean}>{\n try {\n var raw = localStorage.getItem(STORAGE_KEY);\n if(raw) return JSON.parse(raw);\n } catch(_){}\n return JSON.parse(JSON.stringify(DEFAULT_MAP));\n}\n\nfunction saveMap(map: Record<string, {key: string; ctrl: boolean; shift: boolean}>): void{\n try { localStorage.setItem(STORAGE_KEY, JSON.stringify(map)); } catch(_){}\n}\n\nfunction esc(s: string): string{ return String(s).replace(/&/g,'&').replace(/</g,'<').replace(/>/g,'>').replace(/\"/g,'"'); }\n\nconst shortcutCustomizer: Plugin = {\n name: 'shortcutCustomizer',\n order: 6,\n toolbarHTML: '<button type=\"button\" class=\"btn btn-sm btn-light\" title=\"Customize shortcuts\" data-cmd=\"customizeShortcuts\"><i class=\"ti ti-edit\"></i></button>',\n modalHTML: '' +\n '<div class=\"te-modal\" data-te-modal=\"shortcutCustomizer\">' +\n ' <div class=\"te-modal-backdrop\" data-te-close></div>' +\n ' <div class=\"te-modal-dialog\" style=\"width:420px\">' +\n ' <div class=\"te-modal-header\"><strong>Customize Shortcuts</strong><button type=\"button\" class=\"btn-close\" data-te-close></button></div>' +\n ' <div class=\"te-modal-body te-shortcut-body\"></div>' +\n ' <div class=\"te-modal-footer\">' +\n ' <button type=\"button\" class=\"btn btn-sm btn-secondary\" data-te-sc-reset>Reset</button>' +\n ' <button type=\"button\" class=\"btn btn-sm btn-secondary\" data-te-close>Close</button>' +\n ' <button type=\"button\" class=\"btn btn-sm btn-primary\" data-te-shortcut-save>Save</button>' +\n ' </div>' +\n ' </div>' +\n '</div>',\n css: '' +\n '.te-shortcut-body table { width: 100%; border-collapse: collapse; }' +\n '.te-shortcut-body td, .te-shortcut-body th { padding: 4px 8px; border-bottom: 1px solid #dee2e6; text-align: left; font-size: .85rem; }' +\n '.te-shortcut-body th { font-weight: 600; color: #495057; }' +\n '.te-shortcut-body input[type=\"text\"] { width: 40px; padding: 2px 6px; border: 1px solid #dee2e6; border-radius: 3px; font-size: .85rem; }' +\n '.te-shortcut-body input[type=\"text\"]:focus { outline: none; border-color: #86b7fe; box-shadow: 0 0 0 2px rgba(13,110,253,.25); }' +\n '.te-shortcut-body label { font-size: .8rem; margin-left: 4px; }',\n init(ctx: PluginContext): void {\n if(!ctx.features.shortcutCustomizer) return;\n var btn = ctx.wrapper.querySelector('[data-cmd=\"customizeShortcuts\"]');\n if(!btn) return;\n\n btn.addEventListener('click', function(){\n var modal = ctx.wrapper.querySelector('[data-te-modal=\"shortcutCustomizer\"]');\n if(!modal) return;\n var body = modal.querySelector('.te-shortcut-body');\n if(!body) return;\n\n var map = loadMap();\n var names = ['Bold','Italic','Underline','Strike','Undo','Redo','RedoAlt','Link'];\n var html = '<table><tr><th>Action</th><th>Shortcut</th></tr>';\n for(var i = 0; i < names.length; i++){\n var n = names[i];\n var s = map[n] || {key:'', ctrl:true, shift:false};\n var label = n === 'RedoAlt' ? 'Redo (alt)' : n;\n html += '<tr><td>' + label + '</td><td>' +\n 'Ctrl <input type=\"checkbox\" data-ctrl=\"' + n + '\" ' + (s.ctrl ? 'checked' : '') + ' />' +\n ' Shift <input type=\"checkbox\" data-shift=\"' + n + '\" ' + (s.shift ? 'checked' : '') + ' />' +\n ' <input type=\"text\" class=\"te-sc-input\" data-action=\"' + n + '\" value=\"' + esc(s.key) + '\" placeholder=\"key\" maxlength=\"1\" />' +\n '</td></tr>';\n }\n html += '</table>';\n body.innerHTML = html;\n modal.classList.add('is-open');\n });\n\n ctx.wrapper.addEventListener('click', function(e: MouseEvent){\n var saveBtn = (e.target as HTMLElement).closest('[data-te-shortcut-save]');\n if(!saveBtn) return;\n var modal = ctx.wrapper.querySelector('[data-te-modal=\"shortcutCustomizer\"]');\n if(!modal) return;\n var map: Record<string, {key: string; ctrl: boolean; shift: boolean}> = {};\n modal.querySelectorAll('.te-sc-input').forEach(function(inp){\n var action = inp.getAttribute('data-action');\n var key = (inp as HTMLInputElement).value.trim().toLowerCase();\n var ctrl = (modal!.querySelector('[data-ctrl=\"' + action + '\"]') as HTMLInputElement).checked;\n var shift = (modal!.querySelector('[data-shift=\"' + action + '\"]') as HTMLInputElement).checked;\n if(key) map[action!] = {key:key, ctrl:ctrl, shift:shift};\n });\n saveMap(map);\n modal.classList.remove('is-open');\n });\n\n ctx.wrapper.addEventListener('click', function(e: MouseEvent){\n var resetBtn = (e.target as HTMLElement).closest('[data-te-sc-reset]');\n if(!resetBtn) return;\n var modal = ctx.wrapper.querySelector('[data-te-modal=\"shortcutCustomizer\"]');\n if(!modal) return;\n saveMap(JSON.parse(JSON.stringify(DEFAULT_MAP)));\n var body = modal.querySelector('.te-shortcut-body');\n var names = ['Bold','Italic','Underline','Strike','Undo','Redo','RedoAlt','Link'];\n var html = '<table><tr><th>Action</th><th>Shortcut</th></tr>';\n for(var i = 0; i < names.length; i++){\n var n = names[i];\n var s = DEFAULT_MAP[n];\n var label = n === 'RedoAlt' ? 'Redo (alt)' : n;\n html += '<tr><td>' + label + '</td><td>' +\n 'Ctrl <input type=\"checkbox\" data-ctrl=\"' + n + '\" ' + (s.ctrl ? 'checked' : '') + ' />' +\n ' Shift <input type=\"checkbox\" data-shift=\"' + n + '\" ' + (s.shift ? 'checked' : '') + ' />' +\n ' <input type=\"text\" class=\"te-sc-input\" data-action=\"' + n + '\" value=\"' + esc(s.key) + '\" placeholder=\"key\" maxlength=\"1\" />' +\n '</td></tr>';\n }\n html += '</table>';\n if(body) body.innerHTML = html;\n });\n }\n};\n\nexport default shortcutCustomizer;\n","import type { PluginManagerInstance } from '../types';\n\nimport block from './block';\nimport inline from './inline';\nimport pre from './pre';\nimport inlineCode from './inlineCode';\nimport subSuper from './subSuper';\nimport keyboardShortcuts from './keyboardShortcuts';\n\nimport readOnly from './readOnly';\nimport linkTooltip from './linkTooltip';\nimport emojiAutocomplete from './emojiAutocomplete';\nimport statusBar from './statusBar';\nimport codeBlock from './codeBlock';\nimport mediaEmbed from './mediaEmbed';\nimport dragDrop from './dragDrop';\nimport pastePlain from './pastePlain';\nimport findReplace from './findReplace';\nimport indent from './indent';\nimport list from './list';\nimport lineHeight from './lineHeight';\nimport fontSize from './fontSize';\nimport fontFamily from './fontFamily';\nimport specialChars from './specialChars';\nimport colors from './colors';\nimport tableBg from './tableBg';\nimport align from './align';\nimport markdown from './markdown';\nimport link from './link';\nimport image from './image';\nimport imageProps from './imageProps';\nimport imageTools from './imageTools';\nimport iframe from './iframe';\nimport table from './table';\nimport tableTools from './tableTools';\nimport hr from './hr';\nimport unlink from './unlink';\nimport emoji from './emoji';\nimport direction from './direction';\nimport source from './source';\nimport history from './history';\nimport fullscreen from './fullscreen';\nimport toolbarCollapse from './toolbarCollapse';\nimport autosave from './autosave';\nimport autoLinkify from './autoLinkify';\nimport caseTransform from './caseTransform';\nimport shortcutsHelp from './shortcutsHelp';\nimport floatingToolbar from './floatingToolbar';\nimport darkMode from './darkMode';\nimport shortcutCustomizer from './shortcutCustomizer';\n\nexport default function registerDefaultPlugins(pm: PluginManagerInstance): void {\n pm.register('block', block);\n pm.register('inline', inline);\n pm.register('pre', pre);\n pm.register('inlineCode', inlineCode);\n pm.register('subSuper', subSuper);\n pm.register('keyboardShortcuts', keyboardShortcuts);\n\n pm.register('readOnly', readOnly);\n pm.register('linkTooltip', linkTooltip);\n pm.register('emojiAutocomplete', emojiAutocomplete);\n pm.register('statusBar', statusBar);\n pm.register('codeBlock', codeBlock);\n pm.register('mediaEmbed', mediaEmbed);\n pm.register('dragDrop', dragDrop);\n pm.register('pastePlain', pastePlain);\n pm.register('findReplace', findReplace);\n pm.register('indent', indent);\n pm.register('list', list);\n pm.register('lineHeight', lineHeight);\n pm.register('fontSize', fontSize);\n pm.register('fontFamily', fontFamily);\n pm.register('specialChars', specialChars);\n pm.register('colors', colors);\n pm.register('tableBg', tableBg);\n pm.register('align', align);\n pm.register('markdown', markdown);\n pm.register('link', link);\n pm.register('image', image);\n pm.register('imageProps', imageProps);\n pm.register('imageTools', imageTools);\n pm.register('iframe', iframe);\n pm.register('table', table);\n pm.register('tableTools', tableTools);\n pm.register('hr', hr);\n pm.register('unlink', unlink);\n pm.register('emoji', emoji);\n pm.register('direction', direction);\n pm.register('source', source);\n pm.register('history', history);\n pm.register('fullscreen', fullscreen);\n pm.register('toolbarCollapse', toolbarCollapse);\n pm.register('autosave', autosave);\n pm.register('autoLinkify', autoLinkify);\n pm.register('caseTransform', caseTransform);\n pm.register('shortcutsHelp', shortcutsHelp);\n pm.register('floatingToolbar', floatingToolbar);\n pm.register('darkMode', darkMode);\n pm.register('shortcutCustomizer', shortcutCustomizer);\n}\n","import './styles/index.css';\n\nimport PluginManager from './core/PluginManager';\nimport Editor from './core/Editor';\nimport registerDefaultPlugins from './plugins/index';\nimport type {\n EditorOptions,\n EditorInstance,\n BrowseImageHandler,\n TulihEditorStatic,\n} from './types';\n\nconst pm = new PluginManager();\nregisterDefaultPlugins(pm);\npm.injectAllCSS();\n\n// Auto-load the Tabler Icons webfont (used by toolbar buttons) unless it is\n// already present on the page. Tabler Icons is MIT licensed\n// (https://github.com/tabler/tabler-icons). Pinned to the v3 line to avoid\n// unexpected breaking changes from a future major release.\n(function loadTablerIcons(): void {\n if (typeof document === 'undefined') return;\n if (document.querySelector('link[href*=\"tabler-icons\"]')) return;\n const l = document.createElement('link');\n l.rel = 'stylesheet';\n l.href = 'https://cdn.jsdelivr.net/npm/@tabler/icons-webfont@3/dist/tabler-icons.min.css';\n document.head.appendChild(l);\n})();\n\nconst TulihEditor: TulihEditorStatic = {\n pluginManager: pm,\n instances: [],\n onBrowseImage: null,\n onUploadImage: null,\n\n setBrowseImage(handler: BrowseImageHandler): void {\n this.onBrowseImage = handler;\n },\n\n attach(target: string | Element, options?: EditorOptions): EditorInstance | undefined {\n const el = (typeof target === 'string' ? document.querySelector(target) : target) as HTMLElement | null;\n if (!el) return;\n if (String(el.tagName).toUpperCase() !== 'TEXTAREA' && !(el.matches && el.matches('textarea[data-tulih-editor]'))) return;\n const sibling = el.nextElementSibling;\n if (sibling && sibling.querySelector && sibling.querySelector('.te-editor')) return;\n\n return new Editor(el, options, TulihEditor);\n },\n\n create(target: string | Element, options?: EditorOptions): EditorInstance | undefined {\n return this.attach(target, options);\n },\n};\n\nif (typeof document !== 'undefined') {\n document.addEventListener('DOMContentLoaded', () => {\n const allTA = document.querySelectorAll('textarea[data-tulih-editor]');\n allTA.forEach((ta) => { TulihEditor.attach(ta); });\n });\n}\n\n// Expose the classes on the default object for advanced/UMD consumers without\n// adding runtime *named* exports (those would turn the UMD global into\n// `TulihEditor.default`, breaking the documented `<script>` usage).\n(TulihEditor as TulihEditorStatic & { Editor: typeof Editor; PluginManager: typeof PluginManager }).Editor = Editor;\n(TulihEditor as TulihEditorStatic & { Editor: typeof Editor; PluginManager: typeof PluginManager }).PluginManager = PluginManager;\n\nexport default TulihEditor;\nexport type {\n Plugin,\n PluginContext,\n EditorOptions,\n EditorInstance,\n Features,\n SanitizeOptions,\n ResolvedOptions,\n EditorUtils,\n UploadImageHandler,\n BrowseImageHandler,\n TulihEditorStatic,\n PluginManagerInstance,\n HTMLProvider,\n CSSProvider,\n TeHistory,\n TeEditorElement,\n TeWrapperElement,\n} from './types';\n"],"names":["PluginManager","name","plugin","idx","sorted","visited","visiting","map","visit","p","dep","a","b","ctx","features","toolbar","parts","group","i","html","plugins","lastGroup","cssText","style","blockSelector","inlineTags","hasBlockDescendant","el","isInlineElement","tag","wrapNodeInP","node","wrapIframe","wrapper","normalizeParagraphs","root","child","next","ensureInitialParagraph","p0","escapeHtml","str","buildEditorHTML","toolbarHTML","modalHTML","DEFAULT_FEATURES","DEFAULT_SANITIZE","DEFAULT_URL_SCHEMES","DEFAULT_IMAGE_SCHEMES","DEFAULT_IFRAME_ALLOWLIST","DEFAULT_IFRAME_SANDBOX","DEFAULT_IFRAME_ALLOW","Editor","target","options","TulihEditor","isTextarea","hasAttr","sibling","opts","textarea","isMinimal","allOn","k","self","sanitizeHTML","sanOpts","allowedTags","allowedAttrs","container","walker","toUnwrap","comments","attr","aname","isSafeUrl","src","isAllowedIframeUrl","c","url","schemes","u","host","allowed","editorEl","toolbarEl","raw","safeInit","H.normalizeParagraphs","H.ensureInitialParagraph","updateActiveStates","cmd","btn","undoBtn","redoBtn","h","canUndo","canRedo","sel","elNode","inOL","inUL","olBtn","ulBtn","val","clearFrHighlights","m","parent","x","modal","saveSel","s","restoreSel","r","insertImageFile","file","f","cb","cleanWordHtml","out","e","files","pasted","fi","items","ii","imgFile","clipItems","ci","ciTypes","ct","blob","rawHtml","text","toInsert","safe","ro","isRo","instances","myIdx","block","v","inline","pre","inlineCode","txt","H.escapeHtml","subSuper","STORAGE_KEY","DEFAULT_MAP","loadMap","keyboardShortcuts","editor","linkBtn","applyReadOnly","readOnly","linkTooltip","tooltip","hideTimer","hide","href","position","y","EMOJIS","EMOJI_NAMES","emojiAutocomplete","popup","query","activeIdx","buildItems","filter","div","rect","pr","insertEmoji","emoji","range","len","move","dir","active","offset","before","colon","item","statusBar","bar","getActiveTag","n","t","update","hasSel","words","chars","tagEl","rightEl","wEl","cEl","selText","selWords","LANGUAGES","codeBlock","l","lang","cls","EMBED_PROVIDERS","id","mediaEmbed","dragDrop","isImageFile","readFile","reader","handler","pastePlain","findReplace","findInp","replaceInp","countEl","escapeRe","clearHighlights","selectMatch","highlights","currentIdx","doFind","nodes","nodeText","re2","matches","match","span","mid","goNext","goPrev","doFindAndSelect","closePopup","saveUndoState","updateUndoRedoBtns","rbtn","findText","replaceText","re","count","indent","indentBtn","outdentBtn","CLS_RE","OL_STYLES","UL_STYLES","setListStyle","list","findAncestorList","buildOptions","styles","handleSelect","select","execCmd","matched","afterNode","newList","olSel","ulSel","lineHeight","FONT_SIZES","fontSize","FONTS","fontFamily","CHARS","specialChars","ch","colors","foreInput","foreBtn","preview","backInput","backBtn","tableBg","ALIGN_CMDS","getBlockAlignment","cs","ta","align","names","updateActive","RULES","markdown","rule","link","editingLink","linkTools","linkEditPopup","posLinkTools","er","tw","th","left","spaceBelow","top","hideLinkTools","_editPopupTime","hideEditPopup","_from","showEditPopup","pw","ph","openLinkModal","closeLinkModal","fillModal","sub","getSelectedText","actionBtn","action","updateLink","fromTools","form","blank","rel","isOk","relFinal","displayText","closeBtns","image","inputUrl","browseBtn","alt","ok","img","imageProps","altInp","wInp","hInp","clsInp","idInp","styleInp","currentImg","w","idv","safeCss","decl","prop","SAFE","imageTools","currentImage","tools","resizeHandle","getAlign","st","setAlign","clearImageFocus","prev","showResizeHandle","updateAlignBtns","posTools","toolsH","editorRect","below","above","capBtn","brdrBtn","rndBtn","hideTools","dblClick","curBorder","curRadius","fig","figure","caption","resizeData","parentW","currentPct","onResize","onResizeEnd","dx","pctDelta","newPct","iframe","allowOk","attrs","sandbox","allow","MAX_COLS","MAX_ROWS","table","cellsContainer","label","cell","clearActive","highlight","ec","insertTable","cols","rows","rr","cc","tableTools","ed","currentCell","currentTable","lastCell","lastTable","selectedCells","saveHist","updateMergeBtn","toggleHighlight","updateUnmergeBtn","rs","updateValignBtns","cellAlign","toolsW","sx","sy","leftPos","minLeft","maxLeft","spaceAbove","topPos","minTop","maxTop","updateFromSelection","getSelectedCellsForTools","tbl","cells","applyBgColor","value","clearBgColor","bgInput","getCellIndex","forEachRow","sec","row","refocus","scheduleRefocus","mergeCells","positions","minRow","maxRow","minCol","maxCol","mergeBtn","contents","kept","unmergeCell","colspan","rowspan","rowIdx","colIdx","ref","nc","tr","insBefore","newRow","td","after","newCell","any","vAlign","vi","thead","tbody","tb","hr","hc","first","newHead","trh","cap","currentStyle","currentColor","savedRange","saveEditorRange","restoreEditorRange","posPopup","br","insertHR","hidePopup","showPopup","opt","inp","unlink","grid","search","noResult","toolbarBtn","vw","vh","q","visible","direction","source","sourceMode","formatSource","blockTags","openRe","closeRe","toggleSource","allControls","history","fullscreen","isFull","toolbarCollapse","STORAGE_PREFIX","getStorageKey","autosave","key","saved","badge","setStatus","saveTimer","save","URL_RE","autoLinkify","fullUrl","caseTransform","transformed","shortcutsHelp","floatingToolbar","linkInput","restoreRange","isVisible","saveRange","showTools","showLinkInput","toolsRect","liw","lih","darkMode","isDark","icon","saveMap","esc","shortcutCustomizer","body","saveBtn","ctrl","shift","resetBtn","registerDefaultPlugins","pm"],"mappings":"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"}
|