This is the simple app for calculating the total price of selected elements of computer hardware. It should work with innerHTML and change it dinamically.
The problem is that with my code, nothing happens, so you can check it on my fiddle or just look at the code below. It should change the price in the last box???
FIDDLE
Code:
<table style="width:230px;padding:5px;border:1px solid #f0f0f0;font-size:14px;">
<tr style="background-color:#f0f0f0;">
<th style="width:200px;text-align:left;">Elements</th>
<th align="center"></th>
</tr>
<tr style="border-bottom:1px solid #a3a3a3;">
<td>CPU unit</td>
<td align="center">✓</td>
</tr>
<tr>
<tr>
<td>Motherboard</td>
<td align="center">✓</td>
</tr>
<td>Graphic card</td>
<td align="center"><input type="checkbox" id="id_1" value="25" onchange="check();"></td>
</tr>
<tr>
<td>Memory chip</td>
<td align="center"><input type="checkbox" name="" value="" onchange="check();></td>
</tr>
<tr>
<td>Monitor</td>
<td align="center"><input type="checkbox" name="" value="" onchange="check();></td>
</tr>
</table>
<table style="width:220px;padding:1px;border:1px solid #f0f0f0;font-size:22px; font-weight:bold;">
<tr style="border-bottom:1px solid #a3a3a3;text-align:center;background-color:#80CCDC">
<td id="total"><script>document.getElementById('total').innerHTML = price;</script></td></tr><tr>
</table>
JAVASCRIPT
var basic = 300;
var add = 0;
function check()
{
if(document.getElementById("id_1").checked) {
add = 120;
}
if(document.getElementById("id_1").checked) {
add = 40;
}
if(document.getElementById("id_1").checked) {
add = 90;
}
}
var p = basic + add;
var price = p + " €";
There are a few problems
You need to call document.getElementById('total').innerHTML = price; inside check so that it updates when you click the checkbox;
You can't have multiple items with the same ID. I changed them to id_1, id_2, id_3
You need to add to the existing value in the add variable
You have to hookup change for all the checkboxes, not just the first one.
Change your code to the following http://jsfiddle.net/mendesjuan/3ja4X/3/
function check() {
var basic = 300;
var add = 0;
if(document.getElementById("id_1").checked) {
add += 120;
}
if(document.getElementById("id_2").checked) {
add += 40;
}
if(document.getElementById("id_3").checked) {
add += 90;
}
var p = basic + add;
var price = p + " €";
document.getElementById('total').innerHTML = price;
}
check();
For even cleaner code, you can use the following http://jsfiddle.net/mendesjuan/3ja4X/4/
function updateTotal(){
var basic = 300;
var add = 0;
var form = document.getElementById('form');
// Store the value for each item in the checkbox so
// you don't need to have three separate `if`s and IDs for them.
var checkboxes = form.getElementsByClassName('addon');
for (var i=0; i < checkboxes.length; i ++) {
if (checkboxes[i].checked) {
add += parseInt(checkboxes[i].value, 10);
}
}
var p = basic + add;
var price = p + " €";
document.getElementById('total').innerHTML = price;
}
// Hookup handlers from JS, not in the HTML from a single
// place using event delegation
document.getElementById('form').addEventListener('change', updateTotal);
Add your calculations inside the check function, or make it calculate after the numbers are added:
function check(){
if(document.getElementById("id_1").checked) {
add = 120;
}
if(document.getElementById("id_1").checked) {
add = 40;
}
if(document.getElementById("id_1").checked) {
add = 90;
}
var p = basic + add;
var price = p + " €";
document.getElementById('total').innerHTML = price;
}
This the code does not only run once when the page is loaded.
Related
I am using javascript to clone a row then renaming the element id's and incrementing one of the values by 1. This is not the actual code I'm working on but a generic example that shows the problem.
It is appending everything to the top of my row instead of below it
It increments once or twice then stops
The output I'm getting is:
10022018
10032018
10032018
10032018
10032018
10012018
What I'm expecting is:
10012018
10022018
10042018
10052018
10062018
10072018
<table id = "myTable">
<tr id="myRow">
<td>First cell <input type="text" id = "input" value = "10012018"></td>
</tr>
</table><br>
<button onclick="myFunction()">Try it</button>
<script>
function myFunction() {
var i;
for(i=0; i<5;i++){
var row=document.getElementById("myRow");
var cln = row.cloneNode(true);
row.id = "rows" + i;
var inpa = document.getElementById("input");
inpa.id = "input" + i;
var a = parseFloat(document.getElementById("input0").value);
inpa.value = (a + 10000);
document.getElementById("myTable").appendChild(cln);
}
}
</script>
Edit
Robin Zigmond added that input0 was the culprit and not incrementing (corrected but I failed to explain).
var a = parseFloat(document.getElementById("input0").value); // Should be "input"
inpa.value = (a + (10000)); // Needs increment ...a + (10000 * i));
My explanation refers to this assignment to row.
row.id = "rows" + i; /* This assigns a new #id to the original not a clone
-- changed to `cln.id` */
When using a for loop leverage the incremental variable. When the clone was created, your references were still pointing to the original and it wasn't being used to increment anything so that's why it was just copying and not progressing.
Demo
Details commented in demo
<table id="xTable">
<tr id="xRow">
<td>First cell <input type="text" id="input" value="10012018"></td>
</tr>
</table><br>
<button onclick="xFunction()">Try it</button>
<script>
function xFunction() {
// In for loops declare i with let inside loop
// Start with 1 instead of 0 because you cloned the increment starting at 1000
for (let i = 1; i < 5; i++) {
var row = document.getElementById("xRow");
var cln = row.cloneNode(true);
// You are dealing with the clone not the original anymore
// Use i form increments
cln.id = "rows" + i;
// Target the clone specifically
// Use querySelector() to get #id, .class, or <tag>
var inpa = cln.querySelector("input");
// Once again var i to increment
inpa.id = "input" + i;
var a = parseFloat(document.getElementById("input").value);
// Remember i to increment but this is a little trickier
inpa.value = (a + (10000 * i));
document.getElementById("xTable").appendChild(cln);
}
}
</script>
Id's must be unique. Apply class to tr and input instead.
A generic solution
// n -> How many?
// start -> Start value
// index -> Index of value that should be incremented
// id -> Table id
function addRows(n, start, index, id) {
var table = document.getElementById(id);
for (var i = 2; i <= n + 1; i += 1) {
var arr = start.split("");
arr[index] = i.toString();
var incremented = arr.join("");
var tr = table.insertRow(-1);
tr.className = "row-" + i;
var cell = tr.insertCell(-1);
cell.textContent = "Cell ";
var span = document.createElement("span");
span.textContent = i + ": ";
var input = document.createElement("input");
input.className = "input-" + i;
input.value = incremented;
cell.appendChild(span);
cell.appendChild(input);
}
}
<table id="myTable">
<tr class="row-1">
<td>Cell <span>1: </span><input type="text" class="input-1" value="10012018"></td>
</tr>
</table><br>
<button onclick="addRows(5, '10012018', 3, 'myTable')">Try it</button>
<hr>
<table id="mySecondTable">
<tr class="row-1">
<td>Cell <span>1: </span><input type="text" class="input-1" value="14444"></td>
</tr>
</table><br>
<button onclick="addRows(8, '14444', 0, 'mySecondTable')">Try it</button>
I have an HTML table fetching values dynamically from the database and I have used the sum function to calculate the sum of entire column.
These are my columns where I am fetching the sum total of a column
<td id="totalValue13" style="background-color: darkseagreen;"></td>
<td id="totalValue11" style="background-color: darkseagreen;"></td>
<td id="totalValue12" style="background-color: darkseagreen;"></td>
I want to pass the value of these <td>s into a textbox where I want to calculate these three values. I am using JavaScript to calculate it, given below is a JavaScript code for calculations:
<script type="text/javascript">
function calculate() {
var result = document.getElementById('result');
var el, i = 0, total = 0;
while (el = document.getElementById('v'+(i++))) {
el.value = el.value.replace(/\\D/, "");
total = total + Number(el.value);
}
result.value = total;
if (document.getElementById('v0').value == "" && document.getElementById('v1').value == "" && document.getElementById('v2').value == "") {
result.value = "";
}
}
</script>
I just want to know how to pass the id of an HTML table column here. Thanks.
Use .innerHTML instead of .value since table cells don't have a value. Here is an example on how to calculate the sum of given table cells with each having a separate id.
function calculate()
{
var result = document.getElementById('result');
var v1 = document.getElementById('totalValue11');
var v2 = document.getElementById('totalValue12');
var v3 = document.getElementById('totalValue13');
var el, sum = 0;
var inputList = [v1,v2,v3];
for(var i=0; i<inputList.length; i++)
{
el = inputList[i];
if(el.innerHTML != '' && !isNaN(el.innerHTML))
{
sum += parseFloat(el.innerHTML);
}
}
result.value = sum; // If needed to write to cell use result.innerHTML = sum;
}
// Call it whenever you like
calculate();
td
{
background-color: darkseagreen;
}
<table>
<tr>
<td id="totalValue13">5</td>
<td id="totalValue11">3</td>
<td id="totalValue12">25</td>
</tr>
<tr>
<td colspan="2"><label for="result">Result:</label><input type="text" id="result" value="" readonly="readonly"></td>
</tr>
</table>
So I have a form that when you input a number in the Qty and Price boxes it totals them up in the Ext box as it should.
As you continue down the rows to add more Qty and price it continues to calculate the total and populates the Material Total as it should but it's not adding the tax and populating the Total box as it should be.
If you manually input an amount in the Material total box then the tax and total will automatically populate and the total is correct. I've tried using onChange, onKeyup, and even onInput but nothing seems to work.
Here is my sales tax script:
function tax(){
var material = document.getElementById( 'material' ).value;
var salestax = Math.round(((material / 100) * 8.1)*100)/100;
var total = (material*1) + (salestax * 1);
document.getElementById( 'material' ).value = material;
document.getElementById( 'salestax' ).value = salestax;
document.getElementById( 'total' ).value = total;
}
An here is the html related to the script:
<table>
<td style="width: 40px;">
<td style="width: 465px;" class="auto-style6">Material Total</td>
<td><input type="text" name="material_total"style="width: 55px"id="material"onChange="tax()"></td>
</table>
<table>
<td style="width: 40px;">
<td style="width: 465px;" class="auto-style6">Sales Tax</td>
<td><input type="text" name="sales_tax" style="width: 55px" id="salestax" onChange="tax()"></td>
</table>
<table>
<td style="width: 40px;">
<td style="width: 465px;" class="auto-style6">Shipping</td>
<td><input type="text" name="ship_cost" style="width: 55px" id="shipping"></td>
</table>
<table>
<td style="width: 40px;">
<td style="width: 465px;" class="auto-style6">Total</td>
<td><input type="text" name="total_parts_cost" style="width: 55px" id="total"></td>
</table>
Update to question: so after playing with it I found out the onpropertychange will make the form work but only in IE (I'm using IE 10) but not in firefox. I'm including the code that I use to total the Qty and Price boxes that auto populates the Ext box because that works and I use onkeyup. I don't understand why it wont work for the tax section.
enter code here function multiply1() {
var extend1 = 1;
for (var i = 1; i <= 2; i++) {
var id = "1_value" + i;
extend1 = extend1 * document.getElementById(id).value;
}
document.getElementById("extend1").value = extend1;
summate();
}
function multiply2() {
var extend2 = 1;
for (var i = 1; i <= 2; i++) {
var id = "2_value" + i;
extend2 = extend2 * document.getElementById(id).value;
}
document.getElementById("extend2").value = extend2;
summate();
}
function multiply3() {
var extend3 = 1;
for (var i = 1; i <= 2; i++) {
var id = "3_value" + i;
extend3 = extend3 * document.getElementById(id).value ;
}
document.getElementById("extend3").value = extend3;
summate();
}
function multiply4() {
var extend4 = 1;
for (var i = 1; i <= 2; i++) {
var id = "4_value" + i;
extend4 = extend4 * document.getElementById(id).value;
}
document.getElementById("extend4").value = extend4;
summate();
}
function multiply5() {
var extend5 = 1;
for (var i = 1; i <= 2; i++) {
var id = "5_value" + i;
extend5 = extend5 * document.getElementById(id).value;
}
document.getElementById("extend5").value = extend5;
summate();
}
function summate() {
var material = 0;
for (var i = 1; i <= 5; i++) {
var id = "extend" + i;
material = material + document.getElementById(id).value * 1;
}
document.getElementById("material").value = material;
}
I think I understand what you're asking: The onchange event is not firing for the material box because it is being changed programatically, and therefore will not fire.
You can fire this function manually. It appears that you are modifying the material box in your summate() function. To make the material box register a change, add the following line to the very end of the summate() function:
document.getElementById("material").onchange();
Hopefully that was what you wanted. I think you might have to add this sort of thing on some of the quantity or other fields as well if you want it to update whenever a box is modified.
EDIT: This will only work if you have the onchange attribute set for your material element (I noticed you changed it to oninput).
I am trying to replace a div tag that is the same on each row of a dynamically created table. I'm not sure how to go about it. Right now I can get the function to work but it only replaces the first row of div tags. Here is my code:
<script type="text/javascript">
function Calc() {
var qty = 0;
qty=parseInt(document.getElementById('qtyEntry').value);
var weight = parseInt(document.getElementById('weight').innerHTML);
var cube = parseInt(document.getElementById('cube').innerHTML);
var carton = parseInt(document.getElementById('carton').innerHTML);
var newWeight = 0;
var newCube = 0;
var newCarton = 0;
newWeight = qty *weight ;
newCube = qty * cube;
newCarton = qty * carton;
document.getElementById('weight').innerHTML = newWeight;
document.getElementById('cube').innerHTML = newCube;
document.getElementById('carton').innerHTML = newCarton;
}
#{int seq=0;
foreach (var item in Model)
{
seq++;
<tr>
<td>#seq</td>
<td>#item.sku</td>
<td>#item.description</td>
<td><input type=text id="qtyEntry" name="buildQty" size="3" onchange="Calc()"/></td>
<td> <div id="carton">#item.cartonQty</div></td>
<td> <div id="weight">#item.weight</div></td>
<td><div id="cube">#item.cube</div></td>
<td></td>
</tr>
}
}
So essentially I want to update the carton, weight and cube quantities when a user changes the text field for buildQty. I want each row to update. Right now only the first row updates even if I am updating the text on another row.
Glaring issue: id's are meant to be unique. Yours are not. So it only accesses the first one. Try this as a change:
markup:
<tr>
<td>#seq</td>
<td>#item.sku</td>
<td>#item.description</td>
<td><input type=text id="qtyEntry#(seq)" name="buildQty#(seq)" size="3" onchange="Calc(#(seq))"/></td>
<td> <div id="carton#(seq)">#item.cartonQty</div></td>
<td> <div id="weight#(seq)">#item.weight</div></td>
<td> <div id="cube#(seq)">#item.cube</div></td>
<td></td>
</tr>
js:
function Calc(seq) {
var qty = 0;
qty=parseInt(document.getElementById('qtyEntry'+seq).value);
var weight = parseInt(document.getElementById('weight'+seq).innerHTML);
var cube = parseInt(document.getElementById('cube'+seq).innerHTML);
var carton = parseInt(document.getElementById('carton'+seq).innerHTML);
var newWeight = 0;
var newCube = 0;
var newCarton = 0;
newWeight = qty *weight ;
newCube = qty * cube;
newCarton = qty * carton;
document.getElementById('weight'+seq).innerHTML = newWeight;
document.getElementById('cube'+seq).innerHTML = newCube;
document.getElementById('carton'+seq).innerHTML = newCarton;
}
But note! This could possibly change your model binding and you will need to revisit the way you are going to accept this from your post. I would assume it is not properly posting as it is right now because the name is also not unique (and that is part which has to do with model binding).
I am creating a form and I have a field set for client information and the ability to add another field set for another client if needed.
As of now the additional field sets' field id adds by 1 which is good, but I would like for each of the fields in the field set to add by 1 as well.
var _counter = 0;
function Add() {
_counter++;
var oClone = document.getElementById("client1").cloneNode(true);
oClone.id += (_counter + "");
document.getElementById("placehere").appendChild(oClone);
Here's a page that clones and increments the fieldset as well as any children elements within the set. It's assuming that both fieldset and children inputs have a numeric suffix. i.e. fieldset1 and textfield2, etc.
Cheers.
<!DOCTYPE html>
<html>
<head>
<script type='text/javascript'>
// store a reference to the last clone so I can increment off that.
window.lastClone = null;
function incrementId(id) {
// regexp is looking for text with a number suffix. adjust accordingly.
var numberSuffixRegExp = /(.*?)(\d*)$/;
var regExpMatch = numberSuffixRegExp.exec(id);
// assuming a match will be made here, and position 1 and 2 are populated.
var prefix = regExpMatch[1];
var counter = parseInt(regExpMatch[2]);
counter++;
return prefix + counter;
}
function cloneFieldSet() {
if (!window.lastClone) {
window.lastClone = 'fieldset1';
}
var newFieldSet = document.getElementById(lastClone).cloneNode(true);
newFieldSet.id = incrementId(newFieldSet.id);
var tagNames = ['input', 'select', 'textarea']; // insert other tag names here
var elements = [];
for (var i in tagNames) {
// find all fields for each tag name.
var fields = newFieldSet.getElementsByTagName(tagNames[i]);
for(var k = 0; k < fields.length; k++){
elements.push(fields[k]);
}
}
for (var j in elements) {
// increment the id for each child element
elements[j].id = incrementId(elements[j].id);
}
document.getElementById("placehere").appendChild(newFieldSet);
window.lastClone = newFieldSet.id;
}
</script>
</head>
<body>
<input type='button' value='Clone' onclick='cloneFieldSet()'/><br/>
<fieldset id='fieldset1'>
<table>
<tr>
<td>Label One:</td>
<td><input type='text' id='fieldOne1'/></td>
</tr>
<tr>
<td>Label Two:</td>
<td><input type='text' id='fieldTwo1'/></td>
</tr>
<tr>
<td>Label Three:</td>
<td><select id='selectOne1'>
<option>Some Value</option>
</select></td>
</tr>
</table>
</fieldset>
<div id='placehere' style='margin:10px 0; border:1px solid black'>
</div>
</body>
</html>
Try This : It only adds an updated id to user input form elements.
If you want to updated all child elements in the fieldset, remove the if statement :)
var _counter = 0, _fcounter = 0;
function add(){
var i, j,
oClone = document.getElementById("client1").cloneNode(true),
fldTypes = "INPUT SELECT TEXTAREA CHECKBOX RADIO",
fields = oClone.children;
_counter++;
oClone.id += (_counter + "");
for(i=0, j= fields.length; i<j; i++){
if(fldTypes.indexOf(fields[i].nodeName) > -1){ //checks for user input form elements
_fcounter ++;
fields[i].id += (_fcounter + "");
}
}
document.getElementById("placehere").appendChild(oClone);
return oClone;
}
See Example: http://jsfiddle.net/yfn6u/8/