Когда отменять темный режим в жизненном цикле активности?

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

Исходя из этого, я использую тему, унаследованную от DayNight:

В манифесте:

<application
    android:theme="@style/Theme.MyApp"
</application>

В themes.xml:

<style name="Theme.MyApp" parent="Theme.MaterialComponents.DayNight.NoActionBar">
    <item name="colorPrimary">@color/colorPrimary</item>
    <item name="colorPrimaryDark">@color/colorPrimaryDark</item>
    <item name="colorButtonNormal">@color/colorButtonNormal</item>
</style>

Это дает желаемый эффект открытия Activity в светлой или темной теме в зависимости от системных настроек устройства.

Но я хочу дать пользователю возможность переопределить режим, например, всегда быть темным (даже если система находится в светлом режиме).

Но когда система находится в светлом режиме, я обнаруживаю, что мое Activity изначально открывается со светлой темой (вспышка белого цвета), прежде чем я получу возможность переключиться на темную тему. Я переключаюсь, как только могу, в жизненном цикле Activity:

@Override
protected void onCreate(Bundle savedInstanceState) {
    AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_YES);
    super.onCreate(savedInstanceState);
    // ...

Но даже тогда я получаю раздражающую "вспышку света" перед тем, как Activity переключается на темноту.

Как избежать вспышки света?

1 ответ

Из этого проекта я научился тому, как все делать правильно.

В приведенном выше примере приложения они задают одну тему в манифесте, но хитроумно эта тема переопределяется в night вариант темы:

В src/main/res/values/themes.xml:

<style name="Base.MaterialGallery" parent="Theme.MaterialComponents.DayNight.DarkActionBar">
    ... some base styling ...
</style>

<style name="Theme.MaterialGallery" parent="Base.MaterialGallery">
    ... styling specific to LIGHT theme ...
</style>

<style name="Theme.MaterialGallery.DayNight" parent="Theme.MaterialGallery" />

Последний из вышеперечисленных - это то, что установлено в Манифесте:

<application
    android:name=".MaterialGalleryApplication"
    android:allowBackup="false"
    android:icon="@mipmap/ic_launcher"
    android:label="@string/app_name"
    android:roundIcon="@mipmap/ic_launcher"
    android:supportsRtl="true"
    android:theme="@style/Theme.MaterialGallery.DayNight"
    tools:ignore="GoogleAppIndexingWarning">

Хитроумно DayNight тема переопределена для темного режима в src/main/res/values-night/themes.xml:

<style name="Theme.MaterialGallery.DayNight" parent="Theme.MaterialGallery">
    ... styling specific to DARK theme (since we're in the NIGHT values-night/themes.xml ...
</style>

Указав DayNight тема в манифесте, вы получаете нужную тему сразу после запуска Activity, без каких-либо проблем.

Другие вопросы по тегам