Table of Contents

1 Hack 日志

  • 8月22日开始动手修改改vcmi(英雄无敌3的开源游戏引擎)的源码, 让它支持简体中文版的游戏数据。
  • 8月25日,已经有一个可工作的修改版,但自己不满意。这个版本的原理是每次要显 示文本的时候,都用自己写的编码转换函数将字符串从GBK编码转为UTF8编码,从而 能正常地显示中文。但每次显式都转换,每秒游戏要10帧以上,每帧要显示的字符串 可以多达数十个,这样每秒要做数百次字符串转换,效率很低。虽然这样的计算量对 现代CPU来说不算啥,但心里觉得别扭。高效的做法应该是将游戏数据中的GBK编码的 字符串载入内存的时候只做一次编码转换,转换为UTF8编码。
  • 这时开始置疑PC游戏相关工作的意义,所以工作中断了。
  • 中断一个月后,觉得开始的事情没做完,心里别扭,就决定来个收场。于是9月27号, 开始做一个高效的修改。9月28日算大功告成。这个事可以告一段落了。

以下是对源码所做的修改,和怎么编译安装,当时用英文做的记录,懒得再翻译回中文了。

2 Changes

  1. client/CMessage.cpp

    in function CMessage::breakText(), line 153

                // added by jiqingwu@gmail.com, 2013-08-28
    // If the text[z] is less than 0, it is the first byte of a UTF8 Chinese word.
    #ifdef ZH_CN
    else if (text[z] < 0){
    z++;
    z++;
    lineLength += graphics->fonts[font]->getSymbolWidth(text[z]);
    }
    #endif
  2. client/gui/Fonts.cpp

    in function CTrueTypeFont::getStringWidth(), line 255

        // added by jiqingwu@gmail.com, 2013-08-28
    // If we are handling simplified chinese, it is a UTF8 string
    #ifdef ZH_CN
    TTF_SizeUTF8(font.get(), data.c_str(), &width, NULL);
    #else
    TTF_SizeText(font.get(), data.c_str(), &width, NULL);
    #endif

    in function CTrueTypeFont::renderText(), line 279

         if (blended)
    // added by jiqingwu@gmail.com, 2013-09-28 Sat
    // If we are handling simplified chinese game data, it is a UTF8 string
    #ifdef ZH_CN
    rendered = TTF_RenderUTF8_Blended(font.get(), data.c_str(), color);
    #else
    rendered = TTF_RenderText_Blended(font.get(), data.c_str(), color);
    #endif
    else
    // added by jiqingwu@gmail.com, 2013-09-28 Sat
    // If we are handling simplified chinese game data, it is a UTF8 string
    #ifdef ZH_CN
    rendered = TTF_RenderUTF8_Solid(font.get(), data.c_str(), color);
    #else
    rendered = TTF_RenderText_Solid(font.get(), data.c_str(), color);
    #endif
  3. add lib/ConvertEncoding.cpp and lib/ConvertEncoding.h

    The content of ConvertEncoding.h is:

    char * convert_enc(char *src_enc, char *dest_enc, const char * src_string);
    

    The content of ConvertEncoding.cpp is:

    /*
    * ConvertEncoding.cpp, for vcmi using CJK(China/Japan/Korea) data.
    *
    * Authors: Wu Jiqing (jiqingwu@gmail.com)
    *
    * License: GNU General Public License v2.0 or later
    *
    */
    // added by jiqingwu(jiqingwu@gmail.com)
    // 2013-09-27 Fri
    #include <stdio.h>
    #include <iconv.h>
    #include <string.h> // added by jiqingwu@gmail.com, 2013-09-27 Fri
    char * convert_enc(char *src_enc, char *dest_enc, const char * src_string)
    {
    #define UTF8_STR_LEN 5000 static char out_string[UTF8_STR_LEN], *sin, *sout;
    int in_len, out_len, ret;
    iconv_t c_pt; if ((c_pt = iconv_open(dest_enc, src_enc)) == (iconv_t)-1)
    {
    printf("iconv open failed!\n");
    return NULL;
    }
    // iconv(c_pt, NULL, NULL, NULL, NULL);
    in_len = strlen(src_string) + 1;
    out_len = UTF8_STR_LEN;
    sin = (char *)src_string;
    sout = out_string;
    ret = iconv(c_pt, &sin, (size_t *)&in_len, &sout, (size_t *)&out_len);
    if (ret == -1)
    {
    return NULL;
    }
    iconv_close(c_pt);
    return out_string;
    }

    to link ConvertEncoding.o into library, add two lines into lib/CMakeLists.txt:

    set(lib_SRCS
    ...
    ConvertEncoding.cpp
    ) set(lib_HEADERS
    ...
    ConvertEncoding.h
    )
  4. lib/CGeneralTextHandler.cpp,

    To include "ConvertEncoding.h"

    // added by jiqingwu(jiqingwu@gmail.com)
    // 2013-09-27 Fri
    #include "ConvertEncoding.h"

    in function CLegacyConfigParser::readString(), line 112

        // added by jiqingwu@gmail.com, 2013-09-27 Fri
    // convert gbk string to utf-8 string.
    // (For simplified Chinese game data, the string is GBK encoded)
    #ifdef ZH_CN
    char * utf8_str = convert_enc("GBK", "UTF8", ret.c_str());
    return std::string((const char*)utf8_str);
    #else
    return ret;
    #endif
  5. lib/filesystem/CBinaryReader.cpp,

    to include "ConvertEncoding.h":

    // added by <jiqingwu@gmail.com>, 2013-09-28 Sat
    #include "../ConvertEncoding.h"

    in function CBinaryReader::readString(), line 95

        // added by jiqingwu@gmail.com, 2013-08-22
    // If we are handling chinese data, convert gbk string to utf-8 string.
    #ifdef ZH_CN
    char * utf8_str = convert_enc("GBK", "UTF8", ret.c_str());
    return std::string((const char*)utf8_str);
    #else
    return ret;
    #endif

