React / 6 MIN READ
Adding Animation
Getting things to move.
From the original Fervor library. Examples may use older package versions.
Adding Animations to React
Here is a step-by-step tutorial.
Step 1: Create the CSS classes
In your App.css file (or wherever your CSS resides), add the following classes:
.card {
transition: all 0.3s ease-in-out;
}
.card-wiggle-expand {
/* Add your wiggle and expand animation properties here */
transform: scale(1.1);
animation: wiggle 0.5s ease-in-out;
}
@keyframes wiggle {
0% { transform: rotate(0deg); }
10% { transform: rotate(-3deg); }
20% { transform: rotate(3deg); }
30% { transform: rotate(0deg); }
/* Repeat as needed */
}
The card class is for the initial state, while card-wiggle-expand is for the animated state.
Step 2: Create the Card component
In your components directory (or wherever you keep your components), create a new file named Card.js and add the following code:
import React, { Component } from 'react';
import './App.css';
class Card extends Component {
constructor(props) {
super(props);
this.state = {
animate: false
}
}
toggleAnimation = () => {
this.setState(prevState => ({ animate: !prevState.animate }));
}
render() {
const { animate } = this.state;
return (
<div
className={`card ${animate ? 'card-wiggle-expand' : ''}`}
onClick={this.toggleAnimation}
>
{/* Your card content goes here */}
</div>
);
}
}
export default Card;
This Card component uses the state to determine whether the card should animate. When the div is clicked, it toggles the animate state, which in turn adds or removes the card-wiggle-expand CSS class.
Step 3: Use the Card component in your application
Now you can use the Card component in your app. Here’s an example of how to do this in your App.js:
import React from 'react';
import './App.css';
import Card from './components/Card';
function App() {
return (
<div className="App">
<Card />
</div>
);
}
export default App;
Now, when you run your application, you should see the card on the screen. When you click it, it should animate by wiggling and expanding, and if you click it again, it should return to its normal state. Make sure to adjust the CSS to get the exact animation you want.
Bonus Cool Ideas
Here are a few examples of how you could add animations in a React application:
1. Animating List Items
You might want to animate list items when they’re added or removed. For this, you could use the ReactTransitionGroup and CSSTransition components from react-transition-group.
Firstly, install react-transition-group via npm:
npm install react-transition-group
Here’s an example where list items fade in and out:
import React, { useState } from 'react';
import { CSSTransition, TransitionGroup } from 'react-transition-group';
import './App.css';
function App() {
const [items, setItems] = useState(['Item 1', 'Item 2', 'Item 3']);
return (
<div className="App">
<button onClick={() => setItems([...items, `Item ${items.length + 1}`])}>
Add Item
</button>
<TransitionGroup className="todo-list">
{items.map((item, idx) => (
<CSSTransition key={item} timeout={500} classNames="fade">
<div>
{item}
<button onClick={() => setItems(items.filter((i) => i !== item))}>
Remove
</button>
</div>
</CSSTransition>
))}
</TransitionGroup>
</div>
);
}
export default App;
Add the CSS for the fade class:
.fade-enter {
opacity: 0.01;
}
.fade-enter.fade-enter-active {
opacity: 1;
transition: opacity 500ms ease-in;
}
.fade-exit {
opacity: 1;
}
.fade-exit.fade-exit-active {
opacity: 0.01;
transition: opacity 500ms ease-in;
}
2. Page Transitions
You can also animate transitions between different pages or routes in your application. Here’s an example using the react-router-dom and react-transition-group libraries:
Firstly, install react-router-dom via npm:
npm install react-router-dom
import React from 'react';
import { BrowserRouter as Router, Switch, Route, Link } from 'react-router-dom';
import { TransitionGroup, CSSTransition } from 'react-transition-group';
import './App.css';
const HomePage = () => <div>Home Page</div>;
const AboutPage = () => <div>About Page</div>;
function App() {
return (
<Router>
<div className="App">
<Link to="/">Home</Link>
<Link to="/about">About</Link>
<Route render={({ location }) => (
<TransitionGroup>
<CSSTransition key={location.key} classNames="fade" timeout={300}>
<Switch location={location}>
<Route exact path="/" component={HomePage} />
<Route path="/about" component={AboutPage} />
</Switch>
</CSSTransition>
</TransitionGroup>
)} />
</div>
</Router>
);
}
export default App;
This will animate the transition between the HomePage and AboutPage components.
3. Animating Modals
Another common use case is animating the appearance and disappearance of modals. For this, you might use the ReactModal library.
npm install react-modal
Here’s an example:
import React, { useState } from 'react';
import Modal from 'react-modal';
import './App.css';
Modal.setAppElement('#root') // This line is needed for accessibility reasons
function App() {
const [modalIsOpen, setModalIsOpen] = useState(false);
return (
<div className="App">
<button onClick={() => setModalIsOpen(true)}>Open Modal</button>
<Modal
isOpen={modalIsOpen}
onRequestClose={() => setModalIsOpen(false)}
className="Modal"
overlayClassName="Overlay"
>
<h2>Hello</h2>
<button onClick={() => setModalIsOpen(false)}>Close</button>
</Modal>
</div>
);
}
export default App;
You can then define your animations for the .Modal and .Overlay classes in your CSS.
Remember: Always consider the purpose and utility of the animation. While it can improve user experience, unnecessary or overused animation can be distracting and can negatively impact performance and accessibility.
Bonus just add striaght css
Absolutely! Libraries can help with complex animations, but you can do a lot with just CSS and React’s built-in capabilities. Let’s go through a couple of examples:
1. Animating Button Clicks
You might want to add a subtle animation to a button to make it feel more responsive when it’s clicked. You can do this with CSS and React state:
import React, { useState } from 'react';
import './App.css';
function App() {
const [isClicked, setIsClicked] = useState(false);
const handleClick = () => {
setIsClicked(true);
setTimeout(() => setIsClicked(false), 200); // Reset after 200ms
};
return (
<button className={`btn ${isClicked ? 'btn-clicked' : ''}`} onClick={handleClick}>
Click me
</button>
);
}
export default App;
You can then define your animations for the .btn and .btn-clicked classes in your CSS:
.btn {
display: inline-block;
padding: 10px 20px;
font-size: 18px;
background-color: #007BFF;
color: white;
border: none;
cursor: pointer;
transition: transform 0.2s ease;
}
.btn-clicked {
transform: scale(0.9);
}
This is with keyframe animation
.btn {
display: inline-block;
padding: 10px 20px;
font-size: 18px;
background-color: #007BFF;
color: white;
border: none;
cursor: pointer;
}
.btn-clicked {
animation: bounce 0.2s;
}
@keyframes bounce {
0% { transform: scale(1); }
50% { transform: scale(0.9); }
100% { transform: scale(1); }
}
2. Animating Page Transitions
Animating page transitions without a library involves a bit more work, but it’s doable. Here’s an example where we fade between two “pages”:
import React, { useState } from 'react';
import './App.css';
function App() {
const [page, setPage] = useState('home');
const handleClick = (newPage) => {
document.getElementById('app').className = 'page-exit'; // Start exit animation
setTimeout(() => {
setPage(newPage); // Change page after exit animation finishes
document.getElementById('app').className = 'page-enter'; // Start enter animation
}, 200); // Delay should match exit animation duration
};
return (
<div id="app" className="page-enter">
{page === 'home' ? (
<div className="home-page">
<h1>Home Page</h1>
<button onClick={() => handleClick('about')}>Go to About</button>
</div>
) : (
<div className="about-page">
<h1>About Page</h1>
<button onClick={() => handleClick('home')}>Go to Home</button>
</div>
)}
</div>
);
}
export default App;
You can then define your animations for the .page-enter and .page-exit classes in your CSS:
.page-enter, .page-exit {
transition: opacity 0.2s ease;
}
.page-enter {
opacity: 1;
}
.page-exit {
opacity: 0;
}
.home-page, .about-page {
position: absolute;
width: 100%;
padding: 20px;
}
This is with keyframe animation
.page-enter, .page-exit {
animation-fill-mode: forwards;
}
.page-enter {
animation: slideIn 0.2s;
}
.page-exit {
animation: slideOut 0.2s;
}
@keyframes slideIn {
from { transform: translateX(100%); }
to { transform: translateX(0); }
}
@keyframes slideOut {
from { transform: translateX(0); }
to { transform: translateX(-100%); }
}
.home-page, .about-page {
position: absolute;
width: 100%;
padding: 20px;
}
In this example, when you click the button to change the page, it first adds the exit animation class to the app div, waits for the exit animation to finish, then changes the page and adds the enter animation class.
Remember, these are simple examples. You can get much more complex animations using just CSS and React, but it can get complex quite quickly.