Validating a form with JavaScript not working - javascript

I have this code:
function validate(form) {
var errors = 0;
els = form.elements;
for (var i=0; i<form.elements.length; i++) {
if (!els[i].value && els[i].tagName != "select") {
console.log(els[i]);
els[i].style.border = "1px solid red";
errors = 1;
}
}
console.log("Finished for loop");
var skuld_fast = document.getElementsByName("skuld_fast")[0];
var skuld_other = document.getElementsByName("skuld_other")[0];
if ((skuld_fast.value && !skuld_other.value) || (!skuld_fast.value && skuld_other.value)) {
skuld_fast.style.border = "1px solid red";
skuld_other.style.border = "1px solid red";
errors = 1;
}
console.log("Finished if statement for skuld_fast and skuld_other");
if (errors == 0) {
form.submit();
}
else {
alert("Eitthvað fór úrskeiðis.");
}
}
The HTML:
<form>
<input name="input1">
<select name="skuld_other">
(...)
</select>
<select name="skuld_fast">
(...)
</select>
<input type="button" onClick="validate(this.form);">
</form>
input1 works fine. skuld_other and skuld_fast do not, regardless of whether anything is selected or not. The console.log statements are both printed.
The statement I'm trying to make with this code is this: For each element (input or select) in the for loop of form.elements, if nothing has been written into the field, and the tag name of the element is not select, or it is the case that only either of skuld_fast and skuld_other have been chosen, then I set errors = 1.
I should note that for select I am using Select Picker: http://silviomoreto.github.io/bootstrap-select/

Related

document.getElementsByTagName is working but same functionality is not working with document.getElementById

I was trying to change the color of placeholder of input tag using Javascript. I am able to achieve that if I use document.getElementsByTagName, but if I am using document.getElementById then it's not working.
HTML:
<input name="txtfirstName" type="text" id="input" placeholder="First Name" />
<input type="button" name="Button1" value="Register" onclick="ChangePlaceHolderColor();" />
JavaScript (with document.getElementsByTagName):
function ChangePlaceHolderColor() {
var textBoxes = document.getElementsByTagName("input");
for (var i = 0; i < textBoxes.length; i++) {
if (textBoxes[i].type == "text") {
if (textBoxes[i].value == "") {
textBoxes[i].className += " Red";
}
}
}
}
JavaScript (with document.getElementById):
function ChangePlaceHolderColor() {
var textBoxes = document.getElementById("input");
for (var i = 0; i < textBoxes.length; i++) {
if (textBoxes[i].type == "text") {
if (textBoxes[i].value == "") {
textBoxes[i].className += " Red";
}
}
}
}
I am not able to figure why this is happening.
getElementById returns only 1 element, it is not an array
function ChangePlaceHolderColorx() {
var textBoxes = document.getElementsByTagName("input");
for (var i = 0; i < textBoxes.length; i++) {
if (textBoxes[i].type == "text") {
if (textBoxes[i].value == "") {
textBoxes[i].className += "Red";
}
}
}
}
function ChangePlaceHolderColor() {
var textBoxes = document.getElementById("input");
if (textBoxes.type == "text") {
if (textBoxes.value == "") {
textBoxes.className += "Red";
}
}
}
.Red{
color:red;
}
<input name="txtfirstName" type="text" id="input" placeholder="First Name" />
<input type="button" name="Button1" value="Register" onclick="ChangePlaceHolderColor();" />
You have to change function ChangePlaceHolderColor() to:
function ChangePlaceHolderColor() {
var textBoxes = document.getElementById("input");
if (textBoxes.type == "text") {
if (textBoxes.value == "") {
textBoxes.className += " Red";
}
}
}
this is because getElementByTagName() will return HTMLCollection which you can treat as an Array, but getElementById() will return only one element.
getElementsByTagName will always return an array of HTML elements, whereas getElementsById will always return a single HTML element.
function ChangePlaceHolderColor() {
//no loop because the return is one element.
var textBoxes = document.getElementById("input");
if (textBoxes.type == "text") {
if (textBoxes.value == "") {
textBoxes.className += " Red";
}
}
}
In HTML, element IDs must be unique on any given page.

Validating a form

