Javascript help? (form validation)

I have a very basic form validation script, that is very old, and stopped working in Firefox around the time it got to v3.0.

I’ve already done some googling trying to find a replacement script, but the most recent articles I can find are from around 2005. And most are older than that.

It doesn’t have to be super fancy – if all it does is make sure the required fields aren’t empty, that would be enough – but neither would I object to a more complete script which checks the email and/or phone fields for validly formatted input.

You can see the form in action here.

And the code:




<h2>Via Email (<span class="required">»</span> indicates required field)</h2>
		
  <form name="contact" id="contact" action="thankyou.php" method="post" onSubmit="return validateform()">
		
	<script language="JavaScript">
			// browser check
			ns4 = (document.layers)? true:false
			ie4 = (document.all)? true:false
		
			function layerWrite(id,text) {
				if (ns4) {
					// var lyr = eval("document." + id + ".document");
					var lyr = document.desc.document;
					lyr.open()
					lyr.write(text)
					lyr.close()
				}
				else if (ie4) document.all[id].innerHTML = text
			}
		
			function validateform() {
				var errormsg = "";
				if (document.contact.name.value == "") {
					errormsg = "Please complete all required fields.";
				}
		
				if (document.contact.emailaddr.value == "") {
					errormsg = "Please complete all required fields.";
				}
		
				if (document.contact.phone.value == "") {
					errormsg = "Please complete all required fields.";
				}
		
				if (document.contact.service.value == "") {
					errormsg = "Please complete all required fields.";
				}
				
				if (document.contact.messagetext.value == "") {
					errormsg = "Please complete all required fields.";
				}
		
				if (errormsg == "") {
					return true;
				} else {
					layerWrite( "desc", errormsg );
					return false;
				}
			}
		</script>
	 <div id="desc"> </div>
	 <p><span class="required">»</span> Name:  <input name="name" type="text" style="position:relative; left:25px;"><br>
	 <span class="required">»</span> Email: <input name="emailaddr" type="text" style="position:relative; left:28px;"><br>
	 <span class="required">»</span> Phone: <input name="phone" type="text" style="position:relative; left:21px;"></p>
	 <p><span class="required">»</span> Which service are you interested in? 
	 	<select name="service" style="position:relative; left:50px;">
		  <option value="" selected>Please select</option>
		  <option value="Gameheads">Gameheads</option>
		  <option value="Birds">Birds</option>
		  <option value="Lifesize">Lifesize</option>
		  <option value="Fish">Fish</option>
		  <option value="Showroom">Showroom</option>
		  <option value="Other">Other</option>
		</select>
		<br>
		How did you hear about Sportsman's Image?  
		<input name="referredby" type="text" style="position:relative; left:13px;"></p>
		<p><span class="required">»</span> Message: 
		<textarea name="messagetext" cols="30" rows="3" style="position:relative; left:10px; vertical-align:text-top;"></textarea></p>
		<input type="submit" value="Submit" style="position:relative; left:185px;">
  </form>



TIA.

Skip the (broken) browser detection parts, just use the innerHTML thingy - every browser that supports javascript should support it by now.

DON’T use document.elementname.elementname.value stuff. That will only work reliably in IE and has never been standard anyway.

Easiest is probably to use document.getElementById(idOfFormElement).value instead and give every form element an ID identical to its name. Except for “service” -that would be document.getElementById(“service”).options[document.getElementById(“service”).selectedIndex].value

It’s possible to clear that up a bit more, but I’m assuming you can do that yourself.

I’ll take whatever help you can give. I’m a design-brain, not a programming-brain. The extent of my programming ability is to swap out the field names to match the form fields I have rather than the ones originally in the script.

Frex, how do I rewrite the layerWrite function? I gather that the if/else statements go away, so then is it just this?




function layerWrite(id,text) {
     document.all[id].innerHTML = text
			}


Just use




function layerWrite(id,text) {
     document.getElementById(id).innerHTML = text
}


It’s much more reliable. This is a pretty accurate introduction to simple but portable “DHTML” scripting.

Well, I made those edits and now it doesn’t work at all. In either Firefox or IE, I can click Submit without filling out any field at all and it goes right through.

Actually, I don’t really care about keeping this particular script, if someone can point me to a canned script (that’s more recent than 2005) that does what I need and is simple enough to figure out where and how to edit to put in my field names.

The edits:




<h2>Via Email (<span class="required">»</span> indicates required field)</h2>
		
