how to output the minimum value from array on the website - javascript

i have the input values and js creates the array. I need that all values should be sorted by values and output the min value on the web page. User should see smth like this: the subject where u get (3(for example)) should be improved in next few days. please guys!
document.querySelector('button').addEventListener('click', function(e) {
var inputs = document.querySelectorAll('input');
var obj = [].reduce.call(inputs, (accumulator, currentValue, currentIndex) => {
accumulator[`val${currentIndex}`] = currentValue.value
return accumulator
}, {})
console.log(obj)
});
<form>
<table id="tblSearchTally">
<tr>
<td>Biology:<input type= "text" ></td>
</tr>
<tr>
<td>Chemistry:<input type= "text" ></td> </tr>
<tr>
<td>Physics:<input type= "text" ></td> </tr>
<tr>
<td>Math:<input type= "text" ></td>
</tr>
</table>
<button type="button">Go</button>
</form>

Details are commented in demo
// Reference the DOM elements
// Get the first <form> on page
const form = document.forms[0];
// Collect all form controls with [name=grade] into a NodeList
const inputs = form.elements.grade;
const minCell = document.querySelector('.MIN');
const maxCell = document.querySelector('.MAX');
// Register the <form> to the click event
form.onclick = calc;
// Event handler passes event object
function calc(e) {
// if clicked tag (ie e.target) is a button tag...
if (e.target.tagName === "BUTTON") {
/*
covert NodeList into an array
create an array of input values
and convert them into Numbers
then return the array of Numbers
in order from least to greatest
*/
let ordered = [...inputs].map(input => Number(input.value)).sort((a, b) => a - b);
console.log(ordered);
// Display the first Number of the Number array
minCell.textContent = ordered[0];
// Display the last Number of the Number array
maxCell.textContent = ordered[ordered.length - 1];
}
}
:root,
body {
font: 700 small-caps 2vw/1.45 Consolas;
}
table,
td {
table-layout: fixed;
border-collapse: collapse;
width: 200px;
border: 1px solid #000
}
td {
padding: 2px;
width: 50%;
text-align: right;
}
tfoot tr:first-of-type td {
text-align: left;
}
tfoot tr:first-of-type td::before {
content: attr(class)': ';
}
caption {
font-size: 1.25rem
}
input {
font: inherit;
text-align: right;
display: block;
width: 85px
}
button {
font: inherit;
text-align: right;
}
.as-console-wrapper {
width: 350px;
min-height: 100%;
margin-left: 45%;
}
<form>
<table>
<caption>Grades</caption>
<tbody>
<tr>
<td>Biology: </td>
<td><input name='grade' type="number" min='0' max='100' value='0'></td>
</tr>
<tr>
<td>Chemistry: </td>
<td><input name='grade' type="number" min='0' max='100' value='0'></td>
</tr>
<tr>
<td>Physics: </td>
<td><input name='grade' type="number" min='0' max='100' value='0'></td>
</tr>
<tr>
<td>Math: </td>
<td><input name='grade' type="number" min='0' max='100' value='0'></td>
</tr>
</tbody>
<tfoot>
<tr>
<td class='MIN'></td>
<td class='MAX'></td>
</tr>
<tr>
<td colspan='2'><button type="button">GO</button></td>
</tr>
</tfoot>
</table>
</form>

Put all the values in an array and use this: Math.min(...name_of_array) ;
Example:
var arr = [4,1,2,0,9,5];
Math.min(...arr) ;
The output will be: 0

create an array of scores, then calculate min value:
const scores = [...inputs].map( x => Number(x.value) );
const min = Math.min( ...scores );

Instead of reduce, you can use map to save inputs value into an array and sort it.
document.querySelector('button').addEventListener('click', function(e) {
var inputs = document.querySelectorAll('input');
var values = [].map.call(inputs, inputEl => inputEl.value);
values.sort();
console.log(values);
});
The minium value is values[0]

you can do like this by using jquery
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
<title>Document</title>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.4.1/jquery.min.js">
</script>
</head>
<body>
<form>
<table id="tblSearchTally">
<tr>
<td>Biology:<input type="text" /></td>
</tr>
<tr>
<td>Chemistry:<input type="text" /></td>
</tr>
<tr>
<td>Physics:<input type="text" /></td>
</tr>
<tr>
<td>Math:<input type="text" /></td>
</tr>
</table>
<input type="button" onclick="MinValue('input')" value="Go" />
</form>
<script>
function MinValue(selector) {
var min = null;
$(selector).each(function () {
var value = parseInt(this.value, 0);
if (min === null || value < min) {
min = value;
}
});
console.log(min);
}
</script>

Related

Getting Error "(index):1 Uncaught ReferenceError: <func_name> is not defined at HTMLAnchorElement.onclick ((index):1:1)" on clicking delete button

