一、效果图
二、主要代码
获取矩形框中地方的截图数据
1、先获取矩形四点在画布上的实际坐标值;
2、计算矩形此时实际的宽和高,便于设置后期临时矩形的宽和高;
3、可能矩形旋转了一定的角度,我们新建一个临时的画布tempCanvas,然后向反方向摆正,使矩形能正常的显示在临时画布中;
4、因为摆正了矩形,此时需要计算矩形的left和top,方便画图;
5、在创建一个用于画截图的canvas,canvas的宽高就是前面我们画出来的宽高‘
6、然后利用
rotatedCtx.drawImage(
tempCanvas,
left,
top,
width,
height,
0,
0,
width,
height
);
在临时画布中截取矩形框中的部分
7、ctx.drawImage的参数代表的意思请详见:
https://developer.mozilla.org/zh-CN/docs/Web/API/Canvas_API/Tutorial/Using_images
getCanvasImageData(id) {
const viewportTransform = this.fabricCanvas.viewportTransform;
const zoom = this.fabricCanvas.getZoom();
let selectedCoords = null;
let rotationAngle = 0;
let left = 0;
let top = 0;
//根据画布矩阵和缩放信息,获取到矩形实际在画布上的坐标点
this.fabricCanvas.getObjects().forEach(rect => {
if (rect.id == id) {
console.log("rect", rect);
const coords = [];
const points = rect.get("aCoords");
// 将内部坐标转换为实际画布坐标
coords.push(this.getACoords(points["tl"], viewportTransform, zoom));
coords.push(this.getACoords(points["tr"], viewportTransform, zoom));
coords.push(this.getACoords(points["br"], viewportTransform, zoom));
coords.push(this.getACoords(points["bl"], viewportTransform, zoom));
selectedCoords = coords;
rotationAngle = rect.angle;
// left = rect.left;
// top = rect.top;
}
});
if (selectedCoords) {
//2、根据rotationAngle和selectedCoords,计算rect此时的宽高,此时矩形有可能被旋转,有可能被拉伸,所以需要重新计算矩形的宽高
const width = Math.sqrt(
Math.pow(selectedCoords[1][0] - selectedCoords[0][0], 2) +
Math.pow(selectedCoords[1][1] - selectedCoords[0][1], 2)
);
const height = Math.sqrt(
Math.pow(selectedCoords[3][0] - selectedCoords[0][0], 2) +
Math.pow(selectedCoords[3][1] - selectedCoords[0][1], 2)
);
// 计算矩形中心点
const centerX = (selectedCoords[0][0] + selectedCoords[2][0]) / 2;
const centerY = (selectedCoords[0][1] + selectedCoords[2][1]) / 2;
// 新建一个 canvas 元素
const tempCanvas = document.createElement("canvas");
const tempCtx = tempCanvas.getContext("2d");
tempCanvas.height = this.canvasProp.height;
tempCanvas.width = this.canvasProp.width;
// 将原点移动到矩形中心点
tempCtx.translate(centerX, centerY);
// 按中心点旋转画布
tempCtx.rotate(-(rotationAngle * (Math.PI / 180)));
// 将原点移回
tempCtx.translate(-centerX, -centerY);
// 将 fabricCanvas 的内容绘制到临时 canvas 上,并进行裁剪
tempCtx.save();
tempCtx.beginPath();
tempCtx.moveTo(selectedCoords[0][0], selectedCoords[0][1]);
tempCtx.lineTo(selectedCoords[1][0], selectedCoords[1][1]);
tempCtx.lineTo(selectedCoords[2][0], selectedCoords[2][1]);
tempCtx.lineTo(selectedCoords[3][0], selectedCoords[3][1]);
tempCtx.closePath();
tempCtx.clip();
// 获取 fabricCanvas 的数据并绘制到临时 canvas 上
tempCtx.drawImage(this.bgImg, 0, 0);
// 恢复上下文状态
tempCtx.restore();
// return tempCtx.getImageData(
// 0,
// 0,
// tempCanvas.width,
// tempCanvas.height
// );
// 重新计算旋转后的矩形的 left 和 top
const rotatedCoords = selectedCoords.map(coord => {
const x = coord[0] - centerX;
const y = coord[1] - centerY;
const rotatedX =
x * Math.cos((rotationAngle * Math.PI) / 180) +
y * Math.sin((rotationAngle * Math.PI) / 180);
const rotatedY =
-x * Math.sin((rotationAngle * Math.PI) / 180) +
y * Math.cos((rotationAngle * Math.PI) / 180);
return [rotatedX + centerX, rotatedY + centerY];
});
const left = Math.min(
rotatedCoords[0][0],
rotatedCoords[1][0],
rotatedCoords[2][0],
rotatedCoords[3][0]
);
const top = Math.min(
rotatedCoords[0][1],
rotatedCoords[1][1],
rotatedCoords[2][1],
rotatedCoords[3][1]
);
const rotatedCanvas = document.createElement("canvas");
rotatedCanvas.width = width;
rotatedCanvas.height = height;
const rotatedCtx = rotatedCanvas.getContext("2d");
// 将临时canvas的图像绘制到旋转后的canvas上
rotatedCtx.drawImage(
tempCanvas,
left,
top,
width,
height,
0,
0,
width,
height
);
// 返回旋转后的图像数据
return rotatedCtx.getImageData(
0,
0,
rotatedCanvas.width,
rotatedCanvas.height
);
} else {
return null;
}
},
三、组件代码
<template>
<div v-if="canvasProp.width != 0">
<div
class="canvas-wrap"
:style="{
width: canvasProp.width + 'px',
height: canvasProp.height + 'px'
}"
>
<canvas
:width="canvasProp.width"
:height="canvasProp.height"
ref="canvas"
:style="{
width: canvasProp.width + 'px',
height: canvasProp.height + 'px'
}"
id="canvasId"
></canvas>
</div>
<div
class="muane"
:style="{
width: canvasProp.width - 2 + 'px'
}"
>
<span @click="zoomBig">
<i class="el-icon-zoom-in" style="color: #000;font-size: 16px;"></i>
</span>
<span @click="zoomSmall">
<i class="el-icon-zoom-out" style="color: #000;font-size: 16px;"></i>
</span>
<span @click="panChange">
<i
v-if="!isPan"
class="icon iconfont-saber icon-saber-shouzhang mIcon"
style="color: #000;font-size: 15px !important;"
></i>
<i
v-else
class="icon iconfont-saber icon-saber-24gl-pointer mIcon"
style="color: #000;font-size: 16px !important;"
></i>
</span>
</div>
<!-- 隐藏的 canvas -->
<canvas
ref="hiddenCanvas"
:width="canvasProp.width"
:height="canvasProp.height"
style="display: none;"
></canvas>
</div>
</template>
<script>
let backgroundImage = null;
export default {
name: "images-tags",
props: {
// 矩形标注的数据
tagsData: {
type: Array,
default: () => {
return [
{
label: "基表数据",
color: "#0000ff",
type: "rectangle",
width: 150,
height: 50,
rotate: 0,
isInit: true,
startX: 185,
startY: 235
},
{
label: "数据点2",
color: "#0000ff",
type: "rectangle",
width: 150,
height: 50,
rotate: 0,
isInit: false,
startX: 100,
startY: 100
}
];
}
},
// 图片路径
images: {
type: String,
default: ""
}
},
data() {
return {
bgImg: null,
ctx: null,
fabricCanvas: null,
isPan: false,
isDragging: false,
canvasSizeScale: 1,
lastPosX: 0,
lastPosY: 0,
canvasProp: {
width: 0, // canvas的宽度
height: 0, // canvas的高度
translateX: 0,
translateY: 0
}
};
},
mounted() {
this.loadImageAndSetCanvas();
//window.addEventListener("keydown", this.handleKeyDown);
},
beforeDestroy() {
//window.removeEventListener("keydown", this.handleKeyDown);
this.fabricCanvas.off("object:modified", this.modifyRect);
},
methods: {
// 添加新的方法
getCanvasImageData(id) {
console.log("getCanvasImageData");
const viewportTransform = this.fabricCanvas.viewportTransform;
const zoom = this.fabricCanvas.getZoom();
let selectedCoords = null;
let rotationAngle = 0;
this.fabricCanvas.getObjects().forEach(rect => {
if (rect.id == id) {
console.log("rect", rect);
const coords = [];
const points = rect.get("aCoords");
// 将内部坐标转换为实际画布坐标
coords.push(this.getACoords(points["tl"], viewportTransform, zoom));
coords.push(this.getACoords(points["tr"], viewportTransform, zoom));
coords.push(this.getACoords(points["br"], viewportTransform, zoom));
coords.push(this.getACoords(points["bl"], viewportTransform, zoom));
selectedCoords = coords;
rotationAngle = rect.angle;
}
});
if (selectedCoords) {
//2、根据rotationAngle和selectedCoords,计算rect此时的宽高
const width = Math.sqrt(
Math.pow(selectedCoords[1][0] - selectedCoords[0][0], 2) +
Math.pow(selectedCoords[1][1] - selectedCoords[0][1], 2)
);
const height = Math.sqrt(
Math.pow(selectedCoords[3][0] - selectedCoords[0][0], 2) +
Math.pow(selectedCoords[3][1] - selectedCoords[0][1], 2)
);
// 计算矩形中心点
const centerX = (selectedCoords[0][0] + selectedCoords[2][0]) / 2;
const centerY = (selectedCoords[0][1] + selectedCoords[2][1]) / 2;
// 新建一个 canvas 元素
const tempCanvas = document.createElement("canvas");
const tempCtx = tempCanvas.getContext("2d");
tempCanvas.height = this.canvasProp.height;
tempCanvas.width = this.canvasProp.width;
// 将原点移动到矩形中心点
tempCtx.translate(centerX, centerY);
// 按中心点旋转画布
tempCtx.rotate(-(rotationAngle * (Math.PI / 180)));
// 将原点移回
tempCtx.translate(-centerX, -centerY);
// 将 fabricCanvas 的内容绘制到临时 canvas 上,并进行裁剪
tempCtx.save();
tempCtx.beginPath();
tempCtx.moveTo(selectedCoords[0][0], selectedCoords[0][1]);
tempCtx.lineTo(selectedCoords[1][0], selectedCoords[1][1]);
tempCtx.lineTo(selectedCoords[2][0], selectedCoords[2][1]);
tempCtx.lineTo(selectedCoords[3][0], selectedCoords[3][1]);
tempCtx.closePath();
tempCtx.clip();
// 获取 fabricCanvas 的数据并绘制到临时 canvas 上
tempCtx.drawImage(this.bgImg, 0, 0);
// 恢复上下文状态
tempCtx.restore();
// return tempCtx.getImageData(
// 0,
// 0,
// tempCanvas.width,
// tempCanvas.height
// );
// 重新计算旋转后的矩形的 left 和 top
const rotatedCoords = selectedCoords.map(coord => {
const x = coord[0] - centerX;
const y = coord[1] - centerY;
const rotatedX =
x * Math.cos((rotationAngle * Math.PI) / 180) +
y * Math.sin((rotationAngle * Math.PI) / 180);
const rotatedY =
-x * Math.sin((rotationAngle * Math.PI) / 180) +
y * Math.cos((rotationAngle * Math.PI) / 180);
return [rotatedX + centerX, rotatedY + centerY];
});
const left = Math.min(
rotatedCoords[0][0],
rotatedCoords[1][0],
rotatedCoords[2][0],
rotatedCoords[3][0]
);
const top = Math.min(
rotatedCoords[0][1],
rotatedCoords[1][1],
rotatedCoords[2][1],
rotatedCoords[3][1]
);
// 检查并调整宽度和高度,确保不超出画布边界,否则ios无法正常显示
let adjustedWidth = width;
let adjustedHeight = height;
//超过右边界
if (left + width > tempCanvas.width) {
adjustedWidth = tempCanvas.width - left;
}
//超过左边界
if (left<0) {
adjustedWidth = width+left;
if(adjustedWidth>tempCanvas.width){
adjustedWidth = tempCanvas.width;
}
}
//如果横框宽度
//超过下边界
if (top + height > tempCanvas.height) {
adjustedHeight = tempCanvas.height - top;
}
//超过上边界
if(top<0){
adjustedHeight = height+top;
if(adjustedHeight>tempCanvas.height){
adjustedHeight = tempCanvas.height;
}
}
const rotatedCanvas = document.createElement("canvas");
rotatedCanvas.width = adjustedWidth;
rotatedCanvas.height = adjustedHeight;
const rotatedCtx = rotatedCanvas.getContext("2d");
// 将临时canvas的图像绘制到旋转后的canvas上
rotatedCtx.drawImage(
tempCanvas,
left<0 ? 0 : left,
top<0? 0 : top,
adjustedWidth,
adjustedHeight,
0,
0,
adjustedWidth,
adjustedHeight
);
// 返回旋转后的图像数据
return rotatedCtx.getImageData(
0,
0,
rotatedCanvas.width,
rotatedCanvas.height
);
} else {
return null;
}
},
convertToGrayScale(imageData) {
const data = imageData.data;
for (let i = 0; i < data.length; i += 4) {
const avg = 0.3 * data[i] + 0.59 * data[i + 1] + 0.11 * data[i + 2];
data[i] = avg;
data[i + 1] = avg;
data[i + 2] = avg;
}
return imageData;
},
modifyRect(rect) {
console.log(rect, this);
let selectedDataPoint = this.$parent.selectedDataPoint;
let id = rect.target.id;
for (let i = 0; i < selectedDataPoint.length; i++) {
let item = selectedDataPoint[i];
if (item.id == id) {
this.applyGrayScale(id, item.ledThreshold);
break;
}
}
},
//绘制灰色图片
applyGrayScale(id, threshold) {
// 获取选中区域的图像数据
const imageData = this.getCanvasImageData(id);
//对图像数据进行灰度处理
const grayImageData = this.convertToGrayScale(imageData);
this.$emit("getGrayCtxSize", {
id: id,
width: grayImageData.width,
height: grayImageData.height
});
// 找到灰度canvas并放入灰度图片数据
const grayCtx = this.$parent.$refs["grayCanvas-" + id][0].getContext(
"2d"
);
this.$nextTick(() => {
grayCtx.putImageData(grayImageData, 0, 0);
this.applyThreshold(
id,
threshold,
grayImageData.width,
grayImageData.height
);
});
},
applyThreshold(id, threshold, width, height) {
console.log("width", width);
if (!width) return;
if (!threshold) {
threshold = 128;
}
const grayCtx = this.$parent.$refs["grayCanvas-" + id][0].getContext(
"2d"
);
const grayImageData = grayCtx.getImageData(0, 0, width, height);
const data = grayImageData.data;
for (let i = 0; i < data.length; i += 4) {
const avg = data[i];
const value = avg > threshold ? 255 : 0;
data[i] = value;
data[i + 1] = value;
data[i + 2] = value;
}
const binaryCtx = this.$parent.$refs["binaryCanvas-" + id][0].getContext(
"2d"
);
grayCtx.width = binaryCtx.width;
grayCtx.height = binaryCtx.height;
binaryCtx.putImageData(grayImageData, 0, 0);
},
//切换操作切换
panChange() {
this.isPan = !this.isPan;
if (this.isPan) {
this.enablePan();
} else {
this.disablePan();
}
},
enablePan() {
this.fabricCanvas.discardActiveObject(); //取消当前的选中状态
//禁止页面的选择
this.fabricCanvas.forEachObject(function(obj) {
obj.selectable = false; // 禁用对象选择
obj.evented = false; // 禁用对象事件
});
// 设置 canvas 的鼠标样式为 'move'
this.fabricCanvas.defaultCursor = "grab";
this.fabricCanvas.hoverCursor = "grab";
// 添加事件监听
this.fabricCanvas.on("mouse:down", this.onMouseDown);
this.fabricCanvas.on("mouse:move", this.onMouseMove);
this.fabricCanvas.on("mouse:up", this.onMouseUp);
this.fabricCanvas.on("mouse:out", this.onMouseUp);
this.fabricCanvas.renderAll(); // 重绘画布以显示更改
},
disablePan() {
//禁止页面的选择
this.fabricCanvas.forEachObject(function(obj) {
obj.selectable = true; // 禁用对象选择
obj.evented = true; // 禁用对象事件
});
// 恢复 canvas 的默认鼠标样式
this.fabricCanvas.defaultCursor = "default";
this.fabricCanvas.hoverCursor = "default";
// 移除事件监听
this.fabricCanvas.off("mouse:down", this.onMouseDown);
this.fabricCanvas.off("mouse:move", this.onMouseMove);
this.fabricCanvas.off("mouse:up", this.onMouseUp);
this.fabricCanvas.off("mouse:out", this.onMouseUp);
this.fabricCanvas.renderAll(); // 重绘画布以显示更改
},
onMouseDown(event) {
this.isDragging = true;
this.lastPosX = event.e.clientX;
this.lastPosY = event.e.clientY;
this.fabricCanvas.defaultCursor = "grabbing";
},
// onMouseMove(event) {
// if (this.isDragging) {
// const e = event.e;
// const vpt = this.fabricCanvas.viewportTransform;
// vpt[4] += e.clientX - this.lastPosX;
// vpt[5] += e.clientY - this.lastPosY;
// this.fabricCanvas.requestRenderAll();
// this.lastPosX = e.clientX;
// this.lastPosY = e.clientY;
// }
// },
onMouseMove(event) {
if (this.isDragging) {
const e = event.e;
const vpt = this.fabricCanvas.viewportTransform.slice(); // 创建副本,避免直接修改
const zoom = this.fabricCanvas.getZoom();
// 计算平移的距离
const moveX = e.clientX - this.lastPosX;
const moveY = e.clientY - this.lastPosY;
// 获取画布和容器的宽高
const canvasWidth = this.fabricCanvas.getWidth();
const canvasHeight = this.fabricCanvas.getHeight();
const containerWidth = this.canvasProp.width;
const containerHeight = this.canvasProp.height;
// 计算缩放后的宽高
const scaledWidth = canvasWidth * zoom;
const scaledHeight = canvasHeight * zoom;
// 计算边界
const leftBoundary = Math.min(0, containerWidth - scaledWidth);
const topBoundary = Math.min(0, containerHeight - scaledHeight);
// 应用平移限制
vpt[4] = Math.max(leftBoundary, Math.min(0, vpt[4] + moveX));
vpt[5] = Math.max(topBoundary, Math.min(0, vpt[5] + moveY));
// 更新画布视口变换
this.fabricCanvas.setViewportTransform(vpt);
this.lastPosX = e.clientX;
this.lastPosY = e.clientY;
}
},
onMouseUp() {
this.isDragging = false;
this.fabricCanvas.defaultCursor = "grab";
},
zoomBig() {
const currentZoom = this.fabricCanvas.getZoom();
if (currentZoom < 3) {
this.scaleCanvas(currentZoom + 0.1);
}
},
zoomSmall() {
const currentZoom = this.fabricCanvas.getZoom();
if (currentZoom > 1) {
this.scaleCanvas(currentZoom - 0.1);
}
},
scaleCanvas(scale) {
const center = this.getCanvasCenter();
this.fabricCanvas.zoomToPoint({ x: center.x, y: center.y }, scale);
},
//获取画布的中心点
getCanvasCenter() {
const canvasCenter = {
x: this.fabricCanvas.width / 2,
y: this.fabricCanvas.height / 2
};
return canvasCenter;
},
handleKeyDown(event) {
console.log("event.key", event.key);
const step = 5; // 每次移动的步长
switch (event.key) {
case "ArrowUp":
this.canvasProp.translateY -= step;
break;
case "ArrowDown":
this.canvasProp.translateY += step;
break;
case "ArrowLeft":
this.canvasProp.translateX -= step;
break;
case "ArrowRight":
this.canvasProp.translateX += step;
break;
}
this.panCanvas(this.canvasProp.translateX, this.canvasProp.translateY);
},
loadFromJSON(json) {
// this.fabricCanvas.clear();
//背景图替换为当前的背景图
let newjson = JSON.parse(json);
console.log("加载的json", newjson);
newjson.backgroundImage = backgroundImage;
//this.fabricCanvas.loadFromJSON(newjson);
// 反序列化对象
this.fabricCanvas.loadFromJSON(newjson);
},
getCanvasJson() {
console.log("在线获取json", this.fabricCanvas.toJSON(["id"]));
return JSON.stringify(this.fabricCanvas.toJSON(["id"]));
},
hexToRgba(hex, alpha) {
const bigint = parseInt(hex.replace("#", ""), 16);
const r = (bigint >> 16) & 255;
const g = (bigint >> 8) & 255;
const b = bigint & 255;
return `rgba(${r},${g},${b},${alpha})`;
},
// ...其他方法
panCanvas(translateX, translateY) {
// 获取当前的 viewportTransform
const viewportTransform = this.fabricCanvas.viewportTransform.slice(); // 创建一个副本,以免直接修改原始数组
// 更新平移值
viewportTransform[4] = translateX;
viewportTransform[5] = translateY;
// 设置新的 viewportTransform
this.fabricCanvas.setViewportTransform(viewportTransform);
},
loadImageAndSetCanvas() {
if (!this.images) return;
const img = new Image();
img.src = this.images;
img.onload = () => {
console.log("图片加载完毕", img);
this.canvasProp.width = img.width * this.canvasSizeScale;
this.canvasProp.height = img.height * this.canvasSizeScale;
this.bgImg = img;
this.$nextTick(() => {
this.fabricCanvas = new fabric.Canvas("canvasId");
// 设置canvas大小
this.fabricCanvas.setWidth(this.canvasProp.width);
this.fabricCanvas.setHeight(this.canvasProp.height);
this.$refs.hiddenCanvas.width = img.width;
this.$refs.hiddenCanvas.height = img.height;
this.ctx = this.$refs.hiddenCanvas.getContext("2d");
this.ctx.drawImage(img, 0, 0, img.width, img.height);
// 创建 Fabric 图片对象
const fabricImage = new fabric.Image(img, {
left: 0,
top: 0,
width: img.width * this.canvasSizeScale, // 你可以根据需要调整宽度
height: img.height * this.canvasSizeScale, // 高度调整为原来的1.5倍
selectable: false // 防止背景图片被选择
});
// 设置背景图片
let backgroundImageObj = this.fabricCanvas.setBackgroundImage(
fabricImage
);
backgroundImage = backgroundImageObj.backgroundImage;
this.fabricCanvas.on("object:modified", this.modifyRect);
this.$emit("fabricEnd");
//this.drawTags(this.tagsData[0]);
});
};
},
clear() {
this.fabricCanvas.getObjects().forEach(obj => {
if (obj !== this.fabricCanvas.backgroundImage) {
this.fabricCanvas.remove(obj);
}
});
},
getGroupById(id) {
let result = null;
this.fabricCanvas.getObjects().forEach(obj => {
console.log(obj);
if (obj.id === id) {
result = obj;
}
});
return result;
},
remove(item) {
console.log("id", item.id);
let result = this.getGroupById(item.id);
console.log("result", result);
if (result) {
this.fabricCanvas.remove(result);
}
},
drawTags(item, callback = () => {}) {
// 创建一个矩形
const rect = new fabric.Rect({
fill: this.hexToRgba(item.color, 0.2), // 填充颜色,透明度为 0.2
width: item.width, // 矩形的宽度
height: item.height, // 矩形的高度
angle: 0, // 旋转角度
stroke: item.color,
strokeWidth: 2 // 边框宽度
});
// 创建第一个文字对象
const text1 = new fabric.Text(item.label, {
fontFamily: "Arial",
fontSize: 20,
fill: item.color // 文字颜色
// stroke: "#ffffff", // 文字边框颜色
// strokeWidth: 0.5 // 文字边框宽度
});
// 计算文字位置以确保其在矩形的正中央
text1.set({
left: rect.left + rect.width / 2,
top: rect.top + rect.height / 2,
originX: "center",
originY: "center"
});
// 使用fabric.Group将矩形和文字组合在一起
const group = new fabric.Group([rect, text1], {
left: item.isInit
? this.canvasProp.width / 2 - item.width / 2
: item.startX, // 矩形的左上角 x 坐标
top: item.isInit
? this.canvasProp.height / 2 - item.height / 2
: item.startY, // 矩形的左上角 y 坐标
cornerColor: item.color, // 控制点的颜色
cornerSize: 10, // 控制点的大小
borderWidth: 0, // 选中时的边框宽度
transparentCorners: true,
angle: item.rotate, // 组合对象的旋转角度
id: item.id
});
// 将组合添加到画布上
console.log("添加到画布上", group);
this.fabricCanvas.add(group);
callback();
},
saveData() {
this.getPointData();
},
getACoords(point, viewportTransform, zoom) {
return [Math.round(point.x), Math.round(point.y)];
},
getPointData() {
let result = {};
this.fabricCanvas.getObjects().forEach(rect => {
console.log("rect==", rect);
const coords = [];
const points = rect.get("aCoords"); // 获取矩形的绝对坐标
console.log("points", points);
const viewportTransform = this.fabricCanvas.viewportTransform;
const zoom = this.fabricCanvas.getZoom();
// 将内部坐标转换为实际画布坐标
coords.push(this.getACoords(points["tl"], viewportTransform, zoom));
coords.push(this.getACoords(points["tr"], viewportTransform, zoom));
coords.push(this.getACoords(points["br"], viewportTransform, zoom));
coords.push(this.getACoords(points["bl"], viewportTransform, zoom));
console.log("coords", coords);
result[rect.id] = coords;
});
console.log("result", result);
return result;
}
}
};
</script>
<style lang="scss" scoped>
.muane {
height: 36px;
background: #fafafa;
display: flex;
align-items: center;
padding: 0px 1px;
border-left: 1px solid rgb(229, 229, 229);
border-right: 1px solid rgb(229, 229, 229);
border-bottom: 1px solid rgb(229, 229, 229);
span {
width: 50%;
text-align: center;
}
}
.canvas-wrap {
border-left: 1px solid rgb(229, 229, 229);
border-right: 1px solid rgb(229, 229, 229);
border-top: 1px solid rgb(229, 229, 229);
}
</style>