<form name="contact" id="contact" action="thankyou.php" method="post" onSubmit="return validateform()">
		
	<script language="JavaScript">
		function layerWrite(id,text) {
			document.getElementById(id).innerHTML = text
		}
		
		function validateform() {
			var errormsg = "";
			if (document.getElementById(name).value == "") {
				errormsg = "Please complete all required fields.";
			}
		
			if (document.getElementById(emailaddr).value == "") {
				errormsg = "Please complete all required fields.";
			}
		
			if (document.getElementById(phone).value == "") {
				errormsg = "Please complete all required fields.";
			}
		
			if (document.getElementById("service").options[document.getElementById("service").selectedIndex].value == "") {
				errormsg = "Please complete all required fields.";
			}
			if (document.getElementById(messagetext).value == "") {
				errormsg = "Please complete all required fields.";
			}
		
			if (errormsg == "") {
				return true;
			} else {
				layerWrite( "desc", errormsg );
				return false;
			}
		}
	</script>

		<div id="desc"> </div>

		<p><span class="required">»</span> Name:  <input name="name" type="text" style="position:relative; left:25px;"><br>
		<span class="required">»</span> Email: <input name="emailaddr" type="text" style="position:relative; left:28px;"><br>
		<span class="required">»</span> Phone: <input name="phone" type="text" style="position:relative; left:21px;"></p>
		<p><span class="required">»</span> Which service are you interested in? 
			<select name="service" style="position:relative; left:50px;">
			  <option value="" selected>Please select</option>
			  <option value="Gameheads">Gameheads</option>
			  <option value="Birds">Birds</option>
			  <option value="Lifesize">Lifesize</option>
			  <option value="Fish">Fish</option>
			  <option value="Showroom">Showroom</option>
			  <option value="Other">Other</option>
			</select>
		<br>
		How did you hear about Sportsman's Image?  
		<input name="referredby" type="text" style="position:relative; left:13px;"></p>
		<p><span class="required">»</span> Message: 
		<textarea name="messagetext" cols="30" rows="3" style="position:relative; left:10px; vertical-align:text-top;"></textarea></p>
		<input type="submit" value="Submit" style="position:relative; left:185px;">
		</form>



You need to put the element IDs in quotes like you have with “service”. It’s document.getElementById(“id”).value

If you just use a word w/o quotes it’s looking for a variable where there is none.

Also, if you don’t already, use Firefox’s Error Console to see specific errors for troubleshooting.

Well, I put them in quotes, which made it work in IE, but still broken (in the same way) in Firefox. I can submit the form even if it’s blank, it doesn’t validate at all.

I’ve tried Firebug, turned on JavaScript debugger, but it doesn’t seem to actually do anything. If it’s supposed to highlight something, or make note of errors in some way, it doesn’t.

Okay, trying something new.

But again, after modifying the script for my own form, it works in IE but not in Firefox. In Firefox it again, just submits the form without checking anything.

The original script works fine in both browsers. All I did was add in the stuff for the phone number and changed “gender” to “service”; both of which worked when I tested it by modifying the sample form included with the source code.
WTF am I doing wrong?

http://autumneve.com/SportImg/contact-test.php

It’s embedded in the head of the page, so View Source might be easiest, but I’ll include the script here:



