日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

微信拍照和选择相册照片功能chooseImage

發布時間:2023/12/20 编程问答 36 豆豆
生活随笔 收集整理的這篇文章主要介紹了 微信拍照和选择相册照片功能chooseImage 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

這個需求做下來參考了不少文章,其實大多都是一知半解,每個人遇到的問題不同,這篇文章可以說徹底解決wx.chooseImage的各種疑難雜癥,一步到位,因此趁著今天休息把整個過程記錄下來,分享給之后有需要的各位同行!

最近在做一個復雜的跨五端(PC、H5、小程序、iOS、android)的需求,歷時將近兩個多月,其中酸甜苦辣冷暖自知,近日終于可以封板上線,回憶整個開發過程,深坑不斷,收獲頗多,今天先分享一下在微信小程序的web-view里選取照片的功能,此文完整的記錄整個開發過程,徹底解決各種疑難雜癥。

#深度調研
因為跨端所以最開始使用了的方式,簡單粗暴可使用,五端勉強都可以打個及格分,一直到聯調結束PM檢測時說體驗太差了,趁著還有時間(其實我也看不下去),索性就按PM的要求來,開始計劃調用原生的,因為客戶端之前已經提供了這樣的bridge,所以和客戶端的頭像調試輕松完成,剩下的小程序歷經萬千磨難,最終完美謝幕。

首先沒有做過這方面的經驗,兩眼一抹黑,由于是把H5頁面嵌套在小程序的web-view里,所以直接查看官方文檔,小程序向web-view提供了三十多個API-詳情文檔。至此以為可以輕松搞定,于是開始了不斷的趟坑。。。

#按步開發
剛開始直接在H5里使用了wx.chooseImage,發現在開發者工具中不斷的報錯the permission value is offline verifying,慢慢開始搜索才發現在小程序的web-view里也必須使用jweixin,其實就是個公眾號網頁,接下來開始按這套流程走:

// 引入JS文件 // 推薦使用1.3.2以上的版本,之前的版本很多坑😭 https://res.wx.qq.com/open/js/jweixin-1.3.2.js // 我是直接用的npm包,目前基于1.4.0-test的版本 npm install weixin-js-sdk // 通過config接口注入權限驗證配置 wx.config({debug: true, // 開啟調試模式,調用的所有api的返回值會在客戶端alert出來,若要查看傳入的參數,可以在pc端打開,參數信息會通過log打出,僅在pc端時才會打印。appId: '', // 必填,微信公眾號的唯一標識,此處填寫公眾號的appIdtimestamp: , // 必填,生成簽名的時間戳nonceStr: '', // 必填,生成簽名的隨機串signature: '',// 必填,簽名jsApiList: [] // 必填,需要使用的JS接口列表,所有JS接口列表見附錄2 }); // 通過ready接口處理成功驗證 wx.ready(function(){// config信息驗證后會執行ready方法,所有接口調用都必須在config接口獲得結果之后,config是一個客戶端的異步操作,所以如果需要在頁面加載時就調用相關接口,則須把相關接口放在ready函數中調用來確保正確執行。對于用戶觸發時才調用的接口,則可以直接調用,不需要放在ready函數中。 }); // 通過error接口處理失敗驗證 wx.error(function(res){// config信息驗證失敗會執行error函數,如簽名過期導致驗證失敗,具體錯誤信息可以打開config的debug模式查看,也可以在返回的res參數中查看,對于SPA可以在這里更新簽名。 }); // 判斷當前客戶端版本是否支持指定JS接口 wx.checkJsApi({jsApiList: ['chooseImage'] // 需要檢測的JS接口列表success: function(res) {// 以鍵值對的形式返回,可用的api值true,不可用為false// 如:{"checkResult":{"chooseImage":true},"errMsg":"checkJsApi:ok"}},fail: function(err) {// checkJsApi接口調用失敗} }); // 接口調用 wx.chooseImage({count: 1, // 默認9sizeType: ['original', 'compressed'], // 可以指定是原圖還是壓縮圖,默認二者都有sourceType: ['album', 'camera'], // 可以指定來源是相冊還是相機,默認二者都有success: function (res) {var localIds = res.localIds; // 返回選定照片的本地ID列表,localId可以作為img標簽的src屬性顯示圖片} });

本部分要特別注意以下幾點:

invalid url domain:當前頁面所在域名與使用appid沒有綁定(可在該公眾號后臺的應用可信域名中配置當前H5頁面的域名);
invalid signature簽名錯誤:建議按如下順序檢查,主要可能是域名一般帶的參數,所以域名每次都不一樣,必須在調用前通過域名來獲取signature;
服務上線之后無法獲取jsapi_ticket,一般是access_token調用次數過多被限制了,需要在服務端做緩存;
permission denied:該公眾號號沒有權限使用這個JSAPI(部分接口需要認證之后才能使用);
#處理圖片數據為base64
wx.chooseImage獲取到的圖片為一個臨時路徑,微信同時提供了wx.getLocalImgData方法可以把獲取到的路徑轉為base64格式的數據,至此就可以輕松許多了,但是轉出來的base64在android和iOS中稍有不同,需要特別注意一下:

