mirror of
https://github.com/Alvin-Zilverstand/pokedex.git
synced 2026-03-06 11:07:31 +01:00
251 lines
6.5 KiB
JavaScript
251 lines
6.5 KiB
JavaScript
let currentPokemonId = null;
|
|
|
|
document.addEventListener("DOMContentLoaded", () => {
|
|
const pokemonID = new URLSearchParams(window.location.search).get("id");
|
|
const id = parseInt(pokemonID, 10);
|
|
|
|
if (isNaN(id) || id < 1) {
|
|
console.error(`Invalid Pokémon ID: ${id}`);
|
|
return (window.location.href = "./index.html");
|
|
}
|
|
|
|
currentPokemonId = id;
|
|
loadPokemon(id);
|
|
});
|
|
|
|
async function loadPokemon(id) {
|
|
try {
|
|
console.log(`Loading data for Pokémon ID ${id}...`);
|
|
const pokemon = await fetch(`./get-pokemon.php?id=${id}`).then((res) =>
|
|
res.json()
|
|
);
|
|
|
|
if (pokemon.error) {
|
|
throw new Error(pokemon.error);
|
|
}
|
|
|
|
const abilitiesWrapper = document.querySelector(
|
|
".pokemon-detail-wrap .pokemon-detail.move"
|
|
);
|
|
abilitiesWrapper.innerHTML = "";
|
|
|
|
if (currentPokemonId === id) {
|
|
displayPokemonDetails(pokemon);
|
|
document.querySelector(".body3-fonts.pokemon-description").textContent =
|
|
pokemon.flavor_text;
|
|
|
|
const [leftArrow, rightArrow] = ["#leftArrow", "#rightArrow"].map((sel) =>
|
|
document.querySelector(sel)
|
|
);
|
|
leftArrow.removeEventListener("click", navigatePokemon);
|
|
rightArrow.removeEventListener("click", navigatePokemon);
|
|
|
|
leftArrow.addEventListener("click", () => {
|
|
navigatePokemon(id - 1);
|
|
});
|
|
rightArrow.addEventListener("click", () => {
|
|
navigatePokemon(id + 1);
|
|
});
|
|
|
|
window.history.pushState({}, "", `./detail.html?id=${id}`);
|
|
}
|
|
|
|
return true;
|
|
} catch (error) {
|
|
console.error("An error occurred while fetching Pokémon data:", error);
|
|
return (window.location.href = "./index.html");
|
|
}
|
|
}
|
|
|
|
async function navigatePokemon(id) {
|
|
currentPokemonId = id;
|
|
await loadPokemon(id);
|
|
}
|
|
|
|
const typeColors = {
|
|
normal: "#A8A878",
|
|
fire: "#F08030",
|
|
water: "#6890F0",
|
|
electric: "#F8D030",
|
|
grass: "#78C850",
|
|
ice: "#98D8D8",
|
|
fighting: "#C03028",
|
|
poison: "#A040A0",
|
|
ground: "#E0C068",
|
|
flying: "#A890F0",
|
|
psychic: "#F85888",
|
|
bug: "#A8B820",
|
|
rock: "#B8A038",
|
|
ghost: "#705898",
|
|
dragon: "#7038F8",
|
|
dark: "#705848",
|
|
steel: "#B8B8D0",
|
|
dark: "#EE99AC",
|
|
};
|
|
|
|
function setElementStyles(elements, cssProperty, value) {
|
|
elements.forEach((element) => {
|
|
element.style[cssProperty] = value;
|
|
});
|
|
}
|
|
|
|
function rgbaFromHex(hexColor) {
|
|
return [
|
|
parseInt(hexColor.slice(1, 3), 16),
|
|
parseInt(hexColor.slice(3, 5), 16),
|
|
parseInt(hexColor.slice(5, 7), 16),
|
|
].join(", ");
|
|
}
|
|
|
|
function setTypeBackgroundColor(pokemon) {
|
|
const mainType = pokemon.types[0];
|
|
const color = typeColors[mainType];
|
|
|
|
if (!color) {
|
|
console.warn(`Color not defined for type: ${mainType}`);
|
|
return;
|
|
}
|
|
|
|
const detailMainElement = document.querySelector(".detail-main");
|
|
setElementStyles([detailMainElement], "backgroundColor", color);
|
|
setElementStyles([detailMainElement], "borderColor", color);
|
|
|
|
setElementStyles(
|
|
document.querySelectorAll(".power-wrapper > p"),
|
|
"backgroundColor",
|
|
color
|
|
);
|
|
|
|
setElementStyles(
|
|
document.querySelectorAll(".stats-wrap p.stats"),
|
|
"color",
|
|
color
|
|
);
|
|
|
|
setElementStyles(
|
|
document.querySelectorAll(".stats-wrap .progress-bar"),
|
|
"color",
|
|
color
|
|
);
|
|
|
|
const rgbaColor = rgbaFromHex(color);
|
|
const styleTag = document.createElement("style");
|
|
styleTag.innerHTML = `
|
|
.stats-wrap .progress-bar::-webkit-progress-bar {
|
|
background-color: rgba(${rgbaColor}, 0.5);
|
|
}
|
|
.stats-wrap .progress-bar::-webkit-progress-value {
|
|
background-color: ${color};
|
|
}
|
|
`;
|
|
document.head.appendChild(styleTag);
|
|
}
|
|
|
|
function capitalizeFirstLetter(string) {
|
|
return string.charAt(0).toUpperCase() + string.slice(1).toLowerCase();
|
|
}
|
|
|
|
function createAndAppendElement(parent, tag, options = {}) {
|
|
const element = document.createElement(tag);
|
|
Object.keys(options).forEach((key) => {
|
|
element[key] = options[key];
|
|
});
|
|
parent.appendChild(element);
|
|
return element;
|
|
}
|
|
|
|
function displayPokemonDetails(pokemon) {
|
|
const { name, id, types, weight, height, abilities, hp, attack, defense, sp_attack, sp_defense, speed } = pokemon;
|
|
const capitalizePokemonName = capitalizeFirstLetter(name);
|
|
|
|
document.querySelector("title").textContent = capitalizePokemonName;
|
|
|
|
const detailMainElement = document.querySelector(".detail-main");
|
|
detailMainElement.classList.add(name.toLowerCase());
|
|
|
|
document.querySelector(".name-wrap .name").textContent =
|
|
capitalizePokemonName;
|
|
|
|
document.querySelector(
|
|
".pokemon-id-wrap .body2-fonts"
|
|
).textContent = `#${String(id).padStart(3, "0")}`;
|
|
|
|
const imageElement = document.querySelector(".detail-img-wrapper img");
|
|
imageElement.src = pokemon.image_url;
|
|
imageElement.alt = name;
|
|
|
|
const typeWrapper = document.querySelector(".power-wrapper");
|
|
typeWrapper.innerHTML = "";
|
|
types.forEach((type) => {
|
|
createAndAppendElement(typeWrapper, "p", {
|
|
className: `body3-fonts type ${type}`,
|
|
textContent: type,
|
|
});
|
|
});
|
|
|
|
document.querySelector(
|
|
".pokemon-detail-wrap .pokemon-detail p.body3-fonts.weight"
|
|
).textContent = `${weight / 10}kg`;
|
|
document.querySelector(
|
|
".pokemon-detail-wrap .pokemon-detail p.body3-fonts.height"
|
|
).textContent = `${height / 10}m`;
|
|
|
|
const abilitiesWrapper = document.querySelector(
|
|
".pokemon-detail-wrap .pokemon-detail.move"
|
|
);
|
|
abilities.forEach((ability) => {
|
|
createAndAppendElement(abilitiesWrapper, "p", {
|
|
className: "body3-fonts",
|
|
textContent: ability,
|
|
});
|
|
});
|
|
|
|
const statsWrapper = document.querySelector(".stats-wrapper");
|
|
statsWrapper.innerHTML = "";
|
|
|
|
const statNameMapping = {
|
|
hp: "HP",
|
|
attack: "ATK",
|
|
defense: "DEF",
|
|
sp_attack: "SATK",
|
|
sp_defense: "SDEF",
|
|
speed: "SPD",
|
|
};
|
|
|
|
const stats = { hp, attack, defense, sp_attack, sp_defense, speed };
|
|
|
|
Object.keys(stats).forEach((stat) => {
|
|
const statDiv = document.createElement("div");
|
|
statDiv.className = "stats-wrap";
|
|
statsWrapper.appendChild(statDiv);
|
|
|
|
createAndAppendElement(statDiv, "p", {
|
|
className: "body3-fonts stats",
|
|
textContent: statNameMapping[stat],
|
|
});
|
|
|
|
createAndAppendElement(statDiv, "p", {
|
|
className: "body3-fonts",
|
|
textContent: String(stats[stat]).padStart(3, "0"),
|
|
});
|
|
|
|
createAndAppendElement(statDiv, "progress", {
|
|
className: "progress-bar",
|
|
value: stats[stat],
|
|
max: 100,
|
|
});
|
|
});
|
|
|
|
setTypeBackgroundColor(pokemon);
|
|
}
|
|
|
|
function getEnglishFlavorText(pokemonSpecies) {
|
|
for (let entry of pokemonSpecies.flavor_text_entries) {
|
|
if (entry.language.name === "en") {
|
|
let flavor = entry.flavor_text.replace(/\f/g, " ");
|
|
return flavor;
|
|
}
|
|
}
|
|
return "";
|
|
}
|