在线图片标注

需求:在线简易PS (效果类似 http://120.92.164.43:3000/)
功能:

  1. 可以快捷键控制图片局部放大缩小
  2. 可标记点、线、框(并记录下标记坐标信息)、多边形
  3. 可以动态创建XY轴的标尺,且标尺跟随鼠标移动.
  4. 可以把标注的信息导出为json 或xml

设计:Canvas 编辑
问题:如何保证图像缩放、放大的标注比例和定位。
请有开发经验的分享一下,大致处理方法。

阅读 5.7k
1 个回答

考虑框架吗?fabric(https://github.com/fabricjs/fabric.js)绝对值得一用。
它不仅有自己的各种绘图api,还自带拖拽、缩放功能,然后自带各种监听事件,不论是canvas自身的事件还是节点的事件,都可以使用;
然后我这边提供了一个方法,限制拖拽的时候不超出边界。
具体的缩放、拖拽对于中心点位置的处理方式请参考以下博主的博客:
基于Vue的Fabricjs的画布移动和缩放,以及鼠标在缩放与移动后的画布上的定位(二)
基于Vue的Fabricjs的画布移动和缩放,以及鼠标在缩放与移动后的画布上的定位(二)

demo传送门,在原来作者的基础上新增了拖拽不超出边界的方法、图片作为画布背景,更好的处理缩放拖拽等功能。
vue-fabric-drawing

keepPositionInBounds(flag) {
  var zoom = this.fabricObj.getZoom();
  var xMin = ((2 - zoom) * this.fabricObj.getWidth()) / 2;
  var xMax = (zoom * this.fabricObj.getWidth()) / 2;
  var yMin = ((2 - zoom) * this.fabricObj.getHeight()) / 2;
  var yMax = (zoom * this.fabricObj.getHeight()) / 2;
  var point = new fabric.Point(
    this.fabricObj.getWidth() / 2,
    this.fabricObj.getHeight() / 2
  );
  var center = fabric.util.transformPoint(
    point,
    this.fabricObj.viewportTransform
  );
  var clampedCenterX = this.clamp(center.x, xMin, xMax);
  var clampedCenterY = this.clamp(center.y, yMin, yMax);
  var diffX = clampedCenterX - center.x;
  var diffY = clampedCenterY - center.y;
  if (diffX != 0 || diffY != 0) {
    this.relativeMouseX += diffX; //累计每一次移动时候的偏差
    this.relativeMouseY += diffY;
    this.fabricObj.relativePan(new fabric.Point(diffX, diffY));
  }
  if (flag) this.resetOriginAfterZoom();
},
撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题