当你显示一个字符串|getstrcodepages函数的使用
当你显示一个字符串 , 但是字符串中的某些字符不被当前字体所支持 , 这个时候 , 你将会看到系统会使用一个方框来代替这个不可显示的字符 。
让我们回忆我们的例子程序 , 然后 , 我们在PaintContent函数中添加如下的代码:
文章图片
在上面的代码中 , 我们构造了一个比较有意思的字符串:它的前三个字符是罗马字母的”ABC” , 然后是西里尔的”ABC” , 最后是泰文的”ABC” 。
如果你执行这个程序 , 你会看到除了罗马字母ABC之外 , 其他的字母都显示为了方框 , 为什么?
因为系统字体(SYSTEMFont)只支持有限的几个字符集 。
有人会问了 , 那怎样才能选择正确的字体呢?万一字符串中还包括韩文或者日文怎么办?遗憾的是 , 没有一个单一字体能包含Unicode字符集中的所有字符 。 那有什么好办法解决这个问题吗?解决之道:字体链接(FontLinking)
字体链接可以用来将字符串打散成不同的片段 , 然后每个片段都可以使用一种合适的字体来显示 。
IMLangFontLink2接口中的一些方法可以用来打散字符串 。 GetStrCodePages这个方法可以接收一个字符串 , 然后将字符串打散为不同的片段 , 在同一个片段中的所有字符都可以使用相同的字体来显示 , 然后 , 可以使用MapFont方法来创建字体 。
好了 , 让我们来编写一个新版本的TextOut函数 , 这个函数使用了上面所提到的字体链接概念 。 我们会一步一步地编写这个函数 , 咱们先从下面的函数开始:
文章图片
【当你显示一个字符串|getstrcodepages函数的使用】当我们搞清楚了默认字体所支持的代码页之后 , 我们将会调用GetStrCodePages来将字符串打散为一个一个的片段 , 对于每个片段 , 我们会创建与之对应的字体并以正确的方式 , 在正确的地方 , 来显示这个字符串片段 , 直至所有字符串片段都得到这样的处理 。
接下来就是一些细节方面的优化工作了 。
首先 , 什么是”正确的地方”?我们希望下一个块在前一个块停止的地方继续 。 为此 , 我们利用了TA_UPDATECP文本对齐样式 , 它表示GDI应该在当前位置绘制文本 , 并将当前位置更新到绘制文本的末尾(因此 , 在下一个块的位置) 。
因此 , 我们需要设置DC的当前位置 , 并设置文本模式为TA_UPDATECP , 如下图所示:
文章图片
然后 , 我们只是将坐标”0,0″传递给TextOut函数 , 因为如果文本对齐模式是TA_UPDATECP , 则TextOut函数会忽略掉传递给它的坐标值 , 它会始终在当前位置进行绘制 。
当然 , 我们不能像这样乱搞DC的设置 。 如果调用者没有设置TA_UPDATECP , 那么调用者就不会期望我们干预当前位置 。 因此 , 我们必须保存原始位置并在之后恢复它(以及原始文本对齐方式) 。 
文章图片
接下来是一个改进:我们应该利用GetStrCodePages的第二个参数 , 它指定了我们希望使用的代码页 。 显然 , 我们应该更喜欢使用我们想要使用的字体支持的代码页 , 这样如果字符可以直接以该字体显示 , 那么我们就不应该映射替代字体 。 代码修改如下:
文章图片
当然 , 你可能想知道这个神奇的pfl是从哪里来的 。 它来自mlang中的Multilanguage对象 , 如下图所示:
- |三星Galaxy Z Fold 4 封面显示曝光 外部显示器23: 9 纵横比
- 格力电器|游戏玩家超爱!雷神27英寸Fast-IPS显示器现在入手
- 三星|传三星显示将向BMW供应400万片车用OLED显示屏
- 显示器|买到就是赚到?这台300块的显示器快把我整自闭了
- Apple Watch|稳了,iPhone 息屏显示功能来了
- 雅典表把动力储存显示立体化,抢眼度不输本身的飞行陀飞轮
- |华为推出新款显示器,提供高色域,可旋转屏幕,售价899元
- 云厂商为什么都在冲这个KPI?
- 华为|知网终于被立案审查 多个迹象显示这还只是其倒霉的第一步
- 英特尔|入手12代酷睿的注意了,Intel似乎埋下一个“大坑”
