首頁  >  文章  >  後端開發  >  詳細介紹PHP驗證碼實作的原理

詳細介紹PHP驗證碼實作的原理

黄舟
黄舟原創
2017-03-11 10:38:131515瀏覽

拓展

我們需要開啟gd拓展,可以使用下面的程式碼來檢視是否開啟gd拓展。

<?phpecho "Hello World!!!!";echo phpinfo();?>

然後在瀏覽器上Ctrl+F查找gd選項即可驗證自己有沒有裝這個拓展,如果沒有的話,還需要自己全裝一下這個拓展。

背景圖

imagecreatetruecolor

預設產生黑色背景

<?php
// 使用gd的
imagecreatetruecolor();创建一张背景图
$image = imagecreatetruecolor(100,30);// 在显示这张图片的时候一定要先声明头信息
header(&#39;content-type:image/png&#39;);

imagepng($image);// 释放资源,销毁执行对象imagedestroy($image);

imagecolorallocate

建立一個填滿色,並用imagefill(image,x ,y,color)方法來附著。

<?php
// 使用gd的
imagecreatetruecolor();创建一张背景图
$image = imagecreatetruecolor(100,30);// 生成填充色
$bgcolor = imagecolorallocate($image,255,255,255);// 将填充色填充到背景图上
imagefill($image,0,0,$bgcolor);// 在显示这张图片的时候一定要先声明头信息
header(&#39;content-type:image/png&#39;);

imagepng($image);// 释放资源,销毁执行对象imagedestroy($image);

imagepng

在使用這個方法之前,一定要先設定頭訊息,否則不會正常的顯示圖片

imagedestory(image)

適時的釋放資源會減輕對伺服器請求的壓力。

簡易數字驗證碼

imagecolorallocate

#產生顏色訊息,方便待會的賦予處理。

$fontcolor=imagecolorallocate($image,rand(0,255),rand(0,255),rand(0,255));

imagestring

把內容資訊寫到圖片的對應位置。

imagestring($image,$fontsize,$x,$y,$fontcontent,$fontcolor);

增加識別幹擾

增加點

// 生成一些干扰的点,这里是200个
for($i=0;$i<200;$i++){    
$pointcolor = imagecolorallocate($image,rand(50,255),rand(50,255),rand(50,255));
    imagesetpixel($image,rand(0,100),rand(0,30),$pointcolor);
}

增加線

// 生成一些干扰线 这里是5个
for($i=0;$i<5;$i++){    // 设置为浅色的线,防止喧宾夺主
    $linecolor = imagecolorallocate($image,rand(50,255),rand(50,255),rand(50,255));
    imageline($image,rand(0,99),rand(0,29),rand(0,99),rand(0,29),$linecolor);

}

數字字母混合驗證碼

<?php
// 使用gd的imagecreatetruecolor();创建一张背景图
$image = imagecreatetruecolor(100,40);// 生成填充色
$bgcolor = imagecolorallocate($image,255,255,255);// 将填充色填充到背景图上
imagefill($image,0,0,$bgcolor);//////// 生成随机4位字母以及数字混合的验证码
for($i=0;$i<4;$i++){    
$fontsize = rand(6,8);    
$fontcolor = imagecolorallocate($image,rand(0,255),rand(0,255),rand(0,255));    
// 为了避免用户难于辨认,去掉了某些有歧义的字母和数字
    $rawstr = &#39;abcdefghjkmnopqrstuvwxyz23456789ABCDEFGHJKLMNOPQRSTUVWXYZ&#39;;    
    $fontcontent = substr($rawstr,rand(0,strlen($rawstr)),1);    
    // 避免生成的图片重叠
    $x += 20;    $y = rand(10,20);
    imagestring($image,$fontsize,$x,$y,$fontcontent,$fontcolor);   
}// 生成一些干扰的点,这里是200个for($i=0;$i<200;$i++){    
$pointcolor = imagecolorallocate($image,rand(50,255),rand(50,255),rand(50,255));
    imagesetpixel($image,rand(0,100),rand(0,30),$pointcolor);
}
// 生成一些干扰线 这里是4个for($i=0;$i<4;$i++){    
// 设置为浅色的线,防止喧宾夺主
    $linecolor = imagecolorallocate($image,rand(50,255),rand(50,255),rand(50,255));
    imageline($image,rand(0,99),rand(0,29),rand(0,99),rand(0,29),$linecolor);

}


header(&#39;content-type:image/png&#39;);

imagepng($image);// 释放资源,销毁执行对象imagedestroy($image);

使用驗證碼

開啟session的時機

注意: 開啟session一定要在開始的地方

## 驗證的原理

驗證的過程就是客戶端輸入的驗證碼和存在於session域中的驗證碼進行比較。即:

if(isset($_REQUEST[&#39;checkcode&#39;])){
        session_start();        
        if($_REQUEST[&#39;checkcode&#39;]==$_SESSION[&#39;checkcode&#39;]){            
        echo "<font color=&#39;green&#39;>Success!</font>"; 
        }else{            
        echo "<font color=&#39;red&#39;>Failed!</font>";    
        }        
        exit();
    }

優化驗證

但是簡單的這樣驗證有一點不好的地方,那就是字母的大小寫容易出錯。所以我們要做一下轉換,將使用者輸入的數值全部變成小寫的。

if(strtolower($_REQUEST[&#39;checkcode&#39;])==$_SESSION[&#39;checkcode&#39;]){···}

小案例

產生驗證碼

表單驗證

<?php
header("Content-Type:text/html;charset=utf8");        
if(isset($_REQUEST[&#39;checkcode&#39;])){
            session_start();            
            if(strtolower($_REQUEST[&#39;checkcode&#39;])==$_SESSION[&#39;checkcode&#39;]){                
            echo "<font color=&#39;green&#39;>Success!</font>"; 
            }else{                
            echo "<font color=&#39;red&#39;>Failed!</font>";    
            }            
            exit();
        }?>
        <!DOCTYPE html><html><head>
    <meta charset="utf-8" />
    <title>验证验证码信息</title>
    <script>
        function change(){
            document.getElementById("image_checkcode").src=&#39;./store.php?r=&#39;+Math.random();  
        }    </script></head><body><form action="./form.php" method="post"><p>验证码图片:</p>
        <img id="image_checkcode" src="./store.php?r=<?php echo rand();?>"   />
        <a href="javascript:void(0)" onclick="change()">看不清楚</a>
        <br/>请输入验证码<input type="text" name="checkcode" /><br /><p>
        <input type="submit" value="提交" /></p></form>
        </body></html>

總結

最後,來個總結吧。

  • 使用php製作驗證碼需要gd拓展的支援。

  • 使用imagecreatetruecolor方法產生背景色,並用imagefill填滿一個由imagecolorallocate產生的顏色。

  • 使用imagestring來實作驗證碼和背景圖的結合

  • 使用imagesetpixel來新增幹擾點

  • #使用imageline來新增幹擾線

  • 使用session之前要在開頭開啟session_start()方法

  • 使用JavaScript來動態的修改驗證碼的src,來滿足使用者「換一張」的需求。

  • #

以上是詳細介紹PHP驗證碼實作的原理的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn