java生成图片验证码

来源:互联网 发布:编程笔记本推荐 编辑:程序博客网 时间:2024/06/17 10:20

一、说明:

   此图片验证码生成的图片由大小写字母、数字、汉字组成,图片中字符大小被不同程度的缩放,或旋转。

 

二、常见的验证码:

  1、文本验证码:由一组数字组成,以文本的方式返回。

  2、简易的图片验证码:由数字和字母组成,以图片的方式返回。

  3、加入干扰线的图片验证码:由数字、字母、干扰线组成,,以图片的方式返回。

  4、单击验证码框时才生成并显示的验证码:除了是在单击验证码时,生成的验证码图片外,其他的和第三种一样。

 

三、示例代码:

  1、IdentifyingCode.java类。此类主要用于生成验证码字符串、画干扰线。

         在看此类之前应该先了解一下汉字的区位码:在国标GBK2312-80中规定,所有的国标汉字以及符号分配在一个94行、94列的方阵中,方阵的每一行称为一个“区”,编号为01区到94区,每一列称为一个“位”,编号01位到94位,方阵中的每一个汉字和符号所在的区号和位号组合在一起组成的4个阿拉伯数字就是他们的“区位码”。所有的汉字和符号所在的区分为4个组:

            a、01区到15区:图形符号区,其中01区到09区为标准符号区,10区到15区为自定义字符区。

            b、16区到55区:一级常用汉字区,包括2755个一级汉字。这40个区的汉字是按汉语拼音排序的,同音字按笔画顺序排序。

            c、56区到87区:二级汉字区,包括3008个二级汉字,按部首排序。

            d、88区到94区。

      代码:

