Page 1 of 1

Captcha Made Easy creating a simple captcha

#1 rgfirefly24  Icon User is online

  • D.I.C Lover
  • member icon


Reputation: 267
  • View blog
  • Posts: 1,477
  • Joined: 07-April 08

Post icon  Posted 05 May 2008 - 09:52 AM

Ok, so you've created your asp.net site, but something is troubleing you. You want to be able to check to make sure the person behind the user creation is actually human. Well an easy way to do this is called CAPTCHA.

CAPTCHA stands for : Completely Automated Turing Test To Tell Computers and Humans Apart

now Using captcha is not fool proof. There are programs out there called OCR's. OCR stands for optical character recognition. Basically this means that it takes an image, removes background clutter(meaning small lines and background images), segments the image if possible and reads each character individually. Most OCR readers have a 30%-50% effectiveness.

To create a captcha you need to break it down into several steps.


before we begin the process i would like to point out that this site Simple Captcha with ASP.NET was where i went to in order to start out in creating a CAPTCHA. You will notice that the Structure of
my code and the code on that site are similar. The reason is only for functionality. The variable names have been changed and alot has been added to make it more secure.

step 1:
you will need to create all the variables and other items needed for the CAPTCHA. start off by making a Bitmap and defining the Graphics for it. you will need to declare at least 1 random number generator, but in the following example i declared 3 to make the CAPTCHA a bit more challenging.
				Bitmap captchabmp = new Bitmap(120,50);
		
				Graphics captchagraphic = Graphics.FromImage(captchabmp);
		
				captchagraphic.Clear(Color.Black);
		
				captchagraphic.TextRenderingHint = TextRenderingHint.AntiAlias;
		
				Font captchafont = new Font("Ariel", 24);
				Font captchafont2 = new Font("Ariel", 24);
				HatchBrush captchafont3 = new HatchBrush(HatchStyle.Shingle, Color.GhostWhite, Color.Gold); 
		
				string captchastr = "";
		
				char[] captchaarray = new char[5];
		
				int x;
		
				Random rand = new Random();
				Random upperlower = new Random();
				Random captcha = new Random();
				
				int z;
				int y;
		string temp;


Now we have our variables declared and setup our bitmap to be filled. A few things i want to point out
HatchBrush captchafont3 = new HatchBrush(HatchStyle.Shingle, Color.GhostWhite, Color.Gold);


What this line does is it Breaks up the actual image into a multicolored image based of the HatchStyle. This will make it alot harder for OCR readers as
they typically look for a solid color.


once you have your variables declared its time to start building the actual captcha image. For this you will need to learn the hex codes for letters A-Z, a-z, and numbers 1-9 (i leave out zero because its too easy to get confused with the letter o)

after that you will declare 2 for loops to build the actual image along with a few if statements:
 for (x = 0; x < 5; x++)
		 {
			 z = captcha.Next(0,3);
			 if (z ==  1)
			 {
				 captchaarray[x] = System.Convert.ToChar(rand.Next(65,90));
			 }
			 else
			 {
				 captchaarray[x] = System.Convert.ToChar(rand.Next(49,57));
			 }
		 }



at this point you now have an array of 5 random numbers and letters. From here you will use the 2nd for loop to change the letter to either upper or lower case( i did not need to parse out numbers as they are uneffected by this for loop)
		for (x = 0; x < 5; x++)
				{
					y = upperlower.Next(0,99);
					if (y >= 0 || y < 50)
					{
						temp = (captchaarray[x].ToString());
						temp = temp.ToLower();
						randomStr += temp.ToString();
					}
					else
					{
						temp = (captchaarray[x].ToString());
						temp = temp.ToUpper();
						randomStr += temp.ToString();
					}
				}




now that you've got your Captcha array built and placed into a single string instead of an array its time to place it into the session for comparison in your actual program.
  /* this adds the string to the Session variable to be called upon in your main code. */

		Session.Add("captchastr", captchastr);



now it is time to Build up the actual image that will be displayed to the user. I have removed a good portion of this code for redundancy reasons.
String backgroundstring = "-OCR-";/* this will be used as a way to merge the image letters/numbers to make it hard for an OCR reader to segment*/


		captchagraphic.DrawString(backgroundstring, captchafont2, Brushes.Gold, 0, 3);// adds the backgroundstring to the image
		captchagraphic.DrawLine(new Pen(Brushes.Red), 1, 0, 1, 50);//these lines create the checkered background
		captchagraphic.DrawLine(new Pen(Brushes.Red), 5, 0, 5, 50);
		captchagraphic.DrawLine(new Pen(Brushes.Red), 10, 0, 10, 50);
		captchagraphic.DrawLine(new Pen(Brushes.Red), 15, 0, 15, 50);
		captchagraphic.DrawLine(new Pen(Brushes.Red), 20, 0, 20, 50);
		captchagraphic.DrawLine(new Pen(Brushes.Red), 25, 0, 25, 50);
		captchagraphic.DrawString(captchastr, captchafont, captchafont3, 3, 3);//adds the string we created to the image
	captchagraphic.DrawLine(new Pen(Brushes.Olive), 0, 20, 100, 20);//these next 3 lines create the "strike-through" effect
	captchagraphic.DrawLine(new Pen(Brushes.Azure), 0, 0, 100, 50);
		captchagraphic.DrawLine(new Pen(Brushes.Blue), 0, 50, 100, 0);



