Here we will learn step by step process to make a project
Stay tuned and follow the steps.
Step1: go to folder where you want to make this project and run the command.
Step 2:
select : react as framework and js as language
Step3:
Run the commands directed
Now you will see the below web page when try to run localhost:5173
step4:
Now create a folder Components
inside components create two folder named: search and pokedex
step5
Make a file search.jsx
now i will show what to write under these files
Pokedex.jsx
import React from 'react';
import Search1 from "../Search/Searchs";
import "./Pokedex.css";
function Pokedex()
{
return(
<div className='pokedex-wrapper'>
<h1 id='pokedex-heading'>Pokedex</h1>
<Search1/>
{/* // this is the name that you import from the file*/}
</div>
)
}
export default Pokedex;
pokedex.css
.pokedex-wrapper
{
display: flex;
flex-direction : column;
}
#pokedex-heading
{
margin: 0 auto;
letter-spacing: 5px;
}
search.css
.search-wrapper {
margin: 0 auto;
}
#pokemon-name-search {
margin: 2rem;
width: 600px;
padding: 1.5rem;
}
search.jsx
import './Search.css'
function Search() {
return (
<div className='search-wrapper'>
< input id="pokemon-name-search" type="text"
placeholder="pokemon name...." />
</div>
);
}
export default Search;
app.jsx
import './App.css'
import Pokedex from './Components/Pokedex/Pokedex'
function App(){
return (
<>
<Pokedex/>
</>
)
}
export default App
I m attaching how your folders look like
step 6:
How to download lists of pokemon
Goto pokeapi
PokemonList.jsx
import { useState } from "react";
import { useEffect } from "react"
function PokemonList()
{
const [x , setx] = useState(0);
const [y , sety] = useState(0);
useEffect(()=>
{
console.log("effect ")
} ,[x]);
return(
<>
<div>
x : {x} <button onClick={() => setx(x+1)}> Inc </button>
</div>
<div>
y : {y} <button onClick={() => sety(y+1)}> Inc </button>
</div>
</>
)
}
export default PokemonList
Pokedex.jsx
import React from 'react';
import Search1 from "../Search/Searchs";
import "./Pokedex.css";
import PokemonList from '../PokemonList/PokemonList';
function Pokedex()
{
return(
<div className='pokedex-wrapper'>
<h1 id='pokedex-heading'>Pokedex</h1>
<Search1/>
{/* // this is the name that you import from the file*/}
<PokemonList/>
</div>
)
}
export default Pokedex;
Step7:
Now for downloading data we can either use fetch api or axios :
In this case we will use axios.
npm install axios
now the files will be:
PokemonList.jsx
import { useEffect } from "react"
import axios from 'axios'
import './PokemonList.css'
function PokemonList() {
async function downloadPokemons() {
const response = await axios.get('https://pokeapi.co/api/v2/pokemon')
console.log(response.data)
}
useEffect(() => {
downloadPokemons();
}, []);
return (
<div className="pokemon-list-wrapper">
Pokemon list
</div>
)
}
export default PokemonList
pokemonList.css
.pokemon-list-wrapper
{
margin: 0 auto;
}
Step 8:
fetching details of pokemon and setting url
i have provided the code please go through it and try to understand it through searching by yourself it will help you
I m linking the updated code now:
PokemonList.css
.pokemon-list-wrapper
{
margin: 2rem auto;
display: flex;
flex-direction: column;
align-items: center;
}
.pokemon-wrapper
{
display: flex;
flex-direction: row;
flex-wrap: wrap;
justify-content: space-evenly;
}
.pokemon-name-list-colour
{
color: rgb(59, 17, 197);
font-size: x-large;
font-family: 'Lucida Sans', 'Lucida Sans Regular', 'Lucida Grande', 'Lucida Sans Unicode', Geneva, Verdana, sans-serif;
}
.button-control
{
margin-left: 1rem;
padding: 1rem 0.5rem;
color: aqua;
}
PokemonList.jsx
import { useEffect } from "react"
import axios from 'axios'
import './PokemonList.css'
import { useState } from "react"
import Pokemon from "../Pokemon/Pokemon";
function PokemonList() {
const [pokemonList, setPokemonList] = useState([]);
const [isLoading, setisloading] = useState(true);
// const PokedexUrl = 'https://pokeapi.co/api/v2/pokemon'
const [PokedexUrl, setPokedexUrl] = useState
('https://pokeapi.co/api/v2/pokemon')
const [nextUrl , setNextUrl] =useState('');
const [prevUrl , setPrevUrl] =useState('');
async function downloadPokemons() {
//as soon as download pokemons is called setisloading should be true
setisloading(true)
const response = await axios.get(PokedexUrl) //this will download
//list of 20 pokemons
const pokemonResults = response.data.results;// we get the
// array of pokemons from results
console.log(response.data)
setNextUrl(response.data.next);
setPrevUrl(response.data.previous);
// iterating over the array of pokemons and using their url
// to create an arry of promises that will download these pokemons
const pokemonResultPromise = pokemonResults.map((pokemon) =>
axios.get(pokemon.url));
// passing promise array to axios.all
const pokemonData = await axios.all(pokemonResultPromise);
console.log(pokemonData)// the pokemonData has all the
//detailed information of all the 20 pokemons
// saving data in pokemon list and iterating over data of
// each pokemon and extracting id name image types
const res = pokemonData.map((pokeData) => {
const pokemon = pokeData.data;
return {
id : pokemon.id,
name: pokemon.name,
image: (pokemon.sprites.other) ?
pokemon.sprites.other.dream_world.front_default : pokemon.sprites.front_shiny,
types: pokemon.types
}
});
console.log(res)
setPokemonList(res)
setisloading(false);
}
useEffect(() => {
downloadPokemons();
}, [PokedexUrl]);
return (
<>
<div className="pokemon-list-wrapper">
<div className="pokemon-name-list-colour"> Pokemon list : </div>
<div className="pokemon-wrapper">
{(isLoading) ? 'laoding' : pokemonList.map((p) =>
<Pokemon name = {p.name} image ={p.image} key={p.id} />)
}
</div>
<div className="button-control">
<button disabled={prevUrl ==null} onClick={()=>
setPokedexUrl(prevUrl)}>prev</button>
<button disabled={nextUrl ==null} onClick={()=>
setPokedexUrl(nextUrl)}>next</button>
</div>
</div>
</>
)
}
export default PokemonList
Pokemon.css
.pokemon
{
flex-basis: 30%;
height: 250px;
width: 280px;
align-items: center;
display: flex;
flex-direction: column;
}
.pokemon-name
{
font-size:large;
font-weight: 100;
font-family:'Times New Roman', Times, serif;
color: rgb(255, 0, 30);
}
.pokemon-image
{
margin: 1rem;
height: 180px;
max-height: 80%;
}
.pokemon:hover
{
background-color: rgb(180, 197, 197);
}
/* * {background-color: black} */
Pokemon.jsx
import './Pokemon.css'
function Pokemon({ name, image }) {
return (
<>
<div className='pokemon'>
<div className='pokemon-name'>{name}</div>
<div><img className="pokemon-image" src={image}/></div>
</div>
</>
)
}
export default Pokemon
Pokedex.css
.pokedex-wrapper
{
display: flex;
flex-direction : column;
}
#pokedex-heading
{
margin: 0 auto;
letter-spacing: 5px;
color: rgb(24, 222, 37);
}
Pokedex.jsx
import React from 'react';
import Search from "../Search/Searchs";
import "./Pokedex.css";
import PokemonList from '../PokemonList/PokemonList';
function Pokedex()
{
return(
<div className='pokedex-wrapper'>
<h1 id='pokedex-heading'>Pokedex</h1>
<Search/>
<PokemonList/>
</div>
)
}
export default Pokedex;
search.css
.search-wrapper {
margin: 0 auto;
}
#pokemon-name-search {
margin: 2rem;
width: 600px;
padding: 1.5rem;
}
Search.jsx
import './Search.css'
function Search() {
return (
<div className='search-wrapper'>
< input id="pokemon-name-search" type="text"
placeholder="pokemon name...." />
</div>
);
}
export default Search;
Step 9:
In this we will try to extract information of the pokemon we clicked
run this command inside your folder : npm i react -router -dom
make a folder in src named routes
pokedex.css
.pokedex-wrapper
{
display: flex;
flex-direction : column;
}
Pokedex.jsx
import React from 'react';
import Search from "../Search/Searchs";
import "./Pokedex.css";
import PokemonList from '../PokemonList/PokemonList';
function Pokedex()
{
return(
<div className='pokedex-wrapper'>
<Search/>
<PokemonList/>
</div>
)
}
export default Pokedex;
Pkemon.css
.pokemon
{
flex-basis: 30%;
height: 250px;
width: 280px;
align-items: center;
display: flex;
flex-direction: column;
}
.pokemon-name
{
font-size:large;
font-weight: 100;
font-family:'Times New Roman', Times, serif;
color: rgb(255, 0, 30);
}
.pokemon-image
{
margin: 1rem;
height: 180px;
max-height: 80%;
}
.pokemon:hover
{
background-color: rgb(180, 197, 197);
}
/* * {background-color: black} */
Pokemon.jsx
import './Pokemon.css'
import { Link } from 'react-router-dom'
function Pokemon({ name, image , id }) {
return (
<>
<div className='pokemon'>
<Link to={`/pokemon/${id}`}>
<div className='pokemon-name'>{name}</div>
<div><img className='pokemon-image' src={image}/></div>
</Link>
</div>
</>
)
}
export default Pokemon
Pokemondetails.css
.pokemon-name
{
font-size: larger;
color: rgba(15, 157, 57, 0.962);
text-align: center;
font-family: Cambria, Cochin, Georgia, Times, 'Times New Roman', serif;
font-weight: bolder;
}
.pokemon-types {
border: 3px solid black;
padding: 0.3rem;
display: flex;
flex-direction: column;
gap: 0.2rem;
background-color: antiquewhite;
align-items: center;
justify-content: center;
text-align: center;
margin: 1rem; /* Adds space outside the box */
}
.wid-height {
color: crimson;
display: flex;
flex-direction: column;
align-items: center; /* Centers items horizontally */
justify-content: center; /* Centers items vertically */
height: 100%; /* Ensure it takes full height of parent if needed */
}
PokemonDetails.jsx
import axios from "axios";
import { useState, useEffect } from "react";
import { useParams } from "react-router-dom";
import './PokemonDetails.css'
function PokemonDetails() {
const { id } = useParams();
const [pokemon, setPokemon] = useState({
name: '',
image: '',
weight: 0,
height: 0,
types: []
});
async function downloadPokemon() {
try {
const response = await axios.get(`https://pokeapi.co/api/v2/pokemon/${id}`);
setPokemon({
name: response.data.name,
image: response.data.sprites.other.dream_world.front_default,
weight: response.data.weight,
height: response.data.height,
types: response.data.types.map((t) => t.type.name)
});
} catch (error) {
console.error('Error fetching Pokémon data:', error);
}
}
useEffect(() => {
downloadPokemon();
}, [id]);
return (
<div className="pokemon-details-wrapper">
<div className="pokemon-name">Name: {pokemon.name}</div>
<img className="pokemon-image" src={pokemon.image} alt={pokemon.name} />
< div className="wid-height">
<div >Height: {pokemon.height}</div>
<div >Weight: {pokemon.weight}</div>
</div>
<div className="pokemon-types">
{pokemon.types.length > 0 ? (
pokemon.types.map((t) => <div key={t}>{t}</div>)
) : (
<div>Loading types...</div>
)}
</div>
</div>
);
}
export default PokemonDetails;
PokemonList.css
.pokemon-list-wrapper
{
margin: 2rem auto;
display: flex;
flex-direction: column;
align-items: center;
}
.pokemon-wrapper
{
display: flex;
flex-direction: row;
flex-wrap: wrap;
justify-content: space-evenly;
}
.pokemon-name-list-colour
{
color: rgb(59, 17, 197);
font-size: x-large;
font-family: 'Lucida Sans', 'Lucida Sans Regular', 'Lucida Grande', 'Lucida Sans Unicode', Geneva, Verdana, sans-serif;
}
.button-control
{
margin-left: 1rem;
padding: 1rem 0.5rem;
color: aqua;
}
Pokemonlist.jsx
import { useEffect } from "react"
import axios from 'axios'
import './PokemonList.css'
import { useState } from "react"
import Pokemon from "../Pokemon/Pokemon";
function PokemonList() {
const [pokemonList, setPokemonList] = useState([]);
const [isLoading, setisloading] = useState(true);
// const PokedexUrl = 'https://pokeapi.co/api/v2/pokemon'
const [PokedexUrl, setPokedexUrl] = useState ('https://pokeapi.co/api/v2/pokemon')
const [nextUrl , setNextUrl] =useState('');
const [prevUrl , setPrevUrl] =useState('');
async function downloadPokemons() {
//as soon as download pokemons is calling setisloading should be true
setisloading(true)
const response = await axios.get(PokedexUrl) //this will download list of 20 pokemons
const pokemonResults = response.data.results;// we get the array of pokemons from results
console.log(response.data)
setNextUrl(response.data.next);
setPrevUrl(response.data.previous);
// iterating over the array of pokemons and using their url to create an arry of promises that will download these pokemons
const pokemonResultPromise = pokemonResults.map((pokemon) => axios.get(pokemon.url));
// passing promise array to axios.all
const pokemonData = await axios.all(pokemonResultPromise);
console.log(pokemonData)// the pokemonData has all the detailed information of all the 20 pokemons
// saving data in pokemon list and iterating over data of each pokemon and extracting id name image types
const res = pokemonData.map((pokeData) => {
const pokemon = pokeData.data;
return {
id : pokemon.id,
name: pokemon.name,
image: (pokemon.sprites.other) ? pokemon.sprites.other.dream_world.front_default : pokemon.sprites.front_shiny,
types: pokemon.types
}
});
console.log(res)
setPokemonList(res)
setisloading(false);
}
useEffect(() => {
downloadPokemons();
}, [PokedexUrl]);
return (
<>
<div className="pokemon-list-wrapper">
<div className="pokemon-name-list-colour"> Pokemon list : </div>
<div className="pokemon-wrapper">
{(isLoading) ? 'laoding' : pokemonList.map((p) => <Pokemon name = {p.name} image ={p.image} key={p.id} id ={p.id}/>)
}
</div>
<div className="button-control">
<button disabled={prevUrl ==null} onClick={()=> setPokedexUrl(prevUrl)}>prev</button>
<button disabled={nextUrl ==null} onClick={()=> setPokedexUrl(nextUrl)}>next</button>
</div>
</div>
</>
)
}
export default PokemonList
Search.css
.search-wrapper {
margin: 0 auto;
}
#pokemon-name-search {
margin: 2rem;
width: 600px;
padding: 1.5rem;
}
Search.jsx
import './Search.css'
function Search() {
return (
<div className='search-wrapper'>
< input id="pokemon-name-search" type="text"
placeholder="pokemon name...." />
</div>
);
}
export default Search;
CustomRoutes.jsx
import {Route, Routes} from "react-router-dom"
import PokemonDetails from "../Components/PokemonDetails/PokemonDetails"
import Pokedex from "../Components/Pokedex/Pokedex"
function CustomRoutes()
{
return(
<Routes>
{/* // giving a route component inside route */}
{/* Keep in remember whenever we are giving any component it should be wrapped inside the </> */}
<Route path = "/" element ={<Pokedex/>}/>
<Route path ="/pokemon/:id" element ={<PokemonDetails/>}/>
</Routes>
)
}
export default CustomRoutes
App.jsx
import './App.css'
import Pokedex from './Components/Pokedex/Pokedex'
import CustomRoutes from './routes/CustomRoutes'
import { Link } from 'react-router-dom'
function App(){
return (
<div className='outer'>
<h1 id='pokedex-heading'>
<Link to ="/">Pokedex</Link></h1>
<CustomRoutes/>
</div>
)
}
export default App
main.jsx
import React from 'react'
import ReactDOM from 'react-dom/client'
import App from './App.jsx'
import './index.css'
import {BrowserRouter} from 'react-router-dom'
ReactDOM.createRoot(document.getElementById('root')).render(
<BrowserRouter>
<App />
</BrowserRouter>
)
this is how your folder should look like
Tip: Please try to run and try different things in this code