How to update activity after changing the language (locale) inside the application

Users of my application can change the language in the application settings. Is it possible to change the language inside the application without affecting the general language settings? stack overflow.squite After changing the language of the newly created actions, it is displayed with the changed new language, but the current activity and previously created actions that are paused are not updated. How to update actions? I also spent a lot of time changing my preferences, but it didn't work out. When the application restarts, all actions are created again, so now the language has changed correctly.

android:configChanges="locale" 

also added to manifest for all activities. and also support full screen. Currently, I have not done anything in the onResume () method. Is there a way to refresh or refresh activity (without shutting down and restarting)? Am I missing something in the onResume () method?

+45
android
Nov 08 2018-11-11T00:
source share
8 answers

After changing the displayed new types of activity with the changed new language, but the current activity and previously created actions that are paused are not updated. How to update actions?

Pre API 11 (Honeycomb), the easiest way to do existing actions to display in a new language is to restart it. Thus, you do not bother to reload each resource yourself.

 private void restartActivity() { Intent intent = getIntent(); finish(); startActivity(intent); } 

Register OnSharedPreferenceChangeListener in your onShredPreferenceChanged() , call restartActivity() if the language preference has been changed. In my example, only PreferenceActivity is restarted, but you can restart other activities to resume activity by setting a flag.