IM working on a simple form, and Im trying to validate the fields,
with below code I able to validate the field and add a message if the field is empty.
}
First you need to scan the page for labels:
var labels = document.getElementsByTagName('LABEL');
for (var i = 0; i < labels.length; i++) {
if (labels[i].htmlFor != '') {
var elem = document.getElementById(labels[i].htmlFor);
if (elem)
elem.label = labels[i];
}
}
Then you can simply use following in your IF-ELSE condition,
document.getElementById(id).label.classList.add('red-text');
and
document.getElementById(id).label.classList.remove('red-text');
I also added CSS class for the text to be red.
.red-text {
color: #ff0000;
}
Final code:
function validation(id) {
var labels = document.getElementsByTagName('LABEL');
for (var i = 0; i < labels.length; i++) {
if (labels[i].htmlFor != '') {
var elem = document.getElementById(labels[i].htmlFor);
if (elem)
elem.label = labels[i];
}
}
var value = document.getElementById(id).value;
if (value === "" || value == null) {
document.getElementById('Err' + id).innerHTML = "- Field Required";
document.getElementById(id).classList.add('class');
document.getElementById(id).label.classList.add('red-text');
} else {
document.getElementById('Err' + id).innerHTML = "";
document.getElementById(id).classList.remove('class');
document.getElementById(id).label.classList.remove('red-text');
}
}
.class {
background: #f97d7d;
color: #ff0000;
border: 1px solid #ff0000 !important;
}
.red-text {
color: #ff0000;
}
<label for="Name">* Name <span class="error" id="ErrName"></span></label>
<input type="text" name="Name" id="Name" onblur="validation('Name')">
Change your javascript code to following:
function validation(id) {
var value = document.getElementById(id).value;
if (value === "" || value == null) {
document.getElementById('Err' + id).innerHTML = "- Field Required";
document.getElementById(id).classList.add('class');
var label = findLabel(document.getElementById('Name'));
label.classList.add('class');
} else {
document.getElementById('Err' + id).innerHTML = "";
document.getElementById(id).classList.remove('class');
var label = findLabel(document.getElementById('Name'));
label.classList.remove('class');
}
}
function findLabel(el) {
var idVal = el.id;
labels = document.getElementsByTagName('label');
for (var i = 0; i < labels.length; i++) {
if (labels[i].htmlFor == idVal)
return labels[i];
}
}
.class
{
background: #f97d7d;
color: #ff0000;
border: 1px solid #ff0000 !important;
}
<label class="" for="Name">* Name <span class="error" id="ErrName"></span></label>
<input type="text" name="Name" id="Name" onblur="validation('Name')">
I've added a function findLable to get the label for that input, and using that, added error class to that label.
The span is defined as class "error" but you haven't defined that class.
I think it is better to bind blur and input events
the code:
Name.addEventListener('blur', function(){
if (!Name.value){
ErrName.innerHTML="Field Required";
this.classList.add('class');
ErrName.parentNode.style.color="red";
}
});
Name.addEventListener('input',function(){
if (Name.value.length && ErrName.innerHTML=="Field Required" ){
ErrName.innerHTML="";
this.classList.remove('class');
ErrName.parentNode.style.color="black";
}
});
a liddle fiddle

onBlur change textbox background color

How can i change my textbox background and border color if return true from the function ? if return false my textbox background border will change, but when return true it remain red color. how can i fix this ? any help will be appreciated.
Javascript
function checkPostcode()
{
var message = "";
if (document.mainform.POSTCODE.value.length != 5)
{
message += "Invalid entry. Postcode must be in 5 number.";
}
else
{
for (var i = 0; i < document.mainform.POSTCODE.value.length; i++)
{
var f = document.mainform.POSTCODE.value.charAt(i);
if (!(parseFloat(f) >= 0) || !(parseFloat(f) <= 9))
{
var jdap = "no";
}
}
if (jdap=="no")
{
message += "Invalid entry. Please enter numbers only.";
}
}
if (message != "")
{
document.getElementById("posterrMsg").innerHTML = message;
document.getElementById("posterrMsg").style.display = "inline";
document.getElementById("POSTCODE").style.border = "thin solid red";
document.getElementById("POSTCODE").style.background = "#FFCECE";
document.mainform.POSTCODE.value = "";
document.mainform.POSTCODE.focus();
return false;
}
else{
document.getElementById("posterrMsg").innerHTML = "";
document.getElementById("posterrMsg").style.display = "";
document.getElementById("POSTCODE").style.border = "thin solid #CCCCCCC";
document.getElementById("POSTCODE").style.background = "FFFFFF";
return true;
}
}
HTML
<label id="posterrMsg" class="errMsg"></label>
<input type="text" name="POSTCODE" id="POSTCODE" value="<%=POSTCODE%>" onblur="checkPostcode();" maxlength="5" />
Just change
document.getElementById("POSTCODE").style.border = "thin solid #CCCCCCC";
to
document.getElementById("POSTCODE").style.border = "";
Another option:
document.getElementById("POSTCODE").className = "validPostcode";
or
document.getElementById("POSTCODE").className = "invalidPostcode";
If you want to add more styling.
Both are valid options here.
I would refactor your code a bit and maybe create an outer function which calls checkPostcode for validation.
Use !== so
if (message !== "")
so that you are checking the same type and value.
You also had a couple of typeos in your background colours.
See working JSFiddle here

