@witchcraft/editor 0.2.0 → 0.2.1
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/README.md +1 -0
- package/dist/module.d.mts +1 -1
- package/dist/module.json +1 -1
- package/dist/module.mjs +2 -2
- package/dist/runtime/pm/features/Base/plugins/debugSelectionPlugin.d.ts +1 -5
- package/dist/runtime/pm/features/Base/plugins/debugSelectionPlugin.js +43 -17
- package/dist/runtime/pm/features/CodeBlock/components/CodeBlockView.vue +0 -1
- package/dist/runtime/pm/features/Collaboration/createCollaborationPlugins.js +4 -1
- package/dist/runtime/pm/features/DocumentApi/composables/useEditorContent.js +6 -2
- package/dist/runtime/pm/features/Link/components/BubbleMenuExternalLink.vue +0 -2
- package/dist/runtime/pm/features/Link/components/BubbleMenuInternalLink.vue +0 -1
- package/package.json +7 -7
- package/src/module.ts +3 -3
- package/src/runtime/pm/features/Base/plugins/debugSelectionPlugin.ts +53 -28
- package/src/runtime/pm/features/CodeBlock/components/CodeBlockView.vue +0 -1
- package/src/runtime/pm/features/Collaboration/createCollaborationPlugins.ts +5 -2
- package/src/runtime/pm/features/DocumentApi/composables/useEditorContent.ts +6 -2
- package/src/runtime/pm/features/Link/components/BubbleMenuExternalLink.vue +0 -2
- package/src/runtime/pm/features/Link/components/BubbleMenuInternalLink.vue +0 -1
- package/src/runtime/pm/utils/generator/createPsuedoSentence.ts +1 -1
package/README.md
CHANGED
|
@@ -54,6 +54,7 @@ The components library explains how to configure anything, you just need to add
|
|
|
54
54
|
//without Nuxt:
|
|
55
55
|
@import "@witchcraft/ui/utils.css";
|
|
56
56
|
@import "@witchcraft/ui/base.css";
|
|
57
|
+
@import "@witchcraft/ui/animations.css";
|
|
57
58
|
// source used components
|
|
58
59
|
@source "/path/to/node_modules/@witchcraft/ui/src/runtime/components";
|
|
59
60
|
|
package/dist/module.d.mts
CHANGED
package/dist/module.json
CHANGED
package/dist/module.mjs
CHANGED
|
@@ -10,7 +10,7 @@ const module$1 = defineNuxtModule({
|
|
|
10
10
|
configKey: "witchcraftEditor"
|
|
11
11
|
},
|
|
12
12
|
defaults: {
|
|
13
|
-
_playgroundWorkaround:
|
|
13
|
+
_playgroundWorkaround: void 0
|
|
14
14
|
},
|
|
15
15
|
moduleDependencies: {
|
|
16
16
|
"@witchcraft/ui/nuxt": {
|
|
@@ -36,7 +36,7 @@ const module$1 = defineNuxtModule({
|
|
|
36
36
|
addTemplate({
|
|
37
37
|
filename: "witchcraft-editor.css",
|
|
38
38
|
write: true,
|
|
39
|
-
getContents: () => options._playgroundWorkaround ? crop`
|
|
39
|
+
getContents: () => options._playgroundWorkaround === "@witchcraft/editor" ? crop`
|
|
40
40
|
@import "${resolve("./runtime/assets/base.css")}";
|
|
41
41
|
@import "${resolve("./runtime/assets/utils.css")}";
|
|
42
42
|
@source "${resolve("./runtime/components")}";
|
|
@@ -1,9 +1,5 @@
|
|
|
1
1
|
import type { Editor } from "@tiptap/core";
|
|
2
2
|
import { Plugin, PluginKey } from "@tiptap/pm/state";
|
|
3
3
|
export declare const debugSelectionPluginKey: PluginKey<any>;
|
|
4
|
-
/**
|
|
5
|
-
* Sets the window title to the current selection for debugging in development mode (by checking import.meta.dev).
|
|
6
|
-
*
|
|
7
|
-
* For embedded editors, adds the selection as `[from - to]`.
|
|
8
|
-
*/
|
|
4
|
+
/** Renders a floating tooltip directly above the selection point in dev mode only. */
|
|
9
5
|
export declare const debugSelectionPlugin: (editor: Editor, log?: boolean) => Plugin;
|
|
@@ -1,47 +1,73 @@
|
|
|
1
1
|
import { Plugin, PluginKey } from "@tiptap/pm/state";
|
|
2
|
+
import { Decoration, DecorationSet } from "@tiptap/pm/view";
|
|
2
3
|
import { isEmbeddedBlock } from "../../EmbeddedDocument/utils/isEmbeddedBlock.js";
|
|
3
|
-
const ROOT_SELECTION_REGEX = /([0-9 -]*)(\[|$)/;
|
|
4
|
+
const ROOT_SELECTION_REGEX = /(DEBUG: [0-9 -]*)(\[|$)/;
|
|
4
5
|
const SUB_SELECTION_REGEX = /(\[[0-9 -]*\])/;
|
|
5
6
|
export const debugSelectionPluginKey = new PluginKey("debugSelection");
|
|
6
7
|
export const debugSelectionPlugin = (editor, log = false) => {
|
|
7
8
|
let initialized = false;
|
|
9
|
+
let currentDisplayString = "";
|
|
8
10
|
return new Plugin({
|
|
9
11
|
key: debugSelectionPluginKey,
|
|
10
12
|
state: {
|
|
11
13
|
init() {
|
|
14
|
+
return DecorationSet.empty;
|
|
12
15
|
},
|
|
13
|
-
apply(tr) {
|
|
14
|
-
if (!import.meta.dev)
|
|
15
|
-
return;
|
|
16
|
-
}
|
|
16
|
+
apply(tr, oldSet) {
|
|
17
|
+
if (!import.meta.dev) return oldSet.map(tr.mapping, tr.doc);
|
|
17
18
|
const sel = `${tr.selection.from} - ${tr.selection.to}`;
|
|
18
19
|
if (isEmbeddedBlock(editor.view)) {
|
|
19
|
-
if (log) {
|
|
20
|
-
|
|
21
|
-
}
|
|
22
|
-
const hasEmbeddedSelection = document.title.match(SUB_SELECTION_REGEX);
|
|
20
|
+
if (log) console.log(`embedded selection: ${sel}`);
|
|
21
|
+
const hasEmbeddedSelection = currentDisplayString.match(SUB_SELECTION_REGEX);
|
|
23
22
|
if (hasEmbeddedSelection) {
|
|
24
|
-
|
|
23
|
+
currentDisplayString = currentDisplayString.replace(
|
|
25
24
|
SUB_SELECTION_REGEX,
|
|
26
25
|
`[${sel}]`
|
|
27
26
|
);
|
|
28
27
|
} else {
|
|
29
|
-
|
|
28
|
+
const prefix = currentDisplayString.startsWith("DEBUG: ") ? "" : "DEBUG: ";
|
|
29
|
+
currentDisplayString = `${prefix}${currentDisplayString} [${sel}]`;
|
|
30
30
|
}
|
|
31
31
|
} else {
|
|
32
|
-
if (log) {
|
|
33
|
-
console.log(`root selection: ${tr.selection.from} - ${tr.selection.to}`);
|
|
34
|
-
}
|
|
32
|
+
if (log) console.log(`root selection: ${sel}`);
|
|
35
33
|
if (!initialized) {
|
|
36
34
|
initialized = true;
|
|
37
|
-
|
|
35
|
+
currentDisplayString = `DEBUG: ${sel}`;
|
|
38
36
|
} else {
|
|
39
|
-
|
|
37
|
+
currentDisplayString = currentDisplayString.replace(
|
|
40
38
|
ROOT_SELECTION_REGEX,
|
|
41
|
-
|
|
39
|
+
`DEBUG: ${sel} $2`
|
|
42
40
|
);
|
|
43
41
|
}
|
|
44
42
|
}
|
|
43
|
+
const widget = document.createElement("div");
|
|
44
|
+
Object.assign(widget.style, {
|
|
45
|
+
position: "absolute",
|
|
46
|
+
top: "110%",
|
|
47
|
+
right: "0",
|
|
48
|
+
zIndex: "100",
|
|
49
|
+
padding: "2px 6px",
|
|
50
|
+
fontSize: "10px",
|
|
51
|
+
fontFamily: "monospace",
|
|
52
|
+
color: "white",
|
|
53
|
+
backgroundColor: "rgba(0, 0, 0, 0.7)",
|
|
54
|
+
borderRadius: "2px",
|
|
55
|
+
pointerEvents: "none",
|
|
56
|
+
whiteSpace: "nowrap",
|
|
57
|
+
lineHeight: "1"
|
|
58
|
+
});
|
|
59
|
+
widget.textContent = currentDisplayString;
|
|
60
|
+
const deco = Decoration.widget(tr.selection.to, widget, {
|
|
61
|
+
side: -1,
|
|
62
|
+
// Ensure it stays to the left of the cursor
|
|
63
|
+
key: "debug-selection-tooltip"
|
|
64
|
+
});
|
|
65
|
+
return DecorationSet.create(tr.doc, [deco]);
|
|
66
|
+
}
|
|
67
|
+
},
|
|
68
|
+
props: {
|
|
69
|
+
decorations(state) {
|
|
70
|
+
return debugSelectionPluginKey.getState(state);
|
|
45
71
|
}
|
|
46
72
|
}
|
|
47
73
|
});
|
|
@@ -20,7 +20,6 @@
|
|
|
20
20
|
ref="codeBlockLangPickerEl"
|
|
21
21
|
>
|
|
22
22
|
<!-- and here we only style everything but the suggestions so the input matches the code block background -->
|
|
23
|
-
<!-- @vue-expect-error -->
|
|
24
23
|
<WSimpleInput
|
|
25
24
|
:border="false"
|
|
26
25
|
wrapper-class="lang-picker-input flex-nowrap z-10"
|
|
@@ -9,7 +9,10 @@ export function createCollaborationPlugins(options, schema, getConnectedEditors)
|
|
|
9
9
|
const storage = {
|
|
10
10
|
isDisabled: false
|
|
11
11
|
};
|
|
12
|
-
const fragment = options.fragment ? options.fragment : options.document
|
|
12
|
+
const fragment = options.fragment ? options.fragment : options.document?.getXmlFragment(options.field);
|
|
13
|
+
if (!fragment) {
|
|
14
|
+
throw new Error("No fragment or document provided.");
|
|
15
|
+
}
|
|
13
16
|
const yUndoPluginInstance = yUndoPlugin(options.yUndoOptions);
|
|
14
17
|
const originalUndoPluginView = yUndoPluginInstance.spec.view;
|
|
15
18
|
yUndoPluginInstance.spec.view = (view) => {
|
|
@@ -25,7 +25,11 @@ export function useEditorContent(editor, content, id, documentApi, recreate) {
|
|
|
25
25
|
let attached = false;
|
|
26
26
|
async function load(changed) {
|
|
27
27
|
if (content.value) {
|
|
28
|
-
editor.value
|
|
28
|
+
if (!editor.value) {
|
|
29
|
+
recreate((options) => ({ ...options, content: content.value }));
|
|
30
|
+
} else {
|
|
31
|
+
editor.value?.commands.setContent(content.value);
|
|
32
|
+
}
|
|
29
33
|
} else if (documentApi) {
|
|
30
34
|
if (changed && id.value) {
|
|
31
35
|
await documentApi.load({ docId: id.value });
|
|
@@ -65,7 +69,7 @@ export function useEditorContent(editor, content, id, documentApi, recreate) {
|
|
|
65
69
|
if (oldId !== void 0 && newId !== oldId && documentApi) {
|
|
66
70
|
unload(oldId);
|
|
67
71
|
await load(true);
|
|
68
|
-
} else if (_newContent) {
|
|
72
|
+
} else if (_newContent !== _oldContent && _newContent) {
|
|
69
73
|
await load(false);
|
|
70
74
|
}
|
|
71
75
|
}, { deep: false });
|
|
@@ -4,7 +4,6 @@
|
|
|
4
4
|
ref="el"
|
|
5
5
|
>
|
|
6
6
|
<div class="flex flex-col gap-1">
|
|
7
|
-
<!-- @vue-expect-error -->
|
|
8
7
|
<WSimpleInput
|
|
9
8
|
class="text-input"
|
|
10
9
|
wrapper-class="flex flex-nowrap gap-1"
|
|
@@ -24,7 +23,6 @@
|
|
|
24
23
|
</WLabel>
|
|
25
24
|
</template>
|
|
26
25
|
</WSimpleInput>
|
|
27
|
-
<!-- @vue-expect-error -->
|
|
28
26
|
<WSimpleInput
|
|
29
27
|
class="link-input"
|
|
30
28
|
wrapper-class="flex flex-nowrap gap-1"
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@witchcraft/editor",
|
|
3
3
|
"description": "Block base prosemirror editor with partial/full editable document embeds, infinite embeds, and document uploads.",
|
|
4
|
-
"version": "0.2.
|
|
4
|
+
"version": "0.2.1",
|
|
5
5
|
"main": "./dist/runtime/main.lib.js",
|
|
6
6
|
"type": "module",
|
|
7
7
|
"sideEffects": false,
|
|
@@ -94,7 +94,7 @@
|
|
|
94
94
|
"@tiptap/pm": "^3.12.0",
|
|
95
95
|
"@tiptap/vue-3": "^3.12.0",
|
|
96
96
|
"@tiptap/y-tiptap": "^3.0.1",
|
|
97
|
-
"@witchcraft/ui": "^0.3.
|
|
97
|
+
"@witchcraft/ui": "^0.3.25",
|
|
98
98
|
"tailwindcss": "^4.1.17",
|
|
99
99
|
"vue": "^3.5.25"
|
|
100
100
|
},
|
|
@@ -111,7 +111,7 @@
|
|
|
111
111
|
},
|
|
112
112
|
"dependencies": {
|
|
113
113
|
"@alanscodelog/eslint-config": "^6.3.1",
|
|
114
|
-
"@alanscodelog/utils": "^6.0
|
|
114
|
+
"@alanscodelog/utils": "^6.2.0",
|
|
115
115
|
"@commitlint/cli": "^20.1.0",
|
|
116
116
|
"@faker-js/faker": "^10.0.0",
|
|
117
117
|
"@fortawesome/fontawesome-svg-core": "^7.0.1",
|
|
@@ -121,7 +121,7 @@
|
|
|
121
121
|
"@nuxt/eslint-config": "^1.11.0",
|
|
122
122
|
"@tiptap/html": "^3.12.0",
|
|
123
123
|
"@witchcraft/nuxt-utils": "^0.3.6",
|
|
124
|
-
"@witchcraft/ui": "^0.3.
|
|
124
|
+
"@witchcraft/ui": "^0.3.25",
|
|
125
125
|
"colord": "^2.9.3",
|
|
126
126
|
"defu": "^6.1.4",
|
|
127
127
|
"highlight.js": "^11.11.1",
|
|
@@ -137,8 +137,8 @@
|
|
|
137
137
|
},
|
|
138
138
|
"devDependencies": {
|
|
139
139
|
"@alanscodelog/commitlint-config": "^3.1.2",
|
|
140
|
-
"@alanscodelog/semantic-release-config": "^6.0.
|
|
141
|
-
"@alanscodelog/tsconfigs": "^6.
|
|
140
|
+
"@alanscodelog/semantic-release-config": "^6.0.2",
|
|
141
|
+
"@alanscodelog/tsconfigs": "^6.3.0",
|
|
142
142
|
"@alanscodelog/vite-config": "^0.0.7",
|
|
143
143
|
"@iconify/json": "^2.2.412",
|
|
144
144
|
"@nuxt/kit": "^4.2.1",
|
|
@@ -154,7 +154,7 @@
|
|
|
154
154
|
"@vitejs/plugin-vue": "^6.0.2",
|
|
155
155
|
"@vitest/browser-playwright": "^4.0.14",
|
|
156
156
|
"@vitest/coverage-v8": "^4.0.14",
|
|
157
|
-
"@witchcraft/ui": "^0.3.
|
|
157
|
+
"@witchcraft/ui": "^0.3.25",
|
|
158
158
|
"concurrently": "^9.2.1",
|
|
159
159
|
"cross-env": "^10.0.0",
|
|
160
160
|
"eslint": "^9.39.1",
|
package/src/module.ts
CHANGED
|
@@ -21,7 +21,7 @@ declare module "@nuxt/schema" {
|
|
|
21
21
|
|
|
22
22
|
export interface ModuleOptions {
|
|
23
23
|
/** @internal */
|
|
24
|
-
_playgroundWorkaround?:
|
|
24
|
+
_playgroundWorkaround?: string
|
|
25
25
|
}
|
|
26
26
|
|
|
27
27
|
export default defineNuxtModule<ModuleOptions>({
|
|
@@ -30,7 +30,7 @@ export default defineNuxtModule<ModuleOptions>({
|
|
|
30
30
|
configKey: "witchcraftEditor"
|
|
31
31
|
},
|
|
32
32
|
defaults: {
|
|
33
|
-
_playgroundWorkaround:
|
|
33
|
+
_playgroundWorkaround: undefined
|
|
34
34
|
},
|
|
35
35
|
moduleDependencies: {
|
|
36
36
|
"@witchcraft/ui/nuxt": {
|
|
@@ -60,7 +60,7 @@ export default defineNuxtModule<ModuleOptions>({
|
|
|
60
60
|
addTemplate({
|
|
61
61
|
filename: "witchcraft-editor.css",
|
|
62
62
|
write: true,
|
|
63
|
-
getContents: () => options._playgroundWorkaround
|
|
63
|
+
getContents: () => options._playgroundWorkaround === "@witchcraft/editor"
|
|
64
64
|
? crop`
|
|
65
65
|
@import "${resolve("./runtime/assets/base.css")}";
|
|
66
66
|
@import "${resolve("./runtime/assets/utils.css")}";
|
|
@@ -1,56 +1,81 @@
|
|
|
1
1
|
/* eslint-disable no-console */
|
|
2
2
|
import type { Editor } from "@tiptap/core"
|
|
3
|
-
import { Plugin, PluginKey
|
|
3
|
+
import { Plugin, PluginKey } from "@tiptap/pm/state"
|
|
4
|
+
import { Decoration, DecorationSet } from "@tiptap/pm/view"
|
|
4
5
|
|
|
5
6
|
import { isEmbeddedBlock } from "../../EmbeddedDocument/utils/isEmbeddedBlock.js"
|
|
6
7
|
|
|
7
|
-
const ROOT_SELECTION_REGEX = /([0-9 -]*)(\[|$)/
|
|
8
|
+
const ROOT_SELECTION_REGEX = /(DEBUG: [0-9 -]*)(\[|$)/
|
|
8
9
|
const SUB_SELECTION_REGEX = /(\[[0-9 -]*\])/
|
|
9
10
|
|
|
10
11
|
export const debugSelectionPluginKey = new PluginKey("debugSelection")
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
*
|
|
14
|
-
* For embedded editors, adds the selection as `[from - to]`.
|
|
15
|
-
*/
|
|
12
|
+
|
|
13
|
+
/** Renders a floating tooltip directly above the selection point in dev mode only. */
|
|
16
14
|
export const debugSelectionPlugin = (editor: Editor, log: boolean = false): Plugin => {
|
|
17
15
|
let initialized = false
|
|
16
|
+
let currentDisplayString = ""
|
|
17
|
+
|
|
18
18
|
return new Plugin({
|
|
19
19
|
key: debugSelectionPluginKey,
|
|
20
20
|
state: {
|
|
21
|
-
init()
|
|
22
|
-
apply(tr
|
|
23
|
-
if (!import.meta.dev)
|
|
21
|
+
init() { return DecorationSet.empty },
|
|
22
|
+
apply(tr, oldSet) {
|
|
23
|
+
if (!import.meta.dev) return oldSet.map(tr.mapping, tr.doc)
|
|
24
24
|
const sel = `${tr.selection.from} - ${tr.selection.to}`
|
|
25
|
+
|
|
25
26
|
if (isEmbeddedBlock(editor.view)) {
|
|
26
|
-
if (log) {
|
|
27
|
-
|
|
28
|
-
}
|
|
29
|
-
const hasEmbeddedSelection = document.title.match(SUB_SELECTION_REGEX)
|
|
27
|
+
if (log) console.log(`embedded selection: ${sel}`)
|
|
28
|
+
const hasEmbeddedSelection = currentDisplayString.match(SUB_SELECTION_REGEX)
|
|
30
29
|
if (hasEmbeddedSelection) {
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
)
|
|
30
|
+
currentDisplayString = currentDisplayString.replace(
|
|
31
|
+
SUB_SELECTION_REGEX,
|
|
32
|
+
`[${sel}]`
|
|
33
|
+
)
|
|
36
34
|
} else {
|
|
37
|
-
|
|
35
|
+
// Ensure prefix is present even if starting as an embedded block
|
|
36
|
+
const prefix = currentDisplayString.startsWith("DEBUG: ") ? "" : "DEBUG: "
|
|
37
|
+
currentDisplayString = `${prefix}${currentDisplayString} [${sel}]`
|
|
38
38
|
}
|
|
39
39
|
} else {
|
|
40
|
-
if (log) {
|
|
41
|
-
console.log(`root selection: ${tr.selection.from} - ${tr.selection.to}`)
|
|
42
|
-
}
|
|
43
|
-
|
|
40
|
+
if (log) console.log(`root selection: ${sel}`)
|
|
44
41
|
if (!initialized) {
|
|
45
42
|
initialized = true
|
|
46
|
-
|
|
43
|
+
currentDisplayString = `DEBUG: ${sel}`
|
|
47
44
|
} else {
|
|
48
|
-
|
|
45
|
+
currentDisplayString = currentDisplayString.replace(
|
|
49
46
|
ROOT_SELECTION_REGEX,
|
|
50
|
-
|
|
47
|
+
`DEBUG: ${sel} $2`
|
|
51
48
|
)
|
|
52
49
|
}
|
|
53
|
-
}
|
|
50
|
+
} const widget = document.createElement("div")
|
|
51
|
+
Object.assign(widget.style, {
|
|
52
|
+
position: "absolute",
|
|
53
|
+
top: "110%",
|
|
54
|
+
right: "0",
|
|
55
|
+
zIndex: "100",
|
|
56
|
+
padding: "2px 6px",
|
|
57
|
+
fontSize: "10px",
|
|
58
|
+
fontFamily: "monospace",
|
|
59
|
+
color: "white",
|
|
60
|
+
backgroundColor: "rgba(0, 0, 0, 0.7)",
|
|
61
|
+
borderRadius: "2px",
|
|
62
|
+
pointerEvents: "none",
|
|
63
|
+
whiteSpace: "nowrap",
|
|
64
|
+
lineHeight: "1"
|
|
65
|
+
})
|
|
66
|
+
widget.textContent = currentDisplayString
|
|
67
|
+
|
|
68
|
+
const deco = Decoration.widget(tr.selection.to, widget, {
|
|
69
|
+
side: -1, // Ensure it stays to the left of the cursor
|
|
70
|
+
key: "debug-selection-tooltip"
|
|
71
|
+
})
|
|
72
|
+
|
|
73
|
+
return DecorationSet.create(tr.doc, [deco])
|
|
74
|
+
}
|
|
75
|
+
},
|
|
76
|
+
props: {
|
|
77
|
+
decorations(state) {
|
|
78
|
+
return debugSelectionPluginKey.getState(state)
|
|
54
79
|
}
|
|
55
80
|
}
|
|
56
81
|
})
|
|
@@ -23,7 +23,6 @@
|
|
|
23
23
|
ref="codeBlockLangPickerEl"
|
|
24
24
|
>
|
|
25
25
|
<!-- and here we only style everything but the suggestions so the input matches the code block background -->
|
|
26
|
-
<!-- @vue-expect-error -->
|
|
27
26
|
<WSimpleInput
|
|
28
27
|
:border="false"
|
|
29
28
|
wrapper-class="lang-picker-input flex-nowrap z-10"
|
|
@@ -7,7 +7,6 @@ import {
|
|
|
7
7
|
yUndoPluginKey,
|
|
8
8
|
yXmlFragmentToProsemirrorJSON
|
|
9
9
|
} from "@tiptap/y-tiptap"
|
|
10
|
-
import type { Doc } from "yjs"
|
|
11
10
|
|
|
12
11
|
/**
|
|
13
12
|
* Copied from tiptap's collaboration extension with a few minor changes to make it work with our document api.
|
|
@@ -30,7 +29,11 @@ export function createCollaborationPlugins(
|
|
|
30
29
|
}
|
|
31
30
|
const fragment = options.fragment
|
|
32
31
|
? options.fragment
|
|
33
|
-
:
|
|
32
|
+
: options.document?.getXmlFragment(options.field)
|
|
33
|
+
|
|
34
|
+
if (!fragment) {
|
|
35
|
+
throw new Error("No fragment or document provided.")
|
|
36
|
+
}
|
|
34
37
|
|
|
35
38
|
// Quick fix until there is an official implementation (thanks to @hamflx).
|
|
36
39
|
// See https://github.com/yjs/y-prosemirror/issues/114 and https://github.com/yjs/y-prosemirror/issues/102
|
|
@@ -50,7 +50,11 @@ export function useEditorContent(
|
|
|
50
50
|
|
|
51
51
|
async function load(changed: boolean): Promise<void> {
|
|
52
52
|
if (content.value) {
|
|
53
|
-
editor.value
|
|
53
|
+
if (!editor.value) {
|
|
54
|
+
recreate(options => ({ ...options, content: content.value }))
|
|
55
|
+
} else {
|
|
56
|
+
editor.value?.commands.setContent(content.value)
|
|
57
|
+
}
|
|
54
58
|
} else if (documentApi) {
|
|
55
59
|
if (changed && id.value) {
|
|
56
60
|
await documentApi.load({ docId: id.value })
|
|
@@ -93,7 +97,7 @@ export function useEditorContent(
|
|
|
93
97
|
if (oldId !== undefined && newId !== oldId && documentApi) {
|
|
94
98
|
unload(oldId)
|
|
95
99
|
await load(true)
|
|
96
|
-
} else if (_newContent) {
|
|
100
|
+
} else if (_newContent !== _oldContent && _newContent) {
|
|
97
101
|
await load(false)
|
|
98
102
|
}
|
|
99
103
|
}, { deep: false })
|
|
@@ -4,7 +4,6 @@
|
|
|
4
4
|
ref="el"
|
|
5
5
|
>
|
|
6
6
|
<div class="flex flex-col gap-1">
|
|
7
|
-
<!-- @vue-expect-error -->
|
|
8
7
|
<WSimpleInput
|
|
9
8
|
class="text-input"
|
|
10
9
|
wrapper-class="flex flex-nowrap gap-1"
|
|
@@ -24,7 +23,6 @@
|
|
|
24
23
|
</WLabel>
|
|
25
24
|
</template>
|
|
26
25
|
</WSimpleInput>
|
|
27
|
-
<!-- @vue-expect-error -->
|
|
28
26
|
<WSimpleInput
|
|
29
27
|
class="link-input"
|
|
30
28
|
wrapper-class="flex flex-nowrap gap-1"
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { faker } from "@faker-js/faker"
|
|
2
2
|
|
|
3
|
-
export function createPsuedoSentence({ min = 0, max = 10}: { min?: number, max?: number } = {}) {
|
|
3
|
+
export function createPsuedoSentence({ min = 0, max = 10 }: { min?: number, max?: number } = {}) {
|
|
4
4
|
// sentence generated with string.sample (which contains all possible chars) instead of lorem.sentence
|
|
5
5
|
const sentenceLength = faker.number.int({ min, max })
|
|
6
6
|
const sentence = Array.from(
|