Fix incorrect restarting and theming when system changes night mode.

fork-5.53.8
Cody Henthorne 2020-11-13 14:39:00 -05:00 zatwierdzone przez GitHub
rodzic 2a193ef455
commit 4ecfee292e
Nie znaleziono w bazie danych klucza dla tego podpisu
ID klucza GPG: 4AEE18F83AFDEB23
5 zmienionych plików z 65 dodań i 18 usunięć

Wyświetl plik

@ -12,10 +12,13 @@ import android.view.WindowManager;
import androidx.annotation.NonNull; import androidx.annotation.NonNull;
import androidx.appcompat.app.ActionBar; import androidx.appcompat.app.ActionBar;
import androidx.appcompat.app.AppCompatActivity; import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.app.AppCompatDelegate;
import androidx.core.app.ActivityCompat; import androidx.core.app.ActivityCompat;
import androidx.core.app.ActivityOptionsCompat; import androidx.core.app.ActivityOptionsCompat;
import org.thoughtcrime.securesms.logging.Log; import org.thoughtcrime.securesms.logging.Log;
import org.thoughtcrime.securesms.util.ConfigurationUtil;
import org.thoughtcrime.securesms.util.ContextUtil;
import org.thoughtcrime.securesms.util.TextSecurePreferences; import org.thoughtcrime.securesms.util.TextSecurePreferences;
import org.thoughtcrime.securesms.util.WindowUtil; import org.thoughtcrime.securesms.util.WindowUtil;
import org.thoughtcrime.securesms.util.dynamiclanguage.DynamicLanguageContextWrapper; import org.thoughtcrime.securesms.util.dynamiclanguage.DynamicLanguageContextWrapper;
@ -75,17 +78,20 @@ public abstract class BaseActivity extends AppCompatActivity {
} }
@Override @Override
protected void attachBaseContext(Context newBase) { protected void attachBaseContext(@NonNull Context newBase) {
super.attachBaseContext(newBase); super.attachBaseContext(newBase);
Configuration configuration = new Configuration(); Configuration configuration = new Configuration(newBase.getResources().getConfiguration());
configuration.uiMode = (configuration.uiMode & ~Configuration.UI_MODE_NIGHT_MASK) | getDelegate().getLocalNightMode(); int appCompatNightMode = getDelegate().getLocalNightMode() != AppCompatDelegate.MODE_NIGHT_UNSPECIFIED ? getDelegate().getLocalNightMode()
: AppCompatDelegate.getDefaultNightMode();
configuration.uiMode = (configuration.uiMode & ~Configuration.UI_MODE_NIGHT_MASK) | mapNightModeToConfigurationUiMode(newBase, appCompatNightMode);
applyOverrideConfiguration(configuration); applyOverrideConfiguration(configuration);
} }
@Override @Override
public void applyOverrideConfiguration(Configuration overrideConfiguration) { public void applyOverrideConfiguration(@NonNull Configuration overrideConfiguration) {
DynamicLanguageContextWrapper.prepareOverrideConfiguration(this, overrideConfiguration); DynamicLanguageContextWrapper.prepareOverrideConfiguration(this, overrideConfiguration);
super.applyOverrideConfiguration(overrideConfiguration); super.applyOverrideConfiguration(overrideConfiguration);
} }
@ -97,4 +103,13 @@ public abstract class BaseActivity extends AppCompatActivity {
public final @NonNull ActionBar requireSupportActionBar() { public final @NonNull ActionBar requireSupportActionBar() {
return Objects.requireNonNull(getSupportActionBar()); return Objects.requireNonNull(getSupportActionBar());
} }
private static int mapNightModeToConfigurationUiMode(@NonNull Context context, @AppCompatDelegate.NightMode int appCompatNightMode) {
if (appCompatNightMode == AppCompatDelegate.MODE_NIGHT_YES) {
return Configuration.UI_MODE_NIGHT_YES;
} else if (appCompatNightMode == AppCompatDelegate.MODE_NIGHT_NO) {
return Configuration.UI_MODE_NIGHT_NO;
}
return ConfigurationUtil.getNightModeConfiguration(context.getApplicationContext());
}
} }

