若是說要作驗證碼,那不得不提的就是GDI+繪圖了。咱們都知道驗證碼是以圖片形式展現的,並且是動態生成的,這樣就須要咱們去畫出它。html
科普一下,什麼是GDI+?web
GDI+是圖形設備接口(GDI)的高級版本, 提供了各類豐富的圖形圖像處理功能。GDI+主要由二維矢量圖形、圖像處理和版式3部分組成。GDI+爲使用各類字體、字號和樣式來顯示文本這種複雜任務提供了大量的支持。ajax
下面說說驗證碼,對於驗證碼這樣的圖片,我以爲是由兩部分組成的,一部分是矩形的背景,另外一部分是在其上的字母數字組合(有的時候有漢字,有的時候是純字母或者純數字,這個沒有統一規定,怎麼選擇看你~)。對於矩形的背景咱們能夠直接把其當成畫布,字母數字組合呢?咱們能夠利用隨機數去拼出一組新組合。這樣整個過程咱們都想好了,下面看下代碼吧:數組
聲明一下,我寫的這個驗證碼爲5個字符長度,由大小寫英文字母+數字隨機組合。session
private readonly char[] constant = { '0','1','2','3','4','5','6','7','8','9', 'a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z', 'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z'};//一個由數字和大小寫英文字母組成的字符數組 protected void Page_Load(object sender, EventArgs e) { Bitmap bitmap = new Bitmap(100, 25);//建立一個位圖,寬100,高25,就是我所說的第一部分,矩形背景 Graphics g = Graphics.FromImage(bitmap);//建立畫布 g.Clear(Color.YellowGreen);//爲畫布填充黃綠色 Font font1 = new Font("Arial", 15);//設置字體類型和大小 Brush brush = new SolidBrush(Color.Blue);//設置畫刷顏色 Pen myPen = new Pen(Color.Blue, 5);//建立畫筆對象 StringBuilder random = new StringBuilder(5); //建立可變字符串對象,用於存放隨機生成的驗證碼 Random rd = new Random();//建立一個隨機數生成器對象 for (int i = 0; i < random.Capacity; i++) { random.Append(constant[rd.Next(62)]);//生成一個隨機字符加到random裏 } g.DrawString(random.ToString(), font1, brush, 10, 5);//在畫布上畫出字符串 System.IO.MemoryStream ms = new System.IO.MemoryStream();//建立數據流MemoryStream bitmap.Save(ms, System.Drawing.Imaging.ImageFormat.Gif);//指定圖像的輸出格式爲gif Response.ClearContent(); Response.ContentType = "image/Gif"; Response.BinaryWrite(ms.ToArray());//輸出二進制數據流 }
生成的效果是這樣的:dom
你們可能會以爲這樣看起來很容易辨識,跟咱們平時登陸網站時輸入的驗證碼比起來有點像個小學生。固然,咱們能夠作些改變,比較加上必定的角度。字體
private readonly char[] constant = { '0','1','2','3','4','5','6','7','8','9', 'a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z', 'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z'};//一個由數字和大小寫英文字母組成的字符數組 protected void Page_Load(object sender, EventArgs e) { Bitmap bitmap = new Bitmap(100, 25);//建立一個位圖,寬100,高25,就是我所說的第一部分,矩形背景 Graphics g = Graphics.FromImage(bitmap);//建立畫布 g.Clear(Color.YellowGreen);//爲畫布填充黃綠色 Font font1 = new Font("Arial", 15);//設置字體類型和大小 float angle = 60;//旋轉的一個基礎角度 float length = 0;//顯示字符的基礎位置,日後看 Brush brush = new SolidBrush(Color.Blue);//設置畫刷顏色 Pen myPen = new Pen(Color.Blue, 5);//建立畫筆對象 StringBuilder random = new StringBuilder(5); //建立可變字符串對象,用於存放隨機生成的驗證碼 Random rd = new Random();//建立一個隨機數生成器對象 for (int i = 0; i < random.Capacity; i++) { random.Append(constant[rd.Next(62)]);//生成一個隨機字符加到random裏 g.ResetTransform();//將畫布重置矩陣 SizeF size = g.MeasureString(random[random.Length - 1].ToString(), font1);//獲得新生成字符的尺寸 g.TranslateTransform(length + size.Width / 2, size.Height / 2);//選擇這次旋轉的中心位置 g.RotateTransform((float)rd.NextDouble() * angle * 2 - angle);//進行隨機角度旋轉 g.DrawString(random[random.Length - 1].ToString(), font1, brush, new PointF(-size.Width / 2, -size.Height / 2));//注意,這裏不是前一個例子,一次性把5個字符所有畫出來,而是一個一個畫 length += size.Width;//保證下次畫字符的位置不會覆蓋前一次的字符 } System.IO.MemoryStream ms = new System.IO.MemoryStream();//建立數據流MemoryStream bitmap.Save(ms, System.Drawing.Imaging.ImageFormat.Gif);//指定圖像的輸出格式爲gif Response.ClearContent(); Response.ContentType = "image/Gif"; Response.BinaryWrite(ms.ToArray());//輸出二進制數據流 }
這時生成的效果是這樣的:網站
是否是看起來更專業一些了呢?若是你們仍是以爲不滿意的話,能夠看下GDI+的相關內容,經過添加一些噪點的元素,或者刪除線這樣子的東西來達到提升識別難度的目的,我這裏就不一一列舉啦。ui
關於如何畫驗證碼咱們說過了,可是還有兩點問題我仍是想多說一下。url
一、咱們實際輸出的是一個二進制的流,如何作到顯示到頁面上與頁面其餘元素共存呢?
這裏通用的一種方法就是把畫驗證碼的這段代碼放到一個獨立的Web窗體頁中,在另外一個須要顯示驗證碼的頁面放一個<img>元素,把其src屬性指向該驗證碼頁的url。好比我寫的一段是這樣
<asp:Image ID="image_validatecode" runat="server" ImageUrl="~/PublicMethod/ValidateCode.aspx" style="padding-left:3px"/>
其實這裏我是用你們通用的方法,不過我先前也有單獨寫一個web自定義控件,專門生成驗證碼使用,可是當拖入到頁面中後運行,它仍是會把頁面其餘元素給覆蓋掉,具體緣由我也不清楚。
二、驗證碼主要目的仍是用於驗證使用的,因此咱們在用戶名,密碼是否合法外,同時也要判斷當前輸入的驗證碼是否是與圖片上的驗證碼一致。
我上面的代碼中並無寫這塊,其實只要在隨機生成最終驗證碼以後,把其值存入一個session中去就能夠了。而後在判斷用戶名,密碼的同時去比較一下這個session值就OK了。如:
Session["login_validate_code"] = random.ToString();
三、如何用戶沒有看清此張驗證碼,想換一張如何實現?
能夠經過腳本給img元素的src屬性從新賦值url實現,固然,麻煩點的話也可使用ajax去實現。你們能夠本身試試。