I tried developing an expense tracker app using Javascript, in which the users keep entering the data. I also want to have a delete button which deletes the entered information. I've successfully added the information provided by the users but unable to delete any single information entered by the users. I'm getting the error "(index):1 Uncaught ReferenceError: deleteExpense is not defined at HTMLAnchorElement.onclick ((index):1:1)" after clicking the delete button. Requesting your help. Plese refer my code below.
document.getElementById("submit").addEventListener("click", (e) => {
e.preventDefault();
// Form validation
function validate() {
if (document.myForm.empId.value == "") {
alert("Please provide your Employee ID!");
document.myForm.empId.focus();
return false;
}
if (document.myForm.empName.value == "") {
alert("Please provide your Name!");
document.myForm.empName.focus();
return false;
}
if (document.myForm.PaymentMode.value == "") {
alert("Select your Payment Mode!");
document.myForm.PaymentMode.focus();
return false;
}
if (document.myForm.Date.value == "") {
alert("Please provide the Date!");
document.myForm.Date.focus();
return false;
}
if (document.myForm.Bill.value == "") {
alert("Please provide your Bill Amount!");
document.myForm.Bill.focus();
return false;
}
return true;
}
let id = document.getElementById("id").innerText;
let empId = document.getElementById("empID").value;
let name = document.getElementById("name").innerText;
let empName = document.getElementById("empname").value;
let using = document.getElementById("using").innerText;
let mode = document.getElementById("payment-mode").value;
let day = document.getElementById("day").innerText;
let date = document.getElementById("date").value;
let amount = document.getElementById("amount").innerText;
let bill = document.getElementById("bill").value;
let array = [
[id, empId],
[name, empName],
[using, mode],
[day, date],
[amount, bill],
];
let expenseList = Object.fromEntries(array);
const expenseTable = document.getElementById("expenseTable");
function output() {
if (validate()) {
for (let i = 0; i < Object.keys(expenseList).length; i++) {
expenseTable.innerHTML += `
<tr>
<td>${expenseList[id]}</td>
<td>${expenseList[name]}</td>
<td>${expenseList[using]}</td>
<td>${expenseList[day]}</td>
<td>$${expenseList[amount]}</td>
<td><a class="deleteButton" onclick="deleteExpense(${expenseList[id]})">
Delete</td>
</tr>
`;
break;
}
} else {
return false;
}
const deleteExpense = (id) => {
for (let j = 0; j < Object.keys(expenseList).length; j++) {
if (expenseList[id] == id) {
delete expenseList.id;
}
}
};
deleteExpense();
}
output();
});
.table {
border: 1px solid black;
width: 100%;
}
th {
border-right: 1px solid black;
}
.table td {
border: 1px solid black;
text-align: center;
}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Expense Tracker Project</title>
<link rel="stylesheet" href="./styles.css" />
</head>
<body>
<div class="employee-info">
<form
class="expenesesForm"
name="myForm"
onsubmit="return(validate());"
method="POST"
action=""
>
<table>
<tr>
<td id="id">Employee ID:</td>
<td>
<input id="empID" name="empId" type="text" placeholder="Employee ID" />
</td>
</tr>
<tr>
<td id="name">Name:</td>
<td>
<input id="empname" type="text" placeholder="Name" name="empName" />
</td>
</tr>
<tr>
<td id="using">Payment Mode:</td>
<td>
<select id="payment-mode" name="PaymentMode">
<option class="" value="" selected disabled>
Select from the list
</option>
<option class="mode" value="card">Card</option>
<option class="mode" value="cheque">Cheque</option>
<option class="mode" value="cash">Cash</option>
<option class="mode" value="other">Other</option>
</select>
</td>
</tr>
<tr>
<td id="day">Date of Transaction:</td>
<td><input id="date" type="date" name="Date" /></td>
</tr>
<tr>
<td id="amount">Amount:</td>
<td><input id="bill" type="number" name="Bill" /></td>
</tr>
<tr>
<td>
<br />
<input id="submit" type="submit" value="Submit" />
<input id="reset" type="reset" value="Cancel" />
</td>
</tr>
</table>
</form>
<br />
<table class="table">
<thead>
<tr>
<th>Employee Id</th>
<th>Name</th>
<th>Mode of Transaction</th>
<th>Date of Transaction</th>
<th>Amount</th>
</tr>
</thead>
<tbody id="expenseTable"></tbody>
</table>
</div>
</body>
</html>
Expected Output:
On clicking the delete button in the table, it should delete one row of information entered by the user.
You are trying to reference the function outside its scope. The snippet below works, but I do not know much about your other requirements, so if this approach is breaking something, then please let me know.
document.getElementById("submit").addEventListener("click", (e) => {
e.preventDefault();
// Form validation
function validate() {
if (document.myForm.empId.value == "") {
alert("Please provide your Employee ID!");
document.myForm.empId.focus();
return false;
}
if (document.myForm.empName.value == "") {
alert("Please provide your Name!");
document.myForm.empName.focus();
return false;
}
if (document.myForm.PaymentMode.value == "") {
alert("Select your Payment Mode!");
document.myForm.PaymentMode.focus();
return false;
}
if (document.myForm.Date.value == "") {
alert("Please provide the Date!");
document.myForm.Date.focus();
return false;
}
if (document.myForm.Bill.value == "") {
alert("Please provide your Bill Amount!");
document.myForm.Bill.focus();
return false;
}
return true;
}
let id = document.getElementById("id").innerText;
let empId = document.getElementById("empID").value;
let name = document.getElementById("name").innerText;
let empName = document.getElementById("empname").value;
let using = document.getElementById("using").innerText;
let mode = document.getElementById("payment-mode").value;
let day = document.getElementById("day").innerText;
let date = document.getElementById("date").value;
let amount = document.getElementById("amount").innerText;
let bill = document.getElementById("bill").value;
let array = [
[id, empId],
[name, empName],
[using, mode],
[day, date],
[amount, bill],
];
let expenseList = Object.fromEntries(array);
const expenseTable = document.getElementById("expenseTable");
function output() {
if (validate()) {
for (let i = 0; i < Object.keys(expenseList).length; i++) {
expenseTable.innerHTML += `
<tr>
<td>${expenseList[id]}</td>
<td>${expenseList[name]}</td>
<td>${expenseList[using]}</td>
<td>${expenseList[day]}</td>
<td>$${expenseList[amount]}</td>
<td><a class="deleteButton">
Delete</td>
</tr>
`;
for (let i = 0; i < expenseTable.children.length; i++)expenseTable.children[i].querySelector('.deleteButton').addEventListener("click", function() {
this.parentNode.parentNode.remove();
});
break;
}
} else {
return false;
}
/*const deleteExpense = (id) => {
for (let j = 0; j < Object.keys(expenseList).length; j++) {
if (expenseList[id] == id) {
delete expenseList.id;
}
}
};
deleteExpense();*/
}
output();
});
.table {
border: 1px solid black;
width: 100%;
}
th {
border-right: 1px solid black;
}
.table td {
border: 1px solid black;
text-align: center;
}
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Expense Tracker Project</title>
<link rel="stylesheet" href="./styles.css" />
</head>
<body>
<div class="employee-info">
<form
class="expenesesForm"
name="myForm"
onsubmit="return(validate());"
method="POST"
action=""
>
<table>
<tr>
<td id="id">Employee ID:</td>
<td>
<input id="empID" name="empId" type="text" placeholder="Employee ID" />
</td>
</tr>
<tr>
<td id="name">Name:</td>
<td>
<input id="empname" type="text" placeholder="Name" name="empName" />
</td>
</tr>
<tr>
<td id="using">Payment Mode:</td>
<td>
<select id="payment-mode" name="PaymentMode">
<option class="" value="" selected disabled>
Select from the list
</option>
<option class="mode" value="card">Card</option>
<option class="mode" value="cheque">Cheque</option>
<option class="mode" value="cash">Cash</option>
<option class="mode" value="other">Other</option>
</select>
</td>
</tr>
<tr>
<td id="day">Date of Transaction:</td>
<td><input id="date" type="date" name="Date" /></td>
</tr>
<tr>
<td id="amount">Amount:</td>
<td><input id="bill" type="number" name="Bill" /></td>
</tr>
<tr>
<td>
<br />
<input id="submit" type="submit" value="Submit" />
<input id="reset" type="reset" value="Cancel" />
</td>
</tr>
</table>
</form>
<br />
<table class="table">
<thead>
<tr>
<th>Employee Id</th>
<th>Name</th>
<th>Mode of Transaction</th>
<th>Date of Transaction</th>
<th>Amount</th>
</tr>
</thead>
<tbody id="expenseTable"></tbody>
</table>
</div>
</body>
</html>
deleteExpense is defined inside your event listener function.
onclick attributes execute in the global scope.
It isn't defined in the scope you are trying to access.
This is one of many problems with onclick attributes. Use addEventListener instead.

