Вы можете расширить возможности компонентов извлечения медиаданных и медиакодека, используя расширения поставщиков. API MediaSession2 и MediaParser не поддерживают настройку (но вы можете вносить изменения в устаревшие API MediaPlayer
и MediaSession
).
Для поддержки дополнительных типов медиа в медиафреймворке Android необходимо создать собственный экстрактор и декодер . Например, чтобы добавить поддержку видео Windows Media в AVI-файлах, необходимо создать экстрактор AVI и декодер видео Windows Media.
О расширениях
Если стандартные извлекатели медиафайлов не отвечают вашим требованиям, вы можете разместить пользовательские плагины в /system/lib[64]/extractors/
. Процесс извлечения автоматически загружает плагины из предоставленного Google пакета APEX и из /system/lib[64]/extractors/
.
Аналогичным образом вы можете настроить пользовательские службы медиакодеков, использующие интерфейс Codec 2.0, определённый в frameworks/av/media/codec2/core/
. Базовую реализацию см. в frameworks/av/media/codec2/hidl/services/
. Точкой входа в библиотеку является интерфейс C2ComponentStore
. Пример реализации программного хранилища кодеков по умолчанию см. в frameworks/av/media/codec2/vndk/C2Store.cpp
.
При использовании собственного APEX структурируйте службу кодеков и загрузите файл APEX, используя те же процессы, что и для службы mediaswcodec
. Для этого определите общую библиотеку верхнего уровня, отвечающую за регистрацию всех компонентов C2, а затем создайте пакет APEX (с транзитивными зависимостями), расположенный в разделе поставщика. При запуске процесса службы кодеков поставщика он сможет загрузить эту точку входа верхнего уровня.
Создать экстрактор
При добавлении экстрактора для нового формата убедитесь, что он зависит только от стабильных API NDK и не зависит от каких-либо частных API. Экстракторы должны реализовывать API, определённое в файле frameworks/av/include/media/MediaExtractorPluginApi.h
, и могут использовать удобные обёртки C++ из frameworks/av/include/media/MediaExtractorPluginHelper.h
. Поскольку Android 10 и выше поддерживает только самую высокую версию API экстрактора, обязательно смоделируйте свой экстрактор по образцу экстрактора с самым высоким номером версии API.
Разместите пользовательские экстракторы в /system/lib/64/extractors
или в APEX-файле поставщика, который открывается вместе с APEX Google, содержащим экстракторы Google. Чтобы убедиться, что фреймворк загрузил ваш экстрактор, выполните следующую команду.
adb shell dumpsys media.extractor
Вы должны получить список доступных экстракторов, подобный следующему.
Available extractors:
AAC Extractor: plugin\_version(2), uuid(4fd80eae03d24d729eb948fa6bb54613), version(1), path(/system/lib64/extractors/libaacextractor.so)
AMR Extractor: plugin\_version(2), uuid(c86639c92f3140aca715fa01b4493aaf), version(1), path(/system/lib64/extractors/libamrextractor.so)
FLAC Extractor: plugin\_version(2), uuid(1364b048cc454fda9934327d0ebf9829), version(1), path(/system/lib64/extractors/libflacextractor.so)
MIDI Extractor: plugin\_version(2), uuid(ef6cca0af8a243e6ba5fdfcd7c9a7ef2), version(1), path(/system/lib64/extractors/libmidiextractor.so)
MP3 Extractor: plugin\_version(2), uuid(812a3f6cc8cf46deb5293774b14103d4), version(1), path(/system/lib64/extractors/libmp3extractor.so)
MP4 Extractor: plugin\_version(2), uuid(27575c6744174c548d3d8e626985a164), version(2), path(/system/lib64/extractors/libmp4extractor.so)
MPEG2-PS/TS Extractor: plugin\_version(1), uuid(3d1dcfebe40a436da574c2438a555e5f), version(1), path(/system/lib64/extractors/libmpeg2extractor.so)
Matroska Extractor: plugin\_version(2), uuid(abbedd9238c44904a4c1b3f45f899980), version(1), path(/system/lib64/extractors/libmkvextractor.so)
Ogg Extractor: plugin\_version(2), uuid(8cc5cd06f772495e8a62cba9649374e9), version(1), path(/system/lib64/extractors/liboggextractor.so)
WAV Extractor: plugin\_version(3), uuid(7d61385858374a3884c5332d1cddee27), version(1), path(/system/lib64/extractors/libwavextractor.so)
Если ваш пользовательский экстрактор поддерживает формат, который уже поддерживается экстрактором, предоставленным Google, вы можете заставить фреймворк использовать ваш экстрактор, используя функцию Sniff()
, чтобы вернуть более высокий уровень достоверности, чем предоставленный Google.
Когда медиа-фреймворк загружает ваш экстрактор (из /system/lib/64/extractors
или из APEX-сервера поставщика), он распознаёт файл и получает информацию о его содержимом. Следующий шаг — добавить декодер для этого формата, чтобы фреймворк мог понять, как анализировать содержимое файла.
Создать собственный декодер
Для любого формата, который ещё не поддерживается декодером Google, вам понадобится собственный декодер. Например:
Чтобы добавить поддержку медиафреймворка для файлов AVI, содержащих MP3, вам понадобится экстрактор AVI, но не понадобится декодер MP3, поскольку он уже существует.
Чтобы добавить поддержку медиа-фреймворка для файлов AVI, содержащих Windows Media, вам понадобится как экстрактор AVI, так и декодер Windows Media.
Добавление нового декодера аналогично добавлению собственных аппаратных декодеров для AVC или HEVC.
Хотя экстрактор публикует MIME-тип содержащихся в нём медиатреков, для полной поддержки файла необходимо наличие кодеков, поддерживающих эти MIME-типы. Фактически используемая строка MIME-типа определяется исключительно соглашением между экстрактором и кодеком (добавлять эту строку в файл MediaDefs.h
не требуется).
Интеграция с медиа-сканером
Сканер медиафайлов ищет новые типы файлов и добавляет их в базу данных медиафайлов. Чтобы сканер мог обрабатывать ваш пользовательский тип файла, ему необходимо знать о нём. В Android 10 и выше MimeUtils
(в libcore
) поддерживает сопоставление MIME-расширения. Ранее это сопоставление обрабатывалось в файле MediaFile.java
, который по-прежнему содержит сопоставление типа MIME с константами формата MTP.
Экстрактор может экспортировать список поддерживаемых им расширений файлов (например, MP3 или MP4). Однако это использует только LegacyMediaScanner
; на ModernMediaScanner
, который используется по умолчанию, это не влияет.