Search code examples
javascripthtmlclickaddeventlistenermouseclick-event

Why does my Javascript calculator function return "undefined" RANDOMLY, when I click on number buttons?


I'm working on a building out a fully functioning calculator in javascript. so far im able to add numbers to the display and delete numbers (both using click events).

However, for some reason, when I click on the number buttons, I randomly get "undefined" returned in the display. so using my code as an example, when i click a number button, the currNum variable is supposed to take the button value (which is a number) and append it to the display(numberDisplay). but Its giving me random undefined's instead.

Things I have tried:

  • This undefined error happens even if I delete the "deleteLastnumberFromDisplay" handler and its related clickevent.
  • inside the "addClickedNumberToDisplay" I've also tried running currNum = numberDisplay.value += e.target.value; instead of parseInt(currNum = numberDisplay.value += e.target.value); and it still returns and logs undefined.
  • inside the "addClickedNumberToDisplay" I've also tried running currNum = numberDisplay.value += e.target.value; return parseInt(currNum);

Heres my code so far.

Also, any tips on improving the code that I have so far is also appreciated. thanks

HTML:

<!doctype html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport"
          content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <link rel="stylesheet" href="css/utils.css">
    <link rel="stylesheet" href="css/styles.css">
    <link rel="stylesheet" href="css/svg.css">
    <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.1.1/css/all.min.css"
          integrity="sha512-KfkfwYDsLkIlwQp6LFnl8zNdLGxu9YAA1QvwINks4PhcElQSvqcyVLLD9aMhXd13uQjoXtEKNosOWaZqXgel0g=="
          crossorigin="anonymous" referrerpolicy="no-referrer"/>
    <title>Pretty Calc</title>
</head>
<body>
<div class="calculator">
    <div id="calc_container">
        <h1>Pretty<br> <span>calculator</span></h1>
        <main>
            <input type="text" id="curr_calculation" class="input-field" placeholder=0>
            <div class="num_grid">
                <!--            Row 1-->
                <button type="button" id="clear" class="top-operators btn"><p>clr</p></button>
                <button type="button" id="delete" class="top-operators"><p><i class="fa-solid fa-arrow-left"></i></p>
                </button>
                <button type="button" id="divide" class="operator btn"><p>/</p></button>
                <!--            Row 2-->
                <button type="button" id="seven" class="num-btn" value="7"><p>7</p></button>
                <button type="button" id="eight" class="num-btn" value="8"><p>8</p></button>
                <button type="button" id="nine" class="num-btn" value="9"><p>9</p></button>
                <button type="button" id="multiply btn" class="operator"><p>x</p></button>
                <!--            Row 3-->
                <button type="button" id="four" class="num-btn" value="4"><p>4</p></button>
                <button type="button" id="five" class="num-btn" value="5"><p>5</p></button>
                <button type="button" id="six" class="num-btn" value="6"><p>6</p></button>
                <button type="button" id="subtract btn" class="operator"><p>-</p></button>
                <!--            Row 4-->
                <button type="button" id="one" class="num-btn" value="1"><p>1</p></button>
                <button type="button" id="two" class="num-btn" value="2"><p>2</p></button>
                <button type="button" id="three" class="num-btn" value="3"><p>3</p></button>
                <button type="button" id="plus btn" class="operator"><p>+</p></button>
                <!--            Row 4-->
                <button type="button" id="zero" class="num-btn" value="0"><p>0</p></button>
                <button type="button" id="decimal btn" value="."><p>.</p></button>
                <button type="button" id="equal btn" class="operator"><p>=</p></button>
            </div>
        </main>
    </div>
</div>
<script src="js/pretty-calc.js"></script>
</body>
</html>

JAVASCRIPT:

"use strict";
    
    // global variables
    // let prevNum;
    let currNum;
    let numBtns = Array.from(document.querySelectorAll(".num-btn"));
    let numberDisplay = document.querySelector(".input-field")
    let deleteKey = document.querySelector("#delete")
    
    
    // function calls
    function addClickedNumberToDisplay(e){
        currNum = parseInt(numberDisplay.value += e.target.value);
        return currNum;
    }
    
    function deleteLastNumberFromDisplay(e){
        let y = currNum.toString().substring(0, currNum.toString().length - 1);
        numberDisplay.value = parseInt(y);
        return currNum = parseInt(y);
    }
    
    // eventlisteners
    numBtns.forEach(numberButton => numberButton.addEventListener("click", addClickedNumberToDisplay));
    deleteKey.addEventListener("click", deleteLastNumberFromDisplay)

Solution

  • because sometimes click event happen in <p> element, so you have to get parent element (button) value

    currNum = parseInt(numberDisplay.value += e.target.value || e.target.parentElement.value);
    

    I think it better to write <button>Text</button> instead of <button><p>Text</p></button>