Search code examples
javascripthtmlscopevar

Variables undefined and onclick/onkeydown events working together


I am only asking on here because I feel like no matter what I look up, I am not getting an answer to my issues. Also, my Professor barely knows the material and does not email back or show up to his office. He is no help to any of the students, so I need some help, Please!

We are to write a JavaScript code that will display a randomly generated math equation upon the page loading up. The user then puts in their answer and either hits enter OR clicks the submit button. I am then supposed to compare the total of the random generated number and the users answer and print out a certain text for correct or incorrect. If the user got it correct, there is a 5 second delay and then a new equation needs to be displayed.

With all that said, my issue right now is my variables keep showing up as undefined. I am creating the random equation upon the screen loading, but if I try and pass the total to a new function to compare, I just get undefined over and over. This is where my teacher has not taught us anything about scope, or code that goes over just one function. I feel like I have tried every way that I know of, as well as things I have looked up online. Any ideas on what I am doing wrong? Or any help to just educate me on knowing when you need multiple functions and variable scope? TIA

window.onload = display();

function display() {
    var max = 10;
    var random1 = Math.floor((Math.random() * Math.floor(max)));
    var random2 = Math.floor((Math.random() * Math.floor(max)));
    var total = random1 + random2;
    //console test
    console.log(random1);
    console.log(random2);
    document.getElementById('output').innerHTML = random1 + ' + ' + random2 + " = ";
    compare(total); //I don't want this because then it doesn't wait for the onclick or the onkeydown events to happen before comparing.
}

function checkKey() {
    if (event.keyCode == 13) {
        compare();
    }
}

function compare(total) {
    var answer = document.getElementById('userAnswer').value;
    console.log(answer);
    console.log(total);
//    if (answer === total) {
//        document.getElementById('wrongRight').innerHTML = "Correct! A new equation will display shortly.";
//    } else {
//        document.getElementById('wrongRight').innerHTML = "Incorrect, Please try again";
//    }
}

And here is my html just so you can see what elements I am accessing. I don't have any CSS right now.

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Multiplication</title>
    <script src="math.js" defer></script>
</head>
<body>
   <h2>Below is a randomly generated equation. Please enter your answer</h2>

   <p id="output">testing field for equation</p>
   <input type="text" id="userAnswer" onkeydown="checkKey()" autofocus>
   <button id="submitAnswer" onclick="compare()">Submit Answer</button>

</body>
</html>

Here also is his requirements for the assignment, incase you are confused with where I am going or what is necessary. This is a beginner javascript class and like I said, he does not even know the syntax and has to constantly look things up.

  1. Write a program that will help students learn multiplication. Use Math.random to produce two positve one-digit integers and display the question on an html document. The student will then type in an answer in a form textbox (not a pop-up) and get a response either saying something like "Good!" or "No. Please Try Again". Generate at least 2 variations on the negative responses so that the student will get some variation. Once the student gets the answer right they should get a new question. Check out this screencast to see how it should function: http://screencast.com/t/BuF7iNtrL (Links to an external site.)Links to an external site. Other things that should work:

  2. The input box should receive the focus when the page loads.

  3. The message associated with a wrong answer should display red.
  4. The message associated with a right answer should display in green.
  5. The user should be able to submit the answer either by clicking on a submit button or by hitting the return key.
  6. There should be a three second pause after the green message is displayed and before a new equation is shown.

And don't help if all you are going to do is hate. I'm a noob, and really want to get good with JavaScript, so I need to ask questions.


Solution

  • So, the issue you are facing is that the var total is scoped to the function it is defined in. (Learn more about var scoping.) To fix, you just need to make total be globally available:

    window.onload = display();
    var total;
    
    function display() {
        var max = 10;
        var random1 = Math.floor((Math.random() * max));
        var random2 = Math.floor((Math.random() * max));
        total = random1 + random2;
        document.getElementById('output').innerHTML = random1 + ' + ' + random2 + " = ";
    }
    
    function checkKey() {
        if (event.keyCode === 13) {
            compare();
        }
    }
    
    function compare(total) {
        var answer = document.getElementById('userAnswer').value;
    
        if (answer === total) {
            document.getElementById('wrongRight').innerHTML = "Correct! A new equation will display shortly.";
        } else {
            document.getElementById('wrongRight').innerHTML = "Incorrect, Please try again";
        }
    }
    

    Also, small nit: Math.floor(10) is equal to 10, so no reason to do the Math.floor around max.