diff --git a/react-client/src/components/GameRoom/GameHeader/GameHeader.tsx b/react-client/src/components/GameRoom/GameHeader/GameHeader.tsx index 2dc2f3a..e6321a3 100644 --- a/react-client/src/components/GameRoom/GameHeader/GameHeader.tsx +++ b/react-client/src/components/GameRoom/GameHeader/GameHeader.tsx @@ -22,7 +22,7 @@ function GameHeader({ room, players, fireOff, placing, guessFireOff }: { room: R return ( <>
-
+
logo
-
+

Round

{fireOff ? @@ -45,7 +45,7 @@ function GameHeader({ room, players, fireOff, placing, guessFireOff }: { room: R }}>{room.round + 1}/{room.answers.length} :

{room.round + 1}/{room.answers.length}

}
-

ID: {id}

+

ID: {id}

@@ -63,64 +63,65 @@ function GameHeader({ room, players, fireOff, placing, guessFireOff }: { room: R
-
-
- {players && players.filter((p) => p.uid !== uid).map((player) => ( - { - setSelectedId(player.uid) - setSelectedPlayer(player) - }} - className="first:ml-[.625rem] last:mr-[.625rem]" - > - {selectedId !== player.uid && - +
+ {players && players.filter((p) => p.uid !== uid).map((player) => ( + { + setSelectedId(player.uid) + setSelectedPlayer(player) + }} + className="first:ml-[.625rem] last:mr-[.625rem]" + > + {selectedId !== player.uid && + - {placing[0]?.points > 0 && placing[0]?.uid === player?.uid && ( - - - - )} -

+ {placing[0]?.points > 0 && placing[0]?.uid === player?.uid && ( + + + + )} +

0 && placing[0]?.uid === player?.uid ? - `${guessFireOff.includes(player.uid) ? "text-success scale-[150%] " : "scale-100 text-yellow-300"}` : - `${guessFireOff.includes(player.uid) ? "text-success scale-[150%] " : "scale-100 text-gray-200"} `}`} - > - {player.name}: {player.points} -

-
} -
- ))} + `${guessFireOff.includes(player.uid) ? "text-success scale-[150%] " : "scale-100 text-yellow-300"}` : + `${guessFireOff.includes(player.uid) ? "text-success scale-[150%] " : "scale-100 text-gray-200"} `}`} + > + {player.name}: {player.points} + + } + + ))} +
- -
+ }
- ) } diff --git a/react-client/src/components/GameRoom/Grid/Cell.tsx b/react-client/src/components/GameRoom/Grid/Cell.tsx index 7eecb21..744e9b9 100644 --- a/react-client/src/components/GameRoom/Grid/Cell.tsx +++ b/react-client/src/components/GameRoom/Grid/Cell.tsx @@ -17,9 +17,12 @@ function Cell({ keypress, status = 'empty' }: { keypress?: string; status?: "emp animate={{ scale: 1, opacity: 1, }} exit={{ scale: 0, opacity: 0, }} transition={{ - type: "tween", - duration: 0.15, - ease: "easeInOut", + scale: { + type: "spring", + stiffness: 300, + damping: 30 + }, + duration: 0.05, }}> {keypress?.toLocaleUpperCase()} diff --git a/react-client/src/components/GameRoom/Keyboard/Key.tsx b/react-client/src/components/GameRoom/Keyboard/Key.tsx index 6f5fca4..46df7a0 100644 --- a/react-client/src/components/GameRoom/Keyboard/Key.tsx +++ b/react-client/src/components/GameRoom/Keyboard/Key.tsx @@ -1,5 +1,5 @@ import { m } from "framer-motion"; -import { memo, useCallback, useContext } from "react"; +import { memo, useCallback } from "react"; import { useWindowSize } from "react-use"; import { useKeyboard, useGuesses } from "../../../context/GameContext"; import { CharStatus } from "../Grid/utils/getStatuses"; diff --git a/react-client/src/components/GameRoom/Keyboard/Keyboard.tsx b/react-client/src/components/GameRoom/Keyboard/Keyboard.tsx index e0d93bf..8fac093 100644 --- a/react-client/src/components/GameRoom/Keyboard/Keyboard.tsx +++ b/react-client/src/components/GameRoom/Keyboard/Keyboard.tsx @@ -1,15 +1,48 @@ +import { doc, getFirestore, updateDoc } from "firebase/firestore"; import { m } from "framer-motion"; -import { memo, useCallback, useEffect, useState } from "react"; +import { memo, useCallback, useEffect, useMemo, useState } from "react"; +import { AiFillDelete } from "react-icons/ai"; +import { useParams } from "react-router-dom"; +import { toast } from "react-toastify"; +import { useUid } from "../../../context/AuthContext"; import { useGuesses, useKeyboard } from "../../../context/GameContext"; +import { app } from "../../../utils/firebase"; import { CharStatus } from "../Grid/utils/getStatuses"; import Key from "./Key"; -function Keyboard({ answer, handleEnter, hasGuessed }: { answer: string, handleEnter: any, hasGuessed: boolean }) { +function Keyboard({ room }: { room: Room }) { + const firestore = useMemo(() => getFirestore(app), []) + const [hasGuessed, setHasGuessed] = useState(false) const [statuses, setStatuses] = useState<{ [key: string]: CharStatus }>({}) - const { guesses } = useGuesses() + const { guesses, setGuesses } = useGuesses() const { key, setKey } = useKeyboard() + const answer = room.answers[room.round].toUpperCase() + const { id } = useParams() + const uid = useUid() + const handleEnter = useCallback(async () => { + if (key.length !== 5) return + const playerRef = doc(firestore, "rooms", `${id}`, "players", uid) + setHasGuessed(true) + const res = await fetch(import.meta.env.DEV ? `http://localhost:4000/api/valid?word=${key}` : `https://neo-letter-fastify.vercel.app/api/valid?word=${key}`) + const data = await res.json() + if (!data.isValid && !room.customWords) { + toast.error("Invalid Guess.", { theme: "dark" }) + setHasGuessed(false) + return + } + setKey("") + await new Promise(resolve => setTimeout(resolve, 150)) + setGuesses([...guesses, key]) + await updateDoc(playerRef, { + guesses: [...guesses, key], guessed: true, + }) + await new Promise(resolve => setTimeout(resolve, 450)) + await updateDoc(playerRef, { guessed: false, guessedCorrectly: false }) + setHasGuessed(false) + }, [key, guesses]) + useEffect(() => { handlekeyboardStatuses() }, [guesses]) @@ -59,8 +92,11 @@ function Keyboard({ answer, handleEnter, hasGuessed }: { answer: string, handleE status={statuses[key]} /> ))} + -
+
getFirestore(app), []) const [roomStatus, setRoomStatus] = useState(); - const [room, setRoom] = useState({} as Room); + const [room, setRoom] = useState({ + id: "", + answers: [], + maxPlayers: 0, + players: [], + usernames: [], + roomType: "public", + started: false, + allowLateJoiners: false, + allowMessages: false, + round: 0, + customWords: false, + allowProfanity: false + }); const [fireOff, setFireOff] = useState(false) const [players, setPlayers] = useState([]) - const [answers, setAnswers] = useState([]) - const [round, setRound] = useState(0) - const [placing, setPlacing] = useState([]) const [guessFireOff, setGuessFireOff] = useState([]) - const [hasGuessed, setHasGuessed] = useState(false) const [resetWinner, setResetWinner] = useState(false) const [roundGuessedReset, setRoundGuessedReset] = useState(false) - const { showMessages, setShowMessages, allowMessages, setAllowMessages, setMessages } = useMessages() - const { key, setKey } = useKeyboard() - const { guesses, setGuesses } = useGuesses() - const { height, width } = useWindowSize() + const { setShowMessages, setAllowMessages, setMessages } = useMessages() + const { setKey } = useKeyboard() + const { setGuesses } = useGuesses() + const { width } = useWindowSize() const { id } = useParams() const uid = useUid() const roomRef = useMemo(() => doc(firestore, "rooms", `${id}`), [id]) - const playerRef = useMemo(() => doc(firestore, "rooms", `${id}`, "players", uid), [id, uid]) - const winner = useMemo(() => players.filter(p => p.guesses.includes(answers[round]?.toUpperCase()))[0], [players, answers, round]) + const winner = useMemo(() => players.filter(p => p.guesses.includes(room.answers[room.round]?.toUpperCase()))[0], [players, room]) const currentPlayer = useMemo(() => players.find(p => p.uid === uid) as GamePlayer, [players]) - - + const placing = useMemo(() => players.filter((p) => p.points > 0).length > 0 ? players.sort((a, b) => b.points! - a.points!) : [], [players]) const handleOtherPlayersGuess = useCallback((players: GamePlayer[]) => { setGuessFireOff(players.filter(player => player.guessed).map(player => player.uid)) }, []) - const handleGuess = useCallback(async () => { - if (key.length !== 5) return - setHasGuessed(true) - const res = await fetch(import.meta.env.DEV ? `http://localhost:4000/api/valid?word=${key}` : `https://neo-letter-fastify.vercel.app/api/valid?word=${key}`) - const data = await res.json() - if (!data.isValid && !room.customWords) { - toast.error("Invalid Guess.", { theme: "dark" }) - setHasGuessed(false) - return - } - setKey("") - await new Promise(resolve => setTimeout(resolve, 150)) - setGuesses([...guesses, key]) - await updateDoc(playerRef, { - guesses: [...guesses, key], guessed: true, - }) - await new Promise(resolve => setTimeout(resolve, 450)) - await updateDoc(playerRef, { guessed: false, guessedCorrectly: false }) - setHasGuessed(false) - }, [key, guesses]) + + const handleEveryoneGuessed = useCallback(async (players: GamePlayer[]) => { if (players.length === 0) return if (!players.every(player => player.guesses.length === 6)) return @@ -94,7 +83,7 @@ export default function GameRoom() { points: winner.uid === p.uid ? increment(100 - (p.guesses.length - 1) * 10) : increment(0), }))); await Promise.all([...playerStack, updateDoc(roomRef, { - round: round < answers.length ? increment(1) : increment(0), + round: room.round < room.answers.length ? increment(1) : increment(0), })]); } setFireOff(true); @@ -103,7 +92,7 @@ export default function GameRoom() { setGuesses([]); setKey(""); setResetWinner(false); - }, [answers, players]) + }, [room.answers, players]) const handleRoomStatus = useCallback(async () => { if (players.length > room.maxPlayers) { setRoomStatus("room_full") @@ -113,7 +102,7 @@ export default function GameRoom() { setRoomStatus("user_not_found") return } - if (round >= answers.length && answers.length > 0) { + if (room.round >= room.answers.length && room.answers.length > 0) { setRoomStatus("room_finished") if (!currentPlayer.signedIn) return const lastRoom = (await getDoc(doc(firestore, "users", currentPlayer.uid))).data()?.lastRoom @@ -135,16 +124,13 @@ export default function GameRoom() { updateDoc(roomRef, { started: true }) return } - }, [room, players, round, answers, currentPlayer]) + }, [room, players, currentPlayer]) useEffect(() => { const unsub1 = onSnapshot(collection(firestore, "rooms", `${id}`, "players"), async (playersRes) => { const players = playersRes.docs.map((doc) => { return { ...doc.data() } }) as GamePlayer[] - handleEveryoneGuessed(players) handleOtherPlayersGuess(players) - setPlayers(players) - setPlacing(players.filter((p) => p.points > 0).length > 0 ? players.sort((a, b) => b.points! - a.points!) : []) setGuesses(players.find(p => p.uid === uid)?.guesses as string[]) }) const unsub2 = onSnapshot(roomRef, (roomRes) => { @@ -152,9 +138,6 @@ export default function GameRoom() { if (!room) { setRoomStatus("room_not_found"); return } setAllowMessages(room.allowMessages) setRoom(room as Room) - setAnswers(room.answers) - setRound(room.round) - }) return () => { unsub1() @@ -175,10 +158,10 @@ export default function GameRoom() { }, [roundGuessedReset]) useEffect(() => { handleRoomWin(players) - }, [answers, players]) + }, [room.answers, players]) useEffect(() => { handleRoomStatus() - }, [room, players, round, answers, currentPlayer]) + }, [room, players, currentPlayer]) return ( @@ -209,12 +192,12 @@ export default function GameRoom() { delay: winner ? 4.8 : .5, }} > - +
- handleGuess()} hasGuessed={hasGuessed} answer={`${answers[round]}`.toUpperCase()} /> +
diff --git a/react-client/src/pages/Home.tsx b/react-client/src/pages/Home.tsx index 281a2a4..b173c16 100644 --- a/react-client/src/pages/Home.tsx +++ b/react-client/src/pages/Home.tsx @@ -31,9 +31,6 @@ function Home() { } }, []); - - - useEffect(() => { if (JSON.parse(preference as string)?.showReminder) remindToSignUp(); }, [user]);