diff options
| author | Jean-Philippe Bruyère <jp_bruyere@hotmail.com> | 2026-10-11 12:56:35 +0200 |
|---|---|---|
| committer | Jean-Philippe Bruyère <jp_bruyere@hotmail.com> | 2026-10-11 12:56:35 +0200 |
| commit | 0af4c5e54344fa14bb4bf587c0c2bf6c745a899a (patch) | |
| tree | a77a1a755b1c625300be3c2c7955aabc30a31e02 | |
| parent | b4babe4eab5bf39191e435e288edd78cff3c233b (diff) | |
vertical text support
| -rw-r--r-- | include/vkvg.h | 6 | ||||
| -rw-r--r-- | src/vkvg_context.c | 5 | ||||
| -rw-r--r-- | src/vkvg_fonts.c | 10 | ||||
| -rw-r--r-- | src/vkvg_fonts.h | 1 | ||||
| -rw-r--r-- | tests/fonts/fontquery.c | 24 |
5 files changed, 34 insertions, 12 deletions
diff --git a/include/vkvg.h b/include/vkvg.h index 04e60eb..8356c44 100644 --- a/include/vkvg.h +++ b/include/vkvg.h @@ -1698,6 +1698,12 @@ vkvg_public void vkvg_load_font_from_memory(VkvgContext ctx, unsigned char* font */ vkvg_public void vkvg_set_font_size(VkvgContext ctx, uint32_t size); /** + * @brief vkvg_set_text_direction + * @param ctx + * @param direction + */ +vkvg_public void vkvg_set_text_direction(VkvgContext ctx, vkvg_direction_t direction); +/** * @brief set current font for context, see @ref vkvg_font_create to create fonts. * * @param ctx a valid vkvg @ref context diff --git a/src/vkvg_context.c b/src/vkvg_context.c index 5893c82..129972e 100644 --- a/src/vkvg_context.c +++ b/src/vkvg_context.c @@ -1228,7 +1228,10 @@ void vkvg_set_font_size(VkvgContext ctx, uint32_t size) { } void vkvg_set_text_direction(vkvg_context* ctx, vkvg_direction_t direction) { - + if (vkvg_status(ctx)) + return; + RECORD(ctx, VKVG_CMD_SET_TEXT_DIRECTION, size); + ctx->textDirection = direction; } void vkvg_show_text(VkvgContext ctx, const char* text) { diff --git a/src/vkvg_fonts.c b/src/vkvg_fonts.c index 342654c..b89d27a 100644 --- a/src/vkvg_fonts.c +++ b/src/vkvg_fonts.c @@ -631,10 +631,15 @@ bool try_get_font_size (FontFace face, uint32_t pt26_6, VkvgFont *font) { #ifdef VKVG_USE_HARFBUZZ // Get harfBuzz buffer for provided text. -hb_buffer_t* _get_hb_buffer(VkvgFont font, const char* text, int length) { +hb_buffer_t* _get_hb_buffer(VkvgText textRun, const char* text, int length) { + VkvgFont font = textRun->font; hb_buffer_t* buf = hb_buffer_create(); hb_buffer_add_utf8 (buf, text, length, 0, length); hb_buffer_guess_segment_properties (buf); + + if (textRun->textDirection == VKVG_VERTICAL) + hb_buffer_set_direction(buf, HB_DIRECTION_TTB); + hb_shape(font->face->hb_font, buf, NULL, 0); if (hb_buffer_get_content_type(buf) != HB_BUFFER_CONTENT_TYPE_GLYPHS) { @@ -725,12 +730,13 @@ void _font_cache_show_text(VkvgContext ctx, const char* text) { void text_run_init(VkvgContext ctx, const char* text, int length, VkvgText textRun) { textRun->dev = ctx->dev; textRun->font = ctx->currentFont; + textRun->textDirection = ctx->textDirection; vkvg_font_reference (textRun->font); _font_lock_size(ctx, textRun->font); #ifdef VKVG_USE_HARFBUZZ - textRun->hbBuf = _get_hb_buffer(textRun->font, text, length); + textRun->hbBuf = _get_hb_buffer(textRun, text, length); textRun->glyphs = hb_buffer_get_glyph_positions(textRun->hbBuf, &textRun->glyph_count); #else diff --git a/src/vkvg_fonts.h b/src/vkvg_fonts.h index 25770c6..ca21860 100644 --- a/src/vkvg_fonts.h +++ b/src/vkvg_fonts.h @@ -288,6 +288,7 @@ typedef struct { typedef struct _vkvg_text_run_t { VkvgFont font; /* vkvg font structure pointer */ VkvgDevice dev; /* vkvg device associated with this text run */ + vkvg_direction_t textDirection; /* horizontal or vertical */ vkvg_text_extents_t extents; /* store computed text extends */ const char* text; /* utf8 char array of text*/ unsigned int glyph_count;/* Total glyph count */ diff --git a/tests/fonts/fontquery.c b/tests/fonts/fontquery.c index 37b8a92..5bfe10f 100644 --- a/tests/fonts/fontquery.c +++ b/tests/fonts/fontquery.c @@ -172,6 +172,7 @@ bool try_get_sample_string(FcPattern* font_entry, FT_Face face, char* str) { VkvgFont sans16 = NULL; char txtBuffer[MAX_TXT_LEN]; int txtBuffPtr = 0; +bool vertical = false; float uiFontSize = 18.f; @@ -197,13 +198,14 @@ void draw(VkvgSurface surfFont) { vkvg_move_to(ctx, xQ, yQ); vkvg_show_text(ctx, txtBuffer); - char tmp[1024]; - strcpy(tmp,txtBuffer); + char txtBuffCopy[MAX_TXT_LEN]; + char tmp[MAX_TXT_LEN]; + strcpy(txtBuffCopy,txtBuffer); FcPattern* request = FcPatternCreate(); FcObjectSet* requested_elements = FcObjectSetBuild(FC_FAMILY, FC_STYLE, FC_FILE, FC_LANG, (char *)0); - char *style = strstr(tmp, ":"); + char *style = strstr(txtBuffCopy, ":"); if (style) { *style='\0'; style++; @@ -213,7 +215,7 @@ void draw(VkvgSurface surfFont) { style = NULL; } } - FcPatternAddString(request, FC_FAMILY, (const FcChar8 *)tmp); + FcPatternAddString(request, FC_FAMILY, (const FcChar8 *)txtBuffCopy); FcPatternAddBool(request, FC_SCALABLE, FcTrue); FcPatternAddString(request, FC_FONTFORMAT, (const FcChar8 *)"TrueType"); @@ -240,19 +242,21 @@ void draw(VkvgSurface surfFont) { FcPatternGetString (font, FC_STYLE, 0, &style_variant); VkvgFont f = vkvg_font_create_from_file(device, (char*)fontFile, index, fontSize); if (vkvg_font_status(f)) { - printf("Error trying to load %s, from %s\n", tmp, fontFile); + printf("Error trying to load %s, from %s\n", txtBuffCopy, fontFile); fflush(stdout); goto clean_exit; } vkvg_set_font (ctx, f); + if (vertical) + vkvg_set_text_direction (ctx, VKVG_VERTICAL); penX = 200; penY = 200; - sprintf(tmp, "%s : %s", family_name, style_variant); + sprintf(txtBuffCopy, "%s : %s", family_name, style_variant); vkvg_font_extents_t fe = {0}; vkvg_font_extents(ctx, &fe); - VkvgText tr = vkvg_text_run_create(ctx, tmp); + VkvgText tr = vkvg_text_run_create(ctx, txtBuffCopy); vkvg_text_extents_t extents = {0}; vkvg_text_run_get_extents(tr, &extents); vkvg_rectangle(ctx, penX, penY - fe.ascent, extents.width, extents.height); @@ -280,7 +284,7 @@ void draw(VkvgSurface surfFont) { FcPatternGetString (font, FC_FAMILY, 0, &family_name); FcPatternGetString (font, FC_STYLE, 0, &style_variant); - if (family_name && strstr((char*)family_name, tmp)) { + if (family_name && strstr((char*)family_name, (char*)txtBuffCopy)) { if (!style || (style && style_variant && strstr((char*)style_variant, style))) { sprintf(tmp, "%s:%s", family_name,style_variant); vkvg_move_to(ctx, penX, penY); @@ -291,7 +295,6 @@ void draw(VkvgSurface surfFont) { break; } } - } } clean_exit: @@ -329,6 +332,9 @@ static void key_callback(GLFWwindow* window, int key, int scancode, int action, } txtBuffer[txtBuffPtr]='\0'; break; + case GLFW_KEY_F4: + vertical = !vertical; + break; /*case GLFW_KEY_DELETE: if (txtBuffPtr > 0 && txtBuffPtr < MAX_TXT_LEN - 2) { memmove(&txtBuffer[txtBuffPtr], (&txtBuffer[txtBuffPtr + 1], MAX_TXT_LEN - txtB) |