头像裁剪和上传

<template>
    <!-- 头像、用户名、性别编辑页面 -->
    <el-dialog
        v-dialogDrag
        title="修改个人信息"
        width="640px"
        :visible.sync="visible"
        :append-to-body="true"
        :close-on-click-modal="false"
    >
        <div class="imgBox">
            <div class="left">
                <div class="text" v-show="!flag">
                    <label class="el-button long-button el-button--primary" for="uploads">
                        {{
                        $t('user.selectImg')
                        }}
                    </label>
                    <input
                        ref="imgInput"
                        type="file"
                        id="uploads"
                        :value="imgFile"
                        style="position: absolute; clip: rect(0 0 0 0)"
                        accept="image/png, image/jpeg, image/gif, image/jpg"
                        @change="uploadImg($event, 1)"
                    />
                    <p>{{ $t('user.imgHint') }}</p>
                </div>
                <div v-show="flag">
                    <vueCropper
                        style="width: 400px; height: 400px"
                        ref="cropper"
                        :img="option.img"
                        :autoCrop="option.autoCrop"
                        :centerBox="option.centerBox"
                        :fixedNumber="option.fixedNumber"
                        :infoTrue="option.infoTrue"
                        :fixed="option.fixed"
                        @realTime="preview"
                    ></vueCropper>
                </div>
            </div>
            <div class="right">
                <div>
                    <img v-show="imgUrl" :src="imgUrl" id="newPic1" />
                </div>
                <div>
                    <img v-show="imgUrl" :src="imgUrl" id="newPic2" />
                </div>
                <p v-show="!flag" style="color: #969696; margin-top: 127px">{{ $t('user.preview') }}</p>
                <el-button
                    v-show="flag"
                    style="margin-top: 127px"
                    type="primary"
                    @click="reuploadImg"
                >重新上传</el-button>
            </div>
        </div>
        <div slot="footer" class="dialog-footer">
            <div>
                <span>{{ $t('global.userName') }}:</span>
                <el-input
                    class="wd200"
                    maxlength="20"
                    show-word-limit
                    v-model="listParams.nickName"
                    autocomplete="off"
                ></el-input>
            </div>
            <div>
                <el-button class="long-button" @click="visible = false">取消</el-button>
                <el-button class="long-button" type="primary" :loading="btnLoading" @click="submit">
                    {{
                    $t('global.confirmBtn')
                    }}
                </el-button>
            </div>
        </div>
    </el-dialog>
</template>
<script>
import { updateUserInfo, upload } from '@/api/userCenter/personalCenter'
export default {
    name: 'info-edit',
    props: {},
    components: {},
    data() {
        return {
            visible: false,
            fileList: [],
            // 是否选了图片,true:显示‘重新上传’,false:显示‘预览’
            flag: false,
            btnLoading: false,
            // 选择图片
            text: this.$t('user.u6'),
            // 预览图片地址
            imgUrl: '',
            listParams: {
                type: 2,
                nickName: '', // 用户名
                avatar: null // 头像url
            },
            option: {
                img: '', //图片地址
                fixed: true, //开启截图框宽高固定比例
                fixedNumber: [1, 1], //截图框的宽高比例
                autoCrop: true, //默认生成截图框
                centerBox: true //截图框是否被限制在图片里面
            },
            fileName: '', //本机文件地址
            imgFile: ''
        }
    },
    mounted() {},
    methods: {
        // 重新选择头像图片
        reuploadImg() {
            this.$refs.imgInput.click()
        },
        // 预览
        preview() {
            // 获取Blob类型的图片数据
            this.$refs.cropper.getCropBlob((data) => {
                let img = window.URL.createObjectURL(data)
                this.imgUrl = img
            })
        },
        //选择本地图片
        uploadImg(e, num) {
            this.flag = true
            //上传图片
            let file = e.target.files[0]
            this.fileName = file.name
            if (!/\.(jpg|jpeg|png|JPG|PNG)$/.test(e.target.value)) {
                alert(this.$t('user.imgHint2'))
                return false
            }
            let reader = new FileReader()
            reader.onload = (e) => {
                let data = null
                if (typeof e.target.result === 'object') {
                    // 把Array Buffer转化为blob 如果是base64不需要
                    data = window.URL.createObjectURL(new Blob([e.target.result]))
                } else {
                    data = e.target.result
                }
                if (num === 1) {
                    this.option.img = data
                } else if (num === 2) {
                    this.example2.img = data
                }
            }
            // 转化为base64
            // reader.readAsDataURL(file)
            // 转化为blob
            reader.readAsArrayBuffer(file)
        },
        //  --------------------------------

        init(name, avatar) {
            this.visible = true
            this.listParams.nickName = name
            this.option.img = ''
            this.imgUrl = avatar
            this.listParams.avatar = avatar
            this.flag = false
            this.btnLoading = false
        },
        submit() {
            if (!/^[0-9a-zA-Z\u4e00-\u9fa5]{2,20}$/.test(this.listParams.nickName)) {
                this.$message.error(this.$t('global.nameHint'))
                return false
            } else {
                if (this.flag) {
                    this.getImgUrl()
                    return false
                }
                this.btnLoading = true
                this.updateUserInfo()
            }
        },
        updateUserInfo() {
            updateUserInfo(this.listParams).then((res) => {
                this.btnLoading = false
                if (res) {
                    this.$message.success('修改成功')
                    // 更新用户名和头像
                    this.$store.dispatch('user/getInfo')
                    this.visible = false
                    this.$emit('refresh')
                }
            })
        },
        // 获取图片地址
        getImgUrl() {
            let formData = new FormData()
            formData.append('category', 1)
            // 获取Blob数据
            this.$refs.cropper.getCropBlob((data) => {
                formData.append('file', data, this.fileName)
                upload(formData).then((res) => {
                    if (JSON.stringify(res) !== '{}') {
                        this.listParams.avatar = res
                        this.updateUserInfo()
                    }
                })
            })
        }
    }
}
</script>
<style lang="scss" scoped>
.imgBox {
    width: 600px;
    height: 400px;
    display: flex;
    background-color: #f6f9fe;

    .left {
        flex: 2;

        > div {
            width: 100%;
            height: 100%;
        }

        .text {
            display: flex;
            flex-direction: column;
            justify-content: center;
            align-items: center;
            font-size: 12px;
            color: #969696;
        }
    }

    .right {
        flex: 1;
        display: flex;
        flex-direction: column;
        align-items: center;
        border-left: 1px solid #ffffff;

        > div {
            border-radius: 50%;
            overflow: hidden;
            border: 1px solid #ffffff;
            background-color: #f0f0f0;

            img {
                width: 100%;
                height: 100%;
            }
        }

        > div:nth-child(1) {
            width: 80px;
            height: 80px;

            margin-top: 60px;
        }

        > div:nth-child(2) {
            width: 40px;
            height: 40px;
            margin-top: 40px;
        }
    }
}

.dialog-footer {
    display: flex;
    justify-content: space-between;
}
</style>

在这里插入图片描述
在这里插入图片描述
可以调整图片位置和大小裁剪自己想要的图片区域
在这里插入图片描述

右边预览的图片就是选择的头像区域

注:$t('’) 是使用了vue-i18n做了中英文翻译,所以不是直接写的汉字

参考文档链接:

1、Vue项目图片剪切上传—vue-cropper的使用

图片剪切上传参考文档链接

npm install vue-cropper --save-dev

npm – cropper图片裁剪插件地址

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值