diff --git a/src/App.css b/src/App.css
index ac96f2e..1ec2601 100644
--- a/src/App.css
+++ b/src/App.css
@@ -134,15 +134,19 @@ a:active {
color: #cc77ff;
}
-.App-option {
+.Game-options {
display: flex;
align-items: center;
justify-content: center;
margin-bottom: 1rem;
}
-.App-option input {
- margin-left: 0.5rem;
+.Game-options > * + * {
+ margin-inline-start: 0.5rem;
+}
+
+.Game-options button {
+ min-width: 4rem;
}
.App-footer {
diff --git a/src/App.tsx b/src/App.tsx
index 1f2193c..932bdc7 100644
--- a/src/App.tsx
+++ b/src/App.tsx
@@ -5,54 +5,17 @@ import Game from "./Game";
import { names } from "./names";
import { useState } from "react";
-const targets = common
- .slice(0, 20000) // adjust for max target freakiness
- .filter((word) => dictionarySet.has(word) && !names.has(word));
-
-function randomTarget(wordLength: number) {
- const eligible = targets.filter((word) => word.length === wordLength);
- return pick(eligible);
-}
-
function App() {
- const [wordLength, setWordLength] = useState(5);
- const [target, setTarget] = useState(randomTarget(wordLength));
- if (target.length !== wordLength) {
- throw new Error("length mismatch");
- }
return (
<>
hello wordl
-
-
- {
- const length = Number(e.target.value);
- setTarget(randomTarget(length));
- setWordLength(length);
- }}
- >
-
- {
- setTarget(randomTarget(wordLength));
- }}
- />
+
>
);
diff --git a/src/Game.tsx b/src/Game.tsx
index 4b95dce..023ecf3 100644
--- a/src/Game.tsx
+++ b/src/Game.tsx
@@ -3,6 +3,9 @@ import { Row, RowState } from "./Row";
import dictionary from "./dictionary.json";
import { Clue, clue } from "./clue";
import { Keyboard } from "./Keyboard";
+import common from "./common.json";
+import { dictionarySet, pick } from "./util";
+import { names } from "./names";
enum GameState {
Playing,
@@ -11,34 +14,50 @@ enum GameState {
}
interface GameProps {
- target: string;
- wordLength: number;
maxGuesses: number;
- restart: () => void;
+}
+
+const targets = common
+ .slice(0, 20000) // adjust for max target freakiness
+ .filter((word) => dictionarySet.has(word) && !names.has(word));
+
+function randomTarget(wordLength: number) {
+ const eligible = targets.filter((word) => word.length === wordLength);
+ return pick(eligible);
}
function Game(props: GameProps) {
const [gameState, setGameState] = useState(GameState.Playing);
const [guesses, setGuesses] = useState([]);
const [currentGuess, setCurrentGuess] = useState("");
- const [hint, setHint] = useState(`${props.wordLength} letters`);
+ const [wordLength, setWordLength] = useState(5);
+ const [hint, setHint] = useState(`Make your first guess!`);
+ const [target, setTarget] = useState(randomTarget(wordLength));
+
+ const reset = () => {
+ setTarget(randomTarget(wordLength));
+ setGuesses([]);
+ setCurrentGuess("");
+ setHint("");
+ setGameState(GameState.Playing);
+ };
const onKey = (key: string) => {
if (gameState !== GameState.Playing) {
if (key === "Enter") {
- props.restart();
+ reset();
}
return;
}
if (guesses.length === props.maxGuesses) return;
if (/^[a-z]$/.test(key)) {
- setCurrentGuess((guess) => (guess + key).slice(0, props.wordLength));
+ setCurrentGuess((guess) => (guess + key).slice(0, wordLength));
setHint("");
} else if (key === "Backspace") {
setCurrentGuess((guess) => guess.slice(0, -1));
setHint("");
} else if (key === "Enter") {
- if (currentGuess.length !== props.wordLength) {
+ if (currentGuess.length !== wordLength) {
setHint("Too short");
return;
}
@@ -48,12 +67,12 @@ function Game(props: GameProps) {
}
setGuesses((guesses) => guesses.concat([currentGuess]));
setCurrentGuess((guess) => "");
- if (currentGuess === props.target) {
+ if (currentGuess === target) {
setHint("You won! (Enter to play again)");
setGameState(GameState.Won);
} else if (guesses.length + 1 === props.maxGuesses) {
setHint(
- `You lost! The answer was ${props.target.toUpperCase()}. (Enter to play again)`
+ `You lost! The answer was ${target.toUpperCase()}. (Enter to play again)`
);
setGameState(GameState.Lost);
} else {
@@ -79,7 +98,7 @@ function Game(props: GameProps) {
.fill(undefined)
.map((_, i) => {
const guess = [...guesses, currentGuess][i] ?? "";
- const cluedLetters = clue(guess, props.target);
+ const cluedLetters = clue(guess, target);
const lockedIn = i < guesses.length;
if (lockedIn) {
for (const { clue, letter } of cluedLetters) {
@@ -93,7 +112,7 @@ function Game(props: GameProps) {
return (
@@ -102,6 +121,36 @@ function Game(props: GameProps) {
return (
+
+
+ 0 || currentGuess !== ""}
+ value={wordLength}
+ onChange={(e) => {
+ const length = Number(e.target.value);
+ setTarget(randomTarget(length));
+ setWordLength(length);
+ setHint(`${length} letters`);
+ }}
+ >
+
+
{rowDivs}
{hint || `\u00a0`}