First Pass
This time ChatGPT decided to put all the code in a single file, I guess because all the code is shorter. But just in the interest of keeping things orderly, "professional" and compartmentalized, I decided to separate them into the regular HTML, CSS and JavaScript files. All I have to do is cut and paste in a new file and add the tag <link rel="stylesheet" href="style.css"> in the head of the file and <script src="script.js"></script> at the end of the <body>.
Since this example was considerably shorter than the last I think I'll be a bit more experimental on this project and let the imagination run a little wild, instead of limiting myself to mostly analysis and just a bit of harmless playing around like I did on the previous one.
First of all, I decided that it hurts my eyes to look at such an ugly UI so I'll add some styles of my own. Nothing too fancy, just less ugly. I gave it a dark background and light font color, orange background-color for the buttons and the dark background for the input as well so it looks like it has no background. One other trick that's not 100% beginner CSS is I increased the root font size like this:
:root {
font-size: 22px;
}
That way you don't have to increase the font-size of each tag separately, all the paragraph, headings and other text tags increase proportionately because 1rem is now by default 22 pixels. Only the font inside the input still appeared super small for some reason, but I just needed to give the input a rule of font-size: 1rem;. Not super necessary in this case, but if I wanted to be more specific, I can write input[type=number], but I would probably want any kind of 'input' to have the same rule anyway, so I won't.
That's it for the default styling. But I have three ideas that I want to try out:
- Make the color for the number of guesses change depending on how many are left, like:
- 8, 9, 10 : green;
- 4, 5, 6, 7 : yellow;
- 1, 2, 3 : orange;
- 0 : red
- Give the "message" a red color if you lost, a green color if you won.
- List the numbers you have already guessed.
1. Adding color indicator to attemptsLeft
I was able to do this in three steps:
- I added this
switchstatement inside theguessBtn.addEventListenerblock:
switch (attempts) {
case 10:
attemptsLeft.style.color = "green";
break;
case 9:
attemptsLeft.style.color = "green";
break;
case 8:
attemptsLeft.style.color = "green";
break;
case 7:
attemptsLeft.style.color = "yellow";
break;
case 6:
attemptsLeft.style.color = "yellow";
break;
case 5:
attemptsLeft.style.color = "yellow";
break;
case 4:
attemptsLeft.style.color = "yellow";
break;
case 3:
attemptsLeft.style.color = "orange";
break;
case 2:
attemptsLeft.style.color = "orange";
break;
case 1:
attemptsLeft.style.color = "orange";
break;
case 0:
attemptsLeft.style.color = "red";
break;
}
- I added this line to the
resetBtn.addEventListenerblock:
attemptsLeft.style.color = "green";
So that the number goes back to green after restarting the game.
- Added a rule to the CSS that says:
#attemptsLeft {
color: green;
}
Otherwise the number appears the default text color at the start.
2. Adding color indicator to message
Here's what I'm thinking: create two separate classes in the CSS, one with red color, one with green. Then when the message shows up, add the corresponding class.
.victory {
color: green;
}
.loss {
color: red;
}
Then add the class depending on win or loss. Inside the eventListener callback funtion, after the line that says:
message.textContent = `Correct! The number was ${secretNumber}.`;
add this line:
message.classList.add("victory");
Then, under the one that says:
message.textContent = `Game over! The number was ${secretNumber}`;
add this one:
message.classList.add("loss");
But I was forgetting, you also need to remove the classes upon game reset, otherwise the message keeps showing up with the colored text, even when displaying the remaining attempts. In the reset button's eventListener callback function, add:
message.classList.remove("victory");
message.classList.remove("loss");
And that's it.
3. Add the list of numbers guessed
First I added this <p> tag bellow the remaining attempts:
<p id="guess-list">Numbers guessed: </p>`
and in the CSS I'm adding a rule so it starts hidden and I'll make it display only after the first guess:
#guess-list {
display: none;
}
Next, onto the JavaScript file.
- First thing's first, add a constant for the guess list paragraph:
const guessList = document.getElementById('guess-list');
- I'll create a function that will run in the
guessBtn.addEvenListenerblock. And depending on whether its the first guess, one in the middle, or last, I want it to:
- display the paragraph and add just the number guessed;
- add ", " + the number guessed;
- add ", " + number guessed + "."
- and then return a string to add to the paragraph's content.
This is the function:
function numListAdd(attemptsNum, newGuess) {
let string = "";
if (attemptsNum == 9) {
string += `${newGuess}`;
} else if (attemptsNum == 0) {
string += `, ${newGuess}.`;
} else {
string += `, ${newGuess}`;
}
return string;
}
⮚⮚⮚ Don't confuse parameters with arguments!
Parameters are the placeholder variables that you use in the function's definition, arguments are the actual varriables you use the function with. In many cases you define a function with only one set of variables in mind to use as arguments, and thus it seems easy to just use same names as parameters in the definition, but if you end up trying to reuse that function for something else, it can get confusing; this is a personal preference, of course, but that's why I always try to name the parameters something different.
Anyway, then I need to call the function in the 'Guess' button's eventListener, after updating attemps and the line with attemptsLeft.textContent = attempts; and also make the list paragraph visible, like this:
guessList.style.display = 'block';
guessList.textContent += numListAdd(attempts, guess);
And lastly, just like before, don't forget to delete it when the game restarts, add this to the resetButton function:
guessList.textContent = "Numbers guessed: ";
guessList.style.display = "none";
Sometimes you have to think like a translator. When a function runs, what does each part mean at a certain moment? Suppose I have already guessed 3 times, the previously guessed numbers are "56, 34, 2". So when the function runs with a new guess of '20' the complete statement could be "translated" to something like this:
"Numbers guessed: 56, 34, 2" += ", 20";
Or, breaking it down a little further:
guessList currently has the value "Numbers guessed: 56, 34, 2". Then, the function runs; the first and second conditions evaluate to false, so the third condition runs and returns the string ", 20". So the statement appends the returned string to guessList; the result is: "Numbers guessed: 56, 34, 2, 20", which gets printed in the <p id="guess-list"> tag.