怎样在程序中利用C++支持多国语言

2016-02-19 20:49 9 1 收藏

有一种朋友不在生活里,却在生命力;有一种陪伴不在身边,却在心间。图老师即在大家的生活中又在身边。这么贴心的服务你感受到了吗?话不多说下面就和大家分享怎样在程序中利用C++支持多国语言吧。

【 tulaoshi.com - 编程语言 】

本文以eMule为例,探讨一下多国语言支持的实现。选择emule,因为它的多国语言支持实现的相当好,可以支持动态切换。而且最要害,它是开源的,可以直接通过源码来研究它的实现技术。 !-- frame contents -- !-- /frame contents --   emule是利用动态加载资源DLL来实现多语言切换的,每一个资源DLL中包含了一份对应某一语言的字符串表。在源码的srchybridlang 路径上可以发现一个lang解决方案,其中包含了差不多40个项目,每个项目编译出来都是一个单独的DLL。这些DLL在程序安装时拷贝到指定的目录中。每个DLL里面都是一个大的string table。emule为每一个用到的字符串(大约为1400多个)都指定了一个固定ID,在不同的DLL中这个ID对应了这个字符串的不同语言的翻译版本。这样每当需要这个字串时就通过ID去获取,在当时程序加载的某一特定语言的DLL,就可以取到相应语言的字串。  英文版本的string table编译在主EXE文件中,这样当某一语言不支持,或DLL文件加载失败时还可以使用英语版本。  下面我们就看看具体的实现。  主要实现代码在I18n.cpp文件中。入口函数是 void CPreferences::SetLanguage() ,这个函数在在 void CPreferences::LoadPreferences() 函数中被调用,即载入了程序的各种选项后。当程序第一次运行时,在选项文件(即 preferences.ini)中没有内容,SetLanguage函数会根据系统的本地语言设置来加载对应的语言DLL资源,所以我们第一次安装后就是中文,无需设置。这一点我们后面会说到。  另外在 BOOL CPPgGeneral::OnApply() 中也调用了该函数,即用户在“选项”窗口中改变了语言选择后。  在 void CPreferences::SetLanguage() 函数中,首先调用了 static void InitLanguages(const CString& rstrLangDir, bool bReInit = false) 函数。这个函数主要是通过遍历“语言”目录(即我们前面说地的,专门用于存放各种语言版本DLL的目录),来初始化静态“语言表” (_aLanguages),这是个静态数组,其中的每一项对应一种支持的语言。凡能找到相应DLL文件的,就在表中标记该语言为支持。  然后调用 static bool LoadLangLib(const CString& rstrLangDir, LANGID lid) 来载入相应的语言DLL。这个函数比较简单,通过查“语言表”(_aLanguages),假如要载入的语言是支持的,就加载相应的DLL文件,并将DLL模块句柄存到_hLangDLL中,这也是一个静态变量。我们可以看到假如是英语,是不需要加载的,直接用EXE模块中的资源字符串表。  假如调用LoadLangLib文件加载指定的语言失败,程序会尝试判定本地系统的语言集,并加载对应的语言,假如加载也失败就使用英语。  语言文件加载成功后,程序会尝试从中加载一个字串,假如失败,说明可能DLL文件损坏,则再重设语言为英语。英语字串是内置在EXE文件中的,所以是最可靠的。  至此,加载成功,句柄保存在_hLangDLL静态变量中。  最后在需要字符串的地方程序通过 CString GetResString(UINT uStringID, Word wLanguageID) 或 CString GetResString(UINT uStringID) 函数加载相应的字符串。这个函数的功能很简单,就是从_hLangDLL指定的模块中加载字符串资源。假如_hLangDLL为 NULL就是从当前模块加载,我们前面已经看到了,假如使用英语这个变量的值就是NULL。  在emule的源码中,几乎每个对话框都实现了一个Localize(void)函数,这个函数就是通过调用GetResString来设置对话框上所有控件的文字。在  BOOL CPPgGeneral::OnApply() 函数中我们可以看到,在调用CPreferences::SetLanguage函数切换了语言后,会依次调用对话框和窗口的Localize(void)函数,重新设置UI的文字内容。  最后注重一点,假如你想让应用支持多语言,在设计对话框时要把对话框的Language属性设为“非特定语言”。在“资源”视图中选中相应的对话框节点,再切换到“属性”视图就可以看到这个选项了。假如不设置会出现乱码。 更多内容请看C/C++进阶技术文档专题,或

来源:http://www.tulaoshi.com/n/20160219/1624592.html

延伸阅读
自从微软公司推出Windows 95操作系统以来,系统托盘应用作为一种极具吸引力的用户界面设计深受广大用户的喜爱。使用系统托盘作为用户界面的Windows应用程序数不胜数,比如"金山词霸"、"Winamp"、"RealPlayer"等等。 这些程序运行时不显示运行窗口,只在任务栏上显示一个图标,表示程序正在运行,用户可以通过鼠标与应用程序交互,程序开发人...
if语句 if语句用于测试条件并在条件为真时执行一桌或几条语句。 说明:if表达式后面不能带分号,否则它本身表示代码中的空语句,使编译器将空语句解释为在条件为真时执行的语句。 if (x == 10); // Warning! Extra semicolon! DoSomething(x); 这里DoSomething()函数总会执行,因为编译器不把它看成在条件为真时执行...
作者: 网易 学院 程序系教授管宁 以下两个例子要非常注意,函数传递的不是数组中数组元素的真实值而是数组在内存中的实际地址! /*程序作者:管宁 站点:www.cndev-lab.com 所有稿件均有版权,如要转载,请务必著名出处和作者*/ #include stdio.h void main(void) { void reversal(); static int a[10] = {0,1,2,3,4,5,6,7,8,9};...
一、绪论 当微软推出VS.NET7实现了可扩展的托管C++后,C++程序员们反映不一。尽管大部分的程序员对于能够继续使用C++感到很欣慰,但几乎所有的人对于托管C++提供的晦涩语法感到很痛苦。微软明显从反馈中感觉到托管C++不是那么成功。 2003年10月6日,ECMA(欧洲计算机制造商协会)宣布成立专家组,负责结合ISO标准C++与通用语言,开发一个可...
标签: PHP
  一、简介 如果你对Unix/Linux有所了解的话,你应该知道他们大都自带了C和C++的编译器,分别是GCC和G++。Unix在程序安装及Make等许多地方使用到了这些编译器。利用一些控制台命令,C++和PHP, 我将向你介绍怎样生成一个完整的C++程序例子,他可以在用PHP程序来执行,并能获得相应的输出结果。我将先生成C++程序代码,并编译...

经验教程

46

收藏

81
微博分享 QQ分享 QQ空间 手机页面 收藏网站 回到头部