记录下开发过程中遇到的问题,欢迎大佬指点和纠错,鞠躬😝
InnerAudioContext.destroy()相关
这个这个这个我一定要说一下!!!因为这个问题,导致我项目中所以关于音频播放的内容重写,而且重写后导致了一个接一个的BUG,我的苍天啊!
背景:在多个page中都需要播放不同的音频,且在音频播放过程中出现打断或者退出小程序时,再回来之后需要音频续播,对于打断操作,使用了wx.onAudioInterruptionEnd进行监听,让当前的音频进行播放。
最开始的做法是在每个需要播放音频的位置都都实例化了一个InnerAudioContext,播放结束后,调用 InnerAudioContext.destroy()来销毁当前实例,也就是说最多同时存在一个InnerAudioContext实例,打断续播也是播放当前的音频。
const player = wx.createInnerAudioContext();
wx.onAudioInterruptionEnd(() => {
player.play();
});实际现象:真机调试时发现,IOS设备没有问题,安卓设备上会播放所有播放过的音频,也就是destroy方法并没有把音频实例销毁掉。想想一些十几二十个音频同时播放的效果有多么鬼畜 。
目前解决办法:这个问题我没有找到相关的回复和解答,只能暂时改成全局只实例化一个InnerAudioContext对象,更改且src属性来切换音频,但在这样做带来了巨大的问题,就是音频播放事件的监听,原本可能每个音频的onEnded回调中都有不同的操作,现在只能不断地进行onEnded和offEnded,才能保证在整个流程的顺畅。由于场面比较混乱 ,就先不放代码了。
这个问题我比较费解,因为现象相当严重,而且极其容易复现,觉得官方不应该出这么低级的BUG,所以总是怀疑是我代码写的有问题,如果各位大佬有相关经验,辛苦救救孩子吧🙏
获取权限相关
在小程序中需要使用到录音、拍照等功能时需要获取相关麦克风、摄像头的权限,以录音为例,代码中使用wx.startRecord()或者wx.getRecorderManager()时,会自动调起获取麦克风权限的弹窗,也可以选择优先使用wx.getSetting()判断权限,如果未获得那么通过wx.authorize()进行询问。以下是官方例子:
// 可以通过 wx.getSetting 先查询一下用户是否授权了 "scope.record" 这个 scope
wx.getSetting({
success(res) {
if (!res.authSetting['scope.record']) {
wx.authorize({
scope: 'scope.record',
success () {
// 用户已经同意小程序使用录音功能,后续调用 wx.startRecord 接口不会弹窗询问
wx.startRecord();
},
fail () {
// 用户拒绝小程序使用录音功能
}
})
}
}
})
官方例子乍一看似乎没有什么问题,但其实存在一个小坑:
问题描述:一旦我们拒绝了权限,就没办法再次调起获取权限的弹窗了,wx.authorize()会执行到fail中,对于这个问题官方文档中没有提到,但其实也提供了可以解决的API。
解决方案:wx.openSetting()
通过调用wx.openSetting()可以跳转到微信小程序的一个设置页面,展示设置界面只会出现小程序已经向用户请求过的权限。
注意:2.3.0 版本开始,用户发生点击行为后,才可以跳转打开设置页,管理授权信息。
这是小程序官方文档中的提示,也是我记录这个问题的原因之一,按照开发习惯,相信大多数同学会把这个操作写在某些回调函数里,我也是尝试了之后才发现这样无法跳转,好像也没有报错。
比较通用的做法就是调起一个wx.showModal(),在点击事件中调用wx.openSetting()。不得不吐槽一下,真的是有点麻烦,而且把权限这部分做的很重,但是又有什么办法呢。
以下是完整例子:
wx.getSetting({
success: (res) => {
if (!res.authSetting['scope.record']) {
wx.authorize({
scope: 'scope.record',
success: () => {
wx.startRecord();
},
fail: () => {
wx.showModal({
title: '温馨提示',
confirmText: '去开启',
cancelText: '取消',
content: '需要开启你的麦克风权限',
success: (res) => {
if (res.confirm) {
wx.openSetting({
success: (res) => {
if (res.authSetting['scope.record']) {
this.startRecord();
}
}
})
} else {
// 拒绝开启权限的后续操作
}
},
})
}
})
} else {
wx.startRecord();
}
}
})