-->
Bookmark and Share

CAPTCHA Image

View a sample screen shot.

Default.aspx

This is a very simple sample web form that contains only a few basic elements, namely an <IMG> tag for the image, a text box and a "Submit" button.

<form id="Default" method="post" runat="server">
  <img src="JpegImage.aspx"><br>
  <p>
    <strong>Enter the code shown above:</strong><br>
    <asp:TextBox id="CodeNumberTextBox" runat="server"></asp:TextBox>
    <asp:Button id="SubmitButton" runat="server" Text="Submit">
    </asp:Button><br>
  </p>
  <p>
    <em class="notice">
      (Note: If you cannot read the numbers in the above<br>
      image, reload the page to generate a new one.)</em>
  </p>
  <p><asp:Label id="MessageLabel" runat="server"></asp:Label></p>
</form>

Note that the SRC attribute of the <IMG> tag points to the web form JpegImage.aspx.

The code-behind for Default.aspx simply generates a random text string for the image and validates that this text was entered by the user when the form is submitted. The key is to store the text string in the Session object.

private void Page_Load(object sender, System.EventArgs e)
{
  if (!this.IsPostBack)

    // Create a random code and store it in the Session object.
    this.Session["CaptchaImageText"] = GenerateRandomCode();

  else
  {
    // On a postback, check the user input.
    if (this.CodeNumberTextBox.Text ==
      this.Session["CaptchaImageText"].ToString())
    {
      // Display an informational message.
      this.MessageLabel.CssClass = "info";
      this.MessageLabel.Text = "Correct!";
    }
    else
    {
      // Display an error message.
      this.MessageLabel.CssClass = "error";
      this.MessageLabel.Text = "ERROR: Incorrect, try again.";

      // Clear the input and create a new random code.
      this.CodeNumberTextBox.Text = "";
      this.Session["CaptchaImageText"] = GenerateRandomCode();
    }
  }
}

The reason for storing the text string in the Session object is so that it can be accessed by JpegImage.aspx.

JpegImage.aspx

For this web form, no HTML is needed (what's there is just the default code generated by Visual Studio when the file was created). Instead of HTML, the code will produce a JPEG image.

In the code-behind, we first create a CaptchaImage object, using the text retrieved from the Session object. This creates a bitmap image for us.

private void Page_Load(object sender, System.EventArgs e)
{
  // Create a CAPTCHA image using the text stored in the Session object.
  CaptchaImage ci = new CaptchaImage(
    this.Session["CaptchaImageText"].ToString(),
    200, 50, "Century Schoolbook");

  // Change the response headers to output a JPEG image.
  this.Response.Clear();
  this.Response.ContentType = "image/jpeg";

  // Write the image to the response stream in JPEG format.
  ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg);

  // Dispose of the CAPTCHA image object.
  ci.Dispose();
}

We then modify the HTTP response headers to set the Content-type to "image/jpeg" so the client browser will know we are sending an image.

The last step is to retrieve the bitmap image from CaptchaImage.Image and write it to the HTTP response output stream in JPEG format. Fortunately, the Save() method of the Bitmap object makes this simple. Any other supported image format could be used as well so long as the Content-type header is set accordingly.

Points of Interest

Because the CaptchaImage class contains a Bitmap object, and bitmaps employ unmanaged resources, a custom Dispose() method is implemented. This allows those unmanaged resources to be freed whenever a CaptchaImage is destroyed.

Downloads