/** * 权限管理工具类 * 用于处理各种平台权限申请和检查 */ class PermissionManager { constructor() { this.platform = uni.getSystemInfoSync().platform } /** * 检查录音权限 * @returns {Promise} 是否有权限 */ async checkRecordPermission() { return new Promise((resolve, reject) => { // #ifdef H5 this.checkH5RecordPermission().then(resolve).catch(reject) // #endif // #ifdef MP-WEIXIN || MP-ALIPAY || MP-BAIDU || MP-TOUTIAO this.checkMiniProgramRecordPermission().then(resolve).catch(reject) // #endif // #ifdef APP-PLUS this.checkAppRecordPermission().then(resolve).catch(reject) // #endif }) } /** * 申请录音权限 * @returns {Promise} 是否授权成功 */ async requestRecordPermission() { return new Promise((resolve, reject) => { // #ifdef H5 this.requestH5RecordPermission().then(resolve).catch(reject) // #endif // #ifdef MP-WEIXIN || MP-ALIPAY || MP-BAIDU || MP-TOUTIAO this.requestMiniProgramRecordPermission().then(resolve).catch(reject) // #endif // #ifdef APP-PLUS this.requestAppRecordPermission().then(resolve).catch(reject) // #endif }) } /** * H5平台检查录音权限 */ async checkH5RecordPermission() { return new Promise((resolve, reject) => { if (navigator.mediaDevices && navigator.mediaDevices.getUserMedia) { navigator.mediaDevices.getUserMedia({ audio: true }) .then(() => { resolve(true) }) .catch((error) => { console.error('H5录音权限检查失败:', error) reject(error) }) } else { reject(new Error('浏览器不支持录音功能')) } }) } /** * H5平台申请录音权限 */ async requestH5RecordPermission() { return this.checkH5RecordPermission() } /** * 小程序平台检查录音权限 */ async checkMiniProgramRecordPermission() { return new Promise((resolve, reject) => { uni.getSetting({ success: (res) => { if (res.authSetting['scope.record'] === true) { resolve(true) } else if (res.authSetting['scope.record'] === false) { reject(new Error('用户拒绝了录音权限')) } else { // 未询问过权限 resolve(false) } }, fail: (err) => { reject(err) } }) }) } /** * 小程序平台申请录音权限 */ async requestMiniProgramRecordPermission() { return new Promise((resolve, reject) => { uni.authorize({ scope: 'scope.record', success: () => { resolve(true) }, fail: (err) => { if (err.errMsg.includes('auth deny')) { // 用户拒绝,引导到设置页面 this.showPermissionModal('录音权限', '需要录音权限才能使用语音对讲功能') .then(() => { uni.openSetting({ success: (res) => { if (res.authSetting['scope.record']) { resolve(true) } else { reject(new Error('用户拒绝录音权限')) } }, fail: reject }) }) .catch(reject) } else { reject(err) } } }) }) } /** * App平台检查录音权限 */ async checkAppRecordPermission() { return new Promise((resolve, reject) => { // #ifdef APP-PLUS plus.android.requestPermissions( ['android.permission.RECORD_AUDIO'], (result) => { const granted = result.granted && result.granted.length > 0 resolve(granted) }, (error) => { reject(error) } ) // #endif // #ifndef APP-PLUS resolve(true) // #endif }) } /** * App平台申请录音权限 */ async requestAppRecordPermission() { return this.checkAppRecordPermission() } /** * 显示权限申请弹窗 */ showPermissionModal(permissionName, description) { return new Promise((resolve, reject) => { uni.showModal({ title: '权限申请', content: `需要${permissionName}才能使用相关功能。${description}`, confirmText: '去设置', cancelText: '取消', success: (res) => { if (res.confirm) { resolve() } else { reject(new Error('用户取消权限申请')) } } }) }) } /** * 检查相机权限 */ async checkCameraPermission() { return new Promise((resolve, reject) => { // #ifdef H5 if (navigator.mediaDevices && navigator.mediaDevices.getUserMedia) { navigator.mediaDevices.getUserMedia({ video: true }) .then(() => resolve(true)) .catch(reject) } else { reject(new Error('浏览器不支持相机功能')) } // #endif // #ifdef MP-WEIXIN || MP-ALIPAY || MP-BAIDU || MP-TOUTIAO uni.getSetting({ success: (res) => { if (res.authSetting['scope.camera'] === true) { resolve(true) } else if (res.authSetting['scope.camera'] === false) { reject(new Error('用户拒绝了相机权限')) } else { resolve(false) } }, fail: reject }) // #endif // #ifdef APP-PLUS plus.android.requestPermissions( ['android.permission.CAMERA'], (result) => { const granted = result.granted && result.granted.length > 0 resolve(granted) }, (error) => { reject(error) } ) // #endif }) } /** * 申请相机权限 */ async requestCameraPermission() { return new Promise((resolve, reject) => { // #ifdef H5 this.checkCameraPermission().then(resolve).catch(reject) // #endif // #ifdef MP-WEIXIN || MP-ALIPAY || MP-BAIDU || MP-TOUTIAO uni.authorize({ scope: 'scope.camera', success: () => resolve(true), fail: (err) => { if (err.errMsg.includes('auth deny')) { this.showPermissionModal('相机权限', '需要相机权限才能使用拍照功能') .then(() => { uni.openSetting({ success: (res) => { if (res.authSetting['scope.camera']) { resolve(true) } else { reject(new Error('用户拒绝相机权限')) } }, fail: reject }) }) .catch(reject) } else { reject(err) } } }) // #endif // #ifdef APP-PLUS this.checkCameraPermission().then(resolve).catch(reject) // #endif }) } /** * 检查位置权限 */ async checkLocationPermission() { return new Promise((resolve, reject) => { // #ifdef H5 if (navigator.geolocation) { navigator.geolocation.getCurrentPosition( () => resolve(true), (error) => { if (error.code === error.PERMISSION_DENIED) { reject(new Error('用户拒绝了位置权限')) } else { reject(error) } } ) } else { reject(new Error('浏览器不支持定位功能')) } // #endif // #ifdef MP-WEIXIN || MP-ALIPAY || MP-BAIDU || MP-TOUTIAO uni.getSetting({ success: (res) => { if (res.authSetting['scope.userLocation'] === true) { resolve(true) } else if (res.authSetting['scope.userLocation'] === false) { reject(new Error('用户拒绝了位置权限')) } else { resolve(false) } }, fail: reject }) // #endif // #ifdef APP-PLUS plus.android.requestPermissions( ['android.permission.ACCESS_FINE_LOCATION', 'android.permission.ACCESS_COARSE_LOCATION'], (result) => { const granted = result.granted && result.granted.length > 0 resolve(granted) }, (error) => { reject(error) } ) // #endif }) } /** * 申请位置权限 */ async requestLocationPermission() { return new Promise((resolve, reject) => { // #ifdef H5 this.checkLocationPermission().then(resolve).catch(reject) // #endif // #ifdef MP-WEIXIN || MP-ALIPAY || MP-BAIDU || MP-TOUTIAO uni.authorize({ scope: 'scope.userLocation', success: () => resolve(true), fail: (err) => { if (err.errMsg.includes('auth deny')) { this.showPermissionModal('位置权限', '需要位置权限才能获取当前位置') .then(() => { uni.openSetting({ success: (res) => { if (res.authSetting['scope.userLocation']) { resolve(true) } else { reject(new Error('用户拒绝位置权限')) } }, fail: reject }) }) .catch(reject) } else { reject(err) } } }) // #endif // #ifdef APP-PLUS this.checkLocationPermission().then(resolve).catch(reject) // #endif }) } /** * 获取当前平台 */ getPlatform() { return this.platform } /** * 检查是否为开发环境 */ isDev() { // #ifdef H5 return process.env.NODE_ENV === 'development' // #endif // #ifndef H5 return false // #endif } } // 创建单例实例 const permissionManager = new PermissionManager() export default permissionManager