diff --git a/mastodon/src/main/java/org/joinmastodon/android/GlobalUserPreferences.java b/mastodon/src/main/java/org/joinmastodon/android/GlobalUserPreferences.java index 9274af267..5ef37ee08 100644 --- a/mastodon/src/main/java/org/joinmastodon/android/GlobalUserPreferences.java +++ b/mastodon/src/main/java/org/joinmastodon/android/GlobalUserPreferences.java @@ -1,15 +1,17 @@ package org.joinmastodon.android; +import static org.joinmastodon.android.api.MastodonAPIController.gson; + import android.content.Context; import android.content.SharedPreferences; -import android.content.res.Resources; -import android.os.Build; -import android.os.LocaleList; -import java.util.ArrayList; -import java.util.Arrays; + +import com.google.gson.JsonSyntaxException; +import com.google.gson.reflect.TypeToken; + +import java.lang.reflect.Type; +import java.util.HashMap; import java.util.List; -import java.util.Locale; -import java.util.stream.Collectors; +import java.util.Map; public class GlobalUserPreferences{ public static boolean playGifs; @@ -25,26 +27,19 @@ public class GlobalUserPreferences{ public static boolean voteButtonForSingleChoice; public static ThemePreference theme; public static ColorPreference color; - public static List recentLanguages; - private static String defaultRecentLanguages; - - static { - List systemLocales = new ArrayList<>();; - if (Build.VERSION.SDK_INT < Build.VERSION_CODES.N) { - systemLocales.add(Resources.getSystem().getConfiguration().locale); - } else { - LocaleList localeList = Resources.getSystem().getConfiguration().getLocales(); - for (int i = 0; i < localeList.size(); i++) systemLocales.add(localeList.get(i)); - } - - defaultRecentLanguages = systemLocales.stream().map(Locale::getLanguage).collect(Collectors.joining(",")); - } + private final static Type recentLanguagesType = new TypeToken>>() {}.getType(); + public static Map> recentLanguages; private static SharedPreferences getPrefs(){ return MastodonApp.context.getSharedPreferences("global", Context.MODE_PRIVATE); } + private static T fromJson(String json, Type type, T orElse) { + try { return gson.fromJson(json, type); } + catch (JsonSyntaxException ignored) { return orElse; } + } + public static void load(){ SharedPreferences prefs=getPrefs(); playGifs=prefs.getBoolean("playGifs", true); @@ -60,7 +55,7 @@ public class GlobalUserPreferences{ voteButtonForSingleChoice=prefs.getBoolean("voteButtonForSingleChoice", true); theme=ThemePreference.values()[prefs.getInt("theme", 0)]; color=ColorPreference.values()[prefs.getInt("color", 0)]; - recentLanguages=Arrays.stream(prefs.getString("recentLanguages", defaultRecentLanguages).split(",")).filter(s->!s.isEmpty()).collect(Collectors.toList()); + recentLanguages=fromJson(prefs.getString("recentLanguages", "{}"), recentLanguagesType, new HashMap<>()); } public static void save(){ @@ -77,7 +72,7 @@ public class GlobalUserPreferences{ .putBoolean("disableMarquee", disableMarquee) .putInt("theme", theme.ordinal()) .putInt("color", color.ordinal()) - .putString("recentLanguages", String.join(",", recentLanguages)) + .putString("recentLanguages", gson.toJson(recentLanguages)) .apply(); } diff --git a/mastodon/src/main/java/org/joinmastodon/android/fragments/ComposeFragment.java b/mastodon/src/main/java/org/joinmastodon/android/fragments/ComposeFragment.java index cd099f9b7..3f2666713 100644 --- a/mastodon/src/main/java/org/joinmastodon/android/fragments/ComposeFragment.java +++ b/mastodon/src/main/java/org/joinmastodon/android/fragments/ComposeFragment.java @@ -1,5 +1,9 @@ package org.joinmastodon.android.fragments; +import static org.joinmastodon.android.GlobalUserPreferences.recentLanguages; +import static org.joinmastodon.android.utils.MastodonLanguage.allLanguages; +import static org.joinmastodon.android.utils.MastodonLanguage.defaultRecentLanguages; + import android.animation.ObjectAnimator; import android.annotation.SuppressLint; import android.app.Activity; @@ -98,6 +102,7 @@ import org.joinmastodon.android.ui.views.ComposeEditText; import org.joinmastodon.android.ui.views.ComposeMediaLayout; import org.joinmastodon.android.ui.views.ReorderableLinearLayout; import org.joinmastodon.android.ui.views.SizeListenerLinearLayout; +import org.joinmastodon.android.utils.MastodonLanguage; import org.parceler.Parcel; import org.parceler.Parcels; @@ -106,10 +111,9 @@ import java.net.SocketException; import java.net.UnknownHostException; import java.time.temporal.ChronoUnit; import java.util.ArrayList; -import java.util.Collections; -import java.util.Comparator; import java.util.List; import java.util.Locale; +import java.util.Optional; import java.util.UUID; import java.util.regex.Matcher; import java.util.regex.Pattern; @@ -135,7 +139,6 @@ public class ComposeFragment extends MastodonToolbarFragment implements OnBackPr // from https://github.com/mastodon/mastodon-ios/blob/main/Mastodon/Helper/MastodonRegex.swift private static final Pattern AUTO_COMPLETE_PATTERN=Pattern.compile("(? allIsoLanguages; @SuppressLint("NewApi") // this class actually exists on 6.0 private final BreakIterator breakIterator=BreakIterator.getCharacterInstance(); @@ -198,22 +201,7 @@ public class ComposeFragment extends MastodonToolbarFragment implements OnBackPr private Runnable updateUploadEtaRunnable; private String language; - - static { - Locale[] locales = Locale.getAvailableLocales(); - List allLocales = new ArrayList<>(); - List addedLanguages = new ArrayList<>(); - for (Locale locale : locales) { - String lang = locale.getLanguage(); - if (!addedLanguages.contains(lang)) { - allLocales.add(locale); - addedLanguages.add(lang); - } - } - - Collections.sort(allLocales, Comparator.comparing(l -> l.getDisplayLanguage(Locale.getDefault()))); - allIsoLanguages = allLocales; - } + private MastodonLanguage.LanguageResolver languageResolver; @Override public void onCreate(Bundle savedInstanceState){ @@ -226,6 +214,7 @@ public class ComposeFragment extends MastodonToolbarFragment implements OnBackPr instanceDomain=session.domain; customEmojis=AccountSessionManager.getInstance().getCustomEmojis(instanceDomain); instance=AccountSessionManager.getInstance().getInstanceInfo(instanceDomain); + languageResolver=new MastodonLanguage.LanguageResolver(instance); if(getArguments().containsKey("editStatus")){ editingStatus=Parcels.unwrap(getArguments().getParcelable("editStatus")); redraftStatus=getArguments().getBoolean("redraftStatus"); @@ -657,13 +646,13 @@ public class ComposeFragment extends MastodonToolbarFragment implements OnBackPr } private void updateLanguage(String lang) { - updateLanguage(new Locale(lang)); + updateLanguage(languageResolver.from(lang)); } - private void updateLanguage(Locale loc) { + private void updateLanguage(MastodonLanguage loc) { language = loc.getLanguage(); - languageButton.setText(loc.getDisplayLanguage(loc)); - languageButton.setContentDescription(getActivity().getString(R.string.sk_post_language, loc.getDisplayLanguage(Locale.getDefault()))); + languageButton.setText(loc.getLanguageName()); + languageButton.setContentDescription(getActivity().getString(R.string.sk_post_language, loc.getDefaultName())); } @SuppressLint("ClickableViewAccessibility") @@ -678,31 +667,31 @@ public class ComposeFragment extends MastodonToolbarFragment implements OnBackPr languageButton.setCompoundDrawableTintList(languageButton.getTextColors()); languageButton.setCompoundDrawablePadding(V.dp(6)); + Preferences prefs = AccountSessionManager.getInstance().getAccount(accountID).preferences; + String defaultLang = prefs != null ? prefs.postingDefaultLanguage : null; + if (defaultLang != null) updateLanguage(defaultLang); + else updateLanguage(languageResolver.getDefault()); + languagePopup=new PopupMenu(getActivity(), languageButton); languageButton.setOnTouchListener(languagePopup.getDragToOpenListener()); languageButton.setOnClickListener(v->languagePopup.show()); - Preferences prefs = AccountSessionManager.getInstance().getAccount(accountID).preferences; - String defaultLang = prefs != null ? prefs.postingDefaultLanguage : null; - if (defaultLang != null) updateLanguage(defaultLang); - else updateLanguage(Locale.getDefault()); - Menu languageMenu = languagePopup.getMenu(); - for (String recentLanguage : GlobalUserPreferences.recentLanguages) { - Locale loc = new Locale(recentLanguage); - languageMenu.add(0, allIsoLanguages.indexOf(loc), Menu.NONE, loc.getDisplayLanguage(Locale.getDefault())); + for (String recentLanguage : Optional.ofNullable(recentLanguages.get(accountID)).orElse(defaultRecentLanguages)) { + MastodonLanguage l = languageResolver.from(recentLanguage); + languageMenu.add(0, allLanguages.indexOf(l), Menu.NONE, getActivity().getString(R.string.sk_language_name, l.getDefaultName(), l.getLanguageName())); } SubMenu allLanguagesMenu = languageMenu.addSubMenu(R.string.sk_all_languages); - for (int i = 0; i < allIsoLanguages.size(); i++) { - Locale loc = allIsoLanguages.get(i); - allLanguagesMenu.add(0, i, Menu.NONE, loc.getDisplayLanguage(Locale.getDefault())); + for (int i = 0; i < allLanguages.size(); i++) { + MastodonLanguage l = allLanguages.get(i); + allLanguagesMenu.add(0, i, Menu.NONE, getActivity().getString(R.string.sk_language_name, l.getDefaultName(), l.getLanguageName())); } languagePopup.setOnMenuItemClickListener(i->{ if (i.hasSubMenu()) return false; - updateLanguage(allIsoLanguages.get(i.getItemId())); + updateLanguage(allLanguages.get(i.getItemId())); return true; }); @@ -861,11 +850,13 @@ public class ComposeFragment extends MastodonToolbarFragment implements OnBackPr .exec(accountID); } - List recentLanguages = new ArrayList<>(GlobalUserPreferences.recentLanguages); - recentLanguages.remove(language); - recentLanguages.add(0, language); - GlobalUserPreferences.recentLanguages = recentLanguages.stream().limit(4).collect(Collectors.toList()); - GlobalUserPreferences.save(); + if (replyTo == null) { + List newRecentLanguages = new ArrayList<>(Optional.ofNullable(recentLanguages.get(accountID)).orElse(defaultRecentLanguages)); + newRecentLanguages.remove(language); + newRecentLanguages.add(0, language); + recentLanguages.put(accountID, newRecentLanguages.stream().limit(4).collect(Collectors.toList())); + GlobalUserPreferences.save(); + } } private boolean hasDraft(){ diff --git a/mastodon/src/main/java/org/joinmastodon/android/fragments/SettingsFragment.java b/mastodon/src/main/java/org/joinmastodon/android/fragments/SettingsFragment.java index f25afd82d..60648fe9b 100644 --- a/mastodon/src/main/java/org/joinmastodon/android/fragments/SettingsFragment.java +++ b/mastodon/src/main/java/org/joinmastodon/android/fragments/SettingsFragment.java @@ -48,6 +48,7 @@ import org.joinmastodon.android.ui.utils.UiUtils; import org.joinmastodon.android.updater.GithubSelfUpdater; import java.util.ArrayList; +import java.util.Objects; import java.util.function.Consumer; import androidx.annotation.DrawableRes; @@ -160,7 +161,7 @@ public class SettingsFragment extends MastodonToolbarFragment{ items.add(new TextItem(R.string.sk_settings_contribute, ()->UiUtils.launchWebBrowser(getActivity(), "https://github.com/sk22/megalodon"))); items.add(new TextItem(R.string.settings_clear_cache, this::clearImageCache)); items.add(new TextItem(R.string.sk_clear_recent_languages, ()->UiUtils.showConfirmationAlert(getActivity(), R.string.sk_clear_recent_languages, R.string.sk_confirm_clear_recent_languages, R.string.clear, ()->{ - GlobalUserPreferences.recentLanguages.clear(); + GlobalUserPreferences.recentLanguages.remove(accountID); GlobalUserPreferences.save(); }))); items.add(new TextItem(R.string.log_out, this::confirmLogOut)); diff --git a/mastodon/src/main/java/org/joinmastodon/android/utils/MastodonLanguage.java b/mastodon/src/main/java/org/joinmastodon/android/utils/MastodonLanguage.java new file mode 100644 index 000000000..2e4eb949a --- /dev/null +++ b/mastodon/src/main/java/org/joinmastodon/android/utils/MastodonLanguage.java @@ -0,0 +1,101 @@ + +package org.joinmastodon.android.utils; + +import static org.joinmastodon.android.api.MastodonAPIController.gson; + +import android.content.res.Resources; +import android.os.Build; +import android.os.LocaleList; + +import org.joinmastodon.android.model.Instance; + +import java.util.ArrayList; +import java.util.Collections; +import java.util.Comparator; +import java.util.List; +import java.util.Locale; +import java.util.Objects; +import java.util.stream.Collectors; + +public class MastodonLanguage { + // On an up-to-date Mastodon instance: + // copy(JSON.stringify(JSON.stringify(JSON.parse(document.getElementById('initial-state').textContent).languages))) + public static String languagesJson = + "[[\"aa\",\"Afar\",\"Afaraf\"],[\"ab\",\"Abkhaz\",\"аҧсуа бызшәа\"],[\"ae\",\"Avestan\",\"avesta\"],[\"af\",\"Afrikaans\",\"Afrikaans\"],[\"ak\",\"Akan\",\"Akan\"],[\"am\",\"Amharic\",\"አማርኛ\"],[\"an\",\"Aragonese\",\"aragonés\"],[\"ar\",\"Arabic\",\"اللغة العربية\"],[\"as\",\"Assamese\",\"অসমীয়া\"],[\"av\",\"Avaric\",\"авар мацӀ\"],[\"ay\",\"Aymara\",\"aymar aru\"],[\"az\",\"Azerbaijani\",\"azərbaycan dili\"],[\"ba\",\"Bashkir\",\"башҡорт теле\"],[\"be\",\"Belarusian\",\"беларуская мова\"],[\"bg\",\"Bulgarian\",\"български език\"],[\"bh\",\"Bihari\",\"भोजपुरी\"],[\"bi\",\"Bislama\",\"Bislama\"],[\"bm\",\"Bambara\",\"bamanankan\"],[\"bn\",\"Bengali\",\"বাংলা\"],[\"bo\",\"Tibetan\",\"བོད་ཡིག\"],[\"br\",\"Breton\",\"brezhoneg\"],[\"bs\",\"Bosnian\",\"bosanski jezik\"],[\"ca\",\"Catalan\",\"Català\"],[\"ce\",\"Chechen\",\"нохчийн мотт\"],[\"ch\",\"Chamorro\",\"Chamoru\"],[\"co\",\"Corsican\",\"corsu\"],[\"cr\",\"Cree\",\"ᓀᐦᐃᔭᐍᐏᐣ\"],[\"cs\",\"Czech\",\"čeština\"],[\"cu\",\"Old Church Slavonic\",\"ѩзыкъ словѣньскъ\"],[\"cv\",\"Chuvash\",\"чӑваш чӗлхи\"],[\"cy\",\"Welsh\",\"Cymraeg\"],[\"da\",\"Danish\",\"dansk\"],[\"de\",\"German\",\"Deutsch\"],[\"dv\",\"Divehi\",\"Dhivehi\"],[\"dz\",\"Dzongkha\",\"རྫོང་ཁ\"],[\"ee\",\"Ewe\",\"Eʋegbe\"],[\"el\",\"Greek\",\"Ελληνικά\"],[\"en\",\"English\",\"English\"],[\"eo\",\"Esperanto\",\"Esperanto\"],[\"es\",\"Spanish\",\"Español\"],[\"et\",\"Estonian\",\"eesti\"],[\"eu\",\"Basque\",\"euskara\"],[\"fa\",\"Persian\",\"فارسی\"],[\"ff\",\"Fula\",\"Fulfulde\"],[\"fi\",\"Finnish\",\"suomi\"],[\"fj\",\"Fijian\",\"Vakaviti\"],[\"fo\",\"Faroese\",\"føroyskt\"],[\"fr\",\"French\",\"Français\"],[\"fy\",\"Western Frisian\",\"Frysk\"],[\"ga\",\"Irish\",\"Gaeilge\"],[\"gd\",\"Scottish Gaelic\",\"Gàidhlig\"],[\"gl\",\"Galician\",\"galego\"],[\"gu\",\"Gujarati\",\"ગુજરાતી\"],[\"gv\",\"Manx\",\"Gaelg\"],[\"ha\",\"Hausa\",\"هَوُسَ\"],[\"he\",\"Hebrew\",\"עברית\"],[\"hi\",\"Hindi\",\"हिन्दी\"],[\"ho\",\"Hiri Motu\",\"Hiri Motu\"],[\"hr\",\"Croatian\",\"Hrvatski\"],[\"ht\",\"Haitian\",\"Kreyòl ayisyen\"],[\"hu\",\"Hungarian\",\"magyar\"],[\"hy\",\"Armenian\",\"Հայերեն\"],[\"hz\",\"Herero\",\"Otjiherero\"],[\"ia\",\"Interlingua\",\"Interlingua\"],[\"id\",\"Indonesian\",\"Bahasa Indonesia\"],[\"ie\",\"Interlingue\",\"Interlingue\"],[\"ig\",\"Igbo\",\"Asụsụ Igbo\"],[\"ii\",\"Nuosu\",\"ꆈꌠ꒿ Nuosuhxop\"],[\"ik\",\"Inupiaq\",\"Iñupiaq\"],[\"io\",\"Ido\",\"Ido\"],[\"is\",\"Icelandic\",\"Íslenska\"],[\"it\",\"Italian\",\"Italiano\"],[\"iu\",\"Inuktitut\",\"ᐃᓄᒃᑎᑐᑦ\"],[\"ja\",\"Japanese\",\"日本語\"],[\"jv\",\"Javanese\",\"basa Jawa\"],[\"ka\",\"Georgian\",\"ქართული\"],[\"kg\",\"Kongo\",\"Kikongo\"],[\"ki\",\"Kikuyu\",\"Gĩkũyũ\"],[\"kj\",\"Kwanyama\",\"Kuanyama\"],[\"kk\",\"Kazakh\",\"қазақ тілі\"],[\"kl\",\"Kalaallisut\",\"kalaallisut\"],[\"km\",\"Khmer\",\"ខេមរភាសា\"],[\"kn\",\"Kannada\",\"ಕನ್ನಡ\"],[\"ko\",\"Korean\",\"한국어\"],[\"kr\",\"Kanuri\",\"Kanuri\"],[\"ks\",\"Kashmiri\",\"कश्मीरी\"],[\"ku\",\"Kurdish\",\"Kurdî\"],[\"kv\",\"Komi\",\"коми кыв\"],[\"kw\",\"Cornish\",\"Kernewek\"],[\"ky\",\"Kyrgyz\",\"Кыргызча\"],[\"la\",\"Latin\",\"latine\"],[\"lb\",\"Luxembourgish\",\"Lëtzebuergesch\"],[\"lg\",\"Ganda\",\"Luganda\"],[\"li\",\"Limburgish\",\"Limburgs\"],[\"ln\",\"Lingala\",\"Lingála\"],[\"lo\",\"Lao\",\"ລາວ\"],[\"lt\",\"Lithuanian\",\"lietuvių kalba\"],[\"lu\",\"Luba-Katanga\",\"Tshiluba\"],[\"lv\",\"Latvian\",\"latviešu valoda\"],[\"mg\",\"Malagasy\",\"fiteny malagasy\"],[\"mh\",\"Marshallese\",\"Kajin M̧ajeļ\"],[\"mi\",\"Māori\",\"te reo Māori\"],[\"mk\",\"Macedonian\",\"македонски јазик\"],[\"ml\",\"Malayalam\",\"മലയാളം\"],[\"mn\",\"Mongolian\",\"Монгол хэл\"],[\"mr\",\"Marathi\",\"मराठी\"],[\"ms\",\"Malay\",\"Bahasa Melayu\"],[\"mt\",\"Maltese\",\"Malti\"],[\"my\",\"Burmese\",\"ဗမာစာ\"],[\"na\",\"Nauru\",\"Ekakairũ Naoero\"],[\"nb\",\"Norwegian Bokmål\",\"Norsk bokmål\"],[\"nd\",\"Northern Ndebele\",\"isiNdebele\"],[\"ne\",\"Nepali\",\"नेपाली\"],[\"ng\",\"Ndonga\",\"Owambo\"],[\"nl\",\"Dutch\",\"Nederlands\"],[\"nn\",\"Norwegian Nynorsk\",\"Norsk Nynorsk\"],[\"no\",\"Norwegian\",\"Norsk\"],[\"nr\",\"Southern Ndebele\",\"isiNdebele\"],[\"nv\",\"Navajo\",\"Diné bizaad\"],[\"ny\",\"Chichewa\",\"chiCheŵa\"],[\"oc\",\"Occitan\",\"occitan\"],[\"oj\",\"Ojibwe\",\"ᐊᓂᔑᓈᐯᒧᐎᓐ\"],[\"om\",\"Oromo\",\"Afaan Oromoo\"],[\"or\",\"Oriya\",\"ଓଡ଼ିଆ\"],[\"os\",\"Ossetian\",\"ирон æвзаг\"],[\"pa\",\"Panjabi\",\"ਪੰਜਾਬੀ\"],[\"pi\",\"Pāli\",\"पाऴि\"],[\"pl\",\"Polish\",\"Polski\"],[\"ps\",\"Pashto\",\"پښتو\"],[\"pt\",\"Portuguese\",\"Português\"],[\"qu\",\"Quechua\",\"Runa Simi\"],[\"rm\",\"Romansh\",\"rumantsch grischun\"],[\"rn\",\"Kirundi\",\"Ikirundi\"],[\"ro\",\"Romanian\",\"Română\"],[\"ru\",\"Russian\",\"Русский\"],[\"rw\",\"Kinyarwanda\",\"Ikinyarwanda\"],[\"sa\",\"Sanskrit\",\"संस्कृतम्\"],[\"sc\",\"Sardinian\",\"sardu\"],[\"sd\",\"Sindhi\",\"सिन्धी\"],[\"se\",\"Northern Sami\",\"Davvisámegiella\"],[\"sg\",\"Sango\",\"yângâ tî sängö\"],[\"si\",\"Sinhala\",\"සිංහල\"],[\"sk\",\"Slovak\",\"slovenčina\"],[\"sl\",\"Slovenian\",\"slovenščina\"],[\"sn\",\"Shona\",\"chiShona\"],[\"so\",\"Somali\",\"Soomaaliga\"],[\"sq\",\"Albanian\",\"Shqip\"],[\"sr\",\"Serbian\",\"српски језик\"],[\"ss\",\"Swati\",\"SiSwati\"],[\"st\",\"Southern Sotho\",\"Sesotho\"],[\"su\",\"Sundanese\",\"Basa Sunda\"],[\"sv\",\"Swedish\",\"Svenska\"],[\"sw\",\"Swahili\",\"Kiswahili\"],[\"ta\",\"Tamil\",\"தமிழ்\"],[\"te\",\"Telugu\",\"తెలుగు\"],[\"tg\",\"Tajik\",\"тоҷикӣ\"],[\"th\",\"Thai\",\"ไทย\"],[\"ti\",\"Tigrinya\",\"ትግርኛ\"],[\"tk\",\"Turkmen\",\"Türkmen\"],[\"tl\",\"Tagalog\",\"Wikang Tagalog\"],[\"tn\",\"Tswana\",\"Setswana\"],[\"to\",\"Tonga\",\"faka Tonga\"],[\"tr\",\"Turkish\",\"Türkçe\"],[\"ts\",\"Tsonga\",\"Xitsonga\"],[\"tt\",\"Tatar\",\"татар теле\"],[\"tw\",\"Twi\",\"Twi\"],[\"ty\",\"Tahitian\",\"Reo Tahiti\"],[\"ug\",\"Uyghur\",\"ئۇيغۇرچە‎\"],[\"uk\",\"Ukrainian\",\"Українська\"],[\"ur\",\"Urdu\",\"اردو\"],[\"uz\",\"Uzbek\",\"Ўзбек\"],[\"ve\",\"Venda\",\"Tshivenḓa\"],[\"vi\",\"Vietnamese\",\"Tiếng Việt\"],[\"vo\",\"Volapük\",\"Volapük\"],[\"wa\",\"Walloon\",\"walon\"],[\"wo\",\"Wolof\",\"Wollof\"],[\"xh\",\"Xhosa\",\"isiXhosa\"],[\"yi\",\"Yiddish\",\"ייִדיש\"],[\"yo\",\"Yoruba\",\"Yorùbá\"],[\"za\",\"Zhuang\",\"Saɯ cueŋƅ\"],[\"zh\",\"Chinese\",\"中文\"],[\"zu\",\"Zulu\",\"isiZulu\"],[\"ast\",\"Asturian\",\"Asturianu\"],[\"ckb\",\"Sorani (Kurdish)\",\"سۆرانی\"],[\"jbo\",\"Lojban\",\"la .lojban.\"],[\"kab\",\"Kabyle\",\"Taqbaylit\"],[\"kmr\",\"Kurmanji (Kurdish)\",\"Kurmancî\"],[\"ldn\",\"Láadan\",\"Láadan\"],[\"lfn\",\"Lingua Franca Nova\",\"lingua franca nova\"],[\"sco\",\"Scots\",\"Scots\"],[\"tok\",\"Toki Pona\",\"toki pona\"],[\"zba\",\"Balaibalan\",\"باليبلن\"],[\"zgh\",\"Standard Moroccan Tamazight\",\"ⵜⴰⵎⴰⵣⵉⵖⵜ\"]]"; + public static final List allLanguages; + public static final MastodonLanguage ENGLISH = new MastodonLanguage("en", "English", "English"); + + static { + String[][] languages = gson.fromJson(languagesJson, String[][].class); + allLanguages = new ArrayList<>(); + for (String[] language : languages) allLanguages.add(new MastodonLanguage(language[0], language[1], language[2])); + Collections.sort(allLanguages, Comparator.comparing(MastodonLanguage::getDefaultName)); + } + + public static List defaultRecentLanguages; + + static { + List systemLocales = new ArrayList<>();; + if (Build.VERSION.SDK_INT < Build.VERSION_CODES.N) { + systemLocales.add(Resources.getSystem().getConfiguration().locale); + } else { + LocaleList localeList = Resources.getSystem().getConfiguration().getLocales(); + for (int i = 0; i < localeList.size(); i++) systemLocales.add(localeList.get(i)); + } + + defaultRecentLanguages = systemLocales.stream().map(Locale::getLanguage).collect(Collectors.toList()); + } + + public final String languageTag, name, englishName; + public final Locale locale; + + private MastodonLanguage(String languageTag, String englishName, String name) { + this.locale = new Locale(languageTag); + this.languageTag = languageTag.toLowerCase(Locale.ROOT); + this.name = name; + this.englishName = englishName; + } + + public String getDefaultName() { + String accordingToLocale = locale.getDisplayLanguage(Locale.getDefault()); + return accordingToLocale.equals(languageTag) ? englishName : accordingToLocale; + } + + public String getLanguageName() { return name; } + + public String getLanguage() { return languageTag; } + + @Override + public boolean equals(Object o) { + if (this == o) return true; + if (o == null || getClass() != o.getClass()) return false; + return Objects.equals(languageTag, ((MastodonLanguage) o).languageTag); + } + + @Override + public int hashCode() { + return languageTag != null ? languageTag.hashCode() : 0; + } + + public static class LanguageResolver { + private final MastodonLanguage fallbackLanguage; + + public LanguageResolver(Instance instanceInfo) { + String fallbackLanguageTag = !instanceInfo.languages.isEmpty() ? instanceInfo.languages.get(0) : ENGLISH.languageTag; + fallbackLanguage = allLanguages.stream() + .filter(l->l.languageTag.equalsIgnoreCase(fallbackLanguageTag)).findAny() + .orElse(ENGLISH); + } + + public MastodonLanguage from(String language) { + return allLanguages.stream() + .filter(l->l.locale.equals(new Locale(language))).findAny() + .orElse(fallbackLanguage); + } + + public MastodonLanguage getDefault() { + return from(Locale.getDefault().getLanguage()); + } + } +} + diff --git a/mastodon/src/main/res/values/strings_sk.xml b/mastodon/src/main/res/values/strings_sk.xml index 7dbe7a06f..617804bf5 100644 --- a/mastodon/src/main/res/values/strings_sk.xml +++ b/mastodon/src/main/res/values/strings_sk.xml @@ -53,6 +53,7 @@ Translated using %s Language: %s All languages + %s (%s) Clear recent languages Are you sure you want to clear your recently used languages?