【问题标题】:Unable to reset Boolean value - Javascript无法重置布尔值 - Javascript
【发布时间】:2019-10-20 13:05:02
【问题描述】:

我再次询问有关我正在为学校开发的西蒙游戏的一些代码的另一个问题。 我将布尔值设置为 false,游戏首先检查按键,然后将值设置为 true。如果用户得到不正确的游戏顺序,它应该将值重新设置为 false。出于某种原因,我的代码没有在需要时来回更改布尔值,我不太确定为什么。

/*************VARIABLES*************/
//store colors
var buttonColors = [
    "green", //0
    "red", //1
    "yellow", //2
    "blue" //3
]
//Game Pattern Storage
var gamePattern = [ /*Added From nextSequence*/ ];
var userClicks = [ /* Added from userClickHistory*/ ];

var level = 0;
var gameOn = false;

/******************BASIC FUNCTIONS*********************/

/*AWAIT KEYPRESS TO BEGIN GAME*/
$(document).keypress(function () {
    if (!gameOn) {
        nextSequence();
        $(`#level-title`).text(`Level: ` + level);
        var gameOn = true;
    }
});

//log user clicks after nextSequence() has executed, check the userClicks vs gamePattern using checkAnswer(lastInArray)
$(`.btn`).click(function () {
    var buttonClicked = $(this).attr(`id`);
    userClicks.push(buttonClicked);
    animate(buttonClicked);
    playSound(buttonClicked);

    checkAnswer(userClicks.length - 1);
});


function checkAnswer(usersLastClick) {
    //if the gamePatterns last call is equal to the users last click
    if (gamePattern[usersLastClick] === userClicks[usersLastClick]) {
        console.log("success");
        //if the userClicks and the gamePatterns lengths are equal, call nextSequence()
        if (userClicks.length === gamePattern.length) {
            setTimeout(function () {
                nextSequence();
                //update the titles level indicator
                $(`#level-title`).text(`Level: ` + level);
            }, 1000);
        }
    } else {
        $(`#level-title`).text(`You have made it to level ` + level + '! Hit enter to try again')
        //play sound for incorrect click
        var wrongSound = new Audio('sounds/wrong.mp3');
        wrongSound.play();
        console.log("wrong")
        console.log(`[` + userClicks + `]`);
        console.log(`[` + gamePattern + `]`);
        reset();
    }

}
/************* NEXT SEQUENCE TO PROGRESS GAME *********/
function nextSequence() {
    userClicks = [];
    level++;
    console.log(level);

    randomNumber = Math.floor(Math.random() * 4)
    randomChosenColor = buttonColors[randomNumber];
    gamePattern.push(randomChosenColor);
    animate(randomChosenColor);
    playSound(randomChosenColor);
}

function reset() {
    var level = 0;
    var gamePattern = [];
    var gameOn = false;
}


/******************** SOUNDS AND ANIMATIONS*************************************/

//buttons animations
function animate(clickedButton) {
    $(`#` + clickedButton).fadeOut(100).fadeIn(100);
};

//Play a sound in correlation to randomChosenColor
function playSound(color) {
    var sound = new Audio('sounds/' + color + '.mp3');
    sound.play();
};

当我的代码运行时,内部的布尔值没有任何变化,而且我还注意到,当游戏也应该重置时,我的数组也没有被清空。当我 console.log(gameOn) 它总是返回 false,无论游戏是否正在运行。

【问题讨论】:

  • 您两次声明 gameOn。 Javascript 变量的作用域是函数。当你将 gameOn 设置为 true 时,你有 var gameOn = true;,这是一个匿名函数,因为 var 你声明了一个新变量,而不是引用外部变量。摆脱第二个变量。
  • 您在按键处理程序中将gameOn 重新声明为局部变量。删除var
  • 您每次都在声明var gameOn =,而不是重用同一个变量。本质上,每次都创建一个新的
  • if (!gameOn) { nextSequence(); ..... var gameOn = true; } 你为什么要再次声明 gameOn 变量。您可以直接使用变量gameOn=...,因为它是在外部作用域中声明并在内部作用域中可用
  • 啊,太好了,谢谢大家,没有意识到我不需要每次都使用 var。

标签: javascript


【解决方案1】:

在您的$(document).keypress 函数中,尝试在“gameOn = true”之前取出“var”。我认为现在就好像您正在声明一个新变量,而您确实想更改全局 gameOn var。

【讨论】:

  • 在声明我的变量时,不知何故我对这个问题存在巨大的学习差距。部分原因可能是因为我很久以前就开始学习 Python 和 Ruby,并且声明变量非常不同,部分原因是在学习以前的 vanilla Javascript 版本之前尝试学习 ES6 的困惑。谢谢你的澄清。
【解决方案2】:

if (!gameOn) { nextSequence(); ..... var gameOn = true; }

不要再次声明 gameOn 变量。您可以直接使用变量gameOn=...,因为它是在函数的外部作用域中声明的,并且在内部作用域中可用

【讨论】:

    【解决方案3】:

    正如其他人所说,不要两次声明 gameOn,它应该可以解决。

    但我一直在阅读越来越多的关于 JavaScript 中全局变量“邪恶”的文章,因为全局命名空间意味着任何东西都可以编辑这些变量,甚至是其他脚本。

    很多人似乎倾向于的解决方案是将变量包装在一个对象中,如下所示:

    var globals = {
    buttonColors: [ "green", "red", "yellow", "blue"],
    gamePattern: [ /*Added From nextSequence*/ ],
    userClicks: [ /* Added from userClickHistory*/ ],
    level: 0,
    gameOn: false,
    }
    

    然后,只需使用“globals.buttonColors”来引用您的变量。

    如果您打算保持较小的范围,则不是 100% 必要,但无论如何都是一个很好的实践。

    【讨论】:

    • 我得稍微研究一下,它看起来更干净,肯定有助于避免像我一样意外重新分配
    • 是的,我看了一点,这让我大开眼界:w3schools.com/js/js_best_practices.asp 是其中之一“哦……哎呀!”当我争先恐后地改变我过去创造的很多东西的时候。
    猜你喜欢
    • 1970-01-01
    • 2012-10-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-12-15
    • 2023-03-09
    • 2018-06-30
    相关资源
    最近更新 更多