mirror of
https://github.com/toeverything/AFFiNE.git
synced 2026-02-17 14:27:02 +08:00
refactor(editor): move connector overlay to connector package (#11944)
This commit is contained in:
@@ -4,3 +4,4 @@ export * from './element-renderer';
|
||||
export * from './export-manager';
|
||||
export * from './legacy-slot-extension';
|
||||
export * from './query';
|
||||
export * from './surface-middleware';
|
||||
|
||||
@@ -1,9 +1,7 @@
|
||||
import type { NoteBlockModel } from '@blocksuite/affine-model';
|
||||
import type { Connectable, NoteBlockModel } from '@blocksuite/affine-model';
|
||||
import type { GfxModel } from '@blocksuite/std/gfx';
|
||||
import type { BlockModel } from '@blocksuite/store';
|
||||
|
||||
import type { Connectable } from '../managers/connector-manager';
|
||||
|
||||
export function isConnectable(
|
||||
element: GfxModel | null
|
||||
): element is Connectable {
|
||||
|
||||
@@ -0,0 +1,23 @@
|
||||
import { createIdentifier } from '@blocksuite/global/di';
|
||||
import type { ExtensionType } from '@blocksuite/store';
|
||||
|
||||
import type { SurfaceBlockModel } from '../surface-model';
|
||||
|
||||
export type SurfaceMiddleware = (surface: SurfaceBlockModel) => () => void;
|
||||
|
||||
export const surfaceMiddlewareIdentifier = createIdentifier<{
|
||||
middleware: SurfaceMiddleware;
|
||||
}>('surface-middleware');
|
||||
|
||||
export function surfaceMiddlewareExtension(
|
||||
id: string,
|
||||
middleware: SurfaceMiddleware
|
||||
): ExtensionType {
|
||||
return {
|
||||
setup: di => {
|
||||
di.addImpl(surfaceMiddlewareIdentifier(id), {
|
||||
middleware,
|
||||
});
|
||||
},
|
||||
};
|
||||
}
|
||||
@@ -7,18 +7,6 @@ export {
|
||||
SurfaceGroupLikeModel,
|
||||
} from './element-model/base.js';
|
||||
export { CanvasElementType } from './element-model/index.js';
|
||||
import {
|
||||
isConnectorAndBindingsAllSelected,
|
||||
isConnectorWithLabel,
|
||||
} from './managers/connector-manager.js';
|
||||
export {
|
||||
calculateNearestLocation,
|
||||
ConnectionOverlay,
|
||||
ConnectorEndpointLocations,
|
||||
ConnectorEndpointLocationsOnTriangle,
|
||||
ConnectorPathGenerator,
|
||||
PathGenerator,
|
||||
} from './managers/connector-manager.js';
|
||||
export { CanvasRenderer } from './renderer/canvas-renderer.js';
|
||||
export type { ElementRenderer } from './renderer/elements/index.js';
|
||||
export * from './renderer/elements/type.js';
|
||||
@@ -60,11 +48,6 @@ export type { Options } from './utils/rough/core';
|
||||
export { sortIndex } from './utils/sort';
|
||||
export { updateXYWH } from './utils/update-xywh.js';
|
||||
|
||||
export const ConnectorUtils = {
|
||||
isConnectorAndBindingsAllSelected,
|
||||
isConnectorWithLabel,
|
||||
};
|
||||
|
||||
export const TextUtils = {
|
||||
wrapFontFamily,
|
||||
getFontFaces,
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -9,8 +9,8 @@ import { BlockSchemaExtension, defineBlockSchema } from '@blocksuite/store';
|
||||
import * as Y from 'yjs';
|
||||
|
||||
import { elementsCtorMap } from './element-model/index.js';
|
||||
import { surfaceMiddlewareIdentifier } from './extensions/surface-middleware.js';
|
||||
import { SurfaceBlockTransformer } from './surface-transformer.js';
|
||||
import { connectorWatcher } from './watchers/connector.js';
|
||||
import { groupRelationWatcher } from './watchers/group.js';
|
||||
|
||||
export const SurfaceBlockSchema = defineBlockSchema({
|
||||
@@ -39,15 +39,19 @@ export const SurfaceBlockSchema = defineBlockSchema({
|
||||
export const SurfaceBlockSchemaExtension =
|
||||
BlockSchemaExtension(SurfaceBlockSchema);
|
||||
|
||||
export type SurfaceMiddleware = (surface: SurfaceBlockModel) => () => void;
|
||||
|
||||
export class SurfaceBlockModel extends BaseSurfaceModel {
|
||||
private readonly _disposables: DisposableGroup = new DisposableGroup();
|
||||
|
||||
override _init() {
|
||||
this._extendElement(elementsCtorMap);
|
||||
super._init();
|
||||
[connectorWatcher(this), groupRelationWatcher(this)].forEach(disposable =>
|
||||
this.doc.provider
|
||||
.getAll(surfaceMiddlewareIdentifier)
|
||||
.forEach(({ middleware }) => {
|
||||
this._disposables.add(middleware(this));
|
||||
});
|
||||
|
||||
[groupRelationWatcher(this)].forEach(disposable =>
|
||||
this._disposables.add(disposable)
|
||||
);
|
||||
}
|
||||
|
||||
@@ -1,88 +0,0 @@
|
||||
import type { ConnectorElementModel } from '@blocksuite/affine-model';
|
||||
import type { GfxModel } from '@blocksuite/std/gfx';
|
||||
|
||||
import { ConnectorPathGenerator } from '../managers/connector-manager.js';
|
||||
import type { SurfaceBlockModel, SurfaceMiddleware } from '../surface-model.js';
|
||||
|
||||
export const connectorWatcher: SurfaceMiddleware = (
|
||||
surface: SurfaceBlockModel
|
||||
) => {
|
||||
const hasElementById = (id: string) =>
|
||||
surface.hasElementById(id) || surface.doc.hasBlock(id);
|
||||
const elementGetter = (id: string) =>
|
||||
surface.getElementById(id) ?? (surface.doc.getModelById(id) as GfxModel);
|
||||
const updateConnectorPath = (connector: ConnectorElementModel) => {
|
||||
if (
|
||||
((connector.source?.id && hasElementById(connector.source.id)) ||
|
||||
(!connector.source?.id && connector.source?.position)) &&
|
||||
((connector.target?.id && hasElementById(connector.target.id)) ||
|
||||
(!connector.target?.id && connector.target?.position))
|
||||
) {
|
||||
ConnectorPathGenerator.updatePath(connector, null, elementGetter);
|
||||
}
|
||||
};
|
||||
const pendingList = new Set<ConnectorElementModel>();
|
||||
let pendingFlag = false;
|
||||
const addToUpdateList = (connector: ConnectorElementModel) => {
|
||||
pendingList.add(connector);
|
||||
|
||||
if (!pendingFlag) {
|
||||
pendingFlag = true;
|
||||
queueMicrotask(() => {
|
||||
pendingList.forEach(updateConnectorPath);
|
||||
pendingList.clear();
|
||||
pendingFlag = false;
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
const disposables = [
|
||||
surface.elementAdded.subscribe(({ id }) => {
|
||||
const element = elementGetter(id);
|
||||
|
||||
if (!element) return;
|
||||
|
||||
if ('type' in element && element.type === 'connector') {
|
||||
addToUpdateList(element as ConnectorElementModel);
|
||||
} else {
|
||||
surface.getConnectors(id).forEach(addToUpdateList);
|
||||
}
|
||||
}),
|
||||
surface.elementUpdated.subscribe(({ id, props }) => {
|
||||
const element = elementGetter(id);
|
||||
|
||||
if (props['xywh'] || props['rotate']) {
|
||||
surface.getConnectors(id).forEach(addToUpdateList);
|
||||
}
|
||||
|
||||
if (
|
||||
'type' in element &&
|
||||
element.type === 'connector' &&
|
||||
(props['mode'] !== undefined ||
|
||||
props['target'] ||
|
||||
props['source'] ||
|
||||
(props['xywh'] && !(element as ConnectorElementModel).updatingPath))
|
||||
) {
|
||||
addToUpdateList(element as ConnectorElementModel);
|
||||
}
|
||||
}),
|
||||
surface.doc.slots.blockUpdated.subscribe(payload => {
|
||||
if (
|
||||
payload.type === 'add' ||
|
||||
(payload.type === 'update' && payload.props.key === 'xywh')
|
||||
) {
|
||||
surface.getConnectors(payload.id).forEach(addToUpdateList);
|
||||
}
|
||||
}),
|
||||
];
|
||||
|
||||
surface
|
||||
.getElementsByType('connector')
|
||||
.forEach(connector =>
|
||||
updateConnectorPath(connector as ConnectorElementModel)
|
||||
);
|
||||
|
||||
return () => {
|
||||
disposables.forEach(d => d.unsubscribe());
|
||||
};
|
||||
};
|
||||
@@ -1,5 +1,6 @@
|
||||
import { SurfaceGroupLikeModel } from '../element-model/base.js';
|
||||
import type { SurfaceBlockModel, SurfaceMiddleware } from '../surface-model.js';
|
||||
import type { SurfaceMiddleware } from '../extensions/surface-middleware.js';
|
||||
import type { SurfaceBlockModel } from '../surface-model.js';
|
||||
|
||||
export const groupRelationWatcher: SurfaceMiddleware = (
|
||||
surface: SurfaceBlockModel
|
||||
|
||||
Reference in New Issue
Block a user