MediaCodec编码音频PCM数据为Amr数据时,出错

qq_28251907 2017-07-28 07:40:05
编码出来的数据是噪音,而且时长也不对。
下面是我的设置:
初始化操作
try {
//参数对应-> mime type、采样率、声道数
// MediaFormat encodeFormat = MediaFormat.createAudioFormat(AUDIO_AMR, 8000, 1);//参数对应-> mime type、采样率、声道数
MediaFormat encodeFormat = new MediaFormat();
encodeFormat.setString(MediaFormat.KEY_MIME, AUDIO_AMR);
encodeFormat.setInteger(MediaFormat.KEY_SAMPLE_RATE, 8000);
encodeFormat.setInteger(MediaFormat.KEY_CHANNEL_COUNT, 1);
encodeFormat.setInteger(MediaFormat.KEY_BIT_RATE, BitRate.MR795);//比特率
encodeFormat.setLong(MediaFormat.KEY_DURATION, duration);//时长
// encodeFormat.setInteger(MediaFormat.KEY_AAC_PROFILE, MediaCodecInfo.CodecProfileLevel.AACObjectLC);
encodeFormat.setInteger(MediaFormat.KEY_MAX_INPUT_SIZE, 100 * 1024);
// encodeFormat.setInteger("pcm-encoding", AudioFormat.ENCODING_PCM_16BIT);
// encodeFormat.setInteger(MediaFormat.KEY_PCM_ENCODING, AudioFormat.ENCODING_PCM_16BIT);
//比特率
// if content is AAC audio, specifies the desired profile
// encodeFormat.setInteger(MediaFormat.KEY_AAC_PROFILE, MediaCodecInfo.CodecProfileLevel.AACObjectLC);
//作用于inputBuffer的大小
mediaEncode = MediaCodec.createByCodecName(getEncoderNamesForType(AUDIO_AMR));
// mediaEncode = MediaCodec.createEncoderByType(AUDIO_AMR);
mediaEncode.configure(encodeFormat, null, null, MediaCodec.CONFIGURE_FLAG_ENCODE);
} catch (Exception e) {
e.printStackTrace();
}
mediaEncode.start();
encodeInputBuffers = mediaEncode.getInputBuffers();
encodeOutputBuffers = mediaEncode.getOutputBuffers();

//用于描述解码得到的byte[]数据的相关信息
encodeBufferInfo = new MediaCodec.BufferInfo();
byte[] header = new byte[]{0x23, 0x21, 0x41, 0x4D, 0x52, 0x0A};
bos.write(header);
LogUtils.d(TAG, "head success");
bos.flush();


编码:

for (int i = 0; i < encodeInputBuffers.length - 1; i++) {
chunkPCM = getPCMData();
if (chunkPCM == null) {
break;
}
//LogUtils.d(TAG, "读取的PCM大小: " + chunkPCM.length);
//同解码时的操作
inputIndex = mediaEncode.dequeueInputBuffer(kTimeOutUs);
if (inputIndex >= 0) {
inputBuffer = encodeInputBuffers[inputIndex];
inputBuffer.clear();
inputBuffer.limit(chunkPCM.length);
//将PCM的数据填充给inputBuffer
inputBuffer.put(chunkPCM);
// encodeTimeUs += stampTime;
//通知mediaEncode编码刚刚传入的数据
mediaEncode.queueInputBuffer(inputIndex, 0, chunkPCM.length, 0, 0);
}
}
outputIndex = mediaEncode.dequeueOutputBuffer(encodeBufferInfo, kTimeOutUs);
// LogUtils.d(TAG, "cur outIndex:" + outputIndex);
if (outputIndex == MediaCodec.INFO_OUTPUT_BUFFERS_CHANGED) {
encodeOutputBuffers = mediaEncode.getOutputBuffers();
} else if (outputIndex == MediaCodec.INFO_OUTPUT_FORMAT_CHANGED) {
// Subsequent data will conform to new format.
MediaFormat format = mediaEncode.getOutputFormat();
}
while (outputIndex >= 0) {
outBitSize = encodeBufferInfo.size;
// outPacketSize = outBitSize + 1;
outputBuffer = encodeOutputBuffers[outputIndex];//拿到输出Buffer
// TODO 这两个方法是用来干嘛的
outputBuffer.position(encodeBufferInfo.offset);
outputBuffer.limit(encodeBufferInfo.offset + outBitSize);
// chunkAudio = new byte[outPacketSize];
chunkAudio = new byte[outBitSize];
// addADTS(chunkAudio, outPacketSize);//添加ADTS 代码后面会贴上
// outputBuffer.get(chunkAudio, 1, outBitSize);//将编码得到的AAC数据 取出到byte[]中 偏移量offset=7 你懂得
outputBuffer.get(chunkAudio, 0, outBitSize);//将编码得到的AAC数据 取出到byte[]中 偏移量offset=7 你懂得
outputBuffer.position(encodeBufferInfo.offset);
try {
bos.write(chunkAudio, 0, chunkAudio.length);//BufferOutputStream 将文件保存到内存卡中 *.aac
} catch (IOException e) {
e.printStackTrace();
}
//此操作一定要做,不然MediaCodec用完所有的Buffer后 将不能向外输出数据
mediaEncode.releaseOutputBuffer(outputIndex, false);
outputIndex = mediaEncode.dequeueOutputBuffer(encodeBufferInfo, 10000);
}


以上代码有些省略,但核心的代码在这。如果我编码为AAC,在添加到ADST头,编码出来的AAC文件是正常的,不知道是哪出问题了,感谢各位帮看一下!
...全文
450 3 打赏 收藏 转发到动态 举报
写回复
用AI写文章
3 条回复
切换为时间正序
请发表友善的回复…
发表回复
qq_28251907 2017-07-28
  • 打赏
  • 举报
回复
有人帮看看吗?
qq_28251907 2017-07-28
  • 打赏
  • 举报
回复
有人知道是为什么吗
qq_28251907 2017-07-28
  • 打赏
  • 举报
回复
chuckPCM是我读取到的PCM原始数据

80,351

社区成员

发帖
与我相关
我的任务
社区描述
移动平台 Android
androidandroid-studioandroidx 技术论坛(原bbs)
社区管理员
  • Android
  • yechaoa
  • 失落夏天
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