Updated Mastermind.

This commit is contained in:
Jacob Signorovitch
2024-11-19 20:56:51 -05:00
parent 0f8c20aa73
commit f05d56e566

View File

@@ -1,10 +1,8 @@
package mastermind;
import java.awt.Color;
import java.awt.Image;
import java.util.Random;
import javalib.funworld.*;
import javalib.worldcanvas.*;
import javalib.worldimages.*;
import tester.Tester;
@@ -343,7 +341,7 @@ class Game extends World {
DEFAULTCONF,
DEFAULTCONF.options.gen(DEFAULTCONF.len),
DEFAULTCONF.nguesses,
new MtGuess(),
ConsPlaceholderGuess.mkN(DEFAULTCONF.nguesses),
false,
false
);
@@ -360,6 +358,34 @@ class Game extends World {
return this.bigBang(this.calcW(), this.calcH());
}
public Game onKeyEvent(String key) {
if ("123456789".contains(key)) { // User has entered a number.
int choice = Integer.valueOf(key);
return this.addDot(choice - 1);
//} else if (key.equals("backspace")) {
//return this.dropDot();
}
return this;
}
// Attempt to add the nth dot option to the incomplete guess.
Game addDot(int choice) {
return new Game(
this.conf,
this.solution,
this.guessesLeft,
this.guesses.addToIncomplete(
this.conf.options.get(choice),
this.conf.len
),
this.won,
this.done
);
}
// Attempt to remove the last dot from the incomplete guess.
//Game dropDot() {}
// Calculate the width of the window without drawing anything.
int calcW() {
return (
@@ -372,7 +398,10 @@ class Game extends World {
// Calculate the height of the window without drawing anything.
int calcH() {
return ((this.conf.nguesses + 2) * Dot.r * 2); // Width of all the guess rows, plus the two rows above and below (for solution and options respectively.)
return (
((this.conf.nguesses + 2) * Dot.r * 2) +
((this.conf.nguesses) * Util.gapW)
);
}
// Draw the current game state.
@@ -413,29 +442,6 @@ class Game extends World {
WorldImage draw_options() {
return this.conf.options.draw();
}
// Convenience methods for testing -- not part of program.
Game win() {
return new Game(
this.conf,
this.solution,
this.guessesLeft,
this.guesses,
true,
true
);
}
Game addGuess(Guess guess) {
return new Game(
this.conf,
this.solution,
this.guessesLeft,
new ConsGuess(guess, this.guesses),
this.won,
this.done
);
}
}
// A game configuration.
@@ -471,6 +477,7 @@ class GameConf {
// A list of guesses.
interface ILoGuess {
WorldImage draw();
ILoGuess addToIncomplete(Dot dot, int limit);
}
class ConsGuess implements ILoGuess {
@@ -486,6 +493,59 @@ class ConsGuess implements ILoGuess {
public WorldImage draw() {
return Util.pairGapAbove(guess.draw(), this.nxt.draw());
}
public ILoGuess addToIncomplete(Dot dot, int limit) {
return this.nxt.addToIncomplete(dot, limit);
}
}
class ConsIncompleteGuess implements ILoGuess {
IncompleteGuess guessSoFar;
ILoGuess nxt;
ConsIncompleteGuess(IncompleteGuess guessSoFar, ILoGuess nxt) {
this.guessSoFar = guessSoFar;
this.nxt = nxt;
}
public WorldImage draw() {
return Util.pairGapAbove(guessSoFar.draw(), this.nxt.draw());
}
public ILoGuess addToIncomplete(Dot dot, int limit) {
return new ConsIncompleteGuess(
this.guessSoFar.tryAppend(dot, limit),
this.nxt
);
}
}
// Placeholder for guesses yet to be guessed.
class ConsPlaceholderGuess implements ILoGuess {
ILoGuess nxt;
ConsPlaceholderGuess(ILoGuess nxt) {
this.nxt = nxt;
}
public WorldImage draw() {
return Util.pairGapAbove(
new RectangleImage(1, 2 * Dot.r, OutlineMode.SOLID, Color.BLACK),
this.nxt.draw()
);
}
// Fill a list with n placeholders.
static ILoGuess mkN(int n) {
if (n == 0) return new MtGuess();
return new ConsPlaceholderGuess(mkN(n - 1));
}
public ILoGuess addToIncomplete(Dot dot, int limit) {
return this.nxt.addToIncomplete(dot, limit);
}
}
class MtGuess implements ILoGuess {
@@ -493,6 +553,10 @@ class MtGuess implements ILoGuess {
public WorldImage draw() {
return new EmptyImage();
}
public ILoGuess addToIncomplete(Dot dot, int limit) {
return this;
}
}
// A guess.
@@ -523,6 +587,14 @@ class IncompleteGuess {
WorldImage draw() {
return guessSoFar.draw();
}
// Append the dot, unless length exceeds limit.
IncompleteGuess tryAppend(Dot dot, int limit) {
if (this.guessSoFar.len() + 1 <= limit) return new IncompleteGuess(
this.guessSoFar.append(dot)
);
else return this;
}
}
// Feedback for a guess.
@@ -582,6 +654,8 @@ interface ILoDot {
WorldImage draw(); // Draw the dots.
int getW(); // Get the total width, in pixels, of the list.
ILoDot append(Dot dot);
}
class ConsDot implements ILoDot {
@@ -600,6 +674,10 @@ class ConsDot implements ILoDot {
this(dot, nxt, new Random());
}
public ILoDot append(Dot dot) {
return new ConsDot(this.dot, this.nxt.append(dot), this.rand);
}
public ILoDot gen(int n) {
return n <= 0
? new MtDot()
@@ -703,6 +781,10 @@ class ConsDot implements ILoDot {
class MtDot implements ILoDot {
public ILoDot append(Dot dot) {
return new ConsDot(dot, this);
}
public ILoDot gen(int n) {
return new MtDot();
}