Maxieprodmoore
Maxieprodmoore

Reputation: 57

Is there a way to invoke a function and log the results made within as Variables for future use in Javascript?

I want to invoke a function used to grab the numbers (as numbers and not strings) I typed out on an input form to calculate the total amount of tea drunk in a month, and later in a year, + the amount he would have spent drinking just the cheapest coffee available vs the most expensive coffee available to him, and the in-between. Then, I want to store the resulting information as separate variables and then invoke the information as needed elsewhere since I'm trying to craft out an Estimator app.

However, it needed a button to trigger the calculations needed for each variable to work. Here's what I have when I tried to troubleshoot on a single function required to get the cups of tea drunk in a month based on user input:

<input type="number" id="cupMon" >
<input type="number" id="cupTues">
<input type="number" id="cupWed">
<input type="number" id="cupThurs">
<input type="number" id="cupFri">
<input type="number" id="cupSat">
<input type="number" id="cupSun">

<p>Click the button to get the number of the number field.</p>

<button onclick="teaMth()">Calculate Total number of cups of tea drunk!</button>


<p id="demo"></p>

<script>
let tea_Mth = teaMth();

function teaMth() {
    //Enter amt_TeaMonday
        let cupsMon = document.getElementById("cupMon").value;
        let teaMon = (parseInt(cupsMon));
    //Enter amt_TeaTuesday
        let cupsTues = document.getElementById("cupTues").value;
        let teaTues = (parseInt(cupsTues));
    //Enter amt_TeaWednesday
        let cupsWed = document.getElementById("cupWed").value;
        let teaWed = (parseInt(cupsWed));
    //Enter amt_TeaThursday
        let cupsThurs = document.getElementById("cupThurs").value;
        let teaThurs = (parseInt(cupsThurs));
    //Enter amt_TeaFriday
        let cupsFri = document.getElementById("cupFri").value;
        let teaFri = (parseInt(cupsFri));
    //Enter amt_TeaSaturday
        let cupsSat = document.getElementById("cupSat").value;
        let teaSat = (parseInt(cupsSat));
    //Enter amt_TeaSunday
        let cupsSun = document.getElementById("cupSun").value;
        let teaSun = (parseInt(cupsSun));
    //Procedure amt_TeaMth {amt_TeaMonth * 4}
    let tea4Mth = ((teaMon + teaTues + teaWed + teaThurs + teaFri + teaSat + teaSun) * 4); 
        document.getElementById("demo").innerHTML = tea4Mth
      }  
      document.getElementById("demo").innerHTML = tea_Mth

</script>

I wanted to use the invoked function as a variable that would replace the content of the empty paragraph patch, (which would be accessed via a get Element by Id tag when things get chaotic), then store that new information for future use, such as when I get the app to calculate the amount of tea drunk in a year and how much money he would have spent. But thus far I could only grab that data when I invoked a designated variable within the function itself. Otherwise I would have gotten an NaN instead.

Could someone see what's wrong with the code since I would have to grab input information concerning the cost of the user's cheapest cup of tea and cost of his most expensive cup of tea drunk and use that information + the average cost of said tea to see the total projected expenditure in a month and then a year's time? Thanks in advance!

Upvotes: 0

Views: 56

Answers (3)

CssProblem
CssProblem

Reputation: 275

Here is a jsFiddle I made of the answer. Or, alternatively, the code snippet below. The answer uses jQuery (you can do all of this without jQuery, but, as a beginner, I recommend you learn jQuery, since it's much more powerful than regular JavaScript) and uses an array of days and dayValues (dayValues[0] = Monday etc - you could alternative store the values in an object, if you wanted to access them by the name of the day, rather than an int representation of the day (i.e. Monday = 0; Sunday = 6). The elements are also created at runtime (with 7 fields, it's a bit annoying to have to create 7 fields, 7 different variables, to add 7 seperate events etc...so it's better to just create things dynamically. With 50, 100 or 10000 elements, then, of course, unless you enjoyed self-harm, you would have to create them dynamically). Let me know if you don't understand the code

var days = ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"];
var dayValues = [];

$(document).ready(function(){
  createInputFields(days);
})

function createInputFields(days){
  days.forEach(function(d){
    $("#dayWrapper").append("<label for'cup" + d + "'>" + d + "</label><input type='number' id='cup" + d + "' class='teaInput'/>");
  })
  
  $("#dayWrapper input").on("input", function(){
    var weeklyTotal = 0;
    dayValues = [];
    $("#dayWrapper input").each(function(){
        var n = fieldToInt($(this).val());
      weeklyTotal += n;
      dayValues.push(n);
    })
    $("#weeklyTotal").text(weeklyTotal);
    $("#monthlyTotal").text(weeklyTotal * 4);
    console.log(dayValues);
  })
}

function fieldToInt(v){
  if(v == "") return 0;
  else return parseInt(v);
}
@import('https://fontlibrary.org/face/glacial-indifference');

*{
  margin: 0;
  padding: 0;
  color: white;
  font-family: 'GlacialIndifferenceRegular', sans-serif;
}

html{
  height: 100%;
}

body{
  height: 100%;
  background: #222;
  background: url('https://cbsnews3.cbsistatic.com/hub/i/r/2018/02/05/a8617d9c-4d06-427e-8e86-6e39cbd36c9e/thumbnail/1200x630/bd66ca034448164d0c7c2d28ea5bde2c/istock-466073662.jpg') no-repeat center center fixed; 
  -webkit-background-size: cover;
  -moz-background-size: cover;
  -o-background-size: cover;
  background-size: cover;
  display: flex;
  align-items: center;
  justify-content: center;
}

h2{
  margin-bottom: 20px;
  text-align: center;
}

#teaApp{
  padding: 30px;
  background: #000000cc;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
}

