这几天做android的摄像头录像的工作,遇到的坑一个接一个。留点记录给有缘人。
网上有前人写过避坑指南,避坑指北,那我就指下东吧,也许后续会有其他人来指西,一桌麻将齐了,^_^
网上的很多示例都采用同步方式dequeueInputBuffer/dequeueOutputBuffer,但见doc里面建议采用的是异步方式(setCallback(new MediaCodec.Callback(...)),于是毫不犹豫地选择了异步,现在想想都是泪。
进入正题:
1, 误区:保存关键帧时,在其前面附加配置帧(MediaCodec.BufferInfo.flags == BUFFER_FLAG_CODEC_CONFIG) 后再保存。 实际情况:不用加,直接将关键帧输入给MediaMuxer.writeSampleData()进行保存。 2, 使用异步方法录像时(MediaCodec.setCallback(new MediaCodec.Callback()),MediaMuxer.stop()时会报告 E/MPEG4Writer: Missing codec specific data 解决方法:使用MediaMuxer.addTrack()的Format必须使用onOutputFormatChanged()传入的format,其中带有csd-0, csd-1信息, 或者自己构造带该信息的Format对象,否则MediaMuxer.stop()时会报告异常: E/MPEG4Writer: Missing codec specific data 3, MediaCodec.queueInputBuffer()时间戳设置不对导致录像文件播放时间不是实际的录像时间 解决方法: MediaCodec.Callback.onInputBufferAvailable(),如果当前没有等待录制的帧,则输入空数据: MediaCodec.queueInputBuffer(inputBufferId, 0, 0, 0, 0); 否则,输入有效帧 mMediaCodec.queueInputBuffer(inputBufferId, 0, length, (System.nanoTime() - mStartTime) / 1000, 0); mStartTime为录像开始时的System.nanoTime() 4, doc中指示图像格式MediaCodecInfo.CodecCapabilities.COLOR_FormatYUV420SemiPlanar已经弃用, 新的代替类型是COLOR_FormatYUV420Flexible。 实际情况:选择COLOR_FormatYUV420Flexible会导致颜色通道被忽略,只剩下灰色通道。 应该还是使用COLOR_FormatYUV420SemiPlanar。 5, 录像文件的图像颜色不正确。 解决方法:帧数据没有做nv21转nv12的格式转换。具体怎么转网上有很多说明,不详述。