Инструкции

Высокоскоростная съемка и замедленная видеосъемка с помощью CameraX 1.5

Чтение займет 6 минут.
Leo Huang
Программист

Четкая съемка динамичных сцен — ключевая функция современных приложений для камер. Это достигается за счет высокоскоростной съемки — процесса получения кадров со скоростью 120 или 240 кадров в секунду. Такая высококачественная съемка может использоваться для двух целей: создания видео с высокой частотой кадров для детального покадрового анализа или создания замедленного видео , где действие эффектно разворачивается на экране.

Ранее реализация этих функций с помощью API Camera2 требовала больше ручного труда. Теперь, с новым высокоскоростным API в CameraX 1.5, весь процесс упрощен, предоставляя вам возможность создавать как видео с высокой частотой кадров, так и готовые к воспроизведению замедленные клипы. В этой статье мы покажем вам, как освоить оба варианта. Тем, кто только начинает знакомиться с CameraX, рекомендуем ознакомиться собзором CameraX .


Принцип замедленной съемки

Основной принцип замедленной съемки заключается в том, чтобы записывать видео с гораздо большей частотой кадров, чем оно воспроизводится. Например, если вы запишете событие длительностью в одну секунду со скоростью 120 кадров в секунду (fps) , а затем воспроизведете эту запись со стандартной частотой 30 кадров в секунду, воспроизведение видео займет четыре секунды. Именно это «растяжение» времени создает впечатляющий эффект замедленной съемки, позволяя увидеть детали, которые слишком быстро мелькают для невооруженного глаза.

Для обеспечения плавности и непрерывности конечного видеоряда его обычно следует рендерить с частотой не менее 30 кадров в секунду. Это означает, что для создания видео с 4-кратным замедлением исходная частота кадров захвата должна составлять не менее 120 кадров в секунду (120 кадров в секунду захвата ÷ 4 = 30 кадров в секунду воспроизведения).

После того, как видеозапись с высокой частотой кадров будет сделана, существует два основных способа достижения желаемого результата:

  • Замедленная съемка (видео с высокой частотой кадров) с помощью проигрывателя: высокоскоростная запись (например, 120 кадров в секунду) сохраняется непосредственно в виде видеофайла с высокой частотой кадров. Затем проигрыватель отвечает за замедление скорости воспроизведения. Это дает пользователю возможность переключаться между обычным и замедленным воспроизведением.
  • Видео в замедленном режиме (перекодированное видео) готово к воспроизведению: высокоскоростной видеопоток обрабатывается и перекодируется в файл со стандартной частотой кадров (например, 30 кадров в секунду). Эффект замедления «встраивается» путем корректировки временных меток кадров. Полученное видео будет воспроизводиться в замедленном режиме в любом стандартном видеоплеере без специальной обработки. Хотя видео воспроизводится в замедленном режиме по умолчанию, видеоплееры могут предоставлять элементы управления скоростью воспроизведения, позволяющие пользователю увеличить скорость и смотреть видео с исходной скоростью.

API CameraX упрощает этот процесс, предоставляя единый способ выбора нужного подхода, как вы увидите ниже.


Новый API для высокоскоростного видео

Новое решение CameraX построено на двух основных компонентах:

  • Recorder#getHighSpeedVideoCapabilities(CameraInfo) : Этот метод позволяет проверить, может ли камера записывать видео на высокой скорости и, если да, то какие разрешения (объекты Quality ) поддерживаются.
  • HighSpeedVideoSessionConfig : Это специальный объект конфигурации, который объединяет сценарии использования VideoCapture и Preview , указывая CameraX на необходимость создания единого высокоскоростного сеанса съемки. Обратите внимание, что, хотя поток VideoCapture будет работать с настроенной высокой частотой кадров, поток Preview обычно будет ограничен стандартной частотой не менее 30 кадров в секунду системой камеры для обеспечения плавного отображения на экране.

Начиная

Прежде чем начать, убедитесь, что вы добавили необходимые зависимости CameraX в файл build.gradle.kts вашего приложения. Вам понадобится артефакт camera-video вместе с основными библиотеками CameraX.

// build.gradle.kts (Module: app)

dependencies {

    val camerax_version = "1.5.1"


    implementation("androidx.camera:camera-core:$camerax_version")

    implementation("androidx.camera:camera-camera2:$camerax_version")

    implementation("androidx.camera:camera-lifecycle:$camerax_version")

    implementation("androidx.camera:camera-video:$camerax_version")

    implementation("androidx.camera:camera-view:$camerax_version")

}

Примечание об экспериментальных API

