Функция не остановится

0

У меня, похоже, очень плохо с моим кодом. В первый раз, когда я назвал функцию битвы, она работает нормально, но во второй раз, когда я ее вызываю, он просто использует параметр, который был передан во время первого вызова. Я думаю, что функция все еще работает от первого вызова. Вот мой код, в котором я пытался только поместить существенные части:

var player = {
    // Name
    // Position
    totalHealth: 20, // total Health
    currentHealth : 20, // current Health
    Level: 1, // Level
    // Defense
    // Attack
    // Luck
    Win: false,
    EXP: 0,
    EXPNeededCalculation: function (Level) {
        return (Level * 100) - player.EXP;
    },
    EXPGainedCalculation: function (opponentLevel, playerCurrentHealth, playerTotalHealth) {
        return player.EXP += Math.ceil(opponentLevel * 10 - ((playerTotalHealth - playerCurrentHealth) / 2));
    },
    // Items are in an object {Description:  powers, used : false, use() : yadayadayada}
    DefenseDoubled: false,
    attack: function (Attack, Luck, opponentDefense) {
        var possibleAttacks = [];
        var possibleDefense = [999]; // arbitrary number to fill one space
        for (var i = 0 ; i < Luck ; i++) {
            possibleAttacks.push(Math.ceil(Math.random() * Attack));
        };
        possibleAttacks.sort(); 
        var a = Math.ceil(Math.random() * 10);
        if (a > 7) {
            for (var x = 0 ; x < opponentDefense ; x++) {
                possibleDefense.push(Math.floor(Math.random() * opponentDefense) - 1);
            };
        }
        possibleDefense.sort(); 
        if (possibleDefense[0] <= 0) {
            var b = 0;
        } else {
            var b = 998; // arbitrary number
        }

        if (b === 0) {
            player["attackDamage"] = 0;
        } else {
            player["attackDamage"] = possibleAttacks[possibleAttacks.length - 1];
        }


    },
    defend: function() {
        player.Defense *= 2;
        player.DefenseDoubled = true;
    },
    undefend: function() {
        player.Defense /= 2;
        player.DefenseDoubled = false;
    }
};

function opponent(Level, Type, Name) {
    this.Name = Name;
    this.Level = Level;
    this.Type = Type;
    this.Health = calcHealth(Level);
    this.currentHealth = calcHealth(Level);
    this.Defense = calcStats(Level, Type);
    this.Attack = calcStats(Level, Type);
    this.Luck = calcStats(Level, Type);
    this.attackDamage =  0;
    this.DefenseDoubled = false;
    this.Poisoned = false;
    this.Burned = false;
    this.Frozen = false;

    function calcHealth(Level) {
        this.Health = Level * 5;
        this.currentHealth = this.Health;
        return this.Health; return this.currentHealth;
    };

    function calcStats(Level, Type) {
        this.Defense = Level * 2;
        this.Attack = Math.ceil(Level * 1.5);
        this.Luck = Math.ceil(Level * 1.25);
        return this.Defense ; return this.Attack ; return this.Luck; 
        if (Type === "snake" || Type === "Snake") {
            this.Luck += 1;
        }
    };
    this.attack = function(Attack, Luck, playerDefense) {
        var possibleAttacks = [];
        var possibleDefense = [999]; // arbitrary number to fill one space
        for (var i = 0 ; i < Luck ; i++) {
            possibleAttacks.push(Math.ceil(Math.random() * Attack));
        };
        possibleAttacks.sort(); 
        var a = Math.ceil(Math.random() * 10);
        if (a > 7) {
            for (var x = 0 ; x < playerDefense ; x++) {
                possibleDefense.push(Math.floor(Math.random() * playerDefense) - 1);
            };
        } 
        possibleDefense.sort(); 
        if (possibleDefense[0] <= 0) {
            var b = 0;
        } else {
            var b = 998; // arbitrary number
        }
        if (b === 0) {
            this.attackDamage = 0;
        } else {
            this.attackDamage = possibleAttacks[possibleAttacks.length - 1];
        }
    };

    this.defend = function() {
        this.Defense *= 2;
        this.DefenseDoubled = true;
    };
    this.undefend = function() {
        this.Defense /= 2;
        this.DefenseDoubled = false;
    }
}
$yesButton.click(function() {
yPressed = true;
if (value === 4 && yPressed === true) {
        addToValue(1);
        yPressed = false;
        $showBattleSummaryBox();
        $statsBox.append("<p class='center'>Health: " + player.totalHealth + "</p>");
        $battleSummaryBox.append("<p id='playersHealth' class='center'>Your Health: " + player.currentHealth + "/" + player.totalHealth + "</p>");
        $outputBox.append("<p>On the right is your Battle Summary Box. Your health has also shown up. If your health reaches zero, then you will faint, but if your enemy health reaches zero, then you win.</p>");
        $outputBox.append("<p>Battles are turn-based. You will make an action and then your opponent will. During your turn, you can either attack, defend, or use an item.</p>");
        $outputBox.append("<p>I happen to have a level 1 python for you to practice with. </p>");
        scroll($outputBox);
        var e1 = new opponent(1, "snake", "Python"); 
        $battleSummaryBox.append("<p id='opponentsHealth' class='center'>Enemy Health: " + e1.currentHealth + "/" + e1.Health + "</p>");
        $showBattleCommandBox();
        battle(e1);
    } 
});