How could I accomplish this with Jquery?

How can I make it so Jquery checks that ESNStart and ESNEND in the HTML form are in the same range otherwise it throws an alert saying that both numbers need to be in the same range to the user after typing in the value for ESNEnd ??
I still don't understand how I could also make it so ESNList gets checked for all its multiple values entered in the text field to be in the same range otherwise it also throws an alert to the user to enter a number in the same range as shown by the if statements ? A fiddle demonstrating this would help me learn so much , thanks a bunch !
<html>
<head>
<script type="text/javascript" src="jquery/jquery-1.8.3.js"></script>
<script type="text/javascript">
$(function() {
$(":text").css("border", "2px solid red");
$(":text").keyup(function() {
var enteredData = $(this).val()
console.log(enteredData);
if (enteredData == "") {
$(this).css("border", "2px solid red");
} else {
$(this).css("border", "inherit");
}
if ($(this).attr("id") == "ESNList") {
esnList = parseInt(enteredData);
switch (true) {
case (esnList >= 986329 && esnList <= 999999):
$("#ddl_StxName").val("stx2");
$("#ddl_rtumodel").val("globalstar");
break;
case (esnList >= 660000 && esnList <= 699999):
$("#ddl_StxName").val("mmt");
$("#ddl_rtumodel").val("globalstar");
break;
case (esnList >= 200000 && esnList <= 299999):
$("#ddl_StxName").val("stm3");
$("#ddl_rtumodel").val("stmcomtech");
break;
case (esnList >= 1202114 && esnList <= 1299999):
$("#ddl_StxName").val("smartone");
$("#ddl_rtumodel").val("globalstar");
break;
}
}
});
});
</script>
</head>
<body>
<form id="provision">ESNList:
<input type="text" id="ESNList" name="ESNList" size="30" />
<br />ESN Start:
<input type="text" id="ESNStart" name="ESNStart" size="10" />
<br />ESN End:
<input type="text" id="ESNStart" name="ESNStart" size="10" />
<br />UnitName:
<input type="text" id="STxName" name="STxName" size="30" />
<br />Unit Model:
<select name="STxName" id="ddl_StxName">
<option value="stx2">STX2</option>
<option value="stm3" selected>STM3</option>
<option value="acutec">Acutec</option>
<option value="trackpack">Trackpack</option>
<option value="mmt">MMT</option>
<option value="smartone">Smartone</option>
<option value="smartoneb">SmartOneB</option>
</select>
<br />RTU Model Type:
<select name="rtumodel" id="ddl_rtumodel">
<option value="globalstar">GlobalStar</option>
<option value="both">Both</option>
<option value="comtech">Comtech</option>
<option value="stmcomtech">STMComtech</option>
</select>
<br />
<input type="submit" value="submit" />
</form>
</body>
</html>
I created some methods that seem to work, although I haven't created groups of numbers that are out of range.
I strongly suggest you don't allow user to enter comma separated lists as it will be hard to point to user the invalid entries. It would be a lot cleaner having each number in it's own input. You can easily add a button for "Add new number" and create a new input for it.
I used arrays to store ranges and the values for the valid range that get changed for other fields. This module is not trivial and suggest you create a testing sandbox with a wide variety of numbers you can test with.
$('#ESNList').keyup(function(){
var enteredData = $(this).val();
$(this).removeClass('valid');
if( enteredData == ''){
return;
}
if(hasMultipleValues(enteredData)){
var range=rangeCheckMultipleNumbers(enteredData)
if( range===false){
log('Numbers not in same range');
return;
} else{
setRangeValues(range);
$(this).addClass('valid');
}
}
var rangeIdx = getRangeIndex(enteredData);
if(rangeIdx===false){
log('Number not in range');
}else{
setRangeValues(rangeIdx);
$(this).addClass('valid');
}
});
function hasMultipleValues( str){
/* second test for a singel entry with comma at end*/
return str.indexOf(',') !=-1 && str.indexOf(',') != str.length-1;
}
var ranges = [
[986329, 999999],
[660000, 699999],
[200000, 299999],
[1202114, 1299999]
];
var rangeText = [
["stx2", "globalstar"],
["mmt", "globalstar"],
["stm3", "stmcomtech"],
["smartone", "globalstar"]
]
/* returns range index if all in same range, otherwise returns false*/
function rangeCheckMultipleNumbers(str) {
var nums = str.split(',');
var rangeMatch = true; /* clean array to remove empty values if extra commas*/
nums = $.grep(array, function(item, index) {
return parseInt(item);
});
var groupRange = getRangeIndex(nums[0]);
if(nums.length > 1) {
for(i = 1; i < nums.length; i++) {
if(!checkSameRange(nums[i - 1], nums[i])) {
rangeMatch = false;
}
}
}
return rangeMatch ? groupRange : false;
}
function setRangeValues(rangeIndex) {
$("#ddl_StxName").val(rangeText[rangeIndex][0]);
$("#ddl_rtumodel").val(rangeText[rangeIndex][1]);
}
function checkSameRange(num1, num2) {
return getRangeIndex(parseInt(num1, 10)) == getRangeIndex(parseInt(num2, 10));
}
/* returns false if out of range, otherwise returns range index*/
function getRangeIndex(num) {
var idx = false;
$.each(ranges, function(i, range) {
if(num >= range[0] && num <= range[1]) {
idx = i;
return false;
}
});
return idx;
}
DEMO: http://jsfiddle.net/hXsQ8/1/

