微信小程序canvas商品分享海报

先上效果图
在这里插入图片描述
1、wxml

 <button class="footer-item" bindtap="creatShareImageTap">分享</button>
 <view class='share-mask' hidden="{{shareMask == false}}" catchtouchmove='true'></view>
 <view class='canvas-box'>
   <canvas canvas-id="goods-share" style='width:750rpx;height:1206rpx;position:fixed;left:9999px'></canvas>
 </view>

2、wxss

 .share-mask{
  width: 100%;
  height: 100%;
  position: fixed;
  z-index: 998;
  left: 0;
  top: 0;
  background: #000;
  opacity: 0.5;
 }
 .imagePathBox{
  position: fixed;
  top: 0;
  right: 0;
  bottom: 0;
  z-index: 999;
  width: 100%;
  height: 100%;
  /* width: 264px;
  height: 376px; */
  left:0;
  /* margin-left:-132px; */
}
.shengcheng{
  width: 70.4%;
  height: 62.3%;
  position: fixed;
  top: 164rpx;
  left: 50%;
  margin-left: -35.2%;
  z-index: 10;
}
.imagePathBox .share-btns{
  display: flex;
  justify-content: space-between;
  position: fixed;
  bottom:150rpx;
  width: 72.4%;
  left:13.8%;
  z-index: 9999;
}
.imagePathBox .share-btn{
  font-size: 32rpx;
  background-color: #FABE00;
  color: #333;
  border-radius: 40rpx;
  width: 43%;
  height: 80rpx;
  bottom:30rpx;
  padding:0;
  margin: 0;
}
.imagePathBox .share-btn::after{
  border:none;
}
.close-btn{
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  z-index: 999;
  position: fixed;
  height: 20px;
}
.closeBtn{
  width: 44rpx;
  height: 44rpx;
  text-align: center;
  vertical-align: middle;
  position: fixed;
  top:84rpx;
  right:84rpx;
}
.previewimg image{ 
  width:100%; 
  height:100%; 
 }

3、js

