From afd02a91edc9e8df03b422e66f3229ce3fea721e Mon Sep 17 00:00:00 2001 From: Syco21 Date: Fri, 15 May 2026 22:03:13 +0200 Subject: [PATCH] Add artwork switcher: arrow buttons cycle through multiple card artworks --- src/context/CardContext.jsx | 33 +++++++++++++---------------- src/pages/HomePage.jsx | 42 +++++++++++++++++++++++++++++-------- src/services/api.js | 7 +++++-- 3 files changed, 52 insertions(+), 30 deletions(-) diff --git a/src/context/CardContext.jsx b/src/context/CardContext.jsx index b483d35..405c3c1 100644 --- a/src/context/CardContext.jsx +++ b/src/context/CardContext.jsx @@ -3,38 +3,33 @@ import React, { createContext, useState } from 'react'; export const CardContext = createContext(); export function CardProvider({ children }) { - // ownedAmounts structure: - // { [card_id]: { "[set_id]-[rarity_id]": amount, ... }, ... } const [ownedAmounts, setOwnedAmounts] = useState({}); const [expandedCardId, setExpandedCardId] = useState(null); + // cardImages[cardId] is an array of base64 strings, one per artwork index const [cardImages, setCardImages] = useState({}); const updateAmount = (card_id, key, amount) => { setOwnedAmounts(prev => ({ ...prev, - [card_id]: { - ...prev[card_id], - [key]: amount - } + [card_id]: { ...prev[card_id], [key]: amount } })); }; - const setCardImage = (card_id, blob) => { - setCardImages(prev => ({ ...prev, [card_id]: blob })); + const setCardImage = (card_id, index, blob) => { + setCardImages(prev => { + const existing = prev[card_id] ? [...prev[card_id]] : []; + existing[index] = blob; + return { ...prev, [card_id]: existing }; + }); }; return ( - + {children} ); -} \ No newline at end of file +} diff --git a/src/pages/HomePage.jsx b/src/pages/HomePage.jsx index 9758606..bc3a721 100644 --- a/src/pages/HomePage.jsx +++ b/src/pages/HomePage.jsx @@ -32,6 +32,7 @@ function HomePage() { const [sortBy, setSortBy] = useState('name'); const { expandedCardId, setExpandedCardId, cardImages, setCardImage, ownedAmounts } = useContext(CardContext); + const [artworkIndex, setArtworkIndex] = useState(0); const debouncedSearch = useDebounce(searchTerm, 250); const loadCards = useCallback(() => fetchCards().then(setCards), []); @@ -40,12 +41,16 @@ function HomePage() { loadCards().catch(err => setError(err.message)).finally(() => setLoading(false)); }, [loadCards]); + useEffect(() => { setArtworkIndex(0); }, [expandedCardId]); + useEffect(() => { - if (!expandedCardId || cardImages[expandedCardId]) return; - fetchCardImage(expandedCardId) - .then(image => setCardImage(expandedCardId, image)) + if (!expandedCardId || !expandedCard) return; + const imageId = expandedCard.image_ids?.[artworkIndex]; + if (!imageId || cardImages[expandedCardId]?.[artworkIndex]) return; + fetchCardImage(expandedCardId, imageId) + .then(image => setCardImage(expandedCardId, artworkIndex, image)) .catch(err => console.error('Failed to load card image', err)); - }, [expandedCardId, cardImages, setCardImage]); + }, [expandedCardId, artworkIndex, expandedCard, cardImages, setCardImage]); const getTotal = useCallback((card) => card.printings?.reduce((sum, p) => { @@ -127,11 +132,30 @@ function HomePage() {
{expandedCard ? ( <> - {cardImages[expandedCardId] ? ( - {expandedCard.name} - ) : ( -
Loading image…
- )} +
+ {cardImages[expandedCardId]?.[artworkIndex] ? ( + {expandedCard.name} + ) : ( +
Loading image…
+ )} + {(expandedCard.image_ids?.length ?? 0) > 1 && ( +
+ + + {artworkIndex + 1} / {expandedCard.image_ids.length} + + +
+ )} +
{expandedCard.name}
diff --git a/src/services/api.js b/src/services/api.js index cc4d87e..a5cce7c 100644 --- a/src/services/api.js +++ b/src/services/api.js @@ -7,8 +7,11 @@ export async function fetchCards() { return await response.json(); } -export async function fetchCardImage(cardId) { - const response = await fetch(`${API_BASE}/cardImage/${cardId}`); +export async function fetchCardImage(cardId, imageId) { + const url = imageId + ? `${API_BASE}/cardImage/${cardId}?imageId=${imageId}` + : `${API_BASE}/cardImage/${cardId}`; + const response = await fetch(url); if (!response.ok) throw new Error('Failed to fetch card image'); const data = await response.json(); return data.image;