Java代码  收藏代码
  1. import java.awt.Color;  
  2. import java.awt.Graphics2D;  
  3. import java.awt.geom.AffineTransform;  
  4. import java.util.Random;  
  5.   
  6. /** 
  7.  * 验证码图片生成器 
  8.  *  
  9.  * @author WuZhengFei 
  10.  *  
  11.  */  
  12. public class IdentifyingCode {  
  13.     /** 
  14.      * 验证码图片的宽度。 
  15.      */  
  16.     private int width = 80;  
  17.     /** 
  18.      * 验证码图片的高度。 
  19.      */  
  20.     private int height = 40;  
  21.     /** 
  22.      * 验证码的数量。 
  23.      */  
  24.     private Random random = new Random();  
  25.       
  26.     public IdentifyingCode(){}  
  27.     /** 
  28.      * 生成随机颜色 
  29.      * @param fc    前景色 
  30.      * @param bc    背景色 
  31.      * @return  Color对象,此Color对象是RGB形式的。 
  32.      */  
  33.     public Color getRandomColor(int fc, int bc) {  
  34.         if (fc > 255)  
  35.             fc = 200;  
  36.         if (bc > 255)  
  37.             bc = 255;  
  38.         int r = fc + random.nextInt(bc - fc);  
  39.         int g = fc + random.nextInt(bc - fc);  
  40.         int b = fc + random.nextInt(bc - fc);  
  41.         return new Color(r, g, b);  
  42.     }  
  43.       
  44.     /** 
  45.      * 绘制干扰线 
  46.      * @param g Graphics2D对象,用来绘制图像 
  47.      * @param nums  干扰线的条数 
  48.      */  
  49.     public void drawRandomLines(Graphics2D g ,int nums ){  
  50.         g.setColor(this.getRandomColor(160200)) ;  
  51.         for(int i=0 ; i<nums ; i++){  
  52.             int x1 = random.nextInt(width) ;  
  53.             int y1 = random.nextInt(height);  
  54.             int x2 = random.nextInt(12) ;  
  55.             int y2 = random.nextInt(12) ;  
  56.             g.drawLine(x1, y1, x2, y2) ;  
  57.         }  
  58.     }  
  59.       
  60.     /** 
  61.      * 获取随机字符串, 
  62.      *      此函数可以产生由大小写字母,汉字,数字组成的字符串 
  63.      * @param length    随机字符串的长度 
  64.      * @return  随机字符串 
  65.      */  
  66.     public String drawRandomString(int length , Graphics2D g){  
  67.         StringBuffer strbuf = new StringBuffer() ;  
  68.         String temp = "" ;  
  69.         int itmp = 0 ;  
  70.         for(int i=0 ; i<length ; i++){  
  71.             switch(random.nextInt(5)){  
  72.             case 1:     //生成A~Z的字母  
  73.                 itmp = random.nextInt(26) + 65 ;  
  74.                 temp = String.valueOf((char)itmp);  
  75.                 break;  
  76.             case 2:  
  77.                 itmp = random.nextInt(26) + 97 ;  
  78.                 temp = String.valueOf((char)itmp);  
  79.             case 3:     //生成汉字  
  80.                 String[] rBase = {"0" , "1" , "2" , "3" , "4" , "5" , "6" , "7" ,   
  81.                         "8" , "9" , "a" , "b" , "c" , "d" , "e" , "f" };  
  82.                 int r1 = random.nextInt(3)+11 ;     //生成第1位的区码  
  83.                 String strR1 = rBase[r1] ;      //生成11~14的随机数  
  84.                 int r2 ;        //生成第2位的区码  
  85.                 if(r1 == 13)  
  86.                     r2 = random.nextInt(7) ;    //生成0~7的随机数  
  87.                 else  
  88.                     r2 = random.nextInt(16) ;   //生成0~16的随机数  
  89.                 String strR2 = rBase[r2] ;  
  90.                 int r3 = random.nextInt(6) + 10 ;   //生成第1位的位码  
  91.                 String strR3 = rBase[r3] ;  
  92.                 int r4 ;        //生成第2位的位码  
  93.                 if(r3 == 10)  
  94.                     r4 = random.nextInt(15) + 1;    //生成1~16的随机数  
  95.                 else if(r3 == 15)  
  96.                     r4 = random.nextInt(15) ;       //生成0~15的随机数  
  97.                 else  
  98.                     r4 = random.nextInt(16) ;       //生成0~16的随机数  
  99.                 String strR4 = rBase[r4] ;  
  100.                 //将生成的机内码转换成数字  
  101.                 byte[] bytes = new byte[2]   ;        
  102.                 String strR12 = strR1 + strR2 ;     //将生成的区码保存到字节数组的第1个元素中  
  103.                 int tempLow = Integer.parseInt(strR12, 16) ;  
  104.                 bytes[0] = (byte)tempLow;  
  105.                 String strR34 = strR3 + strR4 ;     //将生成的区码保存到字节数组的第2个元素中  
  106.                 int tempHigh = Integer.parseInt(strR34, 16) ;  
  107.                 bytes[1] = (byte)tempHigh;  
  108.                 temp = new String(bytes);           //根据字节数组生成汉字  
  109.                 break;  
  110.             default:  
  111.                 itmp = random.nextInt(10) + 48 ;  
  112.                 temp = String.valueOf((char)itmp) ;  
  113.                 break;  
  114.             }  
  115.             Color color = new Color(20+random.nextInt(20) , 20+random.nextInt(20) ,20+random.nextInt(20) );  
  116.             g.setColor(color) ;  
  117.             //想文字旋转一定的角度  
  118.             AffineTransform trans = new AffineTransform();  
  119.             trans.rotate(random.nextInt(45)*3.14/18015*i+87) ;  
  120.             //缩放文字  
  121.             float scaleSize = random.nextFloat() + 0.8f ;  
  122.             if(scaleSize>1f)  
  123.                 scaleSize = 1f ;  
  124.             trans.scale(scaleSize, scaleSize) ;  
  125.             g.setTransform(trans) ;  
  126.             g.drawString(temp, 15*i+1814) ;  
  127.               
  128.             strbuf.append(temp) ;  
  129.         }  
  130.         g.dispose() ;  
  131.         return strbuf.toString() ;  
  132.     }  
  133.     public int getWidth() {  
  134.         return width;  
  135.     }  
  136.     public void setWidth(int width) {  
  137.         this.width = width;  
  138.     }  
  139.     public int getHeight() {  
  140.         return height;  
  141.     }  
  142.     public void setHeight(int height) {  
  143.         this.height = height;  
  144.     }  
  145. }     

 

 

  2、PictureCheckCode.java类。此类是一个servlet。

      代码:

