使用 Cordova 在 Android 中记录并获取音量以生成波形
Record and get volume to generate a waveform in Android using Cordova
我一直在学习 Cordova,现在我正在开发一个应用程序来录制语音,我想获得正在录制的声音的 volume/Db/Amplitude。
我知道 Cordova 没有官方插件,所以我搜索并测试了一些插件:
Wavesurfer.js:
很简单,功能也很多,但是在android里面用不了,不知道是webview的问题还是什么(我有Android 4.1.2)
以下是我对这个插件的问题的详细信息:
https://github.com/katspaugh/wavesurfer.js/issues/341
MicVolume.js:
https://github.com/shukriadams/micVolume
我试了但没有成功,我不知道到底是什么问题,但我认为在这种情况下它在 cordova.exec
我找不到更多插件。还有其他我可以做或使用的东西吗,或者我做错了什么?我觉得我找不到简单的这种插件很奇怪,所以也许它开始从头开始学习 java 的解决方案? >:(
提前致谢。
您应该使用 Crosswalk,这样您就可以在没有 Cordova 插件的情况下访问网络音频 API。从那里你可以使用类似这个例子的东西:
http://tyleregeto.com/article/extracting-audio-data-with-the-web-audio-api
从当前的 Crosswalk 版本开始,Web Audio API 得到了完全支持,并且由于您使用的是 Cordova,因此您无需担心任何跨源问题(例如,您将在'localhost' 所以不会有任何 HTTPS 问题。
我在 Angular 中构建了一个节拍器,我在最近的一个带 Crosswalk 的 Ionic 应用程序中使用了它,它运行良好(即使在我用于测试的非常糟糕的 XGODY 设备上)。请参阅下面的要点:
我不知道这个问题有多重要,因为这个问题是 1 年前提出的。
但它可能会帮助其他人寻找答案。 MicVolume.js 有效,但文档很少,我花了很多时间弄明白。以下代码应该有效:
function audioSuccessCallback(e) {
setInterval(function() {
micVolume.read(function(reading) {
console.log(reading.volume);
},
function(error){
console.log(error);
});
}, 200);
}
function audioErrorCallback(e) {
console.log(e);
}
micVolume.start(audioSuccessCallback, audioErrorCallback);
您需要做的就是循环 micVolume.read() 函数,这将 return 您 "loudness" 录音。通过内部麦克风或外部麦克风。请记住在 deviceready 触发后调用 micVolume.start() 。
如果您需要获取声音的频率,可以在插件中添加以下代码 "MicVolumePlugin.java":
//Now we need to decode the PCM data using the Zero Crossings Method
int numCrossing = 0; //initialize your number of zero crossings to 0
for (int p = 0; p<bufferSize/4; p+=4) {
if (buffer[p]>0 && buffer[p+1]<=0) numCrossing++;
if (buffer[p]<0 && buffer[p+1]>=0) numCrossing++;
if (buffer[p+1]>0 && buffer[p+2]<=0) numCrossing++;
if (buffer[p+1]<0 && buffer[p+2]>=0) numCrossing++;
if (buffer[p+2]>0 && buffer[p+3]<=0) numCrossing++;
if (buffer[p+2]<0 && buffer[p+3]>=0) numCrossing++;
if (buffer[p+3]>0 && buffer[p+4]<=0) numCrossing++;
if (buffer[p+3]<0 && buffer[p+4]>=0) numCrossing++;
}//for p
for (int p=(bufferSize/4)*4;p<bufferSize-1;p++) {
if (buffer[p]>0 && buffer[p+1]<=0) numCrossing++;
if (buffer[p]<0 && buffer[p+1]>=0) numCrossing++;
}
// Set the audio Frequency to half the number of zero crossings, times the number of samples our buffersize is per second.
float frequency = (44100*4/bufferSize)*(numCrossing/2);
returnObj.put("frequency", frequency);
FFT 更准确,但速度要慢得多。这很好地完成了工作。 (我不记得我是在哪里找到这个 java 代码的,但是要感谢写它的人!)
我一直在学习 Cordova,现在我正在开发一个应用程序来录制语音,我想获得正在录制的声音的 volume/Db/Amplitude。 我知道 Cordova 没有官方插件,所以我搜索并测试了一些插件:
Wavesurfer.js:
很简单,功能也很多,但是在android里面用不了,不知道是webview的问题还是什么(我有Android 4.1.2) 以下是我对这个插件的问题的详细信息: https://github.com/katspaugh/wavesurfer.js/issues/341
MicVolume.js:
https://github.com/shukriadams/micVolume 我试了但没有成功,我不知道到底是什么问题,但我认为在这种情况下它在 cordova.exec
我找不到更多插件。还有其他我可以做或使用的东西吗,或者我做错了什么?我觉得我找不到简单的这种插件很奇怪,所以也许它开始从头开始学习 java 的解决方案? >:(
提前致谢。
您应该使用 Crosswalk,这样您就可以在没有 Cordova 插件的情况下访问网络音频 API。从那里你可以使用类似这个例子的东西:
http://tyleregeto.com/article/extracting-audio-data-with-the-web-audio-api
从当前的 Crosswalk 版本开始,Web Audio API 得到了完全支持,并且由于您使用的是 Cordova,因此您无需担心任何跨源问题(例如,您将在'localhost' 所以不会有任何 HTTPS 问题。
我在 Angular 中构建了一个节拍器,我在最近的一个带 Crosswalk 的 Ionic 应用程序中使用了它,它运行良好(即使在我用于测试的非常糟糕的 XGODY 设备上)。请参阅下面的要点:
我不知道这个问题有多重要,因为这个问题是 1 年前提出的。 但它可能会帮助其他人寻找答案。 MicVolume.js 有效,但文档很少,我花了很多时间弄明白。以下代码应该有效:
function audioSuccessCallback(e) {
setInterval(function() {
micVolume.read(function(reading) {
console.log(reading.volume);
},
function(error){
console.log(error);
});
}, 200);
}
function audioErrorCallback(e) {
console.log(e);
}
micVolume.start(audioSuccessCallback, audioErrorCallback);
您需要做的就是循环 micVolume.read() 函数,这将 return 您 "loudness" 录音。通过内部麦克风或外部麦克风。请记住在 deviceready 触发后调用 micVolume.start() 。 如果您需要获取声音的频率,可以在插件中添加以下代码 "MicVolumePlugin.java":
//Now we need to decode the PCM data using the Zero Crossings Method
int numCrossing = 0; //initialize your number of zero crossings to 0
for (int p = 0; p<bufferSize/4; p+=4) {
if (buffer[p]>0 && buffer[p+1]<=0) numCrossing++;
if (buffer[p]<0 && buffer[p+1]>=0) numCrossing++;
if (buffer[p+1]>0 && buffer[p+2]<=0) numCrossing++;
if (buffer[p+1]<0 && buffer[p+2]>=0) numCrossing++;
if (buffer[p+2]>0 && buffer[p+3]<=0) numCrossing++;
if (buffer[p+2]<0 && buffer[p+3]>=0) numCrossing++;
if (buffer[p+3]>0 && buffer[p+4]<=0) numCrossing++;
if (buffer[p+3]<0 && buffer[p+4]>=0) numCrossing++;
}//for p
for (int p=(bufferSize/4)*4;p<bufferSize-1;p++) {
if (buffer[p]>0 && buffer[p+1]<=0) numCrossing++;
if (buffer[p]<0 && buffer[p+1]>=0) numCrossing++;
}
// Set the audio Frequency to half the number of zero crossings, times the number of samples our buffersize is per second.
float frequency = (44100*4/bufferSize)*(numCrossing/2);
returnObj.put("frequency", frequency);
FFT 更准确,但速度要慢得多。这很好地完成了工作。 (我不记得我是在哪里找到这个 java 代码的,但是要感谢写它的人!)