微信小程序上传图片裁剪
上传图片裁剪
一、we-cropper 一款灵活小巧的canvas图片裁剪器
克隆至本地处理
git clone https://github.com/we-plugin/we-cropper.git
npm方式引入
npm install we-cropper --save
图片裁剪常用于头像选择和图片合成等。
插件下载:GitHub - we-plugin/we-cropper: 微信小程序图片裁剪工具
参考教程:we-cropper - 小程序图片裁剪工具
文档:https://we-plugin.github.io/we-cropper/#/
图片裁剪解决方案:
目前网络上知名的微信小程序图片裁剪插件是we-cropper
操作步骤:下载好we-cropper文件夹,拷贝到小程序目录,可以放在pages列表中。
参考例子:example文件夹下面直接引入参考
二、自定义实例
1.在pages中创建imgcorp.wxml文件,将下载的we-cropper文件拷贝到pages中
imgcorp.wxml
<import src="/pages/we-cropper/index.wxml" /> <!-- 上传图片未裁剪时 --> <block wx:if="{{!cropImgInfo.imgUrl}}"> <view class="cropper-wrapper"> <view class="wecropper"> <template is="we-cropper" data="{{...cropperOpt}}" /> </view> <view class="cropper-buttons"> <view class="upload btn" catchtap="uploadTap">上传图片</view> <view class="getCropperImage btn" catchtap="getCropperImage">生成图片</view> </view> </view> </block> <!-- 已裁剪图片 --> <block wx:if="{{cropImgInfo.imgUrl}}"> <view class="cropper-wrapper" style="background: #202020;"> <image src="{{cropImgInfo.imgUrl}}" class="cropper-img" mode="widthFix"></image> <view class="cropper-buttons"> <view class="upload btn" catchtap="onCancelImg">取消</view> <view class="getCropperImage btn" catchtap="onConfirmImg">确定</view> </view> </view> </block>
imgcorp.wxss
.cropper-wrapper { position: relative; display: flex; flex-direction: row; justify-content: space-between; align-items: center; justify-content: center; height: 100vh; background-color: #e5e5e5; } .cropper { width: 100%; overflow: hidden; position: absolute; top: 0; left: 0; z-index: 10; } .cropper-img { display: block; width: 100%; } .cropper-buttons { display: flex; flex-direction: row; justify-content: space-between; align-items: center; position: fixed; bottom: 0; left: 0; z-index: 999999999; width: 100%; height: 55px; padding: 0 40rpx; box-sizing: border-box; line-height: 55px; background-color: rgba(0, 0, 0, 0.9); } .btn { height: 60rpx; line-height: 60rpx; padding: 0 24rpx; border-radius: 4rpx; color: #ffffff; } .upload, .getCropperImage { text-align: center; }
imgcorp.js
// pages/we-cropper/imgcorp.js const dataMainModule = require('../../utils/main.js'); const common = require('../../utils/common.js'); const WeCropper = require('./index.js'); const device = wx.getSystemInfoSync(); // 获取设备信息 const width = device.windowWidth // 示例为一个与屏幕等宽的正方形裁剪框 const height = device.windowHeight - 55; const croWidth = width * 0.8; Page({ data: { isfrom: null, //页面来源 isfiles: null, //是否是其他页面上传图片过来 tempFiles: null, //其他页面上传图片信息 fileSize: 10, //上传图片文件大小 cropperOpt: { id: 'cropper', // 用于手势操作的canvas组件标识符 targetId: 'targetCropper', // 用于用于生成截图的canvas组件标识符 pixelRatio: device.pixelRatio, // 传入设备像素比 width, // 画布宽度 height, // 画布高度 scale: 2.5, // 最大缩放倍数 zoom: 8, // 缩放系数 cut: { x: (width - croWidth) / 2, // 裁剪框x轴起点 y: (height - croWidth) / 2, // 裁剪框y轴期起点 width: croWidth, // 裁剪框宽度 height: croWidth // 裁剪框高度 } }, imgUrl: null, //是否有上传图片 cropImgInfo: { url: null, //裁剪过的图片 imgUrl: null, //裁剪过的图片全地址 fileType: null, //图片类型 }, }, cropper: null, onLoad: function (options) { wx.removeStorageSync('cropImgInfo'); if (options) { if (options.isfrom) { this.setData({ isfrom: options.isfrom }) } if (options.fileSize) { this.setData({ fileSize: options.fileSize }) } if (options.fileType) { this.setData({ ['cropImgInfo.fileType']: options.fileType }) } if (options.isfiles) { var tempFiles = common.copyVueData(JSON.parse(wx.getStorageSync('tempFiles'))); this.setData({ isfiles: options.isfiles, tempFiles: tempFiles, imgUrl: tempFiles.path }) wx.removeStorageSync('tempFiles'); } } if (this.data.isfiles) { this.init(this.data.tempFiles); } else { this.init(); } }, init(tempFiles) { //实例化裁剪图片 const { cropperOpt } = this.data this.cropper = new WeCropper(cropperOpt) .on('ready', (ctx) => { console.log(`wecropper is ready for work!`) }) .on('beforeImageLoad', (ctx) => { common.loading(true, '上传中'); }) .on('imageLoad', (ctx) => { common.loading(false); }) this.cropper.updateCanvas(); if (!common.isEmpty(tempFiles)) { this.initWeCropper(tempFiles); } }, initWeCropper(tempFiles) { //显示图片 if (tempFiles) { this.cropper.pushOrign(tempFiles.path); } }, touchStart(e) { this.cropper.touchStart(e); }, touchMove(e) { this.cropper.touchMove(e); }, touchEnd(e) { this.cropper.touchEnd(e); }, uploadTap() { // 上传图片 let that = this; wx.chooseImage({ count: 1, // 默认9 sizeType: ['original', 'compressed'], // 可以指定是原图还是压缩图,默认二者都有 sourceType: ['album', 'camera'], // 可以指定来源是相册还是相机,默认二者都有 success: res => { let tempFiles = res.tempFiles[0]; if (common.getIsfileSize(tempFiles.size, that.data.fileSize)) { return; } that.setData({ imgUrl: tempFiles.path }) that.initWeCropper(tempFiles); } }) }, getCropperImage() { //生成图片 let that = this; if (common.isEmpty(this.data.imgUrl)) { common.getToast('请先上传图片'); return; } common.loading(true, '正在生成图片'); this.cropper.getCropperImage() //裁剪临时图片文件 // this.cropper.getCropperBase64() //裁剪base64图片文件 .then((res) => { if (res) { that.getUploadFile(res); //上传临时图片 // that.uploadHsFile(res); //上传base64图片 } else { common.getToast('生成图片失败,请稍后重试') } }).catch((err) => { wx.showModal({ title: '温馨提示', content: err.message }) }) }, getUploadFile(imgUrl) { //上传服务器图片-临时文件 let that = this; var temp = { url: imgUrl } common.loading(true, '正在生成图片'); dataMainModule.getUploadFile(temp, (res) => { common.loading(false); if (res.retCode == 200) { if (res.retData) { var retItem = res.retData[0]; that.setData({ ['cropImgInfo.url']: retItem.fileReturnId, ['cropImgInfo.imgUrl']: common.getViewImageUrl(retItem.fileReturnId) }) } } }, (res) => { common.loading(false); common.getToast(res); }) }, uploadHsFile(imageData) { //上传服务器图片-base64 let that = this; let temp = { imageData: imageData } common.loading(true, '正在生成图片'); dataMainModule.uploadHsFile(temp, (res) => { common.loading(false); if (res.retCode == 200) { if (res.data) { that.setData({ ['cropImgInfo.url']: res.data, ['cropImgInfo.imgUrl']: common.getViewImageUrl(res.data) }) } } }, (res) => { common.loading(false); common.getToast(res); }) }, onConfirmImg() { //确定 if (this.data.cropImgInfo.imgUrl) { wx.setStorageSync('cropImgInfo', JSON.stringify(this.data.cropImgInfo)); this.getBack(); } else { common.getToast('请先生成图片'); } }, onCancelImg() { //取消裁剪图片 this.setData({ cropImgInfo: { url: null, imgUrl: null, }, imgUrl: null, }) setTimeout(() => { this.init(); }, 300); }, getBack() { //返回 common.getWxBack(); }, })