import type { BlockHub } from '@blocksuite/blocks'; import { EditorContainer } from '@blocksuite/editor'; import { assertExists } from '@blocksuite/global/utils'; import type { Page } from '@blocksuite/store'; import type { CSSProperties, ReactElement } from 'react'; import { memo, useCallback, useEffect, useRef } from 'react'; import type { FallbackProps } from 'react-error-boundary'; import { ErrorBoundary } from 'react-error-boundary'; export type EditorProps = { page: Page; mode: 'page' | 'edgeless'; onInit: (page: Page, editor: Readonly) => void; onLoad?: (page: Page, editor: EditorContainer) => void; style?: CSSProperties; }; export type ErrorBoundaryProps = { onReset?: () => void; }; declare global { // eslint-disable-next-line no-var var currentPage: Page | undefined; // eslint-disable-next-line no-var var currentEditor: EditorContainer | undefined; } const BlockSuiteEditorImpl = (props: EditorProps): ReactElement => { const page = props.page; assertExists(page, 'page should not be null'); const editorRef = useRef(null); const blockHubRef = useRef(null); if (editorRef.current === null) { editorRef.current = new EditorContainer(); editorRef.current.autofocus = true; globalThis.currentEditor = editorRef.current; } const editor = editorRef.current; assertExists(editorRef, 'editorRef.current should not be null'); if (editor.mode !== props.mode) { editor.mode = props.mode; } if (editor.page !== props.page) { editor.page = props.page; if (page.root === null) { props.onInit(page, editor); } props.onLoad?.(page, editor); } const ref = useRef(null); useEffect(() => { const editor = editorRef.current; assertExists(editor); const container = ref.current; if (!container) { return; } if (page.awarenessStore.getFlag('enable_block_hub')) { editor.createBlockHub().then(blockHub => { if (blockHubRef.current) { blockHubRef.current.remove(); } blockHubRef.current = blockHub; const toolWrapper = document.querySelector('#toolWrapper'); if (!toolWrapper) { console.warn( 'toolWrapper not found, block hub feature will not be available.' ); } else { toolWrapper.appendChild(blockHub); } }); } container.appendChild(editor); return () => { blockHubRef.current?.remove(); container.removeChild(editor); }; }, [page]); return (
); }; const BlockSuiteErrorFallback = ( props: FallbackProps & ErrorBoundaryProps ): ReactElement => { return (

Sorry.. there was an error

{props.error.message}
); }; export const BlockSuiteEditor = memo(function BlockSuiteEditor( props: EditorProps & ErrorBoundaryProps ): ReactElement { return ( ( ), [props.onReset] )} > ); }); BlockSuiteEditor.displayName = 'BlockSuiteEditor';