How do i animate letters like this?

So I’ve been playing two games recently that have a really cool dialogue system that I’ve been trying copy for a while, I tried a couple of things to get this effect bu none of them worked and honestly i have no clue how they do this and I’m hoping to get some help from this forum post

clip:
https://gyazo.com/0e2731034362385bb4b0404e452796ab

credit: Demonfist

1 Like

You can create individual text labels for each letter then move them into place.

Here is how I would implement it.

local TweenService = game:GetService("TweenService") -- TweenService for tweening

-- Variables to reference our UI
local UI = script.Parent
local Frame = UI.Frame

-- predefined configuration options 
local LABEL_SIZE = UDim2.new(1 / 50, 0, 1 / 5, 0) -- The size of each letter
local LABEL_OFFSET = UDim2.new(0, 0, -1 / 5, 0) -- The offset the letter has from where it will end up. We spawn it slightly higher so we can animate it downwards. 
local LABEL_FLOAT_TIME_SECONDS = 1 / 10 -- The time the label will be floating into its position. 
local LABEL_TWEENINFO = TweenInfo.new(LABEL_FLOAT_TIME_SECONDS, 0, 0) -- The tweeninfo for constructing the tween later in the code. 
local CHARACTERS_PER_SECOND = 10 -- how many characters appear each second. 
	-- the range of this value is (0, 30] because of the limitations of wait() and division by 0
 
local function RenderText(Text)
	local X = 0 -- keep track of the X position of each label. 
	local Y = 0 -- keep track of the Y position of each label. 
	
	for Char in Text:gmatch(".") do -- gmatch creates and returns an iterator function for the given pattern. 
		-- the "." pattern represents every character so it will return each character per iteration. 
		local Label = Instance.new("TextLabel") -- construct new label
		
		Label.BackgroundTransparency = 1 
		Label.Text = Char 
		Label.Size = LABEL_SIZE -- set its size to our predefined size
		Label.Position = UDim2.new(X * LABEL_SIZE.X.Scale, 0, Y * LABEL_SIZE.Y.Scale, 0) + LABEL_OFFSET -- set the position to be its goal position + offset position
		Label.Parent = Frame
		
		local Tween = TweenService:Create(Label, LABEL_TWEENINFO, { -- tween it to the goal position
			Position = Label.Position - LABEL_OFFSET
		})
		
		Tween:Play()
		
		-- update the x position
		X = X + 1
		
		-- check if (x + 1) * the size is > 1. Scale is a property that usually ranges from [0, 1]. 
		-- if the next value would be > 1 that means it would stick outside of the text box. 
		-- we do this code below for text wrapping
		if ((X + 1) * LABEL_SIZE.X.Scale > 1) then
			Y = Y + 1 -- update y position if needed
			X = 0 -- reset x position
		end
		
		-- wait		
		wait(1 / CHARACTERS_PER_SECOND)
	end
end

RenderText("this is super epic just like nyan cat! i think im going to go eat some waffles now :3")

6 Likes

Can you explain the script if you dont mind, especially the numbers its all just confusing numbers that I cant wrap my head around

I’ve edited my original post to have some comments every line.

Sorry this is off topic but what’s the music called its so cool lol

Caramelldansen by Caramella Girls

1 Like

I found an issue with this approach, if you play test on the mobile emulator the characters are too close to eachother amd if you play test on a normal monitor they’re too far away from each other

mobile:
image

PC: