vue 图形验证码组件

简介: vue 图形验证码组件

1.新建公共组件 /src/page/common/IdentifyCode.vue

<template>
  <div class="canvas-box" @click="changeCode">
    <canvas id="cont-canvas" :width="contentWidth" :height="contentHeight"></canvas>
  </div>
</template>

<script>
export default {
  name: "IdentifyCode",
  data() {
    return {
      identifyCode: ""
    };
  },
  props: {
    identifyCodes: {
      //验证码从该字段中抽取生成
      type: String,
      default: "ABCDEFGHJKMNPQRSTWXYZabcdefhijkmnprstwxyz2345678"
    },
    fontSizeMin: {
      // 字体最小值
      type: Number,
      default: 25
    },
    fontSizeMax: {
      // 字体最大值
      type: Number,
      default: 35
    },
    backgroundColorMin: {
      // 验证码图片背景色最小值
      type: Number,
      default: 200
    },
    backgroundColorMax: {
      // 验证码图片背景色最大值
      type: Number,
      default: 220
    },
    dotColorMin: {
      // 背景干扰点最小值
      type: Number,
      default: 60
    },
    dotColorMax: {
      // 背景干扰点最大值
      type: Number,
      default: 120
    },
    contentWidth: {
      //容器宽度
      type: Number,
      default: 100
    },
    contentHeight: {
      //容器高度
      type: Number,
      default: 40
    }
  },
  watch: {
    identifyCode() {
      this.drawPic();
    }
  },
  mounted() {
    this.drawPic();
    this.makeCode(this.identifyCodes, 4);
  },
  methods: {
    // 生成一个随机数
    randomNum(min, max) {
      return Math.floor(Math.random() * (max - min) + min);
    },
    // 生成一个随机的颜色
    randomColor(min, max) {
      let r = this.randomNum(min, max);
      let g = this.randomNum(min, max);
      let b = this.randomNum(min, max);
      return "rgb(" + r + "," + g + "," + b + ")";
    },
    drawPic() {
      let canvas = document.getElementById("cont-canvas");
      let ctx = canvas.getContext("2d");
      ctx.textBaseline = "bottom";
      // 绘制背景
      ctx.fillStyle = this.randomColor(
        this.backgroundColorMin,
        this.backgroundColorMax
      );
      ctx.fillRect(0, 0, this.contentWidth, this.contentHeight);
      // 绘制文字
      for (let i = 0; i < this.identifyCode.length; i++) {
        this.drawText(ctx, this.identifyCode[i], i);
      }
      this.drawLine(ctx);
      this.drawDot(ctx);
    },
    drawText(ctx, txt, i) {
      ctx.fillStyle = this.randomColor(50, 160); //随机生成字体颜色
      ctx.font =
        this.randomNum(this.fontSizeMin, this.fontSizeMax) + "px SimHei"; //随机生成字体大小
      let x = (i + 1) * (this.contentWidth / (this.identifyCode.length + 1));
      let y = this.randomNum(this.fontSizeMax, this.contentHeight - 5);
      var deg = this.randomNum(-30, 30);
      // 修改坐标原点和旋转角度
      ctx.translate(x, y);
      ctx.rotate((deg * Math.PI) / 180);
      ctx.fillText(txt, 0, 0);
      // 恢复坐标原点和旋转角度
      ctx.rotate((-deg * Math.PI) / 180);
      ctx.translate(-x, -y);
    },
    drawLine(ctx) {
      // 绘制干扰线
      for (let i = 0; i < 4; i++) {
        ctx.strokeStyle = this.randomColor(100, 200);
        ctx.beginPath();
        ctx.moveTo(
          this.randomNum(0, this.contentWidth),
          this.randomNum(0, this.contentHeight)
        );
        ctx.lineTo(
          this.randomNum(0, this.contentWidth),
          this.randomNum(0, this.contentHeight)
        );
        ctx.stroke();
      }
    },
    drawDot(ctx) {
      // 绘制干扰点
      for (let i = 0; i < 30; i++) {
        ctx.fillStyle = this.randomColor(0, 255);
        ctx.beginPath();
        ctx.arc(
          this.randomNum(0, this.contentWidth),
          this.randomNum(0, this.contentHeight),
          1,
          0,
          2 * Math.PI
        );
        ctx.fill();
      }
    },
    /*切换验证码start*/
    changeCode() {
      this.identifyCode = "";
      this.makeCode(this.identifyCodes, 4);
    },
    makeCode(e, n) {
      for (let i = 0; i < n; i++) {
        this.identifyCode += e[this.randomNum(0, e.length)];
      }
      console.log('code = ',this.identifyCode)
      this.$emit("update:changeCode", this.identifyCode);
    },
    randomNum(min, max) {
      return Math.floor(Math.random() * (max - min) + min);
    }
    /*切换验证码end*/
  }
};
</script>
<style scoped>
.canvas-box {
    padding-top: 7px;
}
</style>

2.使用方法

<template>
    <div>
        <identify-code :changeCode.sync='identifyCode'></identify-code>
    </div>
</template>

<script>
import IdentifyCode from '@/page/common/IdentifyCode'
export default {
    components: {
        IdentifyCode
    },
    data() {
        return {
            identifyCode:'',    //当前生成的验证码
        }
    }
}
</script>
目录
相关文章
|
6天前
|
缓存 监控 JavaScript
探讨优化Vue应用性能和加载速度的策略
【5月更文挑战第17天】本文探讨了优化Vue应用性能和加载速度的策略:1) 精简代码和组件拆分以减少冗余;2) 使用计算属性和侦听器、懒加载、预加载和预获取优化路由;3) 数据懒加载和防抖节流处理高频事件;4) 图片压缩和选择合适格式,使用CDN加速资源加载;5) 利用浏览器缓存和组件缓存提高效率;6) 使用Vue Devtools和性能分析工具监控及调试。通过这些方法,可提升用户在复杂应用中的体验。
21 0
|
7天前
|
JavaScript 前端开发
vue(1),小白看完都会了
vue(1),小白看完都会了
|
1天前
|
JavaScript
vue知识点
vue知识点
11 4
|
2天前
|
JavaScript Java 关系型数据库
基于SprinBoot+vue的租房管理系统2
基于SprinBoot+vue的租房管理系统2
9 0
|
2天前
|
自然语言处理 JavaScript 数据可视化
5个值得推荐的Vue后台管理框架
几个优秀好看的 Vue 后台管理框架,每个框架都有自己的特点和优势,开发者可以根据项目需求选择适合的框架。
15 0
|
6天前
|
JavaScript 开发工具 git
Vue 入门系列:.env 环境变量
Vue 入门系列:.env 环境变量
13 1
|
7天前
|
JavaScript 前端开发 定位技术
Vue使用地图以及实现轨迹回放 附完整代码
Vue使用地图以及实现轨迹回放 附完整代码
Vue使用地图以及实现轨迹回放 附完整代码
|
7天前
|
JavaScript
Vue中避免滥用this去读取data中数据
Vue中避免滥用this去读取data中数据
|
7天前
|
JavaScript
vue中使用pinia及持久化
vue中使用pinia及持久化
12 0
|
7天前
|
JavaScript 前端开发 UED
Vue class和style绑定:动态美化你的组件
Vue class和style绑定:动态美化你的组件