2015-04-25 2 views
2

У меня есть многоязычное приложение, которое Locale изменено программно.Изменение локали программно с помощью ActionBarActivity и SupportActionBar

Когда приложение впервые создано, он просматривает конкретный файл SharedPreferences и устанавливает локаль соответственно.

Тогда пользователь может перейти к определенному Activity P и выбрать один из доступных языков (теперь доступны только два языка).

Это то, что я делаю в P с lang будучи String:

// set locale to that chosen by the user 
((MyApp) getApplication()).setMyAppLocale(lang); 

// get the Locale object 
Locale locale = ((MyApp) getApplication()).getMyAppLocale(); 

// classic code 
Locale.setDefault(locale); 
Configuration config = new Configuration(); 
config.locale = locale; 
getBaseContext().getResources().updateConfiguration(config, 
     getBaseContext().getResources().getDisplayMetrics()); 

// clear the activity stack and restart the MainActivity 
Intent intent = new Intent(this, MainActivity.class); 
Bundle extras = new Bundle(); 
extras.putBoolean(MainActivity.PARAM_DO_RESTART, true); 
intent.putExtras(extras); 
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TOP); 
startActivity(intent); 
finish(); 

Активность MainActivity получает новый Intent и делает это:

@Override 
public void onNewIntent(Intent anotherIntent) { 
    super.onNewIntent(anotherIntent); 
    setIntent(anotherIntent); 
} 

@Override 
protected void onResume() { 
    super.onResume(); 

    Intent intent = getIntent(); 
    Bundle extras = intent.getExtras(); 
    if(extras != null) { 
     if (extras.getBoolean(PARAM_DO_RESTART, false)) { 
      intent.putExtra(PARAM_DO_RESTART, false); 
      setIntent(intent); 
      finish(); 
      startActivity(intent); 
     } 
    } // if extras != null 

Таким образом, MainActivity «ы onCreate вызывается снова, и ресурсы снова загружаются в новый Locale.

Все в порядке, но одна вещь.

Все строки отображаются в правильной локали, , но названия всех видов деятельности остаются на том языке, в котором они были впервые созданы, когда приложение было запущено. Они не изменились. Мои действия на самом деле являются экземплярами ActionBarActivity, а названия показаны в SupportActionBar.

Вопрос: как я могу заставить эти названия быть изменены в соответствии с текущим Locale?

Примечание. Простым решением является называть getSupportActionBar().setTitle(getString(R.string.title_activity_X)); за каждые Activity X. Однако, поскольку существует немало мероприятий, я бы скорее нашел способ сделать это автоматически.

Примечание: Я использую API-уровень 19 с поддержкой библиотеки v7.

ответ

0

В соответствии с этим answer заголовок доступен только для чтения, поэтому вы должны указывать заголовок вручную и не можете делать это автоматически. Я предполагаю, что он использует ресурс, указанный в AndroidManifest.xml, который нельзя изменить динамически.

+0

В этом проблема, но это ошибка или ее следует учитывать. Заголовок не доступен только для чтения. Есть способ сделать это автоматически, я добавлю ответ, как только мне позволено. –

+0

К сожалению, я не мог найти никаких документов об этом, но, на мой взгляд, это не может быть сделано так же, как и в 'manifest', есть другие метки, например' Theme', не могут быть изменены, если вы не назовете 'setTheme()' , Я добавляю этот вопрос в избранное, я бы хотел прочитать ответ, если вы найдете трюк. Cheers :) – Yurets

0

Я нашел способ в ответе, предоставленном MiroM, this question on StackOverflow. Добавьте следующий код в свой базовый класс Activity, где он лучше всего подходит.

PackageManager pm = getPackageManager(); 
    try { 
     ActivityInfo ai = pm.getActivityInfo(this.getComponentName(), PackageManager.GET_ACTIVITIES|PackageManager.GET_META_DATA); 
     if (ai.labelRes != 0) { 
      getSupportActionBar().setTitle(ai.labelRes); 
     } 
    } catch (PackageManager.NameNotFoundException e) { 
     e.stacktrace(); 
    } 

Я надеюсь, что кто-то еще достигнет этого вопроса и предоставит более общий способ сделать это. Этот метод действительно полезен, когда ваши действия имеют общий суперкласс, который был моим делом, но в целом это не так.

+1

хорошо один.также для того, чтобы сделать его более общим, я думаю, что этот метод можно использовать в «BaseActivity.class», расширенном от «ActionBarActivity», поэтому все другие действия, распространяемые от «BaseActivity», будут иметь такое же поведение. – Yurets

Смежные вопросы