Запись замедленного видео с помощью MediaCodec на Android
Я осуществляю запись видео с помощью камеры Android. Я использую MediaCodec для кодирования кадров из обратного вызова onPreviewFrame().
Теперь я хочу записать замедленное видео. Как я могу установить частоту захвата камеры или частоту кадров? Где я могу установить эти параметры, например, если я хочу записывать со скоростью 120 кадров в секунду и играть со скоростью 30 кадров в секунду?
Вот что я исследовал:
Я записал видео в замедленном режиме с помощью MOTO X (со встроенной функцией записи замедленного видео) и использовал FFmpeg для проверки его fps. Я обнаружил, что записи на скорости 110 к / с (около 120 к / с) и воспроизведении на 30 к / с Это доказывает, что он обеспечивает аппаратную поддержку записи с высокой частотой кадров.
Тем не менее, когда я использую getSupportedPreviewFpsRange для проверки поддерживаемого диапазона fps, есть только 4 набора поддерживаемых диапазонов fps, ни один из которых не превышает 30 fps:
min_fps: 15.0, max_fps15.0
min_fps: 15.0, max_fps20.0
min_fps: 15.0, max_fps30.0
min_fps: 24.0, max_fps30.0
Я использовал setPreviewFpsRange, чтобы установить fps выше, но он остается не более 30fps. Я также попытался установить KEY_FRAME_RATE и KEY_CAPTURE_RATE MediaFormat. Но это все равно не работает.
Я также искал решение, установив CamcorderProfile или setVideoFrameRate с MediaRecorder. Но я делаю с MediaCodec.
Кто-нибудь может мне помочь с этой проблемой?
3 ответа
Захват видеокадров с более высокой скоростью не решает проблему. Если вы снимаете со скоростью 120 кадров в секунду и воспроизводите со скоростью 120 кадров в секунду, у вас есть высокоскоростное видео, воспроизводимое с нормальной скоростью.
Что вы хотите сделать, это изменить метки времени. MediaCodec поддерживает видео VFR (с переменной частотой кадров). Вместо того, чтобы тратить 1 секунду на запись 60 кадров, которые будут воспроизводиться со скоростью 30 кадров в секунду, вы записываете 30 кадров в секунду, которые будут воспроизводиться со скоростью 15 кадров в секунду.
Поток H.264, сгенерированный кодером AVC MediaCodec, вообще не включает временные метки. Вы указываете временную метку для каждого кадра при подаче вывода в MediaMuxer, создавая файл.mp4. В большинстве примеров кода просто берется временная метка, полученная с камеры, и она передается через MediaCodec в MediaMuxer без изменений, но вы можете настроить ее. Единственное, что вы не можете сделать, это позволить отметке времени вернуться назад.
Если вы посмотрите, как в Grafika генерируется фильм с восьмью частями, вы увидите, что он воспроизводится с выходной меткой времени, чтобы фильм проигрывался медленнее или быстрее.
Другой простой способ сделать то же самое без изменения частоты кадров - это удвоить количество кадров. Для медленной части просто передайте один и тот же кадр кодеру несколько раз. Опять же, вам нужно настроить метки времени представления для каждого кадра, но ваше видео будет иметь постоянные 30 кадров в секунду. (Это выглядело бы лучше, если бы вы интерполировали кадры, но это намного сложнее.)
Для медленной записи.
mMediaRecorder.setVideoFrameRate (QUALITY_HIGH_SPEED_LOW);
для высокоскоростной записи.
mMediaRecorder.setVideoFrameRate(QUALITY_HIGH_SPEED_HIGH);
Я думаю, что этот вопрос заключает в себе две отдельные проблемы.
- Как я могу активировать высокоскоростной режим захвата, который быстрее, чем в 60FPS?
- Как я могу замедлить FPS, генерируемый
MediaCodec
кодер?
Вторая часть проста. Как описано в этом ответе , вы можете либо вставлять интерполирующие/фиктивные кадры, либо изменять метки времени. Первая часть отличается тем, что большинство примеров кодов имеют дело с обычным режимом захвата, а не с высокоскоростным захватом, необходимым в этом случае использования (обычно выше 60 кадров в секунду, и вообще говоря, мы имеем дело со 120~240 кадрами в секунду).
Что касается первой части вопроса, я хотел бы, чтобы вы взглянули на описание ограниченных высокоскоростных API захвата Camera2, например это . К сожалению, похоже, что на такой API существует только нишевый спрос, и я не смог собрать много информации о своих собственных выводах, и в настоящее время я сам занимаюсь умственными проектами, чтобы создать образец кода самостоятельно. Однако, судя по его сходству с обычной видеозаписью и серийной съемкой , я не думаю, что получение такого варианта использования будет таким уж сложным.