29

我在 values/strings.xml 中有一个带有英文字符串的 Android 应用程序。对于该文件中的每个字符串,我在 values-ja/strings.xml 中有一个条目,其中包含该字符串的日语翻译。如果我将模拟器、Nexus One 或 Nexus S 设置为日语,UI 会始终显示日语文本。大多数时候。

有时,即使当前语言环境是 ja-JP,UI 的某些部分也会以英文显示。例如,我在我的一项活动的 onCreate() 方法中编写了这个测试代码:

Log.e(TAG, "Default locale = '" + Locale.getDefault().toString() + "'");
Log.e(TAG, "My string = '" + getResources().getString(R.string.my_string) + "'");

有时我会在 LogCat 中看到:

Default locale is 'ja_JP'
My string is '日本'

其他时候我会看到:

Default locale is 'ja_JP'
My string is 'English'

有时这个问题可以通过旋转手机来解决。有时可以通过退出并重新启动应用程序来解决。有时,单个屏幕只有一部分是英文的。有时,通过代码从资源中提取的字符串会出现此问题,有时会出现仅由布局引用的字符串。在我的应用程序中,我没有调用 Locale.setDefault(),所以这不会导致问题。

更新

我找到了一种方法来纠正特定活动的问题。在该活动的 onCreate() 中:

Log.e(TAG, "getString: '" + getString(R.string.my_string) + "'");
Log.e(TAG, "getResources().getConfiguration(): '" +
      getResources().getConfiguration().toString() + "'");
Log.e(TAG, "getResources().getDisplayMetrics(): '" +
      getResources().getDisplayMetrics().toString() + "'");

Log.e(TAG, "Setting configuration to getConfiguration()");
getResources().updateConfiguration(getResources().getConfiguration(),
     getResources().getDisplayMetrics());

Log.e(TAG, "getString: '" + getString(R.string.my_string) + "'");
Log.e(TAG, "getResources().getConfiguration(): '" +
      getResources().getConfiguration().toString() + "'");
Log.e(TAG, "getResources().getDisplayMetrics(): '" +
      getResources().getDisplayMetrics().toString() + "'");

这会在 LogCat 中产生以下结果:

getString: 'English'
getResources().getConfiguration(): '{ scale=1.0 imsi=0/0 loc=ja_JP touch=3 keys=1/1/2 nav=3/1 orien=1 layout=34 uiMode=17 seq=8}'
getResources().getDisplayMetrics(): 'DisplayMetrics{density=1.5, width=480, height=800, scaledDensity=1.5, xdpi=254.0, ydpi=254.0}'
Setting configuration to getConfiguration()
getString: '日本'
getResources().getConfiguration(): '{ scale=1.0 imsi=0/0 loc=ja_JP touch=3 keys=1/1/2 nav=3/1 orien=1 layout=34 uiMode=17 seq=8}'
getResources().getDisplayMetrics(): 'DisplayMetrics{density=1.5, width=480, height=800, scaledDensity=1.5, xdpi=254.0, ydpi=254.0}'

从日志中可以看出,当前配置没有任何变化,但 getString() 给出了不同的结果。

在我的应用程序中可能使用资源的每个地方都使用此解决方法是不切实际的,但希望这可以提供有关问题所在的提示。

4

3 回答 3

1

这只是一个理论,但您可能会泄漏上下文。基本上,旧的活动可能会报告字符串值,而不是新创建的。

一种测试方法是:

  1. 将 TAG 更改为成员变量(不是静态的!)。
  2. OnCreate,设置TAG = this.toString(),这会将activity的内存地址作为tag。
  3. 让活动使用初始语言环境打印出东西。
  4. 做任何事情来改变语言环境。这应该(从未验证过)重新启动活动,您将获得一个新活动。如果你这样做。然后查看日志,看看标签的内存地址是否正在改变。如果内存地址与上下文泄漏之前相同。
于 2011-04-23T07:08:58.713 回答
0

您是否在应用程序运行时更改区域设置?如果是这样,您是否正确实现了 Activity 生命周期的各种元素(包括onSaveInstanceState()onRestoreInstanceState())?

根据http://developer.android.com/guide/topics/resources/runtime-changes.html,运行时配置的更改会导致 Activity 被销毁并重新启动。听起来您的应用程序注意到了新配置,但没有正确重新启动(直到重新启动整个应用程序或更改方向)。

你在做任何时髦的事情onSaveInstanceStateonDestroy

Ps 如果它仅在某些方向更改时进行自我纠正,您能否告知这些方向更改是否发生在具有不同垂直和水平布局文件的布局上?

于 2011-02-14T20:48:24.760 回答
0

我遇到了同样的问题。

onCreate()对我来说,在从共享首选项(在 中完成)导入语言设置之前,我试图获取字符串(在中onResume())。

于 2019-09-07T08:08:12.273 回答