Update (thanks @stackunderflow): with API 11 (Honeycomb) you should use recreate() instead of restartActivity() .

 public class PreferenceActivity extends android.preference.PreferenceActivity implements OnSharedPreferenceChangeListener { // ... @Override public void onSharedPreferenceChanged(SharedPreferences sharedPreferences, String key) { if (key.equals("pref_language")) { ((Application) getApplication()).setLocale(); restartActivity(); } } @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); addPreferencesFromResource(R.xml.preferences); getPreferenceScreen().getSharedPreferences().registerOnSharedPreferenceChangeListener(this); } @Override protected void onStop() { super.onStop(); getPreferenceScreen().getSharedPreferences().unregisterOnSharedPreferenceChangeListener(this); } } 

I have a post blog on this subject in more detail, but it is in Chinese. Full source code is in github: PreferenceActivity.java

+56
Dec 13
source share

If I imagined that you installed android:configChanges in manifest.xml and created several directories for several languages, such as: values-fr OR values-nl , I could suggest this code (in the Activity class):

 @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.main); Button btn = (Button) findViewById(R.id.btn); btn.setOnClickListener(new OnClickListener() { @Override public void onClick(View v) { // change language by onclick a button Configuration newConfig = new Configuration(); newConfig.locale = Locale.FRENCH; onConfigurationChanged(newConfig); } }); } @Override public void onConfigurationChanged(Configuration newConfig) { super.onConfigurationChanged(newConfig); getBaseContext().getResources().updateConfiguration(newConfig, getBaseContext().getResources().getDisplayMetrics()); setContentView(R.layout.main); setTitle(R.string.app_name); // Checks the active language if (newConfig.locale == Locale.ENGLISH) { Toast.makeText(this, "English", Toast.LENGTH_SHORT).show(); } else if (newConfig.locale == Locale.FRENCH){ Toast.makeText(this, "French", Toast.LENGTH_SHORT).show(); } } 

I tested this code, it is correct.

+20
Jul 23 2018-12-12T00:
source share

Since line resources will already be loaded for the existing locale, already open actions are not automatically displayed using lines from the new locale. The only way to solve this problem is to reload all the lines and set them again in the views. Typically, calling setContentView(...) will be able to cover this (depending on your activity structure), but of course it has the side effect of losing any view state that you had.

 public void onResume() { super.onResume(); ... if (localeHasChanged) { setContentView(R.layout.xxx); } ... } 

You probably won't want to reload the views every time in onResume() , but only when the locale changes. Checking when to refresh views (i.e., localeHasChanged ) is to propagate the locale change event to previous actions. This can be done in various ways, for example, using a static singleton state or saving this event for storage.

You can also try to minimize the number of operations that can be opened when you can change the locale, for example. by selecting on one of the home screens.

+8
Mar 11 '12 at 1:16
source share

For Android 4.2 (API 17) you need to use android:configChanges="locale|layoutDirection" in your AndroidManifest.xml. See onConfigurationchanged not called via jellybean (4.2.1)

+8
Apr 11 '13 at 18:24
source share

I solved the problem with this code

 public void setLocale(String lang) { myLocale = new Locale(lang); Resources res = getResources(); DisplayMetrics dm = res.getDisplayMetrics(); Configuration conf = res.getConfiguration(); conf.locale = myLocale; res.updateConfiguration(conf, dm); onConfigurationChanged(conf); } @Override public void onConfigurationChanged(Configuration newConfig) { iv.setImageDrawable(getResources().getDrawable(R.drawable.keyboard)); greet.setText(R.string.greet); textView1.setText(R.string.langselection); super.onConfigurationChanged(newConfig); } 
+4
Mar 19 '14 at 12:08
source share

You can use recreate(); to restart your activity when the language changes.

I use the following code to restart activity when the language changes:

 SharedPreferences settings = PreferenceManager.getDefaultSharedPreferences(this); Configuration config = getBaseContext().getResources().getConfiguration(); String lang = settings.getString("lang_list", ""); if (! "".equals(lang) && ! config.locale.getLanguage().equals(lang)) { recreate(); //this is used for recreate activity Locale locale = new Locale(lang); Locale.setDefault(locale); config.locale = locale; getBaseContext().getResources().updateConfiguration(config, getBaseContext().getResources().getDisplayMetrics()); } 
+4
Jul 22 '16 at 16:32
source share

Call this method to change the localization of the application:

 public void settingLocale(Context context, String language) { Locale locale; Configuration config = new Configuration(); if(language.equals(LANGUAGE_ENGLISH)) { locale = new Locale("en"); Locale.setDefault(locale); config.locale = locale; }else if(language.equals(LANGUAGE_ARABIC)){ locale = new Locale("hi"); Locale.setDefault(locale); config.locale = locale; } context.getResources().updateConfiguration(config, null); // Here again set the text on view to reflect locale change // and it will pick resource from new locale tv1.setText(R.string.one); //tv1 is textview in my activity } 

Note. Put your lines in the values ​​and values ​​folder.

+3
Jun 03 '15 at 9:05
source share

The way we did this was to use translations:

  • Send a broadcast every time a user changes their language.
  • Register the broadcast receiver in AppActivity.onCreate() and unregister in AppActivity.onDestroy()
  • In BroadcastReceiver.onReceive() just restart the action.

AppActivity is a parent activity that applies to all other activity subclasses.




Below is a snippet of my code that was not tested outside the project, but should give you a good idea.

When a user changes language

 sendBroadcast(new Intent("Language.changed")); 

And in parental activity

 public class AppActivity extends Activity { /** * The receiver that will handle the change of the language. */ private BroadcastReceiver mLangaugeChangedReceiver; @Override protected void onCreate(final Bundle savedInstanceState) { super.onCreate(savedInstanceState); // ... // Other code here // ... // Define receiver mLangaugeChangedReceiver = new BroadcastReceiver() { @Override public void onReceive(final Context context, final Intent intent) { startActivity(getIntent()); finish(); } }; // Register receiver registerReceiver(mLangaugeChangedReceiver, new IntentFilter("Language.changed")); } @Override protected void onDestroy() { super.onDestroy(); // ... // Other cleanup code here // ... // Unregister receiver if (mLangaugeChangedReceiver != null) { try { unregisterReceiver(mLangaugeChangedReceiver); mLangaugeChangedReceiver = null; } catch (final Exception e) {} } } } 

It will also update the activity that changed the language (if it subclasses the above action).

This will lead to the loss of any data, but if it is important, you should have already taken care of this with Actvity.onSaveInstanceState() and Actvity.onRestoreInstanceState() (or the like).

Let me know your thoughts on this.

Hurrah!

+2
Apr 7 '15 at 10:08
source share



All Articles