Building a Simple Rock–Paper–Scissors Game Using HTML, CSS, and JavaScript

Rock–Paper–Scissors is one of the best beginner-friendly projects to understand how JavaScript interacts with the DOM, handles events, and updates UI elements.
In this article, we will walk through a fully working implementation of the game using simple logic and clean code.
The goal of the project is to let the user pick Rock, Paper, or Scissors, then let the computer randomly choose its own option, and finally display the result.
Understanding the HTML Structure
The HTML layout contains three main parts:
- The result area showing user and CPU hands
- The text result (who wins)
- The three clickable options
<div class="result_images">
<span class="user_result"><img src="images/rock.png"></span>
<span class="cpu_result"><img src="images/rock.png"></span>
</div>
<div class="result">Let's Play!!</div>
<div class="option_images">
<span class="option_image"><img src="images/rock.png"><p>Rock</p></span>
<span class="option_image"><img src="images/paper.png"><p>Paper</p></span>
<span class="option_image"><img src="images/scissors.png"><p>Scissors</p></span>
</div>
Each option (.option_image) is clickable, and each contains an image and a label.
Selecting Elements in JavaScript
We begin the script by selecting all the elements we will interact with:
const gameContainer = document.querySelector('.container');
const userResult = document.querySelector('.user_result img');
const cpuResult = document.querySelector('.cpu_result img');
const result = document.querySelector('.result');
const optionsImages = document.querySelectorAll('.option_image');
These references allow us to update the UI dynamically (changing images, text, animations).
Adding Click Logic to Each Choice
We loop through each option (rock, paper, scissors), and attach a click event listener:
optionsImages.forEach((image, index) => {
image.addEventListener('click', (e) => {
// logic here
});
});
The index represents:
- 0 → Rock
- 1 → Paper
- 2 → Scissors
This index will be important later to determine the user’s choice.
User Clicks — Start Animation and Reset UI
When a user clicks on an option:
image.classList.add('active');
userResult.src = cpuResult.src = "images/rock.png";
result.textContent = "Wait...";
This resets the hands to the default rock image, gives visual feedback, and shows “Wait…” during the CPU animation.
Then we remove “active” class from other options:
optionsImages.forEach((image2, index2) => {
index !== index2 && image2.classList.remove('active');
});
We also start shaking animation:
gameContainer.classList.add('start');
Step 2: Delay the CPU Choice
The game waits 2.5 seconds before revealing the results:
setTimeout(() => {
gameContainer.classList.remove('start');
Inside this timeout, the real logic happens.
Step 3: Show User’s Real Choice
We extract the image source of what the user clicked:
let imageSrc = e.target.querySelector('img').src;
userResult.src = imageSrc;
Step 4: Generate CPU Random Choice
The CPU picks a random number 0, 1, or 2:
let randomNumber = Math.floor(Math.random() * 3);
let cpuImages = ['images/rock.png','images/paper.png','images/scissors.png'];
cpuResult.src = cpuImages[randomNumber];
The CPU now displays a random hand.
Step 5: Compare User and CPU Values
We convert the options into short values:
let cpuValue = ['R','P','S'][randomNumber];
let userValue = ['R','P','S'][index];
Our outcomes are mapped like this:
let outComes = {
RP:'Cpu',
RS:'User',
PS:'Cpu',
PR:'User',
SR:'Cpu',
SP:'User'
};
Example:
- RS → Rock beats Scissors → User wins
- PR → Paper beats Rock → User wins
We get the result:
let outComeValue = outComes[userValue + cpuValue];
result.textContent = userValue === cpuValue ? 'Match Draw' : `${outComeValue} Won`;
If both values are the same, it is a draw.
CSS Animation (Short Explanation)
When the game starts, CSS applies shaking animations:
.container.start .user_result { animation: userShake 0.7s infinite; }
.container.start .cpu_result { animation: cpuShake 0.7s infinite; }
This makes the game feel more alive and fun.
Final Result
With a few lines of JavaScript and CSS animations, we created a fully functional Rock–Paper–Scissors game where:
- User clicks an option
- UI animates and resets
- CPU randomly selects an option
- JavaScript compares results
- The game announces a winner
Want to See the Full Code?
I uploaded the complete project to a public repository.
You can check it here:
Building a Simple Rock–Paper–Scissors Game Using HTML, CSS, and JavaScript was originally published in Javarevisited on Medium, where people are continuing the conversation by highlighting and responding to this story.
This post first appeared on Read More

