vue uses exif to get sample code of picture rotation and compression

  • 2021-10-13 06:26:21
  • OfStack


<template>
 <div>
  <input type="file" id="upload" accept="image" @change="upload" />
 </div>
</template>
<script>
export default {
 data() {
  return {
   picValue:{},
   headerImage:''
  };
 },
 components: {},
 methods: {
  upload(e) {
   console.log(e);
   let files = e.target.files || e.dataTransfer.files;
   if (!files.length) return;
   this.picValue = files[0];
   this.imgPreview(this.picValue);
  },
  imgPreview(file) {
   let self = this;
   let Orientation;
   // To get the information when taking pictures and solve the rotation problem of the taken photos 
   self.Exif.getData(file, function() {
    Orientation = self.Exif.getTag(this, 'Orientation');
   });
   //  See if it is supported or not FileReader
   if (!file || !window.FileReader) return;

   if (/^image/.test(file.type)) {
    //  Create 1 A reader
    let reader = new FileReader();
    //  Putting a picture 2 Will be converted to  base64  Format 
    reader.readAsDataURL(file);
    //  Callback after successful reading 
    reader.onloadend = function() {
     let result = this.result;
     let img = new Image();
     img.src = result;
     // Determine whether the picture is larger than 100K, If yes, upload it directly, otherwise compress the picture 
     if (this.result.length <= 100 * 1024) {
      self.headerImage = this.result;
      self.postImg();
     } else {
      img.onload = function() {
       let data = self.compress(img, Orientation);
       self.headerImage = data;
       self.postImg();
      };
     }
    };
   }
  },
  compress(img, Orientation) {
   let canvas = document.createElement('canvas');
   let ctx = canvas.getContext('2d');
   // Tile canvas
   let tCanvas = document.createElement('canvas');
   let tctx = tCanvas.getContext('2d');
   let initSize = img.src.length;
   let width = img.width;
   let height = img.height;
   // If the picture is larger than 4 Megapixels, calculate the compression ratio and press the size to 400 Below ten thousand 
   let ratio;
   if ((ratio = (width * height) / 4000000) > 1) {
    console.log(' Greater than 400 Ten thousand pixels ');
    ratio = Math.sqrt(ratio);
    width /= ratio;
    height /= ratio;
   } else {
    ratio = 1;
   }
   canvas.width = width;
   canvas.height = height;
   //     Pave the background color 
   ctx.fillStyle = '#fff';
   ctx.fillRect(0, 0, canvas.width, canvas.height);
   // If the picture pixels are larger than 100 Ten thousand are drawn with tiles 
   let count;
   if ((count = (width * height) / 1000000) > 1) {
    console.log(' Exceed 100W Pixel ');
    count = ~~(Math.sqrt(count) + 1); // Calculate how many tiles to divide into 
    //       Calculate the width and height of each tile 
    let nw = ~~(width / count);
    let nh = ~~(height / count);
    tCanvas.width = nw;
    tCanvas.height = nh;
    for (let i = 0; i < count; i++) {
     for (let j = 0; j < count; j++) {
      tctx.drawImage(
       img,
       i * nw * ratio,
       j * nh * ratio,
       nw * ratio,
       nh * ratio,
       0,
       0,
       nw,
       nh
      );
      ctx.drawImage(tCanvas, i * nw, j * nh, nw, nh);
     }
    }
   } else {
    ctx.drawImage(img, 0, 0, width, height);
   }
   // Repair ios When uploading pictures,   The problem of being rotated 
   if (Orientation != '' && Orientation != 1) {
    switch (Orientation) {
     case 6: // Need clockwise (left) 90 Degree rotation 
      this.rotateImg(img, 'left', canvas);
      break;
     case 8: // Need counterclockwise (right) 90 Degree rotation 
      this.rotateImg(img, 'right', canvas);
      break;
     case 3: // Need 180 Degree rotation 
      this.rotateImg(img, 'right', canvas); // Turn twice 
      this.rotateImg(img, 'right', canvas);
      break;
    }
   }
   // Perform minimum compression 
   let ndata = canvas.toDataURL('image/jpeg', 0.1);
   tCanvas.width = tCanvas.height = canvas.width = canvas.height = 0;
   return ndata;
  },
  rotateImg(img, direction, canvas) {
   // Minimum and maximum rotation directions, picture rotation 4 Return to the original direction after the second time 
   const min_step = 0;
   const max_step = 3;
   if (img == null) return;
   //img The height and width of cannot be in the img Element is hidden, otherwise an error will occur 
   let height = img.height;
   let width = img.width;
   let step = 2;
   if (step == null) {
    step = min_step;
   }
   if (direction == 'right') {
    step++;
    // Rotate to the original position, that is, exceed the maximum value 
    step > max_step && (step = min_step);
   } else {
    step--;
    step < min_step && (step = max_step);
   }
   // The rotation angle is based on the radian value 
   let degree = (step * 90 * Math.PI) / 180;
   let ctx = canvas.getContext('2d');
   switch (step) {
    case 0:
     canvas.width = width;
     canvas.height = height;
     ctx.drawImage(img, 0, 0);
     break;
    case 1:
     canvas.width = height;
     canvas.height = width;
     ctx.rotate(degree);
     ctx.drawImage(img, 0, -height);
     break;
    case 2:
     canvas.width = width;
     canvas.height = height;
     ctx.rotate(degree);
     ctx.drawImage(img, -width, -height);
     break;
    case 3:
     canvas.width = height;
     canvas.height = width;
     ctx.rotate(degree);
     ctx.drawImage(img, -width, 0);
     break;
   }
  },
  postImg() {
   // Write the interface here 
      // Printed pictures base64

   console.log('this.headerImage',this.headerImage);
   // Interface  axios
  }
 }
};
</script>

To run first


npm install exif-js --save

Then add in main. js


import Exif from 'exif-js'
Vue.use(Exif)
Vue.prototype.Exif = Exif

Above is the vue use exif to obtain image rotation, compression sample code details, more about vue image rotation, compression information please pay attention to other related articles on this site!


Related articles: