Пример класса captcha на php (2)
<?php
/**
* CaptchaV2 File
* Generates CAPTCHA Numbers and Chars Image
* @author Albert Demeter <borex8@hotmail.com>
* @version 2.1
* GNU General Public License (Version 2.1, March 7th, 2006)
*
* based on Hadar Porat's Captcha Numbers class v.1.5 <hpman28@gmail.com>
*
* This program is free software; you can redistribute
* it and/or modify it under the terms of the GNU
* General Public License as published by the Free
* Software Foundation; either version 2 of the License,
* or (at your option) any later version.
*
* This program is distributed in the hope that it will
* be useful, but WITHOUT ANY WARRANTY; without even the
* implied warranty of MERCHANTABILITY or FITNESS FOR A
* PARTICULAR PURPOSE. See the GNU General Public License
* for more details.
*/
/**
* CaptchaNumbersV2 Class
* @access public
* @author Albert Demeter <borex8@hotmail.com>
* @version 2.0
*/
class CaptchaNumbersV2 {
var $length = 6;
var $font = 'fonts/arial.ttf';
var $size = 15;
var $angle = 10;
var $type = 'png';
var $height = 40;
var $width = 80;
var $grid = 7;
var $string = '';
var $captchaType = 'mixed';
// automatically calculated based on the percent in the constructor
var $dotsCount = 0;
// background colors RED, GREEN and BLUE values (provide it as a number between 0-255)
var $bgColorRed = 240;
var $bgColorGreen = 240;
var $bgColorBlue = 240;
// if true then grid is drawn
var $drawGrid = false;
// if true then every grid line will have a different color
var $randomGridColor = true;
// if true then every letter will have a different color
var $randomLetterColor = true;
// fonts
// there is feature of this script that it picks random fonts for each character displayed
// you should define a fonts folder
// a folder named fonts within this scripts directory is tested and working.
var $fonts_folder = 'fonts/';
// the range of font size of each letter displayed as pixels. if you choose them same,
// fonts will be at that exact size.
var $font_size_min = 14;
var $font_size_max = 16;
// font angles are for placing the fonts at a random angle. high values of angles might result unexpected.
var $font_angle_min = 0;
var $font_angle_max = 15;
/**
* @return void
* @param int $length string length
* @param int $size font size
* @param String $type image type
* @param String $captchaType text contain digits, chars or mixed
* @param int $dotsPercent random pixels generated in image
* @desc generate the main image
*/
function CaptchaNumbersV2($length = '', $size = '', $type = '', $captchaType = '', $dotsPercent = 10) {
if ($length!='') $this -> length = $length;
if ($size!='') $this -> size = $size;
if ($type!='') $this -> type = $type;
if ($captchaType!='') $this -> captchaType = $captchaType;
$this -> width = $this -> length * $this -> size + $this -> grid + $this -> grid;
$this -> height = $this -> size + (2 * $this -> grid);
// dots count equals #% of all points in the image
$this -> dotsCount = round(($this -> width * $this -> height) * $dotsPercent / 100);
$this -> generateString();
}
/**
* @return void
* @desc display captcha image
*/
function display() {
$this -> sendHeader();
$image = $this -> generate();
switch ($this-> type) {
case 'jpeg': imagejpeg($image); break;
case 'png': imagepng($image); break;
case 'gif': imagegif($image); break;
default: imagepng($image); break;
}
}
// following function is gathered from php.net, author is "fankounter@libero.it"
// it is used for gathering the fonts from the spesicfied folder. I have modifeid it slightly
function ls($__dir="./",$__pattern="*.*")
{
settype($__dir, "string");
settype($__pattern, "string");
$__ls = array();
$__regexp = preg_quote($__pattern,"/");
$__regexp = preg_replace("/[\\x5C][\x2A]/",".*",$__regexp);
$__regexp = preg_replace("/[\\x5C][\x3F]/",".", $__regexp);
if(is_dir($__dir))
if(($__dir_h=@opendir($__dir))!==FALSE)
{
while(($__file=readdir($__dir_h))!==FALSE)
if(preg_match("/^".$__regexp."$/",$__file))
array_push($__ls,$__file);
closedir($__dir_h);
sort($__ls,SORT_STRING);
}
return $__ls;
}
// function picks a random font for each letter each time
function random_font() {
$fonts = $this -> ls($this -> fonts_folder, "*.ttf");
$rand = mt_rand(0, sizeof($fonts)-1);
$this -> font = $this -> fonts_folder.$fonts[$rand];
}
// the font size would be determined randomly within the limits defined above.
function random_font_size() {
$this -> size = mt_rand($this -> font_size_min, $this -> font_size_max );
}
// the angle would be determined randomly within the limits defined above.
function random_font_angle() {
$this -> angle = mt_rand($this -> font_angle_min, $this -> font_angle_max );
}
/**
* @return Image
* @desc generate the image
*/
function generate() {
$image = ImageCreate($this -> width, $this -> height) or die("Cannot Initialize new GD image stream");
// colors
$background_color = ImageColorAllocate($image, $this -> bgColorRed, $this -> bgColorGreen, $this -> bgColorBlue);
if (!$this -> randomLetterColor)
{
$net_color_1 = ImageColorAllocate($image, 10, 200, 10);
$net_color_2 = ImageColorAllocate($image, 200, 10, 10);
}
if (!$this -> randomLetterColor)
{
$stringcolor_1 = ImageColorAllocate($image, 150, 150, 150);
$stringcolor_2 = ImageColorAllocate($image, 120, 120, 250);
}
if ($this -> drawGrid)
for ($i = $this -> grid; $i < $this -> height; $i+=$this -> grid)
{
if ($this -> randomGridColor)
{
$net_color_1 = ImageColorAllocate($image, mt_rand(0,255), mt_rand(0,250), mt_rand(0,250));
$net_color_2 = ImageColorAllocate($image, mt_rand(0,255), mt_rand(0,250), mt_rand(0,250));
}
if ($i%2) ImageLine($image, 0, $i, $this -> width, $i, $net_color_1);
else ImageLine($image, 0, $i, $this -> width, $i, $net_color_2);
}
// make the text
$str = $this -> getString();
$x = $this -> grid;
for($i = 0, $n = strlen($str); $i < $n; $i++)
{
if ($this -> randomLetterColor)
{
$stringcolor_1 = ImageColorAllocate($image, mt_rand(0,255), mt_rand(0,250), mt_rand(0,250));
$stringcolor_2 = ImageColorAllocate($image, mt_rand(0,255), mt_rand(0,250), mt_rand(0,250));
}
$this -> random_font();
$this -> random_font_size();
$this -> random_font_angle();
if ($i%2) ImageTTFText($image, $this -> size, $this -> angle, $x, $this -> size + $this -> grid - mt_rand(0, 5), $stringcolor_1, $this -> font, $str{$i} );
else ImageTTFText($image, $this -> size, $this -> angle, $x, $this -> size + $this -> grid + mt_rand(0, 5), $stringcolor_2, $this -> font, $str{$i} );
$x = $x + $this -> size;
}
// grid
if ($this -> drawGrid)
for ($i = $this -> grid; $i < $this -> width; $i+=$this -> grid)
{
if ($this -> randomGridColor)
{
$net_color_1 = ImageColorAllocate($image, mt_rand(0,255), mt_rand(0,250), mt_rand(0,250));
$net_color_2 = ImageColorAllocate($image, mt_rand(0,255), mt_rand(0,250), mt_rand(0,250));
}
if ($i%2) ImageLine($image, $i, 0, $i, $this -> height, $net_color_1);
else ImageLine($image, $i, 0, $i, $this -> height, $net_color_2);
}
for ($i = 0; $i < $this -> dotsCount; $i++)
{
$x = rand(0, $this -> width - 1);
$y = rand(0, $this -> height - 1);
$rgbIndex = imagecolorat($image, $x, $y);
$rgb = imagecolorsforindex($image, $rgbIndex);
//print $x . ' x ' . $y . ' : ' . $rgbIndex . '(' . $rgb['red'] . '-' . $rgb['green'] . '-' . $rgb['blue'] . ')<br>';
// if background color create random pixel color
if ($rgb['red'] == $this -> bgColorRed
&& $rgb['green'] == $this -> bgColorGreen
&& $rgb['blue'] == $this -> bgColorBlue)
{
$dotColor = ImageColorAllocate($image, mt_rand(0,255), mt_rand(0,255), mt_rand(0,255));
}
else
{
// not background color then generate a close shade color
$rgb['red'] = $rgb['red'] + ((mt_rand(0,100) % 2) == 1 ? 1 : -1) * mt_rand(0, 255 - $rgb['red']);
if ($rgb['red'] < 0 || $rgb['red'] > 255) $rgb['red'] = mt_rand(0, 255);
$rgb['green'] = $rgb['green'] + ((mt_rand(0,100) % 2) == 1 ? 1 : -1) * mt_rand(0, 255 - $rgb['green']);
if ($rgb['green'] < 0 || $rgb['green'] > 255) $rgb['green'] = mt_rand(0, 255);
$rgb['blue'] = $rgb['blue'] + ((mt_rand(0,100) % 2) == 1 ? 1 : -1) * mt_rand(0, 255 - $rgb['blue']);
if ($rgb['blue'] < 0 || $rgb['blue'] > 255) $rgb['blue'] = mt_rand(0, 255);
$dotColor = ImageColorAllocate($image, $rgb['red'], $rgb['green'], $rgb['blue']);
}
ImageSetPixel($image, $x, $y, $dotColor);
}
return $image;
}
/**
* @return String
* @desc generate the string
*/
function generateString() {
$string = $this->create_random_value($this -> length, $this -> captchaType);
$this -> string = $string;
return true;
}
/**
* @return void
* @desc send image header
*/
function sendHeader() {
header('Content-type: image/' . $this -> type);
}
/**
* @return String
* @desc return the string
*/
function getString() {
return $this -> string;
}
function create_random_value($length, $type = 'mixed') {
if ( ($type != 'mixed') && ($type != 'chars') && ($type != 'digits')) return false;
$rand_value = '';
while (strlen($rand_value) < $length) {
if ($type == 'digits') {
$char = mt_rand(0,9);
} else {
$char = chr(mt_rand(0,255));
}
if ($type == 'mixed') {
if (preg_match('/^[a-z0-9]$/i', $char)) $rand_value .= $char;
} elseif ($type == 'chars') {
if (preg_match('/^[a-z]$/i', $char)) $rand_value .= $char;
} elseif ($type == 'digits') {
if (preg_match('/^[0-9]$/', $char)) $rand_value .= $char;
}
}
return $rand_value;
}
}
?>