from here its time to Set the type of file you want it to be, and output it in that format. Also a good idea to dispose of your items so
future changes can be made with out worry.
 Response.ContentType = "image/GIF";
 
		 captchabmp.Save(Response.OutputStream, ImageFormat.Gif);
 
		 captchafont.Dispose();
		 captchafont2.Dispose();
 
 
		 captchagraphic.Dispose();
 
		captchabmp.Dispose();



awsome now you have your Captcha image built.

Attached Image

Now remember i told you about segmentation.
OCR readers attempt to "break-up" an image into different sections based on where it interprets one letter starts and ends.
By adding the background word, and the "strike-through" effect i am attempting to block an OCR readers ability to segment my image.


now lets look at the code you need to place in your actual .aspx page

The actual code is only one line. Why? simply because we store the CAPTCHA letter/number combination in a Session variable. so in your button click event put this in before any actual code

if (Page.IsValid && (txtCaptcha.Text.ToString() == Session["captchastr"].ToString()))
{
}



now there are other ways of going about securing your site. You can use the AJAX toolkit no bot control which will deny any IP that hits the submit button in too short of time, or use another form of CAPTCHA your current choices are: MAPTCHA, CAPTCHA KittenAuth, Microsoft's "Asirra", and 3-D captcha

I hope this tutorial will get you well on your way to basic site security and user authentication. Later i will be posting tutorials on the NoBot control.

This post has been edited by skyhawk133: 05 May 2008 - 10:28 AM


Is This A Good Question/Topic? 0
  • +

Replies To: Captcha Made Easy

#2 mocker  Icon User is offline

  • D.I.C Regular
  • member icon

Reputation: 50
  • View blog
  • Posts: 466
  • Joined: 14-October 07

Posted 05 May 2008 - 02:13 PM

good tutorial, but you may want to keep in mind that you want humans to be able to read it, not just make sure bots cannot. I have turned away in disgust from a number of websites that put so much obfuscation into their captcha that it looks like a mess and it blocks people as well as bots. In your sample image, having a background word makes it a complete pain in the ass to read, and unless I had to go to your site.. I wouldn't. Don't forget the users..
Was This Post Helpful? 0
  • +
  • -

#3 Nova Dragoon  Icon User is offline

  • The Innocent Shall Suffer, Big Time
  • member icon

Reputation: 36
  • View blog
  • Posts: 6,169
  • Joined: 16-August 01

Posted 05 May 2008 - 02:16 PM

Posted Image
Was This Post Helpful? 0
  • +
  • -

#4 ajaymatrix  Icon User is offline

  • D.I.C Regular
  • member icon

Reputation: 1
  • View blog
  • Posts: 410
  • Joined: 15-May 07

Posted 05 May 2008 - 06:44 PM

good one..
the same thing can be done with PHP, I guess
Was This Post Helpful? 0
  • +
  • -

#5 Fuingurth  Icon User is offline

  • D.I.C Head
  • member icon

Reputation: 11
  • View blog
  • Posts: 118
  • Joined: 13-August 09

Posted 19 August 2009 - 09:49 AM

View PostNova Dragoon, on 5 May, 2008 - 01:16 PM, said:

Posted Image

row 1, column2
row2 colum1
row 3 column 3......
final answer?
Was This Post Helpful? 0
  • +
  • -

#6 Guest_jstawski*


Reputation:

Posted 30 March 2010 - 02:21 PM

Dude, that picture is totally unreadable. I agree with mocker...
Was This Post Helpful? 0

#7 Robin19  Icon User is offline

  • D.I.C Addict
  • member icon

Reputation: 272
  • View blog
  • Posts: 552
  • Joined: 07-July 10

Posted 18 August 2010 - 08:44 AM

		Random rand = new Random();
		Random upperlower = new Random();
		Random captcha = new Random();

Random() does not create a random number. It creates a new number based on the system time and a complex formula. Running these Random() calls in a row will create Randoms with the same seed number.
		Random rand = new Random();
		Random upperlower = new Random(DateTime.NOW + this.GetHashCode());
		Random captcha = new Random(DateTime.NOW - this.GetHashCode());

Doing something like this will create 3 different randoms.
Was This Post Helpful? 0
  • +
  • -

#8 SimonSays  Icon User is offline

  • New D.I.C Head

Reputation: 1
  • View blog
  • Posts: 34
  • Joined: 06-March 10

Posted 18 September 2010 - 04:55 PM

View Postmocker, on 05 May 2008 - 01:13 PM, said:

good tutorial, but you may want to keep in mind that you want humans to be able to read it, not just make sure bots cannot. I have turned away in disgust from a number of websites that put so much obfuscation into their captcha that it looks like a mess and it blocks people as well as bots. In your sample image, having a background word makes it a complete pain in the ass to read, and unless I had to go to your site.. I wouldn't. Don't forget the users..

Yeah I agree, the captcha you generated is pretty much unreadable. There is a real fine line when it comes to captchas.
Was This Post Helpful? 0
  • +
  • -

Page 1 of 1