Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion src/App.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,9 @@ export default function App() {

<main>
<div className="shows-grid">
{/* TODO - shows.map((show)=>{ return <ShowCard id={show.id} .../> })*/}
{shows.map((show) => {
return <ShowCard key={show.id} {...show} />;
})}
</div>
</main>
</div>
Expand Down
89 changes: 53 additions & 36 deletions src/components/showCard/ShowCard.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { useState } from "react";
import { useEffect, useState } from "react";

export interface ShowCardProps {
artist: string;
Expand All @@ -8,65 +8,82 @@ export interface ShowCardProps {
ticketsLeft: number;
image: string;
}
const BUTTON_INTERESTED_STATUS = {
ADDED: "Add to interested",
REMOVE: "Remove from interested",
};

export default function ShowCard(
/* TODO 1: Accept props with ShowCardProps type here */
) {
// TODO 2: Create state called isInterested of type boolean (default false)
// const [isInterested, setIsInterested] = ...
const INTERESTED_STATUS = {
ADDED: "This show is in your interested list 🎟️",
NOT_ADDED: "You haven't added this show yet",
};

// TODO 3: Function that toggles true/false in isInterested
// function handleToggleInterested() {}
const TICKETS_STATUS = {
SOLD_OUT: "SOLD OUT",
LAST_TICKETS: "Last tickets hurry up!",
AVAILABLE: "Tickets available",
};

// TODO 4: Create ticketsStatusText (string):
// 0 → "SOLD OUT"
// 1–30 → "Last tickets – hurry up!"
// >30 → "Tickets available"
export default function ShowCard({
artist,
stage,
day,
hour,
ticketsLeft,
image,
}: ShowCardProps) {
const [isInterested, setIsInterested] = useState(false);
const [ticketsStatusText, setTicketsStatusText] = useState("");

// TODO 5: Create text for interest status based on isInterested:
// false → "You haven't added this show yet"
// true → "This show is in your interested list 🎟️"
useEffect(() => {
const handleTicketsStatusText = (ticketsLeft: number) => {
if (ticketsLeft === 0) {
setTicketsStatusText(TICKETS_STATUS.SOLD_OUT);
return;
}
if (ticketsLeft > 0 && ticketsLeft <= 30) {
setTicketsStatusText(TICKETS_STATUS.LAST_TICKETS);
return;
}

setTicketsStatusText(TICKETS_STATUS.AVAILABLE);
};
handleTicketsStatusText(ticketsLeft);
}, []);

const handleToggleInterested = () => {
setIsInterested(!isInterested);
};

return (
<article className="show-card">
<div className="show-image-wrapper">
{/* TODO 6: Replace placeholder with real <img> from props */}
{/* <img src={image} alt={artist} className="show-image" /> */}
<img src={image} alt={artist} className="show-image" />

<div className="show-image-placeholder">Image goes here</div>
</div>

<header className="show-header">
<h2 className="show-artist">
{/* TODO 7: If isInterested → show ⭐ before artist name */}
"Artist name here"
{isInterested ? "⭐ " : ""} {artist}
</h2>
<p className="show-meta">
{/* TODO 8: Display stage, day, hour from props */}
"Stage · Day · Hour"
{stage}· {day} ·{hour}
</p>
</header>

<section className="show-info">
<p className="tickets-status">
{/* TODO 9: Display the ticketsStatusText */}
"Tickets status text"
</p>
<p className="tickets-status">{ticketsStatusText}</p>

<p className="interested-status">
{/* TODO 10: Display the interestedText */}
"Interested status text"
{isInterested ? INTERESTED_STATUS.ADDED : INTERESTED_STATUS.NOT_ADDED}
</p>
</section>

<button
className="interested-button"
// TODO 11: Connect onClick to handleToggleInterested function
>
{/* TODO 12: Button text:
false → "Mark as interested"
true → "Remove from my list"
*/}
"Button text"
<button className="interested-button" onClick={handleToggleInterested}>
{isInterested
? BUTTON_INTERESTED_STATUS.REMOVE
: BUTTON_INTERESTED_STATUS.ADDED}
</button>
</article>
);
Expand Down