Vue + exif实现图片旋转

html5+canvas进行移动端手机照片上传时,发现ios手机上传竖拍照片会逆时针旋转90度,横拍照片无此问题;Android手机没这个问题。

因此解决这个问题的思路是:获取到照片拍摄的方向角,对非横拍的ios照片进行角度旋转修正。
注:在开发时发现 三星手机提交时会向右旋转90度 所以对仅对安卓系统中三星手机进行特别处理
这里主要用到Orientation属性。说明如下:

旋转角度 参数
1
顺时针90° 6
逆时针90° 8
180° 3

一、html文件

<a href="javascript:document.getElementById('fileobj').click()">
  <button type="button" class="upload-image-btn" >
  <span class="upload-btn-text" v-if="!show_upload_next_button" v-text="Camera / Photo">span>
  <span class="upload-btn-text" v-text="Please add the images" v-else>span>
  button>
a>
<input type="file" id="fileobj" accept="image/*" style="display:none" @change="fileobj_change">

二、js文件

fileobj_change: function(e) {
  var vue_this = this;
  var file = e.target.files[0];
  vue_this.show_loading = true;
  var orientation = 0;
  EXIF.getData(file, function() {
    EXIF.getAllTags(this);
    orientation = EXIF.getTag(this, 'Orientation');
  });
  // console.log(orientation)
  var reader = new FileReader();
  reader.onload = function(readerEvent) {
  var face_image = new Image();
    face_image.onload = function(imageEvent) {
      var canvas = document.getElementById('sketchpad');
      drawPhotoImage(this, canvas, face_image, orientation);
      vue_this.image_url = canvas.toDataURL('image/jpeg');
      vue_this.show_upload_next_button = true;
      vue_this.show_loading = false;
    };
    face_image.src = readerEvent.target.result;
  };
  reader.readAsDataURL(file);
}
function drawPhotoImage(image, canvas, face_image, orientation) {
  var max_size = 544,
    width = face_image.width,
    height = face_image.height;
    if (width > height) {
      if (width > max_size) {
         height *= max_size / width;
         width = max_size;
      }
    } else {
      if (height > max_size) {
        width *= max_size / height;
        height = max_size;
      }
  }
  canvas.width = width;
  canvas.height = height;
  if (navigator.userAgent.match(/iphone/i)) {
    if (orientation != "" && orientation != 1) {
      switch (orientation) {
        case 6:
          rotateImg(image, 'left', canvas, width, height);
            break;
        case 8:
          rotateImg(image, 'right', canvas, width, height);
            break;
        case 3:
          /*
          //原资料中旋转180度方法为调用两遍90度 但是我这边不起作用 所以增加一种新的方式 => right2
          rotateImg(image, 'right', canvas, width, height);
          rotateImg(image, 'right', canvas, width, height);*/
          rotateImg(image, 'right2', canvas, width, height);
          break;
        default:
          canvas.getContext('2d').drawImage(face_image, 0, 0, width, height);
          break;
      }
    } else {
      canvas.getContext('2d').drawImage(face_image, 0, 0, width, height);
    }
  }else if(get_ua_info()){
    rotateImg(image, 'left', canvas, width, height);
  }else {
    canvas.getContext('2d').drawImage(face_image, 0, 0, width, height);
  }
}

function rotateImg(img, direction, canvas, width, height) {
  var min_step = 0;
  var max_step = 3;
  if (img == null) {
    return;
  }
  var step = 2;
  if (step == null) {
    step = min_step;
  }
  if (direction == 'right') {
    step++;
    step > max_step && (step = min_step);
  }else if(direction == 'right2'){
    step = 2;
  }else {
    step--;
    step < min_step && (step = max_step);
  }
  var degree = step * 90 * Math.PI / 180;
  var ctx = canvas.getContext('2d');
  switch (step) {
    case 0:
      canvas.width = width;
      canvas.height = height;
      ctx.drawImage(img, 0, 0, width, height);
      break;
    case 1:
      canvas.width = height;
      canvas.height = width;
      ctx.rotate(degree);
      ctx.drawImage(img, 0, -height, width, height);
      break;
    case 2:
      canvas.width = width;
      canvas.height = height;
      ctx.rotate(degree);
      ctx.drawImage(img, -width, -height, width, height);
      break;
    case 3:
      canvas.width = height;
      canvas.height = width;
      ctx.rotate(degree);
      ctx.drawImage(img, -width, 0, width, height);
      break;
    }
}
//判断是否为三星手机
//注:此方法准确率欠佳 若有需求可参考https://github.com/fex-team/ua-device
function get_ua_info(){
  if(navigator.userAgent.indexOf(" SM-")!=-1)
    return true;
  else 
    return false;
}

github:

https://github.com/exif-js/exif-js

你可能感兴趣的:(Web)