Ajax contact form that opens in a lightbox

In this tutorial we show how-to create a modern Ajax contact form using a Lightbox and jQuery. The form is linked by a simple text link and opens in the Lightbox where all form handling, including reCAPTCHA validations, are processed by PHP and the jQuery Ajax function. After the form submission was successful we are using the PHP Class script PHPMailer to send the message via SMTP.

There are many people having problems using the “lightbox” together with jQuery. We’re using the thickbox instead, a jQuery plugin which works perfect for most websites.

These days it’s very hard to prevent your e-mail box against spam if you like to get in touch with your website’s visitors. If you place some e-mail address on your website or even a regular contact form makes you possibly a victim of spam bots. There are many methods to protect your e-mail inbox against spam. The most common method is the spam filter, but you should use extra protections on your contact form page as well.

Previous Tutorials we have used for this application

Create custom reCAPTCHA images using their API
We use the reCAPTCHA API to create a user validation image to protect the form against spam attacks.

Sending e-mails via SMTP with PHPmailer and Gmail
We send e-mail messages using the PHPmailer script via SMTP, the mail function from this previous tutorial is the base for this tutorial as well.

Next we use the Ajax function from jQuery to send the form variables to our PHP e-mail script. This tutorial describes how-to to use all the functions in one application, please check the other tutorials if you need more information. We will not explain the code for PHPMailer and reCAPTCHA in this tutorial. You need an API key for the reCAPTCHA service.

Thickbox jQuery (lightbox) Plugin

As mentioned before we’re using for this tutorial the lightbox variant, the Thickbox plugin which is also a very flexible solution. If you visit the Thickbox website you will notice some “warning” from the developer, he says that he doesn’t continue the development. Since the application is not related to the Thickbox plugin, it should be easy to use that code with most other Lightbox and jQuery scripts as well.

Ajax contact form

This page is used to collect the users input, will validate the input on the client side and will post the data to the PHP e-mail script. Create a file with this code and call it contact-form.html

<html>
<head>
<title>Contact form</title>
<script type="text/javascript" src="jquery-1.3.2.min.js"></script>
<script type="text/javascript" src="http://api.recaptcha.net/js/recaptcha_ajax.js"></script>
<script type="text/javascript">

Next we have the jQuery script block for the form validations, Ajax contact form submission and the code to request the challenge image from the reCAPTCHA API.

After the document is loaded the reCAPTCHA images is added. If the user has clicked the button #submit_button the Ajax function is called with:

  • Options like the PHP e-mail script,
  • the form data,
  • the data type JSON,
  • a pre-submit handler for the form field validations
  • and a success handler that put the response into the #output container.
$(document).ready(function() { 	
	var RecaptchaOptions = { theme : 'custom' };
 	Recaptcha.create('your public key', 'recaptcha_image', RecaptchaOptions);
 	Recaptcha.focus_response_field();
	$('#submit_button').click(function() { 
		$.ajax({
			type: 'POST',
			url: 'email.php',
			data: $('form#myform').serialize(),
			dataType: 'json',
			beforeSend: function() {
				var resp_field = $('#recaptcha_response_field').val();
				var name = $('#name').val();
				var email = $('#email').val();
				var message = $('#message').val();
				if (!resp_field || !name || !email || !message) { 
					$('#output').html('All fields are required');
					return false; 
				}
				emailpat = /^([a-z0-9])+([\.a-z0-9_-])*@([a-z0-9])+(\.[a-z0-9_-]+)+$/i;
				if (!emailpat.test(email)) {
					$('#output').html('The e-mail address is not valid.'); 
					return false;
				}
			},
			success: function(response) {
				if (response.status == 'success') {
					$('#formcont').html('');
				}
				$('#output').html(response.errmessage);
			}
		});
	});
});

The form has just a few fields for name, e-mail address and message. Note the container with the ID reaptcha_image, this DIV element holds the reCAPTCHA challenge image.

</script>
</head>
<body>
	<h1>Contact form</h1>
	<div id="formcont">				
		<form id="myform">
			<p>
				<label for="naam">Name:</label>
				<input type="text" name="name" id="name" size="30" />
			</p>
			<p>
				<label for="email">E-mail:</label>
				<input type="text" name="email" id="email" size="30" />
			</p>
			<p>
				<label for="message">Message:</label>
				<textarea rows="5" cols="30" name="message" id="message"></textarea>
			</p>
			<div id="recaptcha_image"></div>
			<p>
				<input type="text" name="recaptcha_response_field" id="recaptcha_response_field" size="20" />
				<input type="button" value="Submit" id="submit_button" /> 
			</p>
		</form>
	</div>
	<div id="output"></div>
