我写了这个函数来显示我正在制作的西蒙游戏的闪光灯。闪烁的部分正在工作,但我每次move.color.backgroundColor === colors[0]
尝试播放声音,这是突出显示的颜色。对于我来说,数组的循环速度太快了,而且我尝试解决这些不同的方法时遇到了几个不同的错误,包括在闪烁完成之前所有声音都响起,因为for循环变量完成了更快的循环比变量显示闪烁然后打破闪烁功能,即使它应该在每个循环1秒。这是代码 -
game.computerMoves = {green, blue, blue, red, red, yellow};
const colors = [
new Map([[green, "lime"], [yellow, "#FF6"], [blue, "dodgerblue"], [red, "salmon"]]),
new Map([[green, "green"], [yellow, "#CC0"], [red, "red"], [blue, "blue"]])
];
const sounds = {
green : new Audio("https://s3.amazonaws.com/freecodecamp/simonSound1.mp3"),
blue : new Audio("https://s3.amazonaws.com/freecodecamp/simonSound4.mp3"),
yellow : new Audio("https://s3.amazonaws.com/freecodecamp/simonSound3.mp3"),
red : new Audio("https://s3.amazonaws.com/freecodecamp/simonSound2.mp3")
};
game.computerMoves = {green, yellow, yellow, blue, red, red};
const colorFlashPeriod = 1000; // in ms
function showMoves() {
let moveCounter = 0;
const timeoutCount = game.computerMoves.length * 2;
(function nextColor() {
//this variable was finished looping before the backgroundColor finished flashing and it incremented faster than 1 second per loop. The flashing was shown at the correct times though, but I can't use this to set keys to add sounds
let move = game.computerMoves[moveCounter >> 1];
let c = game.computerMoves[moveCounter]
console.log(c.id);
move.style.backgroundColor = colors[(moveCounter++) & 1].get(move);
if (moveCounter < timeoutCount) { setTimeout(nextColor, colorFlashPeriod) }
})();
}
我还重写了showMoves函数,将闪光灯变成了工作版本
function showMoves() {
let i = 0;
const start = setInterval(function() {
if (i >= game.computerMoves.length) {
clearInterval(start);
return;
}
const move = game.computerMoves[i];
setLight(move, true);
setTimeout(setLight.bind(null, move, false), 1000); //Using bind to preset arguments
i++;
}, 2000);
}
function setLight(color, isOn) {
if(isOn){
sounds[color.id].play();
}
color.style.backgroundColor = isOn ? colors[0].get(color) : colors[1].get(color);
}
这个版本正在按照我想要的方式工作并在正确的闪烁时间播放声音,但我不确定它的设计是否比我上面的showMoves功能设计得更好我无法弄清楚如何让声音发挥作用。我很感激任何帮助。
以下是完整代码,但您必须在控制台中激活这些功能才能查看问题。 randomMoves(num)
设置showMoves()
的随机数组,以查看我遇到问题的闪烁灯。:
const simonHTML = {
power : document.querySelector('.powerButton'),
strictButton : document.getElementById('strict'),
startButton : document.getElementById('start'),
displayScore : document.getElementById('score'),
colors : document.getElementsByClassName('color')
}
const game = {
on : false,
start : false,
strict : false,
score : 0,
computerMoves : [],
playerMoves : [],
colors : [greenBox = document.getElementById('green'),
blueBox = document.getElementById('blue'),
yellowBox = document.getElementById('yellow'),
redBox = document.getElementById('red')]
}
//move the purple div back and forth
function turnOn () {
if(!game.on){
simonHTML.power.classList.add('moveRight');
simonHTML.power.classList.remove('moveLeft')
game.on = true;
simonHTML.displayScore.textContent = game.score.toString();
}
else if(game.on){
simonHTML.power.classList.remove('moveRight');
simonHTML.power.classList.add('moveLeft');
game.on = false;
simonHTML.displayScore.textContent = '-';
}
}
function randomMoves (num) {
for(let i = 0; i < num; i++){
let moves = game.colors[Math.floor(Math.random() * game.colors.length)]
game.computerMoves.push(moves);
}
return game.computerMoves;
}
function resetMoves () {
game.computerMoves = [];
}
const colors = [
new Map([[green, "lime"], [yellow, "#FF6"], [blue, "dodgerblue"], [red, "salmon"]]),
new Map([[green, "green"], [yellow, "#CC0"], [red, "red"], [blue, "blue"]])
];
const sounds = {
green : new Audio("https://s3.amazonaws.com/freecodecamp/simonSound1.mp3"),
blue : new Audio("https://s3.amazonaws.com/freecodecamp/simonSound4.mp3"),
yellow : new Audio("https://s3.amazonaws.com/freecodecamp/simonSound3.mp3"),
red : new Audio("https://s3.amazonaws.com/freecodecamp/simonSound2.mp3")
};
const colorFlashPeriod = 1000; // in ms
function showMoves() {
let moveCounter = 0;
const timeoutCount = game.computerMoves.length * 2;
(function nextColor() {
let move = game.computerMoves[moveCounter >> 1];
let c = game.computerMoves[moveCounter]
console.log(c.id);
move.style.backgroundColor = colors[(moveCounter++) & 1].get(move);
if (moveCounter < timeoutCount) { setTimeout(nextColor, colorFlashPeriod) }
})();
}
function playerMoveDown(e){
e.target.style.backgroundColor = colors[0].get(e.target);
let color = e.target.id;
sounds[color].play();
return game.playerMoves.push(e.target);
}
function playerMoveUp(e){
e.target.style.backgroundColor = colors[1].get(e.target);
}
for (let i = 0; i < simonHTML.colors.length; i++){
simonHTML.colors[i].addEventListener('mousedown', playerMoveDown);
simonHTML.colors[i].addEventListener('mouseup', playerMoveUp);
}
simonHTML.power.addEventListener('click', turnOn);
&#13;
*{
box-sizing: border-box;
-moz-box-sizing: border-box;
-webkit-box-sizing: border-box;
margin: 0;
padding: 0;
}
.flex-row{
width:100%;
height:100%;
display:flex;
flex-direction:row;
}
.center-options{
align-self:center;
display:flex;
flex-direction:column;
align-items:center;
}
body{
background-color: gray;
}
.centered {
position: fixed;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
}
.outer{
height: 30em;
width:30em;
background-color:rgba(21, 56, 41, 1);
display: flex;
flex-direction: row;
flex-wrap: wrap;
border-radius: 50%;
border-style: solid;
border-width: 10px;
box-shadow: 0px 0px 12px #222;
}
/*=============Color buttons=================*/
.color{
flex-grow:1;
flex-shrink: 1;
flex-basis: 50%;
position: relative;
cursor:pointer;
}
#green{
background-color:green;
border-bottom-left-radius: 100%;
border-top: 10px solid;
border-right:5px solid
}
#blue{
background-color:blue;
border-top-left-radius: 100%;
border-right:5px solid
}
#yellow{
background-color:rgb(204,204,0);
border-bottom-right-radius: 100%;
border-top: 10px solid;
border-left:5px solid;
}
#red{
background-color:red;
border-top-right-radius: 100%;
border-left: 5px solid;
}
/*=============Controller=================*/
#controller{
z-index: 1;
height:14em;
width:14em;
border-radius:100%;
background-color:gray;
border: 10px solid;
display:flex;
align-items:center;
flex-direction:column;
}
#controller h3{
margin-top:1em;
align-self: center;
font-size: 30px;
}
.options{
margin-top: .5em;
justify-content:space-evenly;
}
.on-circle{
width: 20px;
height: 20px;
background-color:red;
border: 3px solid black;
border-radius:100%;
box-shadow: 0px 2px 3px #222;
cursor: pointer;
}
/*===============off-on================*/
#onOff{
height:100%;
width:100%;
justify-content:space-evenly;
}
#onOff h4:nth-of-type(1) {
margin-top:5px;
margin-left:20px;
}
#onOff h4:nth-of-type(2) {
margin-top:5px;
margin-right:20px;
}
#onOff > div {
height:2em;
border-radius:10%;
width:4em;
background-color:#404040;
}
#onOff > div > div {
height:100%;
width:35%;
background-color:purple;
margin-left:1px;
border-radius:10%;
border:3px solid black;
cursor: pointer;
}
.moveRight{
transition: all .2s linear;
transform: translateX(2.5em);
}
.moveLeft{
transition: all .2s linear;
transform: translateX(0);
}
&#13;
<!DOCTYPE html>
<html lang='en'>
<head>
<meta charset='utf-8'>
<title>Simon Game</title>
<link rel='stylesheet' href='./main.css'>
<script type='text/javascript' src='./simon.js' async></script>
</head>
<body>
<div class='container outer centered'>
<div id = 'blue' class= 'color shade'></div>
<div id = 'red' class= 'color shade'></div>
<div id = 'controller' class='centered'>
<h3>Simon</h3>
<div class='options flex-row'>
<div class='center-options'>
<h4>Score</h4>
<h5 id='score'>-</h5>
</div>
<div class='center-options'>
<h4>Start</h4>
<div id='start' class='on-circle'></div>
</div>
<div class='center-options'>
<h4>Strict</h4>
<div id='strict' class='on-circle'></div>
</div>
</div>
<div id='onOff' class='flex-row'>
<h4>Off</h4>
<div>
<div class='powerButton'></div>
</div>
<h4>On</h4>
</div>
</div>
<div id = 'green' class= 'color shade'></div>
<div id = 'yellow' class= 'color shade'></div>
</div>
</body>
</html>
&#13;