Computers and Technology
Custom E-mail Form
AH! So I have to create a custom e-mail sending form. He wants me to create a webform that will ask for a person’s name and e-mail address. Once those are input, an e-mail will be sent to the person’s e-mail account with a thank you message. Meanwhile, the website will reload with a custom coupon that bears their name. I’ll need it printable so I’ll have to add a print button as well.
Sounds simple enough, right?.. right?
First off, go create a coupon. After you’re done with that, we can start working. Make sure the “name” field is left out though, we’ll add that in later with some CSS. Originally, I wanted to send the coupon in the e-mail, forcing the customer to input the right e-mail address but I realized that most e-mail clients do not support CSS and especially not the “position: absolute;” property and value.
Tip: I update the script periodically, and have numerous times while writing this tutorial. None of the scripts mentioned in this post are necessarily WRONG but at the bottom of the page is the current “release” that I’ve created. The images may not correspond directly with the code they represent.
Setup
Alright, here’s what you’ll need to do. You need to download MIME (MultiplePurpose Internet Mail Extensions), which is an e-mail extension for php that allows you to send HTML e-mails. If your site operates under c-panel, like mine is, then just scroll down, find the PHP extension icon. Search for “MIME” and install the packages. If you need to install them manually, search through google “Installing MIME on” your OS. I cannot really help you out more than that because I am not an expert on PHP extensions. There are multiple guides online though that WILL help you out.
Once you press install, the package will automatically install. It may ask if it can install other dependent packages, simply OK it.
Basic Form
Let’s start scripting. I advise you to create a mail.php form that you can “include ()” or “require()” into your existing website. It’s much neater this way and the PHP won’t get in the way of your layout. Here’s the basic form I created for our purposes:
<form action="<?php $_SERVER['PHP_SELF'];?>" method="post"> Name:<br /> <input type="text" name="name" maxlength="41" /><br /> E-mail address:<br /> <input type="text" name="email" maxlength="40" /><br /> Message (<i>optional</i>):<br /> <textarea name="optmessage" cols="30" rows"10" maxlength"140"></textarea><br /> <input type="submit" name="submit" value="save" /> </form>
I used the “$_SERVER['PHP_SELF']” variable for the action so that we won’t have to create yet another script page to use the information. The “name” field will translate to $_POST['name'], the”e-mail address” into $_POST['email'], and the optional “message” into $_POST['optmessage']. There is nothing much more to it. I used maxlength for the name 41 characters because my full fictional name, “Captain Soren William Alexander Janus VI.”, is exactly 41 characters long . 40 characters for the e-mail seems sufficient enough as well. 140 character message is the same as twitter’s max tweet. There is nothing much else to this.
Are you feeling “Loopy”?
Let’s move on. We need to create a loop that will ensure our data has been entered and that we are not dealing with a blank form. The purpose of this basic loop is to show the initial form for the user to submit the data to, reload the form if any errors were made during submission (ie invalid entries), and send the email in the end.
<?php
if (!isset($_POST['submit']) { ?>
Form goes here
<?php } elseif (empty($_POST['email']) || empty($_POST['name']) ||
(isEmailAddress($_POST['email']) == 0) || (trim($_POST['email']) == '')
|| (trim($_POST['name']) == '')) {
?>
Something entered was wrong, please re-enter your information:
form goes here.
<?php }
else {
store variables, send e-mail, and show a new page with a coupon }
?>
Confused? Don’t be. The beginning tells us if the form has been previously submitted, if not, the form will load. The second part after “elseif” checks if all the data entered is correct. After all the conditions have been met, we progress to the last “else” which will execute the mail sending.
“Validate This!”
If you look above, you’ll see a strange function called “isEmailAddress”. I set this function up using a script I found. Here is the function:
function isEmailAddress($value) {
return eregi('^([a-z0-9])+([\.a-z0-9_-])*@([a-z0-9_-])+(\.[a-z0-9_-]+)*\.([a-z]{2,6})$', $value);
}
It basically checks if the e-mail is in the correct format. It also makes sure that only a single e-mail address has been entered and that it does not contain any malicious code.
Tip: If you wish to add database support to this script, you’ll have to use a validation function for the name and message as well!
Next part of validation are the “empty()” and “trim()” functions. “Empty()” is self-explanatory. You entered the variable name and the function will check if it is empty or not. If it is, the function returns TRUE. “Trim()” works similarly except here it takes out all the extra spaces and such. If it equals ‘ ‘ or an empty space, then it will return TRUE. The “elseif” statement is setup so that it checks the e-mail and name value.
Tip: If you have some time on your hand you can create a function that will check for each of these statements like: function CheckValue ($var) { if (empty($var) {return TRUE;} if (trim($var) == ‘ ‘) { return TRUE;} }
Second Form
You have a choice here. Under “elseif ()”, you can create new “if” statements and inform the user of what exactly is wrong. For example if the name is empty, you can create an if statement like this:
if (empty($_POST['name'] || trim($_POST['name']) == ' ') { ?>
echo "You left the name field empty";
<?php } ?>
I like to keep the user in the shadows and put all of the validation together using the || which means “or” and the same original form will show up with the message “Error: Please enter a valid e-mail address and your name”. Add the following form under “elseif()” between the php tags:
Error: Please enter a valid e-mail address and your name <form action="<?php $_SERVER['PHP_SELF'];?>" method="post"> Name:<br /> <input type="text" name="name" maxlength="41" /><br /> E-mail address:<br /> <input type="text" name="email" maxlength="40" /><br /> Message (<i>optional</i>):<br /> <textarea name="optmessage" cols="30" rows"10" maxlength"140"></textarea><br /> <input type="submit" name="submit" value="Submit" /> </form>
It’s the same form with a little message on top.
Everything “Else”
So all the variables go through, the script is validated. What now then? Now we’ll send the e-mail and refresh the site. I am using e-mails for a good reason. Whenever a user asks for a coupon, I’ll have a copy of their name and their e-mail address for future reference. I COULD use a database system but I’m a lazy person. I’ll point you in the right direction if you wish to do that though. Instead, let’s focus on what I already have done.
We should set up our variables first, writing out $_POST['email'] is quite a hassle. Plus, we have to set up the e-mail variables as well. Also note that this is in the last else {} section:
//variables $to = $_POST['email']; $subject = "Coupon from the Chiropractors"; $name = $_POST['name']; $optmessage= $_POST['optmessage']; $opt = wordwrap ($optmessage, 70);
The mail function works like this:
mail (to, subject, message, headers)
So we set up the “$to” variable which we will direct to the e-mail. We’ve also set up the subject of the e-mail and put $_POST['name'] into the $name variable for later use. Next, I transferred the optional message into $optmessage variable which I then word-wrapped into $opt. You have to word-wrap your e-mail message and the longest line can only have 70 characters. Using the “wordwrap ()” function and the parameter “70″, we’ve accomplished that. Let’s write the message:
$message = "<html> <head> <meta http-equiv=\"Content-Type\" content=\"text/html; charset=utf-8\" /> <title>Chiropractic</title> </head> <body> <p> Dear $name,<br /> Thank you for visiting us at our<a href=\"http://www.davepcguy.com\">Website</a>. <p> Please print out your coupon and present it on your next visit. Thank you, and we hope to see you soon!</p> <p style=\"margin-left: 50px\"> Sincerely, Alexander </p> <p>optional message:<br /> $opt</p> <p> Your e-mail: $to </p> </body> </html>";
Note that e-mail clients have different support of HTML and CSS. Don’t include any XHTML, that’s way too complicated. This is the reason why I did not put the coupon into the e-mail. Most e-mail clients do not support the “position: absolute”. Alright, let’s setup our header variable. With headers, you can define who the e-mail is from, where to reply to the e-mail, send different copies, and most importantly, use MIME.
//header information $from = "no-reply@davepcguy.com"; $headers = "From: $from" . "\r\n"; $headers .= 'MIME-Version: 1.5.2' . "\r\n"; $headers .= 'Content-type: text/html; charset=iso-8859-1' . "\r\n"; $headers .= "BCC: reply@davepcguy.com" . "\r\n";
I used an e-mail address I set up through c-panel. Set it up the same way you set up any other e-mail account. And you won’t even have to include the password in your script. Let’s break down the header.
The first header establishes from where the e-mail will be sent. Always break the lines when setting up the header variable using “\r\n”. Next, set up your MIME and its version. The newest one should be 1.5.2 but check your version under the PHP addons/modules in your c-panel. If you can’t make it work, use “MIME-Version: 1.0″. Next, set the content-type. Just copy the above, there should be no other alternative. The script will also send a BCC (Blind Carbon Copy) of every e-mail to my own e-mail address so that I can keep records. Let’s send it then!
//functions
$mail_sent= mail("$to", $subject, $message, $headers);
All that work and it’s summed up in one single line, amazing, eh?
The Script After
Hmm…I think I should give the user the coupon finally, don’t you think? They’ve done SO much work. Well, let me set up the message then:
//announcement $sent= " <p> Dear $name,<br /> Thank you for visiting us at <a href=\"http://www.davepcguy.com\">Website</a> Here is your coupon</p> <div align=\"center\" style=\"padding=\"50px\"> <div style=\"position: absolute; margin: 75px 120px 10px 50px; font-size: 30px; border-bottom: 2px solid black; width: 250px\"> $name </div> <img src=\"coupon2.png\" width=\"436\" height=\"292\" /></div> <p> Please print this coupon out and present it on your next visit. Thank you, and we hope to see you soon!</p> <p style=\"margin-left: 50px\"> Sincerely, Alexander </p> <p> P.S. please print out your coupon immediately or save this page because it will not be available after you close out. If you're having any trouble, please contact our <a href=\"mailto:alexander@davepcguy.com\">webmaster</a>. </p> <p>Optional Message: <br /> $opt </p> "; echo $mail_sent ? $sent : "Mail failed"; echo $sent; } ?>
Haha, I know, it looks complicated, doesn’t it? Well not really, the “$sent” just sets up a variable with the html code I plan to use in my webpage. Beware, you’ll have to adjust this according to your own webpage. the echo $mail_sent ? $sent: “Mail failed”; is a short hand for an if loop ” if ($mail_sent) {$sent} else { “Mail Failed”};” then the $sent variable will echo out.
Extras
- database support
- extra validation
This is how I finished out my script. I don’t plan on doing too much to it other than making it printable. I’m thinking about making a pop-up window that will display all of that information. Let’s review some of the extras you can add.
Database Support First, you can add database support. Simply make a new database in MySQL (using PHPmyAdmin) and set up two columns, one for name, and the other for name. Set up the table or use this SQL command if you can, creating the database might be tricky, but you should be able to use the “CREATE TABLE” part. If you can’t, just set it up manually using the values shown:
CREATE DATABASE coupondb;
CREATE TABLE `coupons` (
`id` int(11) NOT NULL auto_increment,
`name` varchar(255) NOT NULL default '',
`email` varchar(255) NOT NULL default '',
PRIMARY KEY (`id`)
) TYPE=MyISAM;
You can probably make a third column for an order (1., 2., 3.) or for the date and time. Add this at the beginning of the “else{}” :
//MySQL variable
$host = "localhost";
$user = "user";
$pass = "password";
$db = "coupondb";
//connect
$connection = mysql_connect($host, $user, $pass) or die ("Unable to connect!");
// select database
mysql_select_db($db) or die ("Unable to select database!");
First, set up the host variable ie, where the database is. I’ll trust my WordPress senses and leave that with localhost. You’ll have to create a new username and password as well as a database manually using c-panel or a different site manager your hosting provides you. Input the user and password. Change the “die” variable to something like “internal server error” or something, this is just for educational purposes. I got it off Zend Dev Zone again. Make sure you put this BEFORE the e-mail sending (ie the mail() function) because it’s senseless to send the e-mail but not make a database entry. Here’s the basic query:
// create query
$query = "INSERT INTO coupons (name, email) VALUES ('$name', '$to')";
// execute query
$result = mysql_query($query) or die ("Error in query: $query. ".mysql_error());
// close connection
mysql_close($connection);
And there you go, database support added. Check out my full script on the bottom for the full implementation with the duplicate entries check as well as other features.
Print
Let’s check out how to print all this stuff out. I found a neat piece of JavaScript that can accomplish this. It’s a bit tricky and I still can’t get it to show the best results but, it seems to work well nonetheless. You can find it here. Add the header part into the real header where you’ll use this mail.php script. Then, modify the $sent variable:
$sent= "<div id=\"printReady\"> <div style=\" width: 457px; background: white; text-align: center\"> <p> Dear $name,<br /> Thank you for visiting us at <a href=\"http://www.davepcguy.com\">Website</a> Here is your coupon</p> <div align=\"center\" style=\"padding=\"50px\"> <div style=\"position: absolute; margin: 75px 120px 10px 50px; font-size: 30px; border-bottom: 2px solid black; width: 250px\"> $name </div> <img src=\"coupon2.png\" width=\"436\" height=\"292\" /></div> <p> Please print this coupon out and present it on your next visit. Thank you, and we hope to see you soon!</p> <p style=\"margin-left: 50px\"> Sincerely, Alexander </p> <p> P.S. please print out your coupon immediately or save this page because it will not be available after you close out. If you're having any trouble, please contact our <a href=\"mailto:alexander@davepcguy.com\">webmaster</a>. </p> <p>Optional Message: <br /> $opt </p></div></div> <form id=\"printMe\" name=\"printMe\"> <input type=\"button\" name=\"printMe\" onClick=\"printSpecial()\" value=\"Print this Page\"> </form> ";
Change the width to suit your needs. And I am completely aware there is a million different divs just in this script (you should see the pages I code, million more divs) but they are mostly mandatory. You can switch the “div” around the “$name” variable to <span>. You’ll have to spend some time adjusting this, the width of the page, the margin, as well as the different positions to suit your needs. It worked for me almost perfectly
Extra Validation Okay, so if you want to use a database with this form, you’ll need some extra validation as a precaution against SQL injection. We’ve already validated the e-mail address and I won’t be validating the optional message just yet. So let’s validate the name. I used a function from the same script I cited when I used the e-mail validation function:
// check whether input is alphabetic
function isAlpha($value) {
return preg_match('/^[a-zA-Z]+$/', $value);
}
Add this function to the beginning of the document and add another || to the elseif () {} part of the loop saying “!isAlpha($_POST['name'])”. Also, warn the user that they can use only letters for the name and no periods or other characters nor numbers. The optional message SHOULD be validated but I am not certain how to go about it just yet. I’d like to let the user be able to use some personalized html code so I won’t look into it too much. Also, I am not storing that message so I don’t have to fear an SQL attack.
Conclusion
I hope this shed some light on how you’d create an e-mail form as well as how to use the mail() function. As you can see, the possibilities with PHP are endless. I’d like to also inform you that it took me several hours to write this script with numerous trial&error runs. I’m self-taught, and mostly used the PHP manual as a reference. I hope this helped and that you have fun trying this out for yourselves!
I’d appreciate any comments regarding the security of this script as well as usability. I, myself, am about to launch the script on one of my pages so I’d like to know what people have to say about it.
Final Script with all its features added: Note that I will update this part of the post as necessary when I find bugs and optimize it.
<?php
//functions
/* PHP script written by Alexander Janus
contact: alexander@davepcguy.com
blog: http://www.davepcguy.com
if you want to use this script, include this header
*/
function isEmailAddress($value) {
return eregi('^([a-z0-9])+([\.a-z0-9_-])*@([a-z0-9_-])+(\.[a-z0-9_-]+)*\.([a-z]{2,6})$', $value);
}
// check whether input is alphabetic
function isAlpha($value) {
return preg_match('/^[a-zA-Z]+$/', $value);
}
function name ($var) {
if (!isset($var)){
return TRUE;
}
if (empty($var)){
return TRUE;
}
if (trim($var) == ''){
return TRUE;
}
if (isAlpha($var) == 0){
return TRUE;
}
}
function email ($var) {
if (!isset($var)){
return TRUE;
}
if (empty($var)){
return TRUE;
}
if (trim($var) == ''){
return TRUE;
}
if (isEmailAddress($var) == 0){
return TRUE;
}
}
//loop
if(!isset($_POST['submit'])){
?>
Please enter your name and e-mail address. The name field supports only alphabetic characters (letters).
<form action="<?php $_SERVER['PHP_SELF'];?>" method="post">
Name:<br /> <input type="text" name="name" maxlength="41" /><br />
E-mail address:<br /> <input type="text" name="email" maxlength="40" /><br />
Message (<i>optional</i>):<br /> <textarea name="optmessage" cols="30" rows"10" maxlength"140"></textarea><br />
<input type="submit" name="submit" value="Submit" />
</form>
<?php
}
elseif (name($_POST['name']) || email($_POST['email'])) {
if (name($_POST['name'])) {
echo "Please enter a valid name. Periods, commas, or other non-alpha characters are not supported.<br/>";
}
if (email($_POST['email'])){
echo "Please enter a valid e-mail address in this format: account@email.com. <br />";}
?>
<form action="<?php $_SERVER['PHP_SELF'];?>" method="post">
Name:<br /> <input type="text" name="name" maxlength="41" /><br />
E-mail address:<br /> <input type="text" name="email" maxlength="40" /><br />
Message (<i>optional</i>):<br /> <textarea name="optmessage" cols="30" rows"10" maxlength"140"></textarea><br />
<input type="submit" name="submit" value="Submit" />
</form>
<?php
}
else {
//Database connection
//MySQL variable
$host = "localhost";
$user = "user";
$pass = "password";
$db = "coupon";
//connect
$connection = mysql_connect($host, $user, $pass) or die ("Unable to connect!");
// select database
mysql_select_db($db) or die ("Unable to select database!");
//variables
$to = $_POST['email'];
$subject = "Coupon from the Chiropractors";
$name = $_POST['name'];
$optmessage= $_POST['optmessage'];
$opt = wordwrap ($optmessage, 70);
$sent= "<div id=\"printReady\">
<div style=\" width: 457px; background: white; text-align: center;\">
<p> Dear $name,<br />
Thank you for visiting us at <a href=\"http://www.davepcguy.com\">Website</a>
Here is your coupon</p>
<div align=\"center\" style=\"padding=\"50px\">
<span style=\"position: absolute; margin: 75px 120px 10px 50px; font-size: 30px; border-bottom: 2px solid black; width: 250px\"> $name </span>
<img src=\"coupon2.png\" width=\"436\" height=\"292\" /></div>
<p> Please print this coupon out and present it on your next visit. Thank you, and we hope to see you soon!</p>
<p style=\"margin-left: 50px\"> Sincerely, Alexander </p>
<p> P.S. please print out your coupon immediately or save this page because it will not be available after you close out.
If you're having any trouble, please contact our <a href=\"mailto:alexander@davepcguy.com\">webmaster</a>. </p>
<p>Optional Message: <br />
$opt
</p></div></div>
<form id=\"printMe\" name=\"printMe\"> <input type=\"button\" name=\"printMe\" onClick=\"printSpecial()\" value=\"Print this Page\"> </form>
";
//MYSQL QUERY
//check for duplicates
$duplicate = mysql_query("SELECT * FROM coupons where email='$to'");
$affected_rows = mysql_num_rows($duplicate);
if($affected_rows >= 1)
{
echo $sent;
echo "<span style=\"color: red;\">Note: If you have already entered your e-mail address before, you will not get another e-mail message. <br />
This is to prevent spamming.</span>";
die('');
}
else {
// create query
$query = "INSERT INTO coupons (name, email) VALUES ('$name', '$to')";
// execute query
$result = mysql_query($query) or die ("Error in query: $query. ".mysql_error());
// close connection
mysql_close($connection);
}
//html message
$message = "<html>
<head>
<meta http-equiv=\"Content-Type\" content=\"text/html; charset=utf-8\" />
<title>Chiropractic</title>
</head>
<body>
<p> Dear $name,<br />
Thank you for visiting us at our<a href=\"http://www.davepcguy.com\">Website</a>
<p> Please print out your coupon and present it on your next visit. Thank you, and we hope to see you soon!</p>
<p style=\"margin-left: 50px\"> Sincerely, Alexander </p>
<p>optional message:<br />
$opt</p>
<p>
Your e-mail: $to </p>
</body>
</html>";
//header information
$from = "no-reply@davepcguy.com";
$headers = "From: $from" . "\r\n";
$headers .= 'MIME-Version: 1.5.2' . "\r\n";
$headers .= 'Content-type: text/html; charset=iso-8859-1' . "\r\n";
$headers .= "BCC: reply@davepcguy.com" . "\r\n";
//functions
$mail_sent= mail("$to", $subject, $message, $headers);
//announcement
echo $mail_sent ? $sent : "Mail failed";
echo $sent;
}
?>
| Print article | This entry was posted by Admin on October 15, 2009 at 14:14, and is filed under PHP and Scripting, Tutorials. Follow any responses to this post through RSS 2.0. You can leave a response or trackback from your own site. |








about 2 years ago
Hey, I found your blog while searching on Google. I have a blog on online stock trading, I’ll bookmark your site.
about 2 years ago
Hello from Russia!
Can I quote a post in your blog with the link to you?
about 2 years ago
yeah, go ahead
about 2 years ago
Awesome blog!
I thought about starting my own blog too but I’m just too lazy so, I guess I‘ll just have to keep checking yours out.
LOL,
about 2 years ago
Tutorial added to thewebtuts.com
about 2 years ago
Wow, thanks!
about 2 years ago
Great work… Complex but easy to learn… Thx!