</body>
</html>

PHP e-mail script

So far the client side code, now we need an email script called email.php with following functions:

  • One that validates the submitted reCAPTCHA answer against the API,
  • has some basic validations on the server side (empty fields)
  • sends the e-mail message using the PHPmailer class,
  • and responds (echo) the message in JSON format.
IsSMTP(); // enable SMTP
			$mail->SMTPDebug = 0;  // debugging: 1 = errors and messages, 2 = messages only
			$mail->SMTPAuth = true;  // authentication enabled
			$mail->SMTPSecure = 'ssl'; // secure transfer enabled REQUIRED for Gmail
			$mail->Host = 'smtp.gmail.com';
			$mail->Port = 465; 
			$mail->Username = 'you at gmail dot com';
			$mail->Password = 'your gmail password';      
			$mail->SetFrom('you@website.com'); 
			$mail->Body = 'Name: '.$_POST['name'] . PHP_EOL . 
				'E-mail: ' . $_POST['email'] . PHP_EOL . PHP_EOL . 
				'Message:' . PHP_EOL . $_POST['message'];
			$mail->Subject = 'Some message from your site';
			$mail->AddAddress('Igetthe@mail.com');
			if (!$mail->Send()) {
				$resp['errmessage'] = 'Mail error: '.$mail->ErrorInfo;
			} else {
				$resp['errmessage'] = 'Message submitted succesfully!';
                                $resp['status'] = 'success';
			}
		} else {
			if ($response[1] == 'incorrect-captcha-sol') {
				$resp['errmessage'] = 'The entered text from the Captcha image is wrong.';
			} else {
				$resp['errmessage'] = 'Can\'t validate the Captcha image.';
			}
		}
	} else {
		$resp['errmessage'] = 'Missing required fields!';
	}
} 
echo json_encode($resp);
?>

If you have problems using Google (Gmail) as SMTP service provider, try ElasticEmail a very powerful SMTP mail provider. Signup for an account and send 25.000 mails to 10.000 contacts every month for FREE.

How-to use it on your website?

If you have finished both files you can use them on your site, upload the two created files, the jQuery library, the Thickbox (lightbox) jQuery plugin files and the PHPmailer class (if you don’t have those files on your server). Double check all the paths and add the jQuery library and the Thickbox plugin files to the page header from that page, where you like to place one or more Contact links:

<script type="text/javascript" src="jquery-1.3.2.min.js"></script>
<script type="text/javascript" src="thickbox.js"></script>
<link href="thickbox.css" rel="stylesheet" type="text/css" />

You don’t need to add more jQuery code because the required code is included inside the Thickbox plugin file. Use the following code for each link:

<a href="contact-form.html?TB_iframe=true&height=480&width=640" class="thickbox">Contact</a>

That’s all, if you have any questions please post them below. At the moment there is no demo but you can download the script code here.

Published in: jQuery Code · PHP Scripts

