Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 8858ff2b authored by Calvin Pan's avatar Calvin Pan Committed by Automerger Merge Worker
Browse files

Merge "Filter the locale not in resources" into tm-dev am: 53c97993

parents be55f650 53c97993
Loading
Loading
Loading
Loading
+77 −19
Original line number Diff line number Diff line
@@ -20,12 +20,15 @@ import static com.android.internal.app.AppLocaleStore.AppLocaleResult.LocaleStat

import android.app.LocaleConfig;
import android.content.Context;
import android.content.pm.ApplicationInfo;
import android.content.pm.InstallSourceInfo;
import android.content.pm.PackageManager;
import android.os.LocaleList;
import android.util.Log;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.Locale;
import java.util.stream.Collectors;

class AppLocaleStore {
    private static final String TAG = AppLocaleStore.class.getSimpleName();
@@ -34,7 +37,8 @@ class AppLocaleStore {
            Context context, String packageName) {
        LocaleConfig localeConfig = null;
        AppLocaleResult.LocaleStatus localeStatus = LocaleStatus.UNKNOWN_FAILURE;
        ArrayList<Locale> appSupportedLocales = new ArrayList<>();
        HashSet<Locale> appSupportedLocales = new HashSet<>();
        HashSet<Locale> assetLocale = getAssetLocales(context, packageName);

        try {
            localeConfig = new LocaleConfig(context.createPackageContext(packageName, 0));
@@ -45,32 +49,43 @@ class AppLocaleStore {
        if (localeConfig != null) {
            if (localeConfig.getStatus() == LocaleConfig.STATUS_SUCCESS) {
                LocaleList packageLocaleList = localeConfig.getSupportedLocales();
                if (packageLocaleList.size() > 0) {
                    localeStatus = LocaleStatus.GET_SUPPORTED_LANGUAGE_FROM_LOCAL_CONFIG;
                boolean shouldFilterNotMatchingLocale = !hasInstallerInfo(context, packageName) &&
                        isSystemApp(context, packageName);

                Log.d(TAG, "filterNonMatchingLocale. " +
                        ", shouldFilterNotMatchingLocale: " + shouldFilterNotMatchingLocale +
                        ", assetLocale size: " + assetLocale.size() +
                        ", packageLocaleList size: " + packageLocaleList.size());

                for (int i = 0; i < packageLocaleList.size(); i++) {
                    appSupportedLocales.add(packageLocaleList.get(i));
                }
                if (shouldFilterNotMatchingLocale) {
                    appSupportedLocales = filterNotMatchingLocale(appSupportedLocales, assetLocale);
                }

                if (appSupportedLocales.size() > 0) {
                    localeStatus = LocaleStatus.GET_SUPPORTED_LANGUAGE_FROM_LOCAL_CONFIG;
                } else {
                    localeStatus = LocaleStatus.NO_SUPPORTED_LANGUAGE_IN_APP;
                }
            } else if (localeConfig.getStatus() == LocaleConfig.STATUS_NOT_SPECIFIED) {
                String[] languages = getAssetLocales(context, packageName);
                if (languages.length > 0) {
                if (assetLocale.size() > 0) {
                    localeStatus = LocaleStatus.GET_SUPPORTED_LANGUAGE_FROM_ASSET;
                    for (String language : languages) {
                        appSupportedLocales.add(Locale.forLanguageTag(language));
                    }
                    appSupportedLocales = assetLocale;
                } else {
                    localeStatus = LocaleStatus.ASSET_LOCALE_IS_EMPTY;
                }
            }
        }
        Log.d(TAG, "getAppSupportedLocales(). status: " + localeStatus
        Log.d(TAG, "getAppSupportedLocales(). package: " + packageName
                + ", status: " + localeStatus
                + ", appSupportedLocales:" + appSupportedLocales.size());
        return new AppLocaleResult(localeStatus, appSupportedLocales);
    }

    private static String[] getAssetLocales(Context context, String packageName) {
    private static HashSet<Locale> getAssetLocales(Context context, String packageName) {
        HashSet<Locale> result = new HashSet<>();
        try {
            PackageManager packageManager = context.getPackageManager();
            String[] locales = packageManager.getResourcesForApplication(
@@ -78,16 +93,59 @@ class AppLocaleStore {
                            .applicationInfo).getAssets().getNonSystemLocales();
            if (locales == null) {
                Log.i(TAG, "[" + packageName + "] locales are null.");
                return new String[0];
            } else if (locales.length <= 0) {
                Log.i(TAG, "[" + packageName + "] locales length is 0.");
                return new String[0];
            } else {
                for (String language : locales) {
                    result.add(Locale.forLanguageTag(language));
                }
            }
            return locales;
        } catch (PackageManager.NameNotFoundException e) {
            Log.w(TAG, "Can not found the package name : " + packageName + " / " + e);
        }
        return new String[0];
        return result;
    }

    private static HashSet<Locale> filterNotMatchingLocale(
            HashSet<Locale> appSupportedLocales, HashSet<Locale> assetLocale) {
        return appSupportedLocales.stream()
                .filter(locale -> matchLanguageInSet(locale, assetLocale))
                .collect(Collectors.toCollection(HashSet::new));
    }

    private static boolean matchLanguageInSet(Locale locale, HashSet<Locale> localesSet) {
        if (localesSet.contains(locale)) {
            return true;
        }
        for (Locale l: localesSet) {
            if(LocaleList.matchesLanguageAndScript(l, locale)) {
                return true;
            }
        }
        return false;
    }

    private static boolean hasInstallerInfo(Context context, String packageName) {
        InstallSourceInfo installSourceInfo;
        try {
            installSourceInfo = context.getPackageManager().getInstallSourceInfo(packageName);
            return installSourceInfo != null;
        } catch (PackageManager.NameNotFoundException e) {
            Log.w(TAG, "Installer info not found for: " + packageName);
        }
        return false;
    }

    private static boolean isSystemApp(Context context, String packageName) {
        ApplicationInfo applicationInfo;
        try {
            applicationInfo = context.getPackageManager()
                    .getApplicationInfoAsUser(packageName, /* flags= */ 0, context.getUserId());
            return applicationInfo.isSystemApp();
        } catch (PackageManager.NameNotFoundException e) {
            Log.w(TAG, "Application info not found for: " + packageName);
        }
        return false;
    }

    static class AppLocaleResult {
@@ -100,9 +158,9 @@ class AppLocaleStore {
        }

        LocaleStatus mLocaleStatus;
        ArrayList<Locale> mAppSupportedLocales;
        HashSet<Locale> mAppSupportedLocales;

        public AppLocaleResult(LocaleStatus localeStatus, ArrayList<Locale> appSupportedLocales) {
        public AppLocaleResult(LocaleStatus localeStatus, HashSet<Locale> appSupportedLocales) {
            this.mLocaleStatus = localeStatus;
            this.mAppSupportedLocales = appSupportedLocales;
        }
+10 −4
Original line number Diff line number Diff line
@@ -36,7 +36,6 @@ import android.widget.SearchView;

import com.android.internal.R;

import java.util.ArrayList;
import java.util.Collections;
import java.util.HashSet;
import java.util.Locale;
@@ -204,13 +203,20 @@ public class LocalePickerWithRegion extends ListFragment implements SearchView.O
    }

    private Set<LocaleStore.LocaleInfo> filterTheLanguagesNotSupportedInApp(
            boolean shouldShowList, ArrayList<Locale> supportedLocales) {
            boolean shouldShowList, HashSet<Locale> supportedLocales) {
        Set<LocaleStore.LocaleInfo> filteredList = new HashSet<>();
        if (shouldShowList) {
        if (!shouldShowList) {
            return filteredList;
        }

        for(LocaleStore.LocaleInfo li: mLocaleList) {
            if (supportedLocales.contains(li.getLocale())) {
                filteredList.add(li);
            } else {
                for(Locale l: supportedLocales) {
                    if(LocaleList.matchesLanguageAndScript(li.getLocale(), l)) {
                        filteredList.add(li);
                        break;
                    }
                }
            }