diff -r de5736883786 -r f912b591e1c1 src_js/iconolab-bundle/src/components/cutout/snapsvg-zoom.js --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src_js/iconolab-bundle/src/components/cutout/snapsvg-zoom.js Fri Aug 19 19:04:26 2016 +0200 @@ -0,0 +1,173 @@ +/* enable zoom */ +import { eventEmitter } from '../utils' + +class ZoomHandler { + + constructor (params) { + this.zoomFactor = 0.1 || params.zoomFactor; + this.paper = params.paper; + this.MIN_SIZE = 40; + this.imageWidth = parseInt(this.paper.select(".main-image").attr("width")); + this.imageHeight = parseInt(this.paper.select(".main-image").attr("height")); + + this.viewport = { + width: parseInt(this.paper.attr("width")), + height: parseInt(this.paper.attr("height")) + }; + + this.scale = 1; + this.paper.attr({stroke: 2, "fill": "blue" }); + this.disableDrag = false; + this.imgMinSize = Math.min(this.imageWidth, this.imageHeight); + this.lastPosition = []; + this.updateViewBox([0 , 0, this.imageWidth, this.imageHeight]); + } + + testShowCenter (cx, cy) { + + if (this.center) { + this.center.remove(); + } + this.center = this.paper.rect(cx - 3, cy - 3, 20, 20); + this.center.attr({"fill" : "red"}); + } + + drawTestRectangle (cx, cy, w, h) { + var x = cx - w / 2; + var y = cy - h / 2; + this.paper.rect(x, y, w, h); + } + + zoomIn () { + + /* current center */ + if ( this.scale === 9) { this.scale--; return; } + var currentCenterX = this.currentViewBox[0] + (this.currentViewBox[2] / 2); + var currentCenterY = this.currentViewBox[1] + (this.currentViewBox[3] / 2); + var scaleFactor = this.zoomFactor * this.scale; + var viewBoxW = this.imgMinSize - (this.imgMinSize * scaleFactor); + var viewBoxH = viewBoxW; + + this.currentViewBox[0] = currentCenterX - viewBoxW / 2; + this.currentViewBox[1] = currentCenterY - viewBoxH / 2; + + this.currentViewBox[2] = viewBoxW; + this.currentViewBox[3] = viewBoxH; + this.scale ++; + this.updateViewBox(); + } + + updateViewBox (currentViewBox, notify) { + notify = (typeof notify === "boolean") ? notify : true; + + if (currentViewBox && currentViewBox.length != 4) { throw new Error("Provided currentViewBox is not valid!"); } + if (currentViewBox) { + this.currentViewBox = currentViewBox; + } + + this.paper.attr({"viewBox": this.currentViewBox}); + + if (!notify) { return false; } + + var self = this; + eventEmitter.emit("zoomChanged", { + updateFunction: function (updatedViewBox) { + self.updateViewBox(updatedViewBox, false); + }, + "zoomFactor": this.getZoomFactor(), + "viewport": this.viewport, + "currentScale": this.scale, + "imageSize": {width: this.imageWidth, height: this.imageHeight}, + "minSize": Math.min(this.imageWidth, this.imageHeight), + "currentViewBox": this.currentViewBox.slice() + }); + } + + getZoomFactor () { + return { + x: this.viewport.width / this.currentViewBox[2], + y: this.viewport.height / this.currentViewBox[3] + }; + } + + onStart (x, y, e) { + + this.lastPosition[0] = this.currentViewBox[0]; + this.lastPosition[1] = this.currentViewBox[1]; + + if (e.target.className.baseVal === "drawingHandler") { + this.disableDrag = true; + } + } + + canDrag () { + return !this.disableDrag; + } + + onStop () { + this.disableDrag = false; + } + + onDrag (dx, dy, x, y, event) { + + if (!this.canDrag()) { return true; } + + var newX = this.lastPosition[0] - dx; + var newY = this.lastPosition[1] - dy; + + /* maxX bound */ + if (newX + this.currentViewBox[2] >= this.viewport.width) { + newX = this.viewport.width - this.currentViewBox[2]; + } + + /* maxY bound */ + if (newY + this.currentViewBox[3] >= this.viewport.height) { + newY = this.viewport.height - this.currentViewBox[3]; + } + + if (newX <= 0) { newX = 0; } + + if(newY <= 0) { newY = 0; } + + this.currentViewBox[0] = newX; + this.currentViewBox[1] = newY; + + this.updateViewBox(); + } + + reset () { + this.scale = 1; + this.currentViewBox = [0, 0, this.imageWidth, this.imageHeight]; + this.updateViewBox(); + } + + zoomOut () { + if (this.scale == 1) { + return false; + } + + var currentCenterX = this.currentViewBox[0] + (this.currentViewBox[2] / 2); + var currentCenterY = this.currentViewBox[1] + (this.currentViewBox[3] / 2); + var scaleFactor = this.zoomFactor * (this.scale - 1); + + var viewBoxW = this.imgMinSize - (this.imgMinSize * scaleFactor); + var viewBoxH = viewBoxW; + + var topX = currentCenterX - viewBoxW / 2; + var topY = currentCenterY - viewBoxH / 2; + + this.currentViewBox[0] = topX; //deal with X and Y + this.currentViewBox[1] = topY; + this.currentViewBox[2] = viewBoxW; + this.currentViewBox[3] = viewBoxH; + this.updateViewBox(); + this.scale--; + } +} + +export default { + + enable_zoom: function (params) { + return new ZoomHandler(params); + } +} \ No newline at end of file