3 回答

TA貢獻(xiàn)1856條經(jīng)驗(yàn) 獲得超17個贊
背景:
Android WebView是使用WebKit構(gòu)建的。雖然它最初是AOSP的一部分,但從KitKat開始,便決定將其WebView拆分為一個名為Android System WebView的單獨(dú)組件。本質(zhì)上,它是一個預(yù)裝有Android設(shè)備的Android系統(tǒng)應(yīng)用。就像其他系統(tǒng)應(yīng)用(例如Google Play服務(wù)和Play商店應(yīng)用)一樣,它會定期更新。您可以在已安裝的系統(tǒng)應(yīng)用程序列表中看到它:
Android系統(tǒng)WebView
Android 7.0的變化:
從Android N開始,Chrome應(yīng)用將用于渲染W(wǎng)ebView第三方Android應(yīng)用中的任何/全部。在開箱即用的Android N手機(jī)中,根本沒有Android WebView System應(yīng)用程序。在已收到Android N的OTA更新的設(shè)備中,Android系統(tǒng)WebView被禁用:
WebView已禁用
和
WebView已禁用
此外,已引入多語言環(huán)境支持,并且設(shè)備具有多種默認(rèn)語言:
在此處輸入圖片說明
對于具有多種語言的應(yīng)用程序,這具有重要的意義。如果您的應(yīng)用包含WebView,則這些內(nèi)容將使用Chrome應(yīng)用呈現(xiàn)。由于Chrome 本身就是一個Android應(yīng)用,因此以其自己的沙盒流程運(yùn)行,因此不會綁定到您的應(yīng)用設(shè)置的語言環(huán)境。取而代之的是,Chrome將還原為主要設(shè)備的語言環(huán)境。例如,假設(shè)您的應(yīng)用語言環(huán)境設(shè)置為ar-AE,而設(shè)備的主要語言環(huán)境設(shè)置為en-US。在這種情況下,Activity包含的語言環(huán)境WebView將從ar-AE變?yōu)閑n-US,并且將顯示來自相應(yīng)語言環(huán)境文件夾的字符串和資源。您可能會在Activity具有WebViews的那些s 上看到大量的LTR和RTL字符串/資源。
解決方案:
完整的解決方案包括兩個步驟:
步驟1:
首先,在每個Activity(或至少每個Activity具有的)中手動重置默認(rèn)語言環(huán)境WebView。
public static void setLocale(Locale locale){
Context context = MyApplication.getInstance();
Resources resources = context.getResources();
Configuration configuration = resources.getConfiguration();
Locale.setDefault(locale);
configuration.setLocale(locale);
if (Build.VERSION.SDK_INT >= 25) {
context = context.getApplicationContext().createConfigurationContext(configuration);
context = context.createConfigurationContext(configuration);
}
context.getResources().updateConfiguration(configuration,
resources.getDisplayMetrics());
}
在調(diào)用之前調(diào)用上面的方法setContentView(...)在onCreate()所有的活動的方法。該locale參數(shù)應(yīng)該是Locale您希望設(shè)置的默認(rèn)值。例如,如果您希望將阿拉伯語/阿拉伯聯(lián)合酋長國設(shè)置為默認(rèn)語言環(huán)境,則應(yīng)傳遞new Locale("ar", "AE")?;蛘?,如果您希望設(shè)置默認(rèn)語言環(huán)境(即Locale由操作系統(tǒng)自動設(shè)置的語言環(huán)境),則應(yīng)通過Locale.US。
第2步:
此外,您需要添加以下代碼行:
new WebView(this).destroy();
在onCreate()您的Application類(如果有的話),和任何其他地方的用戶可以更改語言。這將處理在更改語言后重新啟動應(yīng)用程序時可能發(fā)生的各種極端情況(您可能已經(jīng)注意到其他語言的字符串,或者在更改語言后在Android 7.0 ++ 上Activities具有相反的對齊方式WebView)。
作為附錄,Chrome自定義標(biāo)簽現(xiàn)在是呈現(xiàn)應(yīng)用內(nèi)網(wǎng)頁的首選方式。

TA貢獻(xiàn)1808條經(jīng)驗(yàn) 獲得超4個贊
您的代碼似乎正在為應(yīng)用本身(MyApplication.getInstance())的配置中設(shè)置語言環(huán)境。但是,您需要在擴(kuò)展活動的內(nèi)容視圖之前更新活動上下文的配置。我發(fā)現(xiàn)修改應(yīng)用程序的上下文是不夠的(事實(shí)證明,甚至沒有必要)。如果我不更新每個活動上下文,則行為在各個活動之間是不一致的。
我采用的方法是子類化AppCompatActivity(或者Activity,如果不使用兼容性庫,則使用子類化),然后從該子類派生我的所有活動類。這是我的代碼的簡化版本:
public class LocaleSensitiveActivity extends AppCompatActivity {
@Override protected void onCreate(Bundle savedInstanceState) {
Locale locale = ... // the locale to use for this activity
fixupLocale(this, locale);
super.onCreate(savedInstanceState);
...
}
static void fixupLocale(Context ctx, Locale newLocale) {
final Resources res = ctx.getResources();
final Configuration config = res.getConfiguration();
final Locale curLocale = getLocale(config);
if (!curLocale.equals(newLocale)) {
Locale.setDefault(newLocale);
final Configuration conf = new Configuration(config);
conf.setLocale(newLocale);
res.updateConfiguration(conf, res.getDisplayMetrics());
}
}
private static Locale getLocale(Configuration config) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
return config.getLocales().get(0);
} else {
//noinspection deprecation
return config.locale;
}
}
}
然后,在調(diào)用使用上下文的任何方法(例如)之前,請確保先調(diào)用super.onCreate(savedInstanceState)每個子類的onCreate()方法。setContentView()
- 3 回答
- 0 關(guān)注
- 1386 瀏覽
添加回答
舉報