From 4c665594d69425a53bcf396ed081f8ab72ca7084 Mon Sep 17 00:00:00 2001 From: pengx17 Date: Wed, 22 Jan 2025 05:20:55 +0000 Subject: [PATCH] fix(editor): ref on click slots should not be global (#9830) fix AF-2129 --- .../src/properties/link/cell-renderer.ts | 7 ++++--- .../embed-linked-doc-block/embed-linked-doc-block.ts | 1 + .../embed-synced-doc-block/embed-synced-doc-block.ts | 5 ++--- .../presets/nodes/footnote-node/footnote-popup.ts | 5 +++-- .../inline/presets/nodes/link-node/affine-link.ts | 7 +++++-- .../presets/nodes/reference-node/reference-node.ts | 7 ++++--- .../presets/nodes/reference-node/reference-popup.ts | 1 + .../inline/presets/nodes/reference-node/types.ts | 2 ++ .../presets/ai/_common/chat-actions-handle.ts | 1 + .../affine/use-register-blocksuite-editor-commands.tsx | 10 +++++++++- .../hooks/affine/use-register-copy-link-commands.tsx | 3 +++ .../pages/workspace/detail-page/detail-page.tsx | 7 +++++-- .../desktop/pages/workspace/detail-page/tabs/chat.tsx | 6 ++++-- .../pages/workspace/detail/mobile-detail-page.tsx | 2 -- .../peek-view/view/doc-preview/doc-peek-view.tsx | 3 +++ 15 files changed, 47 insertions(+), 20 deletions(-) diff --git a/blocksuite/affine/block-database/src/properties/link/cell-renderer.ts b/blocksuite/affine/block-database/src/properties/link/cell-renderer.ts index df158dc3e8..02bfa0f41e 100644 --- a/blocksuite/affine/block-database/src/properties/link/cell-renderer.ts +++ b/blocksuite/affine/block-database/src/properties/link/cell-renderer.ts @@ -119,9 +119,10 @@ export class LinkCell extends BaseCellRenderer { return; } - std - .getOptional(RefNodeSlotsProvider) - ?.docLinkClicked.emit({ pageId: this.docId }); + std.getOptional(RefNodeSlotsProvider)?.docLinkClicked.emit({ + pageId: this.docId, + host: std.host, + }); }; get std() { diff --git a/blocksuite/affine/block-embed/src/embed-linked-doc-block/embed-linked-doc-block.ts b/blocksuite/affine/block-embed/src/embed-linked-doc-block/embed-linked-doc-block.ts index 49f058fc0f..23415d4c74 100644 --- a/blocksuite/affine/block-embed/src/embed-linked-doc-block/embed-linked-doc-block.ts +++ b/blocksuite/affine/block-embed/src/embed-linked-doc-block/embed-linked-doc-block.ts @@ -216,6 +216,7 @@ export class EmbedLinkedDocBlockComponent extends EmbedBlockComponent { @@ -387,8 +387,7 @@ export class EmbedSyncedDocBlockComponent extends EmbedBlockComponent('editor-host') ?? null; + editorHost = editorHost.parentElement?.closest('editor-host') ?? null; } } diff --git a/blocksuite/affine/components/src/rich-text/inline/presets/nodes/footnote-node/footnote-popup.ts b/blocksuite/affine/components/src/rich-text/inline/presets/nodes/footnote-node/footnote-popup.ts index e929b67531..617213a92e 100644 --- a/blocksuite/affine/components/src/rich-text/inline/presets/nodes/footnote-node/footnote-popup.ts +++ b/blocksuite/affine/components/src/rich-text/inline/presets/nodes/footnote-node/footnote-popup.ts @@ -84,14 +84,15 @@ export class FootNotePopup extends WithDisposable(LitElement) { const referenceType = this.footnote.reference.type; const { docId, url } = this.footnote.reference; switch (referenceType) { - case 'doc': + case 'doc': { if (!docId) { break; } this.std .getOptional(RefNodeSlotsProvider) - ?.docLinkClicked.emit({ pageId: docId }); + ?.docLinkClicked.emit({ pageId: docId, host: this.std.host }); break; + } case 'url': if (!url) { break; diff --git a/blocksuite/affine/components/src/rich-text/inline/presets/nodes/link-node/affine-link.ts b/blocksuite/affine/components/src/rich-text/inline/presets/nodes/link-node/affine-link.ts index fbaac9e5f6..aa0e6306b7 100644 --- a/blocksuite/affine/components/src/rich-text/inline/presets/nodes/link-node/affine-link.ts +++ b/blocksuite/affine/components/src/rich-text/inline/presets/nodes/link-node/affine-link.ts @@ -56,11 +56,14 @@ export class AffineLink extends ShadowlessElement { if (!referenceInfo) return; const refNodeSlotsProvider = this.std?.getOptional(RefNodeSlotsProvider); - if (!refNodeSlotsProvider) return; + if (!refNodeSlotsProvider || !this.std) return; e?.preventDefault(); - refNodeSlotsProvider.docLinkClicked.emit(referenceInfo); + refNodeSlotsProvider.docLinkClicked.emit({ + ...referenceInfo, + host: this.std.host, + }); }; private readonly _whenHover = new HoverController( diff --git a/blocksuite/affine/components/src/rich-text/inline/presets/nodes/reference-node/reference-node.ts b/blocksuite/affine/components/src/rich-text/inline/presets/nodes/reference-node/reference-node.ts index 391a8e9513..ddf452b715 100644 --- a/blocksuite/affine/components/src/rich-text/inline/presets/nodes/reference-node/reference-node.ts +++ b/blocksuite/affine/components/src/rich-text/inline/presets/nodes/reference-node/reference-node.ts @@ -200,9 +200,10 @@ export class AffineReference extends WithDisposable(ShadowlessElement) { private _onClick() { if (!this.config.interactable) return; - this.std - .getOptional(RefNodeSlotsProvider) - ?.docLinkClicked.emit(this.referenceInfo); + this.std.getOptional(RefNodeSlotsProvider)?.docLinkClicked.emit({ + ...this.referenceInfo, + host: this.std.host, + }); } override connectedCallback() { diff --git a/blocksuite/affine/components/src/rich-text/inline/presets/nodes/reference-node/reference-popup.ts b/blocksuite/affine/components/src/rich-text/inline/presets/nodes/reference-node/reference-popup.ts index 17743be8d0..cddb59bfbe 100644 --- a/blocksuite/affine/components/src/rich-text/inline/presets/nodes/reference-node/reference-popup.ts +++ b/blocksuite/affine/components/src/rich-text/inline/presets/nodes/reference-node/reference-popup.ts @@ -71,6 +71,7 @@ export class ReferencePopup extends WithDisposable(LitElement) { this.std.getOptional(RefNodeSlotsProvider)?.docLinkClicked.emit({ ...this.referenceInfo, ...event, + host: this.std.host, }); }; diff --git a/blocksuite/affine/components/src/rich-text/inline/presets/nodes/reference-node/types.ts b/blocksuite/affine/components/src/rich-text/inline/presets/nodes/reference-node/types.ts index 15f3beb022..de47129c7b 100644 --- a/blocksuite/affine/components/src/rich-text/inline/presets/nodes/reference-node/types.ts +++ b/blocksuite/affine/components/src/rich-text/inline/presets/nodes/reference-node/types.ts @@ -1,11 +1,13 @@ import type { ReferenceInfo } from '@blocksuite/affine-model'; import type { OpenDocMode } from '@blocksuite/affine-shared/services'; +import type { EditorHost } from '@blocksuite/block-std'; import type { Slot } from '@blocksuite/global/utils'; export type DocLinkClickedEvent = ReferenceInfo & { // default is active view openMode?: OpenDocMode; event?: MouseEvent; + host: EditorHost; }; export type RefNodeSlots = { diff --git a/packages/frontend/core/src/blocksuite/presets/ai/_common/chat-actions-handle.ts b/packages/frontend/core/src/blocksuite/presets/ai/_common/chat-actions-handle.ts index 9f054ab804..2bfc1210fa 100644 --- a/packages/frontend/core/src/blocksuite/presets/ai/_common/chat-actions-handle.ts +++ b/packages/frontend/core/src/blocksuite/presets/ai/_common/chat-actions-handle.ts @@ -433,6 +433,7 @@ const CREATE_AS_DOC = { host.std.getOptional(RefNodeSlotsProvider)?.docLinkClicked.emit({ pageId: newDoc.id, + host, }); let complete = false; (function addContent() { diff --git a/packages/frontend/core/src/components/hooks/affine/use-register-blocksuite-editor-commands.tsx b/packages/frontend/core/src/components/hooks/affine/use-register-blocksuite-editor-commands.tsx index b422bb0650..d595b0416a 100644 --- a/packages/frontend/core/src/components/hooks/affine/use-register-blocksuite-editor-commands.tsx +++ b/packages/frontend/core/src/components/hooks/affine/use-register-blocksuite-editor-commands.tsx @@ -30,7 +30,10 @@ import { pageHistoryModalAtom } from '../../../components/atoms/page-history'; import { useBlockSuiteMetaHelper } from './use-block-suite-meta-helper'; import { useExportPage } from './use-export-page'; -export function useRegisterBlocksuiteEditorCommands(editor: Editor) { +export function useRegisterBlocksuiteEditorCommands( + editor: Editor, + active: boolean +) { const doc = useService(DocService).doc; const docId = doc.id; const mode = useLiveData(editor.mode$); @@ -82,6 +85,10 @@ export function useRegisterBlocksuiteEditorCommands(editor: Editor) { const openInAppService = useServiceOptional(OpenInAppService); useEffect(() => { + if (!active) { + return; + } + const unsubs: Array<() => void> = []; const preconditionStrategy = () => PreconditionStrategy.InPaperOrEdgeless && !trash; @@ -375,5 +382,6 @@ export function useRegisterBlocksuiteEditorCommands(editor: Editor) { defaultPageWidth, checked, openInAppService, + active, ]); } diff --git a/packages/frontend/core/src/components/hooks/affine/use-register-copy-link-commands.tsx b/packages/frontend/core/src/components/hooks/affine/use-register-copy-link-commands.tsx index 02f45ec8a0..c42edf4b99 100644 --- a/packages/frontend/core/src/components/hooks/affine/use-register-copy-link-commands.tsx +++ b/packages/frontend/core/src/components/hooks/affine/use-register-copy-link-commands.tsx @@ -25,6 +25,9 @@ export function useRegisterCopyLinkCommands({ }); useEffect(() => { + if (!isActiveView) { + return; + } const unsubs: Array<() => void> = []; unsubs.push( diff --git a/packages/frontend/core/src/desktop/pages/workspace/detail-page/detail-page.tsx b/packages/frontend/core/src/desktop/pages/workspace/detail-page/detail-page.tsx index f6cb635abf..c2ef57f690 100644 --- a/packages/frontend/core/src/desktop/pages/workspace/detail-page/detail-page.tsx +++ b/packages/frontend/core/src/desktop/pages/workspace/detail-page/detail-page.tsx @@ -165,7 +165,7 @@ const DetailPageImpl = memo(function DetailPageImpl() { return; }, [globalContext, isActiveView, isInTrash]); - useRegisterBlocksuiteEditorCommands(editor); + useRegisterBlocksuiteEditorCommands(editor, isActiveView); const title = useLiveData(doc.title$); usePageDocumentTitle(title); @@ -182,7 +182,10 @@ const DetailPageImpl = memo(function DetailPageImpl() { disposable.add( // the event should not be emitted by AffineReference refNodeSlots.docLinkClicked.on( - ({ pageId, params, openMode, event }) => { + ({ pageId, params, openMode, event, host }) => { + if (host !== editorHost) { + return; + } openMode ??= event && isNewTabTrigger(event) ? 'open-in-new-tab' diff --git a/packages/frontend/core/src/desktop/pages/workspace/detail-page/tabs/chat.tsx b/packages/frontend/core/src/desktop/pages/workspace/detail-page/tabs/chat.tsx index 131488c9af..0bf0f37546 100644 --- a/packages/frontend/core/src/desktop/pages/workspace/detail-page/tabs/chat.tsx +++ b/packages/frontend/core/src/desktop/pages/workspace/detail-page/tabs/chat.tsx @@ -91,8 +91,10 @@ export const EditorChatPanel = forwardRef(function EditorChatPanel( const docModeService = editor.host.std.get(DocModeProvider); const refNodeService = editor.host.std.getOptional(RefNodeSlotsProvider); const disposable = [ - refNodeService?.docLinkClicked.on(() => { - (chatPanelRef.current as ChatPanel).doc = editor.doc; + refNodeService?.docLinkClicked.on(({ host }) => { + if (host === editor.host) { + (chatPanelRef.current as ChatPanel).doc = editor.doc; + } }), docModeService?.onPrimaryModeChange(() => { if (!editor.host) return; diff --git a/packages/frontend/core/src/mobile/pages/workspace/detail/mobile-detail-page.tsx b/packages/frontend/core/src/mobile/pages/workspace/detail/mobile-detail-page.tsx index fe123051cd..03b3e28c7c 100644 --- a/packages/frontend/core/src/mobile/pages/workspace/detail/mobile-detail-page.tsx +++ b/packages/frontend/core/src/mobile/pages/workspace/detail/mobile-detail-page.tsx @@ -1,7 +1,6 @@ import { useThemeColorV2 } from '@affine/component'; import { PageDetailSkeleton } from '@affine/component/page-detail-skeleton'; import { AffineErrorBoundary } from '@affine/core/components/affine/affine-error-boundary'; -import { useRegisterBlocksuiteEditorCommands } from '@affine/core/components/hooks/affine/use-register-blocksuite-editor-commands'; import { useActiveBlocksuiteEditor } from '@affine/core/components/hooks/use-block-suite-editor'; import { useDocMetaHelper } from '@affine/core/components/hooks/use-block-suite-page-meta'; import { usePageDocumentTitle } from '@affine/core/components/hooks/use-global-state'; @@ -140,7 +139,6 @@ const DetailPageImpl = () => { }; }, [globalContext, isInTrash]); - useRegisterBlocksuiteEditorCommands(editor); const title = useLiveData(doc.title$); usePageDocumentTitle(title); diff --git a/packages/frontend/core/src/modules/peek-view/view/doc-preview/doc-peek-view.tsx b/packages/frontend/core/src/modules/peek-view/view/doc-preview/doc-peek-view.tsx index 234f45ba0e..c15fe4ebf9 100644 --- a/packages/frontend/core/src/modules/peek-view/view/doc-preview/doc-peek-view.tsx +++ b/packages/frontend/core/src/modules/peek-view/view/doc-preview/doc-peek-view.tsx @@ -106,6 +106,9 @@ function DocPeekPreviewEditor({ disposableGroup.add( // todo(@pengx17): seems not working refNodeSlots.docLinkClicked.on(options => { + if (options.host !== editorContainer.host) { + return; + } peekView .open({ docRef: { docId: options.pageId },