简体   繁体   中英

Array index link to event listener loop

I'm trying to simplify / re-factor price calculation for multiple products.

Code demo: https://jsfiddle.net/helloKittychan/jLfwgsz6/2/

Structure:

  • Prices: stored in an array as [0] [1].

  • Quantity: user input integer for each product.

  • Subtotal calculation: on 'blur' (user input) * (corresponding array[n]).

Problem

The first product Candy1 works fine up to calculating sub total as I hard-coded variables. Then I embarked upon re-factoring the code using 'blur' event listener loop for quantity input fields for Candy1 & Candy 2. The event listener works fine on the quantity field, but now I'm stuck on how to call the corresponding price value for the current event. I guess either calling directly from array or calling from HTML element is possible, but I couldn't figure out the logic to pinpoint to the right price corresponding to the current event, or not sure if that's possible.

Previous research

I've looked around some posts & pages, but none of them seem simple enough nor similar enough for me to synthesise into my code.

  • The visible effect of this is similar to (I think) what I want, but the logic is not. Accessing child array by index and updating view when index increments (SO post)

  • Logically similar but the HTML structure is different: Get value from select list in JS (SO post)

  • I looked at the section [Arrays and Loops] at the bottom of the page, but I couldn't work it out how to make use of it. Javascript Arrays (by Home and Learn website)

  • Stack Overflow search keywords js array select index

Questions

  1. Given that I'm a novice, is my attempt to re-factor too ambitious?
  2. Or can you suggest a simple solution / point me to relevant ref? (Prefer pure js, no libraries if possible)

I also suspect my HTML design is inefficient. Any suggestions to make my little project work will be much appreciated.

Code demo: https://jsfiddle.net/helloKittychan/jLfwgsz6/2/

Js only:

// Inserting prod prices
var prodPrices = ["0.33", "0.50"];
document.getElementById("prod1").innerHTML = "£ " + prodPrices[0];
document.getElementById("prod2").innerHTML = "£ " + prodPrices[1];

// Setting up a universal Event Listener
document.addEventListener("DOMContentLoaded", 
function() { 

// grabbing (=var) the common Class name within the target block.
var qtyInput =
document.getElementsByClassName("qty-input");

// event listener = counting the number of grabbed Class occurrence (=array) 
// and listening to a defined event (click/blur etc) on them + define event name.
for(var i = 0; i < qtyInput.length; ++i) {
qtyInput[i].addEventListener("blur", gotQty);

}

// Function to identify current element with event.
function gotQty(event) {
var qtyId = this.value;
var bow = qtyId * prodPrices[0];
console.log(qtyId); 
console.log(bow);   
}
});

// Calculating subtotal (qty * price) - currently only works for "Candy 1".
function subTot() {
var prod1Qty = document.getElementById("qtyFlat1").value; //this
var subTotProd1 = prod1Qty * prodPrices[0];
var subTotClean = subTotProd1.toFixed(2);
        document.getElementById("prod1-subtotal").innerHTML = subTotClean;
// condescending health warning
if (prod1Qty > 10 ) {
    document.getElementById("quantity-alert").innerHTML = "Too much sugar is bad for you.<br>Select between 1 ~ 10.";
    return false;
}else{
        return true;
}
}
subTot();
// Clearing invalid data & error message then resetting the sub tot - currently only works for "Candy 1".
function clearSub() {
var prod1QtyOver = document.getElementById("qtyFlat1").value;
if(prod1QtyOver > 10){
    document.getElementById("quantity-alert").innerHTML = "<br><br>";
    document.getElementById("qtyFlat1").value = "";
    document.getElementById("prod1-subtotal").innerHTML = prodPrices[0];
}
}
clearSub();

If I were generating the fields dynamically I would use the data- attribute and set the attribute to be the values of the items. This can then be accessed by the JS when the user clicks out of the field.

For example: in the fields, add another attribute data-price which is set to the items prices respectively (this involves some DOM manipulation).

...
<input class="qty-input" data-price="0.33" id="qtyFlat1" type="text" placeholder="1" class="qty" style="width: 30px;" maxlength="4" onblur="subTot()" onclick="clearSub()" onkeypress=""/>
...
<input class="qty-input" data-price="0.5" id="qtyFlat2" type="text" placeholder="1" class="qty" style="width: 30px;" maxlength="4" onblur="subTot()" onclick="clearSub()" onkeypress=""/>
...

In the javascript:

function gotQty(event) {
  var qtyId = this.value;
  var bow = qtyId * Number(event.srcElement.dataset.price);
  console.log(qtyId);   
  console.log(bow);
}

See http://jsfiddle.net/boo261cc/3 and open up your console.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM