I need help with a project i am working on, i want to be able to display the moves of a pokemon i type in, i can console.log an array of objects that have smaller arrays inside that i want to grab and display, how can i do so? ive tried the cluster of a method getPokemonNames which is supposed to get the names of the moves of the pokemon but this is where i couldnt think anymore.
import React, {useState} from 'react';
import PokemonName from './PokemonName';
import axios from 'axios';
function App() {
const [pokemon, setPokemon] = useState([])
const [loading, setLoading] = useState(false)
const [moves, setMoves] = useState([])
const getPokemon = async (name) =>{
setLoading(true);
const response = await axios.get(`https://pokeapi.co/api/v2/pokemon/${name}`)
const data = response.data;
setPokemon(data);
setMoves(data.moves);
setLoading(false);
console.log(data)
getPokemonNames(data.moves)
// const pokemonMovesAmount = pokemon.moves.map
}
const getPokemonNames = (data) =>{
console.log(data);
data.move.name.map((moves, key)=>(
<div key={key}>
<span>{moves.moves.name}</span>
</div>
))
}
return (
<>
<PokemonName getPokemon={getPokemon}/>
<div>
{!loading && pokemon ? (<div>
</div>): null}
<img src={pokemon.sprites?.front_default}/>
<div className="container">
{getPokemonNames}
</div>
</div>
</>
);
}
export default App;
this is the pokemon name component
import React, {useState} from 'react'
const onSubmit =(e) =>{
e.preventDefault();
}
export default function PokemonName(props) {
const [search, setSearch] = useState('');
return (
<div>
<div>
<h1>{search}</h1>
<form onSubmit={onSubmit}>
<input onChange={e => setSearch(e.target.value)} type ="text" placeholder="Search for Pokemon"></input>
<button onClick={(e) => props.getPokemon(search)}>Search</button>
</form >
</div>
</div>
)
}
EDIT, this shows a bit more about the data i get back after searching up the pokemon mew
CodePudding user response:
First step, making sure you pass the parameter data
const [moves, setMoves] = useState([])
// since you set setMoves to be data.moves second step you can iterate over data only
return (
<>
<PokemonName getPokemon={getPokemon}/>
<div>
{!loading && pokemon ? (<div>
</div>): null}
<img src={pokemon.sprites?.front_default}/>
<div className="container">
{getPokemonNames(moves)}
</div>
</div>
</>
);
Second step, tweak your getPokemon method
const getPokemonNames = (data) => {
return data.map(moveD, key)=>(
<div key={key}>
<span>{moveD.move.name}</span>
</div>
))
}
CodePudding user response:
There's an error in getPokemonNames()
- line 2:
const getPokemonNames = (data) =>{
data.move.name.map((moves, key)=>(
<div key={key}>
<span>{moves.moves.name}</span>
</div>
))
}
It should be
const getPokemonNames = (data) =>{
data.map(moveData, key)=>(
<div key={key}>
<span>{moveData.move.name}</span>
</div>
))
}
The map()
function creates a new array from esisting one. So you should have used it to iterate through your repsonse.moves
array of moves:
repsonse.moves = [
{
move: {
name: "tackle",
...
}
},
{
move: {
name: "tackle",
...
}
},
{
move: {
name: "quickattack",
...
}
},
{
move: {
name: "flamethrower",
...
}
}
]
Here's an example applied to my favourite pokemon - Magikarp.
CodePudding user response:
There is an mistake in your getPokemonNames . You are trying to do data.move.name.map which means you are mapping "move" from inside "data". You need to map "moves" array. Here is how you can do it.
const getPokemonNames = (data) =>{
data.moves.map(item, key)=>(
<div key={key}>
<span>{item.move.name}</span>
</div>
))
}