在微信小程序中保存网络图片


Posted in Javascript onFebruary 12, 2019

微信代码片段点这里, 该功能需要添加appid才能进行正常的测试。

在小程序的文档中我们得知,wx.saveImageToPhotosAlbum 是用来保存图片到相册的。

但是仔细一看会发现这个接口的filePath参数只接受临时文件路径或永久文件路径,不支持网络图片路径,意味着我们不能直接调用这个接口。。

因此先需要把该文件下载至本地,使用 wx.downloadFile 。

但值得注意的是小程序只可以跟指定的域名与进行网络通信,也就是说下载图片之前,我们需要先去微信公众者平台的开发设置里设置uploadFile合法域名。

示例代码如下:

<!-- index.wxml -->
<image class="qr-code" src="{{url}}" mode="aspectFill" />
<button class="text" bindtap="saveImage">保存图片</button>
// index.js
const app = getApp()

Page({
 data: {
  url: 'https://avatars3.githubusercontent.com/u/23024075?s=460&v=4'
 },

 // 保存图片
 saveImage() {
  this.wxToPromise('downloadFile', {
    url: this.data.url
   })
   .then(res => this.wxToPromise('saveImageToPhotosAlbum', {
    filePath: res.tempFilePath
   }))
   .then(res => {
    // do something
    wx.showToast({ title: '保存成功~',icon: 'none' });
   })
   .catch(err) => {
    console.log(err);

    // 如果是用户自己取消的话保存图片的话
    // if (~err.errMsg.indexOf('cancel')) return;
   })
 },

 /**
  * 将 callback 转为易读的 promise
  * @returns [promise]
  */
 wxToPromise(method, opt) {
  return new Promise((resolve, reject) => {
   wx[method]({
    ...opt,
    success(res) {
     opt.success && opt.success();
     resolve(res)
    },
    fail(err) {
     opt.fail && opt.fail();
     reject(err)
    }
   })
  });
 },
})

然后理论上就可以保存图片了... 用户第一次在我们的小程序使用保存图片这个功能是会弹出一个授权弹框,如果用户手滑点了拒绝授权后再点一次保存图片,然后就会发现什么反应都没有了。。。

出现这样的原因是因为这个授权弹框只会出现一次,所以我们得想办法再让用户重新授权一次。这时就想到使用 wx.authorize .

但是经过测试后发现,使用 wx.authorize 后,会报 authorize:fail auth deny 的错误。然后经过查阅资料得知:

  • 如果用户未接受或拒绝过此权限,会弹窗询问用户,用户点击同意后方可调用接口;
  • 如果用户已授权,可以直接调用接口;
  • 如果用户已拒绝授权,则不会出现弹窗,而是直接进入接口 fail 回调。请开发者兼容用户拒绝授权的场景。

emmm... 那这样效果当然不符合我们预期,只能在换一种方式。这时就想到了使用<button open-type="openSetting"/>,在交互上做一个提示弹框,引导用户重新授权:

<image class="qr-code" src="{{url}}" mode="aspectFill" />
<button class="text" bindtap="saveImage">保存图片</button>

<!-- 简陋版提示 -->
<view wx:if="{{showDialog}}" class="dialog-wrap">
 <view class="dialog">
  这是一段提示用户授权的提示语
  <view class="dialog-footer">
   <button
    class="btn"
    open-type="openSetting"
    bindtap="confirm" >
     授权
   </button>
   <button class="btn" bindtap="cancel">取消</button>
  </view>
 </view>
</view>
const app = getApp()