<script language="javascript" type="text/javascript">
// form validation function //
function validate(form) {
  var name = form.name.value;
  var email = form.email.value;
  var phone = form.phone.value;
  var service = form.service.value;
  var message = form.message.value;
  var nameRegex = /^[a-zA-Z]+(([\'\,\.\- ][a-zA-Z ])?[a-zA-Z]*)*$/;
  var emailRegex = /^[\w-\.]+@([\w-]+\.)+[\w-]{2,4}$/;
  var phoneRegex = /^((\+\d{1,3}(-| )?\(?\d\)?(-| )?\d{1,5})|(\(?\d{2,6}\)?))(-| )?(\d{3,4})(-| )?(\d{4})(( x| ext)\d{1,5}){0,1}$/;
  var messageRegex = new RegExp(/<\/?\w+((\s+\w+(\s*=\s*(?:".*?"|'.*?'|[^'">\s]+))?)+\s*|\s*)\/?>/gim);
  if(name == "") {
    inlineMsg('name','You must enter your name.',2);
    return false;
  }
  if(!name.match(nameRegex)) {
    inlineMsg('name','You have entered an invalid name.',2);
    return false;
  }
  if(email == "") {
    inlineMsg('email','<strong>Error</strong><br />You must enter your email.',2);
    return false;
  }
  if(!email.match(emailRegex)) {
    inlineMsg('email','<strong>Error</strong><br />You have entered an invalid email.',2);
    return false;
  }
    if(phone == "") {
    inlineMsg('phone','<strong>Error</strong><br />You must enter your phone.',2);
    return false;
  }
  if(!phone.match(phoneRegex)) {
    inlineMsg('phone','<strong>Error</strong><br />You have entered an invalid phone.',2);
    return false;
  }
  if(service == "") {
    inlineMsg('service','<strong>Error</strong><br />You must select a service.',2);
    return false;
  }
  if(message == "") {
    inlineMsg('message','You must enter a message.');
    return false;
  }
  if(message.match(messageRegex)) {
    inlineMsg('message','You have entered an invalid message.');
    return false;
  }
  return true;
}

// START OF MESSAGE SCRIPT //

var MSGTIMER = 20;
var MSGSPEED = 5;
var MSGOFFSET = 3;
var MSGHIDE = 3;

// build out the divs, set attributes and call the fade function //
function inlineMsg(target,string,autohide) {
  var msg;
  var msgcontent;
  if(!document.getElementById('msg')) {
    msg = document.createElement('div');
    msg.id = 'msg';
    msgcontent = document.createElement('div');
    msgcontent.id = 'msgcontent';
    document.body.appendChild(msg);
    msg.appendChild(msgcontent);
    msg.style.filter = 'alpha(opacity=0)';
    msg.style.opacity = 0;
    msg.alpha = 0;
  } else {
    msg = document.getElementById('msg');
    msgcontent = document.getElementById('msgcontent');
  }
  msgcontent.innerHTML = string;
  msg.style.display = 'block';
  var msgheight = msg.offsetHeight;
  var targetdiv = document.getElementById(target);
  targetdiv.focus();
  var targetheight = targetdiv.offsetHeight;
  var targetwidth = targetdiv.offsetWidth;
  var topposition = topPosition(targetdiv) - ((msgheight - targetheight) / 2);
  var leftposition = leftPosition(targetdiv) + targetwidth + MSGOFFSET;
  msg.style.top = topposition + 'px';
  msg.style.left = leftposition + 'px';
  clearInterval(msg.timer);
  msg.timer = setInterval("fadeMsg(1)", MSGTIMER);
  if(!autohide) {
    autohide = MSGHIDE;  
  }
  window.setTimeout("hideMsg()", (autohide * 1000));
}

// hide the form alert //
function hideMsg(msg) {
  var msg = document.getElementById('msg');
  if(!msg.timer) {
    msg.timer = setInterval("fadeMsg(0)", MSGTIMER);
  }
}

// face the message box //
function fadeMsg(flag) {
  if(flag == null) {
    flag = 1;
  }
  var msg = document.getElementById('msg');
  var value;
  if(flag == 1) {
    value = msg.alpha + MSGSPEED;
  } else {
    value = msg.alpha - MSGSPEED;
  }
  msg.alpha = value;
  msg.style.opacity = (value / 100);
  msg.style.filter = 'alpha(opacity=' + value + ')';
  if(value >= 99) {
    clearInterval(msg.timer);
    msg.timer = null;
  } else if(value <= 1) {
    msg.style.display = "none";
    clearInterval(msg.timer);
  }
}

// calculate the position of the element in relation to the left of the browser //
function leftPosition(target) {
  var left = 0;
  if(target.offsetParent) {
    while(1) {
      left += target.offsetLeft;
      if(!target.offsetParent) {
        break;
      }
      target = target.offsetParent;
    }
  } else if(target.x) {
    left += target.x;
  }
  return left;
}

// calculate the position of the element in relation to the top of the browser window //
function topPosition(target) {
  var top = 0;
  if(target.offsetParent) {
    while(1) {
      top += target.offsetTop;
      if(!target.offsetParent) {
        break;
      }
      target = target.offsetParent;
    }
  } else if(target.y) {
    top += target.y;
  }
  return top;
}

// preload the arrow //
if(document.images) {
  arrow = new Image(7,80); 
  arrow.src = "images/msg_arrow.gif"; 
}
</script>



Change the line


var targetdiv = document.getElementById(target);

to


var targetdiv = document.getElementById('msg');

; variable “target” is not defined.

Or dump Javascript all together.

I see you use PHP. Consider this secure PHP script —> http://www.dagondesign.com/articles/secure-php-form-mailer-script/

Nevermind, I figured it out. The form fields need an id attribute for the script to work.

Thanks, seems I got it now.