How to fix duplicate entries in number field in javascript

I have nine number fields to calculate. I need to check for duplicate entries in these 9 number fields and if found duplicate values, change the background color of the screen to 'red'. I'm not able to find solution for the mentioned.
I have created a table with 9 nine number fields to input the numbers and calculate the sum.
I searched for code to check for duplicate values in number fields, but found code to check for duplicate values in text fields.
<html>
<head>
<script>
function Sum() {
alert("hi");
var num1 = Number(document.getElementById("qty1").value);
var num2 = Number(document.getElementById("qty2").value);
var num3 = Number(document.getElementById("qty3").value);
var num4 = Number(document.getElementById("qty4").value);
var num5 = Number(document.getElementById("qty5").value);
var num6 = Number(document.getElementById("qty6").value);
var num7 = Number(document.getElementById("qty7").value);
var num8 = Number(document.getElementById("qty8").value);
var num9 = Number(document.getElementById("qty9").value);
var sum=num1+num2+num3+num4+num5+num6+num7+num8+num9
document.getElementById("answer").value = sum;
}
</script>
<style>
table>tbody>tr:nth-child(odd){
background-color: blue;
}
table>tbody>tr:nth-child(even){
background-color: green;
}
table>tbody>tr:nth-child(odd)>td:nth-child(odd){
background-color: green;
}
table>tbody>tr:nth-child(odd)>td:nth-child(even){
background-color: blue;
}
table>tbody>tr:nth-child(even)>td:nth-child(odd){
background-color: blue;
}
table>tbody>tr:nth-child(even)>td:nth-child(even){
background-color: green;
}
#sumtable th, #sumtable td{
padding:5px;
}
</style>
</head>
<title>Sum Box</title>
<body>
<table align="center" id="sumtable">
<tbody>
<tr>
<td>
<input type="number" placeholder="input1" value="input1"id="qty1"></td>
<td>
<input type="number" placeholder="input2" value="input2" id="qty2"></td>
<td>
<input type="number"placeholder="input3"value="input3"id="qty3"></td>
</tr>
<tr>
<td><input type="number" placeholder="input4" value="input4" id="qty4" ></td>
<td><input type="number" placeholder="input5" value="input5" id="qty5" ></td>
<td><input type="number" placeholder="input6" value="input6" id="qty6" ></td>
</tr>
<tr>
<td><input type="number" placeholder="input7" value="input7" id="qty7" ></td>
<td><input type="number" placeholder="input8" value="input8" id="qty8" ></td>
<td><input type="number" placeholder="input9" value="input9" id="qty9" ></td>
</tr>
</tbody>
</table>
<!-- Sum : <input type="text" name="total" id="total"/>
Sum-->
<div align="center">
<input type="button" onclick="Sum()" name="Sum" value="Sum" id="sum">
<input id="answer">
</div>
</body>
</html>
The above code generates 9 input number fields in table format to enter numbers and calculate the sum
Add your numbers to an array and loop through. One possible example, see https://codepen.io/anon/pen/yZaBrb:
var a = new Array(1,2,3,4,5,6,7,9,2,4);
var duplicate = false;
for (i=0;i<a.length;i++){
duplicate = false;
for(j=0;j<a.length;j++){
if(i != j && a[i]==a[j])
duplicate = true;
}
if(duplicate)
document.write('<span style="background-color:red;">')
document.write(a[i]);
if(duplicate)
document.write('</span>')
}
Create two events blur & keyup. On blur get the value from the input and push it in an array, on keyup check if the array contains the same value. If the value is present in the array then add a class to the target element or remove it
function Sum() {
alert("hi");
var num1 = Number(document.getElementById("qty1").value);
var num2 = Number(document.getElementById("qty2").value);
var num3 = Number(document.getElementById("qty3").value);
var num4 = Number(document.getElementById("qty4").value);
var num5 = Number(document.getElementById("qty5").value);
var num6 = Number(document.getElementById("qty6").value);
var num7 = Number(document.getElementById("qty7").value);
var num8 = Number(document.getElementById("qty8").value);
var num9 = Number(document.getElementById("qty9").value);
var sum = num1 + num2 + num3 + num4 + num5 + num6 + num7 + num8 + num9
document.getElementById("answer").value = sum;
}
let sumArray = []
document.querySelectorAll('input[type="number"]').forEach((item) => {
item.addEventListener('blur', (e) => {
sumArray.push(e.target.value)
})
item.addEventListener('keyup', (e) => {
if (sumArray.indexOf(e.target.value) !== -1) {
e.target.parentNode.classList.add('error')
} else if (e.target.parentNode.classList.contains('error')) {
e.target.parentNode.classList.remove('error')
}
})
})
table>tbody>tr:nth-child(odd) {
background-color: blue;
}
table>tbody>tr:nth-child(even) {
background-color: green;
}
table>tbody>tr:nth-child(odd)>td:nth-child(odd) {
background-color: green;
}
table>tbody>tr:nth-child(odd)>td:nth-child(even) {
background-color: blue;
}
table>tbody>tr:nth-child(even)>td:nth-child(odd) {
background-color: blue;
}
table>tbody>tr:nth-child(even)>td:nth-child(even) {
background-color: green;
}
#sumtable th,
#sumtable td {
padding: 5px;
}
.error {
border: 2px solid red;
}
<title>Sum Box</title>
<body>
<table align="center" id="sumtable">
<tbody>
<tr>
<td>
<input type="number" placeholder="input1" value="input1" id="qty1"></td>
<td>
<input type="number" placeholder="input2" value="input2" id="qty2"></td>
<td>
<input type="number" placeholder="input3" value="input3" id="qty3"></td>
</tr>
<tr>
<td><input type="number" placeholder="input4" value="input4" id="qty4"></td>
<td><input type="number" placeholder="input5" value="input5" id="qty5"></td>
<td><input type="number" placeholder="input6" value="input6" id="qty6"></td>
</tr>
<tr>
<td><input type="number" placeholder="input7" value="input7" id="qty7"></td>
<td><input type="number" placeholder="input8" value="input8" id="qty8"></td>
<td><input type="number" placeholder="input9" value="input9" id="qty9"></td>
</tr>
</tbody>
</table>
<!-- Sum : <input type="text" name="total" id="total"/>
Sum-->
<div align="center">
<input type="button" onclick="Sum()" name="Sum" value="Sum" id="sum">
<input id="answer">
</div>
its pretty simple just put same class in input field and loop through it like
In Html ,
<td>
<input type="number" class="checkSame" placeholder="input1" value="input1"id="qty1"></td>
<td>
<input type="number" class="checkSame" placeholder="input2" value="input2" id="qty2"></td>
<td>
<input type="number" class="checkSame" placeholder="input3"value="input3"id="qty3"></td>
then in javascript ,
var inputs = document.getElementsByClassName("checkSame");
var temp;
var count = 1;
for(var i = 0; i < inputs .length; i++)
{
temp = document.getElementsByClassName("checkSame")[i].value;
if(temp == document.getElementsByClassName("checkSame")[count++].value)
{
//change your background color here
break;
}
}
i think it works.
I hope this will help you to find duplicate fields
function Sum() {
alert("hi");
let arr = [];
let sum;
let duplicate = false;
for (let i = 1; i <= 9; i++) {
let num = Number(document.getElementById(`qty${i}`).value);
let indexOfDuplicateNum = arr.indexOf(num);
if (indexOfDuplicateNum > -1){
duplicate = true;
alert('Duplicate value found!');
document.getElementsByTagName('body')[0].style.background = 'red';
document.getElementById(`qty${i}`).classList.add('duplicate-error');
document.getElementById(`qty${indexOfDuplicateNum+1}`).classList.add('duplicate-error');
break;
} else{
//remove error class if value is not duplicate
document.getElementById(`qty${i}`).classList.remove('duplicate-error');
arr.push(num);
sum = arr.reduce((a, b) => a+b, 0);
}
}
if (!duplicate) {
document.getElementById('answer').value = sum;
document.getElementsByTagName('body')[0].style.background = 'white';
}
}
.duplicate-error {
border: 2px solid red;
}
table>tbody>tr:nth-child(odd){
background-color: blue;
}
table>tbody>tr:nth-child(even){
background-color: green;
}
table>tbody>tr:nth-child(odd)>td:nth-child(odd){
background-color: green;
}
table>tbody>tr:nth-child(odd)>td:nth-child(even){
background-color: blue;
}
table>tbody>tr:nth-child(even)>td:nth-child(odd){
background-color: blue;
}
table>tbody>tr:nth-child(even)>td:nth-child(even){
background-color: green;
}
#sumtable th, #sumtable td{
padding:5px;
}
<html>
<head>
<title>Sum Calculator</title>
</head>
<title>Sum Box</title>
<body>
<table align="center" id="sumtable">
<tbody>
<tr>
<td>
<input type="number" placeholder="input1" value="input1"id="qty1"></td>
<td>
<input type="number" placeholder="input2" value="input2" id="qty2"></td>
<td>
<input type="number"placeholder="input3"value="input3"id="qty3"></td>
</tr>
<tr>
<td><input type="number" placeholder="input4" value="input4" id="qty4" ></td>
<td><input type="number" placeholder="input5" value="input5" id="qty5" ></td>
<td><input type="number" placeholder="input6" value="input6" id="qty6" ></td>
</tr>
<tr>
<td><input type="number" placeholder="input7" value="input7" id="qty7" ></td>
<td><input type="number" placeholder="input8" value="input8" id="qty8" ></td>
<td><input type="number" placeholder="input9" value="input9" id="qty9" ></td>
</tr>
</tbody>
</table>
<!-- Sum : <input type="text" name="total" id="total"/>
Sum-->
<div align="center">
<input type="button" onclick="Sum()" name="Sum" value="Sum" id="sum">
<input id="answer">
</div>
</body>
</html>

