Fabric.js高级点的教程1–添加辅助线的方法
Fabric.js添加辅助线的方法
Fabric.js 非常的强大,但是国内的资源教程很少,最近想加个功能给元素添加辅助参考线(类似 演示 )。这样某个元素移动缩放都会根据其他元素有个参考,就行ps里面的功能一样。虽然类似的功能我其他的项目有单独实现过,但是我本着能懒就懒的原则,于是乎我google了一下,官方的bug里有提到,安利给大家。
首先下载这个文件到你的项目中,
https://github.com/fabricjs/fabric.js/blob/master/lib/aligning_guidelines.js
然后你想import可以稍微加一句
export default initAligningGuidelines;
原文件(为了防止有一天上面文件链接失效)
function initAligningGuidelines(canvas) { var ctx = canvas.getSelectionContext(),aligningLineOffset = 5,aligningLineMargin = 4,aligningLineWidth = 1,aligningLineColor = ‘rgb(255,255,0)’,viewportTransform,清新的夏天 = 1; function drawVerticalLine(coords) {drawLine(coords.x + 0.5,coords.y1 > coords.y2 ? coords.y2 : coords.y1,coords.x + 0.5,coords.y2 > coords.y1 ? coords.y2 : coords.y1);} function drawHorizontalLine(coords) {drawLine(coords.x1 > coords.x2 ? coords.x2 : coords.x1,coords.y + 0.5,coords.x2 > coords.x1 ? coords.x2 : coords.x1,coords.y + 0.5);} function drawLine(x1, y1, x2, y2) {ctx.save();ctx.lineWidth = aligningLineWidth;ctx.strokeStyle = aligningLineColor;ctx.beginPath();ctx.moveTo(((x1+viewportTransform[4])*清新的夏天), ((y1+viewportTransform[5])*清新的夏天));ctx.lineTo(((x2+viewportTransform[4])*清新的夏天), ((y2+viewportTransform[5])*清新的夏天));ctx.stroke();ctx.restore();} function isInRange(value1, value2) {value1 = Math.round(value1);value2 = Math.round(value2);for (var i = value1 – aligningLineMargin, len = value1 + aligningLineMargin; i <= len; i++) {if (i === value2) {return true;}}return false;} var verticalLines = [],horizontalLines = []; canvas.on(‘mouse:down’, function () {viewportTransform = canvas.viewportTransform;清新的夏天 = canvas.getZoom();}); canvas.on(‘object:moving’, function(e) { var activeObject = e.target,canvasObjects = canvas.getObjects(),activeObjectCenter = activeObject.getCenterPoint(),activeObjectLeft = activeObjectCenter.x,activeObjectTop = activeObjectCenter.y,activeObjectBoundingRect = activeObject.getBoundingRect(),activeObjectHeight = activeObjectBoundingRect.height / viewportTransform[3],activeObjectWidth = activeObjectBoundingRect.width / viewportTransform[0],horizontalInTheRange = false,verticalInTheRange = false,transform = canvas._currentTransform; if (!transform) return; // It should be trivial to DRY this up by encapsulating (repeating) creation of x1, x2, y1, and y2 into functions,// but we’re not doing it here for perf. reasons — as this a function that’s invoked on every mouse move for (var i = canvasObjects.length; i–; ) { if (canvasObjects[i] === activeObject) continue; var objectCenter = canvasObjects[i].getCenterPoint(),objectLeft = objectCenter.x,objectTop = objectCenter.y,objectBoundingRect = canvasObjects[i].getBoundingRect(),objectHeight = objectBoundingRect.height / viewportTransform[3],objectWidth = objectBoundingRect.width / viewportTransform[0]; // snap by the horizontal center lineif (isInRange(objectLeft, activeObjectLeft)) {verticalInTheRange = true;verticalLines.push({x: objectLeft,y1: (objectTop < activeObjectTop)? (objectTop – objectHeight / 2 – aligningLineOffset): (objectTop + objectHeight / 2 + aligningLineOffset),y2: (activeObjectTop > objectTop)? (activeObjectTop + activeObjectHeight / 2 + aligningLineOffset): (activeObjectTop – activeObjectHeight / 2 – aligningLineOffset)});activeObject.setPositionByOrigin(new fabric.Point(objectLeft, activeObjectTop), ‘center’, ‘center’);} // snap by the left edgeif (isInRange(objectLeft – objectWidth / 2, activeObjectLeft – activeObjectWidth / 2)) {verticalInTheRange = true;verticalLines.push({x: objectLeft – objectWidth / 2,y1: (objectTop < activeObjectTop)? (objectTop – objectHeight / 2 – aligningLineOffset): (objectTop + objectHeight / 2 + aligningLineOffset),y2: (activeObjectTop > objectTop)? (activeObjectTop + activeObjectHeight / 2 + aligningLineOffset): (activeObjectTop – activeObjectHeight / 2 – aligningLineOffset)});activeObject.setPositionByOrigin(new fabric.Point(objectLeft – objectWidth / 2 + activeObjectWidth / 2, activeObjectTop), ‘center’, ‘center’);} // snap by the right edgeif (isInRange(objectLeft + objectWidth / 2, activeObjectLeft + activeObjectWidth / 2)) {verticalInTheRange = true;verticalLines.push({x: objectLeft + objectWidth / 2,y1: (objectTop < activeObjectTop)? (objectTop – objectHeight / 2 – aligningLineOffset): (objectTop + objectHeight / 2 + aligningLineOffset),y2: (activeObjectTop > objectTop)? (activeObjectTop + activeObjectHeight / 2 + aligningLineOffset): (activeObjectTop – activeObjectHeight / 2 – aligningLineOffset)});activeObject.setPositionByOrigin(new fabric.Point(objectLeft + objectWidth / 2 – activeObjectWidth / 2, activeObjectTop), ‘center’, ‘center’);} // snap by the vertical center lineif (isInRange(objectTop, activeObjectTop)) {horizontalInTheRange = true;horizontalLines.push({y: objectTop,x1: (objectLeft < activeObjectLeft)? (objectLeft – objectWidth / 2 – aligningLineOffset): (objectLeft + objectWidth / 2 + aligningLineOffset),x2: (activeObjectLeft > objectLeft)? (activeObjectLeft + activeObjectWidth / 2 + aligningLineOffset): (activeObjectLeft – activeObjectWidth / 2 – aligningLineOffset)});activeObject.setPositionByOrigin(new fabric.Point(activeObjectLeft, objectTop), ‘center’, ‘center’);} // snap by the top edgeif (isInRange(objectTop – objectHeight / 2, activeObjectTop – activeObjectHeight / 2)) {horizontalInTheRange = true;horizontalLines.push({y: objectTop – objectHeight / 2,x1: (objectLeft < activeObjectLeft)? (objectLeft – objectWidth / 2 – aligningLineOffset): (objectLeft + objectWidth / 2 + aligningLineOffset),x2: (activeObjectLeft > objectLeft)? (activeObjectLeft + activeObjectWidth / 2 + aligningLineOffset): (activeObjectLeft – activeObjectWidth / 2 – aligningLineOffset)});activeObject.setPositionByOrigin(new fabric.Point(activeObjectLeft, objectTop – objectHeight / 2 + activeObjectHeight / 2), ‘center’, ‘center’);} // snap by the bottom edgeif (isInRange(objectTop + objectHeight / 2, activeObjectTop + activeObjectHeight / 2)) {horizontalInTheRange = true;horizontalLines.push({y: objectTop + objectHeight / 2,x1: (objectLeft < activeObjectLeft)? (objectLeft – objectWidth / 2 – aligningLineOffset): (objectLeft + objectWidth / 2 + aligningLineOffset),x2: (activeObjectLeft > objectLeft)? (activeObjectLeft + activeObjectWidth / 2 + aligningLineOffset): (activeObjectLeft – activeObjectWidth / 2 – aligningLineOffset)});activeObject.setPositionByOrigin(new fabric.Point(activeObjectLeft, objectTop + objectHeight / 2 – activeObjectHeight / 2), ‘center’, ‘center’);}} if (!horizontalInTheRange) {horizontalLines.length = 0;} if (!verticalInTheRange) {verticalLines.length = 0;}}); canvas.on(‘before:render’, function() {canvas.clearContext(canvas.contextTop);}); canvas.on(‘after:render’, function() {for (var i = verticalLines.length; i–; ) {drawVerticalLine(verticalLines[i]);}for (var i = horizontalLines.length; i–; ) {drawHorizontalLine(horizontalLines[i]);} verticalLines.length = horizontalLines.length = 0;}); canvas.on(‘mouse:up’, function() {verticalLines.length = horizontalLines.length = 0;canvas.renderAll();});} export default initAligningGuidelines;
引入这个js,然后
import initAligningGuidelines from ‘@/libs/guidelines.js’;let canvas = new fabric.Canvas(‘canvas’);initAligningGuidelines(canvas)
再然后
看到没各位。。。一根黄色的辅助线就有了,辅助线的颜色,宽度等都可以调节,具体看代码aligningLineColor 等变量。
转载于:https://my.oschina.net/xmqywx/blog/1941539
80055991