Significantly improved font code
This commit is contained in:
5
IDEA.md
5
IDEA.md
@ -1,2 +1,7 @@
|
||||
- Make font measure take in a pointer to a primitive to offer auto buffering of verts
|
||||
- Make a clone of the string into font measure pointing only to real chars?
|
||||
|
||||
- How to do text wrapping efficiently?
|
||||
- Two pointers, one for current char and one for the last known text position.
|
||||
- Start by measuring whole string, this will give me n chars and let me know straight away if text fits
|
||||
- Half divide the pointer to try and find the mid point and figure out if I should go up or down, keep halfing until finding the below then iterate up
|
@ -41,11 +41,7 @@ typedef struct {
|
||||
|
||||
typedef struct {
|
||||
int32_t length;
|
||||
int32_t realChars;
|
||||
float lineHeight, spaceSize;
|
||||
} fonttextinfo_t;
|
||||
|
||||
typedef struct {
|
||||
int32_t realLength;
|
||||
float width, height, scale;
|
||||
stbtt_aligned_quad *quads;
|
||||
} fontmeasure_t;
|
||||
} fonttextinfo_t;
|
@ -40,111 +40,95 @@ void fontInit(font_t *font, char *data) {
|
||||
free(pixels);
|
||||
}
|
||||
|
||||
fonttextinfo_t fontGetTextInfo(font_t *font, char *text) {
|
||||
float x, y;
|
||||
char c;
|
||||
int32_t i;
|
||||
fonttextinfo_t info = {
|
||||
.length = 0,
|
||||
.realChars = 0,
|
||||
.lineHeight = FONT_LINE_HEIGHT,
|
||||
.spaceSize = FONT_SPACE_SIZE
|
||||
};
|
||||
|
||||
// Count how many "real characters" are in the string.
|
||||
i = 0;
|
||||
while(c = text[i++]) {
|
||||
info.length++;
|
||||
if(c == FONT_SPACE) continue;
|
||||
if(c == FONT_NEWLINE) continue;
|
||||
info.realChars++;
|
||||
void fontDispose(font_t *font) {
|
||||
textureDispose(&font->texture);
|
||||
}
|
||||
|
||||
return info;
|
||||
}
|
||||
|
||||
fontmeasure_t * fontTextMeasure(font_t *font, char *text, fonttextinfo_t *info,
|
||||
float scale
|
||||
) {
|
||||
fonttextinfo_t * fontGetTextInfo(font_t *font, char *text, float scale) {
|
||||
int32_t i, j;
|
||||
char c;
|
||||
float x, y;
|
||||
stbtt_aligned_quad *quad;
|
||||
fontmeasure_t *measure;
|
||||
|
||||
scale *= FONT_SCALE_ADJUST;
|
||||
measure = malloc(sizeof(fontmeasure_t));
|
||||
measure->width = 0, measure->height = 0;
|
||||
measure->scale = scale;
|
||||
measure->quads = malloc(sizeof(stbtt_aligned_quad) * info->realChars);
|
||||
// Create info buffer.
|
||||
fonttextinfo_t *info = malloc(sizeof(fonttextinfo_t));
|
||||
|
||||
info->length = 0;
|
||||
info->realLength = 0;
|
||||
|
||||
// Count how many "real characters" are in the string.
|
||||
i = 0;
|
||||
while(c = text[i++]) {
|
||||
info->length++;
|
||||
if(c == FONT_SPACE) continue;
|
||||
if(c == FONT_NEWLINE) continue;
|
||||
info->realLength++;
|
||||
}
|
||||
|
||||
// Now setup the size scales
|
||||
info->quads = malloc(sizeof(stbtt_aligned_quad) * info->realLength);
|
||||
info->scale = scale * FONT_SCALE_ADJUST;
|
||||
info->width = 0, info->height = 0;
|
||||
|
||||
// Begin buffering quads.
|
||||
x = 0;
|
||||
y = FONT_INITIAL_LINE;
|
||||
|
||||
i = 0, j = 0;
|
||||
|
||||
while(c = text[i++]) {
|
||||
// Spaces, don't quad just next
|
||||
if(c == FONT_SPACE) {
|
||||
x += info->spaceSize;
|
||||
x += FONT_SPACE_SIZE;
|
||||
continue;
|
||||
}
|
||||
|
||||
// Newlines reset X
|
||||
if(c == FONT_NEWLINE) {
|
||||
y += info->lineHeight;
|
||||
y += FONT_LINE_HEIGHT;
|
||||
x = 0;
|
||||
continue;
|
||||
}
|
||||
|
||||
// Calculate the quad of the character, store into the array.
|
||||
quad = measure->quads + j;
|
||||
quad = info->quads + j;
|
||||
stbtt_GetBakedQuad(font->characterData,
|
||||
FONT_TEXTURE_WIDTH, FONT_TEXTURE_HEIGHT,
|
||||
((int32_t)c)-FONT_FIRST_CHAR, &x, &y, quad, FONT_FILL_MODE
|
||||
);
|
||||
quad->x0 *= scale, quad->x1 *= scale;
|
||||
quad->y0 *= scale, quad->y1 *= scale;
|
||||
measure->width = mathMax(measure->width, quad->x1);
|
||||
measure->height = mathMax(measure->height, quad->y1);
|
||||
quad->x0 *= info->scale, quad->x1 *= info->scale;
|
||||
quad->y0 *= info->scale, quad->y1 *= info->scale;
|
||||
info->width = mathMax(info->width, quad->x1);
|
||||
info->height = mathMax(info->height, quad->y1);
|
||||
j++;
|
||||
}
|
||||
|
||||
return measure;
|
||||
return info;
|
||||
}
|
||||
|
||||
void fontTextMeasureDispose(fontmeasure_t *measure) {
|
||||
free(measure->quads);
|
||||
free(measure);
|
||||
void fontTextInfoDispose(fonttextinfo_t *info) {
|
||||
free(info->quads);
|
||||
free(info);
|
||||
}
|
||||
|
||||
void fontDispose(font_t *font) {
|
||||
textureDispose(&font->texture);
|
||||
}
|
||||
|
||||
void fontTextBufferFromMeasure(font_t *font, primitive_t *primitive, char *text,
|
||||
fontmeasure_t *measure
|
||||
) {
|
||||
void fontTextBuffer(font_t *font,primitive_t *primitive,fonttextinfo_t *info) {
|
||||
stbtt_aligned_quad *quad;
|
||||
int32_t i, j;
|
||||
char c;
|
||||
int32_t i;
|
||||
|
||||
i = 0, j = 0;
|
||||
while(c = text[i++]) {
|
||||
if(c == FONT_SPACE) continue;
|
||||
if(c == FONT_NEWLINE) continue;
|
||||
quad = measure->quads + j;
|
||||
for(i = 0; i < info->realLength; i++) {
|
||||
quad = info->quads + i;
|
||||
quadBuffer(primitive, 0,
|
||||
quad->x0, quad->y0, quad->s0, quad->t0,
|
||||
quad->x1, quad->y1, quad->s1, quad->t1,
|
||||
j*QUAD_VERTICE_COUNT, j*QUAD_INDICE_COUNT
|
||||
i*QUAD_VERTICE_COUNT, i*QUAD_INDICE_COUNT
|
||||
);
|
||||
j++;
|
||||
}
|
||||
}
|
||||
|
||||
void fontTextInitFromMeasure(font_t *font, primitive_t *primitive, char *text,
|
||||
fonttextinfo_t *info, fontmeasure_t *measure
|
||||
) {
|
||||
void fontTextInit(font_t *font, primitive_t *primitive, fonttextinfo_t *info) {
|
||||
primitiveInit(primitive,
|
||||
QUAD_VERTICE_COUNT*info->realChars, QUAD_INDICE_COUNT*info->realChars
|
||||
QUAD_VERTICE_COUNT * info->realLength, QUAD_INDICE_COUNT * info->realLength
|
||||
);
|
||||
fontTextBufferFromMeasure(font, primitive, text, measure);
|
||||
fontTextBuffer(font, primitive, info);
|
||||
}
|
@ -20,31 +20,28 @@
|
||||
void fontInit(font_t *font, char *data);
|
||||
|
||||
/**
|
||||
* Generates information about how the given font will render the given text.
|
||||
* @param font Font to get the information for.
|
||||
* @param text Text that will be used to render
|
||||
* @return Some information about how the font will render the text.
|
||||
* Clean up a previously loaded font
|
||||
* @param font Loaded font.
|
||||
*/
|
||||
fonttextinfo_t fontGetTextInfo(font_t *font, char *text);
|
||||
void fontDispose(font_t *Font);
|
||||
|
||||
|
||||
/**
|
||||
* Measures (and calculates the quads for) a text prior to rendering it.
|
||||
*
|
||||
* @param font Font to use for rendering and measuring
|
||||
* @param text Text to measure/render.
|
||||
* @param info Info about the text being rendered / measured.
|
||||
* @param scale Scale of the text.
|
||||
* @returns Font measurement calculation.
|
||||
* @returns Font info calculated.
|
||||
*/
|
||||
fontmeasure_t * fontTextMeasure(font_t *font, char *text, fonttextinfo_t *info,
|
||||
float scale
|
||||
);
|
||||
fonttextinfo_t * fontGetTextInfo(font_t *font, char *text, float scale);
|
||||
|
||||
/**
|
||||
* Disposes a previously calculated font text measurement.
|
||||
* @param measure Measurement to dispose.
|
||||
* Disposes a previously calculated font info struct..
|
||||
* @param info Info to dispose.
|
||||
*/
|
||||
void fontTextMeasureDispose(fontmeasure_t *measure);
|
||||
void fontTextInfoDispose(fonttextinfo_t *info);
|
||||
|
||||
|
||||
/**
|
||||
* Buffers the vertices of a font text onto a primitive. Requires some info
|
||||
@ -52,28 +49,15 @@ void fontTextMeasureDispose(fontmeasure_t *measure);
|
||||
*
|
||||
* @param font Font to render.
|
||||
* @param primitive Primitive to render into.
|
||||
* @param text Text to render.
|
||||
* @param measure The precalculated measurement.
|
||||
* @param info The precalculated text info.
|
||||
*/
|
||||
void fontTextBufferFromMeasure(font_t *font, primitive_t *primitive, char *text,
|
||||
fontmeasure_t *measure
|
||||
);
|
||||
void fontTextBuffer(font_t *font, primitive_t *primitive, fonttextinfo_t *info);
|
||||
|
||||
/**
|
||||
* Initializes an uninitialized primitive for rendering.
|
||||
*
|
||||
* @param font Font to render.
|
||||
* @param primitive Primitive to render into.
|
||||
* @param text Text to render.
|
||||
* @param info Text Info to use while rendering.
|
||||
* @param measure The pre calcuted font measurement.
|
||||
*/
|
||||
void fontTextInitFromMeasure(font_t *font, primitive_t *primitive, char *text,
|
||||
fonttextinfo_t *info, fontmeasure_t *measure
|
||||
);
|
||||
|
||||
/**
|
||||
* Clean up a previously loaded font
|
||||
* @param font Loaded font.
|
||||
*/
|
||||
void fontDispose(font_t *Font);
|
||||
void fontTextInit(font_t *font, primitive_t *primitive, fonttextinfo_t *info);
|
@ -13,12 +13,10 @@ void pokerFrameInit(poker_t *poker, render_t *render) {
|
||||
frameBufferInit(&poker->frameWorld, render->width, render->height);
|
||||
frameBufferInit(&poker->frameGui, render->width, render->height);
|
||||
|
||||
fonttextinfo_t info;
|
||||
fonttextinfo_t *info;
|
||||
char *text = "Hello\n World";
|
||||
info = fontGetTextInfo(&poker->font, text);
|
||||
fontmeasure_t *measure = fontTextMeasure(&poker->font, text, &info, 16);
|
||||
fontTextInitFromMeasure(&poker->font, &bruh, text, &info, measure);
|
||||
fontTextMeasureDispose(measure);
|
||||
info = fontGetTextInfo(&poker->font, text, 16);
|
||||
fontTextInit(&poker->font, &bruh, info);
|
||||
}
|
||||
|
||||
void pokerFrameWorld(poker_t *poker, render_t *render) {
|
||||
|
Reference in New Issue
Block a user