This program is a Covid-19 version of whack-a-mole called put-on-a-mask. The idea was inspired by an online game that my friends and I played during the pandemic called Covidopoly, a Covid-19 version of the board game Monopoly. Like this game, I wanted to make some light out of this dark situation we are in a make a fun, easy, time-passing game that will (hopefully) keep making you play until the pandemic is over.
To play is simple: the player must put masks on the viruses as fast as they can. There will be a total of 4 viruses on the screen at all times and once a virus is successfully clicked (accompanied by a “pop” sound), it will regenerate in a random color to a random position. If the player misses or takes too long to click a virus, they will get a strike– an accumulation of 3 strikes will end the game. The virus that was on the screen for too long will disappear on its own and regenerate in a new random color and position. Every 20 points, the player will level up which makes the time it takes a virus to disappear on its own shorter.
If I had more time, I would like to add more complex elements to the game like making the viruses move around, add more viruses to the screen after a certain amount of levels, or add more clickable elements for bonus points or strike reductions.
var covidviruses = [];
var covidImageLinks = ["https://i.imgur.com/iUnzt1x.png",
"https://i.imgur.com/V9cdbDy.png",
"https://i.imgur.com/OjUptCF.png",
"https://i.imgur.com/heDuTxd.png",
"https://i.imgur.com/PoNLrQ1.png",
"https://i.imgur.com/oIF3cp7.png",
"https://i.imgur.com/jc8muyt.png",
"https://i.imgur.com/X6MPvtK.png"]
var mask;
var coronavirusSound;
var popSound;
var clickSound;
var covidX = [150, 200, 300, 350];
var covidY = [300, 150, 200, 250];
var strike = 0;
// array of virus objects
var virus = [];
var page = 1;
var score = 0;
var ageIncrease = 1;
var maxScore = 0;
var gameLevel = 1;
var angle = 20;
function preload() {
// load pictures (different color viruses)
for(var i = 0; i < covidImageLinks.length; i ++) {
covidviruses[i] = loadImage(covidImageLinks[i]);
}
mask = loadImage("https://i.imgur.com/DdBChjv.png");
coronavirusSound = loadSound("https://courses.ideate.cmu.edu/15-104/f2020/wp-content/uploads/2020/12/coronavirus.wav");
popSound = loadSound("https://courses.ideate.cmu.edu/15-104/f2020/wp-content/uploads/2020/12/pop.wav");
clickSound = loadSound("https://courses.ideate.cmu.edu/15-104/f2020/wp-content/uploads/2020/12/click.wav")
}
function setup() {
createCanvas(480, 480);
useSound();
// create array of objects of 4 starter viruses (location, size, color, age)
for(var i = 0; i < 4; i ++) {
virus[i] = new Object();
virus[i].x = covidX[i];
virus[i].y = covidY[i];
virus[i].color = floor(random(0, 8));
virus[i].size = 90;
virus[i].age = 0;
}
frameRate(40);
noStroke();
}
function soundSetup() {
coronavirusSound.setVolume(.5);
popSound.setVolume(.5);
clickSound.setVolume(.5);
}
function draw() {
// title page
if(page == 1) {
cursor();
createTitlePage();
}
// game
if(page == 2) {
noCursor();
background("#BFEDFF");
// draw 4 viruses to begin
for(var i = 0; i < 4; i ++) {
image(covidviruses[virus[i].color], virus[i].x, virus[i].y, virus[i].size, virus[i].size);
// add virus age
virus[i].age += ageIncrease;
// if virus has been unclicked for 200 frames --> strike + new virus replacement
if(virus[i].age == 200) {
makeNewVirus(i);
strike += 1;
}
}
// 3 misses --> game over
if(strike == 3) {
// go to end page
page = 3;
}
// mask on cursor
imageMode(CENTER);
image(mask, mouseX, mouseY, 90, 90);
updateScore();
// level up every 20 points and increase aging rate (so virus disappears faster)
if(score%20 == 0 & score > maxScore) {
ageIncrease += 1;
maxScore = score;
gameLevel += 1;
}
}
// end page
if(page == 3) {
cursor();
createEndPage();
}
// help page
if(page == 4) {
cursor();
createHelpPage();
}
}
function mousePressed() {
// thresholds of a success click for viruses
var d = [];
for(var i = 0; i < 4; i ++) {
d[i] = dist(mouseX, mouseY, virus[i].x, virus[i].y);
}
// title page
if(page == 1) {
// play button --> reset everything
if(mouseX > 190 & mouseX < 290 && mouseY > 305 && mouseY < 355) {
// go to game page
clickSound.play();
strike = 0;
score = 0;
ageIncrease = 1;
maxScore = 20;
gameLevel = 1;
page = 2;
}
if(mouseX > 165 & mouseX < 315 && mouseY > 135 && mouseY < 285){
// sound effect
coronavirusSound.play();
}
if(mouseX > 140 & mouseX < 340 && mouseY > 365 && mouseY < 415) {
clickSound.play();
page = 4;
}
}
// game page
else if(page == 2) {
// if clicks are successes for any 4 of the viruses --> make pop sound, score increase by 1, new virus replacement
if (d[0] < 45) {
popSound.play();
makeNewVirus(0);
score += 1;
}
else if (d[1] < 45) {
popSound.play();
makeNewVirus(1);
score += 1;
}
else if(d[2] < 45) {
popSound.play();
makeNewVirus(2);
score += 1;
}
else if(d[3] < 45) {
popSound.play();
makeNewVirus(3);
score += 1;
}
else { // a miss
strike += 1;
}
}
// end page
else if(page == 3) {
// play again button --> reset everything
if(mouseX > 125 & mouseX < 355 && mouseY > 290 && mouseY < 370) {
clickSound.play();
strike = 0;
score = 0;
ageIncrease = 1;
maxScore = 20;
gameLevel = 1;
page = 2;
}
// go back to main page
if(mouseX > 140 & mouseX < 340 && mouseY > 365 && mouseY < 415) {
clickSound.play();
page = 1;
}
}
// help page
else if(page == 4) {
// play button --> reset everything
if(mouseX > 190 & mouseX < 290 && mouseY > 305 && mouseY < 355) {
// game page
clickSound.play();
strike = 0;
score = 0;
ageIncrease = 1;
maxScore = 20;
gameLevel = 1;
page = 2;
}
// return to main page
if(mouseX > 140 & mouseX < 340 && mouseY > 365 && mouseY < 415) {
clickSound.play();
page = 1;
}
}
}
// replace clicked viruses or missed viruses
function makeNewVirus(index) {
covidX[index] = random(90, 390);
covidY[index] = random(135, 390);
virus[index].x = covidX[index];
virus[index].y = covidY[index];
virus[index].color = floor(random(0, 8));
virus[index].size = 90;
virus[index].age = 0;
}
// title page (page 0)
// button to play
// button to go to help page
// interactive graphic (makes sound)
function createTitlePage() {
background("#D7C9FF");
// play button
if(mouseX > 190 & mouseX < 290 && mouseY > 305 && mouseY < 355) {
fill("pink");
}
else{
fill("white");
}
rectMode(CENTER);
rect(width/2, 330, 100, 50);
// help button
if(mouseX > 140 & mouseX < 340 && mouseY > 365 && mouseY < 415) {
fill("pink");
}
else{
fill("white");
}
rect(width/2, 390, 200, 50);
textSize(30);
textAlign(CENTER);
// text, box labels
fill("black");
text("put on a mask!", width/2, height/4);
text("play!", width/2, 340);
text("how to play", width/2, 400);
textSize(10);
text("click on me!", width/2, 280);
// animation using transformation
// viruses moving around the borders
imageMode(CORNER);
virusBorder();
// sound effect virus
// mouse hover --> rotate
push();
translate(240, 210);
if(mouseX > 165 & mouseX < 315 && mouseY > 135 && mouseY < 285){
rotate(radians(angle));
}
imageMode(CENTER);
image(covidviruses[6], 0, 0, 150, 150);
pop();
angle += 5;
}
// page 3
function createEndPage() {
background("#D7C9FF");
// play button
if(mouseX > 125 & mouseX < 355 && mouseY > 290 && mouseY < 370) {
fill("pink");
}
else {
fill("white");
}
rectMode(CENTER);
rect(width/2, 330, 200, 50);
// return to main page
if(mouseX > 140 & mouseX < 340 && mouseY > 365 && mouseY < 415) {
fill("pink");
}
else {
fill("white");
}
rect(width/2, 390, 200, 50);
// text, button labels
fill("black");
textSize(30);
textAlign(CENTER);
text("game over!", width/2, 150);
textSize(20);
text("Score: " + str(score), width/2, 200);
text("Highest Level: " + str(gameLevel), width/2, 230);
textSize(30);
text("play again!", width/2, 340);
text("main page", width/2, 400);
imageMode(CORNER);
virusBorder();
}
// keep track of score, strikes, level on game page
function updateScore() {
// print current score, strikes, and level at top
textSize(20);
textAlign(CENTER);
text("Score: " + str(score), width/2, 50);
text("Strikes: " + str(strike), width/2, 70);
text("Level " + str(gameLevel), width/2, 90);
}
// border pattern
function virusBorder() {
for(var i = 0; i < width; i += 40) {
image(covidviruses[floor(random(0, 8))], i, 0, 40, 40);
image(covidviruses[floor(random(0, 8))], i, 440, 40, 40);
image(covidviruses[floor(random(0, 8))], 0, i, 40, 40);
image(covidviruses[floor(random(0, 8))], 440, i, 40, 40);
}
}
// help page, page 4
function createHelpPage() {
background("#D7C9FF");
rectMode(CENTER);
// play button
if(mouseX > 190 & mouseX < 290 && mouseY > 305 && mouseY < 355) {
fill("pink");
}
else{
fill("white");
}
rect(width/2, 330, 100, 50);
// return to home button
if(mouseX > 140 & mouseX < 340 && mouseY > 365 && mouseY < 415) {
fill("pink");
}
else{
fill("white");
}
rect(width/2, 390, 200, 50);
// text, labels
fill("black");
textSize(30);
textAlign(CENTER);
// page button
text("play!", width/2, 340);
// help button
text("main page", width/2, 400);
text("how to play:", width/2, 120);
textSize(15);
text("like whack-a-mole but covid edition! click on the viruses as they appear and cover them with masks! make sure to be fast because the higher the score, the faster they disappear! the game ends after you get 3 misses!",
width/2, 300, 300, 300);
imageMode(CORNER);
virusBorder();
}