Java國(guó)際化

使用java編寫(xiě)一個(gè)帶GUI程序或者其他需要給用戶(hù)傳遞文字信息的程序的時(shí)候,就很有可能需要用到國(guó)際化的知識(shí),來(lái)總結(jié)一下。

所謂的國(guó)際化,就是使編寫(xiě)的程序可以適應(yīng)不同的語(yǔ)言環(huán)境,比如,在中文環(huán)境下,可以與用戶(hù)使用中文交互,在英文環(huán)境下則切換為英文。而這個(gè)切換過(guò)程不需要修改代碼或者僅僅修改少量的代碼。java給我們提供了這樣的實(shí)現(xiàn)。

java文件國(guó)際化

我們通過(guò)將與界面顯示有關(guān)系的資源提取出來(lái)到資源文件中,然后讀取不同的資源文件來(lái)達(dá)到國(guó)際化的目的。在java中,這些是通過(guò)ResourceBundle這個(gè)類(lèi)來(lái)實(shí)現(xiàn)的。

ResourceBundle分為兩種,一種是ListResourceBundle,另一種是PropertyResourceBundle。下面介紹這兩種ResourceBundle的使用方法:

首先列出demo工程的代碼結(jié)構(gòu):

TestResourceBundle
|
|--src
    |
    |--kyu
        |
        |--bundle
        |    |
        |    |--ListResourceTranslator.java
        |    |
        |    |--PropertyResourceTranslator.java
        |    |
        |    |--ResourceTranslator.java
        |
        |--test
        |   |
        |   |--App.java
        |
        |--Errors_en_Us.java
        |
        |--Errors_zh_CN.java
        |
        |--Errors.java
        |
        |--Errors_en_Us.properties
        |
        |--Errors_zh_CN.properties
        |
        |--Errors.properties
        

PropertyResourceBundle

  1. 首先需要建立若干語(yǔ)言的properties文件: 自定義名語(yǔ)言代碼國(guó)別代碼.properties

比如:errors_en_US.properties, errors_zh_CN.properties

其中的語(yǔ)言代碼和國(guó)別代碼,分別是你要國(guó)際化的語(yǔ)言。需要幾種語(yǔ)言,就添加幾個(gè)properties文件。

國(guó)別代碼

語(yǔ)言代碼

通過(guò)打印java所支持的語(yǔ)言和國(guó)家查看:

private static void printLocal() {
        Locale[] localeList = Locale.getAvailableLocales();
        for (int i = 0; i < localeList.length; i++) {
            System.out.println(localeList[i].getDisplayCountry() + ": " + localeList[i].getCountry());
            System.out.println(localeList[i].getDisplayLanguage() + ": " + localeList[i].getLanguage());
        }
}
  1. 建立默認(rèn)語(yǔ)言的properties文件:自定義名.properties

比如:errors.properties

當(dāng)所需語(yǔ)言的properties文件不存在的時(shí)候就會(huì)默認(rèn)讀取這個(gè)文件中的內(nèi)容

注意,資源文件都必須是ISO-8859-1編碼,對(duì)于中文等非西方語(yǔ)系,可通過(guò)JDK自帶的工具native2ascii進(jìn)行處理,在Eclipse中也可以安裝插件SimplePropertiesEditor來(lái)處理這類(lèi)文件。

  1. 使用

ResourceTranslator.java

package kyu.bundle;

import java.util.Locale;
import java.util.ResourceBundle;

public abstract class ResourceTranslator {
    protected ResourceBundle bundle;
    protected Locale lc;
    protected static final String PROP_FILE = "kyu.errors";

    public String translate(String id) {
        return bundle.getString(id);
    }
}

PropertyResourceTranslator.java

package kyu.bundle;

import java.util.Locale;
import java.util.PropertyResourceBundle;
import java.util.ResourceBundle;

public class PropertyResourceTranslator extends ResourceTranslator{
    public PropertyResourceTranslator() {
        lc = Locale.getDefault();
        bundle = PropertyResourceBundle.getBundle(PROP_FILE, lc);
    }
    
    public PropertyResourceTranslator(String language, String country) {
        lc = new Locale(language, country);
        bundle = PropertyResourceBundle.getBundle(PROP_FILE, lc);
    }

}

App.java

package kyu.test;

import kyu.bundle.ListResourceTranslator;
import kyu.bundle.PropertyResourceTranslator;

