🔥码云GVP开源项目 12k star Uniapp+ElementUI 功能强大 支持多语言、二开方便! 广告
# GD 绘制验证码 绘制一个简单验证码 ``` <?php // 创建画布 $width = 200; $height = 50; $image = imagecreatetruecolor($width, $height); // 绘制颜色 $white = imagecolorallocate($image, 255, 255, 255); imagefilledrectangle($image, 0, 0, $width, $height, $white); // 绘制画笔颜色 $rand_color = imagecolorallocate($image, mt_rand(0, 255), mt_rand(0, 255), mt_rand(0, 255)); // 开始绘制 $size = mt_rand(20, 28); $angle = mt_rand(-15, 15); $x = 50; $y = 30; $font_file = 'fonts/PingFang.ttc'; $text = mt_rand(1000, 9999); imagettftext($image, $size, $angle, $x, $y, $rand_color, $font_file, $text); // 输出到浏览器 header('content-type:image/png'); imagepng($image); // 销毁画布资源 imagedestroy($image); ``` 添加干扰元素 ``` <?php $width = 160; $height = 40; $image = imagecreatetruecolor($width, $height); $white = imagecolorallocate($image, 255, 255, 255); imagefilledrectangle($image, 0, 0, $width, $height, $white); $string = implode('', array_merge(range(0, 9), range('a', 'z'), range('A', 'Z'))); // 快速创建字符串 $verify_code_length = 4; // 验证码个数 for ($i = 0; $i < $verify_code_length; $i++) { $size = mt_rand(20, 28); $angle = mt_rand(-15, 15); $x = 20 + 40 * $i; $y = 30; $font_file = 'fonts/PingFang.ttc'; $text = str_shuffle($string){0}; imagettftext($image, $size, $angle, $x, $y, rand_color($image), $font_file, $text); } // 绘制点干扰元素 $pixel = 50; for ($i = 1; $i <= $pixel; $i++) { imagesetpixel($image, mt_rand(0, $width), mt_rand(0, $height), rand_color($image)); } // 绘制线段作为干扰元素 $line = 3; for ($i = 1; $i <= $line; $i++) { imageline($image, mt_rand(0, $width), mt_rand(0, $height), mt_rand(0, $width), mt_rand(0, $height), rand_color($image)); } // 绘制圆弧作为干扰元素 $arc = 3; for ($i = 1; $i <= $arc; $i++) { imagearc($image, mt_rand(0, $width), mt_rand(0, $height), mt_rand(0, $width), mt_rand(0, $height), mt_rand(0, 360), mt_rand(0, 360), rand_color($image)); } header('content-type: image/jpeg'); imagejpeg($image); imagedestroy($image); /** * @param $image_resource * @return int */ function rand_color($image_resource) { return imagecolorallocate($image_resource, mt_rand(0, 255), mt_rand(0, 255), mt_rand(0, 255)); } ``` 简单验证码类 ``` <?php class Verify { protected $_font_file; // 字体文件 protected $_width = 120; // 画布宽度 protected $_height = 60; // 画布高度 protected $_size = 20; // 字体大小 protected $_length = 4; // 验证码长度 protected $_snow = 0; // 干扰元素雪花个数 protected $_pixel = 0; // 干扰元素像素个数 protected $_line = 0; // 干扰元素线段个数 private $_image = null; // 画布资源 /** * Verify constructor. * @param array $config */ public function __construct($config = []) { if (is_array($config) && !empty($config)) { // 检测字体文件是否存在并且可读 if ($config['font_file'] && is_file($config['font_file']) && is_readable($config['font_file'])) { $this->_font_file = $config['font_file']; } } else { return false; } // 检测画布宽 if (isset($config['width']) && (int)$config['width'] > 0) { $this->_width = (int)$config['width']; } // 检测画布高 if (isset($config['height']) && (int)$config['height'] > 0) { $this->_height = (int)$config['height']; } // 检测字体大小 if (isset($config['size']) && (int)$config['size'] > 0) { $this->_size = (int)$config['size']; } // 验证码长度 if (isset($config['length']) && (int)$config['length'] > 0) { $this->_length = (int)$config['length']; } // 干扰元素像素 if (isset($config['pixel']) && (int)$config['pixel'] > 0) { $this->_pixel = (int)$config['pixel']; } // 干扰元素线段 if (isset($config['line']) && (int)$config['line'] > 0) { $this->_line = (int)$config['line']; } // 干扰元素雪花 if (isset($config['snow']) && (int)$config['snow'] > 0) { $this->_snow = (int)$config['snow']; } // 图片资源 $this->_image = imagecreatetruecolor($this->_width, $this->_height); return $this->_image; } public function getVerify() { $white = imagecolorallocate($this->_image, 255, 255, 255); imagefilledrectangle($this->_image, 0, 0, $this->_width, $this->_height, $white); // 填充矩形 $string = $this->_generateStr($this->_length); if ($string == false) { return false; } // 绘制验证码 for ($i = 0; $i < $this->_length; $i++) { $x = ceil($this->_width / $this->_length) * $i + mt_rand(5, 10); $y = ceil($this->_height / 1.5); imagettftext($this->_image, $this->_size, mt_rand(-30, 30), $x, $y, $this->_getRandColor(), $this->_font_file, mb_substr($string, $i, 1, 'utf-8')); } // 干扰元素 if ($this->_snow) { $this->_getSnow(); } else { if ($this->_pixel) { $this->_getPixel(); } if ($this->_line) { $this->_getLine(); } } // 输出图像 header('content-type: image/jpeg'); imagejpeg($this->_image); return $string; // 返回验证码字符串 } /** * 生成随机字符串 * * @param $len string 字符长度 * @return bool|string */ private function _generateStr($len) { if ($len < 1 || $len >= 30) { return false; } $chars = ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'j', 'k', 'l', 'm', 'n', 'p', 'x', 'y', 'z', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'J', 'K', 'L', 'M', 'N', 'P', 'X', 'Y', 'Z', 1, 2, 3, 4, 5, 6, 7, 8, 9]; return implode('', array_rand(array_flip($chars), $len)); } /** * 生成随机颜色 * * @return int */ private function _getRandColor() { return imagecolorallocate($this->_image, mt_rand(0, 255), mt_rand(0, 255), mt_rand(0, 255)); } /** * 绘制雪花作为干扰元素 */ private function _getSnow() { for ($i = 1; $i <= $this->_snow; $i++) { imagestring($this->_image, mt_rand(1, 5), mt_rand(0, $this->_width), mt_rand(0, $this->_height), '*', $this->_getRandColor()); } } /** * 绘制相像素作为干扰元素 */ private function _getPixel() { for ($i = 1; $i < $this->_pixel; $i++) { imagesetpixel($this->_image, mt_rand(0, $this->_width), mt_rand(0, $this->_height), $this->_getRandColor()); } } /** * 绘制线段作为干扰元素 */ private function _getLine() { for ($i = 1; $i < $this->_pixel; $i++) { imageline($this->_image, mt_rand(0, $this->_width), mt_rand(0, $this->_height), mt_rand(0, $this->_width), mt_rand(0, $this->_height), $this->_getRandColor()); } } /** * 析构函数 销毁画布 */ public function __destruct() { imagedestroy($this->_image); } } // 使用示例 $config = [ 'font_file' => './fonts/PingFang.ttc', 'pixel' => 50, ]; $verify = new Verify($config); $verify_code = $verify->getVerify(); ```