Applying AutoNumeric.js to an entire class - javascript

I would love if someone could help me with what i thought would be a simple application of AutoNumeric.js. I have the below code:
Fiddle link: https://jsfiddle.net/yu1s9nrv/8/
<table id="shareInput" class="table_standard">
<tr>
<th>Name</th>
<th>Quantity</th>
<th>Price</th>
<th>Growth</th>
<th>Yield</th>
</tr>
<tr>
<td><input type="text" class="input_field_large" id="shareName" value=""></td>
<td><input type="text" class="input_field_medium_num" id="shareQty" value=""></td>
<td><input type="text" class="input_field_medium_dollar" id="sharePrice" value=""></td>
<td><input type="text" class="input_field_medium_pct" id="shareGrowth" value=""></td>
<td><input type="text" class="input_field_medium_pct" id="shareYield" value=""></td>
</tr>
<tr>
<td><input type="text" class="input_field_large" id="shareName" value=""></td>
<td><input type="text" class="input_field_medium_num" id="shareQty" value=""></td>
<td><input type="text" class="input_field_medium_dollar" id="sharePrice" value=""></td>
<td><input type="text" class="input_field_medium_pct" id="shareGrowth" value=""></td>
<td><input type="text" class="input_field_medium_pct" id="shareYield" value=""></td>
</tr>
</table>
<script>
window.onload = function() {
const anElement = new AutoNumeric('.input_field_medium_pct', 0, {
suffixText: "%"
});
};
</script>
The output I expect is for all the fields with the class input_field_medium_pct to have the desired AutoNumeric formatting, however it only formats the first field with that class. The documentation reads:
// The AutoNumeric constructor class can also accept a string as a css
selector. Under the hood this use QuerySelector and limit itself to
only the first element it finds. anElement = new
AutoNumeric('.myCssClass > input'); anElement = new
AutoNumeric('.myCssClass > input', { options });
Taken from: https://github.com/autoNumeric/autoNumeric#initialize-one-autonumeric-object
I'm new to JS the and find the AutoNumeric documentation notes to be slightly confusing, has anyone run into this issue or able to shed some light on why this might be the case? Thanks in advance.

You need to use Autonumeric.multiple to apply it to multiple elements as once.
const anElement = AutoNumeric.multiple('.input_field_medium_pct', 0, {
suffixText: "%"
});
Check the working jsfiddle
Also, check the documentation https://github.com/autoNumeric/autoNumeric#initialize-multiple-autonumeric-objects-at-once

Related

Value not displaying in correct input