wx.getLocalImgData({localId: req.localIds[0].toString(),success: function (res) {const localData = res.localData;let imageBase64 = '';if (localData.indexOf('data:image') == 0) {//蘋果的直接賦值,默認生成'data:image/jpeg;base64,'的頭部拼接imageBase64 = localData;} else {//此處是安卓中的唯一得坑!在拼接前需要對localData進行換行符的全局替換//此時一個正常的base64圖片路徑就完美生成賦值到img的src中了imageBase64 = 'data:image/jpeg;base64,' + localData.replace(/\n/g, '');}} });

#上傳圖片
獲取到圖片的base64數據之后其實我們就可以為所欲為了,不需要使用wx.uploadImage和wx.downloadImage了,不僅需要麻煩的上傳到微信服務器,還有三天的時間限制反而增加了成本,最好的方式就是直接上傳至我們自己的服務器。

一般與服務端交互的這種文件類型一般采用表單提交–multipart/form-data的方式,這就要求我們熟悉傳輸form-data的數據交互,所以需要把剛才獲取到的base64轉為可post的二進制數據,JavaScript提供了原生的atob/btoa用來對base64進行編碼和解碼;

base64ToBlob(dataurl) {let arr = dataurl.split(',');let mime = arr[0].match(/:(.*?);/)[1];let bstr = atob(arr[1]);let n = bstr.length;let u8arr = new Uint8Array(n);while (n--) {u8arr[n] = bstr.charCodeAt(n);}return new Blob([u8arr], { type: mime }); }

ok,處理好可交互的數據就可以上傳到自己的服務器了,之后相當于普通H5頁面的圖片交互了,可上傳可下載

let param = new FormData(); param.append('headPic', imageData); this.$http.post('/upload.json', {headers: {'Content-Type': 'multipart/form-data',},params: param, }).then(res => {console.log('上傳成功', res); });

#完整代碼

<template><div class="card-avatar"><img:src="avatarUrl"><divclass="choose-image"@click="chooseImage"/></div> </template><script> import wx from 'weixin-js-sdk'; const imgUrl = require('../../common/assets/images/default-avatar.png');export default {name: 'Card',components: {},props: {},data() {return {avatarUrl: imgUrl,};},computed: {},watch: {},mounted() {this.getWxConfigDatas();},methods: {getWxConfigDatas() {const params = {checkCode: getUrlParams().checkCode, // 從地址欄獲取checkCode用于校驗signature};this.$http.get('/signature.json', { params }).then(res => {if (res.content.data && res.content.data.signature) {this.registereWxApi(res.content.data.signature);}});},registereWxApi(data) {wx.config({// debug: true,jsApiList: ['chooseImage', 'getLocalImgData'],appId: data.appId,timestamp: data.timestamp,nonceStr: data.nonceStr,signature: data.signature,});},chooseImage() {let that = this;if (window.__wxjs_environment === 'miniprogram') {wx.miniProgram.getEnv(function(res) {if (res.miniprogram) {wx.checkJsApi({jsApiList: ['chooseImage', 'getLocalImgData'],success: function(res) {if (res.checkResult.chooseImage) {wx.chooseImage({count: 1,sizeType: ['compressed'],sourceType: ['album', 'camera'],success: function(req) {wx.getLocalImgData({localId: req.localIds[0].toString(),success: function (res) {const localData = res.localData;let imageBase64 = '';if (localData.indexOf('data:image') == 0) {//蘋果的直接賦值,默認生成'data:image/jpeg;base64,'的頭部拼接imageBase64 = localData;} else {//此處是安卓中的唯一得坑!在拼接前需要對localData進行換行符的全局替換//此時一個正常的base64圖片路徑就完美生成賦值到img的src中了imageBase64 = 'data:image/jpeg;base64,' + localData.replace(/\n/g, '');}that.avatarUrl = imageBase64;that.handleAvatar(that.dataURLtoBlob(imageBase64));}});},fail() {that.$toast.show({type: 'text',text: '選擇頭像失敗!',});}});} else {that.$toast.show({type: 'text',text: '暫不支持修改頭像!',});}},fail: function() {that.$toast.show({type: 'text',text: '暫不支持修改頭像!',});},});} else {that.lgBridgeChooseImage();}});} else {that.lgBridgeChooseImage();}},handleAvatar(imageData) {let that = this;let param = new FormData();param.append('headPic', imageData);that.$http.post('/upload.json', {headers: {'Content-Type': 'multipart/form-data',},params: param,}).then(res => {if (parseInt(res.state, 10) === 1) {that.$toast.show({type: 'success',text: '上傳成功!',});that.avatarUrl = res.content && res.content.data && res.content.data.url;}});},dataURLtoBlob(dataurl) {let arr = dataurl.split(',');let mime = arr[0].match(/:(.*?);/)[1];let bstr = atob(arr[1]);let n = bstr.length;let u8arr = new Uint8Array(n);while (n--) {u8arr[n] = bstr.charCodeAt(n);}return new Blob([u8arr], { type: mime });}} }; </script><style lang="less" scoped> .card-avatar {position: absolute;top: 0;left: 50%;transform: translate(-50%, -50%);width: 180px;height: 180px;border-radius: 100%;overflow: hidden;img {width: 100%;height: 100%;}.choose-image, input {position: absolute;top: 0;left: 0;width: 100%;height: 100%;opacity: 0;} } </style>

這個需求做下來參考了不少文章,其實大多都是一知半解,每個人遇到的問題不同,這篇文章可以說徹底解決wx.chooseImage的各種疑難雜癥,一步到位,因此趁著今天休息把整個過程記錄下來,分享給之后有需要的各位同行!

總結

以上是生活随笔為你收集整理的微信拍照和选择相册照片功能chooseImage的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。