How To Add Spaces In Hangman Javascript
JS | Hangman
Learning Goals
Afterward this lesson, you volition exist able to:
Introduction
In this learning unit, we are going to create the classic game Hangman. In this game, nosotros have to figure out which is the secret word before the man gets hanged. With each error, the human being will exist closer to die!
As we accept learned, nosotros can't confront the whole game without splitting it upward in different steps to brand the solution. We volition divide it up in three dissimilar parts: structure, logic, and game layout.
Structure
To do the game, we volition need iv dissimilar data structures to play the game. This structures are the following:
- Words. An array with some words. We volition accept a random word from this array, and information technology will be the give-and-take that the thespian will have to figure out.
- Secret word. This will be an string to store the word selected randomly.
- Letters. Some other array, in this example just for messages. This ane volition store all the letters used past the player, to show them all. It will be very helpful for the histrion, to avoid select the same letter of the alphabet twice.
- Errors left. Number of errors that the user can brand until the end of the game.
All these variables will be defined in the constructor of the game, as it follows:
role Hangman ( ) { this . words = [ "IRONHACK" , "NODEJS" , "JAVASCRIPT" , "METEOR" , "ANGULAR" ] ; this . secretWord = "" ; this . alphabetic character = [ ] ; this . errorsLeft = 10 ; }
Those are all the information structures nosotros need to play the game. The side by side step is to create the game logic with all the methods we need.
Game logic
Get random give-and-take
The first affair nosotros need to play the game is the word that the thespian will have to discern. We need to choose a random word and assign it to the secretWord
variable we alleged in the constructor.
Hangman . prototype . _getWord = function ( ) { var random = Math . floor ( Math . random ( ) * this . words . length ) ; return this . words [ random ] ; } ;
We will execute this part in the constructor of the game, and assign it to the right variable:
function Hangman ( ) { this . words = [ "IRONHACK" , "NODEJS" , "JAVASCRIPT" , "Falling star" , "ANGULAR" ] ; this . secretWord = "" ; this . messages = [ ] ; this . errorsLeft = 10 ; this . secretWord = this . _getWord ( ) ; }
All right, we have the word, now the actor should be able to betoken a letter to play.
Insert a letter
The user should be able to indicate a letter that he thinks that the word contains. We have to create a function, that nosotros will call askLetter
that will receive as a parameter the user'southward selection. In one case we receive the alphabetic character, nosotros have to add it to the letters
array, update the errors left (if the letter is non in the word), and nosotros have to cheque out if the letter of the alphabet had been inserted before:
Hangman . image . askLetter = role ( letter ) { letter = letter . toUpperCase ( ) ; if ( this . letters . indexOf ( letter ) > - ane ) { render ; } this . letters . push ( letter of the alphabet ) ; var right = this . secretWord . indexOf ( letter of the alphabet ) > - i ; if ( ! right ) { this . errorsLeft -= 1 ; } render right ; } ;
We employ upper-case letter letters to compare the player's selection with the secret word. Utilize upper-case letter (or lower) case letter to compare strings is a good practice.
Testify the current word
The following method we need will be used to show the current status of the word. In other words, how many messages accept to figure out the player. This method volition exist chosen getWordStatus
, and information technology will be equally it follows:
Hangman.paradigm.getWordStatus = function () { var that = this; var wordStatus = []; var splitedWord = this.secretWord.split up(""); splitedWord.forEach(function (letter of the alphabet) { if (that.letters.indexOf(letter of the alphabet) > -i) { wordStatus.push(letter); } else { wordStatus.push("_"); } }); return wordStatus; };
We iterate over all the letters of the surreptitious discussion. If a letter of the alphabet hasn't been selected by the role player, it will be represented every bit an underscore. By doing this, we will get a result similiar to: "IRON_ACK".
Game status
To terminate upward the game logic, we will need to create a method to get its status. We will have three different status:
- Completed.
- Game over.
- Ongoing game.
We will create three dissimilar functions:
Hangman . image . _isFinished = function ( ) { return this . getWordStatus ( ) . indexOf ( "_" ) < 0 ; } ;
If the current word doesn't have any underscore, the give-and-take will be completed. Then this office will help u.s.a. to determine if the player has won the game. We as well demand a function to figure out if the game is over:
Hangman . prototype . _gameOver = function ( ) { return this . errorsLeft === 0 ; } ;
With the variable we defined in the constructor it'due south very easy to know if the game is over or non. Note that both functions are individual, so nosotros take to create a public method to bank check out those possible condition:
Hangman . paradigm . gameStatus = office ( ) { if ( this . _isFinished ( ) ) { return "You Win" ; } else if ( this . _gameOver ( ) ) { render "Game Over" ; } } ;
This role volition return three possible values: "You lot Win", if the player has won, "Game Over" if the thespian has lost, and finally, undefined if the game has to go on.
We already accept all what we demand to play our game. The next step is to create the layout and put them all together.
Game Layout
HTML & CSS
Start of all, we are going to create the layout with HTML and CSS. Subsequently that, we will create the JavaScript that will join the game logic with its layout. Permit'southward do a list of all the things we need to practice the layout:
- New game. We will add a push button to start a new game. It will be always available to let the user restart a game if the give-and-take is as well complicated.
- Hangman. We need, of course, to draw the man to let the player know how much life left he has.
- Word. We need some kind of container to show the user the electric current condition of the word.
- Letters. We also need another container to let the user know which alphabetic character have been already inserted.
- Win/Lose. Last, merely non to the lowest degree, we need some kind of container to let the user know if he has won or non.
New game
First of all nosotros volition create the new push button game. It will be in the meridian office of the page. We volition add customized styles, without using any kind of library similar Bootstrap. The HTML, CSS, and result of this push is the following:
HTML
<button id="new-game"> New game </push button>
CSS
# new-game { background : #43a3e6; edge : ipx solid #43a3e6; edge-radius : sixpx ; box-shadow : 1px ipx 2px #999; color : #fff; padding : 6px 14px ; outline : 0; }
Layout
Note that the font is not the default browser's font. Nosotros take imported the 'Open Sans' font from Google Fonts. You lot can find several font types in this directory :)
Hangman
We will draw the hangman with HTML and CSS. A lot of people is usually afraid of doing something similar to that in HTML and CSS. Permit's evidence that information technology's easier than it seems:
HTML
<div id="hangman"> <div form="right-bar"></div> <div form="top-bar"></div> <div grade="left-bar"></div> <div course="base of operations"></div> <div form="caput"></div> <div course="body"></div> <div class="left-arm"></div> <div class="right-arm"></div> <div grade="left-leg"></div> <div class="correct-leg"></div> <div class="clearfix"></div> </div>
You can meet how nosotros have created a <div>
for each part of the hangman. Each of these parts stand for a life, so we volition accept to notice a good way to show them all, depending on the status of the game. Let's have a look at the CSS and the layout:
# hangman div { background : #000; } # hangman .base of operations { elevation : 2px ; width : 300px ; } # hangman .left-bar { pinnacle : 400px ; width : iipx ; } # hangman .top-bar { superlative : 2px ; width : 200px ; } # hangman .right-bar { bladder : left; height : 30px ; margin-left : 200px ; width : 2px ; } # hangman .caput { background : none; border-radius : 100% ; bladder : left; margin-left : 175px ; margin-superlative : -375px ; height : 50px ; width : fiftypx ; } # hangman .trunk { bladder : left; height : 140px ; margin-top : -321px ; margin-left : 200px ; width : twopx ; } # hangman .left-arm , # hangman .correct-arm , # hangman .left-leg , # hangman .right-leg { float : left; top : ninetypx ; margin-summit : -321px ; margin-left : 173px ; transform : rotate(35deg ); width : 2px ; } # hangman .right-arm , # hangman .right-leg { margin-left : 230px ; margin-peak : -324px ; transform : rotate(140deg ); } # hangman .left-leg , # hangman .right-leg { margin-top : -192px ; }
Equally y'all can see, nosotros are using the div background color to draw information technology. To show the arms and legs, we are rotating the containers, and we play a lot with the margins to classify all the pieces on their correct position. The result will is the following:
Layout
As we said, we will have to show each part depending on how many lifes does the player have. We will solve that by doing setting upward the default groundwork color as white. We will also create classes for each life, and depending on how many lifes he has, we are going to change the background color and gear up it up to black:
# hangman div { background : #fff; } /* ... */ # hangman.lifes-ten .base of operations { groundwork : #000; } # hangman.lifes-9 .left-bar { background : #000; } # hangman.lifes-eight .height-bar { groundwork : #000; } # hangman.lifes-7 .correct-bar { groundwork : #000; } # hangman.lifes-6 .caput { border : 2px solid #000; } # hangman.lifes-5 .body { background : #000; } # hangman.lifes-4 .left-arm { background : #000; } # hangman.lifes-3 .right-arm { groundwork : #000; } # hangman.lifes-two .left-leg { background : #000; } # hangman.lifes-1 .correct-leg { background : #000; }
The only form that is non changing tha background color is the .head
form, that volition alter the border-colour, because nosotros are using a borde-radius to make it round. Nosotros will have to add the classes to the #hangman
container through JavaScript during the game. We will see this later.
Word container
The following pace is to add the container where we will identify the discussion that has to be discerned. We take to call up in the usability of this container: nosotros have to separate the letters between them to let the player know how many letters etch the word:
HTML
<div id="currentWord"> <span>I</bridge> <bridge>R</span> <span>O</span> <span>N</span> <bridge>H</bridge> <span>A</bridge> <span>C</span> <bridge>One thousand</bridge> </div>
We will use an <span>
for each letter in the word. The CSS for this section is the following:
CSS
# currentWord span { brandish : inline-block; margin : 0 xpx ; }
The container by itself doesn't have an specific style, but we add some spacing betwixt <span>
through margin holding.
Layout
The resulting layout is the following:
Letters container
We also demand another container to indicate which letters have already been used. It will exist very similar to the current word container, just the font color volition be unlike to distingish between the word and the letters.
HTML
<div id="letters"> </div>
CSS
# messages { colour : #999; letter-spacing : 5px ; margin : 20px auto 0; text-marshal : heart; width : 400px ; }
Layout
Win/Lose
Finally, we have to add the containers to show the win/lose message. It has no secret, we just accept to create the container, add the message and stylize them.
HTML
<div id="you-win"> <p>Skillful task, you saved our man!</p> </div> <div id="game-over"> <p>Game over!</p> </div>
CSS
# you-win , # game-over { background : #87D892; border : twopx solid #407847; border-radius : 6px ; colour : #407847; margin : xlpx auto 0; text-align : center; width : 300px ; } # game-over { background : #F9C3B9; edge-color : #8A2512; colour : #8A2512; }
Layout
CSS details
Okay, let's analyze what we already accept:
We have to do the following things before start coding our JavaScript:
- Centre all the content in the screen
- Hide the elements we don't demand to start the game
To do the first matter, we will create a container and add together some styles to it:
HTML
<div id="principal"> <button id="new-game"> New game </button> <!-- ... --> </div>
CSS
# main { margin : 40px auto; width : 600px ; }
On the other hand, we will create a form to hide the elements we don't need to commencement the game. With JavaScript, nosotros are going to add and hibernate the elements by adding and removing this class:
HTML
<div id="game" class="hide"> <div id="currentWord"></div> </div> <div id="messages"> </div> <div id="you-win" class="hide"> <p>Good job, yous saved our man!</p> </div> <div id="game-over" class="hibernate"> <p>Game over!</p> </div>
CSS
JavaScript
The last part of the game is to join both the game logic and the game layout. We are going to add all the functionality in a file called awarding.js
. We have to add both files in the right order in the HTML, merely before the closing tag </torso>
.
<script src="js/hangman.js"></script> <script src="js/application.js"></script>
We will have to create, more than or less, the aforementioned functionality that we have created in the layout. Allow's exercise it.
New game
Beginning of all we will declare a global variable to admission to the game functions. This variable will be initialized every time that the "New game" button is clicked.
var hangman; var newGameClick = function () { hangman = new Hangman(); }; document.getElementById("new-game").addEventListener("click", newGameClick);
We are too attaching the click event to the button, so information technology will execute the newGameClick
role. Which is the next thing we have to do? Show the user the discussion he has to discern.
Draw current word
Nosotros will create a office to draw the current word. It will take the word from the hangman
global variable, and add information technology into the container we created in the layout. It volition be executed when nosotros create a new game.
var newGameClick = part () { hangman = new Hangman(); drawCurrentWord(); }; var resetCurrentWord = function () { var word = certificate.getElementById("currentWord"); while (word.firstChild) { word.removeChild(word.firstChild); } }; var drawCurrentWord = function (word) { resetCurrentWord(); var currentWord = word || hangman.getWordStatus(); var currentWordDom = document.getElementById("currentWord"); currentWord.forEach(part (letter) { var spanLetter = document.createElement("span"); var content = document.createTextNode(letter); spanLetter.appendChild(content); currentWordDom.appendChild(spanLetter); }); };
We have likewise created a function that will reset the electric current word container before draw the new status. The following we need is to create a office that will wait for the histrion to insert a letter to the game.
Insert letter
At that place are several ways to insert the letter of the alphabet to check out if it'south in the secret word. We could accept a form where the actor inserts a letter of the alphabet and press a button to ship it. Some other choice is to add together an event to the document to capture whatever press cardinal, and send it to the hangman. We will do the second option.
Nosotros will create the insertLetter
method that will be triggered every time a key is pressed on the document. We have to do several things:
- We don't desire to execute the issue when whatsoever key is pressed. We just want to capture the upshot when a alphabetic character is pressed.
- If the selected letter is not in the word, we have to add it to the used letters list.
- After receive the alphabetic character, nosotros have to render the electric current word, the current hangman condition, and bank check out if the game has finished.
Let'south go step past stride, first of all allow's create the method and attach information technology to the "keyDown" issue of the document.
var insertLetter = function ( event ) { } ; document . addEventListener ( "keydown" , insertLetter ) ;
Y'all can bank check out the keydown documentation to run into the received parameter. Through this parameter we can access to the pressed key, with the upshot.keyCode
property, that will requite us the letter ASCII code.
var insertLetter = part ( event ) { if ( event . keyCode < 65 || event . keyCode > xc ) return ; } ;
The following footstep is to check out if the inserted alphabetic character is contained in the secret word:
var insertLetter = function ( event ) { if ( event . keyCode < 65 || issue . keyCode > ninety ) return ; var letter = String . fromCharCode ( effect . keyCode ) ; var correct = hangman . askLetter ( letter of the alphabet ) ; } ;
String.fromCharCode
returns a string created by using the ASCII representation of the same. Remember that the hangman.askLetter
method returns true if the letter is in the secret word, false if information technology's not, and undefined if the letter was already inserted. We can use this value to add the used letter if it's not correct, and to depict the current status of the word if it exists:
var insertLetter = function ( event ) { if ( ! hangman || ( issue . keyCode < 65 || event . keyCode > 90 ) ) return ; var letter = String . fromCharCode ( result . keyCode ) ; var correct = hangman . askLetter ( letter ) ; if ( right !== undefined && ! correct ) { _addLetter ( letter ) ; } else { drawCurrentWord ( ) ; } } ;
We will add the wrong letter just if it is not in the container yet. We also take to draw the hangman if the letter of the alphabet is wrong. Nosotros oasis't divers this method yet, so information technology could be the next one:
Describe hangman
var drawHangman = function ( ) { document . getElementById ( "hangman" ) . classList += " lifes-" + ( hangman . errorsLeft + i ) ; } ;
We are going to add each lifes-*
grade to the hangman
container, so it will appear a slice of motion-picture show with each error. We just have to call it when the letter of the alphabet is incorrect:
var insertLetter = part ( event ) { if ( ! hangman || ( issue . keyCode < 65 || issue . keyCode > ninety ) ) return ; var letter = String . fromCharCode ( event . keyCode ) ; var correct = hangman . askLetter ( letter ) ; if ( correct !== undefined && ! correct ) { _addLetter ( letter ) ; drawHangman ( ) ; } else { drawCurrentWord ( ) ; } } ;
To finish upwards this method, nosotros just need to check out if the game has finished. We will create an afterRound
office to do that, and it volition be called at the end of the insertLetter
method:
Later on round
var afterRound = part ( ) { var status = hangman . gameStatus ( ) ; if ( ! status ) return ; if ( status . toLowerCase ( ) === "yous win" ) { document . getElementById ( "you-win" ) . classList = "" ; } else { drawCurrentWord ( hangman . secretWord . split ( "" ) ) ; document . getElementById ( "game-over" ) . classList = "" ; } hangman = undefined ; } ;
If the game is not finished, the status will be undefined. On the other hand, if its finished, information technology volition return an string to indicate if the player has won or lost. We also set the hangman
variable to undefined to avoid game interactions in one case it's finished.
If the thespian has lost the game, we should show him the surreptitious word he couldn't discern. We do that by calling the drawCurrentWord
method, indicating as a parameter the undercover word splitted up by characters. Now we will add the call to the afterRound
method after each round:
var insertLetter = function ( outcome ) { if ( ! hangman || ( effect . keyCode < 65 || event . keyCode > 90 ) ) render ; var letter = String . fromCharCode ( outcome . keyCode ) ; var correct = hangman . askLetter ( alphabetic character ) ; if ( correct !== undefined && ! correct ) { _addLetter ( letter ) ; drawHangman ( ) ; } else { drawCurrentWord ( ) ; } afterRound ( ) ; } ;
Once the game is over, we have to give the choice to start a new game. This ways that we take to create the functionality to reset the controls when the "New game" buttons is clicked.
Reset controls
We will create a role to initialize the controls of the game. Information technology will exist called at the start of the newGame
method, and will add together and remove the necessary classes to the containers of the game.
var newGameClick = role ( ) { _initializeControls ( ) ; hangman = new Hangman ( ) ; drawCurrentWord ( ) ; } ; var _initializeControls = function ( ) { document . getElementById ( "y'all-win" ) . classList = "hide" ; certificate . getElementById ( "game-over" ) . classList = "hibernate" ; document . getElementById ( "hangman" ) . classList = "" ; document . getElementById ( "letters" ) . innerHTML = "" ; } ;
This was the terminal feature we had to implement to finish the game. Our hangman is ready to play, permit's enjoy information technology :)
Summary
To sum up, we take seen how we tin can create a game like Hangman splitting it upwards into dissimilar parts. The best way to face this kind of bug is to create first of all the game logic, and then create the layout with HTML and CSS, and finally code the necessary JavaScript that will join both the logic and the layout.
Once nosotros take the basic functionality of this game, we could remember virtually future deportment over it. For example, nosotros could permit to select words with spaces, add together sounds to make it fancy, or call an external API to load a bigger lexicon of words.
Actress Resources
- Hangman online
How To Add Spaces In Hangman Javascript,
Source: https://github.com/ironhack-labs/lab-javascript-hangman
Posted by: bastarachemeself.blogspot.com
0 Response to "How To Add Spaces In Hangman Javascript"
Post a Comment