Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

When running a function again it does not read global array

I'm quite a beginner at coding and StockOverflow. This is my first post ever so please pardon if my post is not formatted correctly as I am only a junior in high school. On that note however, I had a question regarding my code below. Just a little background, this code is supposed to generate a list of fortunes and append each fortune, then once it has gone through the whole list, it regenerates a new one in a random order. (refer to code below) The problem occurs during anotherFortune(). When this function reruns generateFortuneCookie(), for a SECOND time it does not seem to pull any values from the fortunesList array. It console.logs as, "You will ." Also, it does not regenerate a third list, google chrome gives the error below.

app.js:33 Uncaught TypeError: Failed to execute 'appendChild' on 'Node': parameter 1 is not of type 'Node

When the button is clicked after about 10 times. Please note that I have not learned jQuery yet, so any solutions I would prefer a JavaScript solution.

JavaScript code below:

    var fortunesList = ["die 2mrrw", "find a dollar", "become poor", "jump off a cliff", "turn into Batman"];
    //if any fortunes are added to the list above, make sure to change "for loop" paramter one value (var i = " ";) and stats function at bottom
    function generateFortuneCookie(){ //runs for the first time button is pressed
      var cloneList = fortunesList.slice();

      //randomizer for fortunes
      var randomFortune = " ";
      for (var i = 4; i >= 0; i--){       
        randomFortune = cloneList.splice(Math.floor(Math.random() * (i + 1)), 1); //(i + 1) ensures 5 values are returned since the last value in math.random is excluded
        console.log("You will " + randomFortune + ".");
        //temporarily stores random list
        var tempCache = document.getElementById("fortune-cache");
        var nodeone = document.createElement("DIV");
        nodeone.innerText = "You will " + randomFortune + ".";
        tempCache.appendChild(nodeone);
      }

      //changes button to prevent a new list of variables from being created
      document.getElementById("first").style.display = "none";
      document.getElementById("second").style.display = "block";

      //appends last fortune from "fortune-cache" into "fortune-cookie-text"
      var cookieText = document.getElementById("fortune-cookie-text");
      var nodetwo = tempCache.lastChild;
      cookieText.appendChild(nodetwo);
    }

    var count = 0;
    var max = fortunesList.length;
    //variables above pertain to the "count" function that reruns the "generateFortuneCookie()" function
    var heightCount = 0;
    //must be seperate and increase OUTSIDE of function, determines div height (dynamicDiv)
    function anotherFortune(){ //this should run only after the first fortune is produce
      var cookieText = document.getElementById("fortune-cookie-text"); //this variable MUST go before nodethree otherwise if declared after, nodethree won't recognize variable
      //appends text from "fortune-cookie-text" to "previous-fortunes", this must be run first before adding new text from tempCache
      var nodethree = document.createElement("LI");
      nodethree.appendChild(cookieText.lastChild); 
      document.getElementById("previous-fortunes").appendChild(nodethree);

      //button counter
      count++
      //console.log(count);
      if(count == max){ //once it runs out of fortunes, it will regenerate a new list
        generateFortuneCookie();
        count = 0; //resets count back to zero
      }

      //this increases div height as list increases
      var dynamicDiv = document.getElementById("other-fortunes-div");
      var height = dynamicDiv.clientHeight;
      heightCount++
      //console.log(heightCount);
      if(heightCount >= 2){
        dynamicDiv.style.height = height + 1 + "px";
      }

  //appends text from "fortune-cache" into "fortune-cookie-text", runs after appending text into "previous-fortunes"
  var tempCache = document.getElementById("fortune-cache");
  var nodetwo = tempCache.lastChild;
  cookieText.appendChild(nodetwo);
}

HTML code below:

<!DOCTYPE html>
<html>
<head>
  <title>Fortune Cookie Gen</title>
  <script type="text/javascript" src="./JS/app.js"></script>
  <link rel="stylesheet" type="text/css" href="./CSS/styles.css">
  <meta charset="utf-8">
</head>
<body>
  <button onclick="generateFortuneCookie()" id="first">Make My Fortune!</button>
  <button onclick="anotherFortune(); stats();" id="second">Generate Another Fortune!</button>
  <div id="fortune-cache">
  </div>
  <div id="fortune-cookie-text">
    <h3>Your Fortune</h3>
  </div>
  <div id="other-fortunes-div">
    <h3>Previous Fortunes</h3>
      <ul id="previous-fortunes">
      </ul>
  </div>
  <div id="statistics">
    <h3>Fortune Statistics</h3>
    <div id="one">

    </div>
    <div id="two">

    </div>
    <div id="three">

    </div>
    <div id="four">

    </div>
    <div id="five">

    </div>
  </div>
</body>
</html>
like image 484
zak Avatar asked Nov 08 '22 04:11

zak


1 Answers

Because of the splice method your fortunesList list is being "cut" and drops its elements so after the first call of generateFortuneCookie() the array gets emptied. My suggestion is you use a temp array at the beginning of generateFortuneCookie() and pass fortunesList elements to the the temp array each time generateFortuneCookie() is called.

And just in case my explanation sucks just add this line to generateFortuneCookie()

var tempList = fortunesList;

and replace every fortunesList reference in generateFortuneCookie() with tempList.

Alternatively, you can you use slice instead of splice

Let me know if this worked for you.

UPDATE

Ok, I decided to use a clone list of your fortuneList and it seems to work.

function generateFortuneCookie(){ //runs for the first time button is pressed
  var cloneList = fortunesList.slice();
  //randomizer for fortunes
  var randomFortune = " ";
  for (var i = 4; i >= 0; i--){       
    randomFortune = cloneList.splice(Math.floor(Math.random() * (i + 1)), 1); //(i + 1) ensures 5 values are returned since the last value in math.random is excluded
    console.log("You will " + randomFortune + ".");
    //temporarily stores random list
    var tempCache = document.getElementById("fortune-cache");
    var nodeone = document.createElement("DIV");
    nodeone.innerText = "You will " + randomFortune + ".";
    tempCache.appendChild(nodeone);
  }

  //changes button to prevent a new list of variables from being created
  document.getElementById("first").style.display = "none";
  document.getElementById("second").style.display = "block";

  //appends last fortune from "fortune-cache" into "fortune-cookie-text"
  var cookieText = document.getElementById("fortune-cookie-text");
  var nodetwo = tempCache.lastChild;
  cookieText.appendChild(nodetwo);
}
like image 63
catchiecop Avatar answered Nov 14 '22 22:11

catchiecop