mirror of https://github.com/bjornbytes/lovr.git
Font stability; Font line height;
This commit is contained in:
parent
ff5a114e65
commit
12bdaca72b
|
@ -14,6 +14,8 @@ Font* lovrFontCreate(FontData* fontData) {
|
||||||
if (!font) return NULL;
|
if (!font) return NULL;
|
||||||
|
|
||||||
font->fontData = fontData;
|
font->fontData = fontData;
|
||||||
|
font->texture = NULL;
|
||||||
|
font->lineHeight = 1.f;
|
||||||
vec_init(&font->vertices);
|
vec_init(&font->vertices);
|
||||||
map_init(&font->kerning);
|
map_init(&font->kerning);
|
||||||
|
|
||||||
|
@ -21,13 +23,14 @@ Font* lovrFontCreate(FontData* fontData) {
|
||||||
int padding = 1;
|
int padding = 1;
|
||||||
font->atlas.x = padding;
|
font->atlas.x = padding;
|
||||||
font->atlas.y = padding;
|
font->atlas.y = padding;
|
||||||
font->atlas.width = 256;
|
font->atlas.width = 128;
|
||||||
font->atlas.height = 256;
|
font->atlas.height = 128;
|
||||||
font->atlas.padding = padding;
|
font->atlas.padding = padding;
|
||||||
map_init(&font->atlas.glyphs);
|
map_init(&font->atlas.glyphs);
|
||||||
|
|
||||||
while (font->atlas.width < 4 * fontData->size) {
|
// Set initial atlas size
|
||||||
font->atlas.width <<= 1;
|
while (font->atlas.height < 4 * fontData->size) {
|
||||||
|
lovrFontExpandTexture(font);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Texture
|
// Texture
|
||||||
|
@ -59,6 +62,7 @@ void lovrFontPrint(Font* font, const char* str) {
|
||||||
float v = atlas->height;
|
float v = atlas->height;
|
||||||
|
|
||||||
int length = strlen(str);
|
int length = strlen(str);
|
||||||
|
const char* start = str;
|
||||||
const char* end = str + length;
|
const char* end = str + length;
|
||||||
size_t bytes;
|
size_t bytes;
|
||||||
unsigned int previous = '\0';
|
unsigned int previous = '\0';
|
||||||
|
@ -72,7 +76,7 @@ void lovrFontPrint(Font* font, const char* str) {
|
||||||
// Newlines
|
// Newlines
|
||||||
if (codepoint == '\n') {
|
if (codepoint == '\n') {
|
||||||
x = 0;
|
x = 0;
|
||||||
y -= font->fontData->size;
|
y -= font->fontData->size * font->lineHeight;
|
||||||
previous = '\0';
|
previous = '\0';
|
||||||
str += bytes;
|
str += bytes;
|
||||||
continue;
|
continue;
|
||||||
|
@ -82,8 +86,21 @@ void lovrFontPrint(Font* font, const char* str) {
|
||||||
x += lovrFontGetKerning(font, previous, codepoint);
|
x += lovrFontGetKerning(font, previous, codepoint);
|
||||||
previous = codepoint;
|
previous = codepoint;
|
||||||
|
|
||||||
// Glyph geometry
|
// Get glyph
|
||||||
Glyph* glyph = lovrFontGetGlyph(font, codepoint);
|
Glyph* glyph = lovrFontGetGlyph(font, codepoint);
|
||||||
|
|
||||||
|
// Start over if texture was repacked
|
||||||
|
if (u != atlas->width || v != atlas->height) {
|
||||||
|
x = 0;
|
||||||
|
y = -lovrFontGetHeight(font);
|
||||||
|
u = atlas->width;
|
||||||
|
v = atlas->height;
|
||||||
|
str = start;
|
||||||
|
previous = '\0';
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Glyph geometry
|
||||||
int gx = glyph->x;
|
int gx = glyph->x;
|
||||||
int gy = glyph->y;
|
int gy = glyph->y;
|
||||||
int gw = glyph->w;
|
int gw = glyph->w;
|
||||||
|
@ -173,6 +190,14 @@ int lovrFontGetBaseline(Font* font) {
|
||||||
return font->fontData->height / 1.25f;
|
return font->fontData->height / 1.25f;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
float lovrFontGetLineHeight(Font* font) {
|
||||||
|
return font->lineHeight;
|
||||||
|
}
|
||||||
|
|
||||||
|
void lovrFontSetLineHeight(Font* font, float lineHeight) {
|
||||||
|
font->lineHeight = lineHeight;
|
||||||
|
}
|
||||||
|
|
||||||
int lovrFontGetKerning(Font* font, unsigned int left, unsigned int right) {
|
int lovrFontGetKerning(Font* font, unsigned int left, unsigned int right) {
|
||||||
char key[12];
|
char key[12];
|
||||||
snprintf(key, 12, "%d,%d", left, right);
|
snprintf(key, 12, "%d,%d", left, right);
|
||||||
|
@ -224,11 +249,6 @@ void lovrFontAddGlyph(Font* font, Glyph* glyph) {
|
||||||
|
|
||||||
// Expand the texture if needed. Expanding the texture re-adds all the glyphs, so we can return.
|
// Expand the texture if needed. Expanding the texture re-adds all the glyphs, so we can return.
|
||||||
if (atlas->y + glyph->h > atlas->height - 2 * atlas->padding) {
|
if (atlas->y + glyph->h > atlas->height - 2 * atlas->padding) {
|
||||||
if (atlas->width == atlas->height) {
|
|
||||||
atlas->width <<= 1;
|
|
||||||
} else {
|
|
||||||
atlas->height <<= 1;
|
|
||||||
}
|
|
||||||
lovrFontExpandTexture(font);
|
lovrFontExpandTexture(font);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -249,9 +269,23 @@ void lovrFontAddGlyph(Font* font, Glyph* glyph) {
|
||||||
void lovrFontExpandTexture(Font* font) {
|
void lovrFontExpandTexture(Font* font) {
|
||||||
FontAtlas* atlas = &font->atlas;
|
FontAtlas* atlas = &font->atlas;
|
||||||
|
|
||||||
|
if (atlas->width == atlas->height) {
|
||||||
|
atlas->width *= 2;
|
||||||
|
} else {
|
||||||
|
atlas->height *= 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!font->texture) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
// Resize the texture storage
|
// Resize the texture storage
|
||||||
|
while (glGetError());
|
||||||
lovrTextureDataResize(font->texture->textureData, atlas->width, atlas->height, 0x0);
|
lovrTextureDataResize(font->texture->textureData, atlas->width, atlas->height, 0x0);
|
||||||
lovrTextureRefresh(font->texture);
|
lovrTextureRefresh(font->texture);
|
||||||
|
if (glGetError()) {
|
||||||
|
error("Problem expanding font texture (out of space?)");
|
||||||
|
}
|
||||||
|
|
||||||
// Reset the cursor
|
// Reset the cursor
|
||||||
atlas->x = atlas->padding;
|
atlas->x = atlas->padding;
|
||||||
|
|
|
@ -44,6 +44,7 @@ typedef struct {
|
||||||
FontAtlas atlas;
|
FontAtlas atlas;
|
||||||
map_int_t kerning;
|
map_int_t kerning;
|
||||||
vec_float_t vertices;
|
vec_float_t vertices;
|
||||||
|
int lineHeight;
|
||||||
} Font;
|
} Font;
|
||||||
|
|
||||||
Font* lovrFontCreate(FontData* fontData);
|
Font* lovrFontCreate(FontData* fontData);
|
||||||
|
@ -54,6 +55,8 @@ int lovrFontGetHeight(Font* font);
|
||||||
int lovrFontGetAscent(Font* font);
|
int lovrFontGetAscent(Font* font);
|
||||||
int lovrFontGetDescent(Font* font);
|
int lovrFontGetDescent(Font* font);
|
||||||
int lovrFontGetBaseline(Font* font);
|
int lovrFontGetBaseline(Font* font);
|
||||||
|
float lovrFontGetLineHeight(Font* font);
|
||||||
|
void lovrFontSetLineHeight(Font* font, float lineHeight);
|
||||||
int lovrFontGetKerning(Font* font, unsigned int a, unsigned int b);
|
int lovrFontGetKerning(Font* font, unsigned int a, unsigned int b);
|
||||||
Glyph* lovrFontGetGlyph(Font* font, uint32_t codepoint);
|
Glyph* lovrFontGetGlyph(Font* font, uint32_t codepoint);
|
||||||
void lovrFontAddGlyph(Font* font, Glyph* glyph);
|
void lovrFontAddGlyph(Font* font, Glyph* glyph);
|
||||||
|
|
|
@ -6,6 +6,8 @@ const luaL_Reg lovrFont[] = {
|
||||||
{ "getAscent", l_lovrFontGetAscent },
|
{ "getAscent", l_lovrFontGetAscent },
|
||||||
{ "getDescent", l_lovrFontGetDescent },
|
{ "getDescent", l_lovrFontGetDescent },
|
||||||
{ "getBaseline", l_lovrFontGetBaseline },
|
{ "getBaseline", l_lovrFontGetBaseline },
|
||||||
|
{ "getLineHeight", l_lovrFontGetLineHeight },
|
||||||
|
{ "setLineHeight", l_lovrFontSetLineHeight },
|
||||||
{ NULL, NULL }
|
{ NULL, NULL }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -39,3 +41,16 @@ int l_lovrFontGetBaseline(lua_State* L) {
|
||||||
lua_pushinteger(L, lovrFontGetBaseline(font));
|
lua_pushinteger(L, lovrFontGetBaseline(font));
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int l_lovrFontGetLineHeight(lua_State* L) {
|
||||||
|
Font* font = luax_checktype(L, 1, Font);
|
||||||
|
lua_pushinteger(L, lovrFontGetLineHeight(font));
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
int l_lovrFontSetLineHeight(lua_State* L) {
|
||||||
|
Font* font = luax_checktype(L, 1, Font);
|
||||||
|
float lineHeight = luaL_checknumber(L, 2);
|
||||||
|
lovrFontSetLineHeight(font, lineHeight);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
|
@ -7,3 +7,5 @@ int l_lovrFontGetHeight(lua_State* L);
|
||||||
int l_lovrFontGetAscent(lua_State* L);
|
int l_lovrFontGetAscent(lua_State* L);
|
||||||
int l_lovrFontGetDescent(lua_State* L);
|
int l_lovrFontGetDescent(lua_State* L);
|
||||||
int l_lovrFontGetBaseline(lua_State* L);
|
int l_lovrFontGetBaseline(lua_State* L);
|
||||||
|
int l_lovrFontGetLineHeight(lua_State* L);
|
||||||
|
int l_lovrFontSetLineHeight(lua_State* L);
|
||||||
|
|
Loading…
Reference in New Issue