3 Install by compiling

  1. add such a line into ./CMakeLists.txt to enable supporting Simplifed Chinese Game Data

    add_definitions(-DZH_CN)
    
  2. make a directory build under the source dir
    mkdir build
    
  3. create makefiles
    cd build
    cmake ..

    This may take a short while.

  4. compile
    make
    
  5. install (root privilege is needed)
    make install
    

    Check the directories of vcmi

    vcmiclient -v
    

    You will see the result like this:

    Starting...
    VCMI 0.93
    data directory: /usr/local/share/vcmi
    library directory: /usr/local/lib/vcmi
    path to server: /usr/local/bin/vcmiserver

    Here, vcmi is installed under /usr/local

  6. Use the Data from the chinese version of Death of Shadow. Link the 'Data', 'Maps', 'Mp3' directories under /usr/local/share/vcmi like this (You need have root privilege):
    cd /usr/local/share/vcmi
    ln -s /Data/Dir/of/ChineseGame Data
    ln -s /Maps/Dir/of/ChineseGame Maps
    ln -s /Mp3/Dir/of/ChineseGame Mp3
  7. To show chinese characters in this game, you need put a true type font which supports Chinese into /usr/local/share/vcmi/Data.
    cp /chinese/font/path /usr/local/share/vcmi/Data
    

    Edit the /usr/local/share/vcmi/config/fonts.json, modify the truetype font section like this:

    "trueType":
    {
    "BIGFONT" : { "file" : "ChineseFont.ttf", "size" : 22, "blend" : true},
    "CALLI10R" : { "file" : "ChineseFont.ttf", "size" : 10, "blend" : true},
    "CREDITS" : { "file" : "ChineseFont.ttf", "size" : 28, "blend" : true},
    "HISCORE" : { "file" : "ChineseFont.ttf", "size" : 13, "blend" : true},
    "MEDFONT" : { "file" : "ChineseFont.ttf", "size" : 16, "blend" : true},
    "SMALFONT" : { "file" : "ChineseFont.ttf", "size" : 13, "blend" : true},
    "TIMES08R" : { "file" : "ChineseFont.ttf", "size" : 11, "blend" : true},
    "TINY" : { "file" : "ChineseFont.ttf", "size" : 11, "blend" : true},
    "VERD10B" : { "file" : "ChineseFont.ttf", "size" : 13, "blend" : true}
    }

    Where ChineseFont.ttf is your true type font.

  8. Play Game
    vcmiclient
    

4 reply of Ivan

(0004091) Ivan (developer) - 2013-10-20 13:09
http://bugs.vcmi.eu/view.php?id=1420#c4091
----------------------------------------------------------------------
Thanks. I'll take a look on this. I don't like idea of using ifdef's to enable
some functionality but you've tracked every place that needs changes - that will
help.

Date: 2013-10-21T19:48+0800

Author: Jiqing Wu

Org version 7.9.3f with Emacs version 24

Validate XHTML 1.0