function battle(opponent) {
    $battleOutputBox.append("<p>You make the first move!</p>");
    $("#opponentsHealth").text("Enemy Health: " + opponent.currentHealth + "/" + opponent.Health);
    battleInProgress = true;
    $attackButton.click(function () {
        if (player.Win === false && battleInProgress === true) {
            player.attack(player.Attack, player.Luck, opponent.Defense);

            // additional Item effects
            if (player.Items.hasOwnProperty("Poison Arrows")) {
                var e = Math.ceil(Math.random() * 10); 
                if (e > 7) {
                    opponent.Poisoned = true;
                }
            } else if (player.Items.hasOwnProperty("Fire Blade")) {
                var e = Math.ceil(Math.random() * 10); 
                if (e > 7) {
                    opponent.Burned = true;
                    player.attackDamage += 3;
                }
            } else if (player.Items.hasOwnProperty("Blade of Luck")) {
                var e = Math.ceil(Math.random() * 10); 
                if (e > 7) {
                    player.attackDamage += 1;
                } 
            }

            opponent.currentHealth -= player.attackDamage;
            $("#opponentsHealth").text("Enemy Health: " + opponent.currentHealth + "/" + opponent.Health);
            if (player.attackDamage === 0) {
                $battleOutputBox.append("<p>Your attack has been blocked</p>");
            } else {
                $battleOutputBox.append("<p>You inflicted " + player.attackDamage + " damage.</p>");
                scroll($battleOutputBox);
            }
            if (opponent.DefenseDoubled === true) {
                opponent.undefend();
            }
            if (opponent.Poisoned === true) {
                Poison();
            } else if (opponent.Burned === true) {
                Burn();
            } else if (opponent.Frozen === true) {
                Freeze();
            } 
            if (opponent.currentHealth <= 0) {
                player.Win = true;
                return postBattle(opponent);
            } else {opponentTurn();}
        }
    });

    $defendButton.click(function () {
        if (player.Win === false && battleInProgress === true) {
            player.defend();
            $battleOutputBox.append("<p>Your defense has been doubled for one turn.</p>");
            if (opponent.DefenseDoubled === true) {
                opponent.undefend();
            }
            if (opponent.Poisoned === true) {
                Poison();
            } else if (opponent.Burned === true) {
                Burn();
            } else if (opponent.Frozen === true) {
                Freeze();
            } 
            if (opponent.currentHealth <= 0) {
                player.Win = true;
                return postBattle(opponent);
            } else {opponentTurn();}
        }
    }); 

    $useItemButton.click(function () {
        if (player.Win === false && battleInProgress === true) {
            if ($useItemSelection.html().length > 15) {
                var itemBeingUsed = $("select[name='useItemSelection'] option:selected").text();
                if (itemBeingUsed === "Book of Spells" && player.Items.bookOfSpells.used === false) {
                    player.Items.bookOfSpells.use();
                    console.log(player.Items.bookOfSpells.effect);
                    if (player.Items.bookOfSpells.effect === "burn" || player.Items.bookOfSpells.effect === "poison") {
                        $battleOutputBox.append("<p>You have " + player.Items.bookOfSpells.effect + "ed " + opponent.Name + ".</p>");
                        if (player.Items.bookOfSpells.effect === "burn") {
                            opponent.Burned = true;
                        } else {
                            opponent.Poisoned = true;
                        }
                    } else {
                        $battleOutputBox.append("<p>You have froze " + opponent.Name + ".</p>");
                        opponent.Frozen = true;
                    }
                    player.Items.bookOfSpells.used = true;
                } else if (itemBeingUsed === "Shield Charm" && player.Items.shieldCharm.used === false) {
                    player.Items.shieldCharm.use();
                    $battleOutputBox.append("<p>You will block the next attack with your shield charm.</p>");
                    player.Items.shieldCharm.used = true;
                }
                if (opponent.Poisoned === true) {
                    Poison();
                } else if (opponent.Burned === true) {
                    Burn();
                } else if (opponent.Frozen === true) {
                    Freeze();
                } 
                if (opponent.currentHealth <= 0) {
                    player.Win = true;
                    return postBattle(opponent);
                } else {opponentTurn();}
            } else {
                var noUsableItemP = $("<p id='noUsableItemP'>You have no usable items. Select another command.</p>");
                $battleCommandPromptDiv.empty();
                $battleCommandPromptDiv.append(noUsableItemP);
            }
        }
    });

    function opponentTurn() {

        var c = Math.round(Math.random() * 10);
        if (c > 5) {
            opponent.attack(opponent.Attack, opponent.Luck, player.Defense);
            if (player.Items.hasOwnProperty('shieldCharm')) {
                if (player.Items.shieldCharm.active) {
                    var d = 0;
                    player.Items.shieldCharm.active = false;
                } else {
                    var d = opponent.attackDamage;
                }
            } else {
                var d = opponent.attackDamage;
            }
            player.currentHealth -= d;
            $("#playersHealth").text("Your Health: " + player.currentHealth + "/" + player.totalHealth);
            if (d === 0) {
                $battleOutputBox.append("<p class='right'>You have blocked the attack.</p>");
            } else {
                $battleOutputBox.append("<p class='right'>" + d + " damage has been inflicted upon you.</p>");
                scroll($battleOutputBox);
            }
        } else {
            opponent.defend();
            $battleOutputBox.append("<p class='right'>" + opponent.Name + " has doubled his defense for one turn.</p>");
        }
        if (player.DefenseDoubled === true) {
            player.undefend();
        }
        if (player.currentHealth <= 0) {
            postBattle(opponent);
        }
    }
    function Poison() {
        opponent.currentHealth -= 1;
        $("#opponentsHealth").text("Enemy Health: " + opponent.currentHealth + "/" + opponent.Health);
        $battleOutputBox.append("<p> " + opponent.Name + " was hurt by poison.</p>");
        scroll($battleOutputBox);
        $("#opponentStatus").empty();
        $("#opponentStatus").append("<p style='color: green;' id='status'>Poisoned</p>");
    }
    function Burn() {
        opponent.currentHealth -= 1;
        $("#opponentsHealth").text("Enemy Health: " + opponent.currentHealth + "/" + opponent.Health);
        $battleOutputBox.append("<p> " + opponent.Name + " was hurt by burn.</p>");
        scroll($battleOutputBox);
        $("#opponentStatus").empty();
        $("#opponentStatus").append("<p style='color: red;' id='status'>Burned</p>");
    }
    function Freeze() {
        opponent.currentHealth -= 1;
        $("#opponentsHealth").text("Enemy Health: " + opponent.currentHealth + "/" + opponent.Health);
        $battleOutputBox.append("<p> " + opponent.Name + " was hurt by freeze.</p>");
        scroll($battleOutputBox);
        $("#opponentStatus").empty();
        $("#opponentStatus").append("<p style='color: blue;' id='status'>Frozen</p>");
    }
}