Wyświetl plik

@ -1,6 +1,7 @@
package org.thoughtcrime.securesms.util; package org.thoughtcrime.securesms.util;
import android.content.Context; import android.content.Context;
import android.content.res.Configuration;
import android.view.LayoutInflater; import android.view.LayoutInflater;
import android.view.View; import android.view.View;
import android.view.ViewGroup; import android.view.ViewGroup;
@ -50,7 +51,7 @@ public class CachedInflater {
@MainThread @MainThread
@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
public <V extends View> V inflate(@LayoutRes int layoutRes, @Nullable ViewGroup parent, boolean attachToRoot) { public <V extends View> V inflate(@LayoutRes int layoutRes, @Nullable ViewGroup parent, boolean attachToRoot) {
View cached = ViewCache.getInstance().pull(layoutRes, ContextUtil.getNightModeConfiguration(context)); View cached = ViewCache.getInstance().pull(layoutRes, context.getResources().getConfiguration());
if (cached != null) { if (cached != null) {
if (parent != null && attachToRoot) { if (parent != null && attachToRoot) {
parent.addView(cached); parent.addView(cached);
@ -84,9 +85,9 @@ public class CachedInflater {
private final Map<Integer, List<View>> cache = new HashMap<>(); private final Map<Integer, List<View>> cache = new HashMap<>();
private long lastClearTime; private long lastClearTime;
private int nightModeConfiguration;
private int nightModeConfiguration; private float fontScale;
static ViewCache getInstance() { static ViewCache getInstance() {
return INSTANCE; return INSTANCE;
@ -94,10 +95,14 @@ public class CachedInflater {
@MainThread @MainThread
void cacheUntilLimit(@NonNull Context context, @LayoutRes int layoutRes, @Nullable ViewGroup parent, int limit) { void cacheUntilLimit(@NonNull Context context, @LayoutRes int layoutRes, @Nullable ViewGroup parent, int limit) {
int currentNightModeConfiguration = ContextUtil.getNightModeConfiguration(context); Configuration configuration = context.getResources().getConfiguration();
if (nightModeConfiguration != currentNightModeConfiguration) { int currentNightModeConfiguration = ConfigurationUtil.getNightModeConfiguration(configuration);
float currentFontScale = ConfigurationUtil.getFontScale(configuration);
if (nightModeConfiguration != currentNightModeConfiguration || fontScale != currentFontScale) {
clear(); clear();
nightModeConfiguration = currentNightModeConfiguration; nightModeConfiguration = currentNightModeConfiguration;
fontScale = currentFontScale;
} }
AsyncLayoutInflater inflater = new AsyncLayoutInflater(context); AsyncLayoutInflater inflater = new AsyncLayoutInflater(context);
@ -125,8 +130,8 @@ public class CachedInflater {
} }
@MainThread @MainThread
@Nullable View pull(@LayoutRes int layoutRes, int nightModeConfiguration) { @Nullable View pull(@LayoutRes int layoutRes, @NonNull Configuration configuration) {
if (this.nightModeConfiguration != nightModeConfiguration) { if (this.nightModeConfiguration != ConfigurationUtil.getNightModeConfiguration(configuration) || this.fontScale != ConfigurationUtil.getFontScale(configuration)) {
clear(); clear();
return null; return null;
} }

Wyświetl plik

@ -0,0 +1,23 @@
package org.thoughtcrime.securesms.util;
import android.content.Context;
import android.content.res.Configuration;
import androidx.annotation.NonNull;
public final class ConfigurationUtil {
private ConfigurationUtil() {}
public static int getNightModeConfiguration(@NonNull Context context) {
return getNightModeConfiguration(context.getResources().getConfiguration());
}
public static int getNightModeConfiguration(@NonNull Configuration configuration) {
return configuration.uiMode & Configuration.UI_MODE_NIGHT_MASK;
}
public static float getFontScale(@NonNull Configuration configuration) {
return configuration.fontScale;
}
}

Wyświetl plik

@ -1,7 +1,6 @@
package org.thoughtcrime.securesms.util; package org.thoughtcrime.securesms.util;
import android.content.Context; import android.content.Context;
import android.content.res.Configuration;
import android.graphics.drawable.Drawable; import android.graphics.drawable.Drawable;
import androidx.annotation.DrawableRes; import androidx.annotation.DrawableRes;
@ -17,7 +16,4 @@ public final class ContextUtil {
return Objects.requireNonNull(ContextCompat.getDrawable(context, drawable)); return Objects.requireNonNull(ContextCompat.getDrawable(context, drawable));
} }
public static int getNightModeConfiguration(@NonNull Context context) {
return context.getResources().getConfiguration().uiMode & Configuration.UI_MODE_NIGHT_MASK;
}
} }

Wyświetl plik

@ -10,9 +10,12 @@ import androidx.annotation.StyleRes;
import androidx.appcompat.app.AppCompatDelegate; import androidx.appcompat.app.AppCompatDelegate;
import org.thoughtcrime.securesms.R; import org.thoughtcrime.securesms.R;
import org.thoughtcrime.securesms.logging.Log;
public class DynamicTheme { public class DynamicTheme {
private static final String TAG = Log.tag(DynamicTheme.class);
public static final String DARK = "dark"; public static final String DARK = "dark";
public static final String LIGHT = "light"; public static final String LIGHT = "light";
public static final String SYSTEM = "system"; public static final String SYSTEM = "system";
@ -24,18 +27,20 @@ public class DynamicTheme {
public void onCreate(@NonNull Activity activity) { public void onCreate(@NonNull Activity activity) {
int previousGlobalConfiguration = globalNightModeConfiguration; int previousGlobalConfiguration = globalNightModeConfiguration;
onCreateNightModeConfiguration = ContextUtil.getNightModeConfiguration(activity); onCreateNightModeConfiguration = ConfigurationUtil.getNightModeConfiguration(activity);
globalNightModeConfiguration = onCreateNightModeConfiguration; globalNightModeConfiguration = onCreateNightModeConfiguration;
activity.setTheme(getTheme()); activity.setTheme(getTheme());
if (previousGlobalConfiguration != globalNightModeConfiguration) { if (previousGlobalConfiguration != globalNightModeConfiguration) {
Log.d(TAG, "Previous night mode has changed previous: " + previousGlobalConfiguration + " now: " + globalNightModeConfiguration);
CachedInflater.from(activity).clear(); CachedInflater.from(activity).clear();
} }
} }
public void onResume(@NonNull Activity activity) { public void onResume(@NonNull Activity activity) {
if (onCreateNightModeConfiguration != ContextUtil.getNightModeConfiguration(activity)) { if (onCreateNightModeConfiguration != ConfigurationUtil.getNightModeConfiguration(activity)) {
Log.d(TAG, "Create configuration different from current previous: " + onCreateNightModeConfiguration + " now: " + ConfigurationUtil.getNightModeConfiguration(activity));
CachedInflater.from(activity).clear(); CachedInflater.from(activity).clear();
} }
} }
@ -52,10 +57,13 @@ public class DynamicTheme {
String theme = TextSecurePreferences.getTheme(context); String theme = TextSecurePreferences.getTheme(context);
if (theme.equals(SYSTEM)) { if (theme.equals(SYSTEM)) {
Log.d(TAG, "Setting to follow system expecting: " + ConfigurationUtil.getNightModeConfiguration(context.getApplicationContext()));
AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_FOLLOW_SYSTEM); AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_FOLLOW_SYSTEM);
} else if (DynamicTheme.isDarkTheme(context)) { } else if (DynamicTheme.isDarkTheme(context)) {
Log.d(TAG, "Setting to always night");
AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_YES); AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_YES);
} else { } else {
Log.d(TAG, "Setting to always day");
AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_NO); AppCompatDelegate.setDefaultNightMode(AppCompatDelegate.MODE_NIGHT_NO);
} }