让vcmi支持英雄无敌3中文版的更多相关文章

  1. vcmi(魔法门英雄无敌3 - 开源复刻版) 源码编译

    vcmi源码编译 windows+cmake+mingw ##1 准备 HoMM3 gog.com CMake 官网 vcmi 源码 下载 QT5 with mingw 官网 Boost 源码1.55 ...

  2. 英雄无敌3开源引擎vcmi的编译安装

    TAGS: Heroes3, vcmi, opensourceDATE: 2013-08-23 vcmi是什么? vcmi 是经典的 SLG 英雄无敌3 的开源游戏引擎.原来的英雄无敌3只能在Wind ...

  3. 英雄无敌HoMM3-死亡阴影SOD-神之苏醒WOG-封神NABI-MOD等相关文件

    英雄无敌HoMM3:死亡阴影SOD 英雄无敌3之死亡阴影(Heroes of Might and Magic III: Shadow of Death,简记为HoMM III: SOD)发行于1999 ...

  4. 黑科技项目:英雄无敌III Mod <<Fallen Angel>>介绍

    英雄无敌三简介(Heroes of Might and Magic III) 英3是1999年由New World Computing在Windows平台上开发的回合制策略魔幻游戏,其出版商是3DO. ...

  5. Problem A: 英雄无敌3(1)【dp/待补】

      Problem A: 英雄无敌3(1) Time Limit: 1 Sec  Memory Limit: 128 MBSubmit: 86  Solved: 16[Submit][Status][ ...

  6. Problem B: 英雄无敌3(2)【模拟,日期转换】

    Problem B: 英雄无敌3(2) Time Limit: 1 Sec  Memory Limit: 128 MBSubmit: 295  Solved: 52[Submit][Status][W ...

  7. python json库序列化支持中文

    import json d = {"name":"英雄无敌7"} res = json.dumps(d) # 打印res 会显示 {"name&quo ...

  8. github上最全的资源教程-前端涉及的所有知识体系

    前面分享了前端入门资源汇总,今天分享下前端所有的知识体系. 个人站长对个人综合素质要求还是比较高的,要想打造多拉斯自媒体网站,不花点心血是很难成功的,学习前端是必不可少的一个环节, 当然你不一定要成为 ...

  9. github上最全的资源教程-前端涉及的所有知识体系【转】

    github上最全的资源教程-前端涉及的所有知识体系[转自:蓝猫的博客] 综合类 综合类 地址 前端知识体系 http://www.cnblogs.com/sb19871023/p/3894452.h ...

随机推荐

  1. Sprint1回顾

    Sprint目标 此产品为适用于小学生使用的四则运算训练软件.关于第一期Sprint冲刺的目标,我们打算实现产品的以下几点的功能: •1.初始界面设计 •2.四则基本运算算法 •3.能产生随机式子 • ...

  2. java实现hash一致性算法

    import org.apache.commons.lang3.RandomUtils; import org.apache.commons.lang3.StringUtils; import jav ...

  3. 如何选择mysql存储引擎

    一.MySQL的存储引擎 完整的引擎说明还是看官方文档:http://dev.mysql.com/doc/refman/5.6/en/storage-engines.html 这里介绍一些主要的引擎 ...

  4. .Net iTextSharp 生成pdf

    拿别人例子 public ActionResult index() { var ms = new MemoryStream(); #region CreatePDF Document document ...

  5. 【uoj#142】【UER #5】万圣节的南瓜灯 乱搞+并查集

    题目描述 给出一张 $n\times m$ 的网格图,两个格子之间有一条双向边,当且仅当它们相邻,即在网格图中有一条公共边. 特殊地,对于 $1\le x\le n​$ ,$(x,1)​$ 和 $(x ...

  6. Nginx+Tomcat搭建高性能负载均衡集群--Windows本地测试版

    链接:http://www.cnblogs.com/wbyp/p/6860744.html

  7. BZOJ4553: [Tjoi2016&Heoi2016]序列 树套树优化DP

    把pos[i]上出现的平常值定义为nor[i]最大值定义为max[i]最小值定义为min[i],那么我们发现在两个值,i(前),j(后),当且仅当max[i]<=nor[j],nor[i]< ...

  8. 【ZJOI 2018】 历史(lct)

    历史 题目描述 九条可怜是一个热爱阅读的女孩子. 这个世界有 $n$ 个城市,这 $n$ 个城市被恰好 $n-1$ 条双向道路联通,即任意两个城市都可以互相到达.同时城市 $1$ 坐落在世界的中心,占 ...

  9. 【bzoj3527】 Zjoi2014—力

    http://www.lydsy.com/JudgeOnline/problem.php?id=3527 (题目链接) 题意 $${F_i=\sum_{j<i} {\frac{q_iq_j}{( ...

  10. debian安装filebeat5.5收集nginx日志

    先贴一下我的BELK架构 1.Download and install the Public Signing Key: # wget -qO - https://artifacts.elastic.c ...