From d6fa7e6fd47ebcfae957d42caaefead1f36c35c9 Mon Sep 17 00:00:00 2001 From: Artur Arseniev Date: Wed, 20 May 2026 15:48:22 +0400 Subject: [PATCH] Refactor resize command --- packages/core/src/commands/registry.ts | 11 ++++- packages/core/src/commands/view/Resize.ts | 46 ++++++++++++------- .../core/test/specs/commands/view/Resize.ts | 30 ++++++++++++ 3 files changed, 69 insertions(+), 18 deletions(-) create mode 100644 packages/core/test/specs/commands/view/Resize.ts diff --git a/packages/core/src/commands/registry.ts b/packages/core/src/commands/registry.ts index 4ba27e096..328da6d86 100644 --- a/packages/core/src/commands/registry.ts +++ b/packages/core/src/commands/registry.ts @@ -8,6 +8,7 @@ import type { } from './view/CommandAbstract'; import type { FullscreenCommandRegistryRun, FullscreenCommandRegistryStop } from './view/Fullscreen'; import type { PreviewCommandRegistryRun, PreviewCommandRegistryStop } from './view/Preview'; +import type { ResizeCommandRegistryRun, ResizeCommandRegistryStop } from './view/Resize'; type CommandRegistryHandler = (...args: any[]) => any; type CommandRegistryEntry = TId extends keyof TRegistry @@ -16,9 +17,15 @@ type CommandRegistryEntry = TId extends keyof TRe : CommandRegistryHandler : CommandRegistryHandler; -export interface CommandRegistryRun extends FullscreenCommandRegistryRun, PreviewCommandRegistryRun {} +export interface CommandRegistryRun + extends FullscreenCommandRegistryRun, + PreviewCommandRegistryRun, + ResizeCommandRegistryRun {} -export interface CommandRegistryStop extends FullscreenCommandRegistryStop, PreviewCommandRegistryStop {} +export interface CommandRegistryStop + extends FullscreenCommandRegistryStop, + PreviewCommandRegistryStop, + ResizeCommandRegistryStop {} export type CommandRunKnownId = Extract; export type CommandStopKnownId = Extract; diff --git a/packages/core/src/commands/view/Resize.ts b/packages/core/src/commands/view/Resize.ts index 2eac0aa08..d2070fd7a 100644 --- a/packages/core/src/commands/view/Resize.ts +++ b/packages/core/src/commands/view/Resize.ts @@ -3,14 +3,17 @@ import Component from '../../dom_components/model/Component'; import { ComponentsEvents } from '../../dom_components/types'; import ComponentView from '../../dom_components/view/ComponentView'; import StyleableModel, { StyleProps } from '../../domain_abstract/model/StyleableModel'; +import Editor from '../../editor'; import { getUnitFromValue } from '../../utils/mixins'; import Resizer, { RectDim, ResizerOptions } from '../../utils/Resizer'; -import { CommandObject } from './CommandAbstract'; +import type { CommandPublicFnFromHandler } from '../registryHelpers'; +import CommandAbstract from './CommandAbstract'; export interface ComponentResizeOptions extends ResizerOptions { component: Component; componentView?: ComponentView; el?: HTMLElement; + force?: boolean; afterStart?: () => void; afterEnd?: () => void; /** @@ -101,8 +104,25 @@ export enum ConvertUnitsToPx { perc = '%', } -export default { - run(editor, _, options: ComponentResizeOptions) { +export interface ResizeCommandRegistryRun { + 'core:resize': CommandPublicFnFromHandler; + resize: CommandPublicFnFromHandler; +} + +export interface ResizeCommandRegistryStop { + 'core:resize': CommandPublicFnFromHandler; + resize: CommandPublicFnFromHandler; +} + +export default class CommandResize extends CommandAbstract< + ComponentResizeOptions, + ComponentResizeOptions, + Resizer, + void +> { + canvasResizer?: Resizer; + + run(editor: Editor, _: any, options: ComponentResizeOptions): Resizer { const { Canvas, Utils, em } = editor; const canvasView = Canvas.getCanvasView(); const pfx = em.config.stylePrefix || ''; @@ -225,13 +245,13 @@ export default { options.afterEnd?.(); }, - updateTarget: (_el, rect, options) => { - updateTarget(_el, rect, options); + updateTarget: (_el, rect, updateOptions) => { + updateTarget(_el, rect, updateOptions); if (!modelToStyle) { return; } - const { store, selectedHandler, config, resizer, event } = options; + const { store, selectedHandler, config, resizer, event } = updateOptions; const { keyHeight, keyWidth, autoHeight, autoWidth, unitWidth, unitHeight } = config; const onlyHeight = ['tc', 'bc'].indexOf(selectedHandler!) >= 0; const onlyWidth = ['cl', 'cr'].indexOf(selectedHandler!) >= 0; @@ -298,21 +318,21 @@ export default { let { canvasResizer } = this; - // Create the resizer for the canvas if not yet created if (!canvasResizer) { this.canvasResizer = new Utils.Resizer(resizeOptions); canvasResizer = this.canvasResizer; } + canvasResizer = canvasResizer!; canvasResizer.setOptions(resizeOptions, true); canvasResizer.blur(); canvasResizer.focus(el); return canvasResizer; - }, + } stop() { this.canvasResizer?.blur(); - }, + } convertPxToUnit(props: ConvertPxToUnitProps): string { const { el, valuePx, unit, dpi = 96, roundDecimals = 3, isHeight, elComputedStyle } = props; @@ -378,11 +398,5 @@ export default { } return `${+valueResult.toFixed(roundDecimals)}${untiResult}`; - }, -} as CommandObject< - ComponentResizeOptions, - { - canvasResizer?: Resizer; - convertPxToUnit: (props: ConvertPxToUnitProps) => string; } ->; +} diff --git a/packages/core/test/specs/commands/view/Resize.ts b/packages/core/test/specs/commands/view/Resize.ts new file mode 100644 index 000000000..f1b9d7571 --- /dev/null +++ b/packages/core/test/specs/commands/view/Resize.ts @@ -0,0 +1,30 @@ +import Resize, { ConvertUnitsToPx } from '../../../../src/commands/view/Resize'; + +describe('Resize command', () => { + test('stop should blur the canvas resizer', () => { + const command = new Resize({}); + const blur = jest.fn(); + command.canvasResizer = { blur } as any; + + command.stop(); + + expect(blur).toHaveBeenCalledTimes(1); + }); + + test('convertPxToUnit should keep method name and convert pixels to percentage', () => { + const command = new Resize({}); + const parent = document.createElement('div'); + Object.defineProperty(parent, 'offsetWidth', { configurable: true, value: 200 }); + const el = document.createElement('div'); + parent.appendChild(el); + + const result = command.convertPxToUnit({ + el, + valuePx: 50, + unit: ConvertUnitsToPx.perc, + elComputedStyle: window.getComputedStyle(el), + }); + + expect(result).toBe('25%'); + }); +});