Важно отметить, что API для высокоскоростной записи в настоящее время являются экспериментальными. Это означает, что в будущих версиях они могут быть изменены. Для их использования необходимо активировать эту функцию, добавив в код следующую аннотацию:

@kotlin.OptIn(ExperimentalSessionConfig::class, ExperimentalHighSpeedVideo::class)

Выполнение

Реализация обоих вариантов начинается с одинаковых шагов настройки. Выбор между созданием видео с высокой частотой кадров или замедленного видео сводится к одной-единственной настройке.

1. Настройка высокоскоростной съемки

Во-первых, независимо от вашей цели, вам необходимо получить объект ProcessCameraProvider , проверить возможности устройства и создать сценарии использования.

Следующий блок кода демонстрирует полный процесс настройки внутри функции приостановки. Вы можете вызвать эту функцию из области видимости сопрограммы, например, lifecycleScope.launch .

// Add the OptIn annotation at the top of your function or class

@kotlin.OptIn(ExperimentalSessionConfig::class, ExperimentalHighSpeedVideo::class)

private suspend fun setupCamera() {

    // Asynchronously get the CameraProvider

    val cameraProvider = ProcessCameraProvider.awaitInstance(this)



    // -- CHECK CAPABILITIES --

    val cameraInfo = cameraProvider.getCameraInfo(CameraSelector.DEFAULT_BACK_CAMERA)

    val videoCapabilities = Recorder.getHighSpeedVideoCapabilities(cameraInfo)

    if (videoCapabilities == null) {

        // This camera device does not support high-speed video.

        return

    }




    // -- CREATE USE CASES --

    val preview = Preview.Builder().build()    


    // You can create a Recorder with default settings.

    // CameraX will automatically select a suitable quality.

    val recorder = Recorder.Builder().build()


    // Alternatively, to use a specific resolution, you can configure the
    // Recorder with a QualitySelector. This is useful if your app has
    // specific resolution requirements or you want to offer user
    // preferences. 

    // To use a specific quality, you can uncomment the following lines.

    // Get the list of qualities supported for high-speed video. 

    // val supportedQualities = videoCapabilities.getSupportedQualities(DynamicRange.SDR)

    // Build the Recorder using the quality from the supported list.

    // val recorderWithQuality = Recorder.Builder()

    //     .setQualitySelector(QualitySelector.from(supportedQualities.first()))

    //     .build()



    // Create the VideoCapture use case, using either recorder or recorderWithQuality

    val videoCapture = VideoCapture.withOutput(recorder)

    // Now you are ready to configure the session for your desired output...

}

2. Выбор выходных данных

Теперь вы решаете, какой тип видео хотите создать. Этот код будет выполняться внутри функции setupCamera() suspend показанной выше.

Вариант А: Создание видео с высокой частотой кадров

Выберите этот вариант, если хотите, чтобы итоговый файл имел высокую частоту кадров (например, видео 120 кадров в секунду).

// Create a builder for the high-speed session

val sessionConfigBuilder = HighSpeedVideoSessionConfig.Builder(videoCapture)

    .setPreview(preview)


// Query and apply a supported frame rate. Common supported frame rates include 120 and 240 fps.

val supportedFrameRateRanges =

    cameraInfo.getSupportedFrameRateRanges(sessionConfigBuilder.build())


sessionConfigBuilder.setFrameRateRange(supportedFrameRateRanges.first())

Вариант Б: Создание готового к воспроизведению замедленного видео.

Выберите этот вариант, если хотите, чтобы видео автоматически воспроизводилось в замедленном режиме в любом стандартном видеоплеере.

// Create a builder for the high-speed session

val sessionConfigBuilder = HighSpeedVideoSessionConfig.Builder(videoCapture)

    .setPreview(preview)



// This is the key: enable automatic slow-motion!

sessionConfigBuilder.setSlowMotionEnabled(true)



// Query and apply a supported frame rate. Common supported frame rates include 120, 240, and 480 fps.

val supportedFrameRateRanges =

   cameraInfo.getSupportedFrameRateRanges(sessionConfigBuilder.build())

sessionConfigBuilder.setFrameRateRange(supportedFrameRateRanges.first())

Этот единственный флаг является ключом к созданию готового к воспроизведению замедленного видео. Когда setSlowMotionEnabled имеет значение true, CameraX обрабатывает высокоскоростной поток и сохраняет его как стандартный видеофайл с частотой 30 кадров в секунду . Скорость замедленного воспроизведения определяется соотношением частоты кадров захвата к этой стандартной частоте воспроизведения.

