Learn Basic JavaScript by Building a Role Playing Game - Step 118

Tell us what’s happening:

So the above code is Correct and works, but i do not understand where is [fighting] coming from.
i know i’ve declared the

let fighting;

but how does it work? does it work like an index value for monsters?
in the previous functions, fighting selected the monsters, 0 was slime, 1 was fanged beast and 2 was dragon. But the properties for monsters are in monster array, and fighting is just a declared let. Why monsters[fighting].name and not monsters.name?

please explain , I just started with Javascript. Sorry if this sounds obvious, but i want to understand even if i can manage to pass this challenge.

Your code so far

Step 118

Now, set the innerText property of monsterName to be the name property of the current monster. Do the same for monsterHealthText and the health property.

function goFight() {
update(locations[3]);
monsterHealth = monsters[fighting].health;
monsterStats.style.display = “block”;
monsterName.innerText = monsters[fighting].name;
monsterHealthText.innerText = monsterHealth;

}

WARNING

The challenge seed code and/or your solution exceeded the maximum length we can port over from the challenge.

You will need to take an additional step here so the code you wrote presents in an easy to read format.

Please copy/paste all the editor code showing in the challenge from where you just linked.

let xp = 0;
let health = 100;
let gold = 50;
let currentWeapon = 0;
let fighting;
let monsterHealth;
let inventory = ["stick"];

const button1 = document.querySelector('#button1');
const button2 = document.querySelector("#button2");
const button3 = document.querySelector("#button3");
const text = document.querySelector("#text");
const xpText = document.querySelector("#xpText");
const healthText = document.querySelector("#healthText");
const goldText = document.querySelector("#goldText");
const monsterStats = document.querySelector("#monsterStats");
const monsterName = document.querySelector("#monsterName");
const monsterHealthText = document.querySelector("#monsterHealth");
const weapons = [
  { name: 'stick', power: 5 },
  { name: 'dagger', power: 30 },
  { name: 'claw hammer', power: 50 },
  { name: 'sword', power: 100 }
];
const monsters = [
  {
    name: "slime",
    level: 2,
    health: 15
  },
  {
    name: "fanged beast",
    level: 8,
    health: 60
  },
  {
    name: "dragon",
    level: 20,
    health: 300
  }
]
const locations = [
    {
        name: "town square",
        "button text": ["Go to store", "Go to cave", "Fight dragon"],
        "button functions": [goStore, goCave, fightDragon],
        text: "You are in the town square. You see a sign that says \"Store\"."
    },
    {
        name: "store",
        "button text": ["Buy 10 health (10 gold)", "Buy weapon (30 gold)", "Go to town square"],
        "button functions": [buyHealth, buyWeapon, goTown],
        text: "You enter the store."
    },
    {
        name: "cave",
        "button text": ["Fight slime", "Fight fanged beast", "Go to town square"],
        "button functions": [fightSlime, fightBeast, goTown],
        text: "You enter the cave. You see some monsters."
    },
    {
        name: "fight",
        "button text": ["Attack", "Dodge", "Run"],
        "button functions": [attack, dodge, goTown],
        text: "You are fighting a monster."
    }
];

// initialize buttons
button1.onclick = goStore;
button2.onclick = goCave;
button3.onclick = fightDragon;

function update(location) {
  button1.innerText = location["button text"][0];
  button2.innerText = location["button text"][1];
  button3.innerText = location["button text"][2];
  button1.onclick = location["button functions"][0];
  button2.onclick = location["button functions"][1];
  button3.onclick = location["button functions"][2];
  text.innerText = location.text;
}

function goTown() {
  update(locations[0]);
}

function goStore() {
  update(locations[1]);
}

function goCave() {
  update(locations[2]);
}

function buyHealth() {
  if (gold >= 10) {
    gold -= 10;
    health += 10;
    goldText.innerText = gold;
    healthText.innerText = health;
  } else {
    text.innerText = "You do not have enough gold to buy health.";
  }
}

