diff --git a/blocksuite/affine/block-surface/src/consts.ts b/blocksuite/affine/block-surface/src/consts.ts index eee97f7cea249..6fcf8bd4a80be 100644 --- a/blocksuite/affine/block-surface/src/consts.ts +++ b/blocksuite/affine/block-surface/src/consts.ts @@ -6,6 +6,8 @@ export const ZOOM_WHEEL_STEP = 0.1; export const GRID_SIZE = 3000; export const GRID_GAP_MIN = 10; export const GRID_GAP_MAX = 50; +export const DEFAULT_NOTE_OFFSET_X = 30; +export const DEFAULT_NOTE_OFFSET_Y = 40; // TODO: need to check the default central area ratio export const DEFAULT_CENTRAL_AREA_RATIO = 0.3; diff --git a/blocksuite/affine/block-surface/src/index.ts b/blocksuite/affine/block-surface/src/index.ts index 486cc0571b91c..4611c4607b472 100644 --- a/blocksuite/affine/block-surface/src/index.ts +++ b/blocksuite/affine/block-surface/src/index.ts @@ -104,7 +104,12 @@ import { tryMoveNode, } from './utils/mindmap/utils'; export * from './extensions'; -export { getLastPropsKey, getSurfaceBlock } from './utils'; +export { + addNote, + addNoteAtPoint, + getLastPropsKey, + getSurfaceBlock, +} from './utils'; export type { Options } from './utils/rough/core'; export { sortIndex } from './utils/sort'; export { updateXYWH } from './utils/update-xywh.js'; diff --git a/blocksuite/blocks/src/root-block/edgeless/utils/common.ts b/blocksuite/affine/block-surface/src/utils/add-note.ts similarity index 91% rename from blocksuite/blocks/src/root-block/edgeless/utils/common.ts rename to blocksuite/affine/block-surface/src/utils/add-note.ts index 99f4c68588f3f..eb9fa0b92b847 100644 --- a/blocksuite/blocks/src/root-block/edgeless/utils/common.ts +++ b/blocksuite/affine/block-surface/src/utils/add-note.ts @@ -1,4 +1,3 @@ -import { EdgelessCRUDIdentifier } from '@blocksuite/affine-block-surface'; import { focusTextModel } from '@blocksuite/affine-components/rich-text'; import { DEFAULT_NOTE_HEIGHT, @@ -18,7 +17,8 @@ import { serializeXYWH, } from '@blocksuite/global/utils'; -import { DEFAULT_NOTE_OFFSET_X, DEFAULT_NOTE_OFFSET_Y } from './consts.js'; +import { DEFAULT_NOTE_OFFSET_X, DEFAULT_NOTE_OFFSET_Y } from '../consts'; +import { EdgelessCRUDIdentifier } from '../extensions/crud-extension'; export function addNoteAtPoint( std: BlockStdScope, @@ -96,7 +96,7 @@ export function addNote( const doc = std.doc; const blockId = doc.addBlock( - options.childFlavour, + options.childFlavour as BlockSuite.Flavour, { type: options.childType }, noteId ); @@ -107,7 +107,10 @@ export function addNote( note.edgeless.collapsedHeight = height; }); } - gfx.tool.setTool('default'); + gfx.tool.setTool( + // @ts-expect-error FIXME: resolve after gfx tool refactor + 'default' + ); // Wait for edgelessTool updated requestAnimationFrame(() => { diff --git a/blocksuite/affine/block-surface/src/utils/index.ts b/blocksuite/affine/block-surface/src/utils/index.ts index e9ae255b37911..13b41a85ad816 100644 --- a/blocksuite/affine/block-surface/src/utils/index.ts +++ b/blocksuite/affine/block-surface/src/utils/index.ts @@ -33,5 +33,6 @@ export function normalizeWheelDeltaY(delta: number, zoom = 1) { return newZoom; } +export { addNote, addNoteAtPoint } from './add-note'; export { getLastPropsKey } from './get-last-props-key'; export { getSurfaceBlock } from './get-surface-block'; diff --git a/blocksuite/affine/shared/src/services/index.ts b/blocksuite/affine/shared/src/services/index.ts index d6919eaad3979..1c805af7c8732 100644 --- a/blocksuite/affine/shared/src/services/index.ts +++ b/blocksuite/affine/shared/src/services/index.ts @@ -1,13 +1,14 @@ -export * from './doc-display-meta-service.js'; -export * from './doc-mode-service.js'; -export * from './drag-handle-config.js'; -export * from './edit-props-store.js'; -export * from './editor-setting-service.js'; -export * from './embed-option-service.js'; -export * from './font-loader/index.js'; -export * from './generate-url-service.js'; -export * from './notification-service.js'; -export * from './parse-url-service.js'; -export * from './quick-search-service.js'; -export * from './telemetry-service/index.js'; -export * from './theme-service.js'; +export * from './doc-display-meta-service'; +export * from './doc-mode-service'; +export * from './drag-handle-config'; +export * from './edit-props-store'; +export * from './editor-setting-service'; +export * from './embed-option-service'; +export * from './font-loader'; +export * from './generate-url-service'; +export * from './notification-service'; +export * from './page-viewport-service'; +export * from './parse-url-service'; +export * from './quick-search-service'; +export * from './telemetry-service'; +export * from './theme-service'; diff --git a/blocksuite/affine/shared/src/services/page-viewport-service.ts b/blocksuite/affine/shared/src/services/page-viewport-service.ts new file mode 100644 index 0000000000000..69c43fc752884 --- /dev/null +++ b/blocksuite/affine/shared/src/services/page-viewport-service.ts @@ -0,0 +1,15 @@ +import type { ExtensionType } from '@blocksuite/block-std'; +import { createIdentifier } from '@blocksuite/global/di'; +import { Slot } from '@blocksuite/store'; + +import type { Viewport } from '../types'; + +export const PageViewportService = createIdentifier>( + 'PageViewportService' +); + +export const PageViewportServiceExtension: ExtensionType = { + setup: di => { + di.addImpl(PageViewportService, () => new Slot()); + }, +}; diff --git a/blocksuite/blocks/src/root-block/text-selection/utils.ts b/blocksuite/affine/shared/src/utils/auto-scroll.ts similarity index 100% rename from blocksuite/blocks/src/root-block/text-selection/utils.ts rename to blocksuite/affine/shared/src/utils/auto-scroll.ts diff --git a/blocksuite/affine/shared/src/utils/index.ts b/blocksuite/affine/shared/src/utils/index.ts index 85150e84037d1..c858a727afe88 100644 --- a/blocksuite/affine/shared/src/utils/index.ts +++ b/blocksuite/affine/shared/src/utils/index.ts @@ -1,20 +1,21 @@ -export * from './button-popper.js'; -export * from './collapsed/index.js'; -export * from './dnd/index.js'; -export * from './dom/index.js'; -export * from './edgeless.js'; -export * from './event.js'; -export * from './file/index.js'; -export * from './insert.js'; -export * from './is-abort-error.js'; -export * from './math.js'; -export * from './model/index.js'; -export * from './print-to-pdf.js'; -export * from './reference.js'; -export * from './reordering.js'; -export * from './signal.js'; -export * from './spec/index.js'; -export * from './string.js'; -export * from './title.js'; -export * from './url.js'; -export * from './zod-schema.js'; +export * from './auto-scroll'; +export * from './button-popper'; +export * from './collapsed'; +export * from './dnd'; +export * from './dom'; +export * from './edgeless'; +export * from './event'; +export * from './file'; +export * from './insert'; +export * from './is-abort-error'; +export * from './math'; +export * from './model'; +export * from './print-to-pdf'; +export * from './reference'; +export * from './reordering'; +export * from './signal'; +export * from './spec'; +export * from './string'; +export * from './title'; +export * from './url'; +export * from './zod-schema'; diff --git a/blocksuite/affine/widget-drag-handle/package.json b/blocksuite/affine/widget-drag-handle/package.json new file mode 100644 index 0000000000000..2b8753cc1ba9e --- /dev/null +++ b/blocksuite/affine/widget-drag-handle/package.json @@ -0,0 +1,47 @@ +{ + "name": "@blocksuite/affine-widget-drag-handle", + "description": "Drag handle for BlockSuite.", + "type": "module", + "scripts": { + "build": "tsc", + "test:unit": "nx vite:test --run --passWithNoTests", + "test:unit:coverage": "nx vite:test --run --coverage", + "test:e2e": "playwright test" + }, + "sideEffects": false, + "keywords": [], + "author": "toeverything", + "license": "MIT", + "dependencies": { + "@blocksuite/affine-block-list": "workspace:*", + "@blocksuite/affine-block-note": "workspace:*", + "@blocksuite/affine-block-paragraph": "workspace:*", + "@blocksuite/affine-block-surface": "workspace:*", + "@blocksuite/affine-components": "workspace:*", + "@blocksuite/affine-model": "workspace:*", + "@blocksuite/affine-shared": "workspace:*", + "@blocksuite/block-std": "workspace:*", + "@blocksuite/global": "workspace:*", + "@blocksuite/icons": "^2.1.75", + "@blocksuite/inline": "workspace:*", + "@blocksuite/store": "workspace:*", + "@floating-ui/dom": "^1.6.10", + "@lit/context": "^1.1.2", + "@preact/signals-core": "^1.8.0", + "@toeverything/theme": "^1.1.1", + "lit": "^3.2.0", + "minimatch": "^10.0.1", + "zod": "^3.23.8" + }, + "exports": { + ".": "./src/index.ts", + "./effects": "./src/effects.ts" + }, + "files": [ + "src", + "dist", + "!src/__tests__", + "!dist/__tests__" + ], + "version": "0.19.0" +} diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/components/drag-preview.ts b/blocksuite/affine/widget-drag-handle/src/components/drag-preview.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/components/drag-preview.ts rename to blocksuite/affine/widget-drag-handle/src/components/drag-preview.ts diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/components/drop-indicator.ts b/blocksuite/affine/widget-drag-handle/src/components/drop-indicator.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/components/drop-indicator.ts rename to blocksuite/affine/widget-drag-handle/src/components/drop-indicator.ts diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/config.ts b/blocksuite/affine/widget-drag-handle/src/config.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/config.ts rename to blocksuite/affine/widget-drag-handle/src/config.ts diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/consts.ts b/blocksuite/affine/widget-drag-handle/src/consts.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/consts.ts rename to blocksuite/affine/widget-drag-handle/src/consts.ts diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/drag-handle.ts b/blocksuite/affine/widget-drag-handle/src/drag-handle.ts similarity index 98% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/drag-handle.ts rename to blocksuite/affine/widget-drag-handle/src/drag-handle.ts index 6e8f83401312d..97b10bcfc14b2 100644 --- a/blocksuite/blocks/src/root-block/widgets/drag-handle/drag-handle.ts +++ b/blocksuite/affine/widget-drag-handle/src/drag-handle.ts @@ -2,6 +2,7 @@ import { EdgelessCRUDIdentifier } from '@blocksuite/affine-block-surface'; import type { RootBlockModel } from '@blocksuite/affine-model'; import { DocModeProvider } from '@blocksuite/affine-shared/services'; import { + autoScroll, calcDropTarget, type DroppingType, type DropResult, @@ -24,7 +25,6 @@ import { html } from 'lit'; import { query, state } from 'lit/decorators.js'; import { styleMap } from 'lit/directives/style-map.js'; -import { autoScroll } from '../../../root-block/text-selection/utils.js'; import type { DragPreview } from './components/drag-preview.js'; import type { DropIndicator } from './components/drop-indicator.js'; import type { AFFINE_DRAG_HANDLE_WIDGET } from './consts.js'; @@ -75,7 +75,9 @@ export class AffineDragHandleWidget extends WidgetComponent { const blockId = closestBlock.model.id; const model = closestBlock.model; - const isDatabase = matchFlavours(model, ['affine:database']); + const isDatabase = matchFlavours(model, [ + 'affine:database' as BlockSuite.Flavour, + ]); if (isDatabase) return null; // note block can only be dropped into another note block diff --git a/blocksuite/affine/widget-drag-handle/src/effects.ts b/blocksuite/affine/widget-drag-handle/src/effects.ts new file mode 100644 index 0000000000000..7e7545aebd025 --- /dev/null +++ b/blocksuite/affine/widget-drag-handle/src/effects.ts @@ -0,0 +1,10 @@ +import { DragPreview } from './components/drag-preview'; +import { DropIndicator } from './components/drop-indicator'; +import { AFFINE_DRAG_HANDLE_WIDGET } from './consts'; +import { AffineDragHandleWidget } from './drag-handle'; + +export function effects() { + customElements.define('affine-drag-preview', DragPreview); + customElements.define('affine-drop-indicator', DropIndicator); + customElements.define(AFFINE_DRAG_HANDLE_WIDGET, AffineDragHandleWidget); +} diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/helpers/preview-helper.ts b/blocksuite/affine/widget-drag-handle/src/helpers/preview-helper.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/helpers/preview-helper.ts rename to blocksuite/affine/widget-drag-handle/src/helpers/preview-helper.ts diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/helpers/rect-helper.ts b/blocksuite/affine/widget-drag-handle/src/helpers/rect-helper.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/helpers/rect-helper.ts rename to blocksuite/affine/widget-drag-handle/src/helpers/rect-helper.ts diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/helpers/selection-helper.ts b/blocksuite/affine/widget-drag-handle/src/helpers/selection-helper.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/helpers/selection-helper.ts rename to blocksuite/affine/widget-drag-handle/src/helpers/selection-helper.ts diff --git a/blocksuite/affine/widget-drag-handle/src/index.ts b/blocksuite/affine/widget-drag-handle/src/index.ts new file mode 100644 index 0000000000000..508e663d3309a --- /dev/null +++ b/blocksuite/affine/widget-drag-handle/src/index.ts @@ -0,0 +1,7 @@ +import type * as SurfaceEffects from '@blocksuite/affine-block-surface/effects'; + +declare type _GLOBAL_ = typeof SurfaceEffects; + +export * from './consts'; +export * from './drag-handle'; +export * from './utils'; diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/middleware/new-id-cross-doc.ts b/blocksuite/affine/widget-drag-handle/src/middleware/new-id-cross-doc.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/middleware/new-id-cross-doc.ts rename to blocksuite/affine/widget-drag-handle/src/middleware/new-id-cross-doc.ts diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/middleware/reorder-list.ts b/blocksuite/affine/widget-drag-handle/src/middleware/reorder-list.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/middleware/reorder-list.ts rename to blocksuite/affine/widget-drag-handle/src/middleware/reorder-list.ts diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/middleware/surface-ref-to-embed.ts b/blocksuite/affine/widget-drag-handle/src/middleware/surface-ref-to-embed.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/middleware/surface-ref-to-embed.ts rename to blocksuite/affine/widget-drag-handle/src/middleware/surface-ref-to-embed.ts diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/styles.ts b/blocksuite/affine/widget-drag-handle/src/styles.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/styles.ts rename to blocksuite/affine/widget-drag-handle/src/styles.ts diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/utils.ts b/blocksuite/affine/widget-drag-handle/src/utils.ts similarity index 98% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/utils.ts rename to blocksuite/affine/widget-drag-handle/src/utils.ts index 16988a00ac31a..d3e20f6625c72 100644 --- a/blocksuite/blocks/src/root-block/widgets/drag-handle/utils.ts +++ b/blocksuite/affine/widget-drag-handle/src/utils.ts @@ -188,7 +188,9 @@ export const getDropResult = ( const model = closestBlock.model; - const isDatabase = matchFlavours(model, ['affine:database']); + const isDatabase = matchFlavours(model, [ + 'affine:database' as BlockSuite.Flavour, + ]); if (isDatabase) { return dropIndicator; } diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/drag-event-watcher.ts b/blocksuite/affine/widget-drag-handle/src/watchers/drag-event-watcher.ts similarity index 96% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/drag-event-watcher.ts rename to blocksuite/affine/widget-drag-handle/src/watchers/drag-event-watcher.ts index 0923efe2ce176..9f91ad68d6d9e 100644 --- a/blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/drag-event-watcher.ts +++ b/blocksuite/affine/widget-drag-handle/src/watchers/drag-event-watcher.ts @@ -1,4 +1,8 @@ import { ParagraphBlockComponent } from '@blocksuite/affine-block-paragraph'; +import { + addNoteAtPoint, + getSurfaceBlock, +} from '@blocksuite/affine-block-surface'; import type { EmbedCardStyle, NoteBlockModel } from '@blocksuite/affine-model'; import { EMBED_CARD_HEIGHT, @@ -28,8 +32,6 @@ import { GfxControllerIdentifier } from '@blocksuite/block-std/gfx'; import { Bound, Point } from '@blocksuite/global/utils'; import { Job, Slice, type SliceSnapshot } from '@blocksuite/store'; -import type { EdgelessRootBlockComponent } from '../../../edgeless/index.js'; -import { addNoteAtPoint } from '../../../edgeless/utils/common.js'; import { DropIndicator } from '../components/drop-indicator.js'; import { AFFINE_DRAG_HANDLE_WIDGET } from '../consts.js'; import type { AffineDragHandleWidget } from '../drag-handle.js'; @@ -39,16 +41,19 @@ import { surfaceRefToEmbed } from '../middleware/surface-ref-to-embed.js'; import { containBlock, includeTextSelection } from '../utils.js'; export class DragEventWatcher { + private get _gfx() { + return this.widget.std.get(GfxControllerIdentifier); + } + private readonly _computeEdgelessBound = ( x: number, y: number, width: number, height: number ) => { - const controller = this._std.get(GfxControllerIdentifier); const border = 2; const noteScale = this.widget.noteScale.peek(); - const { viewport } = controller; + const { viewport } = this._gfx; const { left: viewportLeft, top: viewportTop } = viewport; const currentViewBound = new Bound( x - viewportLeft, @@ -335,10 +340,9 @@ export class DragEventWatcher { const state = context.get('dndState'); // If drop a note, should do nothing const snapshot = this._deserializeSnapshot(state); - const edgelessRoot = this.widget - .rootComponent as EdgelessRootBlockComponent; + const surfaceBlockModel = getSurfaceBlock(this.widget.doc); - if (!snapshot) { + if (!snapshot || !surfaceBlockModel) { return; } @@ -358,7 +362,7 @@ export class DragEventWatcher { const std = this._std; const job = this._getJob(); job - .snapshotToSlice(snapshot, std.doc, edgelessRoot.surfaceBlockModel.id) + .snapshotToSlice(snapshot, std.doc, surfaceBlockModel.id) .catch(console.error); }; @@ -404,9 +408,9 @@ export class DragEventWatcher { } } - const { left: viewportLeft, top: viewportTop } = edgelessRoot.viewport; + const { left: viewportLeft, top: viewportTop } = this._gfx.viewport; const newNoteId = addNoteAtPoint( - edgelessRoot.std, + this._std, new Point(state.raw.x - viewportLeft, state.raw.y - viewportTop), { scale: this.widget.noteScale.peek(), diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/edgeless-watcher.ts b/blocksuite/affine/widget-drag-handle/src/watchers/edgeless-watcher.ts similarity index 99% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/edgeless-watcher.ts rename to blocksuite/affine/widget-drag-handle/src/watchers/edgeless-watcher.ts index b447fdf8ca284..8981fb4e4223c 100644 --- a/blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/edgeless-watcher.ts +++ b/blocksuite/affine/widget-drag-handle/src/watchers/edgeless-watcher.ts @@ -27,6 +27,7 @@ export class EdgelessWatcher { private readonly _handleEdgelessToolUpdated = ( newTool: GfxToolsFullOptionValue ) => { + // @ts-expect-error FIXME: resolve after gfx tool refactor if (newTool.type === 'default') { this.checkTopLevelBlockSelection(); } else { diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/handle-event-watcher.ts b/blocksuite/affine/widget-drag-handle/src/watchers/handle-event-watcher.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/handle-event-watcher.ts rename to blocksuite/affine/widget-drag-handle/src/watchers/handle-event-watcher.ts diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/keyboard-event-watcher.ts b/blocksuite/affine/widget-drag-handle/src/watchers/keyboard-event-watcher.ts similarity index 100% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/keyboard-event-watcher.ts rename to blocksuite/affine/widget-drag-handle/src/watchers/keyboard-event-watcher.ts diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/page-watcher.ts b/blocksuite/affine/widget-drag-handle/src/watchers/page-watcher.ts similarity index 69% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/page-watcher.ts rename to blocksuite/affine/widget-drag-handle/src/watchers/page-watcher.ts index 75b66cfcc4663..8d287b36fe59e 100644 --- a/blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/page-watcher.ts +++ b/blocksuite/affine/widget-drag-handle/src/watchers/page-watcher.ts @@ -1,26 +1,25 @@ +import { PageViewportService } from '@blocksuite/affine-shared/services'; import { getScrollContainer } from '@blocksuite/affine-shared/utils'; -import type { PageRootBlockComponent } from '../../../page/page-root-block.js'; import type { AffineDragHandleWidget } from '../drag-handle.js'; export class PageWatcher { - get pageRoot() { - return this.widget.rootComponent as PageRootBlockComponent; + get pageViewportService() { + return this.widget.std.get(PageViewportService); } constructor(readonly widget: AffineDragHandleWidget) {} watch() { - const { pageRoot } = this; const { disposables } = this.widget; - const scrollContainer = getScrollContainer(pageRoot); + const scrollContainer = getScrollContainer(this.widget.rootComponent); disposables.add( this.widget.doc.slots.blockUpdated.on(() => this.widget.hide()) ); disposables.add( - pageRoot.slots.viewportUpdated.on(() => { + this.pageViewportService.on(() => { this.widget.hide(); if (this.widget.dropIndicator) { this.widget.dropIndicator.rect = null; diff --git a/blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/pointer-event-watcher.ts b/blocksuite/affine/widget-drag-handle/src/watchers/pointer-event-watcher.ts similarity index 97% rename from blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/pointer-event-watcher.ts rename to blocksuite/affine/widget-drag-handle/src/watchers/pointer-event-watcher.ts index 326cedd745918..69a232c31190d 100644 --- a/blocksuite/blocks/src/root-block/widgets/drag-handle/watchers/pointer-event-watcher.ts +++ b/blocksuite/affine/widget-drag-handle/src/watchers/pointer-event-watcher.ts @@ -6,10 +6,10 @@ import { type PointerEventState, type UIEventHandler, } from '@blocksuite/block-std'; +import { GfxControllerIdentifier } from '@blocksuite/block-std/gfx'; import { Point, throttle } from '@blocksuite/global/utils'; import { computed } from '@preact/signals-core'; -import type { EdgelessRootBlockComponent } from '../../../edgeless/index.js'; import { DRAG_HANDLE_CONTAINER_WIDTH, DRAG_HANDLE_GRABBER_BORDER_RADIUS, @@ -30,19 +30,19 @@ import { } from '../utils.js'; export class PointerEventWatcher { + private get _gfx() { + return this.widget.std.get(GfxControllerIdentifier); + } + private readonly _canEditing = (noteBlock: BlockComponent) => { if (noteBlock.doc.id !== this.widget.doc.id) return false; if (this.widget.mode === 'page') return true; - const edgelessRoot = this.widget - .rootComponent as EdgelessRootBlockComponent; + const selection = this._gfx.selection; const noteBlockId = noteBlock.model.id; - return ( - edgelessRoot.service.selection.editing && - edgelessRoot.service.selection.selectedIds[0] === noteBlockId - ); + return selection.editing && selection.selectedIds[0] === noteBlockId; }; /** diff --git a/blocksuite/affine/widget-drag-handle/tsconfig.json b/blocksuite/affine/widget-drag-handle/tsconfig.json new file mode 100644 index 0000000000000..f1815719da476 --- /dev/null +++ b/blocksuite/affine/widget-drag-handle/tsconfig.json @@ -0,0 +1,44 @@ +{ + "extends": "../../tsconfig.json", + "compilerOptions": { + "rootDir": "./src/", + "outDir": "./dist/", + "noEmit": false + }, + "include": ["./src"], + "references": [ + { + "path": "../../framework/global" + }, + { + "path": "../../framework/store" + }, + { + "path": "../../framework/block-std" + }, + { + "path": "../../framework/inline" + }, + { + "path": "../model" + }, + { + "path": "../components" + }, + { + "path": "../shared" + }, + { + "path": "../block-paragraph" + }, + { + "path": "../block-surface" + }, + { + "path": "../block-note" + }, + { + "path": "../block-list" + } + ] +} diff --git a/blocksuite/blocks/package.json b/blocksuite/blocks/package.json index cb5082b9cccc4..6e04c6fedf4ef 100644 --- a/blocksuite/blocks/package.json +++ b/blocksuite/blocks/package.json @@ -30,6 +30,7 @@ "@blocksuite/affine-components": "workspace:*", "@blocksuite/affine-model": "workspace:*", "@blocksuite/affine-shared": "workspace:*", + "@blocksuite/affine-widget-drag-handle": "workspace:*", "@blocksuite/affine-widget-remote-selection": "workspace:*", "@blocksuite/affine-widget-scroll-anchoring": "workspace:*", "@blocksuite/block-std": "workspace:*", diff --git a/blocksuite/blocks/src/database-block/database-block.ts b/blocksuite/blocks/src/database-block/database-block.ts index 9cfeffecd06f1..05650c80d675c 100644 --- a/blocksuite/blocks/src/database-block/database-block.ts +++ b/blocksuite/blocks/src/database-block/database-block.ts @@ -16,6 +16,7 @@ import { type TelemetryEventMap, TelemetryProvider, } from '@blocksuite/affine-shared/services'; +import { getDropResult } from '@blocksuite/affine-widget-drag-handle'; import { RANGE_SYNC_EXCLUDE_ATTR } from '@blocksuite/block-std'; import { createRecordDetail, @@ -46,7 +47,6 @@ import { computed, signal } from '@preact/signals-core'; import { css, html, nothing, unsafeCSS } from 'lit'; import { EdgelessRootBlockComponent } from '../root-block/index.js'; -import { getDropResult } from '../root-block/widgets/drag-handle/utils.js'; import { popSideDetail } from './components/layout.js'; import type { DatabaseOptionsConfig } from './config.js'; import { HostContextKey } from './context/host-context.js'; diff --git a/blocksuite/blocks/src/effects.ts b/blocksuite/blocks/src/effects.ts index e8359a590261a..289c6671f614b 100644 --- a/blocksuite/blocks/src/effects.ts +++ b/blocksuite/blocks/src/effects.ts @@ -26,6 +26,7 @@ import { SmoothCorner } from '@blocksuite/affine-components/smooth-corner'; import { effects as componentToggleButtonEffects } from '@blocksuite/affine-components/toggle-button'; import { ToggleSwitch } from '@blocksuite/affine-components/toggle-switch'; import { effects as componentToolbarEffects } from '@blocksuite/affine-components/toolbar'; +import { effects as widgetDragHandleEffects } from '@blocksuite/affine-widget-drag-handle/effects'; import { effects as widgetRemoteSelectionEffects } from '@blocksuite/affine-widget-remote-selection/effects'; import { effects as widgetScrollAnchoringEffects } from '@blocksuite/affine-widget-scroll-anchoring/effects'; import type { BlockComponent } from '@blocksuite/block-std'; @@ -148,7 +149,6 @@ import { AFFINE_EMBED_CARD_TOOLBAR_WIDGET, AFFINE_FORMAT_BAR_WIDGET, AffineAIPanelWidget, - AffineDragHandleWidget, AffineEdgelessZoomToolbarWidget, AffineFormatBarWidget, AffineImageToolbarWidget, @@ -176,9 +176,6 @@ import { AIPanelGenerating, AIPanelInput, } from './root-block/widgets/ai-panel/components/index.js'; -import { DragPreview } from './root-block/widgets/drag-handle/components/drag-preview.js'; -import { DropIndicator } from './root-block/widgets/drag-handle/components/drop-indicator.js'; -import { AFFINE_DRAG_HANDLE_WIDGET } from './root-block/widgets/drag-handle/consts.js'; import { AFFINE_EDGELESS_AUTO_CONNECT_WIDGET, EdgelessAutoConnectWidget, @@ -259,6 +256,7 @@ export function effects() { widgetFrameTitleEffects(); widgetEdgelessElementToolbarEffects(); widgetRemoteSelectionEffects(); + widgetDragHandleEffects(); dataViewEffects(); customElements.define('affine-database-title', DatabaseTitle); @@ -433,7 +431,6 @@ export function effects() { 'edgeless-group-title-editor', EdgelessGroupTitleEditor ); - customElements.define('affine-drag-preview', DragPreview); customElements.define(EDGELESS_TOOLBAR_WIDGET, EdgelessToolbarWidget); customElements.define('edgeless-shape-style-panel', EdgelessShapeStylePanel); customElements.define( @@ -446,7 +443,6 @@ export function effects() { ); customElements.define('edgeless-text-editor', EdgelessTextEditor); customElements.define('affine-image-toolbar', AffineImageToolbar); - customElements.define('affine-drop-indicator', DropIndicator); customElements.define('mini-mindmap-root-block', MindmapRootBlock); customElements.define('affine-block-selection', BlockSelection); customElements.define('edgeless-slide-menu', EdgelessSlideMenu); @@ -463,7 +459,6 @@ export function effects() { AFFINE_PAGE_DRAGGING_AREA_WIDGET, AffinePageDraggingAreaWidget ); - customElements.define(AFFINE_DRAG_HANDLE_WIDGET, AffineDragHandleWidget); customElements.define(AFFINE_EDGELESS_COPILOT_WIDGET, EdgelessCopilotWidget); customElements.define(AFFINE_IMAGE_TOOLBAR_WIDGET, AffineImageToolbarWidget); diff --git a/blocksuite/blocks/src/index.ts b/blocksuite/blocks/src/index.ts index 9c9e992b1ee63..55c9cf88ad42f 100644 --- a/blocksuite/blocks/src/index.ts +++ b/blocksuite/blocks/src/index.ts @@ -31,7 +31,6 @@ export { export { CopilotTool } from './root-block/edgeless/gfx-tool/copilot-tool.js'; export * from './root-block/edgeless/gfx-tool/index.js'; export { EditPropsMiddlewareBuilder } from './root-block/edgeless/middlewares/base.js'; -export * from './root-block/edgeless/utils/common.js'; export { EdgelessSnapManager } from './root-block/edgeless/utils/snap-manager.js'; export * from './root-block/index.js'; export * from './schemas.js'; diff --git a/blocksuite/blocks/src/root-block/edgeless/edgeless-root-spec.ts b/blocksuite/blocks/src/root-block/edgeless/edgeless-root-spec.ts index 736cdaf6461fb..9dcc44fe2b128 100644 --- a/blocksuite/blocks/src/root-block/edgeless/edgeless-root-spec.ts +++ b/blocksuite/blocks/src/root-block/edgeless/edgeless-root-spec.ts @@ -4,8 +4,10 @@ import { DocDisplayMetaService, DocModeService, EmbedOptionService, + PageViewportServiceExtension, ThemeService, } from '@blocksuite/affine-shared/services'; +import { AFFINE_DRAG_HANDLE_WIDGET } from '@blocksuite/affine-widget-drag-handle'; import { AFFINE_DOC_REMOTE_SELECTION_WIDGET, AFFINE_EDGELESS_REMOTE_SELECTION_WIDGET, @@ -25,7 +27,6 @@ import { literal, unsafeStatic } from 'lit/static-html.js'; import { ExportManagerExtension } from '../../_common/export-manager/export-manager.js'; import { RootBlockAdapterExtensions } from '../adapters/extension.js'; import { commands } from '../commands/index.js'; -import { AFFINE_DRAG_HANDLE_WIDGET } from '../widgets/drag-handle/consts.js'; import { AFFINE_EDGELESS_AUTO_CONNECT_WIDGET } from '../widgets/edgeless-auto-connect/edgeless-auto-connect.js'; import { AFFINE_EDGELESS_ZOOM_TOOLBAR_WIDGET } from '../widgets/edgeless-zoom-toolbar/index.js'; import { EDGELESS_ELEMENT_TOOLBAR_WIDGET } from '../widgets/element-toolbar/index.js'; @@ -97,6 +98,7 @@ const EdgelessCommonExtension: ExtensionType[] = [ ExportManagerExtension, ToolController, DNDAPIExtension, + PageViewportServiceExtension, DocDisplayMetaService, RootBlockAdapterExtensions, FileDropExtension, diff --git a/blocksuite/blocks/src/root-block/edgeless/gfx-tool/note-tool.ts b/blocksuite/blocks/src/root-block/edgeless/gfx-tool/note-tool.ts index 79017ba99edbf..9c26c01ee0775 100644 --- a/blocksuite/blocks/src/root-block/edgeless/gfx-tool/note-tool.ts +++ b/blocksuite/blocks/src/root-block/edgeless/gfx-tool/note-tool.ts @@ -1,4 +1,5 @@ import type { SurfaceBlockComponent } from '@blocksuite/affine-block-surface'; +import { addNote } from '@blocksuite/affine-block-surface'; import { DEFAULT_NOTE_HEIGHT, DEFAULT_NOTE_WIDTH, @@ -11,7 +12,6 @@ import { Point } from '@blocksuite/global/utils'; import { effect } from '@preact/signals-core'; import { hasClassNameInList } from '../../../_common/utils/index.js'; -import { addNote } from '../utils/common.js'; import { EXCLUDING_MOUSE_OUT_CLASS_LIST } from '../utils/consts.js'; import { DraggingNoteOverlay, NoteOverlay } from '../utils/tool-overlay.js'; diff --git a/blocksuite/blocks/src/root-block/edgeless/utils/consts.ts b/blocksuite/blocks/src/root-block/edgeless/utils/consts.ts index 22e2f6d00d1c5..32efde73a6057 100644 --- a/blocksuite/blocks/src/root-block/edgeless/utils/consts.ts +++ b/blocksuite/blocks/src/root-block/edgeless/utils/consts.ts @@ -6,8 +6,6 @@ import { StrokeStyle, } from '@blocksuite/affine-model'; -export const DEFAULT_NOTE_OFFSET_X = 30; -export const DEFAULT_NOTE_OFFSET_Y = 40; export const NOTE_OVERLAY_OFFSET_X = 6; export const NOTE_OVERLAY_OFFSET_Y = 6; export const NOTE_OVERLAY_WIDTH = 100; diff --git a/blocksuite/blocks/src/root-block/page/page-root-block.ts b/blocksuite/blocks/src/root-block/page/page-root-block.ts index ff9487d82ba7f..fc0986d2e7304 100644 --- a/blocksuite/blocks/src/root-block/page/page-root-block.ts +++ b/blocksuite/blocks/src/root-block/page/page-root-block.ts @@ -1,6 +1,7 @@ import { focusTextModel } from '@blocksuite/affine-components/rich-text'; import type { NoteBlockModel, RootBlockModel } from '@blocksuite/affine-model'; import { NoteDisplayMode } from '@blocksuite/affine-model'; +import { PageViewportService } from '@blocksuite/affine-shared/services'; import type { Viewport } from '@blocksuite/affine-shared/types'; import { focusTitle, @@ -141,10 +142,6 @@ export class PageRootBlockComponent extends BlockComponent< return getScrollContainer(this); } - get slots() { - return this.service.slots; - } - get viewport(): Viewport | null { if (!this.viewportElement) { return null; @@ -172,9 +169,9 @@ export class PageRootBlockComponent extends BlockComponent< get viewportElement(): HTMLDivElement | null { if (this._viewportElement) return this._viewportElement; - this._viewportElement = this.host.closest( + this._viewportElement = this.host.closest( '.affine-page-viewport' - ) as HTMLDivElement | null; + ); return this._viewportElement; } @@ -198,12 +195,14 @@ export class PageRootBlockComponent extends BlockComponent< if (!viewport || !viewportElement) { return; } + + const viewportService = this.std.get(PageViewportService); // when observe viewportElement resize, emit viewport update event const resizeObserver = new ResizeObserver( (entries: ResizeObserverEntry[]) => { for (const { target } of entries) { if (target === viewportElement) { - this.slots.viewportUpdated.emit(viewport); + viewportService.emit(viewport); break; } } diff --git a/blocksuite/blocks/src/root-block/page/page-root-spec.ts b/blocksuite/blocks/src/root-block/page/page-root-spec.ts index 608fa63bbc63f..307ed44e80349 100644 --- a/blocksuite/blocks/src/root-block/page/page-root-spec.ts +++ b/blocksuite/blocks/src/root-block/page/page-root-spec.ts @@ -4,8 +4,10 @@ import { DocDisplayMetaService, DocModeService, EmbedOptionService, + PageViewportServiceExtension, ThemeService, } from '@blocksuite/affine-shared/services'; +import { AFFINE_DRAG_HANDLE_WIDGET } from '@blocksuite/affine-widget-drag-handle'; import { AFFINE_DOC_REMOTE_SELECTION_WIDGET } from '@blocksuite/affine-widget-remote-selection'; import { AFFINE_SCROLL_ANCHORING_WIDGET } from '@blocksuite/affine-widget-scroll-anchoring'; import { @@ -20,7 +22,6 @@ import { literal, unsafeStatic } from 'lit/static-html.js'; import { ExportManagerExtension } from '../../_common/export-manager/export-manager.js'; import { RootBlockAdapterExtensions } from '../adapters/extension.js'; import { commands } from '../commands/index.js'; -import { AFFINE_DRAG_HANDLE_WIDGET } from '../widgets/drag-handle/consts.js'; import { AFFINE_EMBED_CARD_TOOLBAR_WIDGET } from '../widgets/embed-card-toolbar/embed-card-toolbar.js'; import { AFFINE_FORMAT_BAR_WIDGET } from '../widgets/format-bar/format-bar.js'; import { AFFINE_INNER_MODAL_WIDGET } from '../widgets/inner-modal/inner-modal.js'; @@ -74,6 +75,7 @@ export const PageRootBlockSpec: ExtensionType[] = [ WidgetViewMapExtension('affine:page', pageRootWidgetViewMap), ExportManagerExtension, DNDAPIExtension, + PageViewportServiceExtension, DocDisplayMetaService, RootBlockAdapterExtensions, FileDropExtension, diff --git a/blocksuite/blocks/src/root-block/types.ts b/blocksuite/blocks/src/root-block/types.ts index 644046dca8120..d3c9117d317b5 100644 --- a/blocksuite/blocks/src/root-block/types.ts +++ b/blocksuite/blocks/src/root-block/types.ts @@ -1,3 +1,4 @@ +import type { AFFINE_DRAG_HANDLE_WIDGET } from '@blocksuite/affine-widget-drag-handle'; import type { AFFINE_DOC_REMOTE_SELECTION_WIDGET, AFFINE_EDGELESS_REMOTE_SELECTION_WIDGET, @@ -5,7 +6,6 @@ import type { import type { EdgelessRootBlockComponent } from './edgeless/edgeless-root-block.js'; import type { PageRootBlockComponent } from './page/page-root-block.js'; -import type { AFFINE_DRAG_HANDLE_WIDGET } from './widgets/drag-handle/consts.js'; import type { AFFINE_EDGELESS_ZOOM_TOOLBAR_WIDGET } from './widgets/edgeless-zoom-toolbar/index.js'; import type { EDGELESS_ELEMENT_TOOLBAR_WIDGET } from './widgets/element-toolbar/index.js'; import type { AFFINE_EMBED_CARD_TOOLBAR_WIDGET } from './widgets/embed-card-toolbar/embed-card-toolbar.js'; diff --git a/blocksuite/blocks/src/root-block/widgets/index.ts b/blocksuite/blocks/src/root-block/widgets/index.ts index 08bfe595976c1..dc0fa9b3a03fd 100644 --- a/blocksuite/blocks/src/root-block/widgets/index.ts +++ b/blocksuite/blocks/src/root-block/widgets/index.ts @@ -6,7 +6,6 @@ export { type AffineAIPanelState, type AffineAIPanelWidgetConfig, } from './ai-panel/type.js'; -export { AffineDragHandleWidget } from './drag-handle/drag-handle.js'; export { AFFINE_EDGELESS_COPILOT_WIDGET, EdgelessCopilotWidget, @@ -53,7 +52,3 @@ export { type AffineSlashSubMenu, } from './slash-menu/index.js'; export { AffineSurfaceRefToolbar } from './surface-ref-toolbar/surface-ref-toolbar.js'; -export { - AffineDocRemoteSelectionWidget, - EdgelessRemoteSelectionWidget, -} from '@blocksuite/affine-widget-remote-selection'; diff --git a/blocksuite/blocks/src/root-block/widgets/page-dragging-area/page-dragging-area.ts b/blocksuite/blocks/src/root-block/widgets/page-dragging-area/page-dragging-area.ts index cbb068ab95d5a..588c73fe6ce7c 100644 --- a/blocksuite/blocks/src/root-block/widgets/page-dragging-area/page-dragging-area.ts +++ b/blocksuite/blocks/src/root-block/widgets/page-dragging-area/page-dragging-area.ts @@ -1,5 +1,6 @@ import type { RootBlockModel } from '@blocksuite/affine-model'; import { + autoScroll, getScrollContainer, matchFlavours, } from '@blocksuite/affine-shared/utils'; @@ -15,7 +16,6 @@ import { state } from 'lit/decorators.js'; import { styleMap } from 'lit/directives/style-map.js'; import type { PageRootBlockComponent } from '../../index.js'; -import { autoScroll } from '../../text-selection/utils.js'; type Rect = { left: number; diff --git a/blocksuite/blocks/tsconfig.json b/blocksuite/blocks/tsconfig.json index fac7f0d263314..4505763ae3b0d 100644 --- a/blocksuite/blocks/tsconfig.json +++ b/blocksuite/blocks/tsconfig.json @@ -75,6 +75,9 @@ }, { "path": "../affine/widget-remote-selection" + }, + { + "path": "../affine/widget-drag-handle" } ] } diff --git a/tools/utils/src/workspace.gen.ts b/tools/utils/src/workspace.gen.ts index ac6ab7e5bf9b9..914742c4678b1 100644 --- a/tools/utils/src/workspace.gen.ts +++ b/tools/utils/src/workspace.gen.ts @@ -234,6 +234,23 @@ export const PackageList = [ 'blocksuite/framework/store', ], }, + { + location: 'blocksuite/affine/widget-drag-handle', + name: '@blocksuite/affine-widget-drag-handle', + workspaceDependencies: [ + 'blocksuite/affine/block-list', + 'blocksuite/affine/block-note', + 'blocksuite/affine/block-paragraph', + 'blocksuite/affine/block-surface', + 'blocksuite/affine/components', + 'blocksuite/affine/model', + 'blocksuite/affine/shared', + 'blocksuite/framework/block-std', + 'blocksuite/framework/global', + 'blocksuite/framework/inline', + 'blocksuite/framework/store', + ], + }, { location: 'blocksuite/affine/widget-remote-selection', name: '@blocksuite/affine-widget-remote-selection', @@ -274,6 +291,7 @@ export const PackageList = [ 'blocksuite/affine/components', 'blocksuite/affine/model', 'blocksuite/affine/shared', + 'blocksuite/affine/widget-drag-handle', 'blocksuite/affine/widget-remote-selection', 'blocksuite/affine/widget-scroll-anchoring', 'blocksuite/framework/block-std', @@ -624,6 +642,7 @@ export type PackageName = | '@blocksuite/data-view' | '@blocksuite/affine-model' | '@blocksuite/affine-shared' + | '@blocksuite/affine-widget-drag-handle' | '@blocksuite/affine-widget-remote-selection' | '@blocksuite/affine-widget-scroll-anchoring' | '@blocksuite/blocks' diff --git a/tsconfig.project.json b/tsconfig.project.json index a7ea6d2ba0186..700fad5780591 100644 --- a/tsconfig.project.json +++ b/tsconfig.project.json @@ -24,6 +24,7 @@ { "path": "./blocksuite/affine/data-view" }, { "path": "./blocksuite/affine/model" }, { "path": "./blocksuite/affine/shared" }, + { "path": "./blocksuite/affine/widget-drag-handle" }, { "path": "./blocksuite/affine/widget-remote-selection" }, { "path": "./blocksuite/affine/widget-scroll-anchoring" }, { "path": "./blocksuite/blocks" }, diff --git a/yarn.lock b/yarn.lock index b3c832db41cdb..883d3f9cf7665 100644 --- a/yarn.lock +++ b/yarn.lock @@ -3613,6 +3613,32 @@ __metadata: languageName: unknown linkType: soft +"@blocksuite/affine-widget-drag-handle@workspace:*, @blocksuite/affine-widget-drag-handle@workspace:blocksuite/affine/widget-drag-handle": + version: 0.0.0-use.local + resolution: "@blocksuite/affine-widget-drag-handle@workspace:blocksuite/affine/widget-drag-handle" + dependencies: + "@blocksuite/affine-block-list": "workspace:*" + "@blocksuite/affine-block-note": "workspace:*" + "@blocksuite/affine-block-paragraph": "workspace:*" + "@blocksuite/affine-block-surface": "workspace:*" + "@blocksuite/affine-components": "workspace:*" + "@blocksuite/affine-model": "workspace:*" + "@blocksuite/affine-shared": "workspace:*" + "@blocksuite/block-std": "workspace:*" + "@blocksuite/global": "workspace:*" + "@blocksuite/icons": "npm:^2.1.75" + "@blocksuite/inline": "workspace:*" + "@blocksuite/store": "workspace:*" + "@floating-ui/dom": "npm:^1.6.10" + "@lit/context": "npm:^1.1.2" + "@preact/signals-core": "npm:^1.8.0" + "@toeverything/theme": "npm:^1.1.1" + lit: "npm:^3.2.0" + minimatch: "npm:^10.0.1" + zod: "npm:^3.23.8" + languageName: unknown + linkType: soft + "@blocksuite/affine-widget-remote-selection@workspace:*, @blocksuite/affine-widget-remote-selection@workspace:blocksuite/affine/widget-remote-selection": version: 0.0.0-use.local resolution: "@blocksuite/affine-widget-remote-selection@workspace:blocksuite/affine/widget-remote-selection" @@ -3696,6 +3722,7 @@ __metadata: "@blocksuite/affine-components": "workspace:*" "@blocksuite/affine-model": "workspace:*" "@blocksuite/affine-shared": "workspace:*" + "@blocksuite/affine-widget-drag-handle": "workspace:*" "@blocksuite/affine-widget-remote-selection": "workspace:*" "@blocksuite/affine-widget-scroll-anchoring": "workspace:*" "@blocksuite/block-std": "workspace:*"