Reputation: 163
I'm trying to make a simon game and I'm almost done but I got an issue. In a simon game, when the simon's giving you the order (which represented by blinking lights and audio for each light) which you need to remember and repeat afterwards, there's a short delay between each blink (with it's audio) to the next one.
So now, my simon is making sounds but it's doing them all at once, with no delay. I tried using setIntarvel
and setTimeout
but still it played all audios at once.
Since adding the blinking shouldn't be that tough I'm keeping it to the end.
Then I built a timer function:
function timer(delayInMS) {
var time = new Date();
var currentTime = time.getTime();
var nextTime = time.getTime() + delayInMS;
while (currentTime != nextTime) {
time = new Date();
currentTime = time.getTime();
}
}
And used it inside the function which playing the audios, but it's still doing the same thing - playing it all at once.
This is the function which responsible for the audios:
function playAudio(btnSound) {
if (btnSound == "c") {
c.play();
}
if (btnSound == "g") {
g.play();
}
if (btnSound == "a") {
a.play();
}
if (btnSound == "d") {
d.play();
}
}
And this function responsible for the logic of the game:
var btns = ["c", "g", "a", "d"];
var randomOrder = "";
var playerInputOrder = "";
var timer = 1000; //For timer()
function randomSimon() {
var randomBtn = btns[Math.floor(Math.random() * 4)];
randomOrder += randomBtn;
for (i = 0; i <= randomOrder.length - 1; i++) {
for (s = 0; s <= i; s++) {
var someText = "";
someText += randomOrder.charAt(s);
playAudio(randomOrder.charAt(s));
document.getElementById('debug').innerHTML = someText; //this is for debugin, should be ignored.
timer(500);
}
}
}
And this is the whole script for better reading:
var isGameStarted = false;
var d = new Audio("dSharpNote.wav");
var a = new Audio("aSharpNote.wav");
var g = new Audio("gSharpNote.wav");
var c = new Audio("cNote.wav");
var btns = ["c", "g", "a", "d"];
var randomOrder = "";
var playerInputOrder = "";
var timer = 1000;
function startGame() {
isGameStarted = true; //So players won't be able to just press the simon's buttons.
randomOrder = ""; //A variable to keep the random order given by the simon.
playerInputOrder = ""; //A variable to keep the random order the player inputs.
randomSimon(); //Called to give the first button in the order.
}
function randomSimon() { //Adds one random button to the order and saves the order.
var randomBtn = btns[Math.floor(Math.random() * 4)]; //Adds the random button.
randomOrder += randomBtn; //Saves the random order.
for (i = 0; i <= randomOrder.length - 1; i++) { //this should play all the audios one by one according the saved order
for (s = 0; s <= i; s++) {
var someText = "";
someText += randomOrder.charAt(s);
playAudio(randomOrder.charAt(s));
document.getElementById('debug').innerHTML = someText; //this is for debugin, should be ignored.
timer(500);
}
}
}
function timer(delayInMS) {
var time = new Date();
var currentTime = time.getTime();
var nextTime = time.getTime() + delayInMS;
while (currentTime != nextTime) {
time = new Date();
currentTime = time.getTime();
}
}
function playerProgress(btn) { //Getting the player's input and checks if it's in the right order.
if (isGameStarted == true) {
var btnClicked = btn.id; //Gets the id of the button the player clicked.
playAudio(btnClicked); //So this could play it's audio.
playerInputOrder += btnClicked;
if (playerInputOrder.length == randomOrder.length) {
if (playerInputOrder == randomOrder) {
playerInputOrder = "";
setTimeout(randomSimon, 1000);
} else {
document.getElementById('scoreText').innerHTML = randomOrder + " Game Over!";
isGameStarted = false; //Makes the player unable to play the simon's button's audios.
}
}
document.getElementById('debug').innerHTML = playerInputOrder;
}
}
function playAudio(btnSound) {
if (btnSound == "c") {
c.play();
}
if (btnSound == "g") {
g.play();
}
if (btnSound == "a") {
a.play();
}
if (btnSound == "d") {
d.play();
}
}
function someInterval() {
var i = 0;
var anInterval = setInterval(function() {
i++;
if (i > 11) {
clearInterval(anInterval);
timer *= 2;
}
}, timer);
}
Upvotes: 2
Views: 215
Reputation: 1633
You can use setTimeout
and give it an increasing as you go through the colors:
function randomSimon() { //Adds one random button to the order and saves the order.
var randomBtn = btns[Math.floor(Math.random() * 4)]; //Adds the random button.
randomOrder += randomBtn; //Saves the random order.
for (i = 0; i <= randomOrder.length - 1; i++) { //this should play all the audios one by one according the saved order
for (s = 0; s <= i; s++) {
var someText = "";
someText += randomOrder.charAt(s);
>>>>>>> setTimeout(function() { playAudio(randomOrder.charAt(s)); },2000*s);
document.getElementById('debug').innerHTML = someText; //this is for debugin, should be ignored.
}
}
}
This will play first sound instantly, second one after 2s, third after 4s and so on. Hope it helps!
There you have a example with a for
loop and setTimeout
:
for (s = 0; s <= 2; s++) {
setTimeout(function() { console.log('hello world'); },2000*s);
}
OK It seems that memory accessing is messing a bit around here. Try to do it like this.
First create a function to do what you want to do after waiting:
var delayedPlay = function(c,delay) {
setTimeout(
function() { playAudio(c); },
delay);
}
Then call it inside the for
loop:
function randomSimon() { //Adds one random button to the order and saves the order.
var randomBtn = btns[Math.floor(Math.random() * 4)]; //Adds the random button.
randomOrder += randomBtn; //Saves the random order.
for (i = 0; i <= randomOrder.length - 1; i++) { //this should play all the audios one by one according the saved order
for (s = 0; s <= i; s++) {
var someText = "";
someText += randomOrder.charAt(s);
>>>>>>> delayedPlay(randomOrder.charAt(s),2000*s);
document.getElementById('debug').innerHTML = someText; //this is for debugin, should be ignored.
}
}
}
Upvotes: 1
Reputation: 1849
So you want to have a pause after each playAudio call?
I would still go for timeouts
var sounds = {};
sounds.a = ...;
sounds.b = ...;
function playAudio(sound, callback) {
if (typeof sounds[sound] === "undefined") {
throw "sound not available";
}
sounds[sound].play();
if (typeof callback !== "undefined") {
window.setTimeout(callback, 500);
}
}
// play a - pause - b - pause c
playAudio("a", function(){
playAudio("b", function() {
playAudio("c");
});
});
if you build the sequence first you can do this dynamic too
var sequence = ["a", "b", "c"];
var pointer = 0;
playAudio(sequene[pointer], function() {
pointer += 1;
if (typeof sequence[pointer] !== "undefined") {
playAudio(sequence[pointer], this); // this will be bound to the function itself
} else {
alert("sequence finished");
}
});
this is not tested but it should work, let me know if not.
Upvotes: 1