@meta-1/editor 0.0.27

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.
Files changed (130) hide show
  1. package/README.md +458 -0
  2. package/package.json +100 -0
  3. package/src/editor/constants.tsx +66 -0
  4. package/src/editor/container.css +46 -0
  5. package/src/editor/control/character-count/index.tsx +39 -0
  6. package/src/editor/control/drag-handle/index.tsx +85 -0
  7. package/src/editor/control/drag-handle/use.content.actions.ts +71 -0
  8. package/src/editor/control/drag-handle/use.data.ts +29 -0
  9. package/src/editor/control/drag-handle/use.handle.id.ts +6 -0
  10. package/src/editor/control/index.tsx +35 -0
  11. package/src/editor/editor.css +626 -0
  12. package/src/editor/extension/block-quote-figure/BlockquoteFigure.ts +73 -0
  13. package/src/editor/extension/block-quote-figure/Quote/Quote.ts +31 -0
  14. package/src/editor/extension/block-quote-figure/Quote/index.ts +1 -0
  15. package/src/editor/extension/block-quote-figure/QuoteCaption/QuoteCaption.ts +54 -0
  16. package/src/editor/extension/block-quote-figure/QuoteCaption/index.ts +1 -0
  17. package/src/editor/extension/block-quote-figure/index.ts +1 -0
  18. package/src/editor/extension/document/index.ts +5 -0
  19. package/src/editor/extension/figcaption/Figcaption.ts +90 -0
  20. package/src/editor/extension/figcaption/index.ts +1 -0
  21. package/src/editor/extension/figure/Figure.ts +62 -0
  22. package/src/editor/extension/figure/index.ts +1 -0
  23. package/src/editor/extension/font-size/FontSize.ts +64 -0
  24. package/src/editor/extension/font-size/index.ts +1 -0
  25. package/src/editor/extension/global-drag-handle/clipboard-serializer.ts +28 -0
  26. package/src/editor/extension/global-drag-handle/index.ts +377 -0
  27. package/src/editor/extension/heading/index.ts +13 -0
  28. package/src/editor/extension/horizontal-rule/HorizontalRule.ts +10 -0
  29. package/src/editor/extension/horizontal-rule/index.ts +1 -0
  30. package/src/editor/extension/image/index.ts +5 -0
  31. package/src/editor/extension/image-block/ImageBlock.ts +103 -0
  32. package/src/editor/extension/image-block/components/ImageBlockMenu.tsx +100 -0
  33. package/src/editor/extension/image-block/components/ImageBlockView.tsx +47 -0
  34. package/src/editor/extension/image-block/components/ImageBlockWidth.tsx +40 -0
  35. package/src/editor/extension/image-block/index.ts +1 -0
  36. package/src/editor/extension/image-upload/ImageUpload.ts +58 -0
  37. package/src/editor/extension/image-upload/index.ts +1 -0
  38. package/src/editor/extension/image-upload/view/ImageUpload.tsx +27 -0
  39. package/src/editor/extension/image-upload/view/ImageUploader.tsx +64 -0
  40. package/src/editor/extension/image-upload/view/hooks.ts +109 -0
  41. package/src/editor/extension/image-upload/view/index.tsx +1 -0
  42. package/src/editor/extension/index.ts +30 -0
  43. package/src/editor/extension/link/Link.ts +39 -0
  44. package/src/editor/extension/link/index.ts +1 -0
  45. package/src/editor/extension/multi-column/Column.ts +33 -0
  46. package/src/editor/extension/multi-column/Columns.ts +65 -0
  47. package/src/editor/extension/multi-column/index.ts +2 -0
  48. package/src/editor/extension/multi-column/menus/ColumnsMenu.tsx +82 -0
  49. package/src/editor/extension/multi-column/menus/index.ts +1 -0
  50. package/src/editor/extension/selection/Selection.ts +36 -0
  51. package/src/editor/extension/selection/index.ts +1 -0
  52. package/src/editor/extension/slash-command/MenuList.tsx +145 -0
  53. package/src/editor/extension/slash-command/groups.ts +153 -0
  54. package/src/editor/extension/slash-command/index.ts +277 -0
  55. package/src/editor/extension/slash-command/types.ts +25 -0
  56. package/src/editor/extension/table/Cell.ts +126 -0
  57. package/src/editor/extension/table/Header.ts +89 -0
  58. package/src/editor/extension/table/Row.ts +8 -0
  59. package/src/editor/extension/table/Table.ts +9 -0
  60. package/src/editor/extension/table/index.ts +4 -0
  61. package/src/editor/extension/table/menus/TableColumn/index.tsx +73 -0
  62. package/src/editor/extension/table/menus/TableColumn/utils.ts +38 -0
  63. package/src/editor/extension/table/menus/TableRow/index.tsx +74 -0
  64. package/src/editor/extension/table/menus/TableRow/utils.ts +38 -0
  65. package/src/editor/extension/table/menus/index.tsx +2 -0
  66. package/src/editor/extension/table/utils.ts +258 -0
  67. package/src/editor/extension/task-item/index.ts +1 -0
  68. package/src/editor/extension/task-item/task-item.ts +225 -0
  69. package/src/editor/extension/task-list/index.ts +1 -0
  70. package/src/editor/extension/task-list/task-list.ts +81 -0
  71. package/src/editor/extension/trailing-node/index.ts +1 -0
  72. package/src/editor/extension/trailing-node/trailing-node.ts +70 -0
  73. package/src/editor/extension/unique-id/index.ts +1 -0
  74. package/src/editor/extension/unique-id/uniqueId.ts +123 -0
  75. package/src/editor/hooks.ts +264 -0
  76. package/src/editor/index.tsx +53 -0
  77. package/src/editor/menus/LinkMenu/LinkMenu.tsx +75 -0
  78. package/src/editor/menus/LinkMenu/index.tsx +1 -0
  79. package/src/editor/menus/TextMenu/TextMenu.tsx +193 -0
  80. package/src/editor/menus/TextMenu/components/AIDropdown.tsx +140 -0
  81. package/src/editor/menus/TextMenu/components/ContentTypePicker.tsx +76 -0
  82. package/src/editor/menus/TextMenu/components/EditLinkPopover.tsx +25 -0
  83. package/src/editor/menus/TextMenu/components/FontFamilyPicker.tsx +84 -0
  84. package/src/editor/menus/TextMenu/components/FontSizePicker.tsx +56 -0
  85. package/src/editor/menus/TextMenu/hooks/useTextmenuCommands.ts +96 -0
  86. package/src/editor/menus/TextMenu/hooks/useTextmenuContentTypes.ts +86 -0
  87. package/src/editor/menus/TextMenu/hooks/useTextmenuStates.ts +50 -0
  88. package/src/editor/menus/TextMenu/index.tsx +2 -0
  89. package/src/editor/menus/types.ts +21 -0
  90. package/src/editor/panels/Colorpicker/ColorButton.tsx +35 -0
  91. package/src/editor/panels/Colorpicker/Colorpicker.tsx +67 -0
  92. package/src/editor/panels/Colorpicker/index.tsx +2 -0
  93. package/src/editor/panels/LinkEditorPanel/LinkEditorPanel.tsx +76 -0
  94. package/src/editor/panels/LinkEditorPanel/index.tsx +1 -0
  95. package/src/editor/panels/LinkPreviewPanel/LinkPreviewPanel.tsx +32 -0
  96. package/src/editor/panels/LinkPreviewPanel/index.tsx +1 -0
  97. package/src/editor/panels/index.tsx +3 -0
  98. package/src/editor/types.tsx +38 -0
  99. package/src/editor/ui/Button/Button.tsx +70 -0
  100. package/src/editor/ui/Button/index.tsx +2 -0
  101. package/src/editor/ui/Dropdown/Dropdown.tsx +39 -0
  102. package/src/editor/ui/Dropdown/index.tsx +1 -0
  103. package/src/editor/ui/Icon.tsx +21 -0
  104. package/src/editor/ui/Loader/Loader.tsx +39 -0
  105. package/src/editor/ui/Loader/index.ts +1 -0
  106. package/src/editor/ui/Loader/types.ts +7 -0
  107. package/src/editor/ui/Panel/index.tsx +109 -0
  108. package/src/editor/ui/PopoverMenu.tsx +127 -0
  109. package/src/editor/ui/Spinner/Spinner.tsx +10 -0
  110. package/src/editor/ui/Spinner/index.tsx +1 -0
  111. package/src/editor/ui/Surface.tsx +27 -0
  112. package/src/editor/ui/Textarea/Textarea.tsx +20 -0
  113. package/src/editor/ui/Textarea/index.tsx +1 -0
  114. package/src/editor/ui/Toggle/Toggle.tsx +39 -0
  115. package/src/editor/ui/Toggle/index.tsx +1 -0
  116. package/src/editor/ui/Toolbar.tsx +107 -0
  117. package/src/editor/ui/Tooltip/index.tsx +77 -0
  118. package/src/editor/ui/Tooltip/types.ts +17 -0
  119. package/src/editor/utils/cssVar.ts +14 -0
  120. package/src/editor/utils/getRenderContainer.ts +39 -0
  121. package/src/editor/utils/index.ts +16 -0
  122. package/src/editor/utils/isCustomNodeSelected.ts +47 -0
  123. package/src/editor/utils/isTextSelected.ts +25 -0
  124. package/src/editor/utils/locale.ts +5 -0
  125. package/src/editor/viewer/index.tsx +26 -0
  126. package/src/globals.css +1 -0
  127. package/src/index.ts +7 -0
  128. package/src/locales/en-us.ts +133 -0
  129. package/src/locales/zh-cn.ts +133 -0
  130. package/src/locales/zh-tw.ts +133 -0
