首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 網頁程式設計 >> PHP 程式設計 >> PHP 相關知識

PHP 生成數字字母混合驗證碼圖片:GD 庫完整實現與干擾元素優化

     編輯:PHP 相關知識

核心功能點

  • 畫布創建與背景填充
  • 隨機字符生成(數字+大小寫字母)
  • 字符繪製(隨機顏色、位置、角度、字體大小)
  • 干擾點、干擾線生成
  • 輸出 PNG 並銷毀資源

完整實現代碼

<?php
header('Content-Type: image/png');

// 1. 創建畫布
$width = 120;
$height = 40;
$image = imagecreatetruecolor($width, $height);

// 2. 背景色(淺色系)
$bgColor = imagecolorallocate($image, mt_rand(200, 255), mt_rand(200, 255), mt_rand(200, 255));
imagefill($image, 0, 0, $bgColor);

// 3. 字符池(去除易混淆字符:0/O, 1/I/l, 8/B 等)
$chars = '23456789abcdefghjkmnpqrstuvwxyzABCDEFGHJKLMNPQRSTUVWXYZ';
$charLen = strlen($chars);
$code = '';
$codeLen = 4;

// 4. 繪製驗證碼字符
for ($i = 0; $i < $codeLen; $i++) {
    $char = $chars[mt_rand(0, $charLen - 1)];
    $code .= $char;

    $fontSize = mt_rand(18, 24);
    $x = 10 + $i * 25 + mt_rand(-3, 3);
    $y = mt_rand(25, 32);
    $angle = mt_rand(-20, 20);
    $color = imagecolorallocate($image, mt_rand(0, 100), mt_rand(0, 100), mt_rand(0, 100));

    // 使用 TTF 字體需確認服務器字體路徑
    // imagettftext($image, $fontSize, $angle, $x, $y, $color, $fontPath, $char);

    // 內置字體備選
    imagestring($image, 5, $x, $y, $char, $color);
}

// 5. 存入 Session 驗證
session_start();
$_SESSION['captcha_code'] = strtolower($code); // 不區分大小寫

// 6. 干擾點(噪點)
for ($i = 0; $i < 80; $i++) {
    $color = imagecolorallocate($image, mt_rand(150, 255), mt_rand(150, 255), mt_rand(150, 255));
    imagesetpixel($image, mt_rand(0, $width), mt_rand(0, $height), $color);
}

// 7. 干擾線
for ($i = 0; $i < 4; $i++) {
    $color = imagecolorallocate($image, mt_rand(100, 200), mt_rand(100, 200), mt_rand(100, 200));
    imageline($image,
        mt_rand(0, $width/2), mt_rand(0, $height),
        mt_rand($width/2, $width), mt_rand(0, $height),
        $color
    );
}

// 8. 輸出並銷毀
imagepng($image);
imagedestroy($image);

前端調用示例

<img id="captcha" src="captcha.php" alt="點擊刷新" style="cursor:pointer;vertical-align:middle">
<input type="text" name="captcha" placeholder="輸入驗證碼">
<script>
document.getElementById('captcha').onclick = function() {
    this.src = 'captcha.php?' + Date.now(); // 防緩存
};
</script>

後端驗證邏輯

session_start();
if (strtolower($_POST['captcha']) !== ($_SESSION['captcha_code'] ?? '')) {
    exit('驗證碼錯誤');
}
// 通過後繼續業務邏輯
unset($_SESSION['captcha_code']); // 一次性使用

優化建議

方向建議
字體渲染使用 imagettftext + TTF 字體(如 DejaVuSans),效果遠優於內置字體
安全性字符池去除易混淆字符;驗證碼存入 Redis 並設置 5 分鐘過期
用戶體驗增加語音驗證碼選項;失敗後不刷新頁面自動換圖
性能高併發場景預生成驗證碼圖片池,或使用無 Session 的 JWT 簽名驗證碼
無障礙提供語音播報按鈕,符合 WCAG 2.1 AA 級標準

生產環境建議直接使用成熟庫:mewebstudio/captcha (Laravel)、Gregwar/Captcha (通用),避免重複造輪子。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved