title: freetype 字形解析

date: 2019/3/7 20:17:46

toc: true

freetype 字形解析

字体管理

管理字形,这里可以拆分为两个部分,一部分为管理字距,一部分为有效数据(位图信息).

比如字母g,蓝色框里的是有效的位图信息,但是排版的时候,是需要考虑字距的,否则虽然不重叠,但是不太好看.

数据结构

这里记住一个点

我们一般都是先转换到字符到字形槽,然后从字形槽提取位图,提取边界bbox

https://www.freetype.org/freetype2/docs/reference/ft2-index.html

这里有两个结构去描述

位图描述

  typedef struct  FT_Bitmap_
{
unsigned int rows;
unsigned int width;
int pitch;
unsigned char* buffer;
unsigned short num_grays;
unsigned char pixel_mode;
unsigned char palette_mode;
void* palette; } FT_Bitmap;

位图的定位点描述在字形槽里

  //字形槽
typedef struct FT_GlyphSlotRec_
{
FT_Library library;
FT_Face face;
FT_GlyphSlot next;
FT_UInt reserved; /* retained for binary compatibility */
FT_Generic generic; FT_Glyph_Metrics metrics;
FT_Fixed linearHoriAdvance;
FT_Fixed linearVertAdvance;
FT_Vector advance; //下个边界的原点 FT_Glyph_Format format; FT_Bitmap bitmap; //位图的描述
FT_Int bitmap_left; //位图的左上角点
FT_Int bitmap_top; //位图的左上角点 FT_Outline outline; FT_UInt num_subglyphs;
FT_SubGlyph subglyphs; void* control_data;
long control_len; FT_Pos lsb_delta;
FT_Pos rsb_delta; void* other; FT_Slot_Internal internal; } FT_GlyphSlotRec;

位置的边界需要去手动获取

这里的参数是FT_Glyph glyph,可以由face中的槽来转换

//从face的字形槽中取得字形
//FT_EXPORT( FT_Error )FT_Get_Glyph( FT_GlyphSlot slot,FT_Glyph *aglyph );
//字形描述
typedef struct FT_GlyphRec_
{
FT_Library library;
const FT_Glyph_Class* clazz;
FT_Glyph_Format format;
FT_Vector advance; } FT_GlyphRec;
error = FT_Get_Glyph( face->glyph, &glyph ); //从字形中取得bbox边界
FT_Glyph_Get_CBox( glyph, FT_GLYPH_BBOX_TRUNCATE, &bbox );
  FT_EXPORT( void )
FT_Glyph_Get_CBox( FT_Glyph glyph,
FT_UInt bbox_mode,
FT_BBox *acbox ); //传入参数
typedef struct FT_GlyphRec_
{
FT_Library library;
const FT_Glyph_Class* clazz;
FT_Glyph_Format format;
FT_Vector advance; } FT_GlyphRec;
// 传出参数
typedef struct FT_BBox_
{
FT_Pos xMin, yMin;
FT_Pos xMax, yMax; } FT_BBox;

字体抽象

刚开始我想抽象出位图信息



每个像素的bpp
换行像素位置
位图数据地址

那么除非我自己去控制字距,同时需要统计这一行的高度,来确定下一行文字的位置,但是这可能会排版成拥挤的上对齐,或者手动计算位图的大小,去布局,比如先设计一个32*32的边界,然后根据这个位图的大小居中摆放…想想就麻烦,而且这样的话设计字体旋转就没辙了

再仔细看下freetype的布局,其实是创建了一个布局,接着再看下旋转,我们实际刷新数据的时候,一般还是从左到右,从上到下刷新点,没有颜色的数据应该不去刷新,我们看下之前的字体旋转,可以发现是遮挡了的,所以遇到没有颜色的数据,应该去跳过这些点,而不是去绘图.

蓝色框是点阵图,我们刷新像素的位置

红色框是边界,用来描述布局的

我们之前的绘图是这样的

void draw_bitmap( FT_Bitmap*  bitmap,
FT_Int x,
FT_Int y)
{
FT_Int i, j, p, q;
FT_Int x_max = x + bitmap->width;
FT_Int y_max = y + bitmap->rows;
for ( i = x, p = 0; i < x_max; i++, p++ )
{
for ( j = y, q = 0; j < y_max; j++, q++ )
{
if ( i < 0 || j < 0 ||
i >= var.xres || j >= var.yres )
continue; // 添加下面这句话即可
// if(bitmap->buffer[q * bitmap->width + p])
lcd_put_pixel(i,j,bitmap->buffer[q * bitmap->width + p]);
}
}
}

这里对所有点都进行重绘,所以理论上应该会有字符的遮盖,上一节的实验也确实如此,可以看到h会把a遮挡了

修改下代码,判断如果没有颜色,则不需要描点即可,这里可以设置freetype的bpp是1即可,具体字体的颜色另外绘图指定即可.