Fast way to validate if all checkboxes are un-selected?

Is there a quick way or function that would tell me true/false if all check boxes are deselected? Without going through array? (with JS and HTML)
All my check boxes have the same name...
<form action="/cgi-bin/Lib.exe" method=POST name="checks" ID="Form2">
<input type=checkbox name="us" value="Joe" ID="Checkbox1">
<input type=checkbox name="us" value="Dan" ID="Checkbox2">
<input type=checkbox name="us" value="Sal" ID="Checkbox3">
</form>
jQuery would be a mass of unneeded bloat for a task this trivial. Consider using it if you are running it for other purposes, but all you need is something like this:
function AreAnyCheckboxesChecked () {
var checkboxes = document.forms.Form2.elements.us;
for (var i = 0; i < checkboxes.length; i++) {
if (checkboxes[i].checked) {
return true;
}
}
return false;
}
You have to loop through them. Even a library like jQuery will loop through them, just hide it from you.
var form = document.getElementById('Form2');
var inputs = form.getElementsByTagName('input');
var is_checked = false;
for(var x = 0; x < inputs.length; x++) {
if(inputs[x].type == 'checkbox' && inputs[x].name == 'us') {
is_checked = inputs[x].checked;
if(is_checked) break;
}
}
// is_checked will be boolean 'true' if any are checked at this point.
JavaScript:
var allischecked = (function(){
var o = document.getElementById("Form2").getElementsByTagName("input");
for(var i=0,l=o.length;i<l;i++){
o[i].type === "checkbox" && o[i].name === "us" && o[i].checked || return false;
}
return true;
})();
With jQuery:
var allischecked = ($("#Form2 input:checkbox:not(checked)").length === 0);
In summary, this snipped will return true if all are NOT checked. It bails out as soon as a checked one is found.
var a = document.getElementsByName("us");
for(var i=0; i<a.length; i++)
if(a[i].checked)
return false;
return true;
(did not test, but conceptually it is valid)
What do you mean by
Without going through array
?
You could just do
function check() {
var anyChecked = false;
var form = document.getElementById('Form2');
var checkboxes = form.getElementsByTagName('input');
for(var i=0; i < checkboxes.length; i++) {
if (checkboxes[i].checked) {
anyChecked = true;
break;
}
}
alert("Checkboxes checked? " + anyChecked);
}
Working Demo
If you have a large amount of checkboxes that you don't want to loop through to test it might be more efficient to use this approach.
var checked = 0;
$("input[type=checkbox]").live("click", function() {
if($(this).attr("checked")) checked++;
else checked--;
}
Then you would be able to test like this.
if(checked === 0) {
doSomething();
}
The proper solution with jQuery attribute checked:
$checkboxes = $('#Form2 input:checkbox');
$checkboxes.on('click', checkboxes);
function checkboxes() {
var allChecked = $checkboxes.not(':checked').length == 0;
console.log(allChecked);
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.0.0/jquery.min.js"></script>
<form action="/cgi-bin/Lib.exe" method=POST name="checks" ID="Form2">
<input type=checkbox name="us1" value="Joe" ID="Checkbox1"><label>Joe</>
<input type=checkbox name="us2" value="Dan" ID="Checkbox2"><label>Dan</>
<input type=checkbox name="us3" value="Sal" ID="Checkbox3"><label>Sal</>
</form>
Even easier without loop
const toggleCheckboxes = checkbox => {
if(checkbox.checked){
return true
}else{
if(document.querySelectorAll(':checked').length === 0){
// All are unchecked
return false
}
}
}

Categories

Resources