Rock, Paper, Scissors game

HTML
<!-- STARTING SCREEN --> <header class="main-header"> <div class="container"> <h1> <span>Rock,</span> <span>Paper,</span> <span>Scissors</span> </h1> <p class="intro">An Epic battle of Human Vs. Computer</p> </div> <div class="starter-screens"> <!-- START --> <div class="starter-screen start"> <div class="medium-container"> <button class="start button">Start</button> </div> </div> <!-- HOW MANY ROUNDS --> <div class="starter-screen choose-rounds"> <div class="medium-container"> <h2>How many rounds would you like to play?</h2> <ul> <li class="button" data-rounds="3" role="button"><span>3</span></li> <li class="button" data-rounds="5" role="button"><span>5</span></li> <li class="button" data-rounds="9" role="button"><span>9</span></li> <li class="button" data-rounds="15" role="button"><span>15</span></li> </ul> </div> </div> <div class="starter-screen choose-character"> <div class="medium-container"> <h2>Choose your character</h2> <ul> <li role="button" class="character1" data-character="character1"><span>Fluff fluff</span></li> <li role="button" class="character2" data-character="character2"><span>Squidgy</span></li> <li role="button" class="character3" data-character="character3"><span>Timmy</span></li> </ul> </div> </div> <!-- CHARACTERS --> <div class="starter-screen choose-rival"> <div class="medium-container"> <h2>Choose your rival:</h2> <ul> <li role="button" class="robot1" data-character="robot1"><span>Eugene</span></li> <li role="button" class="robot2" data-character="robot2"><span>Ada</span></li> <li role="button" class="robot3" data-character="robot3"><span>Turing</span></li> </ul> </div> </div> </div> </header> <main> <div class="container container-collapse"> <div class="play-area"> <!-- PLAYER & COMPUTER ICON --> <div class="players"> <div class="player-info"> <div class="player-character"></div> <p>Score: <span class="player-score">0</span></p> </div> <span>Vs.</span> <div class="player-info"> <div class="computer-character"></div> <p>Score: <span class="computer-score">0</span></p> </div> </div> <!-- ROUND --> <div class="round-wrap"> <p>Round: <span class="round">1</span>/<span class="best-of"></span></p> </div> <!-- PLAY ARENA --> <div class="arena"> <div class="player-chip"> <h3>Your choice</h3> <span class="player-choice"></span> <div class="player-choice-icon"></div> </div> <div class="computer-chip"> <h3>Computer choice</h3> <span class="computer-choice"></span> <div class="computer-choice-icon"></div> </div> <!-- CHOOSE WEAPON --> <div class="weapon"> <div class="weapon-inner"> <h3>Choose your weapon</h3> <ul> <li class="rock" role="button" data-weapon="rock"><span>Rock</span></li> <li class="paper" role="button" data-weapon="paper"><span>Paper</span></li> <li class="scissors" role="button" data-weapon="scissors"><span>Scissors</span></li> </ul> </div> </div> <!-- ROUND RESULTS --> <div class="result"> <div class="result-inner"> <h3 class="winner"></h3> <button class="play-again button">Play again</button> </div> </div> </div> </div> </div> </main> <!-- END SCREEN --> <section class="end-screen"> <div class="medium-container"> <div class="end-result"></div> <div class="rounds-end-screen"> <h3>Would you like a rematch? How many rounds do you want to play?</h3> <ul> <li class="button rounds-3" data-rounds="3" role="button"><span>3</span></li> <li class="button rounds-5" data-rounds="5" role="button"><span>5</span></li> <li class="button rounds-9" data-rounds="9" role="button"><span>9</span></li> <li class="button rounds-15" data-rounds="15" role="button"><span>15</span></li> </ul> </div> <button class="reset button">Rematch</button> </div> </section>
SCSS
/*========================================== VARIABLES ==========================================*/ /* WIDTHS */ $max-width: 1400px; $med-width: 900px; /* BREAKPOINTS */ $screenS: 600px; $screenM: 800px; $screenL: 1200px; $ml: 1000px; $border-radius-width: 900px; /* FONTS */ $rock: 'Luckiest Guy', cursive; $paper: 'Open Sans Condensed', sans-serif; $scissors: 'Mr Dafoe', cursive; $body-font: $paper; /* COLOURS */ $dark-grey: #333; $white: #f9f9f9; $duck-blue: #78d1dc; $purple: #eee1fe; $yellow: #f9edc5; $pink: #ffcbe2; $green: #ade9dd; /* COLOR ASSIGNMENTS */ $body-bg: $duck-blue; $header-bg: $dark-grey; $border: $duck-blue; $border-dark: $dark-grey; $arena-bg: $dark-grey; $button: $dark-grey; $footer: $dark-grey; /* TIMINGS */ $cubic: cubic-bezier(0.46,-0.41,0.3,1.52); $transition: 0.4s ease-out all; $cubic-transition: 1s $cubic all; /*========================================== BREAKPOINTS ==========================================*/ @mixin bp($point){ // "less than XS" mobile only (saves having to zero out properties on larger breakpoints) @if $point == lt-xs { @media only screen and (max-width: $screenXS) { @content; } } @else if $point == lt-s { @media only screen and (max-width: $screenS) { @content; } } @else if $point == lt-m { @media only screen and (max-width: $screenM) { @content; } } @else if $point == lt-l { @media only screen and (max-width: $screenL) { @content; } } // Extra small devices (smart-phones from 480px) @else if $point == xs { @media only screen and (min-width: $screenXS) { @content; } } // Small devices (tablets, 768px and up) @else if $point == s { @media only screen and (min-width: $screenS) { @content; } } @else if $point == s-m { @media only screen and (min-width: $screenS) and (max-width: $screenM) { @content; } } @else if $point == m { // Medium devices (desktops, 992px and up) @media only screen and (min-width: $screenM) { @content; } } @else if $point == m-l { // Medium to Large only @media only screen and (min-width: $screenM) and (max-width: $screenL) { @content; } } @else if $point == l { // Large devices (large desktops, 1200px and up) @media only screen and (min-width: $screenL) { @content; } } @else if $point == xl { // Large devices (large desktops, 1350px and up) @media only screen and (min-width: $screenXL) { @content; } } @else if $point == landscape { @media only screen and (orientation:landscape) { @content; } } @else if $point == portrait { @media only screen and (orientation:portrait) { @content; } } @else { @media only screen and (min-width: $point) { @content; } } } @mixin hide-text(){ font-size:0; color: transparent; text-shadow: none; background-color: transparent; border: 0; } /*========================================== ANIMATIONS ==========================================*/ @keyframes fade-in-left { 0% { transform: translateX(-100%); opacity: 0; } 100% { transform: translateX(0); opacity: 1; } } @keyframes fade-in-down { 0% { transform: translateY(-100%); opacity: 0; } 100% { transform: translateY(0); opacity: 1; } } @keyframes fade-out-right { 0% { opacity: 1; } 100% { opacity: 0; transform: translateX(100%); } } @keyframes fade-out-left { 0% { opacity: 1; } 100% { opacity: 0; transform: translateX(-100%); } } @keyframes headersize { 0% { height: 100vh; } 100% { height: 3rem; } } @keyframes scale-text { 100% { font-size: 2rem; } } @keyframes bg { 0% { background-position: bottom -20rem center; } 100% { background-position: bottom -0.5rem center; } } /*========================================== LAYOUT ==========================================*/ .container { padding: 0 2rem; max-width: $med-width; margin: 0 auto; width: 100%; &.container-collapse { padding: 0; @include bp(m) { padding: 0.2rem; } } } .medium-container { @extend .container; max-width: $med-width; } /*========================================== GENERAL ==========================================*/ .character { display: inline-block; margin: 0.5rem; border-radius: 100%; background-color: white; border: 5px solid $border; background-repeat: no-repeat; } .button { padding: 10px 20px; border: none; padding: 10px 40px; border: none; background-color: $button; color: $white; font-size: 2rem; cursor: pointer; position: relative; z-index: 1; transition: $transition; overflow: hidden; border-radius: 5px; &.active { background-color: $duck-blue; color: $dark-grey; @include bp(m) { &:hover { color: $dark-grey; &:before, &:after { background-color: $duck-blue; } } } } &:before, &:after { content: ""; position: absolute; z-index: -1; width: 51%; height: 100%; top: 0; background-color: $white; transition: $transition; } &:before { left: -100%; } &:after { right: -100%; } @include bp(m) { &:hover { color: $dark-grey; transition: $transition; &:before, &:after { transition: $transition; } &:before { left: 0; } &:after { right: 0; } } } } /*========================================== BACKGROUNDS ==========================================*/ .tie { background-color: $yellow; } .win { background-color: $green; } .lose { background-color: $pink; } .rock { background-image: url('http://hannahch.com/images/rock.svg'); } .paper { background-image: url('http://hannahch.com/images/paper.svg'); } .scissors { background-image: url('http://hannahch.com/images/scissors.svg'); } .character1 { background-image: url('http://hannahch.com/images/character1.svg'); } .character2 { background-image: url('http://hannahch.com/images/character2.svg'); } .character3 { background-image: url('http://hannahch.com/images/character3.svg'); } .robot1 { background-image: url('http://hannahch.com/images/robot1.svg'); } .robot2 { background-image: url('http://hannahch.com/images/robot2.svg'); } .robot3 { background-image: url('http://hannahch.com/images/robot3.svg'); } /*========================================== GENERAL ==========================================*/ html { font-size: 62.5%; min-width: 300px; } body { background-color: $body-bg; color: white; font-family: $body-font; font-size: 2rem; overflow: hidden; &.game-started { overflow-x: hidden; overflow-y: auto; } } main { padding-top: 7rem; padding-bottom: 1rem; } h2 { font-size: 2.5rem; margin-bottom: 4rem; } h3 { margin-bottom: 3rem; } /*========================================== HEADER ==========================================*/ .main-header { z-index: 10; padding: 10px 0; position: fixed; width: 100vw; height: 100vh; background-color: $header-bg; display: flex; flex-wrap: wrap; align-items: center; border-bottom: 1px solid white; h1 { padding: 30px 0; span { display: inline-block; margin-right: 10px; font-size: 3rem; animation: fade-in-left 0.5s $cubic both 0.5s; .game-started & { animation: scale-text 1s $cubic both 0.2s; } @include bp(s) { font-size: 6rem; } &:first-child { font-family: $rock; } &:nth-child(2) { animation-delay: 0.7s; font-family: $paper; .game-started & { animation-delay: 0.2s; } } &:last-child { animation-delay: 0.9s; font-family: $scissors; .game-started & { animation-delay: 0.2s; } } } } .game-started & { animation: headersize 0.5s ease-out both 0.5s; h1 { padding: 0; } } } .intro { animation: fade-in-left 0.2s ease-out both 1.3s; margin-bottom: 3rem; .game-started & { animation: fade-out-right 0.5s both 1; } } /*========================================== STARTER SCREENS ==========================================*/ .starter-screens { height: 430px; position: relative; width: 100%; .button { background-color: $purple; color: $dark-grey; margin-bottom: 10px; } .game-started & { animation: fade-out-right 0.5s both 0.2s; } } .starter-screen { width: 100%; text-align: center; transform: translateX(-150%); transition: $transition; &.animate-in { animation: fade-in-left 1s $cubic both; } ul { @include bp(m) { display: flex; justify-content: space-between; } } li { font-family: $scissors; font-size: 3rem; @include bp(m) { font-size: 5rem; } } } .start { animation: fade-in-left 1s $cubic both 1.4s; text-align: left; } .choose-character, .choose-rival { li { @extend .character; cursor: pointer; transition: $transition; width: 10rem; height: 10rem; @include bp(m) { width: 15rem; height: 15rem; &:hover { border-color: $white; background-color: $duck-blue; transition: $transition; } } } span { @include hide-text(); } } .player-character, .computer-character { @extend .character; width: 7rem; height: 7rem; border-color: $border-dark; @include bp(m) { width: 10rem; height: 10rem; } } .player-character, .computer-character, .choose-character li, .choose-rival li, .player-character li, .computer-character li { background-position: center; background-size: 70%; } /*========================================== ARENA/PLAY ==========================================*/ .arena { width: 100%; height: 36rem; background-color: $arena-bg; overflow: hidden; position: relative; h3 { text-align: center; width: 100%; } @include bp($border-radius-width) { border-radius: 0 0 1rem 1rem; } } .weapon, .result { z-index: 3; width: 100%; height: 100%; position: absolute; left: 0; display: flex; flex-wrap: wrap; align-items: center; text-align: center; color: $dark-grey; justify-content: center; transition: $cubic-transition; } .result { top: -100%; .weapon-chosen & { top: 0; transition: 1s $cubic all 3s; } h3 { font-size: 3rem; } } .weapon { bottom: 0; background-color: $purple; transition-delay: 0.2s; .weapon-inner { width: 100%; } .weapon-chosen & { bottom: -100%; } h3 { font-size: 2.5rem; margin-bottom: 4rem; } ul { width: 100%; display: flex; justify-content: space-between; } li { @extend .character; width: 24vw; height: 24vw; max-width: 200px; max-height: 200px; cursor: pointer; transition: $transition; margin: 1rem; background-size: 70%; .game-started & { animation: bg 0.3s ease-out both 1s; &:nth-child(2) { animation-delay: 1.2s } &:nth-child(3) { animation-delay: 1.4s } } @include bp(m) { margin: 0 4rem; &:hover { background-color: $duck-blue; border-color: $white; transition: $transition; } } } span { @include hide-text(); } } .computer-chip, .player-chip { position: absolute; width: 100%; text-align: center; h3 { margin-bottom: 2rem; @include bp(m) { font-size: 2.5rem; } } span { @include hide-text(); } @include bp(m) { width: 50%; transform: translateY(-50%); } } .computer-chip { right: -100%; transition: $cubic-transition; bottom: 2rem; @include bp(m) { top: 50%; bottom: auto; } .weapon-chosen & { right: 0; transition: 0.8s $cubic all 1.5s; } } .player-chip { left: -100%; transition: $cubic-transition; top: 2rem; @include bp(m) { top: 50%; } .weapon-chosen & { left: 0; transition: 0.8s $cubic all 0.6s; } } .computer-choice-icon, .player-choice-icon { @extend .character; width: 10rem; height: 10rem; display: inline-block; background-position: bottom -0.5rem center; background-size: 60%; @include bp(l) { width: 20rem; height: 20rem; } } /*========================================== PLAYERS ==========================================*/ .players { margin-bottom: 3rem; display: flex; justify-content: space-between; align-items: center; color: $dark-grey; span { font-size: 2rem; color: $dark-grey; } } .player-info { text-align: center; padding: 0 20px; } .round-wrap { padding: 20px; border-bottom: 1px solid $white; background-color: $dark-grey; @include bp($border-radius-width) { border-radius: 1rem 1rem 0 0; } } /*========================================== END SCREEN ==========================================*/ .end-screen { position: fixed; right: -100%; top: 0; width: 100%; height: 100%; transition: $cubic-transition; display: flex; align-items: center; z-index: 20; text-align: center; color: $dark-grey; h2 { margin-bottom: 1rem; font-size: 5rem; } h3 { margin-bottom: 2.5rem; } p { margin-bottom: 3rem; font-size: 2rem; } .end-game & { right: 0; transition: 1s $cubic all 5s; } } .rounds-end-screen { margin-bottom: 5rem; ul { @include bp(m) { display: flex; justify-content: space-around; } } li { margin-bottom: 1rem; } }
JAVASCRIPT
var gameModule = (function () { $(function() { // General variables var playerChoice, computerChoice, winner, round = 1, playerScore = 0, computerScore = 0, bestOf, overallResultClass, overallResultText, character, choices = ['rock', 'paper', "scissors"]; // Text Variables var playerWinsText = "You win the round!", computerWinsText = "Computer wins the round!", tieText = "It's a Tie!", overallPlayerWinText = "<h2>Well Done!</h2> <p>You won against the computer.</p>", overallComputerWinText = "<h2>You Lose...</h2> <p>The computer has defeated you</p>", overallTieText = "<h2>It's a draw!</h2> <p>Good effort.</p>"; // Set Characters function setCharacter(div, className) { character = $(div).data('character'); $(className).addClass(character); } function nextScreen(div) { div.parents('.starter-screen').hide().next().addClass('animate-in'); } // Decides on whether the computer is playing rock, paper or scissors function computerDecision() { var randomChoice = Math.floor(Math.random() * choices.length); return choices[randomChoice]; } // Plays the game function playGame(playerChoice) { computerChoice = computerDecision(); round++; // Set Choices $('.player-choice-icon').attr('class', 'player-choice-icon ' + playerChoice); $('.computer-choice-icon').attr('class', 'computer-choice-icon ' + computerChoice); winner = decideWinner(playerChoice, computerChoice); // Set the values on the screen setValues(playerChoice, computerChoice, winner); } // Sets all the values on the board function setValues(playerChoice, computerChoice, winnerText) { $('.player-choice').text(playerChoice); // If the player has chosen rock, paper or scissors $('.computer-choice').text(computerChoice); // If the computer has chosen rock, paper or scissors $('.winner').text(winnerText); // Who won the round // If the game has been reset set the score immediately if(round !== 1) { // Set the values once the animation has finished setTimeout(function(){ setScore(); }, 4000); } else { // Set the values immediately setScore(); $('.round').text(round); } } // Set the scores function setScore() { $('.player-score').text(playerScore); // The running score for the player $('.computer-score').text(computerScore); // The running score for the computer } // Decide who wins based on the player & computer choice function decideWinner(playerChoice, computerChoice) { var resultClass; // Who wins, What text is shown & What class is applied to the result screen if (playerChoice === computerChoice) { // If there is a tie winner = tieText; resultClass = "tie"; } else if (playerChoice === "rock") { // If the player chooses "Rock" switch (computerChoice) { case "scissors": winner = playerWinsText; playerScore++; resultClass = "win"; break; case "paper": winner = computerWinsText; computerScore++; resultClass = "lose"; break; } } else if (playerChoice === "paper") { // If the player chooses "Paper" switch (computerChoice) { case "rock": winner = playerWinsText; playerScore++; resultClass = "win"; break; case "scissors": winner = computerWinsText; computerScore++; resultClass = "lose"; break; } } else { // If the player chooses "Scissors" switch (computerChoice) { case "rock": winner = computerWinsText; computerScore++; resultClass = "lose"; break; case "paper": winner = playerWinsText; playerScore++; resultClass = "win"; break; } } // Set the class of the result screen $('.result').attr('class', 'result ' + resultClass); return winner; } // Set all variables to their base values function resetGame () { playerChoice = ""; computerChoice = ""; winner = ""; round = 1; playerScore = 0; computerScore = 0; setValues(); $('body').removeClass('end-game weapon-chosen'); $('.play-again').show(); } // Decide on who is the winner of the whole game function overallWinner() { if (playerScore > computerScore) { // Player wins overallResultText = overallPlayerWinText; overallResultClass = "win"; } else if (playerScore < computerScore) { // Computer wins overallResultText = overallComputerWinText; overallResultClass = "lose"; } else { // Tie overallResultText = overallTieText; overallResultClass = "tie"; } $('.end-result').html(overallResultText); $('.end-screen').attr('class', 'end-screen ' + overallResultClass); } // Show the end screen and final result function endGame() { $('body').addClass('end-game'); $('.play-again').hide(); overallWinner(); } // Set the total number of rounds function setBestOf(selectedRounds) { var endScreenRounds; bestOf = selectedRounds.data('rounds'); $('.best-of').text(bestOf); // Set the active class on the number of rounds on the end screen endScreenRounds = ".rounds-" + bestOf; $(endScreenRounds).addClass('active').siblings().removeClass('active'); } // Start $('.start').on('click', function(e) { e.preventDefault(); nextScreen($(this)); }); // Set what character is chosen and start the game $('.choose-rounds li').on('click', function(e) { e.preventDefault(); setBestOf($(this)); nextScreen($(this)); }); // Set what character is chosen and start the game $('.choose-character li').on('click', function(e) { e.preventDefault(); setCharacter($(this), '.player-character'); nextScreen($(this)); }); // Set what character is chosen and start the game $('.choose-rival li').on('click', function(e) { e.preventDefault(); setCharacter($(this), '.computer-character'); $('body').addClass('game-started'); }); // Play the game $('.weapon li').on('click', function(e) { e.preventDefault(); playerChoice = $(this).data('weapon'); $('body').addClass('weapon-chosen'); playGame(playerChoice); if (round > bestOf) { endGame(); } }); // Play the next round $('.play-again').on('click', function(e) { e.preventDefault(); $('body').removeClass('weapon-chosen'); $('.round').text(round); // How many rounds there have been }); // Reset the game from the beginning $('.reset').on('click', function(e) { e.preventDefault(); resetGame(); }); // Reset the game from the beginning $('.rounds-end-screen li').on('click', function(e) { e.preventDefault(); setBestOf($(this)); }); }); }());
Expand for more options Login