Android 13 представляет конфигурируемую поставщиком статическую библиотеку libtonemap
, которая определяет операции тонального отображения и используется совместно с процессом SurfaceFlinger и реализациями Hardware Composer (HWC). Эта функция позволяет OEM-производителям определять и делиться своими алгоритмами тонального отображения дисплея между фреймворком и поставщиками, уменьшая несоответствие в тональном отображении.
До Android 13 операции тонального отображения, специфичные для дисплея, не были общими между HWC, SurfaceFlinger и приложениями. В зависимости от пути рендеринга для HDR-контента это приводило к несоответствиям в качестве изображения, когда HDR-контент подвергался тональному отображению в выходном пространстве разными способами. Это было заметно в таких сценариях, как поворот экрана, когда стратегия композиции меняется между GPU и DPU, а также в различиях в поведении рендеринга между TextureView и SurfaceView.
На этой странице описываются интерфейс, настройки и детали проверки библиотеки libtonemap
.
Интерфейс к библиотеке тональной компрессии
Библиотека libtonemap
содержит реализации на базе CPU и шейдеры SkSL, которые могут быть подключены SurfaceFlinger для композиции на базе GPU и HWC для генерации таблицы поиска тональной компрессии (LUT). Точкой входа в libtonemap
является android::tonemap::getToneMapper()
, которая возвращает объект, реализующий интерфейс ToneMapper
.
Интерфейс ToneMapper
поддерживает следующие возможности:
Создание LUT-таблицы тонального отображения
Интерфейс
ToneMapper::lookupTonemapGain
— это реализация CPU шейдера, определенного вlibtonemap_LookupTonemapGain()
. Он используется модульными тестами в фреймворке и может использоваться партнерами для помощи в создании LUT тональной компрессии внутри их цветового конвейера.libtonemap_LookupTonemapGain()
принимает значения цвета в абсолютном, ненормализованном линейном пространстве, как в линейном RGB, так и в XYZ, и возвращает число с плавающей точкой, описывающее, на сколько следует умножить входные цвета в линейном пространстве.Сгенерировать шейдер SkSL
Интерфейс
ToneMapper::generateTonemapGainShaderSkSL()
возвращает строку шейдера SkSL, заданную исходным и целевым пространством данных. Шейдер SkSL подключается к реализации Skia дляRenderEngine
, компонента композитинга с ускорением на GPU для SurfaceFlinger. Шейдер также подключается кlibhwui
, так что отображение тонов HDR-SDR может быть эффективно выполнено дляTextureView
. Поскольку сгенерированная строка встроена в другие шейдеры SkSL, используемые Skia, шейдер должен соответствовать следующим правилам:- Строка шейдера должна иметь точку входа с сигнатурой
float libtonemap_LookupTonemapGain(vec3 linearRGB, vec3 xyz)
, гдеlinearRGB
— это значение абсолютных нит пикселей RGB в линейном пространстве, аxyz
— этоlinearRGB
преобразованное в XYZ. - Любые вспомогательные методы, используемые строкой шейдера, должны иметь префикс строки
libtonemap_
, чтобы определения фреймворка шейдера не конфликтовали. Аналогично, входные униформы должны иметь префиксin_libtonemap_
.
- Строка шейдера должна иметь точку входа с сигнатурой
Генерация униформы SkSL
Интерфейс
ToneMapper::generateShaderSkSLUniforms()
возвращает следующее, учитываяstruct
метаданных, описывающую метаданные из различных стандартов HDR и условий отображения:Список униформ, привязанных к шейдеру SkSL.
Равномерные значения
in_libtonemap_displayMaxLuminance
иin_libtonemap_inputMaxLuminance
. Эти значения используются фреймворковыми шейдерами при масштабировании входных данных вlibtonemap
и нормализации выходных данных по мере необходимости.
В настоящее время процесс генерации униформ не зависит от входного и выходного пространства данных.
Настройка
Референсная реализация библиотеки libtonemap
дает приемлемые результаты. Однако, поскольку алгоритм тональной компрессии, используемый композицией GPU, может отличаться от алгоритма, используемого композицией DPU, использование референсной реализации может вызвать мерцание в некоторых сценариях, таких как анимация вращения. Настройка может решить такие проблемы с качеством изображения, специфичные для поставщика.
OEM-производителям настоятельно рекомендуется переопределить реализацию libtonemap
для определения собственного подкласса ToneMapper
, который возвращается getToneMapper()
. При настройке реализации партнеры должны выполнить одно из следующих действий:
- Измените реализацию
libtonemap
напрямую. - Определить собственную статическую библиотеку, скомпилировать ее как автономную и заменить файл
.a
библиотекиlibtonemap
на файл, сгенерированный из их пользовательской библиотеки.
Поставщикам не нужно изменять какой-либо код ядра, но несколько поставщиков должны сообщать сведения об алгоритмах тонального отображения DPU для правильной реализации.
Проверка
Для проверки реализации выполните следующие действия:
Воспроизводите HDR-видео на экране любых стандартов HDR, поддерживаемых вашей системой отображения , например HLG, HDR10, HDR10+ или DolbyVision.
Переключите состав графического процессора, чтобы убедиться в отсутствии заметного пользователю мерцания.
Используйте следующую команду
adb
для переключения состава графического процессора:adb shell service call SurfaceFlinger 1008 i32 <0 to enable HWC composition, 1 to force GPU composition>
Распространенные проблемы
При данной реализации могут возникнуть следующие проблемы:
Полосы возникают, когда цель рендеринга, используемая композицией GPU, имеет более низкую точность, чем типичное значение для контента HDR. Например, полосы могут возникать, когда реализация HWC поддерживает непрозрачные 10-битные форматы для HDR, такие как RGBA1010102 или P010, но требует, чтобы композиция GPU записывала в 8-битный формат, такой как RGBA8888, для поддержки альфа.
Незначительный сдвиг цвета вызван различиями в квантовании, если DPU работает с другой точностью, чем GPU.
Каждая из этих проблем связана с относительными различиями в точности базового оборудования. Типичным решением является обеспечение шага сглаживания в путях с более низкой точностью, что делает любые различия в точности менее заметными для человека.