How to dynamically scale font size in Godot
 
            
        
    In the difficult quest of making games compatible with (almost) all the existing screen resolutions, one of the main problem we've encountered is how to scale texts properly when resizing the UI.
In Godot (at least up to version 4.4) text size is not automatically scaled if its control scale changes (e.g. Label, RichTextLabel, etc...), so we need some tricks to get around this problem.
Our goal target
We're not thinking about resizing the windows!
You might go to Project Settings -> Window -> Strech Mode and then select something like the canvas_item mode (which would scale the entire window). It can definitely work, but it's not for every game or scenario (like ours, where we have some content that is scaling while the window size is the same or scales differently), so we need a proper "scaler" solution!
(I also miss Unity's TextMeshPro "Best Fit" option, which fits the entire text inside the control 🥲)
"Font Scaler" Script
We need to create a script that automatically scales the font of a target text node (e.g. Label, RichTextLabel, etc...).

Initial State
We are scaling the font/text based on the initial state of our label, which means that we need to cache everything from our target text first. This includes the initial font size and the control size itself (so that we can make a linear proportion).
var base_font_size : int
var base_size : Vector2
var label : Label
func _enter_tree():
  # caches initial sizes
  label = get_parent() as Label
  base_size = label.size
  base_font_size = label.get_theme_font_size("font_size", label.get_class())GDScript snippet to initialize the base size
Updating the Font when the Control changes
Every time the control is scaled we need to compare the new size with the base one, and then calculate the scaling ratio and update the font size.
First we need to listen to whenever the control is resized:
func _enter_tree():
  # ...
  label.resized.connect(set_text_size)
  
  # ...
func _exit_tree():
  # remember to disconnect when exiting!
  label.resized.disconnect(set_text_size)Then, the actual method that applies the scale:
# ...
func set_text_size():
  var new_size = label.size;
  
  # scale base on control width
  var scale = new_size.x / base_size.x;
  var scaled_size :int= floor(base_font_size * scale);
  # bitmap cannot be greater than 4096
  if scaled_size>4096:
    continue;
  
  # apply scale
  label.add_theme_font_size_override("font_scale", scaled_size);Now the Label text should automatically scale when the text control changes size. Yay!
Modifying the code for RichTextLabels
RichTextLabels are a bit more complex, because they have multiple font sizes inside their theme (for the "normal" font, italic, bold etc.).
The rest of this post is available for free!
Please create an account to continue reading! It helps us knowing that humans are reading us, and also helps us staying independent and keep posting what we love. Thanks! ❤️
✦ Create a Free Account & Continue ReadingMore Posts
How to make a Triplanar Shader in Godot
We made a simple terrain shader for Godot, which lets you apply different textures on based slopes and more. Have fun!
Text Animator for Godot is Out in Early Access!
Text Animator for Godot is out now in Early Access! Start bringing your texts to life in a few clicks and help us shape the future of this tool in Godot! Cheers!
Text Animator is coming to Godot, Unity and Unreal.. with a fresh new look!
Text Animator is coming to Godot, Unreal and Unity UI Toolkit with a fresh new look! Read more.
I'll be doing a workshop at DevGAMM Lisbon this year!
I'll be doing a workshop at DevGAMM Lisbon this year! Designing tools from start to finish and prototyping with Godot, docs and much more. Looking forward to it!
Creating custom inspectors in Godot C# more easily
Creating custom inspectors in Godot can become a bit tedious in C#, so we have built a custom and free addon that handles this for you!
LinkedIn will use your data to train their AI
Starting November 3rd, 2025, LinkedIn will start using your data to train their AI. Ughh.
 
              
             
            
             
            
             
            
             
            
             
            
            