Qt 字体绘制

1. 字体分类


字体根据数据存储的格式一般把字体分为两类,一类是点阵字体,一类是矢量字体。

点阵字体:

也叫位图字体,格式一般是 .fon 简单来说就是把文字保存为一张图片。一般早期的电脑使用这种方式显示文字。优点是显示速度相当快,比如使用cpu渲染的时候,只需要一次memcopy 就可以把字体显示出来。缺点也很明显,只能清晰的显示在对应的字号下,放大了就会变得失真。

矢量字体:

矢量字体一般格式为.ttf,保存文字的矢量信息,比如一个笔划的起始、终止坐标,半径、弧度等等。在显示、打印这一类字库时,要经过一系列的数学运算才能输出结果,但是这一类字库保存的汉字理论上可以被无限地放大,笔划轮廓仍然能保持圆滑,打印时使用的字库均为此类字库。

2. 矢量字体分类


目前主流的 矢量字体格式有3种:Type1, TrueType和 OpenType,这三种格式都是与平台无关的。

Type1

全称PostScript Type1,是1985年由Adobe公司提出的一套矢量字体标准,由于这个标准是基于PostScript Description Language(PDL),而PDL又是 高端打印机首选的打印描述语言,所以Type1迅速流行起来。但是Type1是非开放字体,Adobe对使用Type1的公司征收高额的使用费。

TrueType

是1991年由Apple公司与 Microsoft公司联合提出另一套矢量字标准。Type1使用三次 贝塞尔曲线来描述字形, TrueType则使用二次贝塞尔曲线来描述字形。所以Type1的字体比 TrueType字体更加精确美观。一个误解是,Type1字体比TrueType字体占用空间多。这是因为同样描述一个圆形,二次贝塞尔曲线只需要8个关键点和7段 二次曲线;而三次贝塞尔曲线则需要12个关键点和11段三次曲线。然而实际情况是一般来说 Type1比TrueType要小10%左右。这是因为对于稍微复杂的字形,为了保持平滑,TrueType必须使用更多的关键点。由于现代大部分打印机都是使用PDL作为打印描述语言,所以Type1字体打印的时候不会产生形变,速度快;而 TrueType则需要翻译成PDL,由于曲线方程的变化,还会产生一定的形变,不如Type1美观。

OpenType

则是Type1与 TrueType之争的最终产物。1995年,Adobe公司和 Microsoft公司开始联手开发一种兼容Type1和TrueType,并且真正支持 Unicode的字体,后来在发布的时候,正式命名为OpenType。OpenType可以嵌入Type1和TrueType,这样就兼有了二者的特点,无论是在屏幕上察看还是打印,质量都非常优秀。可以说 OpenType是一个三赢的结局,无论是Adobe、Microsoft还是最终用户,都从OpenType中得到了好处。Windows家族从Windows 2000开始,正式支持OpenType。

对比

这么说来,Type1应该比 TrueType更具有优势,为什么如今的计算机上TrueType反而比Type1使用更广泛呢?

这是因为第一:Type1由于字体方程的复杂,所以在屏幕上渲染的时候,花费的时间多,解决方案是大部分Type1字体嵌入了 点阵字体,这样渲染快,但是边缘不光滑,比较难看。很多ps文档和ps转换的pdf文档都是这样,在计算机上浏览的时候字体很难看,但是打印出来很美观。TrueType则渲染比较快,可以平滑的显示在屏幕上,看上去很美观。

第二个原因是Type1的高额使用费,使得Type1没有被所有的操作系统所支持。Windows家族只有OS/2和windows 2000及之后的版本从操作系统级别开始支持Type1。由于这个问题,Adobe只好在其所有的产品中嵌入Adobe Type Manager(ATM)作为渲染引擎。

在UOS 上字体基本都是 TrueType,打开字体管理器,右键点击字体查看信息,UOS字体类型基本都是TrueType类型。

3. Qt 中字体绘制原理。


Qt采用第三方开源库 freeType 实现字体渲染。freeType 提供提供字体的轮廓、轮廓关键点解析、上层图形API 通过这些接口进行图形绘制。上层利用freeType 不仅可以使用CPU 绘制,同时也可以使用opengl 进行绘制。FT库使用C语言编写,采用了面向对象的思想,将对应类型封装为结构体或者结构体指针类型。

字体渲染在 Qt中非常复杂,这里做简单的介绍,有兴趣可以深入研究TrueType 库字体渲染,该库在很多图形界面绘制中都会用到。下面通过代码对整个字体绘制大致流程说明。

1. 传入一个字体后,首先初始化 FT_New_Face,使用一个FT_New_Face 打开一个字体文件

2. 设置一些绘制的参数,比如字体大小什么的。

3. 遍历需要绘制文字,通过文字的unicode获取文字所在的index,并保存到glyph中。在绘制的时候通过这个glyph获取字体的轮廓字槽信息。

4. 在绘制的时候,通过glyph获取轮廓字槽。FT_Load_Glyph 把字体信息加载到face的glyph 中。

5. 至此、字的轮廓信息完全存储在outline中,下面的代码就是拿来解析,并渲染轮廓的。

在Qt 中,字体渲染分为了两种,当渲染的字体大于 64 号的时候,Qt会强制不加载字体的点阵图,采用讲字体轮廓转化成点的方式,然后通过我们平时drawpath的方式进行渲染,保证了大字体的情况下不会失真。

然后通过 addGlyphsToPath 将 outline 中的轮廓添加到 path 中,然后中fill的方式将文字渲染出来。这种方式同样使用于opengl 渲染。网上有很多这样的例子。

另一种方式当字体大小小于 64 的时候,是通过 freeType 获取字体对应的位图来渲染。在showDrawCacheGlyphs 函数中会对字体的大小进行判断,小于64的时候会通过drawCacheGlyphs 通过位图渲染

同样的从slot 中获取位图数据,通过memcpy 拷贝到 glyph_buffer 中,最后Qt中绘制图像的函数绘制到界面上。

Qt 中字体的绘制流程大致到这里,字体绘制比较复杂,有兴趣可以研究 trueTypel库,很多图形项目都会用到它。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Qtdesigner是一个功能强大的图形界面设计工具,可以与Python编程语言结合使用。通过Qtdesigner,我们可以轻松地绘制实时图形界面。 在使用Qtdesigner绘制实时图形界面时,我们可以使用Python中的Qt库进行开发。Qt库提供了一系列的组件和功能,以简化图形界面开发过程。 首先,我们可以使用Qtdesigner绘制界面布局,包括窗口、按钮、文本框等组件。通过简单的拖拽操作,我们可以将这些组件放置在指定的位置,并设置它们的属性,如大小、颜色、字体等。 接下来,我们需要在Python中编写代码来实现实时图形界面的功能。通过Qt库提供的信号与槽机制,我们可以建立组件之间的交互关系。例如,当用户点击按钮时,我们可以捕捉到按钮的点击信号,并编写对应的槽函数来处理这个事件。 为了实现实时图形功能,我们可以使用Python中的定时器来更新界面。定时器可以以指定的时间间隔触发,并执行特定的函数。我们可以在定时器函数中更新界面的状态或者显示实时数据。 此外,Qt库还提供了一些绘图功能,如画布、画笔、画刷等。我们可以在绘图函数中使用这些功能来绘制实时图形。例如,我们可以使用画布来创建一个绘图区域,并使用画笔来绘制实时数据的曲线图。 总的来说,使用Qtdesigner和Python的组合,我们可以轻松实现实时图形界面的开发。通过明确的界面设计和合理的编程实现,我们能够展示实时数据,并及时更新界面,提供更好的用户体验。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值