From 88095a87a8243ba101db9f707f74a7304db9a1b7 Mon Sep 17 00:00:00 2001 From: doouding Date: Tue, 18 Feb 2025 08:40:57 +0000 Subject: [PATCH] fix: create linked-doc block when content can't be drop as gfx block (#10250) --- .../shared/src/services/drag-handle-config.ts | 2 + .../src/watchers/drag-event-watcher.ts | 81 ++++++++++++++----- 2 files changed, 63 insertions(+), 20 deletions(-) diff --git a/blocksuite/affine/shared/src/services/drag-handle-config.ts b/blocksuite/affine/shared/src/services/drag-handle-config.ts index 97f2122fba..39334a649a 100644 --- a/blocksuite/affine/shared/src/services/drag-handle-config.ts +++ b/blocksuite/affine/shared/src/services/drag-handle-config.ts @@ -32,6 +32,7 @@ export class DNDAPIExtension extends Extension { docId: string; flavour?: string; blockId?: string; + props?: Record; }): SliceSnapshot | null { const { docId, flavour = 'affine:embed-linked-doc', blockId } = options; @@ -43,6 +44,7 @@ export class DNDAPIExtension extends Extension { return null; } const props = { + ...options.props, ...(blockId ? { blockId } : {}), pageId: docId, }; diff --git a/blocksuite/affine/widget-drag-handle/src/watchers/drag-event-watcher.ts b/blocksuite/affine/widget-drag-handle/src/watchers/drag-event-watcher.ts index cae18f9a04..d26b78fd31 100644 --- a/blocksuite/affine/widget-drag-handle/src/watchers/drag-event-watcher.ts +++ b/blocksuite/affine/widget-drag-handle/src/watchers/drag-event-watcher.ts @@ -18,6 +18,7 @@ import { EMBED_CARD_WIDTH, } from '@blocksuite/affine-shared/consts'; import { + DndApiExtensionIdentifier, DocModeProvider, TelemetryProvider, } from '@blocksuite/affine-shared/services'; @@ -985,6 +986,16 @@ export class DragEventWatcher { snapshot.content.forEach(rewrite); }; + get dndExtension() { + return this.std.getOptional(DndApiExtensionIdentifier); + } + + /** + * This method will try to drop the snapshot as gfx block directly if all blocks can be dropped as gfx block. + * Otherwise, it will create a linked doc to reference the original doc. + * @param snapshot + * @param point + */ private readonly _dropAsGfxBlock = ( snapshot: SliceSnapshot, point: Point @@ -1063,30 +1074,60 @@ export class DragEventWatcher { .catch(console.error); } } else { + const dndExtApi = this.dndExtension; const content = snapshot.content.filter(block => schema.safeValidate(block.flavour, 'affine:note') ); - // create note to wrap the snapshot - const noteId = store.addBlock( - 'affine:note', - { - xywh: new Bound( - point.x, - point.y, - DEFAULT_NOTE_WIDTH, - DEFAULT_NOTE_HEIGHT - ).serialize(), - }, - this.widget.doc.root! - ); + const sourceDocId = snapshot.pageId; - this._dropToModel( - { - ...snapshot, - content, - }, - noteId - ).catch(console.error); + if ( + dndExtApi && + this.std.store.workspace.docs.has(sourceDocId) && + this.gfx.surface + ) { + const style = 'vertical' as EmbedCardStyle; + const linkedDocSnapshot = dndExtApi.fromEntity({ + docId: sourceDocId, + props: { + blockIds: content.map(block => block.id), + style: 'vertical', + xywh: new Bound( + point.x, + point.y, + EMBED_CARD_WIDTH[style], + EMBED_CARD_HEIGHT[style] + ).serialize(), + }, + }); + + if (linkedDocSnapshot) { + this._dropToModel(linkedDocSnapshot, this.gfx.surface.id).catch( + console.error + ); + } + } else { + // create note to wrap the snapshot + const noteId = store.addBlock( + 'affine:note', + { + xywh: new Bound( + point.x, + point.y, + DEFAULT_NOTE_WIDTH, + DEFAULT_NOTE_HEIGHT + ).serialize(), + }, + this.widget.doc.root! + ); + + this._dropToModel( + { + ...snapshot, + content, + }, + noteId + ).catch(console.error); + } } };