creatShareImageTap(){
  var rpx=this.data.rpx;//适配比例
  this.setData({
    shareMask:false
  })
  const url=this.data.myUrl
  //const url='https://ylhdev.oss-cn-beijing.aliyuncs.com/20200426171219.png'
  //开始制作
  this.drawCanvas(this.data.details,url,rpx)
},
drawCanvas: function (sourceData,url,rpx){
  wx.showLoading({
    title: '分享图生成中...'
  })
  var that=this;
  let promise1 = new Promise(function (resolve, reject) {
    wx.getImageInfo({
      src: url,
      success: function (res) {
        resolve(res);
      }
    })
  });
  let promise2 = new Promise(function (resolve, reject) {
    wx.getImageInfo({
      src: sourceData.goodsPicList[0].goodsPicUrl,
      success: function (res) {
        resolve(res);
      }
    })
  });
  let promise3 = new Promise(function (resolve, reject) {
    wx.getImageInfo({
      src: that.data.userInfo.avatarUrl,
      success: function (res) {
        resolve(res);
      }
    })
  });
  Promise.all([
    promise1, promise2,promise3
  ]).then(res=>{
    const ctx = wx.createCanvasContext('goods-share');
    ctx.setFillStyle("#fff")
    ctx.fillRect(0, 0, 375*rpx, 583*rpx)
    // ctx.strokeStyle = "white";
    // ctx.strokeRect(0,0,375*rpx, 583*rpx);
    ctx.setFillStyle('#fff');
    ctx.fillRect(0, 375*rpx, 425*rpx, 255*rpx);
    ctx.drawImage(res[0].path, 272*rpx, 485*rpx, 82*rpx, 82*rpx)
    ctx.drawImage(res[1].path, 0, 0, 375*rpx, 425*rpx)
ctx.save() // 对当前区域保存
ctx.beginPath() // 开始新的区域
ctx.arc(28.5*rpx, 560*rpx, 18*rpx, 0, 2 * Math.PI);
ctx.clip();  // 从画布上裁剪出这个圆形
ctx.drawImage(res[2].path,11.5*rpx, 542*rpx, 35*rpx, 35*rpx)// 把图片填充进裁剪的圆形
ctx.restore() // 恢复
    //绘制说明
    ctx.setTextAlign('left')
    ctx.setFillStyle('#333')
    ctx.font='normal bold 16px sans-serif'
    // ctx.setFontSize(16)
    that.dealWords({
      ctx: ctx,//画布上下文
      fontSize: 16,//字体大小
      word: '         '+sourceData.goodsName,//需要处理的文字
      maxWidth: 335*rpx,//一行文字最大宽度
      x: 13*rpx,//文字在x轴要显示的位置
      y: 425*rpx,//文字在y轴要显示的位置
      maxLine: 2//文字最多显示的行数
    })
    if(sourceData.goodsType==2){
      ctx.setFillStyle('#FF5850')
      ctx.fillRect(11*rpx, 434*rpx, 33*rpx, 18*rpx)
      ctx.setTextAlign('left')
      ctx.setFillStyle('#fff')
      // ctx.setFontSize(14)
      ctx.font='normal normal 14px sans-serif'
      ctx.fillText('严选', 13*rpx, 447*rpx)
    }
    ctx.setTextAlign('left')
    ctx.setFillStyle('#F52340')
    // ctx.setFontSize(14)
    ctx.font='normal normal 14px sans-serif'
    ctx.fillText('特权价¥', 11*rpx, 501*rpx)
    ctx.setTextAlign('left')
    ctx.setFillStyle('#F52340')
    ctx.setFontSize(22)
    ctx.fillText(sourceData.specialPrice||'0.00',70*rpx, 503*rpx)
    ctx.setLineWidth(1);
    ctx.setStrokeStyle('#999')
    if(JSON.stringify(sourceData.selectPrice).length>2&&sourceData.selectPrice>10){
      ctx.moveTo(58*rpx, 521*rpx);
      ctx.lineTo(86*rpx, 521*rpx);
    }else{
      ctx.moveTo(58*rpx, 521*rpx);
      ctx.lineTo(80*rpx, 521*rpx);
    }
    ctx.setTextAlign('left')
    ctx.setFillStyle('#999')
    // ctx.setFontSize(14)
    ctx.font='normal normal 14px sans-serif'
    ctx.fillText('售价¥  ' + sourceData.selectPrice,11*rpx,527*rpx)

    ctx.setTextAlign('left')
    ctx.setFillStyle('#666')
    // ctx.setFontSize(14)
    ctx.font='normal normal 14px sans-serif'
    ctx.fillText(that.data.userInfo.nickName, 51*rpx, 557*rpx)

    ctx.setTextAlign('left')
    ctx.setFillStyle('#999')
    // ctx.setFontSize(10)
    ctx.font='normal normal 10px sans-serif'
    ctx.fillText('邀请好友享受内部优惠价', 51*rpx, 573*rpx)
    
    ctx.setTextAlign('left')
    ctx.setFillStyle('#999')
    ctx.setFontSize(10)
    ctx.fillText('长按识别', 290*rpx, 584*rpx)
    ctx.stroke()
    ctx.draw(false,function(){
      that.share2();
    })
  })
},
//文字处理
dealWords: function (options) {
  options.ctx.setFontSize(options.fontSize);//设置字体大小
  var allRow = Math.ceil(options.ctx.measureText(options.word).width / options.maxWidth);//实际总共能分多少行
  var count = allRow >= options.maxLine ? options.maxLine : allRow;//实际能分多少行与设置的最大显示行数比,谁小就用谁做循环次数
  var endPos = 0;//当前字符串的截断点
  for (var j = 0; j < count; j++) {
    var nowStr = options.word.slice(endPos);//当前剩余的字符串
    var rowWid = 0;//每一行当前宽度  
    if (options.ctx.measureText(nowStr).width > options.maxWidth) {//如果当前的字符串宽度大于最大宽度,然后开始截取
      for (var m = 0; m < nowStr.length; m++) {
        rowWid += options.ctx.measureText(nowStr[m]).width;//当前字符串总宽度
        if (rowWid > options.maxWidth) {
          if (j === options.maxLine - 1) { //如果是最后一行
            options.ctx.fillText(nowStr.slice(0, m - 1) + '...', options.x, options.y + (j + 1) * 24);  //(j+1)*18这是每一行的高度    
          } else {
            options.ctx.fillText(nowStr.slice(0, m), options.x, options.y + (j + 1) * 24);
          }
          endPos += m;//下次截断点
          break;
        }
      }
    } else {//如果当前的字符串宽度小于最大宽度就直接输出
      options.ctx.fillText(nowStr.slice(0), options.x, options.y + (j + 1) * 24);
    }
  }
},
//输出图像到canvas容器
share2: function () {
  var that = this
  wx.canvasToTempFilePath({
    canvasId: 'goods-share',
    success: function (res) {
      console.log('share分享图--------',res)
          that.setData({
            imagePath: res.tempFilePath,
            shareMask:true
          })
      wx.hideLoading();
    },
    fail: function (res) {
      console.log(res)
    }
  })
},