Parsing input without requiring button press with Javascript

I am currently looking for a solution to add some user-typed numbers instantly/automatically without having to click on any button. For now, I have a table asking the user for the numbers and displaying the result after the user clicked on the "Total" button. I would like to get rid of that button and that the "Total" row of the table automatically refresh to the new total, every time the user changes a value.
<!DOCTYPE html>
<html>
<head>
<title>Table</title>
<style>
body {
width: 100%;
height: 650px;
}
#rent, #food, #entertainment, #transportation, #total {
height: 30px;
font-size: 14pt;
}
</style>
</head>
<body>
<center>
<h1></h1>
<script type="text/javascript">
function CalcTotal() {
var total = 0;
var rent = +document.getElementById("rent").value;
var food = +document.getElementById("food").value;
var entertainment = +document.getElementById("entertainment").value;
var transportation = +document.getElementById("transportation").value;
var total = rent + food + entertainment + transportation;
document.getElementById("total").innerHTML = total;
}
</script>
<table border="1">
<tr>
<th>A</th>
<th>B</th>
</tr>
<tr>
<td>Rent</td><td><input type="text" id="rent"></td>
</tr>
<tr>
<td>Food</td><td><input type="text" id="food"></td>
</tr>
<tr>
<td>Entertainment</td><td><input type="text" id="entertainment"></td>
</tr>
<tr>
<td>Transportation</td><td><input type="text" id="transportation"> </td>
</tr>
<tr>
<td>Total</td><td><div id="total"></div></td>
</tr>
</table>
<input type="submit" value="Total" onclick="CalcTotal()" id="total">
</center>
</body>
</html>
Add a keyup listener to every input field:
function CalcTotal() {
var total = 0;
var rent = +document.getElementById("rent").value;
var food = +document.getElementById("food").value;
var entertainment = +document.getElementById("entertainment").value;
var transportation = +document.getElementById("transportation").value;
var total = rent + food + entertainment + transportation;
document.getElementById("total").innerHTML = total;
}
document.querySelectorAll('input[type="text"]')
.forEach(input => input.addEventListener('keyup', CalcTotal));
body {
width: 100%;
height: 250px;
}
#rent,
#food,
#entertainment,
#transportation,
#total {
height: 30px;
font-size: 14pt;
}
<table border="1">
<tr>
<th>A</th>
<th>B</th>
</tr>
<tr>
<td>Rent</td>
<td><input type="text" id="rent"></td>
</tr>
<tr>
<td>Food</td>
<td><input type="text" id="food"></td>
</tr>
<tr>
<td>Entertainment</td>
<td><input type="text" id="entertainment"></td>
</tr>
<tr>
<td>Transportation</td>
<td><input type="text" id="transportation"> </td>
</tr>
<tr>
<td>Total</td>
<td>
<div id="total"></div>
</td>
</tr>
</table>
<input type="submit" value="Total" onclick="CalcTotal()" id="total">
Note that NodeList.forEach is somewhat new - if you have to support old browsers, you'll have to use a polyfill, or iterate over the inputs some other way instead. For example:
Array.prototype.forEach.call(
document.querySelectorAll('input[type="text"]'),
input => input.addEventListener('keyup', CalcTotal)
);

