feat(editor): block painter extension (#10847)

This commit is contained in:
Saul-Mirone
2025-03-14 05:26:58 +00:00
parent be9f44fc4f
commit b8452f56a8
6 changed files with 54 additions and 31 deletions

View File

@@ -1,8 +1,9 @@
import type {
BlockLayout,
BlockLayoutPainter,
TextRect,
WorkerToHostMessage,
import {
type BlockLayout,
type BlockLayoutPainter,
BlockLayoutPainterExtension,
type TextRect,
type WorkerToHostMessage,
} from '@blocksuite/affine-gfx-turbo-renderer';
interface SentenceLayout {
@@ -39,7 +40,7 @@ function isParagraphLayout(layout: BlockLayout): layout is ParagraphLayout {
return layout.type === 'affine:paragraph';
}
export class ParagraphLayoutPainter implements BlockLayoutPainter {
class ParagraphLayoutPainter implements BlockLayoutPainter {
private static readonly supportFontFace =
typeof FontFace !== 'undefined' &&
typeof self !== 'undefined' &&
@@ -114,3 +115,8 @@ export class ParagraphLayoutPainter implements BlockLayoutPainter {
});
}
}
export const ParagraphLayoutPainterExtension = BlockLayoutPainterExtension(
'affine:paragraph',
ParagraphLayoutPainter
);

View File

@@ -0,0 +1,19 @@
import { createIdentifier } from '@blocksuite/global/di';
import type { ExtensionType } from '@blocksuite/store';
import type { BlockLayoutPainter } from '../types';
export const BlockPainterProvider = createIdentifier<BlockLayoutPainter>(
'block-painter-provider'
);
export const BlockLayoutPainterExtension = (
type: string,
painter: new () => BlockLayoutPainter
): ExtensionType => {
return {
setup: di => {
di.addImpl(BlockPainterProvider(type), painter);
},
};
};

View File

@@ -1,3 +1,4 @@
export * from './extension';
export * from './layout/block-layout-provider';
export * from './painter/painter.worker';
export * from './text-utils';

View File

@@ -1,3 +1,7 @@
import { Container, type ServiceProvider } from '@blocksuite/global/di';
import type { ExtensionType } from '@blocksuite/store';
import { BlockPainterProvider } from '../extension';
import type {
BlockLayoutPainter,
HostToWorkerMessage,
@@ -5,28 +9,25 @@ import type {
WorkerToHostMessage,
} from '../types';
class BlockPainterRegistry {
private readonly painters = new Map<string, BlockLayoutPainter>();
register(type: string, painter: BlockLayoutPainter) {
this.painters.set(type, painter);
}
getPainter(type: string): BlockLayoutPainter | undefined {
return this.painters.get(type);
}
}
export class ViewportLayoutPainter {
private readonly canvas: OffscreenCanvas = new OffscreenCanvas(0, 0);
private ctx: OffscreenCanvasRenderingContext2D | null = null;
private zoom = 1;
public readonly registry = new BlockPainterRegistry();
public provider: ServiceProvider;
constructor(painters: Record<string, BlockLayoutPainter>) {
Object.entries(painters).forEach(([type, painter]) => {
this.registry.register(type, painter);
getPainter(type: string): BlockLayoutPainter | undefined {
return this.provider.get(BlockPainterProvider(type));
}
constructor(extensions: ExtensionType[]) {
const container = new Container();
extensions.forEach(extension => {
extension.setup(container);
});
this.provider = container.provider();
self.onmessage = this.handler;
}
@@ -60,7 +61,7 @@ export class ViewportLayoutPainter {
ctx.scale(this.zoom, this.zoom);
layout.blocks.forEach(blockLayout => {
const painter = this.registry.getPainter(blockLayout.type);
const painter = this.getPainter(blockLayout.type);
if (!painter) return;
painter.paint(ctx, blockLayout, layout.rect.x, layout.rect.y);
});

View File

@@ -1,6 +1,4 @@
import { ParagraphLayoutPainter } from '@blocksuite/affine-block-paragraph/turbo-painter';
import { ParagraphLayoutPainterExtension } from '@blocksuite/affine-block-paragraph/turbo-painter';
import { ViewportLayoutPainter } from '@blocksuite/affine-gfx-turbo-renderer/painter';
new ViewportLayoutPainter({
'affine:paragraph': new ParagraphLayoutPainter(),
});
new ViewportLayoutPainter([ParagraphLayoutPainterExtension]);