diff options
Diffstat (limited to 'modules/text_server_fb')
-rw-r--r-- | modules/text_server_fb/text_server_fb.cpp | 141 | ||||
-rw-r--r-- | modules/text_server_fb/text_server_fb.h | 18 |
2 files changed, 145 insertions, 14 deletions
diff --git a/modules/text_server_fb/text_server_fb.cpp b/modules/text_server_fb/text_server_fb.cpp index f598eb80ea..0728812ecb 100644 --- a/modules/text_server_fb/text_server_fb.cpp +++ b/modules/text_server_fb/text_server_fb.cpp @@ -33,6 +33,8 @@ #include "core/error/error_macros.h" #include "core/string/print_string.h" +#include "modules/modules_enabled.gen.h" // For freetype, msdfgen. + #ifdef MODULE_MSDFGEN_ENABLED #include "core/ShapeDistanceFinder.h" #include "core/contour-combiners.h" @@ -736,6 +738,23 @@ _FORCE_INLINE_ bool TextServerFallback::_ensure_cache_for_size(FontDataFallback fd->underline_thickness = (FT_MulFix(fd->face->underline_thickness, fd->face->size->metrics.y_scale) / 64.0) / fd->oversampling * fd->scale; if (!p_font_data->face_init) { + // Get style flags and name. + if (fd->face->family_name != nullptr) { + p_font_data->font_name = String::utf8((const char *)fd->face->family_name); + } + if (fd->face->style_name != nullptr) { + p_font_data->style_name = String::utf8((const char *)fd->face->style_name); + } + p_font_data->style_flags = 0; + if (fd->face->style_flags & FT_STYLE_FLAG_BOLD) { + p_font_data->style_flags |= FONT_BOLD; + } + if (fd->face->style_flags & FT_STYLE_FLAG_ITALIC) { + p_font_data->style_flags |= FONT_ITALIC; + } + if (fd->face->face_flags & FT_FACE_FLAG_FIXED_WIDTH) { + p_font_data->style_flags |= FONT_FIXED_WIDTH; + } // Read OpenType variations. p_font_data->supported_varaitions.clear(); if (fd->face->face_flags & FT_FACE_FLAG_MULTIPLE_MASTERS) { @@ -826,6 +845,66 @@ void TextServerFallback::font_set_data_ptr(RID p_font_rid, const uint8_t *p_data fd->data_size = p_data_size; } +void TextServerFallback::font_set_style(RID p_font_rid, uint32_t /*FontStyle*/ p_style) { + FontDataFallback *fd = font_owner.get_or_null(p_font_rid); + ERR_FAIL_COND(!fd); + + MutexLock lock(fd->mutex); + Vector2i size = _get_size(fd, 16); + ERR_FAIL_COND(!_ensure_cache_for_size(fd, size)); + fd->style_flags = p_style; +} + +uint32_t /*FontStyle*/ TextServerFallback::font_get_style(RID p_font_rid) const { + FontDataFallback *fd = font_owner.get_or_null(p_font_rid); + ERR_FAIL_COND_V(!fd, 0); + + MutexLock lock(fd->mutex); + Vector2i size = _get_size(fd, 16); + ERR_FAIL_COND_V(!_ensure_cache_for_size(fd, size), 0); + return fd->style_flags; +} + +void TextServerFallback::font_set_style_name(RID p_font_rid, const String &p_name) { + FontDataFallback *fd = font_owner.get_or_null(p_font_rid); + ERR_FAIL_COND(!fd); + + MutexLock lock(fd->mutex); + Vector2i size = _get_size(fd, 16); + ERR_FAIL_COND(!_ensure_cache_for_size(fd, size)); + fd->style_name = p_name; +} + +String TextServerFallback::font_get_style_name(RID p_font_rid) const { + FontDataFallback *fd = font_owner.get_or_null(p_font_rid); + ERR_FAIL_COND_V(!fd, String()); + + MutexLock lock(fd->mutex); + Vector2i size = _get_size(fd, 16); + ERR_FAIL_COND_V(!_ensure_cache_for_size(fd, size), String()); + return fd->style_name; +} + +void TextServerFallback::font_set_name(RID p_font_rid, const String &p_name) { + FontDataFallback *fd = font_owner.get_or_null(p_font_rid); + ERR_FAIL_COND(!fd); + + MutexLock lock(fd->mutex); + Vector2i size = _get_size(fd, 16); + ERR_FAIL_COND(!_ensure_cache_for_size(fd, size)); + fd->font_name = p_name; +} + +String TextServerFallback::font_get_name(RID p_font_rid) const { + FontDataFallback *fd = font_owner.get_or_null(p_font_rid); + ERR_FAIL_COND_V(!fd, String()); + + MutexLock lock(fd->mutex); + Vector2i size = _get_size(fd, 16); + ERR_FAIL_COND_V(!_ensure_cache_for_size(fd, size), String()); + return fd->font_name; +} + void TextServerFallback::font_set_antialiased(RID p_font_rid, bool p_antialiased) { FontDataFallback *fd = font_owner.get_or_null(p_font_rid); ERR_FAIL_COND(!fd); @@ -2030,6 +2109,27 @@ TextServer::Direction TextServerFallback::shaped_text_get_direction(RID p_shaped return TextServer::DIRECTION_LTR; } +void TextServerFallback::shaped_text_set_custom_punctuation(RID p_shaped, const String &p_punct) { + _THREAD_SAFE_METHOD_ + ShapedTextData *sd = shaped_owner.get_or_null(p_shaped); + ERR_FAIL_COND(!sd); + + if (sd->custom_punct != p_punct) { + if (sd->parent != RID()) { + full_copy(sd); + } + sd->custom_punct = p_punct; + invalidate(sd); + } +} + +String TextServerFallback::shaped_text_get_custom_punctuation(RID p_shaped) const { + _THREAD_SAFE_METHOD_ + const ShapedTextData *sd = shaped_owner.get_or_null(p_shaped); + ERR_FAIL_COND_V(!sd, String()); + return sd->custom_punct; +} + void TextServerFallback::shaped_text_set_orientation(RID p_shaped, TextServer::Orientation p_orientation) { ShapedTextData *sd = shaped_owner.get_or_null(p_shaped); ERR_FAIL_COND(!sd); @@ -2332,6 +2432,7 @@ RID TextServerFallback::shaped_text_substr(RID p_shaped, int p_start, int p_leng new_sd->orientation = sd->orientation; new_sd->direction = sd->direction; + new_sd->custom_punct = sd->custom_punct; new_sd->para_direction = sd->para_direction; new_sd->line_breaks_valid = sd->line_breaks_valid; new_sd->justification_ops_valid = sd->justification_ops_valid; @@ -2615,27 +2716,41 @@ bool TextServerFallback::shaped_text_update_breaks(RID p_shaped) { } int sd_size = sd->glyphs.size(); + Glyph *sd_glyphs = sd->glyphs.ptrw(); + + int c_punct_size = sd->custom_punct.length(); + const char32_t *c_punct = sd->custom_punct.ptr(); + for (int i = 0; i < sd_size; i++) { - if (sd->glyphs[i].count > 0) { - char32_t c = sd->text[sd->glyphs[i].start]; - if (is_punct(c)) { - sd->glyphs.write[i].flags |= GRAPHEME_IS_PUNCTUATION; + if (sd_glyphs[i].count > 0) { + char32_t c = sd->text[sd_glyphs[i].start]; + if (c_punct_size == 0) { + if (is_punct(c)) { + sd_glyphs[i].flags |= GRAPHEME_IS_PUNCTUATION; + } + } else { + for (int j = 0; j < c_punct_size; j++) { + if (c_punct[j] == c) { + sd_glyphs[i].flags |= GRAPHEME_IS_PUNCTUATION; + break; + } + } } if (is_underscore(c)) { sd->glyphs.write[i].flags |= GRAPHEME_IS_UNDERSCORE; } if (is_whitespace(c) && !is_linebreak(c)) { - sd->glyphs.write[i].flags |= GRAPHEME_IS_SPACE; - sd->glyphs.write[i].flags |= GRAPHEME_IS_BREAK_SOFT; + sd_glyphs[i].flags |= GRAPHEME_IS_SPACE; + sd_glyphs[i].flags |= GRAPHEME_IS_BREAK_SOFT; } if (is_linebreak(c)) { - sd->glyphs.write[i].flags |= GRAPHEME_IS_BREAK_HARD; + sd_glyphs[i].flags |= GRAPHEME_IS_BREAK_HARD; } if (c == 0x0009 || c == 0x000b) { - sd->glyphs.write[i].flags |= GRAPHEME_IS_TAB; + sd_glyphs[i].flags |= GRAPHEME_IS_TAB; } - i += (sd->glyphs[i].count - 1); + i += (sd_glyphs[i].count - 1); } } sd->line_breaks_valid = true; @@ -2713,10 +2828,10 @@ void TextServerFallback::shaped_text_overrun_trim_to_width(RID p_shaped_line, fl width -= sd_glyphs[i].advance * sd_glyphs[i].repeat; if (sd_glyphs[i].count > 0) { - bool above_min_char_treshold = (i >= ell_min_characters); + bool above_min_char_threshold = (i >= ell_min_characters); - if (width + (((above_min_char_treshold && add_ellipsis) || enforce_ellipsis) ? ellipsis_width : 0) <= p_width) { - if (cut_per_word && above_min_char_treshold) { + if (width + (((above_min_char_threshold && add_ellipsis) || enforce_ellipsis) ? ellipsis_width : 0) <= p_width) { + if (cut_per_word && above_min_char_threshold) { if ((sd_glyphs[i].flags & GRAPHEME_IS_BREAK_SOFT) == GRAPHEME_IS_BREAK_SOFT) { last_valid_cut = i; found = true; @@ -2728,7 +2843,7 @@ void TextServerFallback::shaped_text_overrun_trim_to_width(RID p_shaped_line, fl if (found) { trim_pos = last_valid_cut; - if (add_ellipsis && (above_min_char_treshold || enforce_ellipsis) && width - ellipsis_width <= p_width) { + if (add_ellipsis && (above_min_char_threshold || enforce_ellipsis) && width - ellipsis_width <= p_width) { ellipsis_pos = trim_pos; } break; diff --git a/modules/text_server_fb/text_server_fb.h b/modules/text_server_fb/text_server_fb.h index fb7de8f443..67b08d1eac 100644 --- a/modules/text_server_fb/text_server_fb.h +++ b/modules/text_server_fb/text_server_fb.h @@ -42,7 +42,7 @@ #include "core/templates/thread_work_pool.h" #include "scene/resources/texture.h" -#include "modules/modules_enabled.gen.h" +#include "modules/modules_enabled.gen.h" // For freetype, msdfgen. #ifdef MODULE_FREETYPE_ENABLED #include <ft2build.h> @@ -142,6 +142,10 @@ class TextServerFallback : public TextServer { Dictionary variation_coordinates; float oversampling = 0.f; + uint32_t style_flags = 0; + String font_name; + String style_name; + Map<Vector2i, FontDataForSizeFallback *> cache; bool face_init = false; @@ -234,6 +238,15 @@ public: virtual void font_set_data(RID p_font_rid, const PackedByteArray &p_data) override; virtual void font_set_data_ptr(RID p_font_rid, const uint8_t *p_data_ptr, size_t p_data_size) override; + virtual void font_set_style(RID p_font_rid, uint32_t /*FontStyle*/ p_style) override; + virtual uint32_t /*FontStyle*/ font_get_style(RID p_font_rid) const override; + + virtual void font_set_style_name(RID p_font_rid, const String &p_name) override; + virtual String font_get_style_name(RID p_font_rid) const override; + + virtual void font_set_name(RID p_font_rid, const String &p_name) override; + virtual String font_get_name(RID p_font_rid) const override; + virtual void font_set_antialiased(RID p_font_rid, bool p_antialiased) override; virtual bool font_is_antialiased(RID p_font_rid) const override; @@ -361,6 +374,9 @@ public: virtual void shaped_text_set_bidi_override(RID p_shaped, const Array &p_override) override; + virtual void shaped_text_set_custom_punctuation(RID p_shaped, const String &p_punct) override; + virtual String shaped_text_get_custom_punctuation(RID p_shaped) const override; + virtual void shaped_text_set_orientation(RID p_shaped, Orientation p_orientation = ORIENTATION_HORIZONTAL) override; virtual Orientation shaped_text_get_orientation(RID p_shaped) const override; |