function postBattle(opponentBattled) {
    if (player.Win === true) {
        addToValue(1); 
        inMaze = distance > 5 ? true : false;
        $battleOutputBox.append("<p>You have won! You have gained " + player.EXPGainedCalculation(opponentBattled.Level, player.currentHealth, player.totalHealth) + " EXP. You need " + player.EXPNeededCalculation(player.Level) + " EXP to level up.</p>");
        $battleOutputBox.append("<p>Click Yes to continue.</p>");
        scroll($battleOutputBox);
        player.Win = false;
        battleInProgress = false;
    } else { 
        $battleOutputBox.append('<p>You have fainted. Refresh to start over.</p>');
        // Fix to restart quest
    }
}

var e2 = new opponent(1, "Snake", "Rattler");  
inMaze = false;
battle(e2);
Теги:
function

2 ответа

2
Лучший ответ

В вашей battle функции вы привязываетесь к обработчикам кликов. Эти обработчики никогда не сбрасываются. Если вы снова вызовете battle, вы привяжете дополнительные обработчики, вы не замените их. В результате у вас теперь есть 2 набора обработчиков, один со старым opponent и один с новым. Оба будут стрелять.

  • 0
    Как вы освобождаете обработчик или заменяете их?
  • 0
    Вы можете использовать off или off unbind .
Показать ещё 2 комментария
1

Для приложений с одной страницей очень рекомендуется использовать:

$(selector").off("click").on("click", function(){/* handler */});

В противном случае вы связываете несколько событий с одним и тем же элементом.

  • 0
    Я просто хотел бы быть осторожным, так как это отменит все обработчики кликов. Я бы предложил использовать пространство имен, чтобы гарантировать только удаление соответствующих обработчиков. Отключенная документация содержит некоторую информацию о пространствах имен.

Ещё вопросы

Сообщество Overcoder
Наверх
Меню