The typing animation effect has become a popular way to add visual interactivity to web applications. In this blog post, we’ll explore three simple and effective ways to implement typing animations in React.
From creating a typewriter effect from scratch using React to leveraging dedicated typing animation libraries like react-typed
and react-type-animation
, you’ll learn how to implement engaging typewriter effects in your React applications. Jump ahead:
- Using the
useState
Hook andsetTimeout
function - Using the
react-typed
animation library - Using the
react-type-animation
library
You can find the complete project code in this GitHub repository. Let’s get started!
Using the useState
Hook and setTimeout
function
One of the ways to implement a typing animation in React is by utilizing React’s built-in useState
Hook and the setTimeout
function. This method allows you to have full control of the animation.
To get started, you’ll first need to create a component called Typewriter.js
inside the src
folder that will house your typing animation. Within this component, you’ll have a state variable to keep track of the current text to be displayed and an index to determine which character to append next.
You can initialize the state variables using the useState
Hook. The current text will initially be an empty string, and the current index will start at 0
:
import React, { useState, useEffect } from 'react'; const Typewriter = ({ text, delay }) => { const [currentText, setCurrentText] = useState(''); const [currentIndex, setCurrentIndex] = useState(0); // Typing logic goes here return <span>{currentText}</span>; }; export default Typewriter;
In the example above, the text
prop is used to pass the desired text content to the Typewriter
component. This is the text that will be gradually displayed as the typing animation progresses.
The delay
prop is used to specify the delay in milliseconds between each character being appended to the current text. This determines the speed of the typing animation.
Next, we need to implement the animation logic inside the component. This can be achieved by utilizing the useEffect
Hook. In this case, we’ll use the useEffect
Hook to set up a setTimeout
function that appends the next character to the current text after a certain delay:
useEffect(() => { if (currentIndex < text.length) { const timeout = setTimeout(() => { setCurrentText(prevText => prevText + text[currentIndex]); setCurrentIndex(prevIndex => prevIndex + 1); }, delay); return () => clearTimeout(timeout); } }, [currentIndex, delay, text]);
In the useEffect
Hook, we check if the currentIndex
is less than the length of the text
. If true, we set up a setTimeout
function that appends the next character from the text
prop to the currentText
state after the specified delay.
We also increment the currentIndex
to move to the next character. Additionally, we return a cleanup function that clears the timeout when the component unmounts or the dependencies change.
Now, let’s see an example of how we can use the Typewriter
component that we just created:
import Typewriter from "./Typewriter"; const App = () => { return ( <div> <h1> Welcome to <Typewriter text="My React App" delay={100} /> </h1> </div> ); }; export default App;
You should see something like this:
In this case, we only applied the typing animation to the string My React App
and set the delay to 100
milliseconds. If you want to make the typing animation faster or slower, simply increase or decrease the delay as needed.
While the GIF above shows the typing animation repeating on a loop, in reality, the animation effect will only happen once. The text will then display normally, without the typing animation.
However, in some cases, you might want the typing animation to repeat infinitely. Let’s see how to achieve this next.
Adding infinite loop functionality to our React typing animation
In addition to the basic typing animation, we can enhance the Typewriter
component by adding infinite loop functionality. This allows the animation to run infinitely, continuously displaying the text.
To achieve this, we need to add a new prop named infinite
to the Typewriter
component. This prop allows the animation to run infinitely when set to true
.
When the currentIndex
reaches the length of the text
, the component checks if infinite
is true
. If so, it resets the currentIndex
to 0
and set the currentText
equal to an empty string to start the animation from the beginning again.
Your code should look like this:
import { useState, useEffect } from 'react'; const Typewriter = ({ text, delay, infinite }) => { const [currentText, setCurrentText] = useState(''); const [currentIndex, setCurrentIndex] = useState(0); useEffect(() => { let timeout; if (currentIndex <= text.length) { timeout = setTimeout(() => { setCurrentText(prevText => prevText + text[currentIndex]); setCurrentIndex(prevIndex => prevIndex + 1); }, delay); } else if (infinite) { // ADD THIS CHECK setCurrentIndex(0); setCurrentText(''); } return () => clearTimeout(timeout); }, [currentIndex, delay, infinite, text]); return <span>{currentText}</span>; }; export default Typewriter;
Now, let’s see an example of how we can use the updated Typewriter
component with the infinite
prop in your App
component:
import Typewriter from "./Typewriter"; const App = () => { return ( <div> <h1> Welcome to <Typewriter text="My React App" delay={100} infinite /> </h1> </div> ); }; export default App;
Now that you understand how to implement a typing animation using React Hooks and the setTimeout
function, let’s explore other methods that leverage dedicated animation libraries to achieve similar effects with added functionality.
Using the react-typed
animation library
Another approach to implementing a typing animation in React is by utilizing specialized typing animation libraries. One such library is react-typed
, which provides an easy and efficient way to create typing effects with additional features and customization options.
To begin, you’ll need to install the react-typed
library in your project:
npm install react-typed
Once installed, you can import the ReactTyped
component from react-typed
and incorporate it into your React application like this:
// App.js import ReactTyped from "react-typed"; const App = () => { return ( <div> <h1> Welcome to{" "} <ReactTyped strings={["My React App"]} typeSpeed={100} loop /> </h1> </div> ); }; export default App;
In the example above, the App
component utilizes the <ReactTyped />
component from react-typed
. It accepts several props to customize the typing animation:
strings
— An array of strings that will be displayed one after the other. In this example, we have provided an array with only one string:My React App
typeSpeed
— Specifies the speed at which the characters are typed. It represents the time delay in milliseconds between each character being displayedloop
— Determines whether the animation should loop indefinitely. Setting it totrue
will repeat the animation
You should see something like this:
There are also other props we can utilize to customize the ReactTyped
component. These include:
backSpeed
— Determines the speed at which the characters are deleted when the animation loops. It represents the time delay in milliseconds between each character being removedcursorChar
— Allows you to customize the cursor character that appears during the typing animationshowCursor
— Controls whether the cursor should be visible during the typing animation. Setting it totrue
will display the cursor
Here’s an updated example that demonstrates the usage of these additional props:
import ReactTyped from "react-typed"; const App = () => { return ( <div> <h1> Welcome to{" "} <ReactTyped strings={["My React App"]} typeSpeed={100} loop backSpeed={20} cursorChar=">" showCursor={true} /> </h1> </div> ); }; export default App;
See the result below:
Now, let’s create one more example that you must have seen on lots of websites. This is the typewriter effect that showcases different roles or professions. You might have encountered it on personal portfolio websites:
To achieve this typing animation in your React project, your code should look like this:
import ReactTyped from "react-typed"; const App = () => { return ( <div> <h1> I'm a{" "} <ReactTyped strings={["Developer", "Writer", "Designer"]} typeSpeed={100} loop backSpeed={20} cursorChar=">" showCursor={true} /> </h1> </div> ); }; export default App;
In the above code, the strings
prop of the ReactTyped
component is an array of strings representing different roles. In this example, we have provided an array with the strings Developer
, Writer
, and Designer
. The typewriter effect will animate these strings one after the other, as shown in the GIF above.
By utilizing the react-typed
library, we can easily create dynamic typing animations with customizable speed, looping behavior, and multiple strings to display. This method provides a more straightforward approach compared to building the typing animation from scratch in React.
Next, let’s explore another method of implementing a typing animation in React using a different animation library called react-type-animation
.
Using the react-type-animation
library
Besides the previously mentioned react-typed
library, react-type-animation
is another great animation library for creating typing animations in React. This library offers a straightforward way to implement dynamic typewriter effects with various customization options.
To begin, you’ll need to install the react-type-animation
library in your project:
npm install react-type-animation
Once installed, you can import the TypeAnimation
component from react-type-animation
and incorporate them into your React project like this:
import { TypeAnimation } from 'react-type-animation'; const App = () => { return ( <div> <TypeAnimation sequence={[ "I'm a Developer", 1000, "I'm a Writer", 1000, "I'm a Designer", 1000, ]} speed={50} repeat={Infinity} style={{ fontSize: '2em' }} /> </div> ); }; export default App;
In the provided example, the App
component includes the TypeAnimation
component from react-type-animation
. The TypeAnimation
component accepts several props to control the typing animation:
sequence
— An array that defines the sequence of strings and delays for the typing animation. Each element in the array represents either a string to be displayed or a delay in milliseconds before proceeding to the next elementspeed
— Determines the speed at which the characters are typed. It represents the time delay in milliseconds between each character being displayedrepeat
— Controls the number of times the animation will repeat. Setting it toInfinity
will cause the animation to loop indefinitely
Note that in this example, we have a sequence of strings — I'm a Developer
, I'm a Writer
, and I'm a Designer
— with delays of 1000
milliseconds between each string.
More great articles from LogRocket:
- Don't miss a moment with The Replay, a curated newsletter from LogRocket
- Learn how LogRocket's Galileo cuts through the noise to proactively resolve issues in your app
- Use React's useEffect to optimize your application's performance
- Switch between multiple versions of Node
- Discover how to use the React children prop with TypeScript
- Explore creating a custom mouse cursor with CSS
- Advisory boards aren’t just for executives. Join LogRocket’s Content Advisory Board. You’ll help inform the type of content we create and get access to exclusive meetups, social accreditation, and swag.
By including the same initial text in every string and varying the dynamic part, we can create an effect where the static part is only typed out once.
The result should look similar to our last example using the react-typed
library.
Multi-line typing animation using react-type-animation
In addition to single-line typing animations, the react-type-animation
library supports creating multi-line typing effects. This allows you to display multiple lines of text in a sequential and animated manner.
Let’s take a look at an example of a multi-line typing animation using the react-type-animation
library:
import { TypeAnimation } from 'react-type-animation'; const App = () => { return ( <div> <TypeAnimation sequence={[ `Welcome to my website!\nI'm a Developer\nand a Designer.`, 1000, "", ]} speed={50} style={{ whiteSpace: 'pre-line', fontSize: '2em' }} repeat={Infinity} /> </div> ); }; export default App;
In the above example, the sequence
prop contains a multi-line string that represents the text to be displayed. Each line is separated by \n
— the newline character.
The initial message — Welcome to my website!
— is followed by I'm a Developer
on a new line, then and a Designer
on the subsequent line.
To ensure proper line breaks are rendered, we set the whiteSpace
CSS property to pre-line
in the style prop of the TypeAnimation
component. This allows the component to interpret newline characters and display the messages on separate lines. See the result below:
Feel free to modify the text content, typing speed, styling, and other parameters according to your specific requirements.
Conclusion
This concludes our tutorial on how to create typing animation in React. In this tutorial, we explored three different methods for implementing typing animations in React. You can check out the full code on GitHub.
By creating a typing animation from scratch using React, or leveraging dedicated animation libraries like react-typed
and react-type-animation
, we can easily add engaging typewriter effects to our React applications.
I hope this blog has provided you with a better understanding of how to implement a typing animation in your React projects. If you have any questions or feedback, feel free to leave a comment below. Happy coding!
Get set up with LogRocket's modern React error tracking in minutes:
- Visit https://logrocket.com/signup/ to get an app ID.
- Install LogRocket via NPM or script tag.
LogRocket.init()
must be called client-side, not server-side. - (Optional) Install plugins for deeper integrations with your stack:
- Redux middleware
- ngrx middleware
- Vuex plugin
$ npm i --save logrocket
// Code:
import LogRocket from 'logrocket';
LogRocket.init('app/id');
Add to your HTML:
<script src="https://cdn.lr-ingest.com/LogRocket.min.js"></script>
<script>window.LogRocket && window.LogRocket.init('app/id');</script>