Auto calculation in table using jquery

My Requirment:
I have table with quantity cell as editable when change quantity it need to multiply with other parent td value.and sum the column values .
(i.e) if i change quantity to 2 then the parent rows need multiply by 2 & columns get value get added
I done all the calculation part the only thing when i delete or change the quantity the calculated value remain same how to revert back to old values
Here is my fiddle
Fiddle link
$(document).ready(function(){
$('.quantity').on('change, keyup',function(){
var val=$(this).text();
// To avoid auto inc while pressing arrow keys
var preVal =$(this).data('prevval');
<!-- console.log(preVal); -->
if(preVal && preVal == val){
return;
}
$(this).data('prevval',val);
//To avoid auto inc while pressing arrow keys //
if(val =='' || isNaN(val) || val < 1){
return;
}
$(this).siblings().each(function(){
var tbvalue=$(this).text();
var result= parseInt(tbvalue)*parseInt(val);
$(this).text(result);
})
autoSum();
});
autoSum();
});
function autoSum(){
for (var i = 1; i < 8; i++) {
var sum = 0;
$('.auto_sum>tbody>tr>td:nth-child(' + i + ')').each(function() {
sum += parseInt($(this).text()) || 0;
});
// set total in last cell of the column
$('.auto_sum>tbody>tr>td:nth-child(' + i + ')').last().html(sum);
// $('.auto_sum>tbody>tr>td:nth-child(' + i + ')').last().toggleClass('total');
}
}
.total {
background-color: #000;
color: #fff;
font-weight: bold;
}
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css">
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js"></script>
<div class="container">
<h2>Table calculation</h2>
<p>Calculaton</p>
<table class="auto_sum table table-hover">
<thead>
<tr>
<th>value1</th>
<th>value2</th>
<th>value3</th>
<th>Quantity</th>
</tr>
</thead>
<tbody>
<tr>
<td>10</td>
<td>5</td>
<td>4</td>
<td class="quantity" type="number" contenteditable>1</td>
</tr>
<tr>
<td>8</td>
<td type>2</td>
<td>3</td>
<td class="quantity" type="number" contenteditable>1</td>
</tr>
<tr>
<td>20</td>
<td>3</td>
<td>5</td>
<td class="quantity" type="number" contenteditable>1</td>
</tr>
<tr class="total">
<td> </td>
<td> </td>
<td> </td>
<td> </td>
</tr>
</tbody>
</table>
</div>
Inside every row, with the td that store the numbers to be multiplied, keep the original numbers in a data-val attribute in the td, and multiply your content editable value with that. Display the multiplied value as the td text. One change here is that, when you delete the value of contenteditable cell, it takes it as 1 for row calculation, but does not consider it for column multiplication.
HTML part
<div class="container">
<h2>Table calculation</h2>
<p>Calculaton</p>
<table class="auto_sum table table-hover">
<thead>
<tr>
<th>value1</th>
<th>value2</th>
<th>value3</th>
<th>Quantity</th>
</tr>
</thead>
<tbody>
<tr>
<td data-val="10">10</td>
<td data-val="5">5</td>
<td data-val="4">4</td>
<td class="quantity" type="number" contenteditable>1</td>
</tr>
<tr>
<td data-val="8">8</td>
<td data-val="2">2</td>
<td data-val="3">3</td>
<td class="quantity" type="number" contenteditable>1</td>
</tr>
<tr>
<td data-val="20">20</td>
<td data-val="3">3</td>
<td data-val="5">5</td>
<td class="quantity" type="number" contenteditable>1</td>
</tr>
<tr class="total">
<td> </td>
<td> </td>
<td> </td>
<td> </td>
</tr>
</tbody>
</table>
</div>
JS Part
$(document).ready(function(){
$('.quantity').on('change, keyup',function(){
var val=$(this).text();
// To avoid auto inc while pressing arrow keys
var preVal =$(this).data('prevval');
$(this).data('prevval',val);
//To avoid auto inc while pressing arrow keys //
if(val =='' || isNaN(val) || val < 1 || val == undefined){
val = 1;
}
$(this).siblings().each(function(){
var tbvalue=$(this).data("val");
var result= parseInt(tbvalue)*parseInt(val);
$(this).text(result);
});
autoSum();
});
autoSum();
});
function autoSum(){
for (var i = 1; i <= 4; i++) {
var sum = 0;
var tdBoxes = $('.auto_sum>tbody>tr>td:nth-child(' + i + ')');
for(var j=0; j<tdBoxes.length-1;j++)
{
var value = $(tdBoxes[j]).text();
//alert(value);
sum += (value == undefined || value == "")? 0 : parseInt(value);
}
// set total in last cell of the column
$('.auto_sum>tbody>tr>td:nth-child(' + i + ')').last().html(sum);
// $('.auto_sum>tbody>tr>td:nth-child(' + i + ')').last().toggleClass('total');
}
}
All details are commented in working demo. I added <form>, <output>, <input type='number'> and <input type='hidden'>. Also I don't remember <td> having a type attribute or a value of number either.
With the combination of the right elements and attributes (and maybe even a little CSS), you don't have to write so much JS/jQ because there many aspects of form functions built within HTML.
Demo
// Reference the <form>
var main = document.forms.main;
// Reference of all of <input> and <output> of <form>
var field = main.elements;
/* Register the input event on the <form>
|| ANY input event triggered within <form> will...
*/
main.addEventListener('input', function(e) {
// Check to see which field is the user inputing into
if (e.target !== e.currentTarget) {
// Reference that field
var input = document.getElementById(e.target.id);
// console.log(input.value);
// Get the row of the field
var row = input.parentNode.parentNode;
// console.log(row);
/* Gather all hidden fields of that row into a NodeList
|| and convert that NodeList into an array.
*/
var rowArray = Array.from(row.querySelectorAll('[type=hidden]'));
// console.log(rowArray);
// On each hidden field, perform the following function...
rowArray.forEach(function(cel, idx) {
// Get the value of hidden field
const base = cel.value;
// Find the <output> that comes after the hidden field
var output = cel.nextElementSibling;
/* Calculate the product of the hidden field's value
|| and the input field's value
*/
var val = parseInt(base, 10) * parseInt(input.value, 10);
// Display the prouct in the <output>
output.value = val;
});
/* Because we registered the input event on the <form>,
|| we have many ways to manipulate the <form>'s fields.
|| In this demo we have been using:
|| HTMLFormElement and HTMLFormControlsCollection interfaces
|| https://developer.mozilla.org/en-US/docs/Web/API/HTMLFormElement
|| http://www.dyn-web.com/tutorials/forms/references.php#dom0
*/
field.out1.value = Number(field.o1a.value) + Number(field.o1b.value) + Number(field.o1c.value);
field.out2.value = Number(field.o2a.value) + Number(field.o2b.value) + Number(field.o2c.value);
field.out3.value = Number(field.o3a.value) + Number(field.o3b.value) + Number(field.o3c.value);
field.out4.value = Number(field.out1.value) + Number(field.out2.value) + Number(field.out3.value);
}
});
.total {
background-color: #000;
color: #fff;
font-weight: bold;
}
input,
output {
display: inline-block;
font: inherit;
width: 6ch;
border: 0;
text-align: center;
}
.quantity input {
padding-top: .5em;
outline: 0;
}
-
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1, user-scalable=no">
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css">
<style>
</style>
</head>
<body>
<div class="container">
<form id='main'>
<table class="auto_sum table table-hover">
<thead>
<caption>
<h2>Table Calculation</h2>
<h3>Quanities</h3>
</caption>
<tr>
<th>Value1</th>
<th>Value2</th>
<th>Value3</th>
<th>Quantity</th>
</tr>
</thead>
<tbody>
<tr id='rowA'>
<td>
<!--[0][1]-->
<input id='v1a' type='hidden' value='10'>
<output id='o1a'>0</output>
</td>
<td>
<!--[2][3]-->
<input id='v2a' type='hidden' value='5'>
<output id='o2a'>0</output>
</td>
<td>
<!--[4][5]-->
<input id='v3a' type='hidden' value='4'>
<output id='o3a'>0</output>
</td>
<td class="quantity">
<!--[6]-->
<input id='qa' type='number' value='0' max='999' min='0'>
</td>
</tr>
<tr id='rowB'>
<td>
<!--[7][8]-->
<input id='v1b' type='hidden' value='8'>
<output id='o1b'>0</output>
</td>
<td>
<!--[9][10]-->
<input id='v2b' type='hidden' value='2'>
<output id='o2b'>0</output>
</td>
<td>
<!--[11][12]-->
<input id='v3b' type='hidden' value='3'>
<output id='o3b'>0</output>
</td>
<td class="quantity">
<!--[13]-->
<input id='qb' type='number' value='0' max='999' min='0'>
</td>
</tr>
<tr id='rowC'>
<td>
<!--[14][15]-->
<input id='v1c' type='hidden' value='20'>
<output id='o1c'>0</output>
</td>
<td>
<!--[16][17]-->
<input id='v2c' type='hidden' value='3'>
<output id='o2c'>0</output>
</td>
<td>
<!--[18][19]-->
<input id='v3c' type='hidden' value='5'>
<output id='o3c'>0</output>
</td>
<td class="quantity">
<!--[20]-->
<input id='qc' type='number' value='0' max='999' min='0'>
</td>
</tr>
<tr class="total">
<td>
<!--[21]-->
<output id='out1' for='o1a o1b o1c'>0</output>
</td>
<td>
<!--[22]-->
<output id='out2' for='o2a o2b o2c'>0</output>
</td>
<td>
<!--[23]-->
<output id='out3' for='o3a o3b o3c'>0</output>
</td>
<td>
<!--[24]-->
<output id='out4' for='out1 out2 out3'>0</output>
</td>
</tr>
</tbody>
</table>
</form>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js"></script>
</body>
</html>

