In this web development tutorial you will learn how to build web application that can select a random NAME from a list of names using the React JavaScript Framework.
Before you get started with this tutorial, if you are not familiar with the React Framework, then check out my FREE React Crash Course for beginners.
What will you learn in this Tutorial ? In this tutorial you will learn:
- How to install react
- how to use React useState Hook
- how to create and import React Components
- how to use React props
- how to install React Styled Components
- how to use keyframes in react using styled components
- how to create animations
- how to disable a html button in react
- how to use setTimout() in react to handle errors
Source Code for this tutorial
After you have installed your react application please copy and replace the css code for this project.
You can leave the index.css file as it is.
App.css
* {
margin: 0;
padding: 0;
list-style-type: none;
text-decoration: none;
}
.App {
text-align: center;
}
.App-logo {
pointer-events: none;
}
@media (prefers-reduced-motion: no-preference) {
.App-logo {
animation: App-logo-spin infinite 20s linear;
}
}
.App-header {
display: grid;
grid-template-columns: 1fr 2fr 1fr;
text-align: center;
background-color: #37383c;
min-height: 100vh;
align-items: center;
justify-content: center;
font-size: calc(10px + 2vmin);
color: white;
}
a h1 {
font-size: calc(30px + 5vmin);
}
.App-link {
color: #61dafb;
}
@keyframes App-logo-spin {
from {
transform: rotate(0deg);
}
to {
transform: rotate(360deg);
}
}
button {
cursor: pointer;
background-color: #00d8ff;
color: #333;
font-weight: 600;
border: none;
padding: 0.3rem 0.5rem;
border-radius: 5px;
box-shadow: 0px 0px 6px 2px #000;
transition: all 0.2s ease;
}
button:hover {
background-color: #7ceafd;
box-shadow: 0px 0px 1px 1px #000;
}
button:disabled {
background-color: lightgray;
}
.list-item {
border-bottom: 1px solid #00d8ff;
padding-bottom: 0.1rem;
margin: 0.5rem;
margin-top: 0rem;
}
.winners .list-item {
background-color: #ffffff;
border-radius: 3px;
color: #00d8ff;
border-bottom: 1px solid #00d8ff;
padding-bottom: 0.1rem;
margin-bottom: 0.3rem;
animation: listItem 0.3s ease-out;
}
@keyframes listItem {
from {
opacity: 0;
transform: translateX(100px);
}
to {
opacity: 1;
transform: translateX(0);
}
}
#progress {
position: relative;
height: 10px;
/* width: 110%; */
width: 100%;
border: 10px solid #00d8ff;
border-radius: 15px;
}
#progress .color {
position: absolute;
background-color: #ffffff;
width: 0px;
height: 10px;
border-radius: 15px;
animation: progress 3s linear;
}
@keyframes progress {
0% {
width: 0%;
}
25% {
width: 50%;
background-color: #e7f6f9;
}
50% {
width: 75%;
background-color: #bff4fd;
}
75% {
width: 85%;
background-color: #ffe600;
}
85% {
width: 95%;
background-color: #ff6f00;
}
100% {
width: 100%;
background-color: #ff2600;
}
}
The main App file.
I will concentrate the entire project on the main App. js file and try not to overcomplicate things.
The first step would be to create your folder and file structure. In this case I clary know what to expect from my project, meaning that my structure is also clear.
create a components folder in there create the userList.js
file ProgressBar.jsx
and Spinner.jsx
file. I will come back to them later on.
Also import useState from "react"
, this will help you asing state to user names and winners.
App.js
import logo from "./logo.svg";
import "./App.css";
import { userNames } from "./components/userList";
import { useState } from "react";
// Components
import ProgressBar from "./components/ProgressBar";
import Spinner from "./components/Spinner";
function App() {
// States
const [users, setUsers] = useState(userNames);
const [winners, setWinner] = useState([]);
const [uiProps, setUiProps] = useState({
buttonDisabled: false,
displayProgressBarr: false,
});
const [error, setError] = useState({
processTime: 3000,
loading: false,
});
// Utility functions
let randomName;
function getRandomName() {
return (randomName = users[Math.floor(Math.random() * userNames.length)]);
}
// Handlers
const handleGetRandomName = () => {
setUiProps({
buttonDisabled: true,
displayProgressBarr: true,
});
setTimeout(() => {
getRandomName();
console.log(randomName);
if (typeof randomName === "undefined") {
// handle error
setError({ processTime: 1000, loading: true });
handleGetRandomName();
} else {
// Add random name to winner list
setWinner([...winners, randomName]);
// Update and Remove the random name form users
const updateNameList = users.filter((user) => user !== randomName);
setUsers(updateNameList);
setUiProps({
buttonDisabled: false,
displayProgressBarr: false,
});
setError({
processTime: 3000,
loading: false,
});
}
}, error.processTime);
// console.log(getRandomName());
};
return (
<div className="App">
<header className="App-header">
<ul id="userList">
{users.map((user, index) => (
<li className="list-item" key={index}>
{user}
</li>
))}
</ul>
<div className="react-container">
{uiProps.displayProgressBarr && <ProgressBar />}
{error.loading ? (
<Spinner />
) : (
<img src={logo} className="App-logo" alt="logo" />
)}
<h1>30</h1>
<button
onClick={handleGetRandomName}
disabled={uiProps.buttonDisabled}
>
Get random name
</button>
</div>
<ul className="winners">
{winners.map((winner, index) => (
<li key={index} className="list-item">
{winner}
</li>
))}
</ul>
</header>
</div>
);
}
export default App;
UserList componets
The userList.js
is a simple javascript file that exports the variable useName withc is a array of strings. You need to import this file in to your main App.js
file
userList.js
export const userNames = [
"Name-1",
"Name-2",
"Name-3",
"Name-4",
"Name-5",
"Name-6",
"Name-7",
"Name-8",
];
Progress bar component
The progresB
ar component will return a simple div containing another div. I do acknowledge that this could be treated much more elegantly using styled components but I chose regular css.
The code for the animation you will find in the css file
ProgressBar.jsx
import React from "react";
export default function ProgressBar() {
return (
<div id="progress">
<div className="color"></div>
</div>
);
}
Create a animated spinner in react
In order to create the spinner component, you simply create a new spinner.jsx file
import React from "react";
import styled, { keyframes } from "styled-components";
const spin = keyframes`
0%{transform:rotate(0turn)}
100%{transform:rotate(1turn)}
`;
export const SpinnerStyle = styled.img`
margin: 2rem 0;
animation: ${spin} 1s infinite;
`;
export default function Spinner() {
return (
<SpinnerStyle src="https://www.joshwcomeau.com/images/keyframe-animations/loader.svg"></SpinnerStyle>
);
}
Video Tutorial on YouTube
For a more in depth explanation and video tutorial, please visito th
Want to become a web developer ?
Get complete web development courses on HTML, CSS , JavaScript, Bootstrap, Visual Studio Code, Responsive design and much more…