Page({
 data: {
  url: 'https://avatars3.githubusercontent.com/u/23024075?s=460&v=4',
  showDialog: false,
 },

 saveImage() {
  this.wxToPromise('downloadFile', {
    url: this.data.url
   })
   .then(res => this.wxToPromise('saveImageToPhotosAlbum', {
    filePath: res.tempFilePath
   }))
   .then(res => {
    console.log(res);
    // this.hide();
    wx.showToast({
     title: '保存成功~',
     icon: 'none',
    });
   })
   .catch(({ errMsg }) => {
    console.log(errMsg)
    // if (~errMsg.indexOf('cancel')) return;
    if (!~errMsg.indexOf('auth')) {
     wx.showToast({ title: '图片保存失败,稍后再试', icon: 'none' });
    } else {
     // 调用授权提示弹框
     this.setData({
      showDialog: true
     })
    };
   })
 },

 // callback to promise
 wxToPromise(method, opt) {
  return new Promise((resolve, reject) => {
   wx[method]({
    ...opt,
    success(res) {
     opt.success && opt.success();
     resolve(res)
    },
    fail(err) {
     opt.fail && opt.fail();
     reject(err)
    }
   })
  });
 },

 confirm() {
  this.setData({
   showDialog:false
  })
 },

 cancel() {
  this.setData({
   showDialog: false
  })
 }
})

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
JavaScript 学习笔记二 字符串拼接
Mar 28 Javascript
js模拟点击事件实现代码
Nov 06 Javascript
js获取上传文件大小示例代码
Apr 10 Javascript
javascript遇到html5的一些表单属性
Jul 05 Javascript
JavaScript程序开发之JS代码放置的位置
Jan 15 Javascript
Javascript如何判断数据类型和数组类型
Jun 22 Javascript
js操作浏览器的参数方法
Jan 21 Javascript
bootstrap中日历范围选择插件daterangepicker的使用详解
Apr 17 Javascript
微信小程序图片加载失败时替换为默认图片的方法
Dec 09 Javascript
JavaScript实现简易聊天对话框(加滚动条)
Feb 10 Javascript
javascript实现倒计时效果
Feb 17 Javascript
基于JQuery和DWR实现异步数据传递
Oct 16 jQuery
VUE中使用MUI方法
Feb 12 #Javascript
如何利用ES6进行Promise封装总结
Feb 11 #Javascript
在vue项目中引入vue-beauty操作方法
Feb 11 #Javascript
Vue表单控件绑定图文详解
Feb 11 #Javascript
图文讲解vue的v-if使用方法
Feb 11 #Javascript
ES6 如何改变JS内置行为的代理与反射
Feb 11 #Javascript
ES6 更易于继承的类语法的使用
Feb 11 #Javascript
You might like
php下HTTP Response中的Chunked编码实现方法
2008/11/19 PHP
PHP获取当前文件所在目录 getcwd()函数
2009/05/13 PHP
浅析php插件 HTMLPurifier HTML解析器
2013/07/01 PHP
PHP使用mysql与mysqli连接Mysql数据库用法示例
2016/07/07 PHP
php实现小程序支付完整版
2018/10/09 PHP
解决laravel groupBy 对查询结果进行分组出现的问题
2019/10/09 PHP
用javascript实现读取txt文档的脚本
2007/07/20 Javascript
用jquery实现学校的校历(asp.net+jquery ui 1.72)
2010/01/01 Javascript
js实现的点击div区域外隐藏div区域
2014/06/30 Javascript
node.js中的console.info方法使用说明
2014/12/09 Javascript
百度地图自定义控件分享
2015/03/04 Javascript
nodejs实现bigpipe异步加载页面方案
2016/01/26 NodeJs
详解Javascript继承的实现
2016/03/25 Javascript
无阻塞加载js,防止因js加载不了影响页面显示的问题
2016/12/18 Javascript
js实现可输入可选择的select下拉框
2016/12/21 Javascript
JS实现的简单轮播图运动效果示例
2016/12/22 Javascript
Vue.js 点击按钮显示/隐藏内容的实例代码
2018/02/08 Javascript
vue项目中将element-ui table表格写成组件的实现代码
2019/06/12 Javascript
一些可能会用到的Node.js面试题
2019/06/15 Javascript
JavaScript深入V8引擎以及编写优化代码的5个技巧
2019/06/24 Javascript
在Vue 中实现循环渲染多个相同echarts图表
2020/07/20 Javascript
vue的webcamjs集成方式
2020/11/16 Javascript
pandas.dataframe按行索引表达式选取方法
2018/10/30 Python
Python删除n行后的其他行方法
2019/01/28 Python
Python笔记之代理模式
2019/11/20 Python
详解opencv中画圆circle函数和椭圆ellipse函数
2019/12/27 Python
谈一谈数组拼接tf.concat()和np.concatenate()的区别
2020/02/07 Python
Django+boostrap 美化admin后台的操作
2020/03/11 Python
详解Canvas 跨域脱坑实践
2018/11/07 HTML / CSS
校园餐饮创业计划书
2014/01/10 职场文书
护士岗位求职应聘自荐书范文
2014/02/12 职场文书
进口业务员岗位职责
2014/04/06 职场文书
人力资源管理求职信
2014/08/07 职场文书
离职报告范文
2014/11/04 职场文书
毕业生就业推荐表导师评语
2014/12/31 职场文书
写好Python代码的几条重要技巧
2021/05/21 Python