@tiptap/vue-3 3.0.0-next.4 → 3.0.0-next.6

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/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@tiptap/vue-3",
3
3
  "description": "Vue components for tiptap",
4
- "version": "3.0.0-next.4",
4
+ "version": "3.0.0-next.6",
5
5
  "homepage": "https://tiptap.dev",
6
6
  "keywords": [
7
7
  "tiptap",
@@ -20,6 +20,14 @@
20
20
  },
21
21
  "import": "./dist/index.js",
22
22
  "require": "./dist/index.cjs"
23
+ },
24
+ "./menus": {
25
+ "types": {
26
+ "import": "./dist/menus/index.d.ts",
27
+ "require": "./dist/menus/index.d.cts"
28
+ },
29
+ "import": "./dist/menus/index.js",
30
+ "require": "./dist/menus/index.cjs"
23
31
  }
24
32
  },
25
33
  "main": "dist/index.cjs",
@@ -30,18 +38,18 @@
30
38
  "src",
31
39
  "dist"
32
40
  ],
33
- "dependencies": {
34
- "@tiptap/extension-bubble-menu": "^3.0.0-next.4",
35
- "@tiptap/extension-floating-menu": "^3.0.0-next.4"
36
- },
37
41
  "devDependencies": {
38
- "@tiptap/core": "^3.0.0-next.4",
39
- "@tiptap/pm": "^3.0.0-next.4",
42
+ "@tiptap/core": "^3.0.0-next.6",
43
+ "@tiptap/pm": "^3.0.0-next.6",
40
44
  "vue": "^3.5.13"
41
45
  },
46
+ "optionalDependencies": {
47
+ "@tiptap/extension-bubble-menu": "^3.0.0-next.6",
48
+ "@tiptap/extension-floating-menu": "^3.0.0-next.6"
49
+ },
42
50
  "peerDependencies": {
43
- "@tiptap/core": "^3.0.0-next.1",
44
- "@tiptap/pm": "^3.0.0-next.1",
51
+ "@tiptap/core": "^3.0.0-next.4",
52
+ "@tiptap/pm": "^3.0.0-next.4",
45
53
  "vue": "^3.0.0",
46
54
  "@floating-ui/dom": "^1.0.0"
47
55
  },
package/src/Editor.ts CHANGED
@@ -1,5 +1,5 @@
1
1
  /* eslint-disable react-hooks/rules-of-hooks */
2
- import { Editor as CoreEditor, EditorOptions } from '@tiptap/core'
2
+ import { Editor as CoreEditor, EditorOptions, Storage } from '@tiptap/core'
3
3
  import { EditorState, Plugin, PluginKey } from '@tiptap/pm/state'
4
4
  import { AppContext, ComponentInternalInstance, ComponentPublicInstance, customRef, markRaw, Ref } from 'vue'
5
5
 