24 Comments

  1. “If you visit the Thickbox website you will notice some “warning” from the developer, he says that he doesn’t continue the development. If you don’t like to use the Thickbox plugin you need to use one of the other Lightbox plugins available on the Internet. Since the application is not related to the Thickbox plugin, it should be easy to use that code with most other Lightbox scripts as well.”
    Where I have been able to read about this?

    1. Yes that is right, but this information is several years old. In the meantime I used the thickbox in many projects. And of course other lightbox scripts are fine too.

  2. Hello. I have been trying to implement your code with some changes on a project I have. I am actually using the php mail() function to send emails generated on our website. I want to move the email box into a thickbox to mesh with the rest of the site. But I cannot get the thickbox to close upon clicking the submit button, and no information is POSTed. I have stripped out the CAPTCHA image as we do not need it, and renamed a few fields.

    If you look at my site, my name is the only one that actually has this code implemented so far.

  3. Hello Chuck,
    The target script is named “contact.php”, this is the same name as for the contact page where the link for the thickbox is placed. Try a third file to send the mail. You need an extra file because the response is needed on the client side for the message.

  4. Hi!

    Thanks for your script. I’m trying to customise it for my site and find that the “submit” button doesn’t go anywhere. I have inserted my own Captcha public & private keys and also updated the “Gmail” account data.

    Could you please let me know what I’m missing?

    Thanks.

  5. By the way, from the URL I have provided earlier, it’s straight from your sample file.

    I think there isn’t a connection between the ‘contact-form’ page with ’email’. The submit doesn’t process the Captcha codes or generate any error messages.

    Please help! I’ve spent days to work this out but can’t.

    Thanks again.

  6. Hi there,

    The URL is (http: // pato.com.au/ staging/ PrimalUnleashed /contact-form/ test.html)

    Also I have been using Firefox and Safari for testing but both are not working.

    Thanks in advance.

  7. Hi Patrick, you PHP host doesn’t provide JSON functions:

    Fatal error: Call to undefined function: json_encode()

    I get this error if I access your email.php script directly.

  8. Warning: require_once(PHPMailer/class.phpmailer.php) [function.require-once]: failed to open stream: No such file or directory in C:\AppServ\www\LapTrinhPHP\contact-form\email.php on line 2

    Fatal error: require_once() [function.require]: Failed opening required ‘PHPMailer/class.phpmailer.php’ (include_path=’.;C:\php5\pear’) in C:\AppServ\www\LapTrinhPHP\contact-form\email.php on line 2

    1. Hi,
      The error us related to non existing files or using the wrong file path. PHP is telling you where it looks. Just take care that the files are in the folder you’ve entered ;)

  9. Hello, I’ve been trying to get this form to work, but I’m having issues on the submit. I get an “undefined” error from the .ajax() call, but I’m not sure what the issue is. My email.php file seems to be setup correctly, can you take a look and give me some insight? Thanks!

    Form:
    http:// jwarbitrations.cochranetechsolutions.com/ContactForm.html

    Email.php:
    http:// jwarbitrations.cochranetechsolutions.com/email.php

  10. Hi Olaf –

    I noticed something I wanted to ask you about before I stripped out the reCaptcha code. There is a parameter, $_SERVER[“REMOTE_ADDR”]. I still have this code as you have displayed it here, and looking at the reCaptcha help, this is supposed to be the user’s address. Is this the case? Should I change this code to the user’s IP address, and if so, how do I do this? Thanks!

    1. Hello Kat,

      $_SERVER[“REMOTE_ADDR”] is a server variable which holds the IP address from each visitor, you don’t need to change this.

  11. I stripped out the reCaptcha code, and sure enough, the code works with no problems. Any suggestions on where to go from here to get the Captcha to work? Thanks in advance!

    1. Hello Kat,

      do you double checked all settings from reCaptcha? Compare both ID’s, the website’s domain/address you have entered for this IDs.

  12. Forgot to mention one thing, the status comes back as ‘parsererror’, and the error message is ‘undefined’

    1. change this code inside the php script

      if ($response[1] == 'incorrect-captcha-sol') {
      				$resp['errmessage'] = 'The entered text from the Captcha image is wrong.';
      			} else {
      				$resp['errmessage'] = 'Can't validate the Captcha image.';
      			}
      
      

      to this code

      if ($response[1] == 'incorrect-captcha-sol') {
      				$resp['errmessage'] = 'The entered text from the Captcha image is wrong.';
      			} else {
      				$resp['errmessage'] = 'Can't validate the Captcha image. Error code: '.$response[1];
      			}
      
      

      What kind of error code do you get?

  13. I did what you suggested, verified the reCaptcha keys, and replaced the code, all with the same results. Changing the code inside email.php didn’t do anything, because my .ajax function is coming back with an error (parsererror), so the response from email.php is bad. I added this code:

    error: function(test, status) {
    	alert("test: " + test + " | status: " + status);
    		}
    

    to my js file, and that’s how I know I’m getting an error, ‘status’ comes back as ‘parsererror.’

  14. I did finally get the code to work for me. The issue was with these two lines:

    $response = explode(PHP_EOL, $data);
    if ($response[0] == 'true') {
    

    For some reason, the explode function was not recognizing the first “PHP_EOL”, so it was combining the first and second array values, making it “true\nsuccess” for a correct response. Because of this, the next if statement was always false, making errmessage = “Can’t validate the Captcha image.” I changed the first line to this:

    $response = explode("\n", $data);
    

    and it worked. Thanks to Olaf for all his help with this.

    1. Kat,
      well done you found the problem. Line ends on windows systems are different from them on Linux systems.
      Thanks for sharing your solution!

Comments are closed.