dynamically added dom-elements not responding to jQuery-function

Consider the following code:
$(document).ready(function(){
var table1 = $("table").eq(0);
var row_list;
var rows;
var x;
var y;
$("#mybutton").click(function(){
row_list = table1.find("tr");
rows = row_list.length;
x = $("#field_x").val();
y = $("#field_y").val();
if(x>rows || y>rows){
var num;
if(x>y) num=x;
else num=y;
var n = num-rows;
var row; table1.find("tr").eq(0).clone();
while(1){
row = table1.find("tr").eq(0).clone();
table1.append(row);
n--;
if(n===0) break;
}
n = num-rows;
var td;
while(1){
td = table1.find("td").eq(0).clone();
table1.find("tr").append(td);
n--;
if(n===0) break;
}
}
var text = $("#text").val();
var css = $("#css").val();
$("table:eq(0) tr:eq(" + (x-1) + ") td:eq(" + (y-1) + ")").text(text).css("color", css);
});
table1.find("td").click(function(){
$(this).html("");
});
});
* {
font: 14px normal Arial, sans-serif;
color: #000000;
}
table {
margin: 50px auto;
}
table, td {
border: 1px solid #aaa;
border-collapse: collapse;
}
th {
padding: 10px;
font-weight: bold;
}
td {
background-color: #eeeeee;
width: 80px;
height: 80px;
}
table:first-child tr td {
cursor: pointer;
}
td[colspan="4"]{
text-align:center;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<table>
<tbody>
<tr>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
<tr>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
<tr>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
<tr>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
</tbody>
</table>
<table>
<thead>
<tr>
<th colspan="4">Fill a field:</th>
</tr>
</thead>
<tbody>
<tr>
<td>Text: <br/><input type="text" id="text" value=""></td>
<td>Field X: <br/><input type="text" id="field_x" value=""></td>
<td>Field Y: <br/><input type="text" id="field_y" value=""></td>
<td>CSS: <br/><input type="text" id="css" value=""></td>
</tr>
<tr>
<td colspan="4"><button id="mybutton">Fill</button></td>
</tr>
</tbody>
</table>
What the program does is the following:
The user can choose a field by giving an x-value and a y-value. In this field the content from the input field with label "Text" is displayed.
- This part of the program works fine.
If the user chooses an x-value or a y-value larger than the current number of rows (columns), rows and columns are added until the number of rows/columns is equal to the value in the x-(or y-) field.
- This part of the program also works fine.
The only functionality that does not work is the following:
If the user clicks on one of the non-empty fields in the table, the content of the table is supposed to go back to its natural (empty) state.
To this end, the following function was added to the code (see last couple of lines in the javascript part of the code):
table1.find("td").click(function(){
$(this).html("");
});
This piece of code basically means:
If the user clicks on any box ("td") in the table, the content of this box should disappear.
This is more or less the most simple part of the code. But it's also the one aspect that doesn't work. More precisely: It works for the original boxes, but it doesn't work for any boxes that were added. - And I don't get why it behaved that way.
If you are dynamically adding elements to the DOM and expect to be attaching events to them, you should consider using event delegation via the on() function :
// This will wire up a click event for any current AND future 'td' elements
$(table1).on('click', 'td', function(){
$(this).html("");
});
Simply using click() on it's own will only wire up the necessary event handlers for elements that exist in the DOM at the time of that function being called.
You're assigning the event handlers before the user has a chance to input any data. This means that if an additional row or column is added, the new <td>s need event handlers added manually.
Alternately, you can add a single click handler to the entire table:
table1.click(function (ev) { $(ev.target).html(''); }
The ev.currentTarget property will be the <table> element because that's the element the event handler is registered to, but the ev.target property will be the <td> element that you're looking for.
Here's a JSFiddle to experiment with.
Hey there here's what I thought the answer might be,
HTML File:
<!DOCTYPE html>
<html lang="de-DE">
<head>
<meta charset="UTF-8" />
<style>
* {
font: 14px normal Arial, sans-serif;
color: #000000;
}
table {
margin: 50px auto;
}
table, td {
border: 1px solid #aaa;
border-collapse: collapse;
}
th {
padding: 10px;
font-weight: bold;
}
td {
background-color: #eeeeee;
width: 80px;
height: 80px;
}
table:first-child tr td {
cursor: pointer;
}
td[colspan="4"]{
text-align:center;
}
.pre-height {
min-height: 80px;
}
</style>
</head>
<body>
<table>
<tbody>
<tr>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
<tr>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
<tr>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
<tr>
<td class="pre-height"></td>
<td class="pre-height"></td>
<td class="pre-height"></td>
<td class="pre-height"></td>
</tr>
</tbody>
</table>
<table>
<thead>
<tr>
<th colspan="4">Fill a field:</th>
</tr>
</thead>
<tbody>
<tr>
<td>Text: <br/><input type="text" id="text" value=""></td>
<td>Field X: <br/><input type="text" id="field_x" value=""></td>
<td>Field Y: <br/><input type="text" id="field_y" value=""></td>
<td>CSS: <br/><input type="text" id="css" value=""></td>
</tr>
<tr>
<td colspan="4"><button id="myButton">Fill</button></td>
</tr>
</tbody>
</table>
<script src="jquery.min.js"></script>
<script src="jack.js"></script>
</body>
</html>
JACK.JS file:
window.onload = function() {
'use strict';
/**
* Appends 'n' number of rows to the table body.
*
* #param {Number} n - Number of rows to make.
*/
var makeRows = function(n) {
let tbody= document.getElementsByTagName("table")[0].getElementsByTagName("tbody")[0],
tr = document.querySelector("table:first-of-type tbody tr");
for (let i = 0; i < n; i++) {
let row = Node.prototype.cloneNode.call(tr, true);
tbody.appendChild(row);
}
};
/**
* Appends 'n' number of cells to each row.
*
* #param {Number} n - Number of cells to add to each row.
*/
var makeColumns = function(n) {
let addNCells = (function(n, row) {
for (let i = 0; i < n; i++) {
let cell = Node.prototype.cloneNode.call(td, true);
row.appendChild(cell);
}
}).bind(null, n);
let tbody= document.getElementsByTagName("table")[0].getElementsByTagName("tbody")[0],
td = document.querySelector("table:first-of-type tbody tr td"),
rows = document.querySelectorAll("table:first-of-type tbody tr");
rows.forEach(function(row) {
addNCells(row);
});
};
document.getElementById("myButton").addEventListener("click", () => {
let x = document.getElementById("field_x").value,
y = document.getElementById("field_y").value;
makeColumns(x);
makeRows(y);
});
/**
* Newly added code
*/
(function() {
let table = document.querySelector("table");
// We will add event listener to table.
table.addEventListener("click", (e) => {
e.target.innerHTML = "";
e.target.style.backgroundColor = "orange";
});
})();
};
Edit: And I didn't even answer the question completely. You might wanna attach event listener to the nearest non-dynamic parent so that click event will bubble up and you can capture that, check the code under the comment newly added code.

Categories

Resources