summaryrefslogtreecommitdiffstats
path: root/modules/text_server_adv
diff options
context:
space:
mode:
authorbruvzg <7645683+bruvzg@users.noreply.github.com>2023-08-14 10:42:49 +0300
committerbruvzg <7645683+bruvzg@users.noreply.github.com>2023-10-13 12:57:45 +0300
commit9a1e0e4aef06ef1803e227c03f4dff6a964d1ba1 (patch)
tree39238d2782e3af7735c26a91acae06acf5b887a1 /modules/text_server_adv
parent37ee293be82e625e68704a78477b841d0ba17b8f (diff)
downloadredot-engine-9a1e0e4aef06ef1803e227c03f4dff6a964d1ba1.tar.gz
[Bitmap fonts] Add support for scaling.
Diffstat (limited to 'modules/text_server_adv')
-rw-r--r--modules/text_server_adv/text_server_adv.cpp114
-rw-r--r--modules/text_server_adv/text_server_adv.h4
2 files changed, 114 insertions, 4 deletions
diff --git a/modules/text_server_adv/text_server_adv.cpp b/modules/text_server_adv/text_server_adv.cpp
index 2e994f277d..16046ef053 100644
--- a/modules/text_server_adv/text_server_adv.cpp
+++ b/modules/text_server_adv/text_server_adv.cpp
@@ -2249,7 +2249,7 @@ void TextServerAdvanced::_font_set_msdf_size(const RID &p_font_rid, int64_t p_ms
int64_t TextServerAdvanced::_font_get_msdf_size(const RID &p_font_rid) const {
FontAdvanced *fd = _get_font_data(p_font_rid);
- ERR_FAIL_NULL_V(fd, false);
+ ERR_FAIL_NULL_V(fd, 0);
MutexLock lock(fd->mutex);
return fd->msdf_source_size;
@@ -2265,12 +2265,28 @@ void TextServerAdvanced::_font_set_fixed_size(const RID &p_font_rid, int64_t p_f
int64_t TextServerAdvanced::_font_get_fixed_size(const RID &p_font_rid) const {
FontAdvanced *fd = _get_font_data(p_font_rid);
- ERR_FAIL_NULL_V(fd, false);
+ ERR_FAIL_NULL_V(fd, 0);
MutexLock lock(fd->mutex);
return fd->fixed_size;
}
+void TextServerAdvanced::_font_set_fixed_size_scale_mode(const RID &p_font_rid, TextServer::FixedSizeScaleMode p_fixed_size_scale_mode) {
+ FontAdvanced *fd = _get_font_data(p_font_rid);
+ ERR_FAIL_NULL(fd);
+
+ MutexLock lock(fd->mutex);
+ fd->fixed_size_scale_mode = p_fixed_size_scale_mode;
+}
+
+TextServer::FixedSizeScaleMode TextServerAdvanced::_font_get_fixed_size_scale_mode(const RID &p_font_rid) const {
+ FontAdvanced *fd = _get_font_data(p_font_rid);
+ ERR_FAIL_NULL_V(fd, FIXED_SIZE_SCALE_DISABLE);
+
+ MutexLock lock(fd->mutex);
+ return fd->fixed_size_scale_mode;
+}
+
void TextServerAdvanced::_font_set_allow_system_fallback(const RID &p_font_rid, bool p_allow_system_fallback) {
FontAdvanced *fd = _get_font_data(p_font_rid);
ERR_FAIL_NULL(fd);
@@ -2507,6 +2523,12 @@ double TextServerAdvanced::_font_get_ascent(const RID &p_font_rid, int64_t p_siz
if (fd->msdf) {
return fd->cache[size]->ascent * (double)p_size / (double)fd->msdf_source_size;
+ } else if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ return fd->cache[size]->ascent * (double)p_size / (double)fd->fixed_size;
+ } else {
+ return fd->cache[size]->ascent * Math::round((double)p_size / (double)fd->fixed_size);
+ }
} else {
return fd->cache[size]->ascent;
}
@@ -2533,6 +2555,12 @@ double TextServerAdvanced::_font_get_descent(const RID &p_font_rid, int64_t p_si
if (fd->msdf) {
return fd->cache[size]->descent * (double)p_size / (double)fd->msdf_source_size;
+ } else if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ return fd->cache[size]->descent * (double)p_size / (double)fd->fixed_size;
+ } else {
+ return fd->cache[size]->descent * Math::round((double)p_size / (double)fd->fixed_size);
+ }
} else {
return fd->cache[size]->descent;
}
@@ -2560,6 +2588,12 @@ double TextServerAdvanced::_font_get_underline_position(const RID &p_font_rid, i
if (fd->msdf) {
return fd->cache[size]->underline_position * (double)p_size / (double)fd->msdf_source_size;
+ } else if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ return fd->cache[size]->underline_position * (double)p_size / (double)fd->fixed_size;
+ } else {
+ return fd->cache[size]->underline_position * Math::round((double)p_size / (double)fd->fixed_size);
+ }
} else {
return fd->cache[size]->underline_position;
}
@@ -2587,6 +2621,12 @@ double TextServerAdvanced::_font_get_underline_thickness(const RID &p_font_rid,
if (fd->msdf) {
return fd->cache[size]->underline_thickness * (double)p_size / (double)fd->msdf_source_size;
+ } else if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ return fd->cache[size]->underline_thickness * (double)p_size / (double)fd->fixed_size;
+ } else {
+ return fd->cache[size]->underline_thickness * Math::round((double)p_size / (double)fd->fixed_size);
+ }
} else {
return fd->cache[size]->underline_thickness;
}
@@ -2619,6 +2659,12 @@ double TextServerAdvanced::_font_get_scale(const RID &p_font_rid, int64_t p_size
if (fd->msdf) {
return fd->cache[size]->scale * (double)p_size / (double)fd->msdf_source_size;
+ } else if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ return fd->cache[size]->scale * (double)p_size / (double)fd->fixed_size;
+ } else {
+ return fd->cache[size]->scale * Math::round((double)p_size / (double)fd->fixed_size);
+ }
} else {
return fd->cache[size]->scale / fd->cache[size]->oversampling;
}
@@ -2828,6 +2874,12 @@ Vector2 TextServerAdvanced::_font_get_glyph_advance(const RID &p_font_rid, int64
double scale = _font_get_scale(p_font_rid, p_size);
if (fd->msdf) {
return (gl[p_glyph | mod].advance + ea) * (double)p_size / (double)fd->msdf_source_size;
+ } else if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ return (gl[p_glyph | mod].advance + ea) * (double)p_size / (double)fd->fixed_size;
+ } else {
+ return (gl[p_glyph | mod].advance + ea) * Math::round((double)p_size / (double)fd->fixed_size);
+ }
} else if ((scale == 1.0) && ((fd->subpixel_positioning == SUBPIXEL_POSITIONING_DISABLED) || (fd->subpixel_positioning == SUBPIXEL_POSITIONING_AUTO && size.x > SUBPIXEL_POSITIONING_ONE_HALF_MAX_SIZE))) {
return (gl[p_glyph | mod].advance + ea).round();
} else {
@@ -2875,6 +2927,12 @@ Vector2 TextServerAdvanced::_font_get_glyph_offset(const RID &p_font_rid, const
if (fd->msdf) {
return gl[p_glyph | mod].rect.position * (double)p_size.x / (double)fd->msdf_source_size;
+ } else if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size.x) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ return gl[p_glyph | mod].rect.position * (double)p_size.x / (double)fd->fixed_size;
+ } else {
+ return gl[p_glyph | mod].rect.position * Math::round((double)p_size.x / (double)fd->fixed_size);
+ }
} else {
return gl[p_glyph | mod].rect.position;
}
@@ -2920,6 +2978,12 @@ Vector2 TextServerAdvanced::_font_get_glyph_size(const RID &p_font_rid, const Ve
if (fd->msdf) {
return gl[p_glyph | mod].rect.size * (double)p_size.x / (double)fd->msdf_source_size;
+ } else if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size.x) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ return gl[p_glyph | mod].rect.size * (double)p_size.x / (double)fd->fixed_size;
+ } else {
+ return gl[p_glyph | mod].rect.size * Math::round((double)p_size.x / (double)fd->fixed_size);
+ }
} else {
return gl[p_glyph | mod].rect.size;
}
@@ -3143,6 +3207,12 @@ Dictionary TextServerAdvanced::_font_get_glyph_contours(const RID &p_font_rid, i
double scale = (1.0 / 64.0) / fd->cache[size]->oversampling * fd->cache[size]->scale;
if (fd->msdf) {
scale = scale * (double)p_size / (double)fd->msdf_source_size;
+ } else if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ scale = scale * (double)p_size / (double)fd->fixed_size;
+ } else {
+ scale = scale * Math::round((double)p_size / (double)fd->fixed_size);
+ }
}
for (short i = 0; i < fd->cache[size]->face->glyph->outline.n_points; i++) {
points.push_back(Vector3(fd->cache[size]->face->glyph->outline.points[i].x * scale, -fd->cache[size]->face->glyph->outline.points[i].y * scale, FT_CURVE_TAG(fd->cache[size]->face->glyph->outline.tags[i])));
@@ -3225,6 +3295,12 @@ Vector2 TextServerAdvanced::_font_get_kerning(const RID &p_font_rid, int64_t p_s
if (kern.has(p_glyph_pair)) {
if (fd->msdf) {
return kern[p_glyph_pair] * (double)p_size / (double)fd->msdf_source_size;
+ } else if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ return kern[p_glyph_pair] * (double)p_size / (double)fd->fixed_size;
+ } else {
+ return kern[p_glyph_pair] * Math::round((double)p_size / (double)fd->fixed_size);
+ }
} else {
return kern[p_glyph_pair];
}
@@ -3235,6 +3311,12 @@ Vector2 TextServerAdvanced::_font_get_kerning(const RID &p_font_rid, int64_t p_s
FT_Get_Kerning(fd->cache[size]->face, p_glyph_pair.x, p_glyph_pair.y, FT_KERNING_DEFAULT, &delta);
if (fd->msdf) {
return Vector2(delta.x, delta.y) * (double)p_size / (double)fd->msdf_source_size;
+ } else if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ return Vector2(delta.x, delta.y) * (double)p_size / (double)fd->fixed_size;
+ } else {
+ return Vector2(delta.x, delta.y) * Math::round((double)p_size / (double)fd->fixed_size);
+ }
} else {
return Vector2(delta.x, delta.y);
}
@@ -3499,8 +3581,20 @@ void TextServerAdvanced::_font_draw_glyph(const RID &p_font_rid, const RID &p_ca
cpos.y = Math::floor(cpos.y);
cpos.x = Math::floor(cpos.x);
}
- cpos += gl.rect.position;
+ Vector2 gpos = gl.rect.position;
Size2 csize = gl.rect.size;
+ if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ double gl_scale = (double)p_size / (double)fd->fixed_size;
+ gpos *= gl_scale;
+ csize *= gl_scale;
+ } else {
+ double gl_scale = Math::round((double)p_size / (double)fd->fixed_size);
+ gpos *= gl_scale;
+ csize *= gl_scale;
+ }
+ }
+ cpos += gpos;
if (lcd_aa) {
RenderingServer::get_singleton()->canvas_item_add_lcd_texture_rect_region(p_canvas, Rect2(cpos, csize), texture, gl.uv_rect, modulate);
} else {
@@ -3591,8 +3685,20 @@ void TextServerAdvanced::_font_draw_glyph_outline(const RID &p_font_rid, const R
cpos.y = Math::floor(cpos.y);
cpos.x = Math::floor(cpos.x);
}
- cpos += gl.rect.position;
+ Vector2 gpos = gl.rect.position;
Size2 csize = gl.rect.size;
+ if (fd->fixed_size > 0 && fd->fixed_size_scale_mode != FIXED_SIZE_SCALE_DISABLE && size.x != p_size) {
+ if (fd->fixed_size_scale_mode == FIXED_SIZE_SCALE_ENABLED) {
+ double gl_scale = (double)p_size / (double)fd->fixed_size;
+ gpos *= gl_scale;
+ csize *= gl_scale;
+ } else {
+ double gl_scale = Math::round((double)p_size / (double)fd->fixed_size);
+ gpos *= gl_scale;
+ csize *= gl_scale;
+ }
+ }
+ cpos += gpos;
if (lcd_aa) {
RenderingServer::get_singleton()->canvas_item_add_lcd_texture_rect_region(p_canvas, Rect2(cpos, csize), texture, gl.uv_rect, modulate);
} else {
diff --git a/modules/text_server_adv/text_server_adv.h b/modules/text_server_adv/text_server_adv.h
index 57cca819be..f1932d9c50 100644
--- a/modules/text_server_adv/text_server_adv.h
+++ b/modules/text_server_adv/text_server_adv.h
@@ -305,6 +305,7 @@ class TextServerAdvanced : public TextServerExtension {
bool mipmaps = false;
bool msdf = false;
int msdf_range = 14;
+ FixedSizeScaleMode fixed_size_scale_mode = FIXED_SIZE_SCALE_DISABLE;
int msdf_source_size = 48;
int fixed_size = 0;
bool allow_system_fallback = true;
@@ -763,6 +764,9 @@ public:
MODBIND2(font_set_fixed_size, const RID &, int64_t);
MODBIND1RC(int64_t, font_get_fixed_size, const RID &);
+ MODBIND2(font_set_fixed_size_scale_mode, const RID &, FixedSizeScaleMode);
+ MODBIND1RC(FixedSizeScaleMode, font_get_fixed_size_scale_mode, const RID &);
+
MODBIND2(font_set_allow_system_fallback, const RID &, bool);
MODBIND1RC(bool, font_is_allow_system_fallback, const RID &);