From 6e4a9777f8f5b61668446924cc51bcfb1412fd1f Mon Sep 17 00:00:00 2001
From: Sam Lantinga <[EMAIL REDACTED]>
Date: Thu, 26 Sep 2024 20:04:28 -0700
Subject: [PATCH] Added TTF_GetGlyphScript()
Fixes https://github.com/libsdl-org/SDL_ttf/issues/351
Closes https://github.com/libsdl-org/SDL_ttf/pull/312
---
build-scripts/SDL_migration.cocci | 5 ++++
docs/README-migration.md | 1 +
include/SDL3_ttf/SDL_ttf.h | 28 ++++++++++++++++++---
src/SDL_ttf.c | 42 ++++++++++++++++++++++++++++++-
src/SDL_ttf.sym | 3 ++-
5 files changed, 73 insertions(+), 6 deletions(-)
diff --git a/build-scripts/SDL_migration.cocci b/build-scripts/SDL_migration.cocci
index 81b3788f..9a7c931d 100644
--- a/build-scripts/SDL_migration.cocci
+++ b/build-scripts/SDL_migration.cocci
@@ -155,3 +155,8 @@
- TTF_IsFontScalable
+ TTF_FontIsScalable
(...)
+@@
+@@
+- TTF_SetFontScriptName
++ TTF_SetFontScript
+ (...)
diff --git a/docs/README-migration.md b/docs/README-migration.md
index 422011fc..bebaa9b7 100644
--- a/docs/README-migration.md
+++ b/docs/README-migration.md
@@ -63,6 +63,7 @@ The following functions have been renamed:
* TTF_RenderUTF8_Shaded_Wrapped() => TTF_RenderText_Shaded_Wrapped()
* TTF_RenderUTF8_Solid() => SDL_RenderText_Solid()
* TTF_RenderUTF8_Solid_Wrapped() => TTF_RenderText_Solid_Wrapped()
+* TTF_SetFontScriptName() => TTF_SetFontScript()
* TTF_SetFontWrappedAlign() => TTF_SetFontWrapAlignment()
* TTF_SizeUTF8() => TTF_SizeText()
diff --git a/include/SDL3_ttf/SDL_ttf.h b/include/SDL3_ttf/SDL_ttf.h
index 31b376c6..cebe9e1c 100644
--- a/include/SDL3_ttf/SDL_ttf.h
+++ b/include/SDL3_ttf/SDL_ttf.h
@@ -1280,7 +1280,7 @@ typedef enum TTF_Direction
* - `TTF_DIRECTION_TTB` (Top to Bottom)
* - `TTF_DIRECTION_BTT` (Bottom to Top)
*
- * If SDL_ttf was not built with HarfBuzz support, this function returns -1.
+ * If SDL_ttf was not built with HarfBuzz support, this function returns false.
*
* \param font the font to specify a direction for.
* \param direction the new direction for text to flow.
@@ -1299,23 +1299,43 @@ extern SDL_DECLSPEC bool SDLCALL TTF_SetFontDirection(TTF_Font *font, TTF_Direct
* The supplied script value must be a null-terminated string of exactly four
* characters.
*
- * If SDL_ttf was not built with HarfBuzz support, this function returns -1.
+ * If SDL_ttf was not built with HarfBuzz support, this function returns false.
*
* \param font the font to specify a script name for.
* \param script null-terminated string of exactly 4 characters.
* \returns true on success or false on failure; call SDL_GetError() for more
* information.
*
+ * \threadsafety This function is not thread-safe.
+ *
+ * \since This function is available since SDL_ttf 3.0.0.
+ */
+extern SDL_DECLSPEC bool SDLCALL TTF_SetFontScript(TTF_Font *font, const char *script);
+
+/**
+ * Get the script used by a 32-bit codepoint.
+ *
+ * The supplied script value will be a null-terminated string of exactly four
+ * characters.
+ *
+ * If SDL_ttf was not built with HarfBuzz support, this function returns false.
+ *
+ * \param ch the character code to check.
+ * \param script a pointer filled in with the script used by `ch`.
+ * \param script_size the size of the script buffer, which must be at least 5 characters.
+ * \returns true on success or false on failure; call SDL_GetError() for more
+ * information.
+ *
* \threadsafety This function should be called on the thread that created the font.
*
* \since This function is available since SDL_ttf 3.0.0.
*/
-extern SDL_DECLSPEC bool SDLCALL TTF_SetFontScriptName(TTF_Font *font, const char *script);
+extern SDL_DECLSPEC bool SDLCALL TTF_GetGlyphScript(Uint32 ch, char *script, size_t script_size);
/**
* Set language to be used for text shaping by a font.
*
- * If SDL_ttf was not built with HarfBuzz support, this function returns -1.
+ * If SDL_ttf was not built with HarfBuzz support, this function returns false.
*
* \param font the font to specify a language for.
* \param language_bcp47 a null-terminated string containing the desired language's BCP47 code. Or null to reset the value.
diff --git a/src/SDL_ttf.c b/src/SDL_ttf.c
index 384286ce..1e9e9152 100644
--- a/src/SDL_ttf.c
+++ b/src/SDL_ttf.c
@@ -2903,7 +2903,7 @@ bool TTF_SetFontDirection(TTF_Font *font, TTF_Direction direction)
#endif
}
-bool TTF_SetFontScriptName(TTF_Font *font, const char *script)
+bool TTF_SetFontScript(TTF_Font *font, const char *script)
{
TTF_CHECK_FONT(font, false);
@@ -2928,6 +2928,46 @@ bool TTF_SetFontScriptName(TTF_Font *font, const char *script)
#endif
}
+bool TTF_GetGlyphScript(Uint32 ch, char *script, size_t script_size)
+{
+#if TTF_USE_HARFBUZZ
+ TTF_CHECK_POINTER("script", script, false);
+
+ if (script_size < 5) {
+ return SDL_SetError("Insufficient script buffer size");
+ }
+
+ hb_buffer_t *hb_buffer = hb_buffer_create();
+
+ if (hb_buffer == NULL) {
+ return SDL_SetError("Cannot create harfbuzz buffer");
+ }
+
+ hb_unicode_funcs_t* hb_unicode_functions = hb_buffer_get_unicode_funcs(hb_buffer);
+
+ if (hb_unicode_functions == NULL) {
+ hb_buffer_destroy(hb_buffer);
+ return SDL_SetError("Cannot get harfbuzz unicode functions");
+ }
+
+ hb_buffer_clear_contents(hb_buffer);
+ hb_buffer_set_content_type(hb_buffer, HB_BUFFER_CONTENT_TYPE_UNICODE);
+
+ uint8_t untagged_script[4] = { HB_UNTAG(hb_unicode_script(hb_unicode_functions, ch)) };
+ script[0] = (char)untagged_script[0];
+ script[1] = (char)untagged_script[1];
+ script[2] = (char)untagged_script[2];
+ script[3] = (char)untagged_script[3];
+ script[4] = '\0';
+
+ hb_buffer_destroy(hb_buffer);
+ return true;
+
+#else
+ return SDL_SetError("Unsupported");
+#endif
+}
+
bool TTF_SetFontLanguage(TTF_Font *font, const char *language_bcp47)
{
TTF_CHECK_FONT(font, false);
diff --git a/src/SDL_ttf.sym b/src/SDL_ttf.sym
index c6891704..b8bfb910 100644
--- a/src/SDL_ttf.sym
+++ b/src/SDL_ttf.sym
@@ -20,6 +20,7 @@ SDL3_ttf_0.0.0 {
TTF_GetFreeTypeVersion;
TTF_GetGlyphKerning;
TTF_GetGlyphMetrics;
+ TTF_GetGlyphScript;
TTF_GetHarfBuzzVersion;
TTF_Init;
TTF_MeasureText;
@@ -46,7 +47,7 @@ SDL3_ttf_0.0.0 {
TTF_SetFontLineSkip;
TTF_SetFontOutline;
TTF_SetFontSDF;
- TTF_SetFontScriptName;
+ TTF_SetFontScript;
TTF_SetFontSize;
TTF_SetFontSizeDPI;
TTF_SetFontStyle;