mirror of
https://github.com/toeverything/AFFiNE.git
synced 2026-07-30 00:29:46 +08:00
chore: dnd cleanup (#9899)
This commit is contained in:
@@ -1,4 +1,4 @@
|
||||
import { FileDropConfigExtension } from '@blocksuite/affine-components/drag-indicator';
|
||||
import { FileDropConfigExtension } from '@blocksuite/affine-components/drop-indicator';
|
||||
import { AttachmentBlockSchema } from '@blocksuite/affine-model';
|
||||
import { TelemetryProvider } from '@blocksuite/affine-shared/services';
|
||||
import {
|
||||
|
||||
@@ -4,7 +4,7 @@ import {
|
||||
popMenu,
|
||||
popupTargetFromElement,
|
||||
} from '@blocksuite/affine-components/context-menu';
|
||||
import { DragIndicator } from '@blocksuite/affine-components/drag-indicator';
|
||||
import { DropIndicator } from '@blocksuite/affine-components/drop-indicator';
|
||||
import { PeekViewProvider } from '@blocksuite/affine-components/peek';
|
||||
import { toast } from '@blocksuite/affine-components/toast';
|
||||
import type { DatabaseBlockModel } from '@blocksuite/affine-model';
|
||||
@@ -241,7 +241,7 @@ export class DatabaseBlockComponent extends CaptionedBlockComponent<DatabaseBloc
|
||||
}
|
||||
);
|
||||
|
||||
indicator = new DragIndicator();
|
||||
indicator = new DropIndicator();
|
||||
|
||||
onDrag = (evt: MouseEvent, id: string): (() => void) => {
|
||||
const result = getDropResult(evt);
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { FileDropConfigExtension } from '@blocksuite/affine-components/drag-indicator';
|
||||
import { FileDropConfigExtension } from '@blocksuite/affine-components/drop-indicator';
|
||||
import { ImageBlockSchema, MAX_IMAGE_WIDTH } from '@blocksuite/affine-model';
|
||||
import { TelemetryProvider } from '@blocksuite/affine-shared/services';
|
||||
import {
|
||||
|
||||
@@ -54,7 +54,7 @@
|
||||
"./caption": "./src/caption/index.ts",
|
||||
"./context-menu": "./src/context-menu/index.ts",
|
||||
"./date-picker": "./src/date-picker/index.ts",
|
||||
"./drag-indicator": "./src/drag-indicator/index.ts",
|
||||
"./drop-indicator": "./src/drop-indicator/index.ts",
|
||||
"./filterable-list": "./src/filterable-list/index.ts",
|
||||
"./virtual-keyboard": "./src/virtual-keyboard/index.ts",
|
||||
"./toggle-button": "./src/toggle-button/index.ts",
|
||||
|
||||
@@ -1,44 +0,0 @@
|
||||
import type { Rect } from '@blocksuite/global/utils';
|
||||
import { css, html, LitElement } from 'lit';
|
||||
import { property } from 'lit/decorators.js';
|
||||
import { styleMap } from 'lit/directives/style-map.js';
|
||||
|
||||
export class DragIndicator extends LitElement {
|
||||
static override styles = css`
|
||||
.affine-drag-indicator {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
background: var(--affine-primary-color);
|
||||
transition-property: width, height, transform;
|
||||
transition-duration: 100ms;
|
||||
transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1);
|
||||
transition-delay: 0s;
|
||||
transform-origin: 0 0;
|
||||
pointer-events: none;
|
||||
z-index: 2;
|
||||
}
|
||||
`;
|
||||
|
||||
override render() {
|
||||
if (!this.rect) {
|
||||
return null;
|
||||
}
|
||||
const { left, top, width, height } = this.rect;
|
||||
const style = styleMap({
|
||||
width: `${width}px`,
|
||||
height: `${height}px`,
|
||||
transform: `translate(${left}px, ${top}px)`,
|
||||
});
|
||||
return html`<div class="affine-drag-indicator" style=${style}></div>`;
|
||||
}
|
||||
|
||||
@property({ attribute: false })
|
||||
accessor rect: Rect | null = null;
|
||||
}
|
||||
|
||||
declare global {
|
||||
interface HTMLElementTagNameMap {
|
||||
'affine-drag-indicator': DragIndicator;
|
||||
}
|
||||
}
|
||||
+2
-4
@@ -25,14 +25,12 @@ export class DropIndicator extends LitElement {
|
||||
return null;
|
||||
}
|
||||
|
||||
const parentRect = this.parentElement!.getBoundingClientRect();
|
||||
const { left, top, width, height } = this.rect;
|
||||
|
||||
const style = styleMap({
|
||||
width: `${width}px`,
|
||||
height: `${height}px`,
|
||||
top: `${top - parentRect.y}px`,
|
||||
left: `${left - parentRect.x}px`,
|
||||
top: `${top}px`,
|
||||
left: `${left}px`,
|
||||
});
|
||||
|
||||
return html`<div class="affine-drop-indicator" style=${style}></div>`;
|
||||
+10
-16
@@ -17,7 +17,7 @@ import { Point, throttle } from '@blocksuite/global/utils';
|
||||
import type { BlockModel, ExtensionType } from '@blocksuite/store';
|
||||
import { computed, signal } from '@preact/signals-core';
|
||||
|
||||
import type { DragIndicator } from './drag-indicator';
|
||||
import { DropIndicator } from './drop-indicator';
|
||||
|
||||
export type DropProps = {
|
||||
std: BlockStdScope;
|
||||
@@ -39,20 +39,7 @@ export type FileDropOptions = {
|
||||
export class FileDropExtension extends LifeCycleWatcher {
|
||||
static override readonly key = 'FileDropExtension';
|
||||
|
||||
static get indicator() {
|
||||
let indicator = document.querySelector<DragIndicator>(
|
||||
'affine-drag-indicator'
|
||||
);
|
||||
|
||||
if (!indicator) {
|
||||
indicator = document.createElement(
|
||||
'affine-drag-indicator'
|
||||
) as DragIndicator;
|
||||
document.body.append(indicator);
|
||||
}
|
||||
|
||||
return indicator;
|
||||
}
|
||||
indicator: DropIndicator = new DropIndicator();
|
||||
|
||||
dragging$ = signal(false);
|
||||
|
||||
@@ -166,10 +153,17 @@ export class FileDropExtension extends LifeCycleWatcher {
|
||||
return this.std.host;
|
||||
}
|
||||
|
||||
override unmounted(): void {
|
||||
super.unmounted();
|
||||
this.indicator.remove();
|
||||
}
|
||||
|
||||
override mounted() {
|
||||
super.mounted();
|
||||
const std = this.std;
|
||||
|
||||
std.host.ownerDocument.body.append(this.indicator);
|
||||
|
||||
std.event.disposables.add(
|
||||
this.point$.subscribe(
|
||||
throttle(
|
||||
@@ -198,7 +192,7 @@ export class FileDropExtension extends LifeCycleWatcher {
|
||||
|
||||
std.event.disposables.add(
|
||||
this.dropTarget$.subscribe(target => {
|
||||
FileDropExtension.indicator.rect = this._disableIndicator
|
||||
this.indicator.rect = this._disableIndicator
|
||||
? null
|
||||
: (target?.rect ?? null);
|
||||
})
|
||||
+3
-3
@@ -1,4 +1,4 @@
|
||||
import { DragIndicator } from './drag-indicator';
|
||||
import { DropIndicator } from './drop-indicator';
|
||||
export {
|
||||
type DropProps,
|
||||
FileDropConfigExtension,
|
||||
@@ -6,8 +6,8 @@ export {
|
||||
type FileDropOptions,
|
||||
} from './file-drop-manager';
|
||||
|
||||
export { DragIndicator };
|
||||
export { DropIndicator };
|
||||
|
||||
export function effects() {
|
||||
customElements.define('affine-drag-indicator', DragIndicator);
|
||||
customElements.define('affine-drop-indicator', DropIndicator);
|
||||
}
|
||||
@@ -36,6 +36,9 @@ export class AffineDragHandleWidget extends WidgetComponent<RootBlockModel> {
|
||||
|
||||
private _anchorModelDisposables: DisposableGroup | null = null;
|
||||
|
||||
/**
|
||||
* Used to handle drag behavior
|
||||
*/
|
||||
private readonly _dragEventWatcher = new DragEventWatcher(this);
|
||||
|
||||
private readonly _handleEventWatcher = new HandleEventWatcher(this);
|
||||
@@ -54,11 +57,6 @@ export class AffineDragHandleWidget extends WidgetComponent<RootBlockModel> {
|
||||
this.isTopLevelDragHandleVisible = false;
|
||||
|
||||
this.pointerEventWatcher.reset();
|
||||
this._resetCursor();
|
||||
};
|
||||
|
||||
private readonly _resetCursor = () => {
|
||||
document.documentElement.classList.remove('affine-drag-preview-grabbing');
|
||||
};
|
||||
|
||||
anchorBlockId = signal<string | null>(null);
|
||||
|
||||
@@ -1,8 +1,6 @@
|
||||
import { DropIndicator } from './components/drop-indicator';
|
||||
import { AFFINE_DRAG_HANDLE_WIDGET } from './consts';
|
||||
import { AffineDragHandleWidget } from './drag-handle';
|
||||
|
||||
export function effects() {
|
||||
customElements.define('affine-drop-indicator', DropIndicator);
|
||||
customElements.define(AFFINE_DRAG_HANDLE_WIDGET, AffineDragHandleWidget);
|
||||
}
|
||||
|
||||
@@ -3,6 +3,7 @@ import {
|
||||
addNoteAtPoint,
|
||||
getSurfaceBlock,
|
||||
} from '@blocksuite/affine-block-surface';
|
||||
import { DropIndicator } from '@blocksuite/affine-components/drop-indicator';
|
||||
import type { EmbedCardStyle, NoteBlockModel } from '@blocksuite/affine-model';
|
||||
import {
|
||||
BLOCK_CHILDREN_CONTAINER_PADDING_LEFT,
|
||||
@@ -23,7 +24,6 @@ import {
|
||||
} from '@blocksuite/affine-shared/utils';
|
||||
import {
|
||||
type BlockComponent,
|
||||
BlockSelection,
|
||||
type BlockStdScope,
|
||||
type DragFromBlockSuite,
|
||||
type DragPayload,
|
||||
@@ -34,7 +34,6 @@ import { GfxControllerIdentifier } from '@blocksuite/block-std/gfx';
|
||||
import { Bound, last, Point, Rect } from '@blocksuite/global/utils';
|
||||
import { Slice, type SliceSnapshot } from '@blocksuite/store';
|
||||
|
||||
import { DropIndicator } from '../components/drop-indicator.js';
|
||||
import type { AffineDragHandleWidget } from '../drag-handle.js';
|
||||
import { PreviewHelper } from '../helpers/preview-helper.js';
|
||||
import { newIdCrossDoc } from '../middleware/new-id-cross-doc.js';
|
||||
@@ -66,6 +65,8 @@ export class DragEventWatcher {
|
||||
|
||||
previewHelper = new PreviewHelper(this.widget);
|
||||
|
||||
dropTargetCleanUps: Map<string, (() => void)[]> = new Map();
|
||||
|
||||
get host() {
|
||||
return this.widget.host;
|
||||
}
|
||||
@@ -257,25 +258,6 @@ export class DragEventWatcher {
|
||||
}
|
||||
};
|
||||
|
||||
private readonly _getDraggedBlock = (draggedBlock: BlockComponent) => {
|
||||
return this._selectAndSetDraggingBlock(draggedBlock);
|
||||
};
|
||||
|
||||
private readonly _selectAndSetDraggingBlock = (
|
||||
hoveredBlock: BlockComponent
|
||||
) => {
|
||||
this.std.selection.setGroup('note', [
|
||||
this.std.selection.create(BlockSelection, {
|
||||
blockId: hoveredBlock.blockId,
|
||||
}),
|
||||
]);
|
||||
|
||||
return {
|
||||
models: [hoveredBlock.model],
|
||||
snapshot: this._toSnapshot([hoveredBlock]),
|
||||
};
|
||||
};
|
||||
|
||||
private readonly _getSnapshotFromHoveredBlocks = () => {
|
||||
const hoverBlock = this.widget.anchorBlockComponent.peek()!;
|
||||
const isInSurface = isGfxBlockComponent(hoverBlock);
|
||||
@@ -620,6 +602,161 @@ export class DragEventWatcher {
|
||||
return std === this.std;
|
||||
}
|
||||
|
||||
private _makeDraggable(target: HTMLElement) {
|
||||
const std = this.std;
|
||||
|
||||
return std.dnd.draggable<DragBlockEntity>({
|
||||
element: target,
|
||||
canDrag: () => {
|
||||
const hoverBlock = this.widget.anchorBlockComponent.peek();
|
||||
return hoverBlock ? true : false;
|
||||
},
|
||||
onDragStart: () => {
|
||||
this.widget.dragging = true;
|
||||
},
|
||||
onDrop: () => {
|
||||
this._cleanup();
|
||||
},
|
||||
setDragPreview: ({ source, container }) => {
|
||||
if (!source.data?.bsEntity?.modelIds.length) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.previewHelper.renderDragPreview(
|
||||
source.data?.bsEntity?.modelIds,
|
||||
container
|
||||
);
|
||||
},
|
||||
setDragData: () => {
|
||||
const { snapshot } = this._getSnapshotFromHoveredBlocks();
|
||||
|
||||
return {
|
||||
type: 'blocks',
|
||||
modelIds: snapshot ? extractIdsFromSnapshot(snapshot) : [],
|
||||
snapshot,
|
||||
};
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
private _makeDropTarget(view: BlockComponent) {
|
||||
if (view.model.role !== 'content' && view.model.role !== 'hub') {
|
||||
return;
|
||||
}
|
||||
|
||||
const widget = this.widget;
|
||||
const cleanups: (() => void)[] = [];
|
||||
|
||||
cleanups.push(
|
||||
this.std.dnd.dropTarget<
|
||||
DragBlockEntity,
|
||||
{
|
||||
modelId: string;
|
||||
}
|
||||
>({
|
||||
element: view,
|
||||
getIsSticky: () => true,
|
||||
canDrop: ({ source }) => {
|
||||
if (source.data.bsEntity?.type === 'blocks') {
|
||||
return (
|
||||
source.data.from?.docId !== widget.doc.id ||
|
||||
source.data.bsEntity.modelIds.every(id => id !== view.model.id)
|
||||
);
|
||||
}
|
||||
|
||||
return false;
|
||||
},
|
||||
setDropData: () => {
|
||||
return {
|
||||
modelId: view.model.id,
|
||||
};
|
||||
},
|
||||
})
|
||||
);
|
||||
|
||||
if (matchFlavours(view.model, ['affine:attachment', 'affine:bookmark'])) {
|
||||
cleanups.push(this._makeDraggable(view));
|
||||
}
|
||||
|
||||
if (this.dropTargetCleanUps.has(view.model.id)) {
|
||||
this.dropTargetCleanUps.get(view.model.id)!.forEach(clean => clean());
|
||||
}
|
||||
|
||||
this.dropTargetCleanUps.set(view.model.id, cleanups);
|
||||
}
|
||||
|
||||
private _monitorBlockDrag() {
|
||||
return this.std.dnd.monitor<DragBlockEntity>({
|
||||
canMonitor: ({ source }) => {
|
||||
const entity = source.data?.bsEntity;
|
||||
|
||||
return entity?.type === 'blocks' && !!entity.snapshot;
|
||||
},
|
||||
onDropTargetChange: ({ location }) => {
|
||||
this._clearDropIndicator();
|
||||
|
||||
if (
|
||||
!this._isDropOnCurrentEditor(
|
||||
(location.current.dropTargets[0]?.element as BlockComponent)?.std
|
||||
)
|
||||
) {
|
||||
return;
|
||||
}
|
||||
},
|
||||
onDrop: ({ location, source }) => {
|
||||
this._clearDropIndicator();
|
||||
|
||||
if (
|
||||
!this._isDropOnCurrentEditor(
|
||||
(location.current.dropTargets[0]?.element as BlockComponent)?.std
|
||||
)
|
||||
) {
|
||||
return;
|
||||
}
|
||||
|
||||
const target = location.current.dropTargets[0];
|
||||
const point = new Point(
|
||||
location.current.input.clientX,
|
||||
location.current.input.clientY
|
||||
);
|
||||
const dragPayload = source.data;
|
||||
const dropPayload = target.data;
|
||||
|
||||
this._onDrop(
|
||||
target.element as BlockComponent,
|
||||
dragPayload,
|
||||
dropPayload,
|
||||
point
|
||||
);
|
||||
},
|
||||
onDrag: ({ location, source }) => {
|
||||
if (
|
||||
!this._isDropOnCurrentEditor(
|
||||
(location.current.dropTargets[0]?.element as BlockComponent)?.std
|
||||
) ||
|
||||
!location.current.dropTargets[0]
|
||||
) {
|
||||
return;
|
||||
}
|
||||
|
||||
const target = location.current.dropTargets[0];
|
||||
const point = new Point(
|
||||
location.current.input.clientX,
|
||||
location.current.input.clientY
|
||||
);
|
||||
const dragPayload = source.data;
|
||||
const dropPayload = target.data;
|
||||
|
||||
this._onDragMove(
|
||||
point,
|
||||
dragPayload,
|
||||
dropPayload,
|
||||
target.element as BlockComponent
|
||||
);
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
watch() {
|
||||
this.widget.handleEvent('pointerDown', ctx => {
|
||||
const state = ctx.get('pointerState');
|
||||
@@ -652,41 +789,6 @@ export class DragEventWatcher {
|
||||
const disposables = widget.disposables;
|
||||
const scrollable = getScrollContainer(this.host);
|
||||
|
||||
disposables.add(
|
||||
std.dnd.draggable<DragBlockEntity>({
|
||||
element: this.widget,
|
||||
canDrag: () => {
|
||||
const hoverBlock = this.widget.anchorBlockComponent.peek();
|
||||
return hoverBlock ? true : false;
|
||||
},
|
||||
onDragStart: () => {
|
||||
this.widget.dragging = true;
|
||||
},
|
||||
onDrop: () => {
|
||||
this._cleanup();
|
||||
},
|
||||
setDragPreview: ({ source, container }) => {
|
||||
if (!source.data?.bsEntity?.modelIds.length) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.previewHelper.renderDragPreview(
|
||||
source.data?.bsEntity?.modelIds,
|
||||
container
|
||||
);
|
||||
},
|
||||
setDragData: () => {
|
||||
const { snapshot } = this._getSnapshotFromHoveredBlocks();
|
||||
|
||||
return {
|
||||
type: 'blocks',
|
||||
modelIds: snapshot ? extractIdsFromSnapshot(snapshot) : [],
|
||||
snapshot,
|
||||
};
|
||||
},
|
||||
})
|
||||
);
|
||||
|
||||
if (scrollable) {
|
||||
disposables.add(
|
||||
std.dnd.autoScroll<DragBlockEntity>({
|
||||
@@ -698,174 +800,30 @@ export class DragEventWatcher {
|
||||
);
|
||||
}
|
||||
|
||||
disposables.add(this._makeDraggable(this.widget));
|
||||
|
||||
// used to handle drag move and drop
|
||||
disposables.add(
|
||||
std.dnd.monitor<DragBlockEntity>({
|
||||
canMonitor: ({ source }) => {
|
||||
const entity = source.data?.bsEntity;
|
||||
|
||||
return entity?.type === 'blocks' && !!entity.snapshot;
|
||||
},
|
||||
onDropTargetChange: ({ location }) => {
|
||||
this._clearDropIndicator();
|
||||
|
||||
if (
|
||||
!this._isDropOnCurrentEditor(
|
||||
(location.current.dropTargets[0]?.element as BlockComponent)?.std
|
||||
)
|
||||
) {
|
||||
return;
|
||||
}
|
||||
},
|
||||
onDrop: ({ location, source }) => {
|
||||
this._clearDropIndicator();
|
||||
|
||||
if (
|
||||
!this._isDropOnCurrentEditor(
|
||||
(location.current.dropTargets[0]?.element as BlockComponent)?.std
|
||||
)
|
||||
) {
|
||||
return;
|
||||
}
|
||||
|
||||
const target = location.current.dropTargets[0];
|
||||
const point = new Point(
|
||||
location.current.input.clientX,
|
||||
location.current.input.clientY
|
||||
);
|
||||
const dragPayload = source.data;
|
||||
const dropPayload = target.data;
|
||||
|
||||
this._onDrop(
|
||||
target.element as BlockComponent,
|
||||
dragPayload,
|
||||
dropPayload,
|
||||
point
|
||||
);
|
||||
},
|
||||
onDrag: ({ location, source }) => {
|
||||
if (
|
||||
!this._isDropOnCurrentEditor(
|
||||
(location.current.dropTargets[0]?.element as BlockComponent)?.std
|
||||
) ||
|
||||
!location.current.dropTargets[0]
|
||||
) {
|
||||
return;
|
||||
}
|
||||
|
||||
const target = location.current.dropTargets[0];
|
||||
const point = new Point(
|
||||
location.current.input.clientX,
|
||||
location.current.input.clientY
|
||||
);
|
||||
const dragPayload = source.data;
|
||||
const dropPayload = target.data;
|
||||
|
||||
this._onDragMove(
|
||||
point,
|
||||
dragPayload,
|
||||
dropPayload,
|
||||
target.element as BlockComponent
|
||||
);
|
||||
},
|
||||
})
|
||||
);
|
||||
|
||||
let dropTargetCleanUps: Map<string, (() => void)[]> = new Map();
|
||||
const makeBlockComponentDropTarget = (view: BlockComponent) => {
|
||||
if (view.model.role !== 'content' && view.model.role !== 'hub') {
|
||||
return;
|
||||
}
|
||||
|
||||
const cleanups: (() => void)[] = [];
|
||||
|
||||
cleanups.push(
|
||||
std.dnd.dropTarget<
|
||||
DragBlockEntity,
|
||||
{
|
||||
modelId: string;
|
||||
}
|
||||
>({
|
||||
element: view,
|
||||
getIsSticky: () => true,
|
||||
canDrop: ({ source }) => {
|
||||
if (source.data.bsEntity?.type === 'blocks') {
|
||||
return (
|
||||
source.data.from?.docId !== widget.doc.id ||
|
||||
source.data.bsEntity.modelIds.every(id => id !== view.model.id)
|
||||
);
|
||||
}
|
||||
|
||||
return false;
|
||||
},
|
||||
setDropData: () => {
|
||||
return {
|
||||
modelId: view.model.id,
|
||||
};
|
||||
},
|
||||
})
|
||||
);
|
||||
|
||||
if (matchFlavours(view.model, ['affine:attachment', 'affine:bookmark'])) {
|
||||
cleanups.push(
|
||||
std.dnd.draggable<DragBlockEntity>({
|
||||
element: view,
|
||||
canDrag: () => {
|
||||
return !isGfxBlockComponent(view);
|
||||
},
|
||||
onDragStart: () => {
|
||||
this.widget.dragging = true;
|
||||
},
|
||||
onDrop: () => {
|
||||
this._cleanup();
|
||||
},
|
||||
setDragPreview: ({ source, container }) => {
|
||||
if (!source.data?.bsEntity?.modelIds.length) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.previewHelper.renderDragPreview(
|
||||
source.data?.bsEntity?.modelIds,
|
||||
container
|
||||
);
|
||||
},
|
||||
setDragData: () => {
|
||||
const { snapshot } = this._getDraggedBlock(view);
|
||||
|
||||
return {
|
||||
type: 'blocks',
|
||||
modelIds: snapshot ? extractIdsFromSnapshot(snapshot) : [],
|
||||
snapshot,
|
||||
};
|
||||
},
|
||||
})
|
||||
);
|
||||
}
|
||||
|
||||
dropTargetCleanUps.set(view.model.id, cleanups);
|
||||
};
|
||||
disposables.add(this._monitorBlockDrag());
|
||||
|
||||
disposables.add(
|
||||
std.view.viewUpdated.on(payload => {
|
||||
if (payload.type === 'add') {
|
||||
makeBlockComponentDropTarget(payload.view);
|
||||
this._makeDropTarget(payload.view);
|
||||
} else if (
|
||||
payload.type === 'delete' &&
|
||||
dropTargetCleanUps.has(payload.id)
|
||||
this.dropTargetCleanUps.has(payload.id)
|
||||
) {
|
||||
dropTargetCleanUps.get(payload.id)!.forEach(clean => clean());
|
||||
dropTargetCleanUps.delete(payload.id);
|
||||
this.dropTargetCleanUps.get(payload.id)!.forEach(clean => clean());
|
||||
this.dropTargetCleanUps.delete(payload.id);
|
||||
}
|
||||
})
|
||||
);
|
||||
|
||||
std.view.views.forEach(block => {
|
||||
makeBlockComponentDropTarget(block);
|
||||
});
|
||||
std.view.views.forEach(block => this._makeDropTarget(block));
|
||||
|
||||
disposables.add(() => {
|
||||
dropTargetCleanUps.forEach(cleanUps => cleanUps.forEach(fn => fn()));
|
||||
dropTargetCleanUps.clear();
|
||||
this.dropTargetCleanUps.forEach(cleanUps => cleanUps.forEach(fn => fn()));
|
||||
this.dropTargetCleanUps.clear();
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -22,7 +22,7 @@ import { effects as componentCaptionEffects } from '@blocksuite/affine-component
|
||||
import { effects as componentColorPickerEffects } from '@blocksuite/affine-components/color-picker';
|
||||
import { effects as componentContextMenuEffects } from '@blocksuite/affine-components/context-menu';
|
||||
import { effects as componentDatePickerEffects } from '@blocksuite/affine-components/date-picker';
|
||||
import { effects as componentDragIndicatorEffects } from '@blocksuite/affine-components/drag-indicator';
|
||||
import { effects as componentDropIndicatorEffects } from '@blocksuite/affine-components/drop-indicator';
|
||||
import { FilterableListComponent } from '@blocksuite/affine-components/filterable-list';
|
||||
import { IconButton } from '@blocksuite/affine-components/icon-button';
|
||||
import { effects as componentPortalEffects } from '@blocksuite/affine-components/portal';
|
||||
@@ -213,7 +213,7 @@ export function effects() {
|
||||
componentPortalEffects();
|
||||
componentRichTextEffects();
|
||||
componentToolbarEffects();
|
||||
componentDragIndicatorEffects();
|
||||
componentDropIndicatorEffects();
|
||||
componentToggleButtonEffects();
|
||||
componentAiItemEffects();
|
||||
componentColorPickerEffects();
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { FileDropExtension } from '@blocksuite/affine-components/drag-indicator';
|
||||
import { FileDropExtension } from '@blocksuite/affine-components/drop-indicator';
|
||||
import {
|
||||
DNDAPIExtension,
|
||||
DocModeService,
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { FileDropExtension } from '@blocksuite/affine-components/drag-indicator';
|
||||
import { FileDropExtension } from '@blocksuite/affine-components/drop-indicator';
|
||||
import {
|
||||
DNDAPIExtension,
|
||||
DocModeService,
|
||||
|
||||
@@ -96,7 +96,7 @@ const chunkGroups = {
|
||||
require.resolve('@blocksuite/affine-components/caption'),
|
||||
require.resolve('@blocksuite/affine-components/context-menu'),
|
||||
require.resolve('@blocksuite/affine-components/date-picker'),
|
||||
require.resolve('@blocksuite/affine-components/drag-indicator'),
|
||||
require.resolve('@blocksuite/affine-components/drop-indicator'),
|
||||
],
|
||||
affine: [
|
||||
require.resolve('@blocksuite/affine-shared'),
|
||||
|
||||
@@ -66,7 +66,7 @@ test('move drag handle in paragraphs', async ({ page }) => {
|
||||
await initThreeParagraphs(page);
|
||||
await assertRichTexts(page, ['123', '456', '789']);
|
||||
await dragHandleFromBlockToBlockBottomById(page, '2', '4');
|
||||
await expect(page.locator('.affine-drag-indicator')).toBeHidden();
|
||||
await expect(page.locator('.affine-drop-indicator')).toBeHidden();
|
||||
await assertRichTexts(page, ['456', '789', '123']);
|
||||
});
|
||||
|
||||
@@ -76,7 +76,7 @@ test('move drag handle in list', async ({ page }) => {
|
||||
await initThreeLists(page);
|
||||
await assertRichTexts(page, ['123', '456', '789']);
|
||||
await dragHandleFromBlockToBlockBottomById(page, '5', '3', false);
|
||||
await expect(page.locator('.affine-drag-indicator')).toBeHidden();
|
||||
await expect(page.locator('.affine-drop-indicator')).toBeHidden();
|
||||
await assertRichTexts(page, ['123', '789', '456']);
|
||||
});
|
||||
|
||||
@@ -106,11 +106,11 @@ test('move drag handle in nested block', async ({ page }) => {
|
||||
await assertRichTexts(page, ['1', '2', '21', '22', '23', '3']);
|
||||
|
||||
await dragHandleFromBlockToBlockBottomById(page, '5', '7');
|
||||
await expect(page.locator('.affine-drag-indicator')).toBeHidden();
|
||||
await expect(page.locator('.affine-drop-indicator')).toBeHidden();
|
||||
await assertRichTexts(page, ['1', '2', '22', '23', '21', '3']);
|
||||
|
||||
await dragHandleFromBlockToBlockBottomById(page, '3', '8');
|
||||
await expect(page.locator('.affine-drag-indicator')).toBeHidden();
|
||||
await expect(page.locator('.affine-drop-indicator')).toBeHidden();
|
||||
await assertRichTexts(page, ['2', '22', '23', '21', '3', '1']);
|
||||
});
|
||||
|
||||
@@ -146,7 +146,7 @@ test('move drag handle into another block', async ({ page }) => {
|
||||
true,
|
||||
2 * BLOCK_CHILDREN_CONTAINER_PADDING_LEFT
|
||||
);
|
||||
await expect(page.locator('.affine-drag-indicator')).toBeHidden();
|
||||
await expect(page.locator('.affine-drop-indicator')).toBeHidden();
|
||||
await assertRichTexts(page, ['1', '2', '22', '23', '21', '3']);
|
||||
// FIXME(DND)
|
||||
// await assertBlockChildrenIds(page, '7', ['5']);
|
||||
@@ -158,7 +158,7 @@ test('move drag handle into another block', async ({ page }) => {
|
||||
// true,
|
||||
// 2 * BLOCK_CHILDREN_CONTAINER_PADDING_LEFT
|
||||
// );
|
||||
// await expect(page.locator('.affine-drag-indicator')).toBeHidden();
|
||||
// await expect(page.locator('.affine-drop-indicator')).toBeHidden();
|
||||
// await assertRichTexts(page, ['2', '22', '23', '21', '3', '1']);
|
||||
// await assertBlockChildrenIds(page, '8', ['3']);
|
||||
});
|
||||
@@ -193,7 +193,7 @@ test('move to the last block of each level in multi-level nesting', async ({
|
||||
);
|
||||
|
||||
await dragHandleFromBlockToBlockBottomById(page, '3', '9');
|
||||
await expect(page.locator('.affine-drag-indicator')).toBeHidden();
|
||||
await expect(page.locator('.affine-drop-indicator')).toBeHidden();
|
||||
|
||||
expect(await getPageSnapshot(page, true)).toMatchSnapshot(
|
||||
`${testInfo.title}_drag_3_9.json`
|
||||
@@ -206,7 +206,7 @@ test('move to the last block of each level in multi-level nesting', async ({
|
||||
true,
|
||||
-(1 * BLOCK_CHILDREN_CONTAINER_PADDING_LEFT)
|
||||
);
|
||||
await expect(page.locator('.affine-drag-indicator')).toBeHidden();
|
||||
await expect(page.locator('.affine-drop-indicator')).toBeHidden();
|
||||
|
||||
expect(await getPageSnapshot(page, true)).toMatchSnapshot(
|
||||
`${testInfo.title}_drag_4_3.json`
|
||||
@@ -220,7 +220,7 @@ test('move to the last block of each level in multi-level nesting', async ({
|
||||
true,
|
||||
-(2 * BLOCK_CHILDREN_CONTAINER_PADDING_LEFT)
|
||||
);
|
||||
await expect(page.locator('.affine-drag-indicator')).toBeHidden();
|
||||
await expect(page.locator('.affine-drop-indicator')).toBeHidden();
|
||||
|
||||
// FIXME(DND)
|
||||
// expect(await getPageSnapshot(page, true)).toMatchSnapshot(
|
||||
@@ -277,7 +277,7 @@ test.fixme(
|
||||
await expect(blockSelections).toHaveCount(2);
|
||||
|
||||
await dragHandleFromBlockToBlockBottomById(page, '2', '4', true);
|
||||
await expect(page.locator('.affine-drag-indicator')).toBeHidden();
|
||||
await expect(page.locator('.affine-drop-indicator')).toBeHidden();
|
||||
|
||||
await assertRichTexts(page, ['789', '123', '456']);
|
||||
|
||||
@@ -350,7 +350,7 @@ test('should blur rich-text first on starting block selection', async ({
|
||||
await expect(page.locator('*:focus')).toHaveCount(1);
|
||||
|
||||
await dragHandleFromBlockToBlockBottomById(page, '2', '4');
|
||||
await expect(page.locator('.affine-drag-indicator')).toBeHidden();
|
||||
await expect(page.locator('.affine-drop-indicator')).toBeHidden();
|
||||
await assertRichTexts(page, ['456', '789', '123']);
|
||||
|
||||
await expect(page.locator('*:focus')).toHaveCount(0);
|
||||
|
||||
Reference in New Issue
Block a user