diff --git a/CMakeLists.txt b/CMakeLists.txt index 09b1200..977912c 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -96,7 +96,7 @@ add_library(Lina::VG ALIAS ${PROJECT_NAME}) target_include_directories(${PROJECT_NAME} PUBLIC ${PROJECT_SOURCE_DIR}/include) target_compile_definitions(${PROJECT_NAME} PUBLIC LINAVG_VERSION_MAJOR=1) target_compile_definitions(${PROJECT_NAME} PUBLIC LINAVG_VERSION_MINOR=4) -target_compile_definitions(${PROJECT_NAME} PUBLIC LINAVG_VERSION_PATCH=1) +target_compile_definitions(${PROJECT_NAME} PUBLIC LINAVG_VERSION_PATCH=2) #-------------------------------------------------------------------- # Subdirectories & linking diff --git a/Examples/include/Backends/GL/GLBackend.hpp b/Examples/include/Backends/GL/GLBackend.hpp index 920bab6..1d841f3 100644 --- a/Examples/include/Backends/GL/GLBackend.hpp +++ b/Examples/include/Backends/GL/GLBackend.hpp @@ -61,12 +61,12 @@ namespace LinaVG::Backend ShaderData m_sdfTextShaderData; ShaderData m_simpleTextShaderData; float m_proj[4][4] = {0}; - char* m_defaultVtxShader = nullptr; - char* m_defaultFragShader = nullptr; - char* m_roundedGradientFragShader = nullptr; - char* m_texturedFragShader = nullptr; - char* m_sdfTextFragShader = nullptr; - char* m_simpleTextFragShader = nullptr; + const char* m_defaultVtxShader = nullptr; + const char* m_defaultFragShader = nullptr; + const char* m_roundedGradientFragShader = nullptr; + const char* m_texturedFragShader = nullptr; + const char* m_sdfTextFragShader = nullptr; + const char* m_simpleTextFragShader = nullptr; bool m_skipDraw = false; }; diff --git a/include/Core/Drawer.hpp b/include/Core/Drawer.hpp index 8efb4f1..a9ea210 100644 --- a/include/Core/Drawer.hpp +++ b/include/Core/Drawer.hpp @@ -469,7 +469,7 @@ namespace LinaVG /// /// For processing UTf8 texts. /// - uint32_t GetNextUnicodeChar(const char* text, uint32_t& byteCount); + std::vector GetUtf8Codepoints(const char* str); #endif }; // namespace Internal diff --git a/include/Core/Math.hpp b/include/Core/Math.hpp index 8ff4683..d65f1ff 100644 --- a/include/Core/Math.hpp +++ b/include/Core/Math.hpp @@ -82,10 +82,10 @@ namespace LinaVG /// static Vec2 GetPolygonCentroidFast(Vec2* points, int size); - static bool Math::IsEqual(const Vec2& v1, const Vec2& v2); - static bool Math::IsEqualMarg(const Vec2& v1, const Vec2& v2, float err = 0.001f); - static bool Math::IsEqualMarg(float f1, float f2, float err = 0.001f); - static bool Math::IsEqual(const Vec4& v1, const Vec4& v2); + static bool IsEqual(const Vec2& v1, const Vec2& v2); + static bool IsEqualMarg(const Vec2& v1, const Vec2& v2, float err = 0.001f); + static bool IsEqualMarg(float f1, float f2, float err = 0.001f); + static bool IsEqual(const Vec4& v1, const Vec4& v2); static float Abs(float f); static float Clamp(float f, float min, float max); static int Clamp(int i, int min, int max); diff --git a/src/Core/Drawer.cpp b/src/Core/Drawer.cpp index 13185a2..c2bb15f 100644 --- a/src/Core/Drawer.cpp +++ b/src/Core/Drawer.cpp @@ -3176,50 +3176,6 @@ namespace LinaVG return offset; } - uint32_t GetNextUnicodeChar(const char* p, uint32_t& byteCount) - { - uint32_t codepoint = 0; - if ((*p & 0b10000000) == 0b00000000) - { - // 1-byte character (ASCII) - auto ch = static_cast(*p); - byteCount = 1; - codepoint = static_cast(ch); - } - else if ((*p & 0b11100000) == 0b11000000) - { - // 2-byte character - codepoint = ((*p & 0b00011111) << 6) | - (*(p + 1) & 0b00111111); - byteCount = 2; - } - else if ((*p & 0b11110000) == 0b11100000) - { - // 3-byte character - codepoint = ((*p & 0b00001111) << 12) | - ((*(p + 1) & 0b00111111) << 6) | - (*(p + 2) & 0b00111111); - byteCount = 3; - } - else if ((*p & 0b11111000) == 0b11110000) - { - // 4-byte character - codepoint = ((*p & 0b00000111) << 18) | - ((*(p + 1) & 0b00111111) << 12) | - ((*(p + 2) & 0b00111111) << 6) | - (*(p + 3) & 0b00111111); - byteCount = 4; - } - else - { - // Invalid UTF-8 sequence - if (Config.errorCallback) - Config.errorCallback("LinaVG -> Invalid UTF-8 sequence!"); - } - - return codepoint; - } - void DrawText(DrawBuffer* buf, LinaVGFont* font, const char* text, const Vec2& position, const Vec2& offset, const Vec4Grad& color, float spacing, bool isGradient, float scale) { const uint8_t* c; @@ -3314,19 +3270,12 @@ namespace LinaVG if (font->m_supportsUnicode) { - const uint8_t* c = (const uint8_t*)text; - for (const char* p = text; *p; p++) - { - uint32_t byteCount = 0; - uint32_t character = GetNextUnicodeChar(p, byteCount); - - if (byteCount == 0) - return; + auto codepoints = GetUtf8Codepoints(text); - auto ch = font->m_characterGlyphs[character]; - drawChar(ch, character); - - p += byteCount - 1; + for (auto cp : codepoints) + { + auto ch = font->m_characterGlyphs[cp]; + drawChar(ch, cp); } } else @@ -3340,6 +3289,39 @@ namespace LinaVG } } + std::vector GetUtf8Codepoints(const char* str) + { + std::vector codepoints; + const char* p = str; + while (*p) + { + int32_t codepoint = 0; + unsigned char c = *p; + if (c < 0x80) + { // 1-byte sequence + codepoint = c; + p += 1; + } + else if (c < 0xE0) + { // 2-byte sequence + codepoint = ((p[0] & 0x1F) << 6) | (p[1] & 0x3F); + p += 2; + } + else if (c < 0xF0) + { // 3-byte sequence + codepoint = ((p[0] & 0x0F) << 12) | ((p[1] & 0x3F) << 6) | (p[2] & 0x3F); + p += 3; + } + else + { // 4-byte sequence + codepoint = ((p[0] & 0x07) << 18) | ((p[1] & 0x3F) << 12) | ((p[2] & 0x3F) << 6) | (p[3] & 0x3F); + p += 4; + } + codepoints.push_back(codepoint); + } + return codepoints; + } + Vec2 CalcTextSize(const char* text, LinaVGFont* font, float scale, float spacing, float sdfThickness) { float maxCharacterHeight = 0.0f; @@ -3355,18 +3337,12 @@ namespace LinaVG if (font->m_supportsUnicode) { - for (const char* p = text; *p; p++) - { - uint32_t byteCount = 0; - uint32_t character = GetNextUnicodeChar(p, byteCount); + auto codepoints = GetUtf8Codepoints(text); - if (byteCount == 0) - return Vec2(0, 0); - - auto ch = font->m_characterGlyphs[character]; - calcSizeChar(ch, character); - - p += byteCount - 1; + for (auto cp : codepoints) + { + auto ch = font->m_characterGlyphs[cp]; + calcSizeChar(ch, cp); } } else