Dje*_*mon 7 c++ opengl freetype
我正在开发一个项目,我在其中实现一个FreeType渲染对象来绘制文本,其中渲染环境是使用正交投影矩阵指定的:
glm::ortho(0, Width, Height, 0);
Run Code Online (Sandbox Code Playgroud)
这确保了坐标与标准GUI系统类似,(0,0)它是窗口的左上角而不是左下角.
然而,当使用FreeType进行渲染时,事情变得困难,因为FreeType的操作原点位于字形的左下角(减去下降部分).我的问题类似于/sf/ask/1774743071/但尚未提供答案,他的解决方案不符合我的意愿(使用的库也是略有不同,我假设他正在使用包装器).
所以我将我的文字渲染如下:
renderText("Testing 123 if text performs sufficiently", 0.0f, 0.0f, 1.0f, 1.0f);
Run Code Online (Sandbox Code Playgroud)
其中renderText包含以下功能:
renderText(const GLchar *text, GLfloat x, GLfloat y, GLfloat sx, GLfloat sy)
{
[...]
GLfloat xpos = x + glyph->bitmap_left * sx;
GLfloat ypos = y - glyph->bitmap_top * sy;
GLfloat w = glyph->bitmap.width * sx;
GLfloat h = glyph->bitmap.rows * sy;
// Update VBO
GLfloat vertices[4][4] = {
{ xpos, ypos, 0, 0 },
{ xpos + w, ypos, 1, 0 },
{ xpos, ypos + h, 0, 1 },
{ xpos + w, ypos + h, 1, 1 }
};
[...]
}
Run Code Online (Sandbox Code Playgroud)
如果我像这样渲染它,它将渲染y坐标下方的文本,0因此除非我向y坐标添加偏移量,否则它将不可见.所以看一下FreeType的字形指标:

我希望将y位置偏移一个等于字形图像的原点和顶部之间的差值的正数量,这样它总能整齐地将文本呈现在我给定的位置.查看图像我认为这是yMax值,所以我在更新VBO之前将以下语句添加到代码中:
ypos += (glyph->face->bbox.yMax >> 6) * sy;
Run Code Online (Sandbox Code Playgroud)
当我加载字体大小为24的FreeType字形时,似乎解决了这个问题,但是当我尝试使用不同的字体大小时,它无法正常工作,如下图所示:

正如你所看到的,它显然不像我想象的那样有效.如果我遗失了一些东西,我一直在搜索FreeType的文档,但我找不到它.我使用错误的指标(使用Ascender不起作用)?
我希望将y位置偏移一个等于字形图像的原点和顶部之间的差值的正数量,这样它总能整齐地将文本呈现在我给定的位置.查看图像我认为这是
yMax值,所以我在更新VBO之前将以下语句添加到代码中:
ypos += (glyph->face->bbox.yMax >> 6) * sy;
Run Code Online (Sandbox Code Playgroud)
实际上,yMax并不是你感兴趣的东西.你可以yMax - yMin用来找到你的字形的高度,但这真的是它的好处.
FT_GlyphSlotRec::bitmap_top可以看出:位图的顶部方位以整数像素表示.请记住,这是从基线到最顶部字形扫描线的距离,向上y坐标为正.
再次查看您在问题中包含的图像,这是有效的bearingY.你的问题是你从不ypos应该的时候减去这个值.你确实需要这个值,我将在下面解释,但你绝对不想减去它.
bitmap_top从计算中消除,则ypos得到以下内容:
这显然是不正确的,因为它忽略了字符串中每个字符之间的上升差异.

在上图中,我已经说明了你的字符串最顶部的红线,最底部的绿色和灰色的所有字形的基线.
正如您所看到的,大写字母'T'具有最大的上升,并且这种泛化适用于大多数字体.在红线的正下方,我已经说明了资本'T'和当前字母之间的上升差异为黄色区域.这是您必须计算以正确对齐字符串的重要数量.
Chars['T'].bitmap_top - glyph->bitmap_top
Run Code Online (Sandbox Code Playgroud)
如果停止减glyph->bitmap_top从ypos,并添加上面的值,你应该得到相同的结果正确对齐图.
对于奖励积分,如果您想将文本与屏幕底部对齐,则概念非常相似,只有您对最大下降(通常是小写'g')字符与当前字符之间的差异感兴趣.这是灰色基线和绿线之间的距离,可以height - bearingY在您的字形度量图中表示.
(glyph->metrics.height >> 6) - glyph->bitmap_top // bitmap_top is in integer coords
Run Code Online (Sandbox Code Playgroud)