132 lines
4.4 KiB
JavaScript
132 lines
4.4 KiB
JavaScript
|
|
/**
|
|||
|
|
* 原生录音工具(使用Android Intent)
|
|||
|
|
* 适用于uni-app录音API不兼容的设备
|
|||
|
|
*/
|
|||
|
|
|
|||
|
|
class NativeRecorder {
|
|||
|
|
/**
|
|||
|
|
* 启动系统录音(简化版,使用MediaRecorder)
|
|||
|
|
* @returns {Promise<string>} 录音文件路径
|
|||
|
|
*/
|
|||
|
|
startSystemRecord() {
|
|||
|
|
return new Promise((resolve, reject) => {
|
|||
|
|
// #ifdef APP-PLUS
|
|||
|
|
try {
|
|||
|
|
console.log('[原生录音] 使用MediaRecorder录音...')
|
|||
|
|
|
|||
|
|
// 导入Android类
|
|||
|
|
const MediaRecorder = plus.android.importClass('android.media.MediaRecorder')
|
|||
|
|
const File = plus.android.importClass('java.io.File')
|
|||
|
|
|
|||
|
|
// 创建MediaRecorder
|
|||
|
|
const recorder = new MediaRecorder()
|
|||
|
|
|
|||
|
|
// 生成文件路径
|
|||
|
|
const timestamp = Date.now()
|
|||
|
|
const fileName = 'native_record_' + timestamp + '.amr'
|
|||
|
|
|
|||
|
|
// 使用plus.io创建文件
|
|||
|
|
plus.io.requestFileSystem(plus.io.PRIVATE_DOC, (fs) => {
|
|||
|
|
fs.root.getFile(fileName, {create: true}, (fileEntry) => {
|
|||
|
|
const filePath = fileEntry.fullPath
|
|||
|
|
console.log('[原生录音] 文件路径:', filePath)
|
|||
|
|
|
|||
|
|
try {
|
|||
|
|
// 配置录音器
|
|||
|
|
recorder.setAudioSource(MediaRecorder.AudioSource.MIC)
|
|||
|
|
recorder.setOutputFormat(MediaRecorder.OutputFormat.AMR_NB)
|
|||
|
|
recorder.setAudioEncoder(MediaRecorder.AudioEncoder.AMR_NB)
|
|||
|
|
recorder.setOutputFile(filePath)
|
|||
|
|
|
|||
|
|
// 准备并开始录音
|
|||
|
|
recorder.prepare()
|
|||
|
|
recorder.start()
|
|||
|
|
|
|||
|
|
console.log('[原生录音] ✓ 录音已开始')
|
|||
|
|
|
|||
|
|
// 提示用户
|
|||
|
|
uni.showModal({
|
|||
|
|
title: '正在录音',
|
|||
|
|
content: '请说话,录音3秒后自动停止',
|
|||
|
|
showCancel: false
|
|||
|
|
})
|
|||
|
|
|
|||
|
|
// 3秒后自动停止
|
|||
|
|
setTimeout(() => {
|
|||
|
|
try {
|
|||
|
|
recorder.stop()
|
|||
|
|
recorder.release()
|
|||
|
|
console.log('[原生录音] ✓ 录音已停止')
|
|||
|
|
|
|||
|
|
uni.hideToast()
|
|||
|
|
|
|||
|
|
// 验证文件
|
|||
|
|
setTimeout(() => {
|
|||
|
|
plus.io.resolveLocalFileSystemURL(filePath, (entry) => {
|
|||
|
|
entry.file((file) => {
|
|||
|
|
console.log('[原生录音] 文件大小:', file.size, 'bytes')
|
|||
|
|
|
|||
|
|
if (file.size > 100) {
|
|||
|
|
console.log('[原生录音] ✓ 录音成功')
|
|||
|
|
resolve(filePath)
|
|||
|
|
} else {
|
|||
|
|
console.log('[原生录音] ⚠️ 文件过小,只有', file.size, 'bytes')
|
|||
|
|
console.log('[原生录音] 可能原因:')
|
|||
|
|
console.log(' 1. 麦克风权限未真正授予')
|
|||
|
|
console.log(' 2. 麦克风被其他应用占用')
|
|||
|
|
console.log(' 3. 麦克风硬件故障')
|
|||
|
|
console.log(' 4. 系统录音服务异常')
|
|||
|
|
|
|||
|
|
reject(new Error(`录音文件过小(${file.size}字节),请测试系统录音机是否正常`))
|
|||
|
|
}
|
|||
|
|
}, reject)
|
|||
|
|
}, reject)
|
|||
|
|
}, 500)
|
|||
|
|
|
|||
|
|
} catch (e) {
|
|||
|
|
console.error('[原生录音] 停止失败:', e)
|
|||
|
|
reject(e)
|
|||
|
|
}
|
|||
|
|
}, 3000)
|
|||
|
|
|
|||
|
|
} catch (e) {
|
|||
|
|
console.error('[原生录音] 启动录音失败:', e)
|
|||
|
|
reject(e)
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
}, reject)
|
|||
|
|
}, reject)
|
|||
|
|
|
|||
|
|
} catch (e) {
|
|||
|
|
console.error('[原生录音] 异常:', e)
|
|||
|
|
reject(e)
|
|||
|
|
}
|
|||
|
|
// #endif
|
|||
|
|
|
|||
|
|
// #ifndef APP-PLUS
|
|||
|
|
reject(new Error('只支持APP环境'))
|
|||
|
|
// #endif
|
|||
|
|
})
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
/**
|
|||
|
|
* 简化版:直接启动录音并返回
|
|||
|
|
* 用于快速测试
|
|||
|
|
*/
|
|||
|
|
quickRecord() {
|
|||
|
|
console.log('[原生录音] 快速测试...')
|
|||
|
|
|
|||
|
|
return this.startSystemRecord()
|
|||
|
|
.then(filePath => {
|
|||
|
|
console.log('[原生录音] ✓ 录音成功:', filePath)
|
|||
|
|
return filePath
|
|||
|
|
})
|
|||
|
|
.catch(error => {
|
|||
|
|
console.error('[原生录音] ✗ 录音失败:', error.message)
|
|||
|
|
throw error
|
|||
|
|
})
|
|||
|
|
}
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
export default new NativeRecorder()
|