@@ -32,7 +32,7 @@ export type ContentComponent = ComponentInternalInstance & {
32
32
  export class Editor extends CoreEditor {
33
33
  private reactiveState: Ref<EditorState>
34
34
 
35
- private reactiveExtensionStorage: Ref<Record<string, any>>
35
+ private reactiveExtensionStorage: Ref<Storage>
36
36
 
37
37
  public contentComponent: ContentComponent | null = null
38
38
 
@@ -32,10 +32,11 @@ export const EditorContent = defineComponent({
32
32
 
33
33
  if (editor && editor.options.element && rootEl.value) {
34
34
  nextTick(() => {
35
- if (!rootEl.value || !editor.options.element.firstChild) {
35
+ if (!rootEl.value || !editor.options.element?.firstChild) {
36
36
  return
37
37
  }
38
38
 
39
+ // TODO using the new editor.mount method might allow us to remove this
39
40
  const element = unref(rootEl.value)
40
41
 
41
42
  rootEl.value.append(...editor.options.element.childNodes)
@@ -0,0 +1,112 @@
1
+ /* eslint-disable no-underscore-dangle */
2
+ import { MarkView, MarkViewProps, MarkViewRenderer, MarkViewRendererOptions } from '@tiptap/core'
3
+ import { Component, defineComponent, h, PropType } from 'vue'
4
+
5
+ import { Editor } from './Editor.js'
6
+ import { VueRenderer } from './VueRenderer.js'
7
+
8
+ export interface VueMarkViewRendererOptions extends MarkViewRendererOptions {
9
+ as?: string
10
+ className?: string
11
+ attrs?: { [key: string]: string }
12
+ }
13
+
14
+ export const markViewProps = {
15
+ editor: {
16
+ type: Object as PropType<MarkViewProps['editor']>,
17
+ required: true as const,
18
+ },
19
+ mark: {
20
+ type: Object as PropType<MarkViewProps['mark']>,
21
+ required: true as const,
22
+ },
23
+ extension: {
24
+ type: Object as PropType<MarkViewProps['extension']>,
25
+ required: true as const,
26
+ },
27
+ inline: {
28
+ type: Boolean as PropType<MarkViewProps['inline']>,
29
+ required: true as const,
30
+ },
31
+ view: {
32
+ type: Object as PropType<MarkViewProps['view']>,
33
+ required: true as const,
34
+ },
35
+ }
36
+
37
+ export const MarkViewContent = defineComponent({
38
+ name: 'MarkViewContent',
39
+
40
+ props: {
41
+ as: {
42
+ type: String,
43
+ default: 'span',
44
+ },
45
+ },
46
+
47
+ render() {
48
+ return h(this.as, {
49
+ style: {
50
+ whiteSpace: 'inherit',
51
+ },
52
+ 'data-mark-view-content': '',
53
+ })
54
+ },
55
+ })
56
+
57
+ export class VueMarkView extends MarkView<Component, VueMarkViewRendererOptions> {
58
+ renderer: VueRenderer
59
+
60
+ constructor(component: Component, props: MarkViewProps, options?: Partial<VueMarkViewRendererOptions>) {
61
+ super(component, props, options)
62
+
63
+ // Create extended component with provide
64
+ const extendedComponent = defineComponent({
65
+ extends: { ...component },
66
+ props: Object.keys(props),
67
+ template: (this.component as any).template,
68
+ setup: reactiveProps => {
69
+ return (component as any).setup?.(reactiveProps, {
70
+ expose: () => undefined,
71
+ })
72
+ },
73
+ // Add support for scoped styles
74
+ __scopeId: (component as any).__scopeId,
75
+ __cssModules: (component as any).__cssModules,
76
+ __name: (component as any).__name,
77
+ __file: (component as any).__file,
78
+ })
79
+ this.renderer = new VueRenderer(extendedComponent, {
80
+ editor: this.editor,
81
+ props,
82
+ })
83
+ }
84
+
85
+ get dom() {
86
+ return this.renderer.element as HTMLElement
87
+ }
88
+
89
+ get contentDOM() {
90
+ return this.dom.querySelector('[data-mark-view-content]') as HTMLElement | null
91
+ }
92
+
93
+ destroy() {
94
+ this.renderer.destroy()
95
+ }
96
+ }
97
+
98
+ export function VueMarkViewRenderer(
99
+ component: Component,
100
+ options: Partial<VueMarkViewRendererOptions> = {},
101
+ ): MarkViewRenderer {
102
+ return props => {
103
+ // try to get the parent component
104
+ // this is important for vue devtools to show the component hierarchy correctly
105
+ // maybe it’s `undefined` because <editor-content> isn’t rendered yet
106
+ if (!(props.editor as Editor).contentComponent) {
107
+ return {} as unknown as MarkView<any, any>
108
+ }
109
+
110
+ return new VueMarkView(component, props, options)
111
+ }
112
+ }
@@ -40,6 +40,18 @@ export const nodeViewProps = {
40
40
  type: Function as PropType<NodeViewProps['deleteNode']>,
41
41
  required: true as const,
42
42
  },
43
+ view: {
44
+ type: Object as PropType<NodeViewProps['view']>,
45
+ required: true as const,
46
+ },
47
+ innerDecorations: {
48
+ type: Object as PropType<NodeViewProps['innerDecorations']>,
49
+ required: true as const,
50
+ },
51
+ HTMLAttributes: {
52
+ type: Object as PropType<NodeViewProps['HTMLAttributes']>,
53
+ required: true as const,
54
+ },
43
55
  }
44
56
 
45
57
  export interface VueNodeViewRendererOptions extends NodeViewRendererOptions {
package/src/index.ts CHANGED
@@ -1,10 +1,9 @@
1
- export * from './BubbleMenu.js'
2
1
  export { Editor } from './Editor.js'
3
2
  export * from './EditorContent.js'
4
- export * from './FloatingMenu.js'
5
3
  export * from './NodeViewContent.js'
6
4
  export * from './NodeViewWrapper.js'
7
5
  export * from './useEditor.js'
6
+ export * from './VueMarkViewRenderer.js'
8
7
  export * from './VueNodeViewRenderer.js'
9
8
  export * from './VueRenderer.js'
10
9
  export * from '@tiptap/core'
@@ -0,0 +1,2 @@
1
+ export * from './BubbleMenu.js'
2
+ export * from './FloatingMenu.js'
File without changes
File without changes