//预览

previewImage1: function () {
  var that = this
  var wximg = that.data.imagePath;
  wx.previewImage({
    urls: Array(wximg)
  })
},

体验线上效果,关注下面云乐汇好物小程序,爆款京东商品,自购省分享赚
在这里插入图片描述

关注我个人微信公众号获取更多前端资讯
在这里插入图片描述

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
微信小程序通过 Canvas 2D 绘制海报可以用于商品展示、广告宣传等场景。下面介绍一下实现流程: 1. 页面结构 在页面中添加一个 Canvas 标签,设置 id 和宽高: ```html <canvas id="poster" style="width: 750rpx; height: 1334rpx;"></canvas> ``` 2. 获取 Canvas 上下文 在页面的 onLoad 函数中获取 Canvas 上下文: ```javascript let ctx = wx.createCanvasContext('poster'); ``` 3. 绘制背景 使用 Canvas 2D 绘制背景,可以使用 fillRect 方法绘制一个填充矩形: ```javascript ctx.setFillStyle('#ffffff'); ctx.fillRect(0, 0, 750, 1334); ``` 4. 绘制图片 使用 drawImage 方法绘制图片,需要先将图片下载到本地: ```javascript wx.getImageInfo({ src: 'https://example.com/image.png', success: function(res) { ctx.drawImage(res.path, 0, 0, 750, 500); } }); ``` 5. 绘制文本 使用 fillText 或者 strokeText 方法绘制文本,需要设置字体样式和对齐方式: ```javascript ctx.setFontSize(32); ctx.setTextAlign('center'); ctx.fillText('这是一段文本', 375, 600); ``` 6. 保存海报 使用 Canvas 2D 的 toTempFilePath 方法将绘制的海报保存到本地: ```javascript ctx.draw(false, function() { wx.canvasToTempFilePath({ x: 0, y: 0, width: 750, height: 1334, canvasId: 'poster', success: function(res) { console.log(res.tempFilePath); } }); }); ``` 完整代码: ```javascript Page({ onLoad: function() { let ctx = wx.createCanvasContext('poster'); ctx.setFillStyle('#ffffff'); ctx.fillRect(0, 0, 750, 1334); wx.getImageInfo({ src: 'https://example.com/image.png', success: function(res) { ctx.drawImage(res.path, 0, 0, 750, 500); } }); ctx.setFontSize(32); ctx.setTextAlign('center'); ctx.fillText('这是一段文本', 375, 600); ctx.draw(false, function() { wx.canvasToTempFilePath({ x: 0, y: 0, width: 750, height: 1334, canvasId: 'poster', success: function(res) { console.log(res.tempFilePath); } }); }); } }); ```

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值