Например:

  • Запись со скоростью 120 кадров в секунду приведет к воспроизведению видео со скоростью в 1/4 раза выше (120 ÷ 30 = 4).
  • Запись со скоростью 240 кадров в секунду позволит получить видео, которое будет воспроизводиться со скоростью в 1/8 раза выше (240 ÷ 30 = 8).

Подведение итогов: запись видео

После настройки HighSpeedVideoSessionConfig и привязки его к жизненному циклу, последним шагом является начало записи. Процесс подготовки параметров вывода, начала записи и обработки видеособытий аналогичен стандартному захвату видео.

В этой статье основное внимание уделяется высокоскоростной настройке, поэтому мы не будем подробно рассматривать процесс записи. Подробное руководство по всем аспектам, от подготовки объекта FileOutputOptions или MediaStoreOutputOptions до обработки коллбэков VideoRecordEvent , вы найдете в документации VideoCapture .

// Bind the session config to the lifecycle

cameraProvider.bindToLifecycle(

    this as LifecycleOwner,

    CameraSelector.DEFAULT_BACK_CAMERA,

    sessionConfigBuilder.build() // Bind the config object from Option A or B

)



// Start the recording using the VideoCapture use case

val recording = videoCapture.output

    .prepareRecording(context, outputOptions) // See docs for creating outputOptions

    .start(ContextCompat.getMainExecutor(context)) { recordEvent ->

        // Handle recording events (e.g., Start, Pause, Finalize)

    }

Поддержка замедленной съемки в Google Фото

При включении setSlowMotionEnabled(true) в CameraX полученный видеофайл мгновенно распознается и воспроизводится как замедленное видео в стандартных видеоплеерах и приложениях галереи. В частности, Google Photos предлагает расширенные возможности для таких замедленных видео, если частота кадров захвата составляет 120, 240, 360, 480 или 960 кадров в секунду:

  • Уникальное распознавание элементов пользовательского интерфейса на миниатюрах: в вашей библиотеке Google Фото замедленные видеоролики можно идентифицировать по определенным элементам пользовательского интерфейса, отличающим их от обычных видео.
normal.png
  • Регулировка скорости воспроизведения сегментов: при воспроизведении замедленного видео Google Photos предоставляет элементы управления для настройки того, какие части видео воспроизводятся с замедленной скоростью, а какие — с нормальной, предоставляя пользователям возможность творческого контроля. Отредактированное видео затем можно экспортировать в новый видеофайл с помощью кнопки «Поделиться» , сохранив при этом заданные вами сегменты замедленного воспроизведения.
normal2.png

Примечание о поддержке устройств

Высокоскоростной API CameraX использует базовую систему Android CamcorderProfile для определения поддерживаемых устройством разрешений и частоты кадров высокоскоростной видеозаписи. Профили CamcorderProfile проверяются с помощью набора тестов совместимости Android (CTS) , что позволяет быть уверенным в заявленных устройством возможностях видеозаписи.

Это означает, что возможность устройства записывать замедленное видео с помощью встроенного приложения камеры не гарантирует работоспособность высокоскоростного API CameraX. Это несоответствие возникает из-за того, что производители устройств отвечают за заполнение записей CamcorderProfile в прошивке своих устройств, и иногда необходимые высокоскоростные профили, такие как CamcorderProfile.QUALITY_HIGH_SPEED_1080P и CamcorderProfile.QUALITY_HIGH_SPEED_720P , не включены. Если эти профили отсутствуют, Recorder.getHighSpeedVideoCapabilities() вернет null .

Поэтому крайне важно всегда использовать Recorder.getHighSpeedVideoCapabilities() для программной проверки поддерживаемых функций, поскольку это наиболее надежный способ обеспечить стабильную работу на разных устройствах. Если вы попытаетесь привязать HighSpeedVideoSessionConfig к устройству, где Recorder.getHighSpeedVideoCapabilities() возвращает null, операция завершится ошибкой IllegalArgumentException . Вы можете подтвердить поддержку на устройствах Google Pixel , поскольку они постоянно включают эти высокоскоростные профили. Кроме того, различные устройства других производителей, такие как Motorola Edge 30, OPPO Find N2 Flip и Sony Xperia 1 V, также поддерживают возможности высокоскоростной видеосъемки.


Заключение

API высокоскоростной видеосъемки CameraX одновременно мощный и гибкий. Независимо от того, нужна ли вам видеосъемка с высокой частотой кадров для технического анализа или вы хотите добавить в свое приложение кинематографические эффекты замедленной съемки, HighSpeedVideoSessionConfig предоставляет унифицированное и простое решение. Понимая роль флага setSlowMotionEnabled , вы можете легко поддерживать оба варианта использования и предоставить своим пользователям больше творческого контроля.

    Автор:

    Продолжить чтение