Java代码  收藏代码
  1. import java.awt.Font;  
  2. import java.awt.Graphics2D;  
  3. import java.awt.image.BufferedImage;  
  4. import java.io.IOException;  
  5.   
  6. import javax.imageio.ImageIO;  
  7. import javax.servlet.ServletException;  
  8. import javax.servlet.http.HttpServlet;  
  9. import javax.servlet.http.HttpServletRequest;  
  10. import javax.servlet.http.HttpServletResponse;  
  11.   
  12. @SuppressWarnings("serial")  
  13. public class PictureCheckCode extends HttpServlet {  
  14.       
  15.     public PictureCheckCode() {  
  16.         super();  
  17.     }  
  18.       
  19.     public void init() throws ServletException {  
  20.         super.init() ;  
  21.     }  
  22.     public void destroy() {  
  23.         super.destroy();   
  24.     }  
  25.   
  26.     public void doGet(HttpServletRequest request, HttpServletResponse response)  
  27.             throws ServletException, IOException {  
  28.         doPost(request, response) ;  
  29.   
  30.     }  
  31.   
  32.     public void doPost(HttpServletRequest request, HttpServletResponse response)  
  33.             throws ServletException, IOException {  
  34.         //设置不缓存图片  
  35.         response.setHeader("Pragma""No-cache");  
  36.         response.setHeader("Cache-Control""No-cache");  
  37.         response.setDateHeader("Expires"0) ;  
  38.         //指定生成的相应图片  
  39.         response.setContentType("image/jpeg") ;  
  40.         IdentifyingCode idCode = new IdentifyingCode();  
  41.         BufferedImage image =new BufferedImage(idCode.getWidth() , idCode.getHeight() , BufferedImage.TYPE_INT_BGR) ;  
  42.         Graphics2D g = image.createGraphics() ;  
  43.         //定义字体样式  
  44.         Font myFont = new Font("黑体" , Font.BOLD , 16) ;  
  45.         //设置字体  
  46.         g.setFont(myFont) ;  
  47.           
  48.         g.setColor(idCode.getRandomColor(200 , 250)) ;  
  49.         //绘制背景  
  50.         g.fillRect(00, idCode.getWidth() , idCode.getHeight()) ;  
  51.           
  52.         g.setColor(idCode.getRandomColor(180200)) ;  
  53.         idCode.drawRandomLines(g, 160) ;  
  54.         idCode.drawRandomString(4, g) ;  
  55.         g.dispose() ;  
  56.         ImageIO.write(image, "JPEG", response.getOutputStream()) ;  
  57.     }  
  58. }  

 

 

  3、web.xml

     代码:

Java代码  收藏代码
  1. <?xml version="1.0" encoding="UTF-8"?>  
  2. <web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"  
  3.     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"  
  4.     xsi:schemaLocation="http://java.sun.com/xml/ns/javaee   
  5.     http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">  
  6.     <servlet>  
  7.         <servlet-name>PictureCheckCode</servlet-name>  
  8.         <servlet-class>com_2.PictureCheckCode</servlet-class>  
  9.     </servlet>  
  10.   
  11.     <servlet-mapping>  
  12.         <servlet-name>PictureCheckCode</servlet-name>  
  13.         <url-pattern>/PictureCheckCode.jpeg</url-pattern>  
  14.     </servlet-mapping>  
  15.   
  16.     <welcome-file-list>  
  17.         <welcome-file>index.jsp</welcome-file>  
  18.     </welcome-file-list>  
  19. </web-app>  

 

 

  4、index.jsp

     代码:

Java代码  收藏代码
  1. <%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>  
  2.   
  3. <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">  
  4. <html>  
  5.   <head>  
  6.     <title>IdentifyingCode page</title>  
  7.     <script type="text/javascript">  
  8.         function myReload(){  
  9.             document.getElementById("createCheckCode").src=document.getElementById("createCheckCode").src + "?nocache="+new Date().getTime();  
  10.         }  
  11.     </script>  
  12.   </head>  
  13.     
  14.   <body>  
  15.     <form action="PictureCheckCode" method="post">  
  16.         <input name="checkCode" type="text" id="checkCode" title="验证码区分大小写" maxlength="4">  
  17.         <img id="createCheckCode" src="PictureCheckCode.jpeg">  
  18.         <a href="#" onClick="myReload()">看不清,换一个</a>  
  19.     </form>  
  20.   </body>  
  21. </html>  
0 0
原创粉丝点击