UNPKG

reactjs-tiptap-editor-pro

Version:

A modern WYSIWYG rich text editor based on tiptap and shadcn ui for React

1,534 lines (1,533 loc) 917 kB
import { Y as aa, Z as oa, B as _n, av as Xo, _ as sa, aw as $o, ax as Ct, ay as nn, az as An, aA as Fe, A as Ce, aB as $e, U as Ze, R as Ve, a9 as en, aC as Bo, Q as xi, aD as fi, aE as Et, aF as Pt, X as kn, $ as Fn, a0 as Sn, a1 as Hh, d as nt, aG as Vo, x as jh, aH as gi, aI as yt, W as st, aJ as Xh, aK as Ko, aL as Ne, aM as Zn, a2 as Fd, aN as Lo, aO as $h, aP as Go, P as Fi, q as Si, v as Bi, aQ as Zo, V as Vh, aR as Kh, aa as Gh, aS as jn, aT as Zh, aU as Yh, aV as Qh, aW as Jh, aX as ef, ae as tf, aY as nf, aZ as rf, a_ as af, a$ as Yo, b0 as of, b1 as sf, b2 as cf, b3 as uc, b4 as Sd, b5 as uf, b6 as df, b7 as lf, b8 as hf, ag as ff, b9 as gf, ba as dc, a7 as Oi, bb as pf, bc as mf, bd as xn, an as Mt, E as bf, be as yf, af as Df, bf as Qo, am as lc, L as Na, I as hc, bg as vf, bh as xf, bi as _f, bj as Jt, bk as wf, ah as Tf, as as Uf, bl as Ot, bm as Ef, bn as Af, bo as Cf, bp as kf, bq as Ff, br as Bd } from "./ColorPicker-B3iXkFey.js"; import { n as wy, w as Ty, G as Uy, K as Ey, M as Ay, bs as Cy, z as ky } from "./ColorPicker-B3iXkFey.js"; import { bundledThemes as Ld, bundledLanguages as Nd, createHighlighter as Sf } from "shiki"; import { jsxs as be, jsx as V, Fragment as ca } from "react/jsx-runtime"; import * as Bn from "react"; import Bf, { useMemo as Dt, useState as je, useRef as qt, useCallback as tn, Fragment as Jo, forwardRef as es, useImperativeHandle as ts, useEffect as ot } from "react"; import { M as Lf, D as Rd, u as kt, a as Nf, b as Rf, c as fc, l as Ke, d as Wd, e as Wf } from "./locale-bundle-CT7qZRHF.js"; import { ChevronDown as ns, Check as If, ChevronUp as Of, Copy as Mf, CopyCheck as Pf, SearchIcon as qf, LoaderIcon as zf, LucideTableProperties as Hf, LucideSheet as jf, LucideImage as Xf, LucideFile as $f, LucideVideo as Vf, LucideAudioLines as Kf } from "lucide-react"; import * as Pe from "@radix-ui/react-select"; import { Slot as Gf } from "@radix-ui/react-slot"; import is from "tippy.js"; import rs from "scroll-into-view-if-needed"; import { EmojiPicker as wn } from "frimousse"; import { Packer as Zf, WidthType as Yf } from "docx"; import { DocxSerializer as Qf, defaultNodes as gn, defaultMarks as Jf } from "prosemirror-docx"; const as = Bf.forwardRef( ({ asChild: e, ...t }, n) => { var a; const i = Xo[t.icon]; return /* @__PURE__ */ be(aa, { children: [ /* @__PURE__ */ V(oa, { asChild: !0, children: /* @__PURE__ */ V( e ? Gf : _n, { className: "h-[32px] min-w-24 overflow-hidden px-[5px] py-0", disabled: t == null ? void 0 : t.disabled, ref: n, variant: "ghost", ...t, children: /* @__PURE__ */ be("div", { className: "flex h-full items-center font-normal", children: [ (t == null ? void 0 : t.title) && /* @__PURE__ */ V("div", { className: "grow truncate text-left text-sm", children: t == null ? void 0 : t.title }), i && /* @__PURE__ */ V(i, { className: "ml-1 size-3 shrink-0 text-zinc-500" }) ] }) } ) }), /* @__PURE__ */ V(sa, { children: /* @__PURE__ */ be("div", { className: "flex max-w-24 flex-col items-center text-center", children: [ (t == null ? void 0 : t.tooltip) && /* @__PURE__ */ V("div", { children: t == null ? void 0 : t.tooltip }), /* @__PURE__ */ V("div", { className: "flex", children: !!((a = t == null ? void 0 : t.shortcutKeys) != null && a.length) && /* @__PURE__ */ V("span", { children: $o(t == null ? void 0 : t.shortcutKeys) }) }) ] }) }) ] }); } ), eg = /(?:^|\s)(\*\*(?!\s+\*\*)((?:[^*]+))\*\*(?!\s+\*\*))$/, tg = /(?:^|\s)(\*\*(?!\s+\*\*)((?:[^*]+))\*\*(?!\s+\*\*))/g, ng = /(?:^|\s)(__(?!\s+__)((?:[^_]+))__(?!\s+__))$/, ig = /(?:^|\s)(__(?!\s+__)((?:[^_]+))__(?!\s+__))/g, rg = Ct.create({ name: "bold", addOptions() { return { HTMLAttributes: {} }; }, parseHTML() { return [ { tag: "strong" }, { tag: "b", getAttrs: (e) => e.style.fontWeight !== "normal" && null }, { style: "font-weight=400", clearMark: (e) => e.type.name === this.name }, { style: "font-weight", getAttrs: (e) => /^(bold(er)?|[5-9]\d{2,})$/.test(e) && null } ]; }, renderHTML({ HTMLAttributes: e }) { return ["strong", Fe(this.options.HTMLAttributes, e), 0]; }, addCommands() { return { setBold: () => ({ commands: e }) => e.setMark(this.name), toggleBold: () => ({ commands: e }) => e.toggleMark(this.name), unsetBold: () => ({ commands: e }) => e.unsetMark(this.name) }; }, addKeyboardShortcuts() { return { "Mod-b": () => this.editor.commands.toggleBold(), "Mod-B": () => this.editor.commands.toggleBold() }; }, addInputRules() { return [ An({ find: eg, type: this.type }), An({ find: ng, type: this.type }) ]; }, addPasteRules() { return [ nn({ find: tg, type: this.type }), nn({ find: ig, type: this.type }) ]; } }), qb = rg.extend({ addOptions() { var e; return { ...(e = this.parent) == null ? void 0 : e.call(this), button: ({ editor: t, t: n }) => ({ component: Ce, componentProps: { action: () => t.commands.toggleBold(), isActive: () => t.isActive("bold") || !1, disabled: !t.can().toggleBold(), icon: "Bold", shortcutKeys: ["mod", "B"], tooltip: n("editor.bold.tooltip") } }) }; } }), ag = /(?:^|\s)(\*(?!\s+\*)((?:[^*]+))\*(?!\s+\*))$/, og = /(?:^|\s)(\*(?!\s+\*)((?:[^*]+))\*(?!\s+\*))/g, sg = /(?:^|\s)(_(?!\s+_)((?:[^_]+))_(?!\s+_))$/, cg = /(?:^|\s)(_(?!\s+_)((?:[^_]+))_(?!\s+_))/g, ug = Ct.create({ name: "italic", addOptions() { return { HTMLAttributes: {} }; }, parseHTML() { return [ { tag: "em" }, { tag: "i", getAttrs: (e) => e.style.fontStyle !== "normal" && null }, { style: "font-style=normal", clearMark: (e) => e.type.name === this.name }, { style: "font-style=italic" } ]; }, renderHTML({ HTMLAttributes: e }) { return ["em", Fe(this.options.HTMLAttributes, e), 0]; }, addCommands() { return { setItalic: () => ({ commands: e }) => e.setMark(this.name), toggleItalic: () => ({ commands: e }) => e.toggleMark(this.name), unsetItalic: () => ({ commands: e }) => e.unsetMark(this.name) }; }, addKeyboardShortcuts() { return { "Mod-i": () => this.editor.commands.toggleItalic(), "Mod-I": () => this.editor.commands.toggleItalic() }; }, addInputRules() { return [ An({ find: ag, type: this.type }), An({ find: sg, type: this.type }) ]; }, addPasteRules() { return [ nn({ find: og, type: this.type }), nn({ find: cg, type: this.type }) ]; } }), zb = ug.extend({ addOptions() { var e; return { ...(e = this.parent) == null ? void 0 : e.call(this), button({ editor: t, t: n }) { return { component: Ce, componentProps: { action: () => t.commands.toggleItalic(), isActive: () => t.isActive("italic") || !1, disabled: !t.can().toggleItalic(), shortcutKeys: ["mod", "I"], icon: "Italic", tooltip: n("editor.italic.tooltip") } }; } }; } }), dg = Ct.create({ name: "underline", addOptions() { return { HTMLAttributes: {} }; }, parseHTML() { return [ { tag: "u" }, { style: "text-decoration", consuming: !1, getAttrs: (e) => e.includes("underline") ? {} : !1 } ]; }, renderHTML({ HTMLAttributes: e }) { return ["u", Fe(this.options.HTMLAttributes, e), 0]; }, addCommands() { return { setUnderline: () => ({ commands: e }) => e.setMark(this.name), toggleUnderline: () => ({ commands: e }) => e.toggleMark(this.name), unsetUnderline: () => ({ commands: e }) => e.unsetMark(this.name) }; }, addKeyboardShortcuts() { return { "Mod-u": () => this.editor.commands.toggleUnderline(), "Mod-U": () => this.editor.commands.toggleUnderline() }; } }), Hb = dg.extend({ addOptions() { var e; return { ...(e = this.parent) == null ? void 0 : e.call(this), button({ editor: t, t: n }) { return { component: Ce, componentProps: { action: () => t.commands.toggleUnderline(), isActive: () => t.isActive("underline") || !1, disabled: !t.can().toggleUnderline(), icon: "Underline", shortcutKeys: ["mod", "U"], tooltip: n("editor.underline.tooltip") } }; } }; } }), lg = /(?:^|\s)(~~(?!\s+~~)((?:[^~]+))~~(?!\s+~~))$/, hg = /(?:^|\s)(~~(?!\s+~~)((?:[^~]+))~~(?!\s+~~))/g, fg = Ct.create({ name: "strike", addOptions() { return { HTMLAttributes: {} }; }, parseHTML() { return [ { tag: "s" }, { tag: "del" }, { tag: "strike" }, { style: "text-decoration", consuming: !1, getAttrs: (e) => e.includes("line-through") ? {} : !1 } ]; }, renderHTML({ HTMLAttributes: e }) { return ["s", Fe(this.options.HTMLAttributes, e), 0]; }, addCommands() { return { setStrike: () => ({ commands: e }) => e.setMark(this.name), toggleStrike: () => ({ commands: e }) => e.toggleMark(this.name), unsetStrike: () => ({ commands: e }) => e.unsetMark(this.name) }; }, addKeyboardShortcuts() { return { "Mod-Shift-s": () => this.editor.commands.toggleStrike() }; }, addInputRules() { return [ An({ find: lg, type: this.type }) ]; }, addPasteRules() { return [ nn({ find: hg, type: this.type }) ]; } }), jb = fg.extend({ addOptions() { var e; return { ...(e = this.parent) == null ? void 0 : e.call(this), button: ({ editor: t, t: n }) => ({ component: Ce, componentProps: { action: () => t.commands.toggleStrike(), isActive: () => t.isActive("strike") || !1, disabled: !t.can().toggleStrike(), icon: "Strikethrough", shortcutKeys: ["shift", "mod", "S"], tooltip: n("editor.strike.tooltip") } }) }; } }), gg = /(^|[^`])`([^`]+)`(?!`)/, pg = /(^|[^`])`([^`]+)`(?!`)/g, mg = Ct.create({ name: "code", addOptions() { return { HTMLAttributes: {} }; }, excludes: "_", code: !0, exitable: !0, parseHTML() { return [ { tag: "code" } ]; }, renderHTML({ HTMLAttributes: e }) { return ["code", Fe(this.options.HTMLAttributes, e), 0]; }, addCommands() { return { setCode: () => ({ commands: e }) => e.setMark(this.name), toggleCode: () => ({ commands: e }) => e.toggleMark(this.name), unsetCode: () => ({ commands: e }) => e.unsetMark(this.name) }; }, addKeyboardShortcuts() { return { "Mod-e": () => this.editor.commands.toggleCode() }; }, addInputRules() { return [ An({ find: gg, type: this.type }) ]; }, addPasteRules() { return [ nn({ find: pg, type: this.type }) ]; } }), Xb = mg.extend({ addOptions() { var e; return { ...(e = this.parent) == null ? void 0 : e.call(this), button: ({ editor: t, t: n }) => ({ component: Ce, componentProps: { action: () => t.commands.toggleCode(), isActive: () => t.isActive("code") || !1, disabled: !t.can().toggleCode(), icon: "Code", shortcutKeys: ["mod", "E"], tooltip: n("editor.code.tooltip") } }) }; } }), bg = /^```([a-z]+)?[\s\n]$/, yg = /^~~~([a-z]+)?[\s\n]$/, Dg = $e.create({ name: "codeBlock", addOptions() { return { languageClassPrefix: "language-", exitOnTripleEnter: !0, exitOnArrowDown: !0, defaultLanguage: null, HTMLAttributes: {} }; }, content: "text*", marks: "", group: "block", code: !0, defining: !0, addAttributes() { return { language: { default: this.options.defaultLanguage, parseHTML: (e) => { var t; const { languageClassPrefix: n } = this.options, a = [...((t = e.firstElementChild) === null || t === void 0 ? void 0 : t.classList) || []].filter((o) => o.startsWith(n)).map((o) => o.replace(n, ""))[0]; return a || null; }, rendered: !1 } }; }, parseHTML() { return [ { tag: "pre", preserveWhitespace: "full" } ]; }, renderHTML({ node: e, HTMLAttributes: t }) { return [ "pre", Fe(this.options.HTMLAttributes, t), [ "code", { class: e.attrs.language ? this.options.languageClassPrefix + e.attrs.language : null }, 0 ] ]; }, addCommands() { return { setCodeBlock: (e) => ({ commands: t }) => t.setNode(this.name, e), toggleCodeBlock: (e) => ({ commands: t }) => t.toggleNode(this.name, "paragraph", e) }; }, addKeyboardShortcuts() { return { "Mod-Alt-c": () => this.editor.commands.toggleCodeBlock(), // remove code block when at start of document or code block is empty Backspace: () => { const { empty: e, $anchor: t } = this.editor.state.selection, n = t.pos === 1; return !e || t.parent.type.name !== this.name ? !1 : n || !t.parent.textContent.length ? this.editor.commands.clearNodes() : !1; }, // exit node on triple enter Enter: ({ editor: e }) => { if (!this.options.exitOnTripleEnter) return !1; const { state: t } = e, { selection: n } = t, { $from: i, empty: r } = n; if (!r || i.parent.type !== this.type) return !1; const a = i.parentOffset === i.parent.nodeSize - 2, o = i.parent.textContent.endsWith(` `); return !a || !o ? !1 : e.chain().command(({ tr: s }) => (s.delete(i.pos - 2, i.pos), !0)).exitCode().run(); }, // exit node on arrow down ArrowDown: ({ editor: e }) => { if (!this.options.exitOnArrowDown) return !1; const { state: t } = e, { selection: n, doc: i } = t, { $from: r, empty: a } = n; if (!a || r.parent.type !== this.type || !(r.parentOffset === r.parent.nodeSize - 2)) return !1; const s = r.after(); return s === void 0 ? !1 : i.nodeAt(s) ? e.commands.command(({ tr: u }) => (u.setSelection(xi.near(i.resolve(s))), !0)) : e.commands.exitCode(); } }; }, addInputRules() { return [ Bo({ find: bg, type: this.type, getAttributes: (e) => ({ language: e[1] }) }), Bo({ find: yg, type: this.type, getAttributes: (e) => ({ language: e[1] }) }) ]; }, addProseMirrorPlugins() { return [ // this plugin creates a code block for pasted content from VS Code // we can also detect the copied code language new Ze({ key: new Ve("codeBlockVSCodeHandler"), props: { handlePaste: (e, t) => { if (!t.clipboardData || this.editor.isActive(this.type.name)) return !1; const n = t.clipboardData.getData("text/plain"), i = t.clipboardData.getData("vscode-editor-data"), r = i ? JSON.parse(i) : void 0, a = r == null ? void 0 : r.mode; if (!n || !a) return !1; const { tr: o, schema: s } = e.state, c = s.text(n.replace(/\r\n?/g, ` `)); return o.replaceSelectionWith(this.type.create({ language: a }, c)), o.selection.$from.parent.type !== this.type && o.setSelection(en.near(o.doc.resolve(Math.max(0, o.selection.from - 2)))), o.setMeta("paste", !0), e.dispatch(o), !0; } } }) ]; } }); let At, Jn; const Ra = /* @__PURE__ */ new Set(), Wa = /* @__PURE__ */ new Set(); function vg() { return At; } function xg(e) { if (!At && !Jn) { const t = e.themes.filter( (i) => !!i && i in Ld ), n = e.languages.filter( (i) => !!i && i in Nd ); return Jn = Sf({ themes: t, langs: n }).then((i) => { At = i; }), Jn; } if (Jn) return Jn; } async function Id(e) { return At && !At.getLoadedThemes().includes(e) && !Wa.has(e) && e in Ld ? (Wa.add(e), await At.loadTheme(e), Wa.delete(e), !0) : !1; } async function Od(e) { return At && !At.getLoadedLanguages().includes(e) && !Ra.has(e) && e in Nd ? (Ra.add(e), await At.loadLanguage(e), Ra.delete(e), !0) : !1; } async function _g({ doc: e, name: t, defaultTheme: n, defaultLanguage: i }) { const r = fi(e, (s) => s.type.name === t), a = [ ...r.map((s) => s.node.attrs.theme), n ], o = [ ...r.map((s) => s.node.attrs.language), i ]; At ? await Promise.all([ ...a.flatMap((s) => Id(s)), ...o.flatMap((s) => !!s && Od(s)) ]) : await xg({ languages: o, themes: a }); } function gc({ doc: e, name: t, defaultTheme: n, defaultLanguage: i }) { const r = []; return fi(e, (o) => o.type.name === t).forEach((o) => { let s = o.pos + 1, c = o.node.attrs.language || i; const u = o.node.attrs.theme || n, d = vg(); if (!d) return; d.getLoadedLanguages().includes(c) || (c = "plaintext"); const f = d.getLoadedThemes().includes(u) ? u : d.getLoadedThemes()[0], g = d.codeToTokensBase(o.node.textContent, { lang: c, theme: f }); for (const l of g) { for (const D of l) { const m = s + D.content.length, h = Pt.inline(s, m, { style: `color: ${D.color}` }); r.push(h), s = m; } s += 1; } }), Et.create(e, r); } function wg({ name: e, defaultLanguage: t, defaultTheme: n }) { const i = new Ze({ key: new Ve("shiki"), view(r) { class a { constructor() { this.initDecorations(); } update() { this.checkUndecoratedBlocks(); } destroy() { } // Initialize shiki async, and then highlight initial document async initDecorations() { const s = r.state.doc; await _g({ doc: s, name: e, defaultLanguage: t, defaultTheme: n }); const c = r.state.tr.setMeta("shikiPluginForceDecoration", !0); r.dispatch(c); } // When new codeblocks were added and they have missing themes or // languages, load those and then add code decorations once again. async checkUndecoratedBlocks() { const s = fi( r.state.doc, (d) => d.type.name === e ); if ((await Promise.all( s.flatMap((d) => [ Id(d.node.attrs.theme), Od(d.node.attrs.language) ]) )).includes(!0)) { const d = r.state.tr.setMeta("shikiPluginForceDecoration", !0); r.dispatch(d); } } } return new a(); }, state: { init: (r, { doc: a }) => gc({ doc: a, name: e, defaultLanguage: t, defaultTheme: n }), apply: (r, a, o, s) => { const c = o.selection.$head.parent.type.name, u = s.selection.$head.parent.type.name, d = fi( o.doc, (l) => l.type.name === e ), f = fi( s.doc, (l) => l.type.name === e ), g = r.docChanged && ([c, u].includes(e) || f.length !== d.length || r.steps.some((l) => l.from !== void 0 && l.to !== void 0 && d.some((D) => D.pos >= l.from && D.pos + D.node.nodeSize <= l.to))); return r.getMeta("shikiPluginForceDecoration") || g ? gc({ doc: r.doc, name: e, defaultLanguage: t, defaultTheme: n }) : a.map(r.mapping, r.doc); } }, props: { //@ts-expect-error decorations(r) { return i.getState(r); } } }); return i; } function Tg({ action: e, languages: t, ...n }) { const i = (a) => { e(a); }, r = Dt(() => t == null ? void 0 : t.map((a) => ({ title: Lf[a] || a, // icon: language.icon, language: a })), [t]); return /* @__PURE__ */ be(kn, { children: [ /* @__PURE__ */ V(Fn, { disabled: n == null ? void 0 : n.disabled, asChild: !0, children: /* @__PURE__ */ V( Ce, { tooltip: n == null ? void 0 : n.tooltip, disabled: n == null ? void 0 : n.disabled, icon: n == null ? void 0 : n.icon } ) }), /* @__PURE__ */ V(Sn, { className: "w-full !max-h-[180px] !overflow-y-scroll", children: r == null ? void 0 : r.map((a) => /* @__PURE__ */ V(Hh, { onClick: () => i(a.language), children: /* @__PURE__ */ V("div", { className: "h-full ml-1", children: a.title }) }, `codeblock-${a.title}`)) }) ] }); } const Ug = Pe.Root, Eg = Pe.Value, Md = Bn.forwardRef(({ className: e, children: t, ...n }, i) => /* @__PURE__ */ be( Pe.Trigger, { ref: i, className: nt( "flex h-10 w-full items-center justify-between rounded-md border border-input bg-background px-3 py-2 text-sm ring-offset-background placeholder:text-muted-foreground focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2 disabled:cursor-not-allowed disabled:opacity-50 [&>span]:line-clamp-1", e ), ...n, children: [ t, /* @__PURE__ */ V(Pe.Icon, { asChild: !0, children: /* @__PURE__ */ V(ns, { className: "h-4 w-4 opacity-50" }) }) ] } )); Md.displayName = Pe.Trigger.displayName; const Pd = Bn.forwardRef(({ className: e, ...t }, n) => /* @__PURE__ */ V( Pe.ScrollUpButton, { ref: n, className: nt( "flex cursor-default items-center justify-center py-1", e ), ...t, children: /* @__PURE__ */ V(Of, { className: "h-4 w-4" }) } )); Pd.displayName = Pe.ScrollUpButton.displayName; const qd = Bn.forwardRef(({ className: e, ...t }, n) => /* @__PURE__ */ V( Pe.ScrollDownButton, { ref: n, className: nt( "flex cursor-default items-center justify-center py-1", e ), ...t, children: /* @__PURE__ */ V(ns, { className: "h-4 w-4" }) } )); qd.displayName = Pe.ScrollDownButton.displayName; const zd = Bn.forwardRef(({ className: e, children: t, position: n = "popper", ...i }, r) => /* @__PURE__ */ V(Pe.Portal, { children: /* @__PURE__ */ be( Pe.Content, { ref: r, className: nt( "relative z-50 max-h-60 overflow-y-auto min-w-[8rem] overflow-hidden rounded-md border bg-popover text-popover-foreground shadow-md data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2", n === "popper" && "data-[side=bottom]:translate-y-1 data-[side=left]:-translate-x-1 data-[side=right]:translate-x-1 data-[side=top]:-translate-y-1", e ), position: n, ...i, children: [ /* @__PURE__ */ V(Pd, {}), /* @__PURE__ */ V( Pe.Viewport, { className: nt( "p-1", n === "popper" && "h-[var(--radix-select-trigger-height)] w-full min-w-[var(--radix-select-trigger-width)]" ), children: t } ), /* @__PURE__ */ V(qd, {}) ] } ) })); zd.displayName = Pe.Content.displayName; const Ag = Bn.forwardRef(({ className: e, ...t }, n) => /* @__PURE__ */ V( Pe.Label, { ref: n, className: nt("py-1.5 pl-8 pr-2 text-sm font-semibold", e), ...t } )); Ag.displayName = Pe.Label.displayName; const No = Bn.forwardRef(({ className: e, children: t, ...n }, i) => /* @__PURE__ */ be( Pe.Item, { ref: i, className: nt( "relative flex w-full cursor-default select-none items-center rounded-sm py-1.5 pl-8 pr-2 text-sm outline-none focus:bg-accent focus:text-accent-foreground data-[disabled]:pointer-events-none data-[disabled]:opacity-50", e ), ...n, children: [ /* @__PURE__ */ V("span", { className: "absolute left-2 flex h-3.5 w-3.5 items-center justify-center", children: /* @__PURE__ */ V(Pe.ItemIndicator, { children: /* @__PURE__ */ V(If, { className: "h-4 w-4" }) }) }), /* @__PURE__ */ V(Pe.ItemText, { children: t }) ] } )); No.displayName = Pe.Item.displayName; const Cg = Bn.forwardRef(({ className: e, ...t }, n) => /* @__PURE__ */ V( Pe.Separator, { ref: n, className: nt("-mx-1 my-1 h-px bg-muted", e), ...t } )); Cg.displayName = Pe.Separator.displayName; function kg() { const [e, t] = je(!1); return { isCopied: e, copyToClipboard: async (i) => { try { await navigator.clipboard.writeText(i), t(!0), setTimeout(() => t(!1), 2e3); } catch (r) { console.error("Failed to copy text: ", r), t(!1); } } }; } const Fg = "_wrap_fsdar_1", Sg = "_maxHeight_fsdar_10", Bg = "_btnCopy_fsdar_13", Lg = "_btnDelete_fsdar_14", Ng = "_blockInfo_fsdar_18", Rg = "_blockInfoEditable_fsdar_28", Wg = "_selectLang_fsdar_32", Ig = "_copied_fsdar_58", $t = { wrap: Fg, maxHeight: Sg, btnCopy: Bg, btnDelete: Lg, blockInfo: Ng, blockInfoEditable: Rg, selectLang: Wg, copied: Ig }; function Og({ editor: e, node: { attrs: t }, updateAttributes: n, extension: i }) { var g, l; const { isCopied: r, copyToClipboard: a } = kg(), o = Dt(() => { var D; return (D = i.options.languages) != null && D.length ? i.options.languages : Rd; }, [i.options.languages]), s = Vo(), c = (l = (g = e == null ? void 0 : e.options) == null ? void 0 : g.editorProps) == null ? void 0 : l.print, { language: u } = t, d = qt(null), f = tn(() => jh(Mg.name, e), [e]); return /* @__PURE__ */ be(gi, { className: yt($t.wrap, !c && $t.maxHeight, "render-wrapper"), children: [ /* @__PURE__ */ be( "div", { className: yt($t.blockInfo, { [$t.blockInfoEditable]: !s }), children: [ /* @__PURE__ */ V( "span", { className: yt($t.btnCopy, r && $t.copied), onClick: () => a(d.current.innerText), children: r ? /* @__PURE__ */ V(Pf, { size: 16 }) : /* @__PURE__ */ V(Mf, { size: 16 }) } ), /* @__PURE__ */ V( "span", { className: $t.btnDelete, onClick: f, children: /* @__PURE__ */ V( st, { name: "Trash2" } ) } ), /* @__PURE__ */ V("div", { className: $t.selectLang, children: /* @__PURE__ */ be( Ug, { defaultValue: u || "auto", disabled: !s, onValueChange: (D) => n({ language: D }), children: [ /* @__PURE__ */ V(Md, { children: /* @__PURE__ */ V(Eg, { placeholder: "Language" }) }), /* @__PURE__ */ be(zd, { className: "max-h-60 overflow-y-auto", children: [ /* @__PURE__ */ V(No, { value: "auto", children: "Auto" }), o.map((D, m) => /* @__PURE__ */ V( No, { value: D, children: D.charAt(0).toUpperCase() + D.slice(1) }, `code-lang-${m}` )) ] }) ] } ) }) ] } ), /* @__PURE__ */ V("pre", { ref: d, children: /* @__PURE__ */ V(Xh, { as: "code" }) }) ] }); } const Mg = Dg.extend({ addOptions() { var e; return { ...(e = this.parent) == null ? void 0 : e.call(this), languages: [], button: ({ editor: t, t: n, extension: i }) => { var a, o, s; const r = (o = (a = i == null ? void 0 : i.options) == null ? void 0 : a.languages) != null && o.length ? (s = i == null ? void 0 : i.options) == null ? void 0 : s.languages : Rd; return { component: Tg, componentProps: { action: (c = "js") => t.commands.setCodeBlock({ language: c }), isActive: () => t.isActive("codeBlock") || !1, disabled: !t.can().toggleCodeBlock(), icon: "Code2", tooltip: n("editor.codeblock.tooltip"), languages: r } }; } }; }, addNodeView() { return Ko(Og); }, addProseMirrorPlugins() { var e; return [ ...((e = this.parent) == null ? void 0 : e.call(this)) || [], wg({ name: this.name, defaultLanguage: null, defaultTheme: this.options.defaultTheme }) ]; } }), Pg = (e) => { if (!e.children.length) return; const t = e.querySelectorAll("span"); t && t.forEach((n) => { var i, r; const a = n.getAttribute("style"), o = (r = (i = n.parentElement) === null || i === void 0 ? void 0 : i.closest("span")) === null || r === void 0 ? void 0 : r.getAttribute("style"); n.setAttribute("style", `${o};${a}`); }); }, qg = Ct.create({ name: "textStyle", priority: 101, addOptions() { return { HTMLAttributes: {}, mergeNestedSpanStyles: !1 }; }, parseHTML() { return [ { tag: "span", getAttrs: (e) => e.hasAttribute("style") ? (this.options.mergeNestedSpanStyles && Pg(e), {}) : !1 } ]; }, renderHTML({ HTMLAttributes: e }) { return ["span", Fe(this.options.HTMLAttributes, e), 0]; }, addCommands() { return { removeEmptyTextStyle: () => ({ tr: e }) => { const { selection: t } = e; return e.doc.nodesBetween(t.from, t.to, (n, i) => { if (n.isTextblock) return !0; n.marks.filter((r) => r.type === this.type).some((r) => Object.values(r.attrs).some((a) => !!a)) || e.removeMark(i, i + n.nodeSize, this.type); }), !0; } }; } }), zg = Ne.create({ name: "fontFamily", addOptions() { return { types: ["textStyle"] }; }, addGlobalAttributes() { return [ { types: this.options.types, attributes: { fontFamily: { default: null, parseHTML: (e) => e.style.fontFamily, renderHTML: (e) => e.fontFamily ? { style: `font-family: ${e.fontFamily}` } : {} } } } ]; }, addCommands() { return { setFontFamily: (e) => ({ chain: t }) => t().setMark("textStyle", { fontFamily: e }).run(), unsetFontFamily: () => ({ chain: e }) => e().setMark("textStyle", { fontFamily: null }).removeEmptyTextStyle().run() }; } }); function Hg(e) { var a, o, s; const { t, lang: n } = kt(), i = qt(null), r = Dt(() => { var d; const c = (d = e == null ? void 0 : e.items) == null ? void 0 : d.find((f) => f.isActive()); return c && !c.default ? { ...c } : { title: e.tooltip, font: t("editor.fontFamily.default.tooltip"), isActive: () => !1, disabled: !1, action: () => e.editor.chain().focus().unsetFontFamily().run() }; }, [t, n, e]); return /* @__PURE__ */ be(kn, { children: [ /* @__PURE__ */ V(Fn, { asChild: !0, disabled: e == null ? void 0 : e.disabled, children: /* @__PURE__ */ V("div", { ref: i, children: /* @__PURE__ */ V( as, { disabled: e == null ? void 0 : e.disabled, icon: "MenuDown", title: ((a = r == null ? void 0 : r.font) == null ? void 0 : a.length) > 7 ? `${(o = r == null ? void 0 : r.font) == null ? void 0 : o.slice(0, 6)}...` : r == null ? void 0 : r.font, tooltip: e == null ? void 0 : e.tooltip } ) }) }), /* @__PURE__ */ V(Sn, { className: "max-h-[40vh] w-32 overflow-y-auto", container: i.current, children: (s = e == null ? void 0 : e.items) == null ? void 0 : s.map((c, u) => { const d = c.font === t("editor.fontFamily.default.tooltip") ? {} : { fontFamily: c.font }; return /* @__PURE__ */ be(Jo, { children: [ /* @__PURE__ */ V( Zn, { checked: (r == null ? void 0 : r.font) === c.font, onClick: c.action, children: /* @__PURE__ */ V("div", { className: "ml-1 h-full", style: d, children: c.font }) } ), c.font === t("editor.fontFamily.default.tooltip") && /* @__PURE__ */ V(Fd, {}) ] }, `font-family-${u}`); }) }) ] }); } const $b = zg.extend({ addOptions() { var e; return { ...(e = this.parent) == null ? void 0 : e.call(this), fontFamilyList: Nf, button({ editor: t, extension: n, t: i }) { var u; const { extensions: r = [] } = t.extensionManager ?? [], a = Lo(((u = n == null ? void 0 : n.options) == null ? void 0 : u.fontFamilyList) || []), o = r.find( (d) => d.name === "base-kit" ), s = a.map((d) => ({ action: () => { t.chain().focus().setFontFamily(d.value).run(); }, isActive: () => t.isActive("textStyle", { fontFamily: d.value }) || !1, disabled: !t.can().setFontFamily(d.value), title: d.name, font: d.value })); o && o.options.textStyle !== !1 && s.unshift({ action: () => t.chain().focus().unsetFontFamily().run(), isActive: () => !1, disabled: !1, font: i("editor.fontFamily.default.tooltip"), title: i("editor.fontFamily.tooltip") }); const c = s.filter((d) => d.disabled).length === s.length; return { component: Hg, componentProps: { tooltip: i("editor.fontFamily.tooltip"), disabled: c, items: s, editor: t } }; } }; } }), jg = $e.create({ name: "heading", addOptions() { return { levels: [1, 2, 3, 4, 5, 6], HTMLAttributes: {} }; }, content: "inline*", group: "block", defining: !0, addAttributes() { return { level: { default: 1, rendered: !1 } }; }, parseHTML() { return this.options.levels.map((e) => ({ tag: `h${e}`, attrs: { level: e } })); }, renderHTML({ node: e, HTMLAttributes: t }) { return [`h${this.options.levels.includes(e.attrs.level) ? e.attrs.level : this.options.levels[0]}`, Fe(this.options.HTMLAttributes, t), 0]; }, addCommands() { return { setHeading: (e) => ({ commands: t }) => this.options.levels.includes(e.level) ? t.setNode(this.name, e) : !1, toggleHeading: (e) => ({ commands: t }) => this.options.levels.includes(e.level) ? t.toggleNode(this.name, "paragraph", e) : !1 }; }, addKeyboardShortcuts() { return this.options.levels.reduce((e, t) => ({ ...e, [`Mod-Alt-${t}`]: () => this.editor.commands.toggleHeading({ level: t }) }), {}); }, addInputRules() { return this.options.levels.map((e) => Bo({ find: new RegExp(`^(#{${Math.min(...this.options.levels)},${e}})\\s$`), type: this.type, getAttributes: { level: e } })); } }); function Xg(e) { var n; const t = Dt(() => { var a; const i = (a = e == null ? void 0 : e.items) == null ? void 0 : a.find((o) => o.isActive()); return i && !i.default ? { ...i } : { title: e.tooltip, level: 0, isActive: () => !1 }; }, [e]); return /* @__PURE__ */ be(kn, { children: [ /* @__PURE__ */ V( Fn, { asChild: !0, disabled: e == null ? void 0 : e.disabled, children: /* @__PURE__ */ V( as, { disabled: e == null ? void 0 : e.disabled, icon: "MenuDown", title: t == null ? void 0 : t.title, tooltip: e == null ? void 0 : e.tooltip } ) } ), /* @__PURE__ */ V(Sn, { className: "w-full", children: (n = e == null ? void 0 : e.items) == null ? void 0 : n.map((i, r) => { var a, o; return /* @__PURE__ */ be(Jo, { children: [ /* @__PURE__ */ be( Zn, { checked: (t == null ? void 0 : t.title) === i.title, onClick: i.action, children: [ /* @__PURE__ */ V("div", { className: `heading- ml-1 h-full${i.level}`, children: i.title }), !!((a = i == null ? void 0 : i.shortcutKeys) != null && a.length) && /* @__PURE__ */ V($h, { className: "pl-4", children: (o = i == null ? void 0 : i.shortcutKeys) == null ? void 0 : o.map((s) => Go(s)).join(" ") }) ] } ), i.level === 0 && /* @__PURE__ */ V(Fd, {}) ] }, `heading-k-${r}`); }) }) ] }); } const Vb = jg.extend({ addOptions() { var e; return { ...(e = this.parent) == null ? void 0 : e.call(this), levels: [1, 2, 3, 4, 5, 6], button({ editor: t, extension: n, t: i }) { var u; const { extensions: r = [] } = t.extensionManager ?? [], a = ((u = n.options) == null ? void 0 : u.levels) || [], o = r.find( (d) => d.name === "base-kit" ), s = a.map((d) => ({ action: () => t.commands.toggleHeading({ level: d }), isActive: () => t.isActive("heading", { level: d }) || !1, disabled: !t.can().toggleHeading({ level: d }), title: i(`editor.heading.h${d}.tooltip`), level: d, shortcutKeys: ["alt", "mod", `${d}`] })); o && o.options.paragraph !== !1 && s.unshift({ action: () => t.commands.setParagraph(), isActive: () => t.isActive("paragraph") || !1, disabled: !t.can().setParagraph(), level: 0, title: i("editor.paragraph.tooltip"), shortcutKeys: ["alt", "mod", "0"] }); const c = s.filter((d) => d.disabled).length === s.length; return { component: Xg, componentProps: { tooltip: i("editor.heading.tooltip"), disabled: c, items: s, editor: t } }; } }; } }), $g = Ne.create({ name: "textAlign", addOptions() { return { types: [], alignments: ["left", "center", "right", "justify"], defaultAlignment: null }; }, addGlobalAttributes() { return [ { types: this.options.types, attributes: { textAlign: { default: this.options.defaultAlignment, parseHTML: (e) => { const t = e.style.textAlign; return this.options.alignments.includes(t) ? t : this.options.defaultAlignment; }, renderHTML: (e) => e.textAlign ? { style: `text-align: ${e.textAlign}` } : {} } } } ]; }, addCommands() { return { setTextAlign: (e) => ({ commands: t }) => this.options.alignments.includes(e) ? this.options.types.map((n) => t.updateAttributes(n, { textAlign: e })).every((n) => n) : !1, unsetTextAlign: () => ({ commands: e }) => this.options.types.map((t) => e.resetAttributes(t, "textAlign")).every((t) => t) }; }, addKeyboardShortcuts() { return { "Mod-Shift-l": () => this.editor.commands.setTextAlign("left"), "Mod-Shift-e": () => this.editor.commands.setTextAlign("center"), "Mod-Shift-r": () => this.editor.commands.setTextAlign("right"), "Mod-Shift-j": () => this.editor.commands.setTextAlign("justify") }; } }); function Vg(e) { var n; const t = Dt(() => { var a; const i = (a = e == null ? void 0 : e.items) == null ? void 0 : a.find((o) => o.isActive()); return i && !i.default ? { ...i, icon: i.icon ? i.icon : e.icon } : { title: e == null ? void 0 : e.tooltip, icon: e.icon, isActive: () => !1 }; }, [e]); return /* @__PURE__ */ be(Fi, { modal: !0, children: [ /* @__PURE__ */ V( Si, { asChild: !0, disabled: e == null ? void 0 : e.disabled, children: /* @__PURE__ */ V( Ce, { customClass: "!w-12 h-12", disabled: e == null ? void 0 : e.disabled, icon: e == null ? void 0 : e.icon, tooltip: e == null ? void 0 : e.tooltip, children: /* @__PURE__ */ V( st, { className: "ml-1 size-3 text-zinc-500", name: "MenuDown" } ) } ) } ), /* @__PURE__ */ V( Bi, { align: "start", className: "flex w-full min-w-4 flex-row gap-1 !p-[4px]", side: "bottom", children: (n = e == null ? void 0 : e.items) == null ? void 0 : n.map((i, r) => { var a, o; return /* @__PURE__ */ be(aa, { children: [ /* @__PURE__ */ V(oa, { asChild: !0, children: /* @__PURE__ */ V( Zo, { className: "size-7 p-1", "data-state": t.title === i.title ? "on" : "off", onClick: i == null ? void 0 : i.action, pressed: t.title === i.title, size: "sm", children: (i == null ? void 0 : i.icon) && /* @__PURE__ */ V(st, { name: i.icon }) } ) }), /* @__PURE__ */ be(sa, { className: "flex flex-col items-center", children: [ /* @__PURE__ */ V("span", { children: i.title }), !!((a = i.shortcutKeys) != null && a.length) && /* @__PURE__ */ V("span", { children: (o = i.shortcutKeys) == null ? void 0 : o.map((s) => Go(s)).join(" ") }) ] }) ] }, `text-align-${r}`); }) } ) ] }); } const Kb = $g.extend({ addOptions() { var e; return { ...(e = this.parent) == null ? void 0 : e.call(this), types: ["heading", "paragraph", "list_item", "title"], button({ editor: t, extension: n, t: i }) { var u; const r = ((u = n.options) == null ? void 0 : u.alignments) || [], a = { left: ["mod", "Shift", "L"], center: ["mod", "Shift", "E"], right: ["mod", "Shift", "R"], justify: ["mod", "Shift", "J"] }, o = { left: "AlignLeft", center: "AlignCenter", right: "AlignRight", justify: "AlignJustify" }, s = r.map((d) => { var f, g, l; return { title: i(`editor.textalign.${d}.tooltip`), icon: o[d], shortcutKeys: a[d], isActive: () => t.isActive({ textAlign: d }) || !1, action: () => { var D, m; return (m = (D = t.commands) == null ? void 0 : D.setTextAlign) == null ? void 0 : m.call(D, d); }, disabled: !((l = (g = (f = t == null ? void 0 : t.can) == null ? void 0 : f.call(t)) == null ? void 0 : g.setTextAlign) != null && l.call(g, d)) }; }), c = s.filter((d) => d.disabled).length === s.length; return { component: Vg, componentProps: { icon: "AlignJustify", tooltip: i("editor.textalign.tooltip"), disabled: c, items: s } }; } }; } }); function Kg(e) { var r; const { t } = kt(), n = qt(null), i = Dt(() => { const a = (e.items || []).find((s) => s.isActive()); return a || { title: t("editor.fontSize.default.tooltip"), isActive: () => !1 }; }, [e]); return /* @__PURE__ */ be(kn, { children: [ /* @__PURE__ */ V(Fn, { asChild: !0, disabled: e == null ? void 0 : e.disabled, children: /* @__PURE__ */ V("div", { ref: n, children: /* @__PURE__ */ V( as, { disabled: e == null ? void 0 : e.disabled, icon: "MenuDown", title: i == null ? void 0 : i.title, tooltip: `${e == null ? void 0 : e.tooltip}` } ) }) }), /* @__PURE__ */ V( Sn, { container: n.current, className: "max-h-[40vh] w-32 overflow-y-auto", children: (r = e == null ? void 0 : e.items) == null ? void 0 : r.map((a, o) => /* @__PURE__ */ V( Zn, { checked: i.title === a.title, onClick: a.action, children: /* @__PURE__ */ V("div", { className: "ml-1 h-full", children: a.title }) }, `font-size-${o}` )) } ) ] }); } const Gb = Ne.create({ name: "fontSize", addOptions() { var e; return { ...(e = this.parent) == null ? void 0 : e.call(this), types: ["textStyle"], fontSizes: [...Rf], button({ editor: t, extension: n, t: i }) { var c; const r = Lo(((c = n.options) == null ? void 0 : c.fontSizes) || fc), a = Lo([fc])[0], o = r.map((u) => ({ title: u.value === a.value ? i("editor.fontSize.default.tooltip") : String(u.name), isActive: () => { const { fontSize: d } = t.getAttributes("textStyle"); return u.value === a.value && d === void 0 ? !0 : t.isActive({ fontSize: String(u.value) }) || !1; }, action: () => { if (u.value === a.value) { t.commands.unsetFontSize(); return; } t.commands.setFontSize(String(u.value)); }, disabled: !t.can().setFontSize(String(u.value)), divider: u.value === a.value || !1, default: u.value === a.value || !1 })), s = o.filter((u) => u.disabled).length === o.length; return { component: Kg, componentProps: { editor: t, tooltip: i("editor.fontSize.tooltip"), disabled: s, items: o, maxHeight: 280 } }; } }; }, addGlobalAttributes() { return [ { types: this.options.types, attributes: { fontSize: { default: null, parseHTML: (e) => e.style.fontSize.replaceAll(/["']+/g, ""), renderHTML: (e) => e.fontSize ? { style: `font-size: ${e.fontSize}` } : {} } } } ]; }, addCommands() { return { setFontSize: (e) => ({ chain: t }) => t().setMark("textStyle", { fontSize: e }).run(), unsetFontSize: () => ({ chain: e }) => e().setMark("textStyle", { fontSize: null }).removeEmptyTextStyle().run() }; } }), Gg = Ne.create({ name: "color", addOptions() { return { types: ["textStyle"] }; }, addGlobalAttributes() { return [ { types: this.options.types, attributes: { color: { default: null, parseHTML: (e) => { var t; return (t = e.style.color) === null || t === void 0 ? void 0 : t.replace(/['"]+/g, ""); }, renderHTML: (e) => e.color ? { style: `color: ${e.color}` } : {} } } } ]; }, addCommands() { return { setColor: (e) => ({ chain: t }) => t().setMark("textStyle", { color: e }).run(), unsetColor: () => ({ chain: e }) => e().setMark("textStyle", { color: null }).removeEmptyTextStyle().run() }; } }); function Zg({ fill: e }) { return /* @__PURE__ */ V( "svg", { width: "18px", height: "18px", viewBox: "0 0 240 240", version: "1.1", xmlns: "http://www.w3.org/2000/svg", children: /* @__PURE__ */ V("g", { stroke: "none", strokeWidth: 1, fill: "none", fillRule: "evenodd", children: /* @__PURE__ */ V("g", { transform: "translate(0.000000, 0.500000)", children: /* @__PURE__ */ be("g", { transform: "translate(39.000000, 17.353553)", children: [ /* @__PURE__ */ V( "path", { d: "M11,201.146447 L167,201.146447 C173.075132,201.146447 178,206.071314 178,212.146447 C178,218.221579 173.075132,223.146447 167,223.146447 L11,223.146447 C4.92486775,223.146447 7.43989126e-16,218.221579 0,212.146447 C-7.43989126e-16,206.071314 4.92486775,201.146447 11,201.146447 Z", id: "矩形", fill: e || "#DF2A3F", fillRule: "evenodd" } ), /* @__PURE__ */ V( "path", { d: "M72.3425855,16.8295583 C75.799482,7.50883712 86.1577877,2.75526801 95.4785089,6.21216449 C100.284516,7.99463061 104.096358,11.7387855 105.968745,16.4968188 L106.112518,16.8745422 L159.385152,161.694068 C161.291848,166.877345 158.635655,172.624903 153.452378,174.531599 C148.358469,176.405421 142.719567,173.872338 140.716873,168.864661 L140.614848,168.598825 L89.211,28.86 L37.3759214,168.623816 C35.4885354,173.712715 29.8981043,176.351047 24.7909589,174.617647 L24.5226307,174.522368 C19.4337312,172.634982 16.7953993,167.044551 18.5287999,161.937406 L18.6240786,161.669077 L72.3425855,16.8295583 Z", id: "路径-21", fill: "currentColor", fillRule: "nonzero" } ), /* @__PURE__ */ V( "path", { d: "M121,103.146447 C126.522847,103.146447 131,107.623599 131,113.146447 C131,118.575687 126.673329,122.994378 121.279905,123.142605 L121,123.146447 L55,123.146447 C49.4771525,123.146447 45,118.669294 45,113.146447 C45,107.717207 49.3266708,103.298515 54.7200952,103.150288 L55,103.146447 L121,10