function buyWeapon() {
  if (currentWeapon < weapons.length - 1) {
    if (gold >= 30) {
      gold -= 30;
      currentWeapon++;
      goldText.innerText = gold;
      let newWeapon = weapons[currentWeapon].name;
      text.innerText = "You now have a " + newWeapon + ".";
      inventory.push(newWeapon);
      text.innerText += " In your inventory you have: " + inventory;
    } else {
      text.innerText = "You do not have enough gold to buy a weapon.";
    }
  } else {
    text.innerText = "You already have the most powerful weapon!";
    button2.innerText = "Sell weapon for 15 gold";
    button2.onclick = sellWeapon;
  }
}

function sellWeapon() {
  if (inventory.length > 1) {
    gold += 15;
    goldText.innerText = gold;
    let currentWeapon = inventory.shift();
    text.innerText = "You sold a " + currentWeapon + ".";
    text.innerText += " In your inventory you have: " + inventory;
  } else {
    text.innerText = "Don't sell your only weapon!";
  }
}

function fightSlime() {
  fighting = 0;
  goFight();
}

function fightBeast() {
  fighting = 1;
  goFight();
}

function fightDragon() {
  fighting = 2;
  goFight();
}

Your browser information:

User Agent is: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36

Challenge Information:

Learn Basic JavaScript by Building a Role Playing Game - Step 118

@serbanescuclaudiu93

Hey there,

It’s common for us to face challenges similar to this throughout our learning curve, and you need not be sorry for that.

Regarding your quesiton, the assumption you made was correct. The variable
fighting will indeed act as index for the monsters array.

Let’s break down what happens, step by step:

Initailly we begin from the below shown interface:

star

When we click on button2 - Go to cave , we reach this updated interface as shown below:

second

Now, let’s say, we clicked button1 - Fight slime, which will trigger/call the function fightSlime()

function fightSlime() {
  fighting = 0;
  goFight();
}

Now, as the first step in executing the function, the variable fighting will be assigned to 0, which is to be noted will be reflected anywhere from this point on code as it was declared using let in global scope(i.e. It can be accessed and re-assigned anywhere on this JS file).

Followed by that, the function goFight() is called.

function goFight() {
  update(locations[3]);
  monsterHealth = monsters[fighting].health;
  monsterStats.style.display = "block";
  monsterName.innerText = monsters[fighting].name;
  monsterHealthText.innerText = monsterHealth;
}

Now, as the first step of executing the goFight() function, the update(locations[3]) is called, follwed by 3 updates:

  1. Assigning the display property of monsterStats from none to block.

  2. Updating the value of monsterName from '' to monsters[fighting].name which is same as monsters[0].name, as fighting is assigned as 0 . Element at index 0 of array monsters is an object, that has "slime" value for its name property as shown below . Thus monsterName will be assigned as "slime".

{
    name: "slime",
    level: 2,
    health: 15
  }
  1. Updating the value of monsterHealthText from '' to monster[fighting].health, which following the similar procedure as above, results in assigning monsterHealthText as 15.

and atlast we’ll reach an updated interface as shown below:

last

I hope my reply was helpful. Feel free to post your further queries, if there’s any. I will try my best replying them.

Happy Coding :keyboard: !

2 Likes

Thank you for taking the time to write this!
Very well explained!

1 Like

well I understand it thanks.
but instead of making a variable called fighting and assign it the index value for the arry and use in the function like
function fightSlime() {
fighting = 0;
goFight();
}
can’t we just write 0 as it’s index in the monsters array.

monsterHealth = monsters[0].health;

instead of

monsterHealth = monsters[fighting].health;

@cyruss747

Hey there,

The catch here is, irrespective of what monster the player is trying to fight, the moment the player clicks the fight button(Fight slime or Fight fanged beast) , its the goFight() function that is going to be called.

Lets say we’ve defined monsterHealth inside goFight() as:

monsterHealth = monsters[0].health;

and a player clicks Fight fanged beast button, which will tigger goFight() function and this will result in setting the monsterHealth value to monster[0].health which is slime’s health and not fanged beast’s health. The same applies for monsterName also.

So it is essential to dynamically define the goFight() function with respect to fighting variable.

Hope you got your answer. If not feel free to reply/query further.

Happy Coding :keyboard: !

1 Like