最近在开发过程中有一个需求:
要在一个不规则的物体图片上画标点,获取所有坐标,然后计算出相对面积。
步骤思路:
用到两个位置数据(官方文档):MouseEvent.clientX,MouseEvent.clientY
他们的概念如下:红点是鼠标点击
用到的一个位置函数(官方文档):getBoundingClientRect()
概念:
var bbox = _this.canvas.getBoundingClientRect();
由上可知:canvas中的实际坐标值为
x = event.clientX - bbox.left
y = event.clientX- bbox.top
之后我们要做的是,把canvas坐标映射成像素点坐标。
<template>
<div>
<div style="float:left;width:90%">
<canvas id="mycanvas" @mousedown="setPoint">canvas>
div>
template>
// imageUrl为后台提供图片地址
doDraw(imageUrl) {
let _this = this;
_this.canvas = document.getElementById("mycanvas");
_this.context = this.canvas.getContext("2d");
if (!_this.canvas) {
return false;
} else {
// 可以理解为一个画笔,可画路径、矩形、文字、图像
_this.img = new Image();
_this.img.src = imageUrl;
// 加载图片
_this.img.onload = function() {
if (_this.img.complete) {
// canvasW就是canvas的实际宽度
if(_this.img.width>700){
_this.canvasW = 700}
else{
_this.canvasW = _this.img.width;
_this.canvas.setAttribute("width", _this.img.width);
_this.canvas.setAttribute("height", _this.img.height);
// 绘制图片
_this.context.drawImage(
_this.img,
0,
0,
_this.img.width,
_this.img.height
);
}
};
}
},
canvasW 是记录实际的canvas大小的,因为没有设置canvas的宽度,那么它的宽度就是图片的宽度。
由于实际要求,图片 max-width: 700px; 即canva最大700px;
//画圆点
setPoint(event) {
let _this = this;
//调用像素坐标计算函数 传参:鼠标坐标
let loc = _this.windowToCanvas(event.clientX, event.clientY);
//设置绘制颜色 宽度
_this.context.strokeStyle = "#ca113f";
_this.context.lineWidth = 2;
//圆点
_this.context.arc(loc.x, loc.y, 1.5, 0, 2 * Math.PI);
//动作存储 方便进行撤销
_this.pointList.push(loc);
_this.context.stroke();
},
//获取实际的像素坐标
windowToCanvas(x, y) {
let _this = this;
//方法返回元素的大小及其相对于视口的位置
var bbox = _this.canvas.getBoundingClientRect();
return {
x: (x - bbox.left)*(_this.img.width/_this.canvasW),
y: (y - bbox.top)*(_this.img.width/_this.canvasW)
};
},
//撤销上一步
undoPoint() {
let _this = this;
// 清空画布
_this.canvas.height = _this.img.height;
// 减少点
_this.pointList.pop();
// 绘制图片
_this.context.drawImage(
_this.img,
0,
0,
_this.img.width,
_this.img.height
);
// 逐个执行绘图动作进行重绘
for (let i = 0; i < _this.pointList.length; i++) {
_this.context.strokeStyle = "#ca113f";
_this.context.lineWidth = 2;
_this.context.arc(
_this.pointList[i].x,
_this.pointList[i].y,
1.5,
0,
2 * Math.PI
);
_this.context.stroke();
}
},