vue3中图片上传使用cropperjs 头像裁剪

1,151 阅读1分钟

ps:因为是在H5中使用,所以用了vant插件,可以根据需求运用插件;

1.引入插件cropperjs

npm install cropperjs

2.图片上传,并弹出裁剪图片的框

我把图片裁剪单独写了一个组件,在需要的页面上引入组件即可;

//html部分
<van-uploader upload-text="点击上传照片" upload-icon="plus" :after-read="afterRead"/>
<van-popup v-model:show="showBigImg">
    <head-cropper v-if="showBigImg" :imgBig="showHead" @clipImg="clipImg"></head-cropper>
</van-popup>
//js部分
<script setup>
import {toRefs,reactive,onMounted} from 'vue';
import headCropper from "@/components/headImg/headCropper";
const showBigImg = ref(false);  //定义是否显示裁剪框
const showHead = ref('');   //定义图片容器
const afterRead = (file) => { //图片上传完成之后
  showHead.value = file.content; //这里是base64
  showBigImg.value=true;
};
const clipImg = (e) =>{   
 //e 为组件传过来的,裁剪后的图片,是base64;
 //这里可以上传头像到服务器;
 console.log(e);
}

</script>

headCropper组件内容;因为vue3没有this.$refs方法获取ref;直接定义一个与html中ref同名的变量,然后.value就能获取ref的内容了(代码中imageVal.value,就是ref为imageVal的内容);

<template>
  <div class="bigContent">   
    <div class="contentMain">
      <img
      ref="imageVal"
      :src="imgBig"
      class="imgClass"              
    />
    </div>
     <div class="bigImgPD">
      <van-button block class="bigImgBtn" color="#004098" @click="sureSave" >
          确认
      </van-button>
    </div>
  </div>  
</template>

<script setup>
import {defineProps,defineEmits,reactive,onMounted,ref} from 'vue';
import Cropper from 'cropperjs'
import 'cropperjs/dist/cropper.css'
//props传值
const props = defineProps({
  imgBig:{
    type:String,
    default:''
  }
})
//emit 返回值
const emit = defineEmits(['clipImg']);
const imageVal = ref(null); //裁剪图片容器区域
const  cropperObj= reactive({
  afterImg:'', //裁剪后的图片
  myCropper:null //进行裁剪
})
onMounted(()=>{
  cropperObj.myCropper = new Cropper(imageVal.value, {
      viewMode: 1, //裁剪框不能超出图片的范围     
      outputType:'jpg', 
      fixed:true,
      dragMode: 'move', //拖拽图片模式 move 图片可移动 
      guides:false, //是否显示裁剪框的虚线  
      center:false, //是否显示裁剪框中间的 ‘+’ 指示器 默认true
      aspectRatio:0.8, //设置裁剪框为固定的宽高比
      background: false,//是否在容器内显示网格状的背景 默认true
      cropBoxMovable:false, //是否可以拖拽裁剪框 默认true
      cropBoxResizable:false, // 是否可以改变裁剪框的尺寸
      autoCrop:true, //默认生成截图框 
      fixedBox:true, //固定截图框大小 不允许改变
      autoCropArea:0.95, //设置裁剪区域占图片的大小 值为 0-1 默认 0.8 表示 80%的区域
      zoomOnWheel: true,//鼠标滑轮是否可以放大缩小图片
      fixedNumber:[0.8,1], //截图框比例
      canMoveBox:false,  //截图框拖动,true 可以拖动
      canMove:true,  //上传图片是否可以拖动
      centerBox:false, //截图框是否被限制在图片里
      autoCropWidth:464, //自动裁剪宽度
      autoCropHeight:576, //自动裁剪高度
      infoTure:true, //看到的裁图框宽高
    })
})
const sureSave = () =>{
  cropperObj.afterImg = cropperObj.myCropper.getCroppedCanvas({
      imageSmoothingQuality: 'high'
    }).toDataURL('image/jpeg')
  emit('clipImg',cropperObj.afterImg);//把裁剪的图片返回到父组件
}
</script>