我正在尝试在 Android 中制作一个通话录音应用程序。我正在使用扬声器录制上行链路和下行链路音频。我面临的唯一问题是音量太低。我已使用 AudioManager 将设备的音量增加到最大值,但不能超过该值。
我首先使用MediaRecorder,但由于它的功能有限并且提供压缩音频,所以我尝试使用AudioRecorder。不过我还没弄清楚如何增加音频。我也查过Github上的项目,但没有用。过去两周我一直在 stackoverflow 上搜索,但根本找不到任何东西。
我非常确定这是可能的,因为许多其他应用程序正在这样做。例如自动通话记录器就可以做到这一点。
我知道我必须对音频缓冲区做一些事情,但我不太确定需要对此做什么。你能指导我吗?
Update:-
很抱歉我忘了提及我已经在使用增益了。我的代码几乎类似于排练助理(事实上我是从那里衍生出来的)。增益不会超过 10dB,并且不会使音量增加太多。我想要的是我应该能够在不把耳朵放在扬声器上的情况下收听音频,这是我的代码中所缺少的。
我在 SoundDesign SE 上问过关于音量/响度功能的类似问题here。它提到增益和响度是相关的,但它没有设置实际的响度级别。我不确定事情是如何运作的,但我决心获得响亮的音量输出。
你显然有AudioRecord
东西正在运行,所以我跳过这个决定sampleRate
and inputSource
。要点是,您需要在录音循环中适当地操作录音数据的每个样本以增加音量。就像这样:
int minRecBufBytes = AudioRecord.getMinBufferSize( sampleRate, AudioFormat.CHANNEL_IN_MONO, AudioFormat.ENCODING_PCM_16BIT );
// ...
audioRecord = new AudioRecord( inputSource, sampleRate, AudioFormat.CHANNEL_IN_MONO, AudioFormat.ENCODING_PCM_16BIT, minRecBufBytes );
// Setup the recording buffer, size, and pointer (in this case quadruple buffering)
int recBufferByteSize = minRecBufBytes*2;
byte[] recBuffer = new byte[recBufferByteSize];
int frameByteSize = minRecBufBytes/2;
int sampleBytes = frameByteSize;
int recBufferBytePtr = 0;
audioRecord.startRecording();
// Do the following in the loop you prefer, e.g.
while ( continueRecording ) {
int reallySampledBytes = audioRecord.read( recBuffer, recBufferBytePtr, sampleBytes );
int i = 0;
while ( i < reallySampledBytes ) {
float sample = (float)( recBuffer[recBufferBytePtr+i ] & 0xFF
| recBuffer[recBufferBytePtr+i+1] << 8 );
// THIS is the point were the work is done:
// Increase level by about 6dB:
sample *= 2;
// Or increase level by 20dB:
// sample *= 10;
// Or if you prefer any dB value, then calculate the gain factor outside the loop
// float gainFactor = (float)Math.pow( 10., dB / 20. ); // dB to gain factor
// sample *= gainFactor;
// Avoid 16-bit-integer overflow when writing back the manipulated data:
if ( sample >= 32767f ) {
recBuffer[recBufferBytePtr+i ] = (byte)0xFF;
recBuffer[recBufferBytePtr+i+1] = 0x7F;
} else if ( sample <= -32768f ) {
recBuffer[recBufferBytePtr+i ] = 0x00;
recBuffer[recBufferBytePtr+i+1] = (byte)0x80;
} else {
int s = (int)( 0.5f + sample ); // Here, dithering would be more appropriate
recBuffer[recBufferBytePtr+i ] = (byte)(s & 0xFF);
recBuffer[recBufferBytePtr+i+1] = (byte)(s >> 8 & 0xFF);
}
i += 2;
}
// Do other stuff like saving the part of buffer to a file
// if ( reallySampledBytes > 0 ) { ... save recBuffer+recBufferBytePtr, length: reallySampledBytes
// Then move the recording pointer to the next position in the recording buffer
recBufferBytePtr += reallySampledBytes;
// Wrap around at the end of the recording buffer, e.g. like so:
if ( recBufferBytePtr >= recBufferByteSize ) {
recBufferBytePtr = 0;
sampleBytes = frameByteSize;
} else {
sampleBytes = recBufferByteSize - recBufferBytePtr;
if ( sampleBytes > frameByteSize )
sampleBytes = frameByteSize;
}
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)