用canvas实现图片信息标注

今天有个可爱的小姐姐有些疑惑,类似于这样的图片标注效果怎么实现呢?
在这里插入图片描述
我就想着也试了一下
大概思路就是用canvas,弄个覆盖在图片上的画布,就可以开始画了。
我们需要找到需要标注的点,比如眼睛,鼻子,嘴巴的坐标位置,找到位置就好画延展的线了,
那么坐标怎么找呢,我们可以在画布上画一个圆点,比如画布是1000宽高的,那么我们圆点就是(500,500)了,画好圆点之后然后通过移动坐标找到五官对应的坐标点了。

const myCanvas = document.getElementById("myCanvas")
  // 画布
  myCanvas.width = 1000
  myCanvas.height = 1000
  let ctx = myCanvas.getContext('2d')

  const xR = myCanvas.height / 2 // 圆点
  const yR = myCanvas.height / 2
  // 绘画点
  function setDian(x, y, r) {
    ctx.beginPath()
    ctx.arc(x, y, r, 0, 2 * Math.PI)
    ctx.fillStyle = 'blue'
    ctx.fill()
    ctx.stroke();
  }
this.setDian(xR , yR , 10) // 圆点

这样找到五官对应的坐标,就可以开始连线了

const xY1 = 500, yY1 = 400 // 眼睛1
  const xY2 = 400, yY2 = 650 // 眼睛2
  const xBZ = 500, yBZ = 550 // 鼻子

连线的地方用到很多,所以和画点一样都写在方法里,下次需要用就调用方法就可以了

function setLine(x, y, x2, y2) {
    ctx.strokeStyle = "blue"
    ctx.beginPath(); //新建一条path
    ctx.moveTo(x, y); //把画笔移动到指定的坐标
    ctx.lineTo(x2, y2);  //绘制一条从当前位置到指定坐标(200, 50)的直线.
    //闭合路径。会拉一条从当前点到path起始点的直线。如果当前点与起始点重合,则什么都不做
    ctx.closePath();
    ctx.stroke(); //绘制路径。
  }

因为就想着实现一下思路,大致就这样,贴一下完整代码:

<!DOCTYPE html>
<html lang="cms-Hans-CN">

<head>
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
  <title>标题</title>
  <style>
    body {
      padding: 0;
      margin: 0;
    }

    .app {
      width: 100vw;
      height: 100vh;
    }

    .img_bg {
      width: 100vw;
      height: 100vh;
      display: flex;
      justify-content: center;
      align-items: center;
    }

    .img {
      width: 100vw;
      height: auto;
    }

    .canvas_bg {
      width: 100vw;
      height: 100vh;
      display: flex;
      justify-content: center;
      align-items: center;
      position: fixed;
      top: 0;
      left: 0;
      z-index: 1;
    }
  </style>
</head>

<body>
  <div class="app">
    <div class="img_bg">
      <img src="https://img2.baidu.com/it/u=1925553718,3069984470&fm=26&fmt=auto&gp=0.jpg" class="img">
    </div>
    <div class="canvas_bg">
      <canvas id="myCanvas" class="canvas"></canvas>
    </div>
  </div>
</body>
<script>
  const myCanvas = document.getElementById("myCanvas")
  // 画布
  myCanvas.width = 1000
  myCanvas.height = 1000
  let ctx = myCanvas.getContext('2d')

  const xR = myCanvas.height / 2 // 圆点
  const yR = myCanvas.height / 2

  const xY1 = 500, yY1 = 400 // 眼睛1
  const xY2 = 400, yY2 = 650 // 眼睛2
  const xBZ = 500, yBZ = 550 // 鼻子

  // 绘画点
  function setDian(x, y, r) {
    ctx.beginPath()
    ctx.arc(x, y, r, 0, 2 * Math.PI)
    ctx.fillStyle = 'blue'
    ctx.fill()
    ctx.stroke();
  }

  function setLine(x, y, x2, y2) {
    ctx.strokeStyle = "blue"
    ctx.beginPath(); //新建一条path
    ctx.moveTo(x, y); //把画笔移动到指定的坐标
    ctx.lineTo(x2, y2);  //绘制一条从当前位置到指定坐标(200, 50)的直线.
    //闭合路径。会拉一条从当前点到path起始点的直线。如果当前点与起始点重合,则什么都不做
    ctx.closePath();
    ctx.stroke(); //绘制路径。
  }

  // 左眼
  this.setDian(xY1, yY1, 10) // 小圆点
  this.setLine(xY1, yY1, xY1, yY1 - 300) // 竖线
  this.setDian(xY1, yY1 - 300, 80) // 大圆点
  ctx.fillStyle = '#fff'
  ctx.font = "40px Georgia";
  ctx.fillText('左眼', xY1 - 40, yY1 - 280) // 字

  // 右眼
  this.setDian(xY2, yY2, 10) // 小圆点
  this.setLine(xY2, yY2, xY2 - 200, yY2) // 横线
  this.setLine(xY2 - 200, yY2, xY2 - 200, yY2 - 300) // 竖线
  this.setDian(xY2 - 200, yY2 - 300, 80) // 大圆点
  ctx.fillStyle = '#fff'
  ctx.font = "40px Georgia";
  ctx.fillText('右眼', xY2 - 240, yY2 - 280) // 字

  this.setDian(xBZ, yBZ, 10) // 小圆点
  this.setLine(xBZ, yBZ, xBZ + 200, yBZ) // 横线
  this.setLine(xBZ + 200, yBZ, xBZ + 200, yBZ - 300) // 竖线
  this.setDian(xBZ + 200, yBZ - 300, 80) // 大圆点
  ctx.fillStyle = '#fff'
  ctx.font = "40px Georgia";
  ctx.fillText('鼻子', xBZ + 160, yBZ - 280) // 字
</script>

</html>

注:图片是随便网上找的可爱猫猫图片地址,所以可能会有图片失效的情况,但不影响其他的

  • 1
    点赞
  • 5
    收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

爱酱丶

你的鼓励将是我创作的最大动力

¥2 ¥4 ¥6 ¥10 ¥20
输入1-500的整数
余额支付 (余额:-- )
扫码支付
扫码支付:¥2
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值