I have an issue with some devices like Note3 designing in portrait mode only I have both RTL and LTR support when I change the language of the App to RTL it is working fine but when I take a photo with the camera the device rotates and when returned to the app the application ignores the defined locale and uses the device locale which is English and the direction of the app changes to LTR but with the strings of the RTL until you navigate to another screen all the app will become LTR and this happens only when the device locale is English only. when the device locale is Arabic this does not happen. Here is my code for the locale
public class MvpApp extends Application {
AppDataManager dataManager;
private Locale locale = null;
private String language;
@Override
public void onCreate() {
super.onCreate();
Fresco.initialize(this);
final Fabric fabric = new Fabric.Builder(this)
.kits(new Crashlytics())
.debuggable(true)
.build();
Fabric.with(fabric);
AppPreferencesHelper preferencesHelper = new AppPreferencesHelper(getApplicationContext());
ApiModule apiModule = new ApiModule(getApplicationContext());
dataManager = new AppDataManager(getApplicationContext(),
preferencesHelper, apiModule.provideApiService());
String lang = dataManager.getLanguage();
if (lang == null)
language = "en";
else language = lang;
LocaleHelper.setLocale(getApplicationContext(),language);
}
@Override
public void onConfigurationChanged(Configuration newConfig) {
super.onConfigurationChanged(newConfig);
if (locale != null) {
newConfig.locale = locale;
Locale.setDefault(locale);
newConfig.setLayoutDirection(locale);
getBaseContext().getResources().updateConfiguration(newConfig, getBaseContext().getResources().getDisplayMetrics());
}
}
public AppDataManager getDataManager() {
return dataManager;
}
and the locale helper class
public class LocaleHelper {
public static Context onAttach(Context context, String language) {
return setLocale(context, language);
}
public static Context setLocale(Context context, String localeSpec) {
Locale locale = new Locale(localeSpec);
Locale.setDefault(locale);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
return updateResources(context, locale);
} else {
return updateResourcesLegacy(context, locale);
}
}
@TargetApi(Build.VERSION_CODES.N)
private static Context updateResources(Context context, Locale locale) {
Configuration configuration = context.getResources().getConfiguration();
configuration.setLocale(locale);
configuration.setLayoutDirection(locale);
return context.createConfigurationContext(configuration);
}
@SuppressWarnings("deprecation")
private static Context updateResourcesLegacy(Context context, Locale locale) {
Resources resources = context.getResources();
Configuration configuration = resources.getConfiguration();
configuration.locale = locale;
configuration.setLayoutDirection(locale);
resources.updateConfiguration(configuration, resources.getDisplayMetrics());
return context;
}
}
I have managed to overcome this issue but overriding onConfigurationChanged in the activities and adding in the manifest this line
android:configChanges="orientation|screenSize|layoutDirection|locale"
@Override
public void onConfigurationChanged(Configuration newConfig) {
super.onConfigurationChanged(newConfig);
Locale locale = new Locale(presenter.getLanguage());
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
newConfig.setLocale(locale);
Locale.setDefault(locale);
newConfig.setLayoutDirection(locale);
this.createConfigurationContext(newConfig);
} else {
newConfig.locale = locale;
Locale.setDefault(locale);
newConfig.setLayoutDirection(locale);
getBaseContext().getResources().updateConfiguration(newConfig, getBaseContext().getResources().getDisplayMetrics());
}
}