您好, 我的问题和您的一样, 在预览和模拟器中正常, 但是真机调试的时候无法绘制, 请问您的问题解决了吗?
canvas 2d 真机调试报错 ?[图片] <!--index.wxml--> <view class="splice-page"> <canvas id="tempCanvas" type="2d" style="position:absolute;left:-999999px"></canvas> <view class="saveButton"> <test class="icon-upload " bindtap="chooseImags">上传</test> <text class="icon-save" bindtap="saveImgToPhone"></text> </view> <view class="header"> <view class="upload_img photoframe" > <image class="frame" mode="widthFix" src="{{frameSrc}}"></image> <image class="photo" src="{{imgSrc}}" disableScroll="true" style="width:{{imgWidth}}px;height:{{imgHeight}}px"></image> </view> <image src="{{canvasImageSrc}}" style="z-index: 3;"/> </view> </view> // index.js // 获取应用实例 const app = getApp() Page({ ctx: null, canvasNode: null, dpr: 1, phoneInfo: null, data: { frameSrc: "https://scpic.chinaz.net/files/pic/pic9/201612/fpic9590.jpg", imgSrc: "", imgWidth: 0, imgHeight: 0, ImgObj:null, frameObj: null, canvasImageSrc: null }, // 事件处理函数 bindViewTap() { wx.navigateTo({ url: '../logs/logs' }) }, onReady() { this.phoneInfo = wx.getSystemInfoSync() const query = wx.createSelectorQuery().in(this); query .select("#tempCanvas") .fields({ node: true, size: true, }) .exec((res) => { this.canvasNode = res[0].node; this.ctx = this.canvasNode.getContext("2d"); this.dpr = this.phoneInfo.pixelRatio; this.canvasNode.width = 230 * this.dpr; this.canvasNode.height = 280 * this.dpr; this.ctx.scale(this.dpr, this.dpr); }); }, onLoad() { }, async chooseImags() { const data = await wx.chooseImage({ count: 1, sizeType: ["original", "compressed"], sourceType: ["album", "camera"], }) console.log(data); const ImgObj = await wx.getImageInfo({ src: data.tempFilePaths[0], }) this.setData({ imgSrc: ImgObj.path, imgWidth: ImgObj.width, imgHeight: ImgObj.height }) console.log(ImgObj); console.log(this.data.frameSrc); const frameObj = await wx.getImageInfo({ src: this.data.frameSrc }) console.log(frameObj); this.setData({ ImgObj, frameObj }) }, saveImgToPhone() { const t = this; const i = this.ctx; const c = this.canvasNode; wx.showLoading({ title: "生成中", }); let {ImgObj, frameObj} = this.data let _offsetX = Math.abs((frameObj.width - ImgObj.width) / 2); let _offsetY = Math.abs((frameObj.height - ImgObj.height) / 2); let _width = Math.max(ImgObj.width, frameObj.width); let _height = Math.max(ImgObj.height, frameObj.height); let framImgEl = c.createImage(); console.log("framImgEl start", framImgEl); framImgEl.onload = () => { i.drawImage( framImgEl, 0, 0, 230, 280, ); }; framImgEl.onerror = (e) => { console.log("framImgEl err", framImgEl, e); } framImgEl.src = frameObj.path; let imgEl = c.createImage(); console.log("imgEl start", imgEl); imgEl.onerror = (e) => { console.log("imgEl err", imgEl, e); } console.log("imgEl create", imgEl); imgEl.onload = () => { console.log("imgEl", imgEl); i.drawImage( imgEl, 20, 20, 230 - 40, 280 - 40 ); }; imgEl.src = ImgObj.path; setTimeout(() => { t.getTemFile({ width: _width, height: _height }) }, 800) }, getTemFile(options) { console.log("getTemFile 触发", options); let t = this; let c = this.canvasNode; wx.canvasToTempFilePath({ canvas: t.canvasNode, }) .then((res) => { console.log("getTemFile success", res); t.setData({ canvasImageSrc: res.tempFilePath, }) wx.saveImageToPhotosAlbum({ filePath: res.tempFilePath, }) .then((_res) => { wx.hideLoading() console.log(" _res", _res); }) .catch((err) => { console.log("err", err); }) }) .catch((err) => { console.log("getTemFile err", err); }); }, }) /**index.wxss**/ /* pages/slicePhoto/slicePhoto.wxss */ .splice-page { height: 100%; overflow: hidden; background-color: #f1f1f1; padding-top: 100rpx; } .saveButton { position: absolute; top: 30rpx; right: 40rpx; padding: 10rpx; font-size: 0; opacity: 0.7; z-index: 5; display: flex; align-items: center; } .icon-upload { font-size: 34rpx; display: inline-block; margin-right: 20rpx; } /* 保存图片按钮 */ .icon-save { background-image: url("data:image/svg+xml,%3Csvg version='1.1' xmlns='http://www.w3.org/2000/svg' width='24' height='24' viewBox='0 0 24 24'%3E %3Ctitle%3Esave%3C/title%3E %3Cpath d='M21.7 7.3l-5-5c-0.2-0.2-0.4-0.3-0.7-0.3h-11c-1.7 0-3 1.3-3 3v14c0 1.7 1.3 3 3 3h14c1.7 0 3-1.3 3-3v-11c0-0.3-0.1-0.5-0.3-0.7zM16 20h-8v-6h8v6zM20 19c0 0.6-0.4 1-1 1h-1v-7c0-0.6-0.4-1-1-1h-10c-0.6 0-1 0.4-1 1v7h-1c-0.6 0-1-0.4-1-1v-14c0-0.6 0.4-1 1-1h1v4c0 0.6 0.4 1 1 1h8c0.6 0 1-0.4 1-1s-0.4-1-1-1h-7v-3h7.6l4.4 4.4v10.6z'%3E%3C/path%3E %3C/svg%3E"); background-size: cover; display: inline-block; width: 60rpx; height: 60rpx; } .saveButton:active .icon-save:active { background-image: url("data:image/svg+xml,%3Csvg version='1.1' xmlns='http://www.w3.org/2000/svg' width='24' height='24' viewBox='0 0 24 24'%3E %3Ctitle%3Esave%3C/title%3E %3Cpath d='M21.7 7.3l-5-5c-0.2-0.2-0.4-0.3-0.7-0.3h-11c-1.7 0-3 1.3-3 3v14c0 1.7 1.3 3 3 3h14c1.7 0 3-1.3 3-3v-11c0-0.3-0.1-0.5-0.3-0.7zM16 20h-8v-6h8v6zM20 19c0 0.6-0.4 1-1 1h-1v-7c0-0.6-0.4-1-1-1h-10c-0.6 0-1 0.4-1 1v7h-1c-0.6 0-1-0.4-1-1v-14c0-0.6 0.4-1 1-1h1v4c0 0.6 0.4 1 1 1h8c0.6 0 1-0.4 1-1s-0.4-1-1-1h-7v-3h7.6l4.4 4.4v10.6z' fill='%23d6204b'%3E%3C/path%3E %3C/svg%3E"); } .saveButton:active .icon-upload { color: blueviolet; } /* 相框区域 */ .header { margin-top: 40rpx; height: 100%; display: flex; justify-content: center; } .header .upload_img { width:100%; min-height: 300px; display: flex; border-radius: 10rpx; align-items: center; background-color: #ffffff; justify-content: center; } .photoframe { position: absolute; width: 100%; overflow: hidden; z-index: 2; } .photoframe .photo { position: absolute; z-index: 2; height: 100%; width: 100%; } .photoframe .frame { position: absolute; z-index: 2; width: 100%; margin: 0; } @-webkit-keyframes animation { 0% { bottom: -900rpx; } 100% { bottom: 0; } } @keyframes animation { 0% { bottom: -900rpx; } 100% { bottom: 0; } } .swiper-content { position: fixed; bottom: 20rpx; margin-top: 20rpx; width: 100%; height: 200rpx; overflow: hidden; white-space: nowrap; background-color: #ffffff; padding: 20rpx 0; } .frameBox { width: 200rpx; height: 180rpx; display: inline-block; margin-right: 20rpx; } .frameBox .frameBox-image { width: 100%; height: 100%; }
2022-05-02