vue2+element ui 项目使用Upload 上传组件,实现图片压缩

使用element ui的Upload 上传组件,实现图片压缩

在template中代码

					<el-form-item 
                            label="图片"
                            :label-width="'120px'"
                            prop="menuName"
                  >
					<el-upload
                                action="#"
                                class="avatar-uploader"
                                :auto-upload="false"
                                :show-file-list="false"
                                :on-success="handleAvatarSuccess"
                                :before-upload="beforeAvatarUpload"
                                :on-change="onChange"
                            >
                                <img v-if="imageUrl" :src="imageUrl" class="avatar">
                                <i v-else class="el-icon-plus avatar-uploader-icon"></i>
                            </el-upload>
                        </el-form-item>

script中代码

<script>
// 引入做压缩处理的函数
import { 
    transitionBase64,
    compressImg,
    dataURItoBlob,
    base64ToFile
 } from '@/utils/compressTransitionImg.js'
export default {
    data() {
        return {
            imageUrl: '',
        }
    },
    methods: {
        // 图片改变
        async onChange(file, fileList) {
            console.log('file, fileList', file, fileList)
            console.log('上传的文件file', file)
            const isJPG = file.type === 'image/jpeg';
            const isLt2M = file.size / 1024 / 1024 < 2;

            /* if (!isJPG) {
                this.$message.error('上传头像图片只能是 JPG 格式!');
            }
            if (!isLt2M) {
                this.$message.error('上传头像图片大小不能超过 2MB!');
            } */

            // 定义需要上传的文件
            let formData = new FormData()
            formData.append('file', file.raw)
            console.log('formData', formData)
            console.log('formData.getAll()', formData.getAll(['file']))
            
            // this.imageUrl = URL.createObjectURL(file.raw)

            let result = await transitionBase64(file.raw)
            let compressImgResult = await compressImg(result, 50 * 1024)
            // console.log(111, result)
            console.log('压缩后的文件', compressImgResult)
            console.log('压缩后的文件转blob', dataURItoBlob(compressImgResult))
            console.log('压缩后的文件转file对象', base64ToFile(compressImgResult, file.name.split('.')[0]))

            // this.imageUrl = URL.createObjectURL(dataURItoBlob(compressImgResult))
            // 显示压缩后的图片
            this.imageUrl = URL.createObjectURL(base64ToFile(compressImgResult, file.name))

        },
        


        // 以下方法无用
        handleAvatarSuccess(res, file) {
            this.imageUrl = URL.createObjectURL(file.raw);
        },
        beforeAvatarUpload(file) {
            console.log('上传的文件file', file)
            const isJPG = file.type === 'image/jpeg';
            const isLt2M = file.size / 1024 / 1024 < 2;

            if (!isJPG) {
                this.$message.error('上传头像图片只能是 JPG 格式!');
            }
            if (!isLt2M) {
                this.$message.error('上传头像图片大小不能超过 2MB!');
            }
            return true;
            return isJPG && isLt2M;
        },
        handleRemove(file) {
            console.log(file);
        },
        handlePictureCardPreview(file) {
            this.dialogImageUrl = file.url;
            this.dialogVisible = true;
        },
        handleDownload(file) {
            console.log(file);
        }
    }
}
</script>

新建compressTransitionImg.js封装压缩图片函数

// 
// 封装上传图片时的压缩方法及其base64转bolb
// 将bolb转换成base64
export function transitionBase64(blob) {
    return new Promise((resolve, reject) => {
        // 创建一个FileReader实例
        const reader = new FileReader();
        let base64String
        // 设置FileReader的onload事件处理程序,当转换完成时调用
        reader.onload = function(event) {
            // 事件的result属性包含了转换完成的数据
            base64String = event.target.result;
            // 输出Base64编码的字符串
            resolve(base64String)
        };
        // 使用readAsDataURL方法开始转换Blob为Base64
        reader.readAsDataURL(blob);
    })
}


/**
* base64转图片File
* @param {String} base64 图片base64
* @param {String} fileName 图片名称| 默认 → imgName
* @returns File 返回转换后的file数据类型
*/
export function base64ToFile (base64, fileName = 'imgName') {
    // 将base64按照 , 进行分割 将前缀  与后续内容分隔开
    let data = base64.split(','),
        // 利用正则表达式 从前缀中获取图片的类型信息(image/png、image/jpeg、image/webp等)
        type = data[0].match(/:(.*?);/)[1],
        // 从图片的类型信息中 获取具体的文件格式后缀(png、jpeg、webp)
        suffix = type.split('/')[1],
        // 使用atob()对base64数据进行解码  结果是一个文件数据流 以字符串的格式输出
        bstr = window.atob(data[1]),
        // 获取解码结果字符串的长度
        n = bstr.length,
        // 根据解码结果字符串的长度创建一个等长的整形数字数组
        // 但在创建时 所有元素初始值都为 0
        u8arr = new Uint8Array(n)

    // 将整形数组的每个元素填充为解码结果字符串对应位置字符的UTF-16 编码单元
    while (n--) {
        // charCodeAt():获取给定索引处字符对应的 UTF-16 代码单元
        u8arr[n] = bstr.charCodeAt(n)
    }
    // 利用构造函数创建File文件对象
    // new File(bits, name, options)
    const file = new File([u8arr], `${fileName}.${suffix}`, {
        type: type
    })
    // 返回file
    return file
}

