MediaCodec: параметр MediaFormat, значение KEY_I_FRAME_INTERVAL игнорируется
Я использую MediaCodec в своем проекте для кодирования видео с камеры. По некоторым причинам мне нужно установить KEY_I_FRAME_INTERVAL в 0, что означает, что каждый кадр в записанном видео mp4 будет ключевым кадром (ключевой кадр содержит все изображение, а не только инкрементную разницу с предыдущим кадром).
И вот тут я сталкиваюсь с проблемой: на нексусе 10, нексусе 7, сяоми редми 2, асус зенфон 5, галактика а5 все ок. Но lenovo vibe s1 записывает ТОЛЬКО с интервалом ключевого кадра, равным 1 секунде. Независимо от того, какое значение установлено в mediaFormat, что я использую в mediaCodec.configure(). Я пытался установить 0, 1, 5, 10, но ключевой кадр в видео всегда каждые 30 кадров.
Есть идеи, как решить эту проблему?
Для получения дополнительной информации, вот моя настройка кодировщика mediaCodec:
videoCodec = MediaCodec.createEncoderByType(MIME_VIDEO_CODEC_H264);
MediaFormat videoFormat = MediaFormat.createVideoFormat(MIME_VIDEO_CODEC_H264, 1280, 720);
videoFormat.setInteger(MediaFormat.KEY_BIT_RATE, 3800000);
videoFormat.setInteger(MediaFormat.KEY_FRAME_RATE, 30);
videoFormat.setInteger(MediaFormat.KEY_COLOR_FORMAT, MediaCodecInfo.CodecCapabilities.COLOR_FormatSurface);
videoFormat.setInteger(MediaFormat.KEY_I_FRAME_INTERVAL, 0);
videoCodec.configure(videoFormat, null, null, MediaCodec.CONFIGURE_FLAG_ENCODE);
//using input surface to get input data from camera
inputSurface = new CodecInputSurface(videoCodec.createInputSurface());
videoCodec.start();
3 ответа
Этот ответ запоздалый и основан на мнении, но может быть полезен.
Что касается многих других вещей в Android, я считаю это скорее своего рода «доброй рекомендацией» кодировщику, чем строгой настройкой. Возможно, за этим API стоят сотни реализаций аппаратного кодировщика, а некоторые более «жесткие» и, вероятно, старые, возможно, не смогут использовать этот параметр, что, возможно, относится к устройству, на котором вы столкнулись с проблемой. Однако это чистое предположение.
Если ваша проблема состоит в том, чтобы увеличить частоту I-кадров в закодированном потоке, вы можете рассмотреть PARAMETER_KEY_REQUEST_SYNC_FRAME
параметр периодически передается в экземпляр MediaCodec. Если кодер поддерживает другие промежуточные режимы, кроме интервалов «ноль секунд» и «одна секунда» между I-кадрами, это может быть способом достижения более частых I-кадров (хотя и не обязательно их точной частоты).
Также стоит отметить, что начиная с Android 7.1
KEY_I_FRAME_INTERVAL
принимает значения с плавающей запятой.
Я столкнулся с той же проблемой, кажется, вам также необходимо установить значение для MediaFormat.KEY_CAPTURE_RATE, и тогда MediaFormat.KEY_I_FRAME_INTERVAL будет соблюдаться.
Вы должны установить KEY_I_FRAME_INTERVAL на 1, что означает один ключевой кадр на KEY_FRAME_RATE.