@jenkin-a/jeditor 1.0.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/dist/jeditor.css +2 -0
- package/dist/jeditor.es.js +523 -0
- package/dist/jeditor.umd.js +5 -0
- package/package.json +49 -0
package/dist/jeditor.css
ADDED
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
:root{--je-blue:#0052d9;--je-blue-active:#e6f0ff;--je-divider:#e0e0e0;--je-hover:#eee;--je-radius:4px}.je-container{-webkit-font-smoothing:antialiased;background:#fff;border:1px solid #e6e6e6;border-radius:4px;flex-direction:column;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica Neue,Arial,PingFang SC,Microsoft YaHei,sans-serif;display:flex;overflow:hidden}.je-toolbar-row{flex-shrink:0;align-items:center;gap:1px;padding:0 12px;display:flex}.je-toolbar-row--primary{background:#fff;height:44px}.je-toolbar-row--secondary{background:#f3f4f6;border-radius:6px;height:42px;margin:0 8px 4px}.je-spacer{flex:1}.v-divider{background-color:var(--je-divider);flex-shrink:0;width:1px;height:16px;margin:0 6px}.tool-btn,.tool-btn-text,.tool-btn-arrow-down{border-radius:var(--je-radius);color:#444;cursor:pointer;background:0 0;border:none;flex-shrink:0;justify-content:center;align-items:center;gap:2px;line-height:1;transition:background-color .1s;display:inline-flex}.tool-btn{width:28px;height:28px;padding:0;font-size:13px}.tool-btn:hover{background-color:var(--je-hover)}.tool-btn-text{white-space:nowrap;height:28px;padding:0 6px;font-size:13px}.tool-btn-text:hover{background-color:var(--je-hover)}.tool-btn-arrow-down{color:#999;width:16px;height:28px;padding:0}.tool-btn-arrow-down:hover{background-color:var(--je-hover)}.tool-btn svg,.tool-btn-text svg,.tool-btn-arrow-down svg{flex-shrink:0;width:20px;height:20px}.tool-btn-text svg,.tool-btn-arrow-down svg{width:14px;height:14px}.je-color-group{flex-shrink:0;align-items:center;display:inline-flex}.je-color-inner{flex-direction:column;align-items:center;gap:1px;line-height:1;display:flex}.je-color-char{font-size:14px;font-weight:600}.je-color-bar{border-radius:1px;width:16px;height:3px}.tool-btn.is-active{background-color:var(--je-blue-active);color:var(--je-blue)}.tool-btn.is-disabled{opacity:.35;pointer-events:none;cursor:default}.je-editor-area{flex-direction:column;flex:1;display:flex}.je-editor-area .tiptap{cursor:text;color:#333;outline:none;flex:1;min-height:700px;padding:32px 60px;font-size:14px;line-height:1.7}.je-editor-area .tiptap h1{margin-bottom:.5em;font-size:2em;font-weight:700}.je-editor-area .tiptap h2{margin-bottom:.5em;font-size:1.5em;font-weight:700}.je-editor-area .tiptap h3{margin-bottom:.5em;font-size:1.25em;font-weight:700}.je-editor-area .tiptap p{margin-bottom:.8em;line-height:1.7}.je-editor-area .tiptap ul{margin-bottom:.8em;padding-left:1.5em;list-style-type:disc}.je-editor-area .tiptap ol{margin-bottom:.8em;padding-left:1.5em;list-style-type:decimal}::-webkit-scrollbar{width:6px}::-webkit-scrollbar-thumb{background:#ddd;border-radius:10px}.image-node-wrapper{cursor:default;-webkit-user-select:none;user-select:none;line-height:0;display:inline-block;position:relative}.image-node-wrapper img{border:2px solid #0000;border-radius:2px;max-width:100%;transition:border-color .15s;display:block}.image-node-wrapper.is-selected img{border-color:var(--je-blue)}.image-resize-handle{background:var(--je-blue);z-index:10;border-radius:50%;width:10px;height:10px;display:none;position:absolute}.image-node-wrapper.is-selected .image-resize-handle{display:block}.image-resize-handle[data-corner=tl]{cursor:nwse-resize;top:-5px;left:-5px}.image-resize-handle[data-corner=tr]{cursor:nesw-resize;top:-5px;right:-5px}.image-resize-handle[data-corner=bl]{cursor:nesw-resize;bottom:-5px;left:-5px}.image-resize-handle[data-corner=br]{cursor:nwse-resize;bottom:-5px;right:-5px}
|
|
2
|
+
/*$vite$:1*/
|
|
@@ -0,0 +1,523 @@
|
|
|
1
|
+
import e from "@tiptap/extension-underline";
|
|
2
|
+
import { Editor as t, Node as n, mergeAttributes as r } from "@tiptap/core";
|
|
3
|
+
import i from "@tiptap/starter-kit";
|
|
4
|
+
//#region src/core/plugin-manager.js
|
|
5
|
+
var a = class {
|
|
6
|
+
constructor() {
|
|
7
|
+
this._plugins = /* @__PURE__ */ new Map();
|
|
8
|
+
}
|
|
9
|
+
register(e) {
|
|
10
|
+
if (!e.name) throw Error("[JEditor] Plugin 缺少 name 字段");
|
|
11
|
+
this._plugins.set(e.name, e);
|
|
12
|
+
}
|
|
13
|
+
registerAll(e) {
|
|
14
|
+
e.forEach((e) => this.register(e));
|
|
15
|
+
}
|
|
16
|
+
get(e) {
|
|
17
|
+
return this._plugins.get(e);
|
|
18
|
+
}
|
|
19
|
+
getAll() {
|
|
20
|
+
return Array.from(this._plugins.values());
|
|
21
|
+
}
|
|
22
|
+
getTiptapExtensions() {
|
|
23
|
+
return this.getAll().filter((e) => e.tiptapExtension != null).map((e) => e.tiptapExtension);
|
|
24
|
+
}
|
|
25
|
+
initAll(e, t = {}) {
|
|
26
|
+
this.getAll().forEach((n) => {
|
|
27
|
+
typeof n.init == "function" && n.init(e, t[n.name] || {});
|
|
28
|
+
});
|
|
29
|
+
}
|
|
30
|
+
destroyAll() {
|
|
31
|
+
this.getAll().forEach((e) => {
|
|
32
|
+
typeof e.destroy == "function" && e.destroy();
|
|
33
|
+
}), this._plugins.clear();
|
|
34
|
+
}
|
|
35
|
+
}, o = {
|
|
36
|
+
placeholder: "开始在此编写文档...",
|
|
37
|
+
toolbar: [[
|
|
38
|
+
"undo",
|
|
39
|
+
"redo",
|
|
40
|
+
"|",
|
|
41
|
+
"insertImage",
|
|
42
|
+
"insert",
|
|
43
|
+
"|",
|
|
44
|
+
"attachment",
|
|
45
|
+
"table",
|
|
46
|
+
"link",
|
|
47
|
+
"mention",
|
|
48
|
+
"|",
|
|
49
|
+
"more",
|
|
50
|
+
"->",
|
|
51
|
+
"fullscreen"
|
|
52
|
+
], /* @__PURE__ */ "heading.|.fontFamily.|.fontSizeDown.fontSize.fontSizeUp.|.bold.italic.underline.strike.clearFormat.|.textColor.highlight.|.bulletList.orderedList.alignLeft.alignCenter.alignRight.lineHeight.|.blockquote.codeBlock".split(".")],
|
|
53
|
+
image: {
|
|
54
|
+
maxSize: 20 * 1024 * 1024,
|
|
55
|
+
uploadUrl: null,
|
|
56
|
+
accept: "image/png,image/jpeg,image/gif,image/webp,image/svg+xml"
|
|
57
|
+
}
|
|
58
|
+
};
|
|
59
|
+
function s(e = {}) {
|
|
60
|
+
let t = {
|
|
61
|
+
...o,
|
|
62
|
+
...e
|
|
63
|
+
};
|
|
64
|
+
return e.image && (t.image = {
|
|
65
|
+
...o.image,
|
|
66
|
+
...e.image
|
|
67
|
+
}), t;
|
|
68
|
+
}
|
|
69
|
+
//#endregion
|
|
70
|
+
//#region src/plugins/bold.js
|
|
71
|
+
var c = {
|
|
72
|
+
name: "bold",
|
|
73
|
+
toolbar: {
|
|
74
|
+
text: "B",
|
|
75
|
+
title: "粗体",
|
|
76
|
+
shortcut: "Ctrl+B",
|
|
77
|
+
className: "font-bold"
|
|
78
|
+
},
|
|
79
|
+
tiptapExtension: null,
|
|
80
|
+
command: (e) => e.chain().focus().toggleBold().run(),
|
|
81
|
+
isActive: (e) => e.isActive("bold")
|
|
82
|
+
}, l = {
|
|
83
|
+
name: "italic",
|
|
84
|
+
toolbar: {
|
|
85
|
+
text: "I",
|
|
86
|
+
title: "斜体",
|
|
87
|
+
shortcut: "Ctrl+I",
|
|
88
|
+
className: "italic"
|
|
89
|
+
},
|
|
90
|
+
tiptapExtension: null,
|
|
91
|
+
command: (e) => e.chain().focus().toggleItalic().run(),
|
|
92
|
+
isActive: (e) => e.isActive("italic")
|
|
93
|
+
}, u = {
|
|
94
|
+
name: "underline",
|
|
95
|
+
toolbar: {
|
|
96
|
+
text: "U",
|
|
97
|
+
title: "下划线",
|
|
98
|
+
shortcut: "Ctrl+U",
|
|
99
|
+
className: "underline"
|
|
100
|
+
},
|
|
101
|
+
tiptapExtension: e,
|
|
102
|
+
command: (e) => e.chain().focus().toggleUnderline().run(),
|
|
103
|
+
isActive: (e) => e.isActive("underline")
|
|
104
|
+
}, d = {
|
|
105
|
+
name: "strike",
|
|
106
|
+
toolbar: {
|
|
107
|
+
text: "S",
|
|
108
|
+
title: "删除线",
|
|
109
|
+
shortcut: "Ctrl+Shift+X",
|
|
110
|
+
className: "line-through text-[13px]"
|
|
111
|
+
},
|
|
112
|
+
tiptapExtension: null,
|
|
113
|
+
command: (e) => e.chain().focus().toggleStrike().run(),
|
|
114
|
+
isActive: (e) => e.isActive("strike")
|
|
115
|
+
}, f = {
|
|
116
|
+
name: "undo",
|
|
117
|
+
toolbar: {
|
|
118
|
+
icon: "<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"20\" height=\"20\" fill=\"currentColor\">\n <path d=\"M6.25 3.75 2.5 6.25l3.75 2.5V6.875h5.938a4.062 4.062 0 1 1 0 8.125H8.125a.625.625 0 1 0 0 1.25h4.063a5.313 5.313 0 0 0 0-10.625H6.25z\"></path>\n</svg>",
|
|
119
|
+
title: "撤销",
|
|
120
|
+
shortcut: "Ctrl+Z"
|
|
121
|
+
},
|
|
122
|
+
tiptapExtension: null,
|
|
123
|
+
command: (e) => e.chain().focus().undo().run(),
|
|
124
|
+
isActive: () => !1,
|
|
125
|
+
isDisabled: (e) => !e.can().undo()
|
|
126
|
+
}, p = {
|
|
127
|
+
name: "redo",
|
|
128
|
+
toolbar: {
|
|
129
|
+
icon: "<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"20\" height=\"20\" fill=\"currentColor\" style=\"transform:scaleX(-1)\">\n <path d=\"M6.25 3.75 2.5 6.25l3.75 2.5V6.875h5.938a4.062 4.062 0 1 1 0 8.125H8.125a.625.625 0 1 0 0 1.25h4.063a5.313 5.313 0 0 0 0-10.625H6.25z\"></path>\n</svg>",
|
|
130
|
+
title: "重做",
|
|
131
|
+
shortcut: "Ctrl+Shift+Z"
|
|
132
|
+
},
|
|
133
|
+
tiptapExtension: null,
|
|
134
|
+
command: (e) => e.chain().focus().redo().run(),
|
|
135
|
+
isActive: () => !1,
|
|
136
|
+
isDisabled: (e) => !e.can().redo()
|
|
137
|
+
}, m = {
|
|
138
|
+
name: "clearFormat",
|
|
139
|
+
toolbar: {
|
|
140
|
+
icon: "slash",
|
|
141
|
+
title: "清除格式"
|
|
142
|
+
},
|
|
143
|
+
tiptapExtension: null,
|
|
144
|
+
command: (e) => e.chain().focus().unsetAllMarks().run(),
|
|
145
|
+
isActive: () => !1
|
|
146
|
+
}, h = {
|
|
147
|
+
name: "formatPainter",
|
|
148
|
+
toolbar: {
|
|
149
|
+
icon: "edit-3",
|
|
150
|
+
title: "格式刷"
|
|
151
|
+
},
|
|
152
|
+
tiptapExtension: null,
|
|
153
|
+
command: () => console.log("[JEditor] 格式刷功能待实现"),
|
|
154
|
+
isActive: () => !1
|
|
155
|
+
}, g = class {
|
|
156
|
+
constructor({ node: e, editor: t, getPos: n }) {
|
|
157
|
+
this.node = e, this.editor = t, this.getPos = n, this._startX = 0, this._startWidth = 0, this._pendingWidth = null, this._activeCorner = null, this.dom = document.createElement("span"), this.dom.className = "image-node-wrapper", this.dom.contentEditable = "false", this.img = document.createElement("img"), this.img.src = e.attrs.src, this.img.alt = e.attrs.alt || "", this.img.draggable = !1, e.attrs.width && (this.img.style.width = e.attrs.width + "px"), this.dom.appendChild(this.img);
|
|
158
|
+
for (let e of [
|
|
159
|
+
"tl",
|
|
160
|
+
"tr",
|
|
161
|
+
"bl",
|
|
162
|
+
"br"
|
|
163
|
+
]) {
|
|
164
|
+
let t = document.createElement("span");
|
|
165
|
+
t.className = "image-resize-handle", t.dataset.corner = e, t.addEventListener("mousedown", (t) => this._onHandleMouseDown(t, e)), this.dom.appendChild(t);
|
|
166
|
+
}
|
|
167
|
+
this.dom.addEventListener("click", (e) => {
|
|
168
|
+
e.stopPropagation();
|
|
169
|
+
let t = this.getPos();
|
|
170
|
+
typeof t == "number" && this.editor.commands.setNodeSelection(t);
|
|
171
|
+
}), this._boundMouseMove = this._handleMouseMove.bind(this), this._boundMouseUp = this._handleMouseUp.bind(this);
|
|
172
|
+
}
|
|
173
|
+
selectNode() {
|
|
174
|
+
this.dom.classList.add("is-selected");
|
|
175
|
+
}
|
|
176
|
+
deselectNode() {
|
|
177
|
+
this.dom.classList.remove("is-selected");
|
|
178
|
+
}
|
|
179
|
+
_onHandleMouseDown(e, t) {
|
|
180
|
+
e.preventDefault(), e.stopPropagation(), this._activeCorner = t, this._startX = e.clientX, this._startWidth = this.img.getBoundingClientRect().width, document.addEventListener("mousemove", this._boundMouseMove), document.addEventListener("mouseup", this._boundMouseUp), document.body.style.userSelect = "none";
|
|
181
|
+
}
|
|
182
|
+
_handleMouseMove(e) {
|
|
183
|
+
let t = e.clientX - this._startX, n = this._activeCorner.includes("r") ? this._startWidth + t : this._startWidth - t;
|
|
184
|
+
n = Math.max(50, Math.round(n)), this.img.style.width = n + "px", this._pendingWidth = n;
|
|
185
|
+
}
|
|
186
|
+
_handleMouseUp() {
|
|
187
|
+
if (document.removeEventListener("mousemove", this._boundMouseMove), document.removeEventListener("mouseup", this._boundMouseUp), document.body.style.userSelect = "", this._pendingWidth !== null) {
|
|
188
|
+
let e = this.getPos();
|
|
189
|
+
typeof e == "number" && this.editor.view.dispatch(this.editor.state.tr.setNodeMarkup(e, null, {
|
|
190
|
+
...this.node.attrs,
|
|
191
|
+
width: this._pendingWidth
|
|
192
|
+
})), this._pendingWidth = null;
|
|
193
|
+
}
|
|
194
|
+
}
|
|
195
|
+
update(e) {
|
|
196
|
+
return e.type === this.node.type ? (this.node = e, this.img.src = e.attrs.src, this.img.alt = e.attrs.alt || "", e.attrs.width ? this.img.style.width = e.attrs.width + "px" : this.img.style.width = "", !0) : !1;
|
|
197
|
+
}
|
|
198
|
+
destroy() {
|
|
199
|
+
document.removeEventListener("mousemove", this._boundMouseMove), document.removeEventListener("mouseup", this._boundMouseUp), document.body.style.userSelect = "";
|
|
200
|
+
}
|
|
201
|
+
}, _ = n.create({
|
|
202
|
+
name: "image",
|
|
203
|
+
group: "inline",
|
|
204
|
+
inline: !0,
|
|
205
|
+
atom: !0,
|
|
206
|
+
draggable: !0,
|
|
207
|
+
addAttributes() {
|
|
208
|
+
return {
|
|
209
|
+
src: { default: null },
|
|
210
|
+
alt: { default: null },
|
|
211
|
+
width: { default: null }
|
|
212
|
+
};
|
|
213
|
+
},
|
|
214
|
+
parseHTML() {
|
|
215
|
+
return [{ tag: "img[src]" }];
|
|
216
|
+
},
|
|
217
|
+
renderHTML({ HTMLAttributes: e }) {
|
|
218
|
+
let t = { ...e };
|
|
219
|
+
return t.width && (t.style = `width:${t.width}px`), delete t.width, ["img", r(t)];
|
|
220
|
+
},
|
|
221
|
+
addNodeView() {
|
|
222
|
+
return (e) => new g(e);
|
|
223
|
+
},
|
|
224
|
+
addCommands() {
|
|
225
|
+
return { setImage: (e) => ({ commands: t }) => t.insertContent({
|
|
226
|
+
type: this.name,
|
|
227
|
+
attrs: e
|
|
228
|
+
}) };
|
|
229
|
+
}
|
|
230
|
+
}), v = null, y = null, b = {};
|
|
231
|
+
function x(e) {
|
|
232
|
+
if (!e || !e.type.startsWith("image/")) return;
|
|
233
|
+
let t = b.maxSize || 20 * 1024 * 1024;
|
|
234
|
+
if (e.size > t) {
|
|
235
|
+
alert(`图片大小不能超过 ${Math.round(t / 1024 / 1024)}MB`);
|
|
236
|
+
return;
|
|
237
|
+
}
|
|
238
|
+
let n = new FileReader();
|
|
239
|
+
n.onload = (e) => {
|
|
240
|
+
y.chain().focus().setImage({ src: e.target.result }).run();
|
|
241
|
+
}, n.readAsDataURL(e);
|
|
242
|
+
}
|
|
243
|
+
function S(e) {
|
|
244
|
+
let t = e.clipboardData?.items;
|
|
245
|
+
if (t) {
|
|
246
|
+
for (let n of t) if (n.type.startsWith("image/")) {
|
|
247
|
+
e.preventDefault(), x(n.getAsFile());
|
|
248
|
+
return;
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
}
|
|
252
|
+
var C = {
|
|
253
|
+
name: "insertImage",
|
|
254
|
+
toolbar: {
|
|
255
|
+
icon: "image",
|
|
256
|
+
title: "插入图片"
|
|
257
|
+
},
|
|
258
|
+
tiptapExtension: _,
|
|
259
|
+
command: () => {
|
|
260
|
+
v && v.click();
|
|
261
|
+
},
|
|
262
|
+
isActive: () => !1,
|
|
263
|
+
init(e, t) {
|
|
264
|
+
y = e, b = t, v = document.createElement("input"), v.type = "file", v.accept = t.accept || "image/png,image/jpeg,image/gif,image/webp,image/svg+xml", v.style.display = "none", document.body.appendChild(v), v.addEventListener("change", () => {
|
|
265
|
+
let e = v.files[0];
|
|
266
|
+
e && x(e), v.value = "";
|
|
267
|
+
}), e.view.dom.addEventListener("paste", S);
|
|
268
|
+
},
|
|
269
|
+
destroy() {
|
|
270
|
+
v &&= (v.remove(), null), y &&= (y.view.dom.removeEventListener("paste", S), null);
|
|
271
|
+
}
|
|
272
|
+
};
|
|
273
|
+
//#endregion
|
|
274
|
+
//#region src/plugins/placeholders.js
|
|
275
|
+
function w(e, t) {
|
|
276
|
+
return {
|
|
277
|
+
name: e,
|
|
278
|
+
toolbar: t,
|
|
279
|
+
tiptapExtension: null,
|
|
280
|
+
command: () => console.log(`[JEditor] ${t.title} — 待实现`),
|
|
281
|
+
isActive: () => !1
|
|
282
|
+
};
|
|
283
|
+
}
|
|
284
|
+
//#endregion
|
|
285
|
+
//#region src/plugins/index.js
|
|
286
|
+
var T = [
|
|
287
|
+
f,
|
|
288
|
+
p,
|
|
289
|
+
c,
|
|
290
|
+
l,
|
|
291
|
+
u,
|
|
292
|
+
d,
|
|
293
|
+
m,
|
|
294
|
+
h,
|
|
295
|
+
C,
|
|
296
|
+
...[
|
|
297
|
+
w("insert", {
|
|
298
|
+
text: "插入",
|
|
299
|
+
title: "插入",
|
|
300
|
+
dropdown: !0
|
|
301
|
+
}),
|
|
302
|
+
w("attachment", {
|
|
303
|
+
icon: "paperclip",
|
|
304
|
+
title: "附件"
|
|
305
|
+
}),
|
|
306
|
+
w("table", {
|
|
307
|
+
icon: "grid",
|
|
308
|
+
title: "表格"
|
|
309
|
+
}),
|
|
310
|
+
w("link", {
|
|
311
|
+
icon: "link",
|
|
312
|
+
title: "链接"
|
|
313
|
+
}),
|
|
314
|
+
w("mention", {
|
|
315
|
+
icon: "at-sign",
|
|
316
|
+
title: "提及"
|
|
317
|
+
}),
|
|
318
|
+
w("more", {
|
|
319
|
+
icon: "more-horizontal",
|
|
320
|
+
title: "更多"
|
|
321
|
+
}),
|
|
322
|
+
w("fullscreen", {
|
|
323
|
+
icon: "maximize-2",
|
|
324
|
+
title: "全屏"
|
|
325
|
+
}),
|
|
326
|
+
w("heading", {
|
|
327
|
+
text: "正文",
|
|
328
|
+
title: "段落样式",
|
|
329
|
+
dropdown: !0
|
|
330
|
+
}),
|
|
331
|
+
w("fontFamily", {
|
|
332
|
+
text: "微软雅黑",
|
|
333
|
+
title: "字体",
|
|
334
|
+
dropdown: !0
|
|
335
|
+
}),
|
|
336
|
+
w("fontSizeDown", {
|
|
337
|
+
icon: "minus",
|
|
338
|
+
title: "减小字号"
|
|
339
|
+
}),
|
|
340
|
+
w("fontSize", {
|
|
341
|
+
text: "14",
|
|
342
|
+
title: "字号"
|
|
343
|
+
}),
|
|
344
|
+
w("fontSizeUp", {
|
|
345
|
+
icon: "plus",
|
|
346
|
+
title: "增大字号"
|
|
347
|
+
}),
|
|
348
|
+
w("textColor", {
|
|
349
|
+
type: "color",
|
|
350
|
+
text: "A",
|
|
351
|
+
colorBar: "#ef4444",
|
|
352
|
+
title: "文字颜色"
|
|
353
|
+
}),
|
|
354
|
+
w("highlight", {
|
|
355
|
+
type: "color",
|
|
356
|
+
text: "笔",
|
|
357
|
+
colorBar: "#facc15",
|
|
358
|
+
title: "背景颜色"
|
|
359
|
+
}),
|
|
360
|
+
w("bulletList", {
|
|
361
|
+
icon: "list",
|
|
362
|
+
title: "无序列表"
|
|
363
|
+
}),
|
|
364
|
+
w("orderedList", {
|
|
365
|
+
icon: "hash",
|
|
366
|
+
title: "有序列表"
|
|
367
|
+
}),
|
|
368
|
+
w("alignLeft", {
|
|
369
|
+
icon: "align-left",
|
|
370
|
+
title: "左对齐"
|
|
371
|
+
}),
|
|
372
|
+
w("alignCenter", {
|
|
373
|
+
icon: "align-center",
|
|
374
|
+
title: "居中"
|
|
375
|
+
}),
|
|
376
|
+
w("alignRight", {
|
|
377
|
+
icon: "align-right",
|
|
378
|
+
title: "右对齐"
|
|
379
|
+
}),
|
|
380
|
+
w("lineHeight", {
|
|
381
|
+
text: "1.5",
|
|
382
|
+
title: "行间距"
|
|
383
|
+
}),
|
|
384
|
+
w("blockquote", {
|
|
385
|
+
icon: "message-square",
|
|
386
|
+
title: "引用"
|
|
387
|
+
}),
|
|
388
|
+
w("codeBlock", {
|
|
389
|
+
text: "</>",
|
|
390
|
+
title: "代码块",
|
|
391
|
+
className: "font-mono font-bold text-indigo-600"
|
|
392
|
+
})
|
|
393
|
+
]
|
|
394
|
+
];
|
|
395
|
+
//#endregion
|
|
396
|
+
//#region src/editor/index.js
|
|
397
|
+
function E(e, n = [], r = {}) {
|
|
398
|
+
return new t({
|
|
399
|
+
element: e,
|
|
400
|
+
extensions: [i.configure({ history: !0 }), ...n],
|
|
401
|
+
editorProps: { attributes: {
|
|
402
|
+
class: "tiptap-editor",
|
|
403
|
+
spellcheck: "false"
|
|
404
|
+
} },
|
|
405
|
+
content: r.content || `<p>${r.placeholder || "开始在此编写文档..."}</p>`
|
|
406
|
+
});
|
|
407
|
+
}
|
|
408
|
+
//#endregion
|
|
409
|
+
//#region src/toolbar/ui.js
|
|
410
|
+
var D = "<svg xmlns=\"http://www.w3.org/2000/svg\" width=\"14\" height=\"14\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><polyline points=\"6 9 12 15 18 9\"></polyline></svg>", O = ["je-toolbar-row je-toolbar-row--primary", "je-toolbar-row je-toolbar-row--secondary"];
|
|
411
|
+
function k(e) {
|
|
412
|
+
return e ? e.startsWith("<") ? e : window.feather?.icons[e] ? feather.icons[e].toSvg({
|
|
413
|
+
width: 20,
|
|
414
|
+
height: 20
|
|
415
|
+
}) : null : null;
|
|
416
|
+
}
|
|
417
|
+
function A(e) {
|
|
418
|
+
let t = e.toolbar, n = t.dropdown === !0;
|
|
419
|
+
if (t.type === "color") {
|
|
420
|
+
let n = document.createElement("div");
|
|
421
|
+
n.className = "je-color-group";
|
|
422
|
+
let r = document.createElement("button");
|
|
423
|
+
r.className = "tool-btn", r.dataset.command = e.name, r.title = t.title || "", r.innerHTML = `<span class="je-color-inner"><span class="je-color-char">${t.text || "A"}</span><span class="je-color-bar" style="background:${t.colorBar || "#000"}"></span></span>`;
|
|
424
|
+
let i = document.createElement("button");
|
|
425
|
+
return i.className = "tool-btn-arrow-down", i.innerHTML = D, n.append(r, i), n;
|
|
426
|
+
}
|
|
427
|
+
if (n) {
|
|
428
|
+
let n = document.createElement("button");
|
|
429
|
+
return n.className = "tool-btn-text", n.dataset.command = e.name, n.title = t.title || "", n.innerHTML = `${t.text || ""} ${D}`, n;
|
|
430
|
+
}
|
|
431
|
+
let r = document.createElement("button");
|
|
432
|
+
r.className = "tool-btn", t.className && (r.className += " " + t.className), r.dataset.command = e.name, r.title = t.shortcut ? `${t.title} (${t.shortcut})` : t.title || "";
|
|
433
|
+
let i = k(t.icon);
|
|
434
|
+
return i ? r.innerHTML = i : r.textContent = t.text || "", r;
|
|
435
|
+
}
|
|
436
|
+
function j() {
|
|
437
|
+
let e = document.createElement("div");
|
|
438
|
+
return e.className = "v-divider", e;
|
|
439
|
+
}
|
|
440
|
+
function M() {
|
|
441
|
+
let e = document.createElement("div");
|
|
442
|
+
return e.className = "je-spacer", e;
|
|
443
|
+
}
|
|
444
|
+
function N(e, t) {
|
|
445
|
+
let n = document.createDocumentFragment();
|
|
446
|
+
return e.toolbar.forEach((e, r) => {
|
|
447
|
+
let i = document.createElement("div");
|
|
448
|
+
i.className = O[r] || O[0], e.forEach((e) => {
|
|
449
|
+
if (e === "|") i.appendChild(j());
|
|
450
|
+
else if (e === "->") i.appendChild(M());
|
|
451
|
+
else {
|
|
452
|
+
let n = t.get(e);
|
|
453
|
+
n && i.appendChild(A(n));
|
|
454
|
+
}
|
|
455
|
+
}), n.appendChild(i);
|
|
456
|
+
}), n;
|
|
457
|
+
}
|
|
458
|
+
function P(e, t, n) {
|
|
459
|
+
e.querySelectorAll("[data-command]").forEach((e) => {
|
|
460
|
+
e.addEventListener("click", () => {
|
|
461
|
+
let r = n.get(e.dataset.command);
|
|
462
|
+
r && r.command(t);
|
|
463
|
+
});
|
|
464
|
+
});
|
|
465
|
+
let r = n.getAll();
|
|
466
|
+
function i() {
|
|
467
|
+
r.forEach((n) => {
|
|
468
|
+
let r = e.querySelector(`[data-command="${n.name}"]`);
|
|
469
|
+
r && (typeof n.isActive == "function" && r.classList.toggle("is-active", n.isActive(t)), typeof n.isDisabled == "function" && r.classList.toggle("is-disabled", n.isDisabled(t)));
|
|
470
|
+
});
|
|
471
|
+
}
|
|
472
|
+
t.on("selectionUpdate", i), t.on("update", i), i();
|
|
473
|
+
}
|
|
474
|
+
//#endregion
|
|
475
|
+
//#region src/jeditor.js
|
|
476
|
+
var F = class e {
|
|
477
|
+
static create(t, n = {}) {
|
|
478
|
+
let r = typeof t == "string" ? document.querySelector(t) : t;
|
|
479
|
+
if (!r) throw Error(`[JEditor] 找不到容器元素: ${t}`);
|
|
480
|
+
return new e(r, n);
|
|
481
|
+
}
|
|
482
|
+
constructor(e, t = {}) {
|
|
483
|
+
this._container = e, this._config = s(t), this._pm = new a(), this._editor = null, this._bootstrap();
|
|
484
|
+
}
|
|
485
|
+
_bootstrap() {
|
|
486
|
+
let { _container: e, _config: t, _pm: n } = this;
|
|
487
|
+
e.classList.add("je-container"), n.registerAll(T), e.appendChild(N(t, n));
|
|
488
|
+
let r = document.createElement("div");
|
|
489
|
+
r.className = "je-editor-area", e.appendChild(r), this._editor = E(r, n.getTiptapExtensions(), t), n.initAll(this._editor, t), P(e, this._editor, n);
|
|
490
|
+
}
|
|
491
|
+
getHTML() {
|
|
492
|
+
return this._editor.getHTML();
|
|
493
|
+
}
|
|
494
|
+
getJSON() {
|
|
495
|
+
return this._editor.getJSON();
|
|
496
|
+
}
|
|
497
|
+
getText() {
|
|
498
|
+
return this._editor.getText();
|
|
499
|
+
}
|
|
500
|
+
setContent(e, t = !1) {
|
|
501
|
+
this._editor.commands.setContent(e, t);
|
|
502
|
+
}
|
|
503
|
+
isEmpty() {
|
|
504
|
+
return this._editor.isEmpty;
|
|
505
|
+
}
|
|
506
|
+
focus() {
|
|
507
|
+
this._editor.commands.focus();
|
|
508
|
+
}
|
|
509
|
+
on(e, t) {
|
|
510
|
+
return this._editor.on(e, t), this;
|
|
511
|
+
}
|
|
512
|
+
off(e, t) {
|
|
513
|
+
return this._editor.off(e, t), this;
|
|
514
|
+
}
|
|
515
|
+
get tiptap() {
|
|
516
|
+
return this._editor;
|
|
517
|
+
}
|
|
518
|
+
destroy() {
|
|
519
|
+
this._pm.destroyAll(), this._editor.destroy(), this._container.innerHTML = "", this._container.classList.remove("je-container"), this._editor = null;
|
|
520
|
+
}
|
|
521
|
+
};
|
|
522
|
+
//#endregion
|
|
523
|
+
export { F as JEditor };
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
(function(e,t){typeof exports==`object`&&typeof module<`u`?t(exports,require(`@tiptap/extension-underline`),require(`@tiptap/core`),require(`@tiptap/starter-kit`)):typeof define==`function`&&define.amd?define([`exports`,`@tiptap/extension-underline`,`@tiptap/core`,`@tiptap/starter-kit`],t):(e=typeof globalThis<`u`?globalThis:e||self,t(e.JEditor={},e.TiptapUnderline,e.TiptapCore,e.StarterKit))})(this,function(e,t,n,r){Object.defineProperty(e,Symbol.toStringTag,{value:`Module`});var i=Object.create,a=Object.defineProperty,o=Object.getOwnPropertyDescriptor,s=Object.getOwnPropertyNames,c=Object.getPrototypeOf,l=Object.prototype.hasOwnProperty,u=(e,t,n,r)=>{if(t&&typeof t==`object`||typeof t==`function`)for(var i=s(t),c=0,u=i.length,d;c<u;c++)d=i[c],!l.call(e,d)&&d!==n&&a(e,d,{get:(e=>t[e]).bind(null,d),enumerable:!(r=o(t,d))||r.enumerable});return e},d=(e,t,n)=>(n=e==null?{}:i(c(e)),u(t||!e||!e.__esModule?a(n,`default`,{value:e,enumerable:!0}):n,e));t=d(t),r=d(r);var f=class{constructor(){this._plugins=new Map}register(e){if(!e.name)throw Error(`[JEditor] Plugin 缺少 name 字段`);this._plugins.set(e.name,e)}registerAll(e){e.forEach(e=>this.register(e))}get(e){return this._plugins.get(e)}getAll(){return Array.from(this._plugins.values())}getTiptapExtensions(){return this.getAll().filter(e=>e.tiptapExtension!=null).map(e=>e.tiptapExtension)}initAll(e,t={}){this.getAll().forEach(n=>{typeof n.init==`function`&&n.init(e,t[n.name]||{})})}destroyAll(){this.getAll().forEach(e=>{typeof e.destroy==`function`&&e.destroy()}),this._plugins.clear()}},p={placeholder:`开始在此编写文档...`,toolbar:[[`undo`,`redo`,`|`,`insertImage`,`insert`,`|`,`attachment`,`table`,`link`,`mention`,`|`,`more`,`->`,`fullscreen`],`heading.|.fontFamily.|.fontSizeDown.fontSize.fontSizeUp.|.bold.italic.underline.strike.clearFormat.|.textColor.highlight.|.bulletList.orderedList.alignLeft.alignCenter.alignRight.lineHeight.|.blockquote.codeBlock`.split(`.`)],image:{maxSize:20*1024*1024,uploadUrl:null,accept:`image/png,image/jpeg,image/gif,image/webp,image/svg+xml`}};function m(e={}){let t={...p,...e};return e.image&&(t.image={...p.image,...e.image}),t}var h={name:`bold`,toolbar:{text:`B`,title:`粗体`,shortcut:`Ctrl+B`,className:`font-bold`},tiptapExtension:null,command:e=>e.chain().focus().toggleBold().run(),isActive:e=>e.isActive(`bold`)},g={name:`italic`,toolbar:{text:`I`,title:`斜体`,shortcut:`Ctrl+I`,className:`italic`},tiptapExtension:null,command:e=>e.chain().focus().toggleItalic().run(),isActive:e=>e.isActive(`italic`)},_={name:`underline`,toolbar:{text:`U`,title:`下划线`,shortcut:`Ctrl+U`,className:`underline`},tiptapExtension:t.default,command:e=>e.chain().focus().toggleUnderline().run(),isActive:e=>e.isActive(`underline`)},v={name:`strike`,toolbar:{text:`S`,title:`删除线`,shortcut:`Ctrl+Shift+X`,className:`line-through text-[13px]`},tiptapExtension:null,command:e=>e.chain().focus().toggleStrike().run(),isActive:e=>e.isActive(`strike`)},y={name:`undo`,toolbar:{icon:`<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" fill="currentColor">
|
|
2
|
+
<path d="M6.25 3.75 2.5 6.25l3.75 2.5V6.875h5.938a4.062 4.062 0 1 1 0 8.125H8.125a.625.625 0 1 0 0 1.25h4.063a5.313 5.313 0 0 0 0-10.625H6.25z"></path>
|
|
3
|
+
</svg>`,title:`撤销`,shortcut:`Ctrl+Z`},tiptapExtension:null,command:e=>e.chain().focus().undo().run(),isActive:()=>!1,isDisabled:e=>!e.can().undo()},b={name:`redo`,toolbar:{icon:`<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" fill="currentColor" style="transform:scaleX(-1)">
|
|
4
|
+
<path d="M6.25 3.75 2.5 6.25l3.75 2.5V6.875h5.938a4.062 4.062 0 1 1 0 8.125H8.125a.625.625 0 1 0 0 1.25h4.063a5.313 5.313 0 0 0 0-10.625H6.25z"></path>
|
|
5
|
+
</svg>`,title:`重做`,shortcut:`Ctrl+Shift+Z`},tiptapExtension:null,command:e=>e.chain().focus().redo().run(),isActive:()=>!1,isDisabled:e=>!e.can().redo()},x={name:`clearFormat`,toolbar:{icon:`slash`,title:`清除格式`},tiptapExtension:null,command:e=>e.chain().focus().unsetAllMarks().run(),isActive:()=>!1},S={name:`formatPainter`,toolbar:{icon:`edit-3`,title:`格式刷`},tiptapExtension:null,command:()=>console.log(`[JEditor] 格式刷功能待实现`),isActive:()=>!1},C=class{constructor({node:e,editor:t,getPos:n}){this.node=e,this.editor=t,this.getPos=n,this._startX=0,this._startWidth=0,this._pendingWidth=null,this._activeCorner=null,this.dom=document.createElement(`span`),this.dom.className=`image-node-wrapper`,this.dom.contentEditable=`false`,this.img=document.createElement(`img`),this.img.src=e.attrs.src,this.img.alt=e.attrs.alt||``,this.img.draggable=!1,e.attrs.width&&(this.img.style.width=e.attrs.width+`px`),this.dom.appendChild(this.img);for(let e of[`tl`,`tr`,`bl`,`br`]){let t=document.createElement(`span`);t.className=`image-resize-handle`,t.dataset.corner=e,t.addEventListener(`mousedown`,t=>this._onHandleMouseDown(t,e)),this.dom.appendChild(t)}this.dom.addEventListener(`click`,e=>{e.stopPropagation();let t=this.getPos();typeof t==`number`&&this.editor.commands.setNodeSelection(t)}),this._boundMouseMove=this._handleMouseMove.bind(this),this._boundMouseUp=this._handleMouseUp.bind(this)}selectNode(){this.dom.classList.add(`is-selected`)}deselectNode(){this.dom.classList.remove(`is-selected`)}_onHandleMouseDown(e,t){e.preventDefault(),e.stopPropagation(),this._activeCorner=t,this._startX=e.clientX,this._startWidth=this.img.getBoundingClientRect().width,document.addEventListener(`mousemove`,this._boundMouseMove),document.addEventListener(`mouseup`,this._boundMouseUp),document.body.style.userSelect=`none`}_handleMouseMove(e){let t=e.clientX-this._startX,n=this._activeCorner.includes(`r`)?this._startWidth+t:this._startWidth-t;n=Math.max(50,Math.round(n)),this.img.style.width=n+`px`,this._pendingWidth=n}_handleMouseUp(){if(document.removeEventListener(`mousemove`,this._boundMouseMove),document.removeEventListener(`mouseup`,this._boundMouseUp),document.body.style.userSelect=``,this._pendingWidth!==null){let e=this.getPos();typeof e==`number`&&this.editor.view.dispatch(this.editor.state.tr.setNodeMarkup(e,null,{...this.node.attrs,width:this._pendingWidth})),this._pendingWidth=null}}update(e){return e.type===this.node.type?(this.node=e,this.img.src=e.attrs.src,this.img.alt=e.attrs.alt||``,e.attrs.width?this.img.style.width=e.attrs.width+`px`:this.img.style.width=``,!0):!1}destroy(){document.removeEventListener(`mousemove`,this._boundMouseMove),document.removeEventListener(`mouseup`,this._boundMouseUp),document.body.style.userSelect=``}},w=n.Node.create({name:`image`,group:`inline`,inline:!0,atom:!0,draggable:!0,addAttributes(){return{src:{default:null},alt:{default:null},width:{default:null}}},parseHTML(){return[{tag:`img[src]`}]},renderHTML({HTMLAttributes:e}){let t={...e};return t.width&&(t.style=`width:${t.width}px`),delete t.width,[`img`,(0,n.mergeAttributes)(t)]},addNodeView(){return e=>new C(e)},addCommands(){return{setImage:e=>({commands:t})=>t.insertContent({type:this.name,attrs:e})}}}),T=null,E=null,D={};function O(e){if(!e||!e.type.startsWith(`image/`))return;let t=D.maxSize||20*1024*1024;if(e.size>t){alert(`图片大小不能超过 ${Math.round(t/1024/1024)}MB`);return}let n=new FileReader;n.onload=e=>{E.chain().focus().setImage({src:e.target.result}).run()},n.readAsDataURL(e)}function k(e){let t=e.clipboardData?.items;if(t){for(let n of t)if(n.type.startsWith(`image/`)){e.preventDefault(),O(n.getAsFile());return}}}var A={name:`insertImage`,toolbar:{icon:`image`,title:`插入图片`},tiptapExtension:w,command:()=>{T&&T.click()},isActive:()=>!1,init(e,t){E=e,D=t,T=document.createElement(`input`),T.type=`file`,T.accept=t.accept||`image/png,image/jpeg,image/gif,image/webp,image/svg+xml`,T.style.display=`none`,document.body.appendChild(T),T.addEventListener(`change`,()=>{let e=T.files[0];e&&O(e),T.value=``}),e.view.dom.addEventListener(`paste`,k)},destroy(){T&&=(T.remove(),null),E&&=(E.view.dom.removeEventListener(`paste`,k),null)}};function j(e,t){return{name:e,toolbar:t,tiptapExtension:null,command:()=>console.log(`[JEditor] ${t.title} — 待实现`),isActive:()=>!1}}var M=[y,b,h,g,_,v,x,S,A,...[j(`insert`,{text:`插入`,title:`插入`,dropdown:!0}),j(`attachment`,{icon:`paperclip`,title:`附件`}),j(`table`,{icon:`grid`,title:`表格`}),j(`link`,{icon:`link`,title:`链接`}),j(`mention`,{icon:`at-sign`,title:`提及`}),j(`more`,{icon:`more-horizontal`,title:`更多`}),j(`fullscreen`,{icon:`maximize-2`,title:`全屏`}),j(`heading`,{text:`正文`,title:`段落样式`,dropdown:!0}),j(`fontFamily`,{text:`微软雅黑`,title:`字体`,dropdown:!0}),j(`fontSizeDown`,{icon:`minus`,title:`减小字号`}),j(`fontSize`,{text:`14`,title:`字号`}),j(`fontSizeUp`,{icon:`plus`,title:`增大字号`}),j(`textColor`,{type:`color`,text:`A`,colorBar:`#ef4444`,title:`文字颜色`}),j(`highlight`,{type:`color`,text:`笔`,colorBar:`#facc15`,title:`背景颜色`}),j(`bulletList`,{icon:`list`,title:`无序列表`}),j(`orderedList`,{icon:`hash`,title:`有序列表`}),j(`alignLeft`,{icon:`align-left`,title:`左对齐`}),j(`alignCenter`,{icon:`align-center`,title:`居中`}),j(`alignRight`,{icon:`align-right`,title:`右对齐`}),j(`lineHeight`,{text:`1.5`,title:`行间距`}),j(`blockquote`,{icon:`message-square`,title:`引用`}),j(`codeBlock`,{text:`</>`,title:`代码块`,className:`font-mono font-bold text-indigo-600`})]];function N(e,t=[],i={}){return new n.Editor({element:e,extensions:[r.default.configure({history:!0}),...t],editorProps:{attributes:{class:`tiptap-editor`,spellcheck:`false`}},content:i.content||`<p>${i.placeholder||`开始在此编写文档...`}</p>`})}var P=`<svg xmlns="http://www.w3.org/2000/svg" width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="6 9 12 15 18 9"></polyline></svg>`,F=[`je-toolbar-row je-toolbar-row--primary`,`je-toolbar-row je-toolbar-row--secondary`];function I(e){return e?e.startsWith(`<`)?e:window.feather?.icons[e]?feather.icons[e].toSvg({width:20,height:20}):null:null}function L(e){let t=e.toolbar,n=t.dropdown===!0;if(t.type===`color`){let n=document.createElement(`div`);n.className=`je-color-group`;let r=document.createElement(`button`);r.className=`tool-btn`,r.dataset.command=e.name,r.title=t.title||``,r.innerHTML=`<span class="je-color-inner"><span class="je-color-char">${t.text||`A`}</span><span class="je-color-bar" style="background:${t.colorBar||`#000`}"></span></span>`;let i=document.createElement(`button`);return i.className=`tool-btn-arrow-down`,i.innerHTML=P,n.append(r,i),n}if(n){let n=document.createElement(`button`);return n.className=`tool-btn-text`,n.dataset.command=e.name,n.title=t.title||``,n.innerHTML=`${t.text||``} ${P}`,n}let r=document.createElement(`button`);r.className=`tool-btn`,t.className&&(r.className+=` `+t.className),r.dataset.command=e.name,r.title=t.shortcut?`${t.title} (${t.shortcut})`:t.title||``;let i=I(t.icon);return i?r.innerHTML=i:r.textContent=t.text||``,r}function R(){let e=document.createElement(`div`);return e.className=`v-divider`,e}function z(){let e=document.createElement(`div`);return e.className=`je-spacer`,e}function B(e,t){let n=document.createDocumentFragment();return e.toolbar.forEach((e,r)=>{let i=document.createElement(`div`);i.className=F[r]||F[0],e.forEach(e=>{if(e===`|`)i.appendChild(R());else if(e===`->`)i.appendChild(z());else{let n=t.get(e);n&&i.appendChild(L(n))}}),n.appendChild(i)}),n}function V(e,t,n){e.querySelectorAll(`[data-command]`).forEach(e=>{e.addEventListener(`click`,()=>{let r=n.get(e.dataset.command);r&&r.command(t)})});let r=n.getAll();function i(){r.forEach(n=>{let r=e.querySelector(`[data-command="${n.name}"]`);r&&(typeof n.isActive==`function`&&r.classList.toggle(`is-active`,n.isActive(t)),typeof n.isDisabled==`function`&&r.classList.toggle(`is-disabled`,n.isDisabled(t)))})}t.on(`selectionUpdate`,i),t.on(`update`,i),i()}e.JEditor=class e{static create(t,n={}){let r=typeof t==`string`?document.querySelector(t):t;if(!r)throw Error(`[JEditor] 找不到容器元素: ${t}`);return new e(r,n)}constructor(e,t={}){this._container=e,this._config=m(t),this._pm=new f,this._editor=null,this._bootstrap()}_bootstrap(){let{_container:e,_config:t,_pm:n}=this;e.classList.add(`je-container`),n.registerAll(M),e.appendChild(B(t,n));let r=document.createElement(`div`);r.className=`je-editor-area`,e.appendChild(r),this._editor=N(r,n.getTiptapExtensions(),t),n.initAll(this._editor,t),V(e,this._editor,n)}getHTML(){return this._editor.getHTML()}getJSON(){return this._editor.getJSON()}getText(){return this._editor.getText()}setContent(e,t=!1){this._editor.commands.setContent(e,t)}isEmpty(){return this._editor.isEmpty}focus(){this._editor.commands.focus()}on(e,t){return this._editor.on(e,t),this}off(e,t){return this._editor.off(e,t),this}get tiptap(){return this._editor}destroy(){this._pm.destroyAll(),this._editor.destroy(),this._container.innerHTML=``,this._container.classList.remove(`je-container`),this._editor=null}}});
|
package/package.json
ADDED
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@jenkin-a/jeditor",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"description": "JEditor - 腾讯系办公风格富文本编辑器",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"main": "dist/jeditor.umd.js",
|
|
7
|
+
"module": "dist/jeditor.es.js",
|
|
8
|
+
"exports": {
|
|
9
|
+
".": {
|
|
10
|
+
"import": "./dist/jeditor.es.js",
|
|
11
|
+
"require": "./dist/jeditor.umd.js"
|
|
12
|
+
},
|
|
13
|
+
"./dist/jeditor.css": "./dist/jeditor.css"
|
|
14
|
+
},
|
|
15
|
+
"files": [
|
|
16
|
+
"dist"
|
|
17
|
+
],
|
|
18
|
+
"publishConfig": {
|
|
19
|
+
"access": "public"
|
|
20
|
+
},
|
|
21
|
+
"scripts": {
|
|
22
|
+
"dev": "vite",
|
|
23
|
+
"build": "vite build",
|
|
24
|
+
"preview": "vite preview"
|
|
25
|
+
},
|
|
26
|
+
"keywords": [
|
|
27
|
+
"editor",
|
|
28
|
+
"rich-text",
|
|
29
|
+
"tiptap",
|
|
30
|
+
"wysiwyg"
|
|
31
|
+
],
|
|
32
|
+
"author": "jenkin",
|
|
33
|
+
"license": "MIT",
|
|
34
|
+
"peerDependencies": {
|
|
35
|
+
"@tiptap/core": "^3.0.0",
|
|
36
|
+
"@tiptap/starter-kit": "^3.0.0",
|
|
37
|
+
"@tiptap/extension-underline": "^3.0.0",
|
|
38
|
+
"@tiptap/extension-image": "^3.0.0",
|
|
39
|
+
"@tiptap/pm": "^3.0.0"
|
|
40
|
+
},
|
|
41
|
+
"devDependencies": {
|
|
42
|
+
"@tiptap/core": "^3.20.4",
|
|
43
|
+
"@tiptap/extension-image": "^3.20.4",
|
|
44
|
+
"@tiptap/extension-underline": "^3.20.4",
|
|
45
|
+
"@tiptap/pm": "^3.20.4",
|
|
46
|
+
"@tiptap/starter-kit": "^3.20.4",
|
|
47
|
+
"vite": "^8.0.1"
|
|
48
|
+
}
|
|
49
|
+
}
|