I am currently developing a Simon says type game using jQuery and JavaScript.
I have linked a fully copy of the game on Github
Github download and unzip to see the game fully https://github.com/Jamiex304/Simon_Says_Game_Demo (Disabled Now)
I have reached a problem I want to add a timer that the player can see.
Currently the level will just go on till the user clicks the wrong button in the sequence.
Some Basic info on the game:
The user will see a random sequence each level a new sequence is added with one more extra move. Each time the user enters the right sequence they go to the next level all info can be found in the attached JavaScript with comments
WHAT I WANT HELP ADDING
I just want to add a timer that starts at 10 seconds when the user clicks the start button.
Each time the enter the right sequence the timer starts again when they reach 5 right sequences the timer adds 5 extra seconds.
I have attached the JavaScript that handles the game events and there is a link to the full site.
Any help would be great.
JavaScript
var game={ //game object
level: 1, //current level
turn: 0, //current turn
difficulty: 1, // user difficulty
score: 0, //current score
active: false, //whether a turn is active or not
handler: false, // whether the click and sound handlers are active
shape: '.shape', // cached string for the pad class
genSequence: [], //array containing the generated/randomized pads
plaSequence: [], //array containing the users pad selections
init: function(){ //initialises the game
if(this.handler === false){ //checks to see if handlers are already active
this.initPadHandler(); //if not activate them
}
this.newGame(); //reset the game defaults
},
initPadHandler: function(){
that=this;
$('.pad').on('mouseup',function(){
if(that.active===true){
var pad=parseInt($(this).data('pad'),10);
that.flash($(this),1,300, pad);
that.logPlayerSequence(pad);
}
});
this.handler=true;
},
newGame: function(){ //resets the game and generates a starts a new level
this.level=1;
this.score=0;
this.newLevel();
this.displayLevel();
this.displayScore();
},
newLevel: function(){
this.genSequence.length=0;
this.plaSequence.length=0;
this.pos=0;
this.turn=0;
this.active=true;
this.randomizePad(this.level); //randomize pad with the correct amount of numbers for this level
this.displaySequence(); //show the user the sequence
},
flash: function(element, times, speed, pad){ //function to make the pads appear to flash
var that = this; //cache this
if(times > 0){ //make sure we are supposed to flash
that.playSound(pad); //play the corresponding pad sound
element.stop().animate({opacity: '1'}, { //animate the element to appear to flash
duration: 50,
complete: function(){
element.stop().animate({opacity: '0.6'}, 200);
}
}); //end animation
}
if (times > 0) { //call the flash function again until done the correct amount of times
setTimeout(function () {
that.flash(element, times, speed, pad);
}, speed);
times -= 1; //times - 1 for each time it's called
}
},
playSound: function(clip){ //plays the sound that corresponds to the pad chosen
var sound= $('.sound'+clip)[0];
console.log(sound);
console.log($('.sound'+clip));
sound.currentTime=0; //resets audio position to the start of the clip
sound.play(); //play the sound
},
randomizePad: function(passes){ //generate random numbers and push them to the generated number array iterations determined by current level
for(i=0;i<passes;i++){
this.genSequence.push(Math.floor(Math.random() * 4) + 1);
}
},
logPlayerSequence: function(pad){ //log the player selected pad to user array and call the checker function
this.plaSequence.push(pad);
this.checkSequence(pad);
},
checkSequence: function(pad){ //checker function to test if the pad the user pressed was next in the sequence
that=this;
if(pad !== this.genSequence[this.turn]){ //if not correct
this.incorrectSequence();
}else{ //if correct
this.keepScore(); //update the score
this.turn++; //incrememnt the turn
}
if(this.turn === this.genSequence.length){ //if completed the whole sequence
this.level++; //increment level, display it, disable the pads wait 1 second and then reset the game
this.displayLevel();
this.active=false;
setTimeout(function(){
that.newLevel();
},1000);
}
},
displaySequence: function(){ //display the generated sequence to the user
var that=this;
$.each(this.genSequence, function(index, val) { //iterate over each value in the generated array
setTimeout(function(){
that.flash($(that.shape+val),1,300,val);
},500*index*that.difficulty); // multiply timeout by how many items in the array so that they play sequentially and multiply by the difficulty modifier
});
},
displayLevel: function(){ //just display the current level on screen
$('.level h2').text('Level: '+this.level);
},
displayScore: function(){ //display current score on screen
$('.score h2').text('Score: '+this.score);
},
keepScore: function(){ //keep the score
var multiplier=0;
switch(this.difficulty) //choose points modifier based on difficulty
{
case '2':
multiplier=1;
break;
case '1':
multiplier=2;
break;
case '0.5':
multiplier = 3;
break;
case '0.25':
multiplier = 4;
break;
}
this.score += (1 * multiplier); //work out the score
this.displayScore(); //display score on screen
},
incorrectSequence: function(){ //if user makes a mistake
var corPad = this.genSequence[this.turn], //cache the pad number that should have been pressed
that = this;
this.active=false;
this.displayLevel();
this.displayScore();
setTimeout(function(){ //flash the pad 4 times that should have been pressed
that.flash($(that.shape+corPad),4,300,corPad);
},500);
$('.start').show(); //enable the start button again and allow difficulty selection again
$('.difficulty').show();
}
};
$(document).ready(function(){ //document ready
$('.start').on('mouseup', function(){ //initialise a game when the start button is clicked
$(this).hide();
game.difficulty = $('input[name=difficulty]:checked').val();
$('.difficulty').hide();
game.init();
});
});
Ok I think i've managed to do it the way you want it, here is full js:
(I've commented the parts i've added)
var game={ //game object
level: 1, //current level
turn: 0, //current turn
difficulty: 1, // user difficulty
score: 0, //current score
active: false, //whether a turn is active or not
handler: false, // whether the click and sound handlers are active
shape: '.shape', // cached string for the pad class
genSequence: [], //array containing the generated/randomized pads
plaSequence: [], //array containing the users pad selections
init: function(){ //initialises the game
if(this.handler === false){ //checks to see if handlers are already active
this.initPadHandler(); //if not activate them
}
this.newGame(); //reset the game defaults
},
initPadHandler: function(){
that=this;
$('.pad').on('mouseup',function(){
if(that.active===true){
var pad=parseInt($(this).data('pad'),10);
that.flash($(this),1,300, pad);
that.logPlayerSequence(pad);
}
});
this.handler=true;
},
newGame: function(){ //resets the game and generates a starts a new level
this.level=1;
this.score=0;
this.newLevel();
this.displayLevel();
this.displayScore();
//initialize timer to 10 seconds
this.timer = 10;
},
newLevel: function(){
this.genSequence.length=0;
this.plaSequence.length=0;
this.pos=0;
this.turn=0;
this.active=true;
this.randomizePad(this.level); //randomize pad with the correct amount of numbers for this level
this.displaySequence(); //show the user the sequence
},
flash: function(element, times, speed, pad){ //function to make the pads appear to flash
var that = this; //cache this
if(times > 0){ //make sure we are supposed to flash
that.playSound(pad); //play the corresponding pad sound
element.stop().animate({opacity: '1'}, { //animate the element to appear to flash
duration: 50,
complete: function(){
element.stop().animate({opacity: '0.6'}, 200);
}
}); //end animation
}
if (times > 0) { //call the flash function again until done the correct amount of times
setTimeout(function () {
that.flash(element, times, speed, pad);
}, speed);
times -= 1; //times - 1 for each time it's called
}
},
playSound: function(clip){ //plays the sound that corresponds to the pad chosen
var sound= $('.sound'+clip)[0];
console.log(sound);
console.log($('.sound'+clip));
sound.currentTime=0; //resets audio position to the start of the clip
sound.play(); //play the sound
},
randomizePad: function(passes){ //generate random numbers and push them to the generated number array iterations determined by current level
for(i=0;i<passes;i++){
this.genSequence.push(Math.floor(Math.random() * 4) + 1);
}
},
logPlayerSequence: function(pad){ //log the player selected pad to user array and call the checker function
this.plaSequence.push(pad);
this.checkSequence(pad);
},
checkSequence: function(pad){ //checker function to test if the pad the user pressed was next in the sequence
that=this;
if(pad !== this.genSequence[this.turn]){ //if not correct
this.incorrectSequence();
}else{ //if correct
this.keepScore(); //update the score
this.turn++; //incrememnt the turn
}
if(this.turn === this.genSequence.length){ //if completed the whole sequence
this.level++; //increment level, display it, disable the pads wait 1 second and then reset the game
this.displayLevel();
this.active=false;
// Stop counting when sequence is correct to avoid time running out before starting next level
clearInterval(this.timerInterval);
//Add 5 seconds each 5th level
this.timer = 10 + 5 * Math.floor(this.level / 5);
//Update timerdisplay to show fulltime while displaying next level sequence
$(".Timer p").html(this.timer);
setTimeout(function(){
that.newLevel();
},1000);
}
},
// Countdown and update timer, call incorrectsequence when time's up
countDown: function(){
this.timer -= 0.1;
$(".Timer p").html(this.timer.toFixed(1)); // Display 9.0 instad of 9
if(this.timer < 0.1){
this.incorrectSequence();
}
},
displaySequence: function(){ //display the generated sequence to the user
var that=this;
var timerCount = 0;
$.each(this.genSequence, function(index, val) { //iterate over each value in the generated array
timerCount = index;
setTimeout(function(){
that.flash($(that.shape+val),1,300,val);
},500*index*that.difficulty); // multiply timeout by how many items in the array so that they play sequentially and multiply by the difficulty modifier
});
// Wait to start timer until full sequence is displayed
setTimeout(function(){ that.timerInterval = setInterval(function(){that.countDown()}, 100)}, 500*timerCount*that.difficulty);
},
displayLevel: function(){ //just display the current level on screen
$('.level h2').text('Level: '+this.level);
},
displayScore: function(){ //display current score on screen
$('.score h2').text('Score: '+this.score);
},
keepScore: function(){ //keep the score
var multiplier=0;
switch(this.difficulty) //choose points modifier based on difficulty
{
case '2':
multiplier=1;
break;
case '1':
multiplier=2;
break;
case '0.5':
multiplier = 3;
break;
case '0.25':
multiplier = 4;
break;
}
this.score += (1 * multiplier); //work out the score
this.displayScore(); //display score on screen
},
incorrectSequence: function(){ //if user makes a mistake
//Stop counting down timer and display start message
clearInterval(this.timerInterval);
$(".Timer p").html("Get Ready your time starts when you click start");
var corPad = this.genSequence[this.turn], //cache the pad number that should have been pressed
that = this;
this.active=false;
this.displayLevel();
this.displayScore();
setTimeout(function(){ //flash the pad 4 times that should have been pressed
that.flash($(that.shape+corPad),4,300,corPad);
},500);
$('.start').show(); //enable the start button again and allow difficulty selection again
$('.difficulty').show();
}
};
$(document).ready(function(){ //document ready
$('.start').on('mouseup', function(){ //initialise a game when the start button is clicked
$(this).hide();
game.difficulty = $('input[name=difficulty]:checked').val();
$('.difficulty').hide();
game.init();
});
});
You can check it out here: JSFiddle (sounds disabled in fiddle)
You don't really say specifically what you want other than a timer, but based off your markup is something like this what you're looking for?
var $timer = $('.Timer'), $timerTitle = $('.TimerTitle'), $start = $('.start'), $increment = $('.increment'), maxDuration = 10, defaultDuration = 10, count = 0, $gameCount = $('#gameCount'); $timerTitle.text("Get ready! You have " + maxDuration + " seconds!"); $start.on('click', function() { getDuration(); return false; }); function getDuration() { $start.prop('disabled', true); setTimeout(function() { var duration = $timer.data('duration'); if(duration === undefined || duration < 0) duration = maxDuration; $timer.text(duration); $timer.data('duration', --duration); if(duration > -1) { if(duration < 5) { if(duration % 2 == 0) { $timer.css({'background-color':'blue', 'color':'white'}); } else { $timer.css({'background-color':'transparent', 'color':'black'}); } } getDuration(); } else { count++; $gameCount.text("Current game count: " + count); if(count % 5 == 0) defaultDuration += 5; maxDuration = defaultDuration; $timer.css({'background-color':'transparent', 'color':'black'}); $timer.text(''); $timerTitle.text("Get ready! You have " + maxDuration + " seconds!"); $start.prop('disabled', false); } }, 1000); }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.0.0/jquery.min.js"></script> <div align='center'> <div class="TimerTitle"></div> <div class="Timer"></div> <br /> <button class="start">start</button> <div id='gameCount'>Current game count: 0</div> </div>
It's a little unconventional (it doesn't count down, but up), but how's this:
http://jsfiddle.net/rudiedirkx/nrp3e269/
The magic is tick()
which triggers 60/s:
var tickStart = 0;
function tick() {
var tickSpent = (Date.now() - tickStart) / 1000,
timeLeft = startTimeLeft - tickSpent;
tl.textContent = Math.round(timeLeft * 10) / 10;
if ( timeLeft > 0 ) {
requestAnimationFrame(tick);
}
else {
document.body.classList.add('gameover');
}
}
The start button kicks off the count:
tickStart = Date.now();
tick();
The move button adds time to the count:
if ( ++moves % 5 == 0 ) {
startTimeLeft += 5;
}
else {
startTimeLeft += 1;
}
It's just a proof of concept. You're gonna have to do the bulk. First thing would be to make it a nice CountDown object with methods and local properties instead of globals.
CountDown.startTimeLeft
CountDown.tickStart
CountDown.tick()
CountDown.start()
CountDown.finish()
CountDown.addTime()
To separate your app logic from the ticker.
Something like this might work?
var n = 100;
setTimeout(countDown,1000);
function countDown(){
n--;
if(n > 0){
setTimeout(countDown,1000);
}
$(".timer").html(n);
}
If i understand you just want to countdown ? from 10 sec and so on ? than this script will help you i think
<script>
<!--
//change below target URL to your own OTHERWISE DELETE
// this link will redirect you to the main page or the page you want
var targetURL="example.com"
//change the second to start counting down from
var countdownfrom=10
var currentsecond=document.redirect.redirect2.value=countdownfrom+1
function countredirect(){
if (currentsecond!=1){
currentsecond-=1
document.redirect.redirect2.value=currentsecond
}
else{
window.location=targetURL
return
}
setTimeout("countredirect()",1000)
}
countredirect()
//-->
</script>
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.