UNPKG

plot-plan-designer

Version:

Design Editor Tools with React.js + ant.design + fabric.js

145 lines (144 loc) 5.86 kB
import { fabric } from 'fabric'; class ZoomHandler { constructor(handler) { /** * Zoom to point * * @param {fabric.Point} point * @param {number} zoom ex) 0 ~ 1. Not percentage value. */ this.zoomToPoint = (point, zoom) => { const { minZoom, maxZoom } = this.handler; let zoomRatio = zoom; if (zoom <= minZoom / 100) { zoomRatio = minZoom / 100; } else if (zoom >= maxZoom / 100) { zoomRatio = maxZoom / 100; } this.handler.canvas.zoomToPoint(point, zoomRatio); this.handler.getObjects().forEach((obj) => { if (obj.superType === 'element') { const { id, width, height, player } = obj; const el = this.handler.elementHandler.findById(id); // update the element this.handler.elementHandler.setScaleOrAngle(el, obj); this.handler.elementHandler.setSize(el, obj); this.handler.elementHandler.setPosition(el, obj); if (player) { player.setPlayerSize(width, height); } } }); if (this.handler.onZoom) { this.handler.onZoom(zoomRatio); } this.handler.canvas.requestRenderAll(); }; /** * Zoom one to one * */ this.zoomOneToOne = () => { const center = this.handler.canvas.getCenter(); this.handler.canvas.setViewportTransform([1, 0, 0, 1, 0, 0]); this.zoomToPoint(new fabric.Point(center.left, center.top), 1); }; /** * Zoom to fit * */ this.zoomToFit = () => { const { width, height, scaleX: workAreaScaleX, scaleY: workAreaScaleY } = this.handler.workarea; const currentWidth = width * workAreaScaleX; const currentHeight = height * workAreaScaleY; let scaleX = this.handler.canvas.getWidth() / currentWidth; const scaleY = this.handler.canvas.getHeight() / currentHeight; if (currentHeight >= currentWidth) { scaleX = scaleY; if (this.handler.canvas.getWidth() < currentWidth * scaleX) { scaleX = scaleX * (this.handler.canvas.getWidth() / (currentWidth * scaleX)); } } else { if (this.handler.canvas.getHeight() < currentHeight * scaleX) { scaleX = scaleX * (this.handler.canvas.getHeight() / (currentHeight * scaleX)); } } const center = this.handler.canvas.getCenter(); this.handler.canvas.setViewportTransform([1, 0, 0, 1, 0, 0]); this.zoomToPoint(new fabric.Point(center.left, center.top), scaleX); }; /** * Zoom in * */ this.zoomIn = () => { let zoomRatio = this.handler.canvas.getZoom(); zoomRatio += 0.05; const center = this.handler.canvas.getCenter(); this.zoomToPoint(new fabric.Point(center.left, center.top), zoomRatio); }; /** * Zoom out * */ this.zoomOut = () => { let zoomRatio = this.handler.canvas.getZoom(); zoomRatio -= 0.05; const center = this.handler.canvas.getCenter(); this.zoomToPoint(new fabric.Point(center.left, center.top), zoomRatio); }; /** * Zoom to center with object * * @param {FabricObject} target If zoomFit true, rescaled canvas zoom. */ this.zoomToCenterWithObject = (target, zoomFit) => { const { left: canvasLeft, top: canvasTop } = this.handler.canvas.getCenter(); const { left, top, width, height } = target; const diffTop = canvasTop - (top + height / 2); const diffLeft = canvasLeft - (left + width / 2); if (zoomFit) { let scaleX; let scaleY; scaleX = this.handler.canvas.getWidth() / width; scaleY = this.handler.canvas.getHeight() / height; if (height > width) { scaleX = scaleY; if (this.handler.canvas.getWidth() < width * scaleX) { scaleX = scaleX * (this.handler.canvas.getWidth() / (width * scaleX)); } } else { scaleY = scaleX; if (this.handler.canvas.getHeight() < height * scaleX) { scaleX = scaleX * (this.handler.canvas.getHeight() / (height * scaleX)); } } this.handler.canvas.setViewportTransform([1, 0, 0, 1, diffLeft, diffTop]); this.zoomToPoint(new fabric.Point(canvasLeft, canvasTop), scaleX); } else { const zoom = this.handler.canvas.getZoom(); this.handler.canvas.setViewportTransform([1, 0, 0, 1, diffLeft, diffTop]); this.zoomToPoint(new fabric.Point(canvasLeft, canvasTop), zoom); } }; /** * Zoom to center with objects * * @param {boolean} [zoomFit] If zoomFit true, rescaled canvas zoom. * @returns */ this.zoomToCenter = (zoomFit) => { const activeObject = this.handler.canvas.getActiveObject(); if (!activeObject) { return; } this.zoomToCenterWithObject(activeObject, zoomFit); }; this.handler = handler; } } export default ZoomHandler;