diff --git a/cypress/e2e/12-canvas.cy.ts b/cypress/e2e/12-canvas.cy.ts index 9af6d25697ae0..385470ac51ff6 100644 --- a/cypress/e2e/12-canvas.cy.ts +++ b/cypress/e2e/12-canvas.cy.ts @@ -16,11 +16,11 @@ const NDVDialog = new NDV(); const DEFAULT_ZOOM_FACTOR = 1; const ZOOM_IN_X1_FACTOR = 1.25; // Zoom in factor after one click const ZOOM_IN_X2_FACTOR = 1.5625; // Zoom in factor after two clicks -const ZOOM_OUT_X1_FACTOR = 0.75; -const ZOOM_OUT_X2_FACTOR = 0.5625; +const ZOOM_OUT_X1_FACTOR = 0.8; +const ZOOM_OUT_X2_FACTOR = 0.64; -const PINCH_ZOOM_IN_FACTOR = 1.32; -const PINCH_ZOOM_OUT_FACTOR = 0.4752; +const PINCH_ZOOM_IN_FACTOR = 1.05702; +const PINCH_ZOOM_OUT_FACTOR = 0.946058; const RENAME_NODE_NAME = 'Something else'; describe('Canvas Node Manipulation and Navigation', () => { @@ -222,8 +222,8 @@ describe('Canvas Node Manipulation and Navigation', () => { ); }); - it('should zoom using pinch to zoom', () => { - WorkflowPage.actions.pinchToZoom(2, 'zoomIn'); + it('should zoom using scroll or pinch gesture', () => { + WorkflowPage.actions.pinchToZoom(1, 'zoomIn'); WorkflowPage.getters .nodeView() .should( @@ -232,7 +232,11 @@ describe('Canvas Node Manipulation and Navigation', () => { `matrix(${PINCH_ZOOM_IN_FACTOR}, 0, 0, ${PINCH_ZOOM_IN_FACTOR}, 0, 0)`, ); - WorkflowPage.actions.pinchToZoom(4, 'zoomOut'); + WorkflowPage.actions.pinchToZoom(1, 'zoomOut'); + // Zoom in 1x + Zoom out 1x should reset to default (=1) + WorkflowPage.getters.nodeView().should('have.css', 'transform', `matrix(1, 0, 0, 1, 0, 0)`); + + WorkflowPage.actions.pinchToZoom(1, 'zoomOut'); WorkflowPage.getters .nodeView() .should( diff --git a/cypress/pages/workflow.ts b/cypress/pages/workflow.ts index 962c212ee0a73..8b9bc04cf6a86 100644 --- a/cypress/pages/workflow.ts +++ b/cypress/pages/workflow.ts @@ -265,7 +265,8 @@ export class WorkflowPage extends BasePage { ctrlKey: true, pageX: cy.window().innerWidth / 2, pageY: cy.window().innerHeight / 2, - deltaY: mode === 'zoomOut' ? 16 * steps : -16 * steps, + deltaMode: 1, + deltaY: mode === 'zoomOut' ? steps : -steps, }); }, hitUndo: () => { diff --git a/packages/editor-ui/src/utils/canvasUtils.ts b/packages/editor-ui/src/utils/canvasUtils.ts index c10b8bbd37457..34863fca661c3 100644 --- a/packages/editor-ui/src/utils/canvasUtils.ts +++ b/packages/editor-ui/src/utils/canvasUtils.ts @@ -13,10 +13,11 @@ import type { Route } from 'vue-router'; '@/utils'. */ -const SCALE_INCREASE_FACTOR = 1.25; -const SCALE_DECREASE_FACTOR = 0.75; +const SCALE_CHANGE_FACTOR = 1.25; const MIN_SCALE = 0.2; const MAX_SCALE = 5; +const SCROLL_ZOOM_SPEED = 0.01; +const MAX_WHEEL_DELTA = 32; const clamp = (min: number, max: number) => (num: number) => { return Math.max(min, Math.min(max, num)); @@ -43,9 +44,9 @@ export const applyScale = }; }; -export const scaleBigger = applyScale(SCALE_INCREASE_FACTOR); +export const scaleBigger = applyScale(SCALE_CHANGE_FACTOR); -export const scaleSmaller = applyScale(SCALE_DECREASE_FACTOR); +export const scaleSmaller = applyScale(1 / SCALE_CHANGE_FACTOR); export const scaleReset = (config: IZoomConfig): IZoomConfig => { return applyScale(1 / config.scale)(config); @@ -108,6 +109,8 @@ export const getConnectionInfo = ( return null; }; +const clampWheelDelta = clamp(-MAX_WHEEL_DELTA, MAX_WHEEL_DELTA); + export const normalizeWheelEventDelta = (event: WheelEvent): { deltaX: number; deltaY: number } => { const factorByMode: Record = { [WheelEvent.DOM_DELTA_PIXEL]: 1, @@ -117,9 +120,12 @@ export const normalizeWheelEventDelta = (event: WheelEvent): { deltaX: number; d const factor = factorByMode[event.deltaMode] ?? 1; - return { deltaX: event.deltaX * factor, deltaY: event.deltaY * factor }; + return { + deltaX: clampWheelDelta(event.deltaX * factor), + deltaY: clampWheelDelta(event.deltaY * factor), + }; }; export const getScaleFromWheelEventDelta = (delta: number): number => { - return 1 - delta / 100; + return Math.pow(2, -delta * SCROLL_ZOOM_SPEED); };