#dayWrapper{
  width: 300px;
  display: grid;
  grid-template-columns: 150px 150px;
  grid-row-gap: 10px;
  font-size: 20px;
}

#dayWrapper label{
  text-align: center;
}

input{
   background: none;
  border: none;
  border-bottom: 2px solid white;
  padding: 5px;
}

input:focus{
  border-color: #007eff;
}

#totals{
  margin-top: 20px;
}

.totalRow{
  font-size: 20px;
  display: grid;
  grid-template-columns: 150px 150px;
  text-align: center;
}

.totalRow:nth-of-type(1){
  margin-bottom: 10px;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id='teaApp'>
  <h2>How many cups of tea<br>did you drink?</h2>
  <div id='dayWrapper'></div>
<div id='totals'>
  <div class='totalRow'>
    <p>Weekly Total:</p>
    <p id='weeklyTotal'>0</p>
  </div>
  <div class='totalRow'>
    <p>Monthly Total:</p>
    <p id='monthlyTotal'>0</p>
  </div>
  </div>
</div>

Upvotes: 0

timotgl
timotgl

Reputation: 2925

Changed your code to a more stateful approach, have a look: https://codepen.io/timotgl/pen/KKzQWXd

HTML:

<label>Monday <input type="number" id="cupMon" value="0" /></label>
<label>Tuesday <input type="number" id="cupTues" value="0" /></label>
<label>Wednesday <input type="number" id="cupWed" value="0" /></label>
<label>Thursday <input type="number" id="cupThurs" value="0" /></label>
<label>Friday <input type="number" id="cupFri" value="0" /></label>
<label>Saturday <input type="number" id="cupSat" value="0" /></label>
<label>Sunday <input type="number" id="cupSun" value="0" /></label>

<h1>Number of cups for the entire month: <span id="sumCupsMonth">0</span></h1>

JS:

const state = {
  cupMon: 0,
  cupTues: 0,
  cupWed: 0,
  cupThurs: 0,
  cupFri: 0,
  cupSat: 0,
  cupSun: 0,
};

const weekDays = Object.keys(state); // ['cupMon', 'cupTues', ...]

const total = document.getElementById('sumCupsMonth');

const calculateCupsPerMonth = () => {
  // Add up all weekdays in state
  const sumWeek = weekDays.reduce((result, weekDay) => {
    const weekDayValue = state[weekDay];
    return result + weekDayValue;
  }, 0);
  return sumWeek * 4;
};

// Update total based on all weekdays
const updateTotal = () => {
  total.innerHTML = calculateCupsPerMonth(); 
};

// Listen to input changes for each weekday, save current value in state.
weekDays.forEach((weekDay) => {
  const input = document.getElementById(weekDay);
  input.addEventListener('change', (changeEvent) => {
    const currentWeekDay = changeEvent.target.id;
    const value = parseInt(changeEvent.target.value, 10);

    // Save value for future calculations
    state[currentWeekDay] = value;

    updateTotal();
  });
});

There is actually no need to store the sum for the entire month anywhere, since it's based on the input values. So you could simply call calculateCupsPerMonth() when you need an up-to-date value.

Upvotes: 0

Jamiec
Jamiec

Reputation: 136174

You're not returning anything from your function, if you did you would be able to store that variable for future use:

let tea_Mth = teaMth();
document.getElementById("demo").innerHTML = tea_Mth;
// note: tea_Mth is available elsewhere now

function teaMth() {

    .....
    
    let tea4Mth = ((teaMon + teaTues + teaWed + teaThurs + teaFri + teaSat + teaSun) * 4); 
    return tea4Mth; // <-- THIS LINE WAS MISSING
}

Live example below:

var tea_Mth;

function calcTeaMth(){
    tea_Mth = teaMth();    
    document.getElementById("demo").innerHTML = tea_Mth
}
function teaMth() {
    //Enter amt_TeaMonday
        let cupsMon = document.getElementById("cupMon").value;
        let teaMon = (parseInt(cupsMon));
    //Enter amt_TeaTuesday
        let cupsTues = document.getElementById("cupTues").value;
        let teaTues = (parseInt(cupsTues));
    //Enter amt_TeaWednesday
        let cupsWed = document.getElementById("cupWed").value;
        let teaWed = (parseInt(cupsWed));
    //Enter amt_TeaThursday
        let cupsThurs = document.getElementById("cupThurs").value;
        let teaThurs = (parseInt(cupsThurs));
    //Enter amt_TeaFriday
        let cupsFri = document.getElementById("cupFri").value;
        let teaFri = (parseInt(cupsFri));
    //Enter amt_TeaSaturday
        let cupsSat = document.getElementById("cupSat").value;
        let teaSat = (parseInt(cupsSat));
    //Enter amt_TeaSunday
        let cupsSun = document.getElementById("cupSun").value;
        let teaSun = (parseInt(cupsSun));
    //Procedure amt_TeaMth {amt_TeaMonth * 4}
    let tea4Mth = ((teaMon + teaTues + teaWed + teaThurs + teaFri + teaSat + teaSun) * 4); 
        return tea4Mth
      }  
<input type="number" id="cupMon" >
<input type="number" id="cupTues">
<input type="number" id="cupWed">
<input type="number" id="cupThurs">
<input type="number" id="cupFri">
<input type="number" id="cupSat">
<input type="number" id="cupSun">

<p>Click the button to get the number of the number field.</p>

<button onclick="calcTeaMth()">Calculate Total number of cups of tea drunk!</button>


<p id="demo"></p>

Upvotes: 1

Related Questions