lexical-vue
Version:
An extensible Vue 3 web text-editor based on Lexical.
78 lines (77 loc) • 3.79 kB
JavaScript
import { createBlock, defineComponent, openBlock, ref, resolveDynamicComponent, unref, watchEffect } from "vue";
import { createBinding } from "@lexical/yjs";
import { useLexicalComposer } from "./LexicalComposer.vine.js";
import { collaborationContext } from "./shared/useCollaborationContext.js";
import { useYjsCollaboration, useYjsFocusTracking, useYjsHistory } from "./shared/useYjsCollaboration.js";
const CollaborationPlugin = (()=>{
const __vine = defineComponent({
name: 'CollaborationPlugin',
props: {
id: {
required: true
},
providerFactory: {
required: true
},
shouldBootstrap: {
required: true,
type: Boolean
},
username: {},
cursorColor: {},
cursorsContainerRef: {},
initialEditorState: {},
excludedProperties: {},
awarenessData: {},
syncCursorPositionsFn: {}
},
setup (__props, param) {
let { expose: __expose } = param;
__expose();
const props = __props;
const isBindingInitialized = ref(false);
const isProviderInitialized = ref(false);
watchEffect(()=>{
if (void 0 !== props.username) collaborationContext.value.name = props.username;
if (void 0 !== props.cursorColor) collaborationContext.value.color = props.cursorColor;
});
const editor = useLexicalComposer();
watchEffect((onInvalidate)=>{
collaborationContext.value.isCollabActive = true;
onInvalidate(()=>{
if (null == editor._parentEditor) collaborationContext.value.isCollabActive = false;
});
});
const provider = ref();
const doc = ref();
watchEffect((onInvalidate)=>{
if (isProviderInitialized.value) return;
isProviderInitialized.value = true;
const newProvider = props.providerFactory(props.id, collaborationContext.value.yjsDocMap);
provider.value = newProvider;
doc.value = collaborationContext.value.yjsDocMap.get(props.id);
onInvalidate(()=>{
newProvider.disconnect();
});
});
const binding = ref();
watchEffect((onInvalidate)=>{
if (!provider.value) return;
if (isBindingInitialized.value) return;
isBindingInitialized.value = true;
const newBinding = createBinding(editor, provider.value, props.id, doc.value || collaborationContext.value.yjsDocMap.get(props.id), collaborationContext.value.yjsDocMap, props.excludedProperties);
binding.value = newBinding;
onInvalidate(()=>{
newBinding.root.destroy(newBinding);
});
});
const cursors = useYjsCollaboration(editor, ()=>props.id, provider, ()=>collaborationContext.value.yjsDocMap, ()=>collaborationContext.value.name, ()=>collaborationContext.value.color, ()=>props.shouldBootstrap, binding, doc, ()=>props.cursorsContainerRef, ()=>props.initialEditorState, ()=>props.awarenessData, ()=>props.syncCursorPositionsFn);
useYjsHistory(editor, binding);
useYjsFocusTracking(editor, provider, ()=>collaborationContext.value.name, ()=>collaborationContext.value.color, props.awarenessData);
return (_ctx, _cache)=>(openBlock(), createBlock(resolveDynamicComponent(unref(cursors))));
}
});
__vine.__vue_vine = true;
return __vine;
})();
export { CollaborationPlugin };