Libgdx之国际化 中英文菜单切换

Posted zqiang_55

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Libgdx之国际化 中英文菜单切换相关的知识,希望对你有一定的参考价值。

有时候我们做的游戏不仅仅发布在国内市场,有时候也需要发布在国际市场,这时候我们至少需要中英2套菜单来供不同的玩家使用,毕竟中文不是每个人都能看懂。
Libgdx中提供了I18NBundle来供我们使用,I18NBundle提供了一套机制可以使我们从属性(properties)文件中加载资源, 属性文件中的资源是以”name”和”values”的形式存在的,而且资源最好有一个父文件,这样防止资源丢失时,可以使用父文件中的值:

通过上面图片可以看出string.properties就是父文件,另外2个分别对应中文文件和英文文件

     1. 由于默认的BitmapFont不支持中文,因此必须自己重新创建一个.fnt文件,文件中必须包含Properties中的所有汉字,具体看前面博客。
      2. 在用Eclipse创建properties文件时默认的编码不是**UTF-8**,这时显示的不是中文,切换编码到**UTF-8**就OK了  

I18NBundle 常用方法说明:
1. static I18NBundle createBundle(FileHandle baseFileHandle, java.util.Locale locale) 根据properties文件和国家编码来创建I18NBundle对象
2. java.lang.String format(java.lang.String key, java.lang.Object… args) 格式化获取的values
3. java.lang.String get(java.lang.String key) 根据key来获取values

下面来看代码,代码中也有说明:

public class LocalizationTest extends ApplicationAdapter 

    SpriteBatch sb;
    Vector3 touch;
    OrthographicCamera cam;

    private BitmapFont font;
    private LanguageManager lm;

    private FileHandle enFileHandle, cnFileHandle;
    private String gameTitle, gameBegin, gameHelp;

    @Override
    public void create() 
        sb = new SpriteBatch();
        touch = new Vector3();
        cam = new OrthographicCamera(640, 480);
        cam.position.set(320, 240, 0);
        cam.update();

        /**
         * 默认字体里面不支持中文,需要自己使用Hiero来创造字体文件
         */
        font = new BitmapFont(Gdx.files.internal("font/in.fnt"));

        lm = new LanguageManager(); // 初始化语言管理器,加载语言

        enFileHandle = Gdx.files.internal("strings_en_GB");
        cnFileHandle = Gdx.files.internal("strings_zh_CN");

        lm.loadLanguage("english", enFileHandle, Locale.UK); // 加载文字文件
        lm.loadLanguage("chinese", cnFileHandle, Locale.CHINA);
        if (lm.getCurrentLanguage().equals("zh_CN")) 
            lm.setCurrentLanguage("chinese");
         else 
            lm.setCurrentLanguage("english");
        

        initializeText();
    

       private void initializeText() 
            I18NBundle b = lm.getCurrentBundle();
            gameTitle = b.get("gameTitle");   // 根据key来获取对应的values
            gameBegin = b.format("gameBegin", 81); // 先根据key来获取对应的values值,再格式化语言
            gameHelp = b.get("gameHelp");

        

        private void translate() 
            if(lm.getCurrentLanguage().equals("chinese"))
                lm.setCurrentLanguage("english");
            else
                lm.setCurrentLanguage("chinese");

            initializeText();
        

    @Override
    public void render() 
        Gdx.gl.glClearColor(0.39f, 0.58f, 0.92f, 1.0f);
        Gdx.gl.glClear(GL20.GL_COLOR_BUFFER_BIT);

        sb.setProjectionMatrix(cam.combined);
        sb.begin();
        font.draw(sb, gameTitle, 60, 260);
        font.draw(sb, gameBegin, 60, 160);
        font.draw(sb, gameHelp, 60, 60);
        font.draw(sb, "Touch Up Translate", 320, 240);
        sb.end();

        if (Gdx.input.justTouched()) 
            touch.set(Gdx.input.getX(), Gdx.input.getY(), 0);
            cam.unproject(touch);
            if (320 < touch.x && touch.x< 640 &&  // 点击第一象限来切换语言
                    240 < touch.y && touch.y< 480) 
                translate();
            
        
    

    @Override
    public void dispose() 
        sb.dispose();
        font.dispose();
    

    public class LanguageManager 
        private ObjectMap<String, I18NBundle> languages;
        private String currentLanguage;

        public LanguageManager() 
            languages = new ObjectMap<String, I18NBundle>();
            /*此处获取的默认语言格式,和后面保存的语言格式不统一,在正式使用时会做一个转换
             * 或者语言和I18NBundle对象不保存在ObjectMap里面,用别的数据结构,此处不考虑这种情况
             * */
            currentLanguage = Locale.getDefault().toString();
        

        public void loadLanguages(String name, I18NBundle bundle) 
            if (name != null && !name.isEmpty() && bundle != null)
                languages.put(name.toLowerCase(), bundle);
        

        /**
         * 储存语言及其对应的I18NBundle对象,方便以后获取
         * @param name 语言名称
         * @param fileHandle  properties文件对象
         * @param locale   国家编码
         */
        public void loadLanguage(String name, FileHandle fileHandle, Locale locale) 
            if (name != null && !name.isEmpty() && fileHandle != null && locale != null)
                languages.put(name.toLowerCase(), I18NBundle.createBundle(fileHandle, locale));
        

        public void loadLanguage(String name, FileHandle fileHandle) 
            if (name != null && !name.isEmpty() && fileHandle != null)
                languages.put(name.toLowerCase(), I18NBundle.createBundle(fileHandle));
        

        public void removeLanguage(String name, I18NBundle bundle) 
            if (name != null && !name.isEmpty() && bundle != null)
                languages.remove(name.toLowerCase());
        

        public void setCurrentLanguage(String name) 
            if (languages.containsKey(name.toLowerCase()))
                currentLanguage = name;
        

        public String getCurrentLanguage() 
            System.out.println("currentLanguage: " + currentLanguage);
            return currentLanguage;
        

        public I18NBundle getCurrentBundle() 
            return languages.get(currentLanguage);
        
    


以上是关于Libgdx之国际化 中英文菜单切换的主要内容,如果未能解决你的问题,请参考以下文章

Libgdx之Game场景切换Screen

Libgdx之Game场景切换Screen

如何从菜单切换到3D FPS设置? (libGDX)

Libgdx之Table 表格排版

Libgdx之Table 表格排版

springboot开发之国际化(中英文切换)