Application language now can be changed in the settings
This commit is contained in:
parent
a8d6039083
commit
224cd16591
@ -95,6 +95,10 @@
|
||||
public static int e(...);
|
||||
}
|
||||
|
||||
-assumenosideeffects class org.solovyev.android.Check {
|
||||
*;
|
||||
}
|
||||
|
||||
#
|
||||
#*********************************************************************
|
||||
#
|
||||
|
166
android-app/src/main/java/org/solovyev/android/Check.java
Normal file
166
android-app/src/main/java/org/solovyev/android/Check.java
Normal file
@ -0,0 +1,166 @@
|
||||
/*
|
||||
* Copyright 2014 serso aka se.solovyev
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
* Contact details
|
||||
*
|
||||
* Email: se.solovyev@gmail.com
|
||||
* Site: http://se.solovyev.org
|
||||
*/
|
||||
|
||||
package org.solovyev.android;
|
||||
|
||||
import android.os.Looper;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Map;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
import javax.annotation.Nullable;
|
||||
|
||||
import static java.lang.Thread.currentThread;
|
||||
|
||||
public final class Check {
|
||||
|
||||
private static final boolean junit = isJunit();
|
||||
|
||||
private static boolean isJunit() {
|
||||
final StackTraceElement[] stackTrace = currentThread().getStackTrace();
|
||||
for (StackTraceElement element : stackTrace) {
|
||||
if (element.getClassName().startsWith("org.junit.")) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private Check() {
|
||||
throw new AssertionError();
|
||||
}
|
||||
|
||||
public static void isMainThread() {
|
||||
if (!junit && Looper.getMainLooper() != Looper.myLooper()) {
|
||||
throw new AssertionException("Should be called on the main thread");
|
||||
}
|
||||
}
|
||||
|
||||
public static void isNotNull(@Nullable Object o) {
|
||||
isNotNull(o, "Object should not be null");
|
||||
}
|
||||
|
||||
public static void isNotNull(@Nullable Object o, @Nonnull String message) {
|
||||
if (o == null) {
|
||||
throw new AssertionException(message);
|
||||
}
|
||||
}
|
||||
|
||||
public static void notEquals(int expected, int actual) {
|
||||
if (expected == actual) {
|
||||
throw new AssertionException("Should not be equal");
|
||||
}
|
||||
}
|
||||
|
||||
public static void equals(int expected, int actual) {
|
||||
if (expected != actual) {
|
||||
throw new AssertionException("Should be equal");
|
||||
}
|
||||
}
|
||||
|
||||
public static void equals(@Nullable Object expected, @Nullable Object actual) {
|
||||
equals(expected, actual, "Should be equal");
|
||||
}
|
||||
|
||||
public static void equals(@Nullable Object expected, @Nullable Object actual, @Nonnull String message) {
|
||||
if (expected == actual) {
|
||||
// both nulls or same
|
||||
return;
|
||||
}
|
||||
|
||||
if (expected != null && actual != null && expected.equals(actual)) {
|
||||
// equals
|
||||
return;
|
||||
}
|
||||
|
||||
throw new AssertionException(message);
|
||||
}
|
||||
|
||||
public static void isTrue(boolean expression, @Nonnull String message) {
|
||||
if (!expression) {
|
||||
throw new AssertionException(message);
|
||||
}
|
||||
}
|
||||
|
||||
public static void isFalse(boolean expression, @Nonnull String message) {
|
||||
if (expression) {
|
||||
throw new AssertionException(message);
|
||||
}
|
||||
}
|
||||
|
||||
public static void isNull(@Nullable Object o) {
|
||||
isNull(o, "Object should be null");
|
||||
}
|
||||
|
||||
public static void isNull(@Nullable Object o, @Nonnull String message) {
|
||||
if (o != null) {
|
||||
throw new AssertionException(message);
|
||||
}
|
||||
}
|
||||
|
||||
public static void isNotEmpty(@Nullable String s) {
|
||||
if (s == null || s.length() == 0) {
|
||||
throw new AssertionException("String should not be empty");
|
||||
}
|
||||
}
|
||||
|
||||
public static void isNotEmpty(@Nullable String[] array) {
|
||||
if (array == null || array.length == 0) {
|
||||
throw new AssertionException("Array should not be empty");
|
||||
}
|
||||
}
|
||||
|
||||
public static void isNotEmpty(@Nullable Collection<?> c) {
|
||||
if (c == null || c.size() == 0) {
|
||||
throw new AssertionException("Collection should not be empty");
|
||||
}
|
||||
}
|
||||
|
||||
public static void isNotEmpty(@Nullable Map<?, ?> c) {
|
||||
if (c == null || c.size() == 0) {
|
||||
throw new AssertionException("Map should not be empty");
|
||||
}
|
||||
}
|
||||
|
||||
public static void same(Object expected, Object actual) {
|
||||
if (expected != actual) {
|
||||
throw new AssertionException("Objects should be the same");
|
||||
}
|
||||
}
|
||||
|
||||
public static void isEmpty(@Nullable Collection<?> c) {
|
||||
if (c != null && !c.isEmpty()) {
|
||||
throw new AssertionException("Collection should be empty");
|
||||
}
|
||||
}
|
||||
|
||||
public static void shouldNotHappen() {
|
||||
throw new AssertionException("Should not happen");
|
||||
}
|
||||
|
||||
private static final class AssertionException extends RuntimeException {
|
||||
private AssertionException(@Nonnull String message) {
|
||||
super(message);
|
||||
}
|
||||
}
|
||||
}
|
@ -38,8 +38,11 @@ import android.util.DisplayMetrics;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.TextView;
|
||||
|
||||
import org.solovyev.android.Activities;
|
||||
import org.solovyev.android.Views;
|
||||
import org.solovyev.android.calculator.language.Language;
|
||||
import org.solovyev.android.calculator.language.Languages;
|
||||
import org.solovyev.android.sherlock.tabs.ActionBarFragmentTabListener;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
@ -50,10 +53,13 @@ public class ActivityUi extends BaseUi {
|
||||
private int layoutId;
|
||||
|
||||
@Nonnull
|
||||
private Preferences.Gui.Theme theme;
|
||||
private Preferences.Gui.Theme theme = Preferences.Gui.Theme.default_theme;
|
||||
|
||||
@Nonnull
|
||||
private Preferences.Gui.Layout layout;
|
||||
private Preferences.Gui.Layout layout = Preferences.Gui.Layout.main_calculator;
|
||||
|
||||
@Nonnull
|
||||
private Language language = Languages.SYSTEM_LANGUAGE;
|
||||
|
||||
private int selectedNavigationIndex = 0;
|
||||
|
||||
@ -73,11 +79,13 @@ public class ActivityUi extends BaseUi {
|
||||
activity.setTheme(theme.getThemeId(activity));
|
||||
|
||||
layout = Preferences.Gui.getLayout(preferences);
|
||||
language = App.getLanguages().getCurrent();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onCreate(@Nonnull Activity activity) {
|
||||
super.onCreate(activity);
|
||||
App.getLanguages().updateLanguage(activity, false);
|
||||
|
||||
if (activity instanceof CalculatorEventListener) {
|
||||
Locator.getInstance().getCalculator().addCalculatorEventListener((CalculatorEventListener) activity);
|
||||
@ -146,16 +154,29 @@ public class ActivityUi extends BaseUi {
|
||||
}
|
||||
|
||||
public void onResume(@Nonnull Activity activity) {
|
||||
restartIfThemeChanged(activity, theme);
|
||||
if (!restartIfThemeChanged(activity, theme)) {
|
||||
restartIfLanguageChanged(activity, language);
|
||||
}
|
||||
}
|
||||
|
||||
public static void restartIfThemeChanged(@Nonnull Activity activity, @Nonnull Preferences.Gui.Theme oldTheme) {
|
||||
public static boolean restartIfThemeChanged(@Nonnull Activity activity, @Nonnull Preferences.Gui.Theme oldTheme) {
|
||||
final Preferences.Gui.Theme newTheme = Preferences.Gui.theme.getPreference(App.getPreferences());
|
||||
final int themeId = oldTheme.getThemeId(activity);
|
||||
final int newThemeId = newTheme.getThemeId(activity);
|
||||
if (themeId != newThemeId) {
|
||||
Activities.restartActivity(activity);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean restartIfLanguageChanged(@Nonnull Activity activity, @Nonnull Language oldLanguage) {
|
||||
final Language current = App.getLanguages().getCurrent();
|
||||
if (!current.equals(oldLanguage)) {
|
||||
Activities.restartActivity(activity);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public void onPause(@Nonnull Activity activity) {
|
||||
@ -254,6 +275,11 @@ public class ActivityUi extends BaseUi {
|
||||
return theme;
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public Language getLanguage() {
|
||||
return language;
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public Preferences.Gui.Layout getLayout() {
|
||||
return layout;
|
||||
|
@ -39,6 +39,7 @@ import org.solovyev.android.Android;
|
||||
import org.solovyev.android.UiThreadExecutor;
|
||||
import org.solovyev.android.Views;
|
||||
import org.solovyev.android.calculator.ga.Ga;
|
||||
import org.solovyev.android.calculator.language.Languages;
|
||||
import org.solovyev.android.calculator.view.ScreenMetrics;
|
||||
import org.solovyev.android.calculator.widget.BaseCalculatorWidgetProvider;
|
||||
import org.solovyev.android.calculator.widget.CalculatorWidgetProvider;
|
||||
@ -117,6 +118,9 @@ public final class App {
|
||||
@Nonnull
|
||||
private static volatile ScreenMetrics screenMetrics;
|
||||
|
||||
@Nonnull
|
||||
private static final Languages languages = new Languages();
|
||||
|
||||
private App() {
|
||||
throw new AssertionError();
|
||||
}
|
||||
@ -177,6 +181,7 @@ public final class App {
|
||||
Android.enableComponent(application, CalculatorWidgetProvider4x4.class, false);
|
||||
}
|
||||
}
|
||||
App.languages.init(App.preferences);
|
||||
|
||||
App.initialized = true;
|
||||
} else {
|
||||
@ -277,6 +282,11 @@ public final class App {
|
||||
return Preferences.Gui.getTheme(getPreferences());
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public static Languages getLanguages() {
|
||||
return languages;
|
||||
}
|
||||
|
||||
public static boolean isLg() {
|
||||
if (lg == null) {
|
||||
lg = "lge".equalsIgnoreCase(Build.BRAND) || "lge".equalsIgnoreCase(Build.MANUFACTURER);
|
||||
|
@ -37,6 +37,7 @@ import org.acra.ReportingInteractionMode;
|
||||
import org.acra.annotation.ReportsCrashes;
|
||||
import org.solovyev.android.Android;
|
||||
import org.solovyev.android.calculator.history.AndroidCalculatorHistory;
|
||||
import org.solovyev.android.calculator.language.Language;
|
||||
import org.solovyev.android.calculator.model.AndroidCalculatorEngine;
|
||||
import org.solovyev.android.calculator.onscreen.CalculatorOnscreenStartActivity;
|
||||
import org.solovyev.android.calculator.plot.AndroidCalculatorPlotter;
|
||||
@ -48,6 +49,7 @@ import org.solovyev.common.msg.MessageType;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
@ -139,8 +141,10 @@ public class CalculatorApplication extends android.app.Application implements Sh
|
||||
preferences.registerOnSharedPreferenceChangeListener(this);
|
||||
|
||||
setTheme(preferences);
|
||||
setLanguageInitially();
|
||||
|
||||
super.onCreate();
|
||||
App.getLanguages().updateLanguage(this, true);
|
||||
|
||||
if (!Preferences.Ga.initialReportDone.getPreference(preferences)) {
|
||||
App.getGa().reportInitially(preferences);
|
||||
@ -199,6 +203,14 @@ public class CalculatorApplication extends android.app.Application implements Sh
|
||||
}, 100, TimeUnit.MILLISECONDS);
|
||||
}
|
||||
|
||||
private void setLanguageInitially() {
|
||||
// should be called before onCreate()
|
||||
final Language language = App.getLanguages().getCurrent();
|
||||
if (!language.isSystem() && !language.locale.equals(Locale.getDefault())) {
|
||||
Locale.setDefault(language.locale);
|
||||
}
|
||||
}
|
||||
|
||||
private void setTheme(@Nonnull SharedPreferences preferences) {
|
||||
final Preferences.Gui.Theme theme = Preferences.Gui.getTheme(preferences);
|
||||
setTheme(theme.getThemeId());
|
||||
|
@ -29,19 +29,28 @@ import android.graphics.Color;
|
||||
import android.support.annotation.StyleRes;
|
||||
import android.util.SparseArray;
|
||||
import android.view.ContextThemeWrapper;
|
||||
import jscl.AngleUnit;
|
||||
import jscl.NumeralBase;
|
||||
|
||||
import org.solovyev.android.calculator.language.Languages;
|
||||
import org.solovyev.android.calculator.math.MathType;
|
||||
import org.solovyev.android.calculator.model.AndroidCalculatorEngine;
|
||||
import org.solovyev.android.calculator.onscreen.CalculatorOnscreenService;
|
||||
import org.solovyev.android.calculator.preferences.PurchaseDialogActivity;
|
||||
import org.solovyev.android.calculator.wizard.WizardActivity;
|
||||
import org.solovyev.android.prefs.*;
|
||||
import org.solovyev.android.prefs.BooleanPreference;
|
||||
import org.solovyev.android.prefs.IntegerPreference;
|
||||
import org.solovyev.android.prefs.LongPreference;
|
||||
import org.solovyev.android.prefs.NumberToStringPreference;
|
||||
import org.solovyev.android.prefs.Preference;
|
||||
import org.solovyev.android.prefs.StringPreference;
|
||||
|
||||
import java.text.DecimalFormatSymbols;
|
||||
import java.util.Locale;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
import javax.annotation.Nullable;
|
||||
import java.text.DecimalFormatSymbols;
|
||||
import java.util.Locale;
|
||||
|
||||
import jscl.AngleUnit;
|
||||
import jscl.NumeralBase;
|
||||
|
||||
import static org.solovyev.android.Android.isPhoneModel;
|
||||
import static org.solovyev.android.DeviceModel.samsung_galaxy_s;
|
||||
@ -80,8 +89,8 @@ public final class Preferences {
|
||||
|
||||
public static final Preference<Theme> theme = StringPreference.ofEnum("org.solovyev.android.calculator.CalculatorActivity_calc_theme", Theme.material_theme, Theme.class);
|
||||
public static final Preference<Layout> layout = StringPreference.ofEnum("org.solovyev.android.calculator.CalculatorActivity_calc_layout", Layout.simple, Layout.class);
|
||||
public static final Preference<String> language = StringPreference.of("gui.language", Languages.SYSTEM_LANGUAGE_CODE);
|
||||
public static final Preference<Boolean> feedbackWindowShown = BooleanPreference.of("feedback_window_shown", false);
|
||||
public static final Preference<Boolean> notesppAnnounceShown = BooleanPreference.of("notespp_announce_shown", false);
|
||||
public static final Preference<Boolean> showReleaseNotes = BooleanPreference.of("org.solovyev.android.calculator.CalculatorActivity_show_release_notes", true);
|
||||
public static final Preference<Boolean> usePrevAsBack = BooleanPreference.of("org.solovyev.android.calculator.CalculatorActivity_use_back_button_as_prev", false);
|
||||
public static final Preference<Boolean> showEqualsButton = BooleanPreference.of("showEqualsButton", true);
|
||||
@ -264,13 +273,13 @@ public final class Preferences {
|
||||
Gui.layout.putDefault(preferences);
|
||||
}
|
||||
applyDefaultPreference(preferences, Gui.feedbackWindowShown);
|
||||
applyDefaultPreference(preferences, Gui.notesppAnnounceShown);
|
||||
applyDefaultPreference(preferences, Gui.showReleaseNotes);
|
||||
applyDefaultPreference(preferences, Gui.usePrevAsBack);
|
||||
applyDefaultPreference(preferences, Gui.showEqualsButton);
|
||||
applyDefaultPreference(preferences, Gui.autoOrientation);
|
||||
applyDefaultPreference(preferences, Gui.hideNumeralBaseDigits);
|
||||
applyDefaultPreference(preferences, Gui.preventScreenFromFading);
|
||||
applyDefaultPreference(preferences, Gui.language);
|
||||
|
||||
applyDefaultPreference(preferences, Graph.plotImag);
|
||||
applyDefaultPreference(preferences, History.showIntermediateCalculations);
|
||||
|
@ -0,0 +1,69 @@
|
||||
package org.solovyev.android.calculator.language;
|
||||
|
||||
import android.content.Context;
|
||||
import android.text.TextUtils;
|
||||
|
||||
import org.solovyev.android.calculator.R;
|
||||
|
||||
import java.util.Locale;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
|
||||
public final class Language {
|
||||
@Nonnull
|
||||
public final String code;
|
||||
|
||||
@Nonnull
|
||||
public final Locale locale;
|
||||
|
||||
@Nonnull
|
||||
final String name;
|
||||
|
||||
public Language(@Nonnull String code, @Nonnull Locale locale) {
|
||||
this.code = code;
|
||||
this.locale = locale;
|
||||
this.name = makeName(code, locale);
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public String getName(@Nonnull Context context) {
|
||||
if (!isSystem()) {
|
||||
return name;
|
||||
} else {
|
||||
return context.getString(R.string.cpp_system_language) + " (" + locale.getDisplayLanguage(locale) + ")";
|
||||
}
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
private static String makeName(@Nonnull String code, @Nonnull Locale locale) {
|
||||
if (code.equals(Languages.SYSTEM_LANGUAGE_CODE)) {
|
||||
return "";
|
||||
}
|
||||
|
||||
final int underscore = code.indexOf("_");
|
||||
if (underscore >= 0 && TextUtils.isEmpty(locale.getDisplayCountry(locale))) {
|
||||
return locale.getDisplayName(locale) + " (" + code.substring(underscore + 1) + ")";
|
||||
}
|
||||
|
||||
return locale.getDisplayName(locale);
|
||||
}
|
||||
|
||||
public boolean isSystem() {
|
||||
return code.equals(Languages.SYSTEM_LANGUAGE_CODE);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) return true;
|
||||
if (o == null || getClass() != o.getClass()) return false;
|
||||
|
||||
final Language language = (Language) o;
|
||||
return code.equals(language.code);
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return code.hashCode();
|
||||
}
|
||||
}
|
@ -0,0 +1,168 @@
|
||||
package org.solovyev.android.calculator.language;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.SharedPreferences;
|
||||
import android.content.res.Configuration;
|
||||
import android.content.res.Resources;
|
||||
import android.text.TextUtils;
|
||||
import android.util.DisplayMetrics;
|
||||
import android.util.Log;
|
||||
|
||||
import org.solovyev.android.Check;
|
||||
import org.solovyev.android.calculator.App;
|
||||
import org.solovyev.android.calculator.Preferences;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.Comparator;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
import javax.annotation.Nullable;
|
||||
|
||||
public final class Languages implements SharedPreferences.OnSharedPreferenceChangeListener {
|
||||
|
||||
@Nonnull
|
||||
private static final Locale[] locales = Locale.getAvailableLocales();
|
||||
@Nonnull
|
||||
public static final String SYSTEM_LANGUAGE_CODE = "00";
|
||||
@Nonnull
|
||||
public static final Language SYSTEM_LANGUAGE = new Language(SYSTEM_LANGUAGE_CODE, Locale.getDefault());
|
||||
@Nonnull
|
||||
private final List<Language> list = new ArrayList<>();
|
||||
|
||||
public void init(@Nonnull SharedPreferences preferences) {
|
||||
preferences.registerOnSharedPreferenceChangeListener(this);
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public List<Language> getList() {
|
||||
Check.isMainThread();
|
||||
if (list.isEmpty()) {
|
||||
loadList();
|
||||
}
|
||||
return list;
|
||||
}
|
||||
|
||||
private void loadList() {
|
||||
Check.isMainThread();
|
||||
Check.isEmpty(list);
|
||||
tryAddLanguage("ar");
|
||||
tryAddLanguage("cs");
|
||||
tryAddLanguage("en");
|
||||
tryAddLanguage("es_ES");
|
||||
tryAddLanguage("de");
|
||||
tryAddLanguage("fi");
|
||||
tryAddLanguage("fr");
|
||||
tryAddLanguage("it");
|
||||
tryAddLanguage("it");
|
||||
tryAddLanguage("pl");
|
||||
tryAddLanguage("pt_BR");
|
||||
tryAddLanguage("pt_PT");
|
||||
tryAddLanguage("ru");
|
||||
tryAddLanguage("vi");
|
||||
tryAddLanguage("uk");
|
||||
tryAddLanguage("ja");
|
||||
tryAddLanguage("zh_CN");
|
||||
tryAddLanguage("zh_TW");
|
||||
Collections.sort(list, new Comparator<Language>() {
|
||||
@Override
|
||||
public int compare(Language lhs, Language rhs) {
|
||||
return lhs.name.compareTo(rhs.name);
|
||||
}
|
||||
});
|
||||
list.add(0, SYSTEM_LANGUAGE);
|
||||
}
|
||||
|
||||
private void tryAddLanguage(@Nonnull String locale) {
|
||||
final Language language = makeLanguage(locale);
|
||||
if (language != null) {
|
||||
list.add(language);
|
||||
}
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private static Language makeLanguage(@Nonnull String localeId) {
|
||||
final Locale locale = findLocaleById(localeId);
|
||||
if (locale == null) {
|
||||
return null;
|
||||
}
|
||||
return new Language(localeId, locale);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private static Locale findLocaleById(@Nonnull String id) {
|
||||
for (Locale locale : locales) {
|
||||
if (TextUtils.equals(locale.toString(), id)) {
|
||||
return locale;
|
||||
}
|
||||
}
|
||||
|
||||
final String language;
|
||||
final int underscore = id.indexOf("_");
|
||||
if (underscore >= 0) {
|
||||
language = id.substring(0, underscore);
|
||||
} else {
|
||||
language = id;
|
||||
}
|
||||
|
||||
for (Locale locale : locales) {
|
||||
if (TextUtils.equals(locale.getLanguage(), language)) {
|
||||
return locale;
|
||||
}
|
||||
}
|
||||
|
||||
Log.d("Languages", "No locale found for " + id);
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public Language getCurrent() {
|
||||
return get(Preferences.Gui.language.getPreference(App.getPreferences()));
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public Language get(@Nonnull String code) {
|
||||
Language language = findLanguageByCode(code);
|
||||
if (language != null) {
|
||||
return language;
|
||||
}
|
||||
return SYSTEM_LANGUAGE;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private Language findLanguageByCode(@Nonnull String code) {
|
||||
for (Language language : getList()) {
|
||||
if (TextUtils.equals(language.code, code)) {
|
||||
return language;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onSharedPreferenceChanged(@Nonnull SharedPreferences p, String key) {
|
||||
if (Preferences.Gui.language.isSameKey(key)) {
|
||||
updateLanguage(App.getApplication(), false);
|
||||
}
|
||||
}
|
||||
|
||||
public void updateLanguage(@Nonnull Context context, boolean initial) {
|
||||
final Language language = getCurrent();
|
||||
// we don't need to set system language while starting up the app
|
||||
if (!initial || !language.isSystem()) {
|
||||
if (!Locale.getDefault().equals(language.locale)) {
|
||||
Locale.setDefault(language.locale);
|
||||
}
|
||||
|
||||
final Resources r = context.getResources();
|
||||
final DisplayMetrics dm = r.getDisplayMetrics();
|
||||
final Configuration c = r.getConfiguration();
|
||||
if (c.locale == null || !c.locale.equals(language.locale)) {
|
||||
c.locale = language.locale;
|
||||
r.updateConfiguration(c, dm);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -6,7 +6,6 @@ import android.content.SharedPreferences;
|
||||
import android.os.Bundle;
|
||||
import android.support.annotation.StringRes;
|
||||
import android.support.annotation.XmlRes;
|
||||
import android.text.TextUtils;
|
||||
import android.util.SparseArray;
|
||||
|
||||
import org.solovyev.android.calculator.ActivityUi;
|
||||
@ -27,15 +26,27 @@ public class PreferencesActivity extends BaseActivity implements SharedPreferenc
|
||||
static final String EXTRA_PREFERENCE_TITLE = "preference-title";
|
||||
|
||||
@Nonnull
|
||||
private static final SparseArray<String> preferences = new SparseArray<>();
|
||||
private static final SparseArray<PrefDef> preferences = new SparseArray<>();
|
||||
|
||||
static {
|
||||
preferences.append(R.xml.preferences, "screen-main");
|
||||
preferences.append(R.xml.preferences_calculations, "screen-calculations");
|
||||
preferences.append(R.xml.preferences_appearance, "screen-appearance");
|
||||
preferences.append(R.xml.preferences_plot, "screen-plot");
|
||||
preferences.append(R.xml.preferences_other, "screen-other");
|
||||
preferences.append(R.xml.preferences_onscreen, "screen-onscreen");
|
||||
preferences.append(R.xml.preferences, new PrefDef("screen-main", R.string.c_app_settings));
|
||||
preferences.append(R.xml.preferences_calculations, new PrefDef("screen-calculations", R.string.c_prefs_calculations_category));
|
||||
preferences.append(R.xml.preferences_appearance, new PrefDef("screen-appearance", R.string.c_prefs_appearance_category));
|
||||
preferences.append(R.xml.preferences_plot, new PrefDef("screen-plot", R.string.prefs_graph_screen_title));
|
||||
preferences.append(R.xml.preferences_other, new PrefDef("screen-other", R.string.c_prefs_other_category));
|
||||
preferences.append(R.xml.preferences_onscreen, new PrefDef("screen-onscreen", R.string.prefs_onscreen_title));
|
||||
}
|
||||
|
||||
static class PrefDef {
|
||||
@Nonnull
|
||||
public final String id;
|
||||
@StringRes
|
||||
public final int title;
|
||||
|
||||
PrefDef(@Nonnull String id, int title) {
|
||||
this.id = id;
|
||||
this.title = title;
|
||||
}
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
@ -53,8 +64,8 @@ public class PreferencesActivity extends BaseActivity implements SharedPreferenc
|
||||
App.getPreferences().registerOnSharedPreferenceChangeListener(this);
|
||||
|
||||
final Intent intent = getIntent();
|
||||
final String preferenceTitle = intent.getStringExtra(EXTRA_PREFERENCE_TITLE);
|
||||
if (!TextUtils.isEmpty(preferenceTitle)) {
|
||||
final int preferenceTitle = intent.getIntExtra(EXTRA_PREFERENCE_TITLE, 0);
|
||||
if (preferenceTitle != 0) {
|
||||
setTitle(preferenceTitle);
|
||||
}
|
||||
|
||||
@ -72,8 +83,12 @@ public class PreferencesActivity extends BaseActivity implements SharedPreferenc
|
||||
|
||||
@Override
|
||||
public void onSharedPreferenceChanged(SharedPreferences sharedPreferences, String key) {
|
||||
if (!paused && Preferences.Gui.theme.isSameKey(key)) {
|
||||
if (!paused) {
|
||||
if (Preferences.Gui.theme.isSameKey(key)) {
|
||||
ActivityUi.restartIfThemeChanged(this, ui.getTheme());
|
||||
} else if (Preferences.Gui.language.isSameKey(key)) {
|
||||
ActivityUi.restartIfLanguageChanged(this, ui.getLanguage());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -97,7 +112,7 @@ public class PreferencesActivity extends BaseActivity implements SharedPreferenc
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
static SparseArray<String> getPreferences() {
|
||||
static SparseArray<PrefDef> getPreferences() {
|
||||
return preferences;
|
||||
}
|
||||
|
||||
@ -107,11 +122,11 @@ public class PreferencesActivity extends BaseActivity implements SharedPreferenc
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
static Intent makeIntent(@Nonnull Context context, int preference, int title) {
|
||||
static Intent makeIntent(@Nonnull Context context, @XmlRes int preference, @StringRes int title) {
|
||||
final Intent intent = new Intent(context, PreferencesActivity.class);
|
||||
intent.putExtra(EXTRA_PREFERENCE, preference);
|
||||
if (title != 0) {
|
||||
intent.putExtra(EXTRA_PREFERENCE_TITLE, context.getString(title));
|
||||
intent.putExtra(EXTRA_PREFERENCE_TITLE, title);
|
||||
}
|
||||
return intent;
|
||||
}
|
||||
|
@ -4,6 +4,7 @@ import android.content.Intent;
|
||||
import android.content.SharedPreferences;
|
||||
import android.os.Build;
|
||||
import android.os.Bundle;
|
||||
import android.preference.ListPreference;
|
||||
import android.preference.Preference;
|
||||
import android.util.SparseArray;
|
||||
import android.view.LayoutInflater;
|
||||
@ -13,12 +14,17 @@ import android.widget.ListView;
|
||||
import org.solovyev.android.calculator.AdView;
|
||||
import org.solovyev.android.calculator.App;
|
||||
import org.solovyev.android.calculator.CalculatorApplication;
|
||||
import org.solovyev.android.calculator.Preferences;
|
||||
import org.solovyev.android.calculator.R;
|
||||
import org.solovyev.android.calculator.language.Language;
|
||||
import org.solovyev.android.calculator.language.Languages;
|
||||
import org.solovyev.android.checkout.BillingRequests;
|
||||
import org.solovyev.android.checkout.Checkout;
|
||||
import org.solovyev.android.checkout.ProductTypes;
|
||||
import org.solovyev.android.checkout.RequestListener;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
import javax.annotation.Nullable;
|
||||
|
||||
@ -51,12 +57,12 @@ public class PreferencesFragment extends org.solovyev.android.material.preferenc
|
||||
App.getPreferences().registerOnSharedPreferenceChangeListener(this);
|
||||
}
|
||||
|
||||
private void setPreferenceIntent(int xml, @Nonnull String name) {
|
||||
final Preference preference = findPreference(name);
|
||||
private void setPreferenceIntent(int xml, @Nonnull PreferencesActivity.PrefDef def) {
|
||||
final Preference preference = findPreference(def.id);
|
||||
if (preference != null) {
|
||||
final Intent intent = new Intent(getActivity(), PreferencesActivity.class);
|
||||
intent.putExtra(PreferencesActivity.EXTRA_PREFERENCE, xml);
|
||||
intent.putExtra(PreferencesActivity.EXTRA_PREFERENCE_TITLE, preference.getTitle());
|
||||
intent.putExtra(PreferencesActivity.EXTRA_PREFERENCE_TITLE, def.title);
|
||||
preference.setIntent(intent);
|
||||
}
|
||||
}
|
||||
@ -67,11 +73,11 @@ public class PreferencesFragment extends org.solovyev.android.material.preferenc
|
||||
|
||||
final int preference = getPreferencesResId();
|
||||
if (preference == R.xml.preferences) {
|
||||
final SparseArray<String> preferences = PreferencesActivity.getPreferences();
|
||||
final SparseArray<PreferencesActivity.PrefDef> preferences = PreferencesActivity.getPreferences();
|
||||
for (int i = 0; i < preferences.size(); i++) {
|
||||
final int xml = preferences.keyAt(i);
|
||||
final String name = preferences.valueAt(i);
|
||||
setPreferenceIntent(xml, name);
|
||||
final PreferencesActivity.PrefDef def = preferences.valueAt(i);
|
||||
setPreferenceIntent(xml, def);
|
||||
}
|
||||
final Preference restartWizardPreference = findPreference("restart_wizard");
|
||||
restartWizardPreference.setOnPreferenceClickListener(new Preference.OnPreferenceClickListener() {
|
||||
@ -96,6 +102,8 @@ public class PreferencesFragment extends org.solovyev.android.material.preferenc
|
||||
}
|
||||
}
|
||||
|
||||
prepareLanguagePreference(preference);
|
||||
|
||||
getCheckout().whenReady(new Checkout.ListenerAdapter() {
|
||||
@Override
|
||||
public void onReady(@Nonnull BillingRequests requests) {
|
||||
@ -121,6 +129,34 @@ public class PreferencesFragment extends org.solovyev.android.material.preferenc
|
||||
onSharedPreferenceChanged(preferences, roundResult.getKey());
|
||||
}
|
||||
|
||||
private void prepareLanguagePreference(int preference) {
|
||||
if (preference != R.xml.preferences_appearance) {
|
||||
return;
|
||||
}
|
||||
|
||||
final ListPreference language = (ListPreference) preferenceManager.findPreference(Preferences.Gui.language.getKey());
|
||||
final Languages languages = App.getLanguages();
|
||||
final List<Language> languagesList = languages.getList();
|
||||
final CharSequence[] entries = new CharSequence[languagesList.size()];
|
||||
final CharSequence[] entryValues = new CharSequence[languagesList.size()];
|
||||
for (int i = 0; i < languagesList.size(); i++) {
|
||||
final Language l = languagesList.get(i);
|
||||
entries[i] = l.getName(getActivity());
|
||||
entryValues[i] = l.code;
|
||||
}
|
||||
language.setEntries(entries);
|
||||
language.setEntryValues(entryValues);
|
||||
language.setSummary(languages.getCurrent().getName(getActivity()));
|
||||
language.setOnPreferenceChangeListener(new Preference.OnPreferenceChangeListener() {
|
||||
@Override
|
||||
public boolean onPreferenceChange(Preference preference, Object newValue) {
|
||||
final Language l = languages.get((String) newValue);
|
||||
language.setSummary(l.getName(getActivity()));
|
||||
return true;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
private Checkout getCheckout() {
|
||||
return ((PreferencesActivity) getActivity()).getCheckout();
|
||||
|
@ -8,9 +8,22 @@ import android.support.v4.app.Fragment;
|
||||
import android.support.v4.app.FragmentManager;
|
||||
import android.support.v4.app.FragmentStatePagerAdapter;
|
||||
import android.support.v4.view.ViewPager;
|
||||
|
||||
import com.viewpagerindicator.PageIndicator;
|
||||
import org.solovyev.android.calculator.*;
|
||||
import org.solovyev.android.wizard.*;
|
||||
|
||||
import org.solovyev.android.calculator.ActivityUi;
|
||||
import org.solovyev.android.calculator.App;
|
||||
import org.solovyev.android.calculator.BaseActivity;
|
||||
import org.solovyev.android.calculator.CalculatorApplication;
|
||||
import org.solovyev.android.calculator.Preferences;
|
||||
import org.solovyev.android.calculator.R;
|
||||
import org.solovyev.android.wizard.ListWizardFlow;
|
||||
import org.solovyev.android.wizard.Wizard;
|
||||
import org.solovyev.android.wizard.WizardFlow;
|
||||
import org.solovyev.android.wizard.WizardStep;
|
||||
import org.solovyev.android.wizard.WizardUi;
|
||||
import org.solovyev.android.wizard.Wizards;
|
||||
import org.solovyev.android.wizard.WizardsAware;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
import javax.annotation.Nullable;
|
||||
@ -190,6 +203,8 @@ public class WizardActivity extends BaseActivity implements WizardsAware, Shared
|
||||
public void onSharedPreferenceChanged(SharedPreferences preferences, String key) {
|
||||
if (Preferences.Gui.theme.isSameKey(key)) {
|
||||
ActivityUi.restartIfThemeChanged(this, ui.getTheme());
|
||||
} else if (Preferences.Gui.language.isSameKey(key)) {
|
||||
ActivityUi.restartIfLanguageChanged(this, ui.getLanguage());
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -7,9 +7,7 @@
|
||||
<string name="c_show_equals_button_title">Show equals button</string>
|
||||
<string name="c_show_equals_button_summary">If turned on equals button is shown</string>
|
||||
<string name="c_hide_numeral_base_digits_title">Hide digits of other numeral systems</string>
|
||||
<string name="c_hide_numeral_base_digits_summary">If turned on numeral base digits of other numeral bases will be
|
||||
hidden
|
||||
</string>
|
||||
<string name="c_hide_numeral_base_digits_summary">If turned on numeral base digits of other numeral bases will be hidden</string>
|
||||
<string name="prefs_history_show_intermediate_calculations_title">Show intermediate calculations in history</string>
|
||||
<string name="prefs_history_show_intermediate_calculations_summary">If turned on all calculations will be shown in the
|
||||
history screen
|
||||
@ -19,4 +17,5 @@
|
||||
<string name="prefs_prevent_screen_from_fading_title">Prevent screen from fading</string>
|
||||
<string name="prefs_prevent_screen_from_fading_summary">If turned on screen will not fade while using the app
|
||||
</string>
|
||||
<string name="prefs_language_title">Language</string>
|
||||
</resources>
|
||||
|
@ -231,4 +231,5 @@
|
||||
<string name="cpp_clear_history">Clear</string>
|
||||
<string name="cpp_new_in_version">New in %1$s version</string>
|
||||
<string name="cpp_release_notes_choose_theme">Do you want to try new Material themes? Choose them from the list:</string>
|
||||
<string name="cpp_system_language">System language</string>
|
||||
</resources>
|
||||
|
@ -23,69 +23,74 @@
|
||||
-->
|
||||
|
||||
<PreferenceScreen xmlns:a="http://schemas.android.com/apk/res/android"
|
||||
xmlns:range="http://schemas.android.com/apk/res-auto">
|
||||
xmlns:m="http://schemas.android.com/apk/res-auto">
|
||||
|
||||
<org.solovyev.android.material.preferences.ListPreference
|
||||
a:key="gui.language"
|
||||
a:title="@string/prefs_language_title"
|
||||
m:materialColor="@color/material_text_selector"/>
|
||||
|
||||
<android.preference.CheckBoxPreference
|
||||
a:defaultValue="true"
|
||||
a:key="@string/p_calc_color_display_key"
|
||||
a:summary="@string/c_calc_color_display_summary"
|
||||
a:title="@string/c_calc_color_display_title"
|
||||
a:defaultValue="true"/>
|
||||
a:title="@string/c_calc_color_display_title"/>
|
||||
|
||||
<ListPreference
|
||||
a:key="hapticFeedback"
|
||||
a:title="@string/c_calc_haptic_feedback_title"
|
||||
a:entries="@array/cpp_haptic_feedback_names"
|
||||
a:entryValues="@array/cpp_haptic_feedback_values"
|
||||
a:key="hapticFeedback"
|
||||
a:summary="@string/c_calc_haptic_feedback_summary"
|
||||
a:entryValues="@array/cpp_haptic_feedback_values"/>
|
||||
a:title="@string/c_calc_haptic_feedback_title"/>
|
||||
|
||||
<ListPreference
|
||||
a:key="@string/p_calc_multiplication_sign_key"
|
||||
a:title="@string/c_calc_multiplication_sign"
|
||||
a:entries="@array/p_multiplication_sign_values"
|
||||
a:entryValues="@array/p_multiplication_sign_values"
|
||||
a:key="@string/p_calc_multiplication_sign_key"
|
||||
a:summary="@string/c_calc_multiplication_sign_summary"
|
||||
a:entryValues="@array/p_multiplication_sign_values"/>
|
||||
a:title="@string/c_calc_multiplication_sign"/>
|
||||
|
||||
<ListPreference
|
||||
a:key="@string/p_calc_theme_key"
|
||||
a:title="@string/c_calc_theme"
|
||||
a:entries="@array/p_theme_names"
|
||||
a:entryValues="@array/p_theme_values"
|
||||
a:key="@string/p_calc_theme_key"
|
||||
a:summary="@string/c_calc_theme_summary"
|
||||
a:entryValues="@array/p_theme_values"/>
|
||||
a:title="@string/c_calc_theme"/>
|
||||
|
||||
<ListPreference
|
||||
a:key="@string/p_calc_layout_key"
|
||||
a:title="@string/c_calc_layout"
|
||||
a:entries="@array/p_layout_names"
|
||||
a:entryValues="@array/p_layout_values"
|
||||
a:key="@string/p_calc_layout_key"
|
||||
a:summary="@string/c_calc_layout_summary"
|
||||
a:entryValues="@array/p_layout_values"/>
|
||||
a:title="@string/c_calc_layout"/>
|
||||
|
||||
<android.preference.CheckBoxPreference
|
||||
a:defaultValue="true"
|
||||
a:key="autoOrientation"
|
||||
a:title="@string/c_auto_orientation_title"
|
||||
a:summary="@string/c_auto_orientation_summary"
|
||||
a:defaultValue="true"/>
|
||||
a:title="@string/c_auto_orientation_title"/>
|
||||
|
||||
|
||||
<android.preference.CheckBoxPreference
|
||||
a:defaultValue="true"
|
||||
a:key="showEqualsButton"
|
||||
a:title="@string/c_show_equals_button_title"
|
||||
a:summary="@string/c_show_equals_button_summary"
|
||||
a:defaultValue="true"/>
|
||||
a:title="@string/c_show_equals_button_title"/>
|
||||
|
||||
<android.preference.CheckBoxPreference
|
||||
a:defaultValue="true"
|
||||
a:key="hideNumeralBaseDigits"
|
||||
a:title="@string/c_hide_numeral_base_digits_title"
|
||||
a:summary="@string/c_hide_numeral_base_digits_summary"
|
||||
a:defaultValue="true"/>
|
||||
a:title="@string/c_hide_numeral_base_digits_title"/>
|
||||
|
||||
<android.preference.CheckBoxPreference
|
||||
a:key="history_show_intermediate_calculations"
|
||||
a:title="@string/prefs_history_show_intermediate_calculations_title"
|
||||
a:summary="@string/prefs_history_show_intermediate_calculations_summary"/>
|
||||
a:summary="@string/prefs_history_show_intermediate_calculations_summary"
|
||||
a:title="@string/prefs_history_show_intermediate_calculations_title"/>
|
||||
|
||||
<android.preference.CheckBoxPreference
|
||||
a:key="preventScreenFromFading"
|
||||
a:title="@string/prefs_prevent_screen_from_fading_title"
|
||||
a:summary="@string/prefs_prevent_screen_from_fading_summary"/>
|
||||
a:summary="@string/prefs_prevent_screen_from_fading_summary"
|
||||
a:title="@string/prefs_prevent_screen_from_fading_title"/>
|
||||
|
||||
</PreferenceScreen>
|
Loading…
Reference in New Issue
Block a user