Реализовать темную тему

Попробуйте способ создания
Jetpack Compose — рекомендуемый набор инструментов пользовательского интерфейса для Android. Узнайте, как работать с темами в Compose.

Рисунок 1. Темная тема.

Темная тема доступна в Android 10 (уровень API 29) и выше. Он имеет следующие преимущества:

  • Значительно снижает энергопотребление в зависимости от технологии экрана устройства.
  • Улучшает видимость для пользователей со слабым зрением и тех, кто чувствителен к яркому свету.
  • Облегчает использование устройства в условиях низкой освещенности.

Темная тема применяется к пользовательскому интерфейсу системы Android и приложениям, работающим на устройстве.

Есть три способа включить темную тему в Android 10 и выше:

  • Используйте системные настройки, перейдя в «Настройки» > «Дисплей» > «Тема», чтобы включить темную тему.
  • Используйте плитку «Быстрые настройки» для переключения тем из панели уведомлений, если она включена.
  • На устройствах Pixel включите режим экономии заряда батареи, чтобы одновременно включить темную тему. Другие устройства могут не поддерживать такое поведение.

Инструкции по применению темной темы к веб-контенту с помощью компонента WebView см. в разделе Затемнение веб-контента в WebView .

Поддержка темной темы в вашем приложении

Чтобы поддерживать темную тему, настройте тему вашего приложения — обычно находящуюся в res/values/styles.xml — наследующую от темы DayNight :

<style name="AppTheme" parent="Theme.AppCompat.DayNight">

Вы также можете использовать темную тему «Компоненты материала» :

<style name="AppTheme" parent="Theme.MaterialComponents.DayNight">

Это связывает основную тему приложения с флагами ночного режима, управляемыми системой, и дает приложению темную тему по умолчанию, когда она включена.

Темы и стили

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

Для темной темы наиболее важны два атрибута темы:

  • ?android:attr/textColorPrimary : цвет текста общего назначения. Он почти черный в светлой теме и почти белый в темной. Он содержит отключенное состояние.
  • ?attr/colorControlNormal : цвет значка общего назначения. Он содержит отключенное состояние.

Мы рекомендуем использовать Material Design Components , поскольку его система цветовых тем , такая как атрибуты темы ?attr/colorSurface и ?attr/colorOnSurface , обеспечивает легкий доступ к подходящим цветам. Вы можете настроить эти атрибуты в своей теме.

Изменение тем в приложении

Вы можете разрешить пользователям менять тему приложения во время его работы. Ниже приведены рекомендуемые варианты:

  • Свет
  • Темный
  • Системная настройка по умолчанию (рекомендуемый вариант по умолчанию)

Эти параметры напрямую соответствуют режимам AppCompat.DayNight :

Чтобы переключить тему, сделайте следующее:

  • На уровне API 31 и выше используйте UiModeManager#setApplicationNightMode чтобы сообщить системе, какую тему использует ваше приложение. Это позволяет системе соответствовать теме во время заставки.

  • На уровне API 30 и ниже используйте AppCompatDelegate.setDefaultNightMode() для переключения темы.

Сила Тьмы

Android 10 предоставляет Force Dark — функцию, позволяющую разработчикам быстро реализовать темную тему без явной установки темы DayNight .

Force Dark анализирует каждый просмотр вашего приложения со светлой темой и автоматически применяет темную тему перед ее отображением на экране. Вы можете использовать сочетание Force Dark и встроенной реализации, чтобы сократить время, необходимое для реализации темной темы.

Приложения должны включить Force Dark, установив android:forceDarkAllowed="true" в теме действия. Этот атрибут установлен для всех световых тем, предоставляемых системой и AndroidX, таких как Theme.Material.Light . Когда вы используете Force Dark, тщательно протестируйте свое приложение и при необходимости исключите просмотры.

Если ваше приложение использует темную тему, например Theme.Material ), Force Dark не применяется. Аналогично, если тема вашего приложения наследуется от темы DayNight , Force Dark не применяется из-за автоматического переключения темы.

Отключить Force Dark на представлении

Force Dark можно контролировать в определенных представлениях с помощью атрибута макета android:forceDarkAllowed или с помощью setForceDarkAllowed() .

Веб-контент

Информацию об использовании темных тем в веб-контенте см. в разделе Затемнение веб-контента в WebView . Пример темной темы, примененной к WebView, см. в демонстрации WebView на GitHub .

Лучшие практики

В следующих разделах представлены рекомендации по реализации темных тем.

Уведомления и виджеты

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

Уведомления

Используйте предоставленные системой шаблоны уведомлений, такие как MessagingStyle . Это означает, что система несет ответственность за применение правильного стиля представления.

Виджеты и пользовательские представления уведомлений

Для виджетов запуска или если ваше приложение использует настраиваемые представления содержимого уведомлений, протестируйте содержимое как на светлой, так и на темной темах.

Общие ошибки, на которые следует обратить внимание, включают следующее:

  • Предполагая, что цвет фона всегда светлый.
  • Жесткое кодирование цветов текста.
  • Установка жестко запрограммированного цвета фона при использовании цвета текста по умолчанию.
  • Использование рисуемого значка статического цвета.

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

Экраны запуска

Если у вашего приложения есть собственный экран запуска, возможно, вам придется изменить его, чтобы он отражал выбранную тему.

Удалите все жестко запрограммированные цвета, например цвета фона, программно установленные на белый цвет. Вместо этого используйте атрибут темы ?android:attr/colorBackground .

Изменения конфигурации

Когда тема приложения меняется либо через системные настройки, либо через AppCompat, это вызывает изменение конфигурации uiMode . Это означает, что действия автоматически воссоздаются.

В некоторых случаях вам может потребоваться, чтобы приложение обрабатывало изменение конфигурации. Например, вы можете захотеть отложить изменение конфигурации, поскольку воспроизводится видео.

Приложение может реализовать реализацию темной темы, заявив, что каждое Activity может обрабатывать изменение конфигурации uiMode :

<activity
    android:name=".MyActivity"
    android:configChanges="uiMode" />

Когда Activity объявляет, что оно обрабатывает изменения конфигурации, его метод onConfigurationChanged() вызывается при изменении темы.

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

Котлин

val currentNightMode = configuration.uiMode and Configuration.UI_MODE_NIGHT_MASK
when (currentNightMode) {
    Configuration.UI_MODE_NIGHT_NO -> {} // Night mode is not active, we're using the light theme.
    Configuration.UI_MODE_NIGHT_YES -> {} // Night mode is active, we're using dark theme.
}

Ява

int currentNightMode = configuration.uiMode & Configuration.UI_MODE_NIGHT_MASK;
switch (currentNightMode) {
    case Configuration.UI_MODE_NIGHT_NO:
        // Night mode is not active, we're using the light theme
        break;
    case Configuration.UI_MODE_NIGHT_YES:
        // Night mode is active, we're using dark theme
        break;
}