public class App {
    public static void main(String[] args) {
        testPropertyResource();
    }

    private static void testPropertyResource() {
        PropertyResourceTranslator translatorDefault = new PropertyResourceTranslator();
        PropertyResourceTranslator translatorZH = new PropertyResourceTranslator("zh", "CN");
        PropertyResourceTranslator translatorEN = new PropertyResourceTranslator("en", "US");
        String def = translatorDefault.translate("ERROR-001");
        String zh = translatorZH.translate("ERROR-001");
        String en = translatorEN.translate("ERROR-001");
        
        System.out.println("test PropertyResourceBundle>>>>>>");
        System.out.println("default: " + def);
        System.out.println("zh: " + zh);
        System.out.println("en: " + en);
    }   
    
}

.properties文件內(nèi)容:

Errors_en_Us.properties:
ERROR-001=error password

Errors.properties
ERROR-001=error password

Errors_zh_CN.properties
ERROR-001=密碼錯(cuò)誤

執(zhí)行App.java的測(cè)試結(jié)果:

test PropertyResourceBundle>>>>>>
default: 密碼錯(cuò)誤
zh: 密碼錯(cuò)誤
en: error password

可以看到,通過(guò)指定Local構(gòu)造函數(shù)的語(yǔ)言和國(guó)別代碼,就能自動(dòng)找到對(duì)應(yīng)的.properties,并匹配其中的內(nèi)容。

當(dāng)使用Locale.getDefault()時(shí),自動(dòng)檢測(cè)當(dāng)前的系統(tǒng)環(huán)境,從而選擇對(duì)應(yīng)的語(yǔ)言。

還有一點(diǎn)要注意的是:

PropertyResourceBundle.getBundle(PROP_FILE, lc);

其中PROP_FILE,為properties文件的路徑,此路徑為properties文件的完整路徑,即 所在完整包名.自定義名稱(chēng)

ListResourceBundle

ListResourceBundle的使用與PropertyResourceBundle的使用大同小異,不過(guò)是將properties文件換成了.java文件

ListResourceTranslator.java

package kyu.bundle;

import java.util.ListResourceBundle;
import java.util.Locale;

public class ListResourceTranslator extends ResourceTranslator{
    public ListResourceTranslator() {
        lc = Locale.getDefault();
        bundle = ListResourceBundle.getBundle(PROP_FILE, lc);
    }
    
    public ListResourceTranslator(String language, String country) {
        lc = new Locale(language, country);
        bundle = ListResourceBundle.getBundle(PROP_FILE, lc);
    }
}

ERRORS_en_US.java

package kyu;

import java.util.ListResourceBundle;

public class ERRORS_en_US extends ListResourceBundle{
    static final Object[][] contents = new String[][] { 
        { "ERROR-001", "error password" } 
    };

    public Object[][] getContents() {
        return contents;
    }
}

ERRORS_zh_CN.java

package kyu;

import java.util.ListResourceBundle;

public class ERRORS_zh_CN extends ListResourceBundle {
    static final Object[][] contents = new String[][] { 
        { "ERROR-001", "密碼錯(cuò)誤" } 
    };

    public Object[][] getContents() {
        return contents;
    }
}

繼承了ListResourceBundle的類(lèi)就相當(dāng)于前面的properties文件,需要提供一個(gè)getContents()方法,返回對(duì)應(yīng)的鍵值對(duì)。

同樣的,要注意ListResourceBundle子類(lèi)的命名規(guī)則,與properties文件相同,路徑也與properties文件相同。

通過(guò)App.java的測(cè)試(將對(duì)應(yīng)的bundle替換),可以得到相同的測(cè)試結(jié)果。

使用Eclipse對(duì)java文件進(jìn)行國(guó)際化

在需要國(guó)際化的類(lèi)文件上點(diǎn)擊右鍵->Source->Externalize Strings...

出現(xiàn)窗口,Eclipse會(huì)自動(dòng)檢測(cè)類(lèi)文件中的字符串,在窗口中可以選擇相應(yīng)的字符串,最后自動(dòng)生成類(lèi)似于上面的PropertyResourceTranslator.java和properties文件,完成國(guó)際化。

其原理與以上所講的相同,故不再詳細(xì)說(shuō)明。

Eclipse RCP國(guó)際化

