vue+elementui+vueCropper裁剪上传图片背景颜色为黑色解决方案
组件 <template><div class="avatar-uploader"><!-- 头像展示 --><div class="avatar-show"><img :src="avatarUrl" v-if="avatarUrl" class="avatar"><i class="el-icon-plus avatar-uploader-icon" v-else></i></div><!-- 上传按钮 --><el-uploadclass="avatar-upload"action="#":show-file-list="false":before-upload="beforeAvatarUpload":http-request="handleUpload"><el-button size="small" type="primary">点击上传</el-button><div slot="tip" class="el-upload__tip">只能上传jpg/png文件,且不超过2MB</div></el-upload><!-- 裁剪对话框 --><el-dialog title="裁剪头像" :visible.sync="dialogVisible" width="800px"><div class="cropper-content"><div class="cropper"><vue-cropperref="cropper":img="cropperImg":output-size="1":output-type="'png'":info="true":full="true":can-move="true":can-move-box="true":fixed="true":fixed-number="[1, 1]":center-box="true":auto-crop="true":auto-crop-width="200":auto-crop-height="200"></vue-cropper></div></div><span slot="footer" class="dialog-footer"><el-button @click="dialogVisible = false">取 消</el-button><el-button type="primary" @click="handleCrop">确 定</el-button></span></el-dialog></div> </template><script> import { VueCropper } from 'vue-cropper'export default {components: {VueCropper},props: {value: String // 用于v-model绑定},data() {return {dialogVisible: false,cropperImg: '', // 裁剪图片的base64// avatarUrl: this.value || require('@/assets/logo.png') // 默认头像avatarUrl: null // 默认头像}},methods: {// 上传前校验beforeAvatarUpload(file) {const isJPG = file.type === 'image/jpeg' || file.type === 'image/png'const isLt2M = file.size / 1024 / 1024 < 2if (!isJPG) {this.$message.error('上传头像图片只能是 JPG/PNG 格式!')}if (!isLt2M) {this.$message.error('上传头像图片大小不能超过 2MB!')}return isJPG && isLt2M},// 处理上传handleUpload(file) {const reader = new FileReader()reader.onload = (event) => {this.cropperImg = event.target.resultthis.dialogVisible = truethis.$nextTick(() => {this.$refs.cropper.replace(event.target.result)})}reader.readAsDataURL(file.file)},// 处理裁剪handleCrop() {this.$refs.cropper.getCropBlob((blob) => {// 创建FormData对象上传const formData = new FormData()formData.append('file', blob, 'avatar.png')// 这里替换为你的上传APIthis.$axios.post('/api/upload/avatar', formData, {headers: {'Content-Type': 'multipart/form-data'}}).then(response => {this.avatarUrl = response.data.urlthis.$emit('input', this.avatarUrl) // 更新v-modelthis.dialogVisible = falsethis.$message.success('头像上传成功!')}).catch(error => {this.$message.error('头像上传失败!')console.error(error)})})},// 也可以使用base64格式handleCropBase64() {this.$refs.cropper.getCropData((data) => {this.avatarUrl = datathis.$emit('input', data) // 更新v-modelthis.dialogVisible = falsethis.$message.success('头像裁剪成功!')})}},watch: {value(newVal) {this.avatarUrl = newVal}} } </script><style scoped> .avatar-uploader {display: flex;flex-direction: column;align-items: center; }.avatar-show {width: 150px;height: 150px;border: 1px dashed #d9d9d9;border-radius: 50%;overflow: hidden;display: flex;justify-content: center;align-items: center;margin-bottom: 20px; }.avatar {width: 100%;height: 100%;object-fit: cover; }.avatar-uploader-icon {font-size: 28px;color: #8c939d; }.cropper-content {display: flex;justify-content: center; }.cropper {width: 500px;height: 500px; }.el-upload__tip {margin-top: 10px;text-align: center; } </style>
组件调用
<template>
<div>
<h2>个人头像设置</h2>
<avatar-uploader v-model="avatar"></avatar-uploader>
</div>
</template>
<script>
import AvatarUploader from '@/components/AvatarUploader'
export default {
components: {
AvatarUploader
},
data() {
return {
avatar: '' // 初始头像地址
}
}
}
</script>
注意一定要配置:output-type="'png'"