// base64 转 blob
export function dataURItoBlob(base64Data) {
    var byteString;

    if(base64Data.split(',')[0].indexOf('base64') >= 0)
        byteString = atob(base64Data.split(',')[1]);//base64 解码
    else{
        byteString = unescape(base64Data.split(',')[1]);
    }
    var mimeString = base64Data.split(',')[0].split(':')[1].split(';')[0];//mime类型

    // var arrayBuffer = new ArrayBuffer(byteString.length); //创建缓冲数组
    // var ia = new Uint8Array(arrayBuffer);//创建视图
    var ia = new Uint8Array(byteString.length);//创建视图
    for(var i = 0; i < byteString.length; i++) {
        ia[i] = byteString.charCodeAt(i);
    }
    var blob = new Blob([ia], {
        type: mimeString
    });
    return blob;
}
/**
* 压缩图片  返回base64
* @param {base64} imgFile 图片base64
* @param {Number} maxSize 上传压缩图片的大学| 默认 → 50 * 1024 kb
* @returns File 返回转换后的file数据类型
*/
export function compressImg(imgFile, maxSize = 50 * 1024) {
    return new Promise((resolve, reject) => {
        var img = new Image();
        img.src = imgFile
        console.log('imgFile', imgFile)
        
        img.onload = function () {
            var canvas = document.createElement('canvas');
            var ctx = canvas.getContext('2d');
            var width = img.width;
            var height = img.height;
            canvas.width = width;
            canvas.height = height;
            ctx.drawImage(img, 0, 0, width, height);
            var quality = 0.8;
            let newBase64Image = canvas.toDataURL('image/jpeg', quality);

            let fileSize = getBase64ImageSize(newBase64Image);
            if (fileSize > maxSize) {
                const qualityArr = [], step = 0.01;
                for (let i = step; i <= quality; i += step) {
                    // qualityArr.push(parseFloat(i.toFixed(2)));
                    qualityArr.push(parseFloat(i));
                }
                let left = 0,
                    right = qualityArr.length - 1;
                do {
                    console.log('循环次数fileSize', fileSize)
                    const mid = Math.floor((left + right) / 2);
                    newBase64Image = canvas.toDataURL('image/jpeg', qualityArr[mid]);
                    fileSize = getBase64ImageSize(newBase64Image);
                    if (fileSize > maxSize) {
                        right = mid - 1;
                    } else {
                        left = mid + 1;
                    }
                } while (left <= right);
            }
            // 对resultBlob做一些事情,比如从它创建一个新图像或保存它。
            console.log('压缩后的文件newBase64Image', newBase64Image)
            console.log('压缩后的文件fileSize', fileSize)
            resolve(newBase64Image)
        }
    })

}
// 计算base64编码图片大小
function getBase64ImageSize(base64) {
    const indexBase64 = base64.indexOf('base64,');
    if (indexBase64 < 0) return -1;
    const str = base64.substr(indexBase64 + 6);
    // 大小单位:字节
    return (str.length * 0.75).toFixed(2);
}

参考

  • 9
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
好的,下面是实现模糊搜索的步骤: 1. 安装Element UI组件库 在Vue项目使用Element UI组件库需要先安装它,可以使用npm或yarn命令进行安装。具体命令如下: 使用npm安装:`npm i element-ui -S` 使用yarn安装:`yarn add element-ui` 2. 引入Element UI组件Vue项目中需要使用Element UI组件,首先需要在main.js中引入Element UI组件。具体代码如下: ```javascript import Vue from 'vue' import ElementUI from 'element-ui' import 'element-ui/lib/theme-chalk/index.css' Vue.use(ElementUI) ``` 3. 实现模糊搜索功能 在Vue组件的template标签中添加一个el-input组件和el-table组件,其中el-input组件用于输入关键词进行搜索,el-table组件用于显示搜索结果。具体代码如下: ```html <template> <div> <!-- el-input组件 --> <el-input placeholder="请输入关键词" v-model="keyword" @input="handleSearch"></el-input> <!-- el-table组件 --> <el-table :data="tableData"> <el-table-column prop="name" label="姓名"></el-table-column> <el-table-column prop="age" label="年龄"></el-table-column> <el-table-column prop="gender" label="性别"></el-table-column> </el-table> </div> </template> ``` 在Vue组件的script标签中,定义data属性,其中包含tableData数组和keyword字符串。tableData数组用于存储搜索结果,keyword字符串用于存储搜索关键字。同时,在methods中定义handleSearch方法,该方法用于实现模糊搜索功能。具体代码如下: ```javascript <script> export default { data() { return { tableData: [ { name: '张三', age: 18, gender: '男' }, { name: '李四', age: 20, gender: '女' }, { name: '王五', age: 22, gender: '男' }, ], keyword: '' } }, methods: { handleSearch() { if (!this.keyword) { // 如果keyword为空,显示所有数据 this.tableData = [ { name: '张三', age: 18, gender: '男' }, { name: '李四', age: 20, gender: '女' }, { name: '王五', age: 22, gender: '男' }, ] } else { // 使用filter方法实现模糊搜索 this.tableData = this.tableData.filter(item => item.name.includes(this.keyword)) } } } } </script> ``` 以上代码实现了一个简单的模糊搜索功能,当在el-input组件中输入关键词时,el-table组件会根据关键词进行模糊搜索,并显示搜索结果。如果关键词为空,el-table组件会显示所有数据。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值