// pages/index/component/AudioPanel/index.js const RECORD_CONFIG = { duration: 120000, sampleRate: 44100, numberOfChannels: 1, encodeBitRate: 128000, format: 'mp3', } const app = getApp() const API = app.globalData.api Component({ /** * 组件的属性列表 */ properties: { paper: { type: Object } }, /** * 组件的初始数据 */ data: { audio: '', isRecord: false, recordTime: 0, duration: '00:00' }, lockRecord: false, recordHandler: 0, recordManager: null, /** * 组件的方法列表 */ methods: { audioAction: function (e) { if (this.lockRecord) { return false } if (!this.data.paper || !this.data.paper.courseId > 0) { wx.showToast({ title: '请重新扫描题目二维码', icon: 'none' }) return false } this.lockRecord = true this.triggerEvent('enableScan', { enabled: false }) this.startRecord() }, uploadSuccess(accessUrl) { const that = this //文件上传成功后通知服务端 API.notifyServer(that.data.paper.examRecordDataId, that.data.paper.examStudentId, that.data.paper.questionOrder, accessUrl, 'AUDIO').then(res => { // 轮询答案处理结果 const _startTime = new Date().getTime() var times = 10 const handler = setInterval(function () { API.getNotifyResult(res) .then(res => { console.log(res) if (res == 'CONFIRMED') { clearInterval(handler) wx.hideLoading() wx.showToast({ title: '上传成功,继续扫描下一题', icon: 'none', duration: 2500 }) wx.reLaunch({ url: '/pages/index/index' }) } else { throw '答案未同步' } }).catch(exceptions => { times-- if (new Date().getTime() - _startTime >= 1000 * 10 || times < 0) { clearInterval(handler) wx.hideLoading() wx.showToast({ title: '上传失败,请重新上传', icon: 'none' }) } }) }, 1000) }).catch(exceptions => { console.log('catch', exceptions) that.uploadFail(exceptions) }) }, uploadFail(exceptions) { var error = '上传失败,请重新上传' try { if (exceptions.statusCode == 500) { error = exceptions.data.desc } } catch (e) { } wx.hideLoading() wx.showToast({ title: error, icon: 'none' }) }, uploadAudio(e) { // 正在录音 禁止操作 if (this.data.isRecord) { return } const filepath = this.data.audio const that = this wx.showLoading({ title: '正在上传录音', mask: true }) const duration = filepath wx.getFileInfo({ filePath: filepath, success: function (fileRes) { console.log(fileRes) var accessUrl = '' // 获取上传签名 API.getSign(that.data.paper.examRecordDataId, that.data.paper.examStudentId, that.data.paper.questionOrder, fileRes.digest, 'mp3') .then(signRes => { console.log(signRes) // 上传文件 const c_md5 = wx.arrayBufferToBase64(new Uint8Array(fileRes.digest.match(/[\da-f]{2}/gi).map(function (h) { return parseInt(h, 16) }))) console.log('uploadFile::start upload') const task = wx.uploadFile({ url: signRes.formUrl, filePath: filepath, name: 'file', formData: signRes.formParams, success: taskRes => { console.log('uploadFile::upload success', taskRes) that.uploadSuccess(signRes.accessUrl) }, fail: error => { console.log('uploadFile:uploadFile:catch', exceptions) that.uploadFail(exceptions) } }) task.onHeadersReceived(res => { console.log('task header::', res, res.header['Content-MD5'], c_md5) if (c_md5 != res.header['Content-MD5']) { that.uploadFail('文件破损,请重新上传') } }) }).catch(exceptions => { console.log('catch', exceptions) that.uploadFail(exceptions) }) } }) }, startRecord: function () { const that = this if (!this.data.isRecord) { if (this.data.audio) { wx.showModal({ title: '提示', content: '已存在未上传的录音,是否开始重新录音', confirmText: '开始录音', success(res) { if (res.confirm) { that.recordManager.start(RECORD_CONFIG) } else { that.lockRecord = false } } }) } else { wx.showLoading({ title: '', mask: true }) that.recordManager.start(RECORD_CONFIG) } } else { that.recordManager.stop() } }, onRecordStart() { this.lockRecord = false console.log("record start") const that = this this.setData({ audio: '', isRecord: true }) this.recordHandler = setInterval(function () { var recordTime = that.data.recordTime + 0.1 var second = parseInt(recordTime) var msc = parseInt((recordTime - second) * 10) * 10 var duration = (second > 9 ? second : ('0' + second)) + ":" + (msc > 0 ? msc : "00") that.setData({ isRecord: true, recordTime: recordTime, duration: duration }) }, 100) }, onRecordStop(audioPath) { this.triggerEvent('enableScan', {enabled: true}) this.lockRecord = false console.log("record stop", audioPath) clearInterval(this.recordHandler) this.recordHandler = 0 this.setData({ audio: audioPath, recordTime: 0, duration: "00:00", isRecord: false, }) }, }, attached() { const that = this this.recordManager = wx.getRecorderManager() this.recordManager.onError(function (res) { console.log(res) that.lockRecord = false wx.showToast({ title: '录音出错', icon: 'none' }) }) this.recordManager.onStart(function () { //保持屏幕常亮 wx.setKeepScreenOn({ keepScreenOn: true }) wx.hideLoading() that.onRecordStart() }) this.recordManager.onStop(function (res) { wx.setKeepScreenOn({ keepScreenOn: false }) wx.hideLoading() that.onRecordStop(res.tempFilePath) }) this.recordManager.onInterruptionBegin(function () { wx.hideLoading() console.log("onInterruptionBegin") that.lockRecord = false that.recordManager.stop() }) this.recordManager.onInterruptionEnd(function () { wx.hideLoading() that.lockRecord = false console.log("onInterruptionEnd") }) wx.onAppHide(() => { if (that.data.isRecord) { wx.hideLoading() that.recordManager.stop() that.lockRecord = false } }) }, detached() { const that = this wx.offAppHide(() => { if (that.data.isRecord) { that.recordManager.stop() } }) } })