I have a 2 row table with input fields that does a calculation when I focusout on the first input. The problem I am experiencing is when I focusout on the second row, my new value is displayed in the first row corresponding input. I'm not sure why this is happening. I would greatly appreciate your help.
My expectation is when I enter a value in a row input (Cost) and focusout the new value should be set in the same row but in the input (New Cost).
function Calculate(element) {
var dollar = 216.98;
var id = element.id;
var oldcost = $(element).val();
var newcost = oldcost * dollar;
$("#" + id).closest("tr").find("td #new").val(newcost);
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<table>
<tr>
<th>Cost</th>
<th>New Cost</th>
</tr>
<tr>
<td><input type="number" id="old" onfocusout="Caluculate(this)" /></td>
<td><input type="number" new="new" /></td>
</tr>
<tr>
<td><input type="number" id="old" onfocusout="Caluculate(this)" /></td>
<td><input type="number" new="new" /></td>
</tr>
</table>
There's several issues here. Firstly you're repeating the same id attribute which is invalid; they must be unique. I'd suggest using a class instead. Secondly, there's is no new attribute. I presume that's a typo and should be an id, but again see my first point.
Next, the function you defined is named Calculate() yet the call is to Caluculate().
Then you should also be using unobtrusive event handlers as on* event attributes are very outdated and should be avoided where possible. As you've already included jQuery in the page you can use the on() method. The input event would seem to be more applicable to your usage as well, especially given it also catches the up/down arrow usage on the number control, although you can change this to blur if preferred.
Finally, it's a simply a matter of amending your DOM traversal logic to work with the new classes, like this:
var dollar = 216.98;
$('.old').on('input', function() {
var oldcost = $(this).val();
var newcost = oldcost * dollar;
$(this).closest("tr").find(".new").val(newcost);
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<table>
<tr>
<th>Cost</th>
<th>New Cost</th>
</tr>
<tr>
<td><input type="number" class="old" /></td>
<td><input type="number" class="new" /></td>
</tr>
<tr>
<td><input type="number" class="old" /></td>
<td><input type="number" class="new" /></td>
</tr>
</table>
Your use of id's is kind of messed up. First of all be sure to use an id once in the entire HTML file.
For your usecase better use classes.
Also be sure to type your function names correct ;)
function Calculate(element) {
var dollar = 216.98;
var parent = $(element).closest('tr');
var oldcost = $(element).val();
var newcost = oldcost * dollar;
parent.find(".new").val(newcost.toFixed(2));
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<table>
<tr>
<th>Cost</th>
<th>New Cost</th>
</tr>
<tr>
<td><input type="number" class="old" onfocusout="Calculate(this)" /></td>
<td><input type="number" class="new" /></td>
</tr>
<tr>
<td><input type="number" class="old" onfocusout="Calculate(this)" /></td>
<td><input type="number" class="new" /></td>
</tr>
</table>
They have the same ID. You need to make the ID different
Firstly, there is a a typo.Change caluculate to calculate
There must not be the same id two elemnts have the same id.You could change the id of the first to old-1 or something different

How to access HTML array object in javascript?

sorry for asking simple question. I am really a beginner in Javascript. I need to access my HTML array form object in my javascript, but I don't know how to do it.
The goal is to trigger the alert in javascript so the browser will display message according to the condition in javascript. Here is my code :
checkScore = function()
{
//I don't know how to access array in HTML Form, so I just pretend it like this :
var student = document.getElementByName('row[i][student]').value;
var math = document.getElementByName('row[i][math]').value;
var physics = document.getElementByName('row[i][physics]').value;
if (parseInt(math) >= 80 ) {
alert(student + " ,You are good at mathematic");
}
if (parseInt(physics) >= 80 ){
alert(student + " ,You are good at physics");
}
student_score.row[i][otherinfo].focus();
student_score.row[i][otherinfo].select();
}
<h2>HTML Forms</h2>
<form name="student_score" action="/action_page.php">
<table border=1>
<thead>
<td>Student</td>
<td>Math Score</td>
<td>Physics Score</td>
<td>Other info</td>
</thead>
<tbody>
<tr>
<td><input type="text" name="row[1][student]"></td>
<td><input type="number" name="row[1][math]" onblur="checkScore()" min="0" max="100"></td>
<td><input type="number" name="row[1][physics]" onblur="checkScore()" min="0" max="100"></td>
<td><input type="text" name="row[1][otherinfo]"></td>
</tr>
<tr>
<td><input type="text" name="row[2][student]"></td>
<td><input type="number" name="row[2][math]" onblur="checkScore()" min="0" max="100"></td>
<td><input type="number" name="row[2][physics]" onblur="checkScore()" min="0" max="100"></td>
<td><input type="text" name="row[2][otherinfo]"></td>
</tr>
<tr>
<td>
<input type="submit" value="Submit">
</td>
</tr>
</tbody>
</table>
</form>
<p>If you click the "Submit" button, it will save the data.</p>
We are going to leverage few things here to streamline this.
The first is Event Listeners, this removes all javascript from your HTML. It also keeps it more dynamic and easier to refactor if the table ends up having rows added to it via javascript.
Next is parentNode, which we use to find the tr that enclosed the element that was clicked;
Then we use querySelectorAll with an attribute selector to get our target fields from the tr above.
/*This does the work*/
function checkScore(event) {
//Get the element that triggered the blur
var element = event.target;
//Get our ancestor row (the parent of the parent);
var row = element.parentNode.parentNode;
//Use an attribute selector to get our infor from the row
var student = row.querySelector("[name*='[student]']").value;
var math = row.querySelector("[name*='[math]']").value;
var physics = row.querySelector("[name*='[physics]']").value;
var otherField = row.querySelector("[name*='[otherinfo]']");
if (parseInt(math, 10) >= 80) {
alert(student + " ,You are good at mathematic");
}
if (parseInt(physics, 10) >= 80) {
alert(student + " ,You are good at physics");
}
otherField.focus();
otherField.select();
}
/*Wire Up the event listener*/
var targetElements = document.querySelectorAll("input[name*='math'], input[name*='physics']");
for (var i = 0; i < targetElements.length; i++) {
targetElements[i].addEventListener("blur", checkScore);
}
<h2>HTML Forms</h2>
<form name="student_score" action="/action_page.php">
<table border=1>
<thead>
<tr>
<td>Student</td>
<td>Math Score</td>
<td>Physics Score</td>
<td>Other info</td>
</tr>
</thead>
<tbody>
<tr>
<td><input type="text" name="row[1][student]" class='student'></td>
<td><input type="number" name="row[1][math]" min="0" max="100"></td>
<td><input type="number" name="row[1][physics]" min="0" max="100"></td>
<td><input type="text" name="row[1][otherinfo]"></td>
</tr>
<tr>
<td><input type="text" name="row1[2][student]"></td>
<td><input type="number" name="row[2][math]" min="0" max="100"></td>
<td><input type="number" name="row[2][physics]" min="0" max="100"></td>
<td><input type="text" name="row[2][otherinfo]"></td>
</tr>
<tr>
<td>
<input type="submit" value="Submit">
</td>
</tr>
</tbody>
</table>
</form>
Well, it follows your line of code exactly as it is (because you said you do not want to change the code too much).
<h2>HTML Forms</h2>
<form name="student_score" action="/action_page.php">
<table border=1>
<thead>
<td>Student</td>
<td>Math Score</td>
<td>Physics Score</td>
<td>Other info</td>
</thead>
<tbody>
<tr>
<td><input type="text" name="row[1][student]"></td>
<td><input type="number" name="row[1][math]" onblur="checkScore(this)" min="0" max="100"></td>
<td><input type="number" name="row[1][physics]" onblur="checkScore(this)" min="0" max="100"></td>
<td><input type="text" name="row[1][otherinfo]"></td>
</tr>
<tr>
<td><input type="text" name="row1[2][student]"></td>
<td><input type="number" name="row[2][math]" onblur="checkScore(this)" min="0" max="100"></td>
<td><input type="number" name="row[2][physics]" onblur="checkScore(this)" min="0" max="100"></td>
<td><input type="text" name="row[2][otherinfo]"></td>
</tr>
<tr>
<td>
<input type="submit" value="Submit">
</td>
</tr>
</tbody>
</table>
</form>
JavaScript [Edited again using part of the #Jon P code, the query selector is realy more dynamic, and the value of the "other" field you requested is commented out]
//pass element to function, in html, only add [this] in parenteses
checkScore = function (element) {
//Get our ancestor row (the parent of the parent);
var row = element.parentNode.parentNode;
//Use an attribute selector to get our infor from the row
var student = row.querySelector("[name*='[student]']").value;
var math = row.querySelector("[name*='[math]']").value;
var physics = row.querySelector("[name*='[physics]']").value;
var other = row.querySelector("[name*='[otherinfo]']");
if (parseInt(math) >= 80) {
//other.value = student + " ,You are good at mathematic";
alert(student + " ,You are good at mathematic");
}
if (parseInt(physics) >= 80) {
//other.value = student + " ,You are good at physics";
alert(student + " ,You are good at physics");
}
otherField.focus();
otherField.select();
}
Tested :), and sorry about my english!
Try that, haven't tested it
var form = document.getElementsByName("student_score")[0];
var students = form.getElementsByTagName("tr");
for(var i = 0; i < students.length; i++){
var student = students[i].childnodes[0].value;
var math = students[i].childnodes[1].value;
var physics = students[i].childnodes[2].value;
if (parseInt(math) >= 80 ) {
alert(student + " ,You are good at mathematic");
}
if (parseInt(physics) >= 80 ){
alert(student + " ,You are good at physics");
}
}

parseInt() functionis not working

I have a input element to accept number type. I know javascript takes input as a string. so I am using parseInt() to convert into integer. but it is not working.
My code is:
<tr>
<td rowspan="6"><br><br><br><br><br>B1<br> Salary/Pension:</td>
<td>(1) Salary (excluding all allowances, perquisites and profit in lieu of salary</td>
<td><input type="text" id="sal" value="0" name="sal" placeholder="" class="form-control "></td>
</tr>
<tr>
<td>(2) Allowances not exempt</td>
<td><input type="text" id="allowance" value="0" name="allowance" placeholder="" class="form-control "></td>
</tr>
<tr>
<td>(3)Value of perquisites</td>
<td><input type="text" id="perquisites" value="0" name="perquisites" placeholder="" class="form-control "></td>
</tr>
<tr>
<td>(4) Profits in lieu of salary</td>
<td><input type="text" id="profit" name="profit" value="0" placeholder="" class="form-control"></td>
</tr>
<tr>
<td>(5)Deduction u/s 16</td>
<td><input type="text" id="ded16" name="ded16" value="0" placeholder="" class="form-control"></td>
</tr>
<tr>
<td>(6)Income chargable under the head 'Salaries':</td>
<td><input type="text" id="inchargesal" value="0" name="inchargesal" placeholder="" class="form-control" readonly></td>
</tr>
//js part is:
$(document).ready(function() {
function change() {
f = a + b + c + d - e;
alert(f);
$('#inchargesal').removeAttr('readonly').val(f);
}
$('#sal').on('change', function() {
var a = parseInt(document.getElementsById("sal").value);
alert("hi");
change();
});
$('#allowance').on('change', function() {
b = parseInt(document.getElementById("allowance").value)
change();
});
$('#perquisites').on('change', function() {
c = parseInt(document.getElementsById("perquisites").value);
change();
});
$('#profit').on('change', function() {
d = parseInt(document.getElementsById("profit").value);
change();
});
$('#ded16').on('change', function() {
e = parseInt(document.getElementsById("ded16").value);
change();
});
});
here to notice is, when I use alert("hi") above the parseInt statement then alert works fine, however when I use it after that, alert("hi") doesn't work.
what's going wrong? please help.
You are using incorrect method of document. There is no such method saying getElementsById(). In HTML DOM the id field is unique so it can never be getElements but getElement. Use getElementById('id') to make it work.
Also its always better to check console first where most of your problems can be resolved on your own.
Console -

Get value of class with dynamic id jquery

I have the table bellow and I want to get the input $('.note') value from the id of the previous input :
<tr>
<td><input type="text" id='student_1' class='student'></td>
<td><input type="text" class='note'></td>
</tr>
<tr>
<td><input type="text" id='student_2' class='student'></td>
<td><input type="text" class='note'></td>
</tr>
So it can be something like that :
$(".student").change(function () {
alert(this.id.parent('td input.note').val())
})
You could use this.value or $(this).val() :
$('.classname').on('click',function(){
console.log(this.value, $(this).val(), this.id);
})
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<input type='text' class='classname' id="id_1" value='value_1'/>
<input type='text' class='classname' id="id_2" value='value_2'/>
<input type='text' class='classname' id="id_3" value='value_3'/>
<input type='text' class='classname' id="id_4" value='value_4'/>
Edit :
Go up to the parent tr using .closest('tr') then search for the related input note using .find('.note') and get the value :
$(".student").on('input', function () {
console.log( $(this).closest('tr').find('.note').val() );
})
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<table>
<tr>
<td><input type="text" id='student_1' class='student'></td>
<td><input type="text" class='note' value="1111"></td>
</tr>
<tr>
<td><input type="text" id='student_2' class='student'></td>
<td><input type="text" class='note' value="2222"></td>
</tr>
</table>
You can use a combination of closest and find.
$(".student").on('change', function () {
// the student input to which the change event is bound
var $this = $(this);
// Get the wrapper in which the inputs are present
var $closestTr = $this.closest('tr');
// the input vale that is needed
alert($closestTr.find('.note').val());
});
Yes, you can do this $('#' + this.id).val()
You don't need to include the class in the selector because IDs are unique.

Obtain location of input within table cell HTML

I have a a table with inputs inside each table cell like so:
<table width="300" border="1" align="center" id="mainTable">
<tr>
<td><input onkeyup="insertToArray(value)" size="1" maxlength="1" /></td>
<td><input onkeyup="insertToArray(value)" size="1" maxlength="1" /></td>
<td><input onkeyup="insertToArray(value)" size="1" maxlength="1" /></td>
<td><input onkeyup="insertToArray(value)" size="1" maxlength="1" /></td>
</tr>
</table>
I would like to know how to obtain the location (row and column) of an input within the table (using javascript). I know how to do it for a regular cell with nothing inside, but for an input within the cell I can't seem to find a way. The function inside the input is for another purpose.
Modify the call to the function insertToArray(value) to insertToArray(this) and then inside the function do
function insertToArray(elem){
...
var tdElem = elem.parentNode;
var trElem = tdElem.parentNode;
console.log("Row: " + trElem.rowIndex);
console.log("Column: " + tdElem.cellIndex);
...
}
If you are able to get a reference to the table cell, then you just have to get access to the children inside of that node.
You can use `childNodes' which returns a NodeList object and then you use the index to access the children so in your case, the input box.
example:
document.getElementById("firstTableCell").childNodes[0].value;
I adopted the following approach, though it uses the keyup listener from jquery:
HTML:
<table width="300" border="1" align="center" id="mainTable">
<tr>
<td><input size="1" maxlength="1" /></td>
<td><input size="1" maxlength="1" /></td>
<td><input size="1" maxlength="1" /></td>
<td><input size="1" maxlength="1" /></td>
</tr>
<tr>
<td><input size="1" maxlength="1" /></td>
<td><input size="1" maxlength="1" /></td>
<td><input size="1" maxlength="1" /></td>
<td><input size="1" maxlength="1" /></td>
</tr>
</table>
JS:
$("#mainTable input").keyup(function() {
var colIndex = $(this).parent()[0].cellIndex;
var rowIndex = $(this).parent()[0].parentElement.rowIndex;
})
Hope this helps!
It can be done in different ways, the code I included here is just to help you understand it better and depending on what you want to do, this is a nice easy approach to your issue. You can get the indexes instead, again, it depends on what you want to do.
HTML:
<table width="300" border="1" align="center" id="mainTable">
<tr class="row1">
<td><input class="tableCell" id="cell1" size="1" maxlength="1" /></td>
<td><input class="tableCell" id="cell2" size="1" maxlength="1" /></td>
<td><input class="tableCell" id="cell3" size="1" maxlength="1" /></td>
<td><input class="tableCell" id="cell4" size="1" maxlength="1" /></td>
</tr>
</table>
JS
window.onload = function() {
var cells = document.getElementsByClassName("tableCell");
for (var x = 0; x < cells.length; x++) {
cells[x].addEventListener("keyup", function(e) {
// get row class name:
var rowClass = (e.target).parentElement.parentElement.className;
alert("Row classname: " + rowClass);
// get the value insede the cell:
var cellValue = (e.target).value;
alert("Value entered: " + cellValue);
var cellId = e.target.id;
alert("Cell ID: " + cellId);
});
}
You could use a utility method that to looks for the closest parent
using a tag name:
Here's an example
function getClosestParent( needle, haystack ) {
var parent = null;
var target = needle.toUpperCase();
var element = haystack.parentElement;
while ( parent == null ) {
if ( element !== null ) {
if ( element.tagName === target ) {
parent = element;
}
}
else {
break;
}
element = element.parentElement;
}
return parent;
}
document.querySelector("input").addEventListener("click", function() {
var row = getClosestParent("tr", this)
var column = getClosestParent("td", this)
alert(row);
alert(column);
})
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<table width="300" border="1" align="center" id="mainTable">
<tr>
<td><input onkeyup="insertToArray(value)" size="1" maxlength="1" /></td>
</tr>
</table>
I've figured out a great way to do it.
I have 2 global variables representing the column and the row objects (tr, td)
function returnParent(x)
{
parentOfInput = x.parentNode; //td level
parentOfTd = parentOfInput.parentNode; //tr level
}
And I call this function alongside the other as well like so (note that I call returnParent() first since I want the position first thing when I enter something in input):
<table width="300" border="1" align="center" id="mainTable">
<tr>
<td><input onkeyup="returnParent(this); insertToArray(value);" size="1" maxlength="1" /></td>
<td><input onkeyup="returnParent(this); insertToArray(value);" size="1" maxlength="1" /></td>
<td><input onkeyup="returnParent(this); insertToArray(value);" size="1" maxlength="1" /></td>
<td><input onkeyup="returnParent(this); insertToArray(value);" size="1" maxlength="1" /></td>
Finally in my insertToArray(value) function, I get the column and row like so:
function insertToArray(value)
{
var a = value;
//get the cell position using parentNode
tableCol = parentOfInput.cellIndex;
tableRow = parentOfTd.rowIndex;
}

Categories

Resources