freetype 字形解析的更多相关文章

  1. 我所理解的Cocos2d-x

    我所理解的Cocos2d-x(完全基于Cocos2d-x3.0,深度剖析计算机图形学,OpenGL ES及游戏引擎架构,全面提升游戏开发相关知识) 秦春林 著   ISBN 978-7-121-246 ...

  2. freetypeLCD显示

    目录 freetypeLCD显示 安装交叉编译环境 配置 头文件和库的位置 编译安装 复制到PC编译工具链 复制到文件系统 运行测试 LCD显示 编码转换问题 简单显示 角度旋转 换行显示 居中显示 ...

  3. C#+OpenGL+FreeType显示3D文字(1) - 从TTF文件导出字形贴图

    C#+OpenGL+FreeType显示3D文字(1) - 从TTF文件导出字形贴图 +BIT祝威+悄悄在此留下版了个权的信息说: 最近需要用OpenGL绘制文字,这是个很费时费力的事.一般的思路就是 ...

  4. 基于Qt的FreeType字体轮廓解析

    一.本文目的 以前的文档中.详细的介绍了FreeType开源字体引擎库的基础知识.基本用法.但并未详细的阐明在TurboCG中.是如何解析出一个文字的轮廓的,本文集中阐述.怎么样使用FreeType开 ...

  5. FreeType 管理字形

    转自:http://blog.csdn.net/hgl868/article/details/7254687 1.字形度量 顾名思义,字形度量是对应每一个字形的特定距离,以此描述如何对文本排版.    ...

  6. 解析 Qt 字库移植并能显示中文 (上篇)

    原文http://mobile.51cto.com/symbian-272552.htm 本文介绍的是Qt 字库移植并能显示中文,需要的字体库文件,一般是多个.具体移植那一个,看你使用的字库是什么了, ...

  7. CSharpGL(28)得到高精度可定制字形贴图的极简方法

    CSharpGL(28)得到高精度可定制字形贴图的极简方法 回顾 以前我用SharpFont实现了解析TTF文件从而获取字形贴图的功能,并最终实现了用OpenGL渲染文字. 使用SharpFont,美 ...

  8. C#+OpenGL+FreeType显示3D文字(3) - 用PointSprite绘制文字

    C#+OpenGL+FreeType显示3D文字(3) - 用PointSprite绘制文字 上一篇实现了把文字绘制到OpenGL窗口,但实质上只是把含有文字的贴图贴到矩形模型上.本篇我们介绍用Poi ...

  9. C#+OpenGL+FreeType显示3D文字(2) - 用GLSL+VBO绘制文字

    C#+OpenGL+FreeType显示3D文字(2) - 用GLSL+VBO绘制文字 +BIT祝威+悄悄在此留下版了个权的信息说: 上一篇得到了字形贴图及其位置字典(可导出为XML).本篇就利用此贴 ...

随机推荐

  1. Webpack 4教程:为什么要优化代码

    转载请注明出处:葡萄城官网,葡萄城为开发者提供专业的开发工具.解决方案和服务,赋能开发者.原文出处:https://wanago.io/2018/07/30/webpack-4-course-part ...

  2. OrmLite-更符合面向对象的数据库操作方式

    1. jar包下载 下载地址:http://ormlite.com/releases/,一般用core和android包即可. 如果使用的是android studio,也可以直接通过module s ...

  3. 一种解决Android studio 3.0 Build报错的方法

    问题背景: 最近在开始使用AndroidStudio3.0,刚好有一个开源的项目(Material-Movies),需要学习下.因为该项目比较早(2015年),而这段时间AndroidStudio和G ...

  4. MySQL 基础知识梳理学习(六)----锁

    1.什么是锁: 对共享资源进行并发访问控制,提供数据的完整性和一致性. 2.锁的区别: 类型 lock latch 对象 事务 线程 保护 数据库内容 内存数据结构 持续时间 整个事务过程 临界资源 ...

  5. 从0开始的Python学习017Python标准库

    简介 Python标准库使随着Python附带安装的,它包含很多有用的模块.所以对一个Python开发者来说,熟悉Python标准库是十分重要的.通过这些库中的模块,可以解决你的大部分问题. sys模 ...

  6. python学习笔记5_异常

    python学习笔记5_异常 1.什么事异常 Python使用异常对象(exception object) 来表示异常情况.遇到错误会发生异常. 如果异常对象未被处理或被捕捉,程序就会用所谓的回溯(t ...

  7. jQuery的siblings方法

    在使用siblings方法的时候,发现p标签,选中是没有效果的 解决:在w3c中测试也发现是没有效果的,也没有其他的特殊说明,于是度娘之后发现: siblings()获取的是当前标签元素的所有同辈的标 ...

  8. JProfiler的详细使用介绍

    转:https://blog.csdn.net/huangjin0507/article/details/52452946 下载软件 官网地址:http://www.ej-technologies.c ...

  9. 基于nodejs的流水线式的CRUD服务。依赖注入可以支持插件。

    写代码好多年了,发现大家的思路都是写代码.写代码.写代码,还弄了个称号——码农. 我是挺无语的,我的思路是——不写代码.不写代码.不写代码! 无聊的代码为啥要重复写呢?甚至一写写好几年. 举个例子吧, ...

  10. mySQL查看运行的进程

    查看运行的进程 show processlist kill id 杀掉进程