最近在使用Eclipse RCP這項(xiàng)技術(shù)開(kāi)發(fā)程序,其中也有國(guó)際化相關(guān)的東西,總結(jié)下來(lái)。

Eclipse RCP and Plugin Internationalization - Tutorial

上面這篇文章詳細(xì)的說(shuō)明了Eclipse RCP工程中的國(guó)際化問(wèn)題,可以作為一個(gè)備忘錄。下面介紹一下eclipse rcp中比較常用到的國(guó)際化方式:

plugin.xml文件國(guó)際化

plugin.xml文件中保存了擴(kuò)展點(diǎn)等相關(guān)的信息,當(dāng)擴(kuò)展點(diǎn)與界面UI相關(guān)時(shí),就需要用到國(guó)際化

  1. 在工程的根目錄下面建立一個(gè)plugin.properties資源文件,此文件類(lèi)似于我們上面提到的errors.properties。當(dāng)然,也可以建立plugin_zh.properties等文件,這些文件名中的plugin是可以自由定義的。

  2. 在 MANIFEST.MF文件中增加代碼行:Bundle-Localization: plugin

    注意,這個(gè)plugin與上面的properties文件名保持一致。

  3. plugin.xml配置文件對(duì)資源文件進(jìn)行引用時(shí), 在引用的key前面加一個(gè)%,比如:

<view
    id="org.jkiss.dbeaver.core.databaseNavigator"
    category="org.jkiss.dbeaver.core.category"
    class="org.jkiss.dbeaver.ui.navigator.database.DatabaseNavigatorView"
    allowMultiple="false"
    icon="icons/databases.png"
    name="%view.database.navigator.title"/>
<view

類(lèi)文件國(guó)際化

與前面所介紹的java類(lèi)文件國(guó)際化相同,也可以通過(guò)選擇類(lèi)文件點(diǎn)擊右鍵->Source->Externalize Strings...

Eclipse IDE會(huì)自動(dòng)幫你完成國(guó)際化的一些工作,同樣也生成了相關(guān)的類(lèi)和properties文件,但不同的是,生成的類(lèi)文件內(nèi)容類(lèi)似于:

package test;

import org.eclipse.osgi.util.NLS;

public class Messages extends NLS {
        private static final String BUNDLE_NAME
                = "test.messages"; //$NON-NLS-1$
        public static String View_0;
        public static String View_1;
        static {
                // initialize resource bundle
                NLS.initializeMessages(BUNDLE_NAME, Messages.class);
        }

        private Messages() {
        }
}

當(dāng)然,我們也可以手動(dòng)建立這些文件進(jìn)行國(guó)際化操作~不再詳細(xì)說(shuō)明,可以通過(guò)觀察IDE的行為進(jìn)行我們手動(dòng)的國(guó)際化操作

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 背景知識(shí) 通訊的發(fā)達(dá),使得世界各地交流越來(lái)越緊密。許多的軟件產(chǎn)品也要面向世界上不同國(guó)家的用戶(hù)。其中,語(yǔ)言障礙顯然是...
    靜默虛空閱讀 4,713評(píng)論 0 0
  • Spring Cloud為開(kāi)發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見(jiàn)模式的工具(例如配置管理,服務(wù)發(fā)現(xiàn),斷路器,智...
    卡卡羅2017閱讀 136,502評(píng)論 19 139
  • Spring Boot 參考指南 介紹 轉(zhuǎn)載自:https://www.gitbook.com/book/qbgb...
    毛宇鵬閱讀 47,253評(píng)論 6 342
  • 1. Java基礎(chǔ)部分 基礎(chǔ)部分的順序:基本語(yǔ)法,類(lèi)相關(guān)的語(yǔ)法,內(nèi)部類(lèi)的語(yǔ)法,繼承相關(guān)的語(yǔ)法,異常的語(yǔ)法,線程的語(yǔ)...
    子非魚(yú)_t_閱讀 34,623評(píng)論 18 399
  • 兒行千里母擔(dān)憂(yōu)!再遙遠(yuǎn)也不過(guò)相思漫漫,再漫長(zhǎng)也不過(guò)柔柔綿情。似乎再堅(jiān)硬也抵不過(guò)歲月的打磨。我不清楚身邊的老人家年輕...
    檀蕓果C閱讀 174評(píng)論 0 2

友情鏈接更多精彩內(nèi)容