利用canvas做图片裁剪并下载

需求:将一张图片分割成多个图片,并下载下来

实现:

页面部分:

<input id="file" type="file">

主要代码部分:

class SplitImage {
    constructor(options) {
      this.options = {
        col: 3,
        row: 3,
        inputEle: ''
      }
      this.options = Object.assign({}, this.options, options)
      if (!this.options.inputEle) {
        throw new Error('Options.inputEle is invalid! Please check!')
      }
      this.input = null
      this.canvas = null
      this.ctx = null
      this.img = null
      this.init()
    }
    init() {
      this.input = document.getElementById(this.options.inputEle)
      this.input.onchange = this.fileChange.bind(this)
      this.createCanvas()
    }
    async fileChange() {
      let file = this.input.files[0]
      try {
        let base64 = await this.fileReader(file)
        try {
          await this.createImg(base64)
          this.splitImg()
        } catch (e) {
          console.log(e)
        }
      } catch (e) {
        console.log(e)
      }
    }
    fileReader(file) { // 读取文件base64
      return new Promise((resolve, reject) => {
        const reader = new FileReader()
        reader.readAsDataURL(file)
        reader.onload = (e) => {
          const result = e.target.result
          resolve(result)
        }
        reader.onerror = (e) => {
          reject(e)
        }
      })
    }
    createImg(base64) { // 加载图片
      return new Promise((resolve, reject) => {
        const img = new Image()
        img.onload = (e) => {
          this.img = img
          resolve()
        }
        img.onerror = (e) => {
          console.log(e)
          reject(e)
        }
        img.src = base64
      })
    }
    createCanvas() { // 创建canvas
      this.canvas = document.createElement('canvas')
      this.ctx = this.canvas.getContext('2d')
    }
    drawImg(options = {}) { // 绘制图片
      this.canvas.width = options.width
      this.canvas.height = options.height
      this.ctx.drawImage(this.img, options.x, options.y, options.width, options.height, 0, 0, options.width, options.height)
      const base64 = this.canvas.toDataURL()
      // 借用a标签下载图片
      let a = document.createElement("a");
      a.href = base64;
      a.download = options.name + ".png";
      a.click();
      // 下面是将图片放入页面
      // let img = document.createElement('img')
      // img.src = base64
      // img.style.border = '5px solid transparent'
      // img.style.marginBottom = '-5px'
      // document.body.appendChild(img)
    }
    splitImg() { // 切割图片
      /*
	// 这里是手动写的配置,根据需要的设置
	let list = [
        // header
        {
          x: 0,
          y: 0,
          width: 135,
          height: 60,
          name: "header1"
        },
        {
          x: 136,
          y: 28,
          width: 150,
          height: 32,
          name: "header2"
        },
        {
          x: 340,
          y: 28,
          width: 46,
          height: 32,
          name: "header3"
        },
        // body
        {
          x: 0,
          y: 90,
          width: 30,
          height: 150,
          name: "body1"
        },
        {
          x: 50,
          y: 90,
          width: 150,
          height: 150,
          name: "body2"
        },
        {
          x: 340,
          y: 90,
          width: 46,
          height: 150,
          name: "body3"
        },
        // footer
        {
          x: 0,
          y: 390,
          width: 30,
          height: 40,
          name: "footer1"
        },
        {
          x: 50,
          y: 390,
          width: 150,
          height: 40,
          name: "footer2"
        },
        {
          x: 340,
          y: 390,
          width: 46,
          height: 40,
          name: "footer3"
        },
      ]*/
      let list = [];
      // 下面是动态生成的平均分配
      for (let y = 0; y < this.options.row; y++) {
        for (let x = 0; x < this.options.col; x++) {
          let simpleWidth = parseInt(this.img.width / this.options.col)
          let simpleHeight = parseInt(this.img.height / this.options.row)
          list.push({
            x: x * simpleWidth,
            y: y * simpleHeight,
            width: simpleWidth,
            height: simpleHeight
          })
        }
      }
      list.forEach(item => {
        this.drawImg(item)
      })
    }
  }

调用:

let splitImage = new SplitImage({
      col: 3,
      row: 3,
      inputEle: '#file'
    })

猜你喜欢

转载自blog.csdn.net/sunyv1/article/details/107086278