package/README.md ADDED
@@ -0,0 +1,458 @@
1
+ # @meta-1/editor - 富文本编辑器
2
+
3
+ 基于 Tiptap 构建的现代化富文本编辑器组件库,提供完整的编辑功能和灵活的扩展系统。
4
+
5
+ ## ✨ 特性
6
+
7
+ - ✏️ **富文本编辑** - 完整的文本编辑功能
8
+ - 🔌 **扩展系统** - 灵活的插件架构,易于扩展
9
+ - 🎨 **自定义样式** - 可定制的外观和主题
10
+ - 📝 **Markdown 支持** - 支持 Markdown 语法快捷输入
11
+ - 🌍 **国际化** - 内置多语言支持(中文、英文)
12
+ - 🎯 **类型安全** - 完整的 TypeScript 支持
13
+ - 📱 **响应式** - 适配桌面和移动端
14
+ - ⚡ **高性能** - 基于 ProseMirror,性能优异
15
+ - 🎭 **多种工具栏** - 支持固定工具栏、气泡菜单、斜杠命令
16
+
17
+ ## 📦 安装
18
+
19
+ ```bash
20
+ npm install @meta-1/editor
21
+ # 或
22
+ pnpm add @meta-1/editor
23
+ # 或
24
+ yarn add @meta-1/editor
25
+ ```
26
+
27
+ ### 依赖安装
28
+
29
+ 确保安装必要的依赖:
30
+
31
+ ```bash
32
+ pnpm add react react-dom @tiptap/react @tiptap/core
33
+ ```
34
+
35
+ ## 🚀 快速开始
36
+
37
+ ### 基础用法
38
+
39
+ ```tsx
40
+ import { Editor } from '@meta-1/editor';
41
+
42
+ export default function MyEditor() {
43
+ return (
44
+ <Editor
45
+ content="<p>开始编辑...</p>"
46
+ onChange={(html) => console.log(html)}
47
+ />
48
+ );
49
+ }
50
+ ```
51
+
52
+ ### 完整示例
53
+
54
+ ```tsx
55
+ import { Editor } from '@meta-1/editor';
56
+ import { useState } from 'react';
57
+
58
+ export default function MyEditor() {
59
+ const [content, setContent] = useState('<p>初始内容</p>');
60
+
61
+ return (
62
+ <Editor
63
+ content={content}
64
+ placeholder="输入内容..."
65
+ editable={true}
66
+ onUpdate={({ editor }) => {
67
+ const html = editor.getHTML();
68
+ setContent(html);
69
+ }}
70
+ />
71
+ );
72
+ }
73
+ ```
74
+
75
+ ## 🎨 功能特性
76
+
77
+ ### 文本格式
78
+
79
+ - **粗体** - `Ctrl/Cmd + B`
80
+ - *斜体* - `Ctrl/Cmd + I`
81
+ - <u>下划线</u> - `Ctrl/Cmd + U`
82
+ - ~~删除线~~ - `Ctrl/Cmd + Shift + X`
83
+ - `行内代码` - `Ctrl/Cmd + E`
84
+ - 上标和下标
85
+
86
+ ### 段落格式
87
+
88
+ - 标题 1-6 - `Ctrl/Cmd + Alt + 1-6`
89
+ - 引用块 - `Ctrl/Cmd + Shift + B`
90
+ - 代码块 - `Ctrl/Cmd + Alt + C`
91
+ - 水平分割线
92
+
93
+ ### 列表
94
+
95
+ - 有序列表 - `Ctrl/Cmd + Shift + 7`
96
+ - 无序列表 - `Ctrl/Cmd + Shift + 8`
97
+ - 任务列表
98
+
99
+ ### 富媒体
100
+
101
+ - 图片插入和调整大小
102
+ - 链接插入和编辑
103
+ - 表格创建和编辑
104
+ - 视频嵌入(可选)
105
+
106
+ ### 高级功能
107
+
108
+ - 文本颜色和背景色
109
+ - 文本对齐(左、中、右、两端)
110
+ - 字体系列
111
+ - 拖拽排序
112
+ - 代码高亮(支持多种语言)
113
+
114
+ ## 🔧 配置选项
115
+
116
+ ### Props
117
+
118
+ ```tsx
119
+ interface EditorProps {
120
+ // 内容
121
+ content?: string; // HTML 或 JSON 格式的内容
122
+
123
+ // 配置
124
+ placeholder?: string; // 占位符文本
125
+ editable?: boolean; // 是否可编辑
126
+ extensions?: Extension[]; // 自定义扩展
127
+
128
+ // 回调
129
+ onUpdate?: (props: { editor: Editor }) => void;
130
+ onChange?: (html: string) => void;
131
+ onBlur?: () => void;
132
+ onFocus?: () => void;
133
+
134
+ // 国际化
135
+ locale?: Locale; // 语言配置
136
+
137
+ // 样式
138
+ className?: string;
139
+ }
140
+ ```
141
+
142
+ ### 基础配置
143
+
144
+ ```tsx
145
+ <Editor
146
+ content="<p>初始内容</p>"
147
+ placeholder="开始输入..."
148
+ editable={true}
149
+ className="min-h-[300px]"
150
+ />
151
+ ```
152
+
153
+ ### 自定义扩展
154
+
155
+ ```tsx
156
+ import { Editor } from '@meta-1/editor';
157
+ import { Mention } from '@tiptap/extension-mention';
158
+
159
+ <Editor
160
+ extensions={[
161
+ Mention.configure({
162
+ // 配置 @提及 功能
163
+ }),
164
+ ]}
165
+ />
166
+ ```
167
+
168
+ ## 🌍 国际化
169
+
170
+ ### 使用中文
171
+
172
+ ```tsx
173
+ import { Editor } from '@meta-1/editor';
174
+ import zhCN from '@meta-1/editor/locales/zh-cn';
175
+
176
+ <Editor locale={zhCN} />
177
+ ```
178
+
179
+ ### 使用英文
180
+
181
+ ```tsx
182
+ import { Editor } from '@meta-1/editor';
183
+ import enUS from '@meta-1/editor/locales/en-us';
184
+
185
+ <Editor locale={enUS} />
186
+ ```
187
+
188
+ ### 支持的语言
189
+
190
+ - 简体中文 (`zh-cn`)
191
+ - 繁体中文 (`zh-tw`)
192
+ - 英文 (`en-us`)
193
+
194
+ ## 📝 内容格式
195
+
196
+ ### HTML 格式
197
+
198
+ ```tsx
199
+ const htmlContent = '<p>Hello <strong>World</strong></p>';
200
+
201
+ <Editor
202
+ content={htmlContent}
203
+ onChange={(html) => console.log(html)}
204
+ />
205
+ ```
206
+
207
+ ### JSON 格式
208
+
209
+ ```tsx
210
+ const jsonContent = {
211
+ type: 'doc',
212
+ content: [
213
+ {
214
+ type: 'paragraph',
215
+ content: [{ type: 'text', text: 'Hello World' }]
216
+ }
217
+ ]
218
+ };
219
+
220
+ <Editor
221
+ content={jsonContent}
222
+ onUpdate={({ editor }) => {
223
+ const json = editor.getJSON();
224
+ console.log(json);
225
+ }}
226
+ />
227
+ ```
228
+
229
+ ## 🎯 常见用例
230
+
231
+ ### 评论编辑器
232
+
233
+ ```tsx
234
+ import { Editor } from '@meta-1/editor';
235
+
236
+ export function CommentEditor() {
237
+ return (
238
+ <Editor
239
+ placeholder="写下你的评论..."
240
+ extensions={[
241
+ // 只启用基础功能
242
+ ]}
243
+ className="min-h-[100px]"
244
+ />
245
+ );
246
+ }
247
+ ```
248
+
249
+ ### 文章编辑器
250
+
251
+ ```tsx
252
+ import { Editor } from '@meta-1/editor';
253
+
254
+ export function ArticleEditor() {
255
+ return (
256
+ <Editor
257
+ placeholder="开始写作..."
258
+ extensions={[
259
+ // 启用所有功能
260
+ ]}
261
+ className="min-h-[500px]"
262
+ />
263
+ );
264
+ }
265
+ ```
266
+
267
+ ### 只读模式
268
+
269
+ ```tsx
270
+ <Editor
271
+ content={article.content}
272
+ editable={false}
273
+ />
274
+ ```
275
+
276
+ ## 🎨 样式定制
277
+
278
+ ### 自定义样式
279
+
280
+ ```tsx
281
+ <Editor
282
+ className="my-custom-editor"
283
+ content={content}
284
+ />
285
+ ```
286
+
287
+ ```css
288
+ .my-custom-editor {
289
+ /* 自定义编辑器样式 */
290
+ }
291
+
292
+ .my-custom-editor .ProseMirror {
293
+ /* 自定义编辑区域样式 */
294
+ min-height: 300px;
295
+ padding: 1rem;
296
+ }
297
+ ```
298
+
299
+ ### 主题支持
300
+
301
+ 编辑器自动适配明暗主题:
302
+
303
+ ```tsx
304
+ import { ThemeProvider } from 'next-themes';
305
+
306
+ <ThemeProvider>
307
+ <Editor content={content} />
308
+ </ThemeProvider>
309
+ ```
310
+
311
+ ## 📚 高级功能
312
+
313
+ ### 获取编辑器实例
314
+
315
+ ```tsx
316
+ import { useEditor } from '@tiptap/react';
317
+ import StarterKit from '@tiptap/starter-kit';
318
+
319
+ function MyEditor() {
320
+ const editor = useEditor({
321
+ extensions: [StarterKit],
322
+ content: '<p>Hello World</p>',
323
+ });
324
+
325
+ // 使用编辑器实例
326
+ const getContent = () => {
327
+ const html = editor?.getHTML();
328
+ const json = editor?.getJSON();
329
+ return { html, json };
330
+ };
331
+
332
+ return <EditorContent editor={editor} />;
333
+ }
334
+ ```
335
+
336
+ ### 自定义工具栏
337
+
338
+ ```tsx
339
+ import { Editor } from '@meta-1/editor';
340
+
341
+ <Editor
342
+ content={content}
343
+ toolbar={{
344
+ // 自定义工具栏配置
345
+ }}
346
+ />
347
+ ```
348
+
349
+ ### 图片上传
350
+
351
+ ```tsx
352
+ <Editor
353
+ content={content}
354
+ onImageUpload={async (file) => {
355
+ // 上传图片到服务器
356
+ const url = await uploadImage(file);
357
+ return url;
358
+ }}
359
+ />
360
+ ```
361
+
362
+ ### 协作编辑(可选)
363
+
364
+ ```tsx
365
+ import { Editor } from '@meta-1/editor';
366
+ import { Collaboration } from '@tiptap/extension-collaboration';
367
+
368
+ <Editor
369
+ extensions={[
370
+ Collaboration.configure({
371
+ // 配置协作编辑
372
+ }),
373
+ ]}
374
+ />
375
+ ```
376
+
377
+ ## 🔌 扩展开发
378
+
379
+ ### 创建自定义扩展
380
+
381
+ ```tsx
382
+ import { Extension } from '@tiptap/core';
383
+
384
+ const CustomExtension = Extension.create({
385
+ name: 'customExtension',
386
+
387
+ addOptions() {
388
+ return {
389
+ // 扩展选项
390
+ };
391
+ },
392
+
393
+ addCommands() {
394
+ return {
395
+ // 自定义命令
396
+ };
397
+ },
398
+ });
399
+
400
+ <Editor
401
+ extensions={[CustomExtension]}
402
+ />
403
+ ```
404
+
405
+ ## 📖 API 参考
406
+
407
+ ### Editor 方法
408
+
409
+ ```tsx
410
+ // 获取内容
411
+ editor.getHTML() // 获取 HTML 格式
412
+ editor.getJSON() // 获取 JSON 格式
413
+ editor.getText() // 获取纯文本
414
+
415
+ // 设置内容
416
+ editor.commands.setContent(content)
417
+
418
+ // 命令
419
+ editor.commands.toggleBold()
420
+ editor.commands.toggleItalic()
421
+ editor.commands.setHeading({ level: 1 })
422
+ editor.commands.insertContent('<p>Hello</p>')
423
+
424
+ // 判断状态
425
+ editor.isActive('bold')
426
+ editor.isActive('heading', { level: 1 })
427
+
428
+ // 清空内容
429
+ editor.commands.clearContent()
430
+
431
+ // 焦点控制
432
+ editor.commands.focus()
433
+ editor.commands.blur()
434
+ ```
435
+
436
+ ## 🧪 测试
437
+
438
+ ```bash
439
+ # 运行测试
440
+ pnpm test
441
+
442
+ # 运行测试覆盖率
443
+ pnpm test:cov
444
+ ```
445
+
446
+ ## 🤝 贡献
447
+
448
+ 欢迎贡献代码、报告问题或提出建议!
449
+
450
+ ## 📄 许可证
451
+
452
+ MIT
453
+
454
+ ## 🔗 相关链接
455
+
456
+ - [Tiptap 文档](https://tiptap.dev/)
457
+ - [ProseMirror](https://prosemirror.net/)
458
+ - [示例网站](https://editor.example.com)
package/package.json ADDED
@@ -0,0 +1,100 @@
1
+ {
2
+ "name": "@meta-1/editor",
3
+ "version": "0.0.27",
4
+ "keywords": [
5
+ "easykit",
6
+ "tailwindcss",
7
+ "react",
8
+ "editor",
9
+ "tiptap"
10
+ ],
11
+ "description": "Easy kit editor",
12
+ "author": "Grant <284885069@qq.com>",
13
+ "homepage": "https://github.com/zkit-org",
14
+ "license": "MIT",
15
+ "repository": {
16
+ "type": "git",
17
+ "url": "https://github.com/zkit-org/packages.git"
18
+ },
19
+ "type": "module",
20
+ "dependencies": {
21
+ "@tiptap/core": "2.9.1",
22
+ "@tiptap/extension-bubble-menu": "2.9.1",
23
+ "@tiptap/extension-bullet-list": "2.9.1",
24
+ "@tiptap/extension-character-count": "2.9.1",
25
+ "@tiptap/extension-code-block": "2.9.1",
26
+ "@tiptap/extension-code-block-lowlight": "2.9.1",
27
+ "@tiptap/extension-color": "2.9.1",
28
+ "@tiptap/extension-document": "2.9.1",
29
+ "@tiptap/extension-dropcursor": "2.9.1",
30
+ "@tiptap/extension-focus": "2.9.1",
31
+ "@tiptap/extension-font-family": "2.9.1",
32
+ "@tiptap/extension-heading": "2.9.1",
33
+ "@tiptap/extension-highlight": "2.9.1",
34
+ "@tiptap/extension-horizontal-rule": "2.9.1",
35
+ "@tiptap/extension-image": "2.9.1",
36
+ "@tiptap/extension-link": "2.9.1",
37
+ "@tiptap/extension-ordered-list": "2.9.1",
38
+ "@tiptap/extension-paragraph": "2.9.1",
39
+ "@tiptap/extension-placeholder": "2.9.1",
40
+ "@tiptap/extension-subscript": "2.9.1",
41
+ "@tiptap/extension-superscript": "2.9.1",
42
+ "@tiptap/extension-table": "2.9.1",
43
+ "@tiptap/extension-table-header": "2.9.1",
44
+ "@tiptap/extension-table-row": "2.9.1",
45
+ "@tiptap/extension-text": "2.9.1",
46
+ "@tiptap/extension-text-align": "2.9.1",
47
+ "@tiptap/extension-text-style": "2.9.1",
48
+ "@tiptap/extension-typography": "2.9.1",
49
+ "@tiptap/extension-underline": "2.9.1",
50
+ "@tiptap/extension-history": "2.9.1",
51
+ "@tiptap/pm": "2.9.1",
52
+ "@tiptap/react": "2.9.1",
53
+ "@tiptap/starter-kit": "2.9.1",
54
+ "@tiptap/suggestion": "2.9.1",
55
+ "lowlight": "3.1.0",
56
+ "tippy.js": "6.3.7",
57
+ "uuid": "10.0.0",
58
+ "lucide-react": "0.400.0",
59
+ "@radix-ui/react-dropdown-menu": "2.1.1",
60
+ "@radix-ui/react-popover": "1.1.1",
61
+ "@radix-ui/react-slot": "1.1.0",
62
+ "rb-tippyjs-react": "4.3.1",
63
+ "nanoid": "5.0.9",
64
+ "react-colorful": "5.6.1",
65
+ "clsx": "2.1.1",
66
+ "interactjs": "^1.10.27",
67
+ "tailwind-merge": "2.3.0"
68
+ },
69
+ "devDependencies": {
70
+ "@types/uuid": "10.0.0"
71
+ },
72
+ "module": "./src/index.ts",
73
+ "types": "./src/index.ts",
74
+ "exports": {
75
+ ".": {
76
+ "types": "./src/index.ts",
77
+ "default": "./src/index.ts"
78
+ },
79
+ "./locales/zh-cn": {
80
+ "types": "./src/locales/zh-cn.ts",
81
+ "default": "./src/locales/zh-cn.ts"
82
+ },
83
+ "./locales/zh-tw": {
84
+ "types": "./src/locales/zh-tw.ts",
85
+ "default": "./src/locales/zh-tw.ts"
86
+ },
87
+ "./locales/en-us": {
88
+ "types": "./src/locales/en-us.ts",
89
+ "default": "./src/locales/en-us.ts"
90
+ }
91
+ },
92
+ "publishConfig": {
93
+ "access": "public"
94
+ },
95
+ "files": [
96
+ "/src",
97
+ "package.json",
98
+ "README.md"
99
+ ]
100
+ }
@@ -0,0 +1,66 @@
1
+ import type { AiToneOption, LanguageOption } from "./types";
2
+
3
+ export const languages: LanguageOption[] = [
4
+ { name: "arabic", label: "Arabic", value: "ar" as LanguageOption["value"] },
5
+ { name: "chinese", label: "Chinese", value: "zh" as LanguageOption["value"] },
6
+ { name: "english", label: "English", value: "en" as LanguageOption["value"] },
7
+ { name: "french", label: "French", value: "fr" as LanguageOption["value"] },
8
+ { name: "german", label: "German", value: "de" as LanguageOption["value"] },
9
+ { name: "greek", label: "Greek", value: "gr" as LanguageOption["value"] },
10
+ { name: "italian", label: "Italian", value: "it" as LanguageOption["value"] },
11
+ { name: "japanese", label: "Japanese", value: "jp" as LanguageOption["value"] },
12
+ { name: "korean", label: "Korean", value: "ko" as LanguageOption["value"] },
13
+ { name: "russian", label: "Russian", value: "ru" as LanguageOption["value"] },
14
+ { name: "spanish", label: "Spanish", value: "es" as LanguageOption["value"] },
15
+ { name: "swedish", label: "Swedish", value: "sv" as LanguageOption["value"] },
16
+ { name: "ukrainian", label: "Ukrainian", value: "ua" as LanguageOption["value"] },
17
+ ];
18
+
19
+ export const tones: AiToneOption[] = [
20
+ { name: "academic", label: "Academic", value: "academic" },
21
+ { name: "business", label: "Business", value: "business" },
22
+ { name: "casual", label: "Casual", value: "casual" },
23
+ { name: "childfriendly", label: "Childfriendly", value: "childfriendly" },
24
+ { name: "conversational", label: "Conversational", value: "conversational" },
25
+ { name: "emotional", label: "Emotional", value: "emotional" },
26
+ { name: "humorous", label: "Humorous", value: "humorous" },
27
+ { name: "informative", label: "Informative", value: "informative" },
28
+ { name: "inspirational", label: "Inspirational", value: "inspirational" },
29
+ { name: "memeify", label: "Memeify", value: "meme" },
30
+ { name: "narrative", label: "Narrative", value: "narrative" },
31
+ { name: "objective", label: "Objective", value: "objective" },
32
+ { name: "persuasive", label: "Persuasive", value: "persuasive" },
33
+ { name: "poetic", label: "Poetic", value: "poetic" },
34
+ ];
35
+
36
+ export const userNames = [
37
+ "Lea Thompson",
38
+ "Cyndi Lauper",
39
+ "Tom Cruise",
40
+ "Madonna",
41
+ "Jerry Hall",
42
+ "Joan Collins",
43
+ "Winona Ryder",
44
+ "Christina Applegate",
45
+ "Alyssa Milano",
46
+ "Molly Ringwald",
47
+ "Ally Sheedy",
48
+ "Debbie Harry",
49
+ "Olivia Newton-John",
50
+ "Elton John",
51
+ "Michael J. Fox",
52
+ "Axl Rose",
53
+ "Emilio Estevez",
54
+ "Ralph Macchio",
55
+ "Rob Lowe",
56
+ "Jennifer Grey",
57
+ "Mickey Rourke",
58
+ "John Cusack",
59
+ "Matthew Broderick",
60
+ "Justine Bateman",
61
+ "Lisa Bonet",
62
+ ];
63
+
64
+ export const userColors = ["#fb7185", "#fdba74", "#d9f99d", "#a7f3d0", "#a5f3fc", "#a5b4fc", "#f0abfc"];
65
+
66
+ export const themeColors = ["#fb7185", "#fdba74", "#d9f99d", "#a7f3d0", "#a5f3fc", "#a5b4fc"];
@@ -0,0 +1,46 @@
1
+ @import "../globals.css";
2
+
3
+ .editor-container {
4
+ @apply w-full relative;
5
+ }
6
+ .editor-container .readonly {
7
+ .ProseMirror
8
+ [data-type="horizontalRule"]:hover:not(.ProseMirror [data-type="horizontalRule"].ProseMirror-selectednode) {
9
+ @apply bg-transparent cursor-default;
10
+ }
11
+ }
12
+
13
+ .editor-container .editor .tiptap {
14
+ @apply outline-none pt-[1px] -mt-[1px] caret-foreground;
15
+ p.is-empty::before {
16
+ color: var(--muted-foreground);
17
+ opacity: 0.5;
18
+ content: attr(data-placeholder);
19
+ float: left;
20
+ height: 0;
21
+ pointer-events: none;
22
+ }
23
+
24
+ blockquote.is-empty:before {
25
+ color: var(--muted-foreground);
26
+ opacity: 0.5;
27
+ content: attr(data-placeholder);
28
+ }
29
+
30
+ blockquote + figcaption.is-empty:before {
31
+ color: var(--muted-foreground);
32
+ opacity: 0.5;
33
+ content: attr(data-placeholder);
34
+ }
35
+
36
+ td,
37
+ li {
38
+ p.is-empty::before {
39
+ content: none;
40
+ }
41
+ }
42
+
43
+ p {
44
+ @apply leading-7;
45
+ }
46
+ }
@@ -0,0 +1,39 @@
1
+ import type { FC } from "react";
2
+ import type { Editor } from "@tiptap/react";
3
+
4
+ export type CharacterCountControlProps = {
5
+ editor: Editor;
6
+ limit: number;
7
+ };
8
+
9
+ export const CharacterCountControl: FC<CharacterCountControlProps> = (props) => {
10
+ const { editor, limit } = props;
11
+ if (!editor) return null;
12
+
13
+ const percentage = editor ? Math.round((100 / limit) * editor.storage.characterCount.characters()) : 0;
14
+
15
+ return (
16
+ <div
17
+ className={`character-count ${editor.storage.characterCount.characters() === limit ? "character-count--warning" : ""}`}
18
+ >
19
+ <svg height="20" viewBox="0 0 20 20" width="20">
20
+ <title>字符计数进度环</title>
21
+ <circle cx="10" cy="10" fill="#e9ecef" r="10" />
22
+ <circle
23
+ cx="10"
24
+ cy="10"
25
+ fill="transparent"
26
+ r="5"
27
+ stroke="currentColor"
28
+ strokeDasharray={`calc(${percentage} * 31.4 / 100) 31.4`}
29
+ strokeWidth="10"
30
+ transform="rotate(-90) translate(-20)"
31
+ />
32
+ <circle cx="10" cy="10" fill="white" r="6" />
33
+ </svg>
34
+ {editor.storage.characterCount.characters()} / {limit} characters
35
+ <br />
36
+ {editor.storage.characterCount.words()} words
37
+ </div>
38
+ );
39
+ };