资产文件的本地化

资产文件夹中有几个html文件。 我怎样才能本地化他们? 我唯一的select,一些硬编码select正确的文件基于语言环境?

这不是直接支持,但这是我所做的…

按照国家代码将文件分成组(比如你对普通资源文件所做的事情),然后在每个本地化的string.xml文件中创build一个本地化的string,称为“前缀”(前缀为英语“en”例如)。

然后,当你build立你的资产文件名简单地使用像getString("prefix") + "-" + "<name-of-asset->

以上至less有一些变化应该为你工作。

如果你想本地化一个HTML文件,你可以简单地把它放在res / raw- <language> /filename.html (其中<language> = en,es,fr,it等),然后从你的代码中用资源ID R.raw.filename 。 框架将根据区域select正确的文件。

把你的文件放到带有本地后缀的assets文件夹中。 为每个文件定义一个string资源“myLocalizedFileName”,并通过R.string.myLocalizedFileName获取文件名。

例:

文件夹结构:

 assets/ assets/help.html assets/help_de.htlm 

res / values / strings.xml中每个语言的string资源:

 <resource> <string name=helpFile>help.html</string> </resource> 

WebView调用:

 public class HelpActivity extends AppCompatActivity { protected void onCreate(Bundle savedInstanceState) { ... findViewById(R.id.helpWebView) .loadUrl("file:///android_asset/" + getString(R.string.helpFile)); } } 

尝试本地化与assets-ja将无法正常工作,因为可悲的是,这些不是资源文件。 最好的select是以正确的语言环境以编程方式进行本地化。 或者,HTML文件的内容只是纯文本。 如果它符合你的项目,你可以尝试将这个string作为一个条目存储在一个新的values-ja文件夹的strings.xml (或你自己的myHtmlText.xml ?)文件中。

将文件放在原始LOCALE文件夹中会自动select正确的位置,但是如果在webView中加载这些文件,在使用Proguard进行混淆之后,path将会被打破。

Proguard打破了Android的WebView,为什么?

那么唯一的解决办法是使用资产文件夹,并使用文件LOCALE和拿起正确的文件。

每个国家/地区代码使用一个文件(如Andrew White和PJ_Finnegan的答案中所述)的一种替代方法是只定义一次HTML(例如,在assets文件夹中)并在其中使用@string ID,就像

 <html> <body> <p>@string/message_text</p> </body> </html> 

将资源加载到string后,可以将其内容传递给replaceResourceStrings()

 /** * Regex that matches a resource string such as <code>@string/a-b_c1</code>. */ private static final String REGEX_RESOURCE_STRING = "@string/([A-Za-z0-9-_]*)"; /** Name of the resource type "string" as in <code>@string/...</code> */ private static final String DEF_TYPE_STRING = "string"; /** * Recursively replaces resources such as <code>@string/abc</code> with * their localized values from the app's resource strings (eg * <code>strings.xml</code>) within a <code>source</code> string. * * Also works recursively, that is, when a resource contains another * resource that contains another resource, etc. * * @param source * @return <code>source</code> with replaced resources (if they exist) */ public static String replaceResourceStrings(Context context, String source) { // Recursively resolve strings Pattern p = Pattern.compile(REGEX_RESOURCE_STRING); Matcher m = p.matcher(source); StringBuffer sb = new StringBuffer(); while (m.find()) { String stringFromResources = getStringByName(context, m.group(1)); if (stringFromResources == null) { Log.w(Constants.LOG, "No String resource found for ID \"" + m.group(1) + "\" while inserting resources"); /* * No need to try to load from defaults, android is trying that * for us. If we're here, the resource does not exist. Just * return its ID. */ stringFromResources = m.group(1); } m.appendReplacement(sb, // Recurse replaceResourceStrings(context, stringFromResources)); } m.appendTail(sb); return sb.toString(); } /** * Returns the string value of a string resource (eg defined in * <code>values.xml</code>). * * @param name * @return the value of the string resource or <code>null</code> if no * resource found for id */ public static String getStringByName(Context context, String name) { int resourceId = getResourceId(context, DEF_TYPE_STRING, name); if (resourceId != 0) { return context.getString(resourceId); } else { return null; } } /** * Finds the numeric id of a string resource (eg defined in * <code>values.xml</code>). * * @param defType * Optional default resource type to find, if "type/" is not * included in the name. Can be null to require an explicit type. * * @param name * the name of the desired resource * @return the associated resource identifier. Returns 0 if no such resource * was found. (0 is not a valid resource ID.) */ private static int getResourceId(Context context, String defType, String name) { return context.getResources().getIdentifier(name, defType, context.getPackageName()); } 

这种方法的好处是你只需要指定一次HTML的结构,并使用android的本地化机制 。 另外,它允许在strings.xml中recursion引用string,而Context.getResources()不支持。 例如:

 <?xml version="1.0" encoding="utf-8"?> <resources> <string name="message_text">Some string @string/another_one.</string> </resources> 

缺点是parsing是在运行时完成的,因此在应用程序中使用时,为每种语言指定一个专用的HTML会有更好的性能。

有关使用此代码将HTML从资产文件转换为可在TextView显示的“可风化” CharSequence (使用Kuitsi的TagHandler )的示例 ,请参阅TextUtil