使用java绘制图形验证码

验证码(CAPTCHA)是“Completely AutomatedPublic Turing test to tell Computers and Humans Apart”(全自动区分计算机和人类的图灵测试)的缩写。主要是用到了Graphics类或BufferedImage类的相关方法。
jsp页面的代码:

<title>验证码</title>
<script type="text/javascript">
    function changeImg(){
        var imgObj = document.getElementById("img");
        //Math.random() 获取一个随机数,用于防止浏览器缓存导致页面不刷新
        imgObj.src="CheckCodeServlet?ran="+Math.random();
    }
</script>
</head>
<body>
    <fieldset>
        <legend align="left">验证码</legend>
        <form action="CheckCodeServlet">
            验证码:<input type="text" name="safecode" />
            <img src="CheckCodeServlet" id="img" alt="图片加载失败" />
            <a href="javascript:changeImg()">看不清楚换一张</a>
            <input type="submit" value="提交" />
        </form>
    </fieldset>
</body>
</html>

与图片对应的servlet类的代码

public class CheckCodeServlet extends HttpServlet {

    protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        this.doPost(request, response);
    }

    protected void doPost(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        //设置响应头Content-type的类型
        response.setContentType("image/jpeg");
        OutputStream os = response.getOutputStream();
        //图片的宽、高
        int width = 83,height=30;
        //建立指定的宽、高和指定图像类型的BufferdImage对象
        BufferedImage image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
        //创建一个 Graphics 对象,相当于一个画笔
        Graphics g = image.getGraphics();
        //获取当前画笔的颜色并保存到c
        Color c = g.getColor();
        //填充矩形
        g.fillRect(0, 0, width, height);
        //一个字符串,用toCharyArray()转换为一个字符数组,用于随机生成字符
        String code = "abcdefghjknmpqrstuvwxyz23456789";
        char[] ch = code.toCharArray();
        //该数组的长度,即为随机字符的长度
        int length = ch.length;
        //用于保存随机生成的验证码字符串
        String sRand = "";
        //创建一个随机数生成器对象
        Random random = new Random();
        for(int i=0;i<4;i++){
            //通过getFont()方法获取随机的字体
            g.setFont(this.getFont());
            //获取到随机字符串中的一个随机字符,其中Character为char的包装类用来将char类型转换为String
            //等同于  String rand = ch[random.nextInt(length)]+"";
            String rand = new Character(ch[random.nextInt(length)]).toString();
            //拼接字符串,用于获取完整的四位字符
            sRand += rand;
            //创建3个0-255的随机数,用来为画笔g生成随机的颜色
            g.setColor(new Color(random.nextInt(255),random.nextInt(255),random.nextInt(255)));
            //使用此图形上下文的当前字体和颜色绘制由指定 string 给定的文本 
            //drawString(String str, int x, int y) 
            //str - 要绘制的 string。
            //x - x 坐标。
            //y - y 坐标。
            g.drawString(rand, 20*i+6, 25);
        }
        //产生随机干扰点,循环20次,则总共有20个干扰点
        for(int i=0;i<20;i++){
            //生成两个随机数,分别位于宽和高的范围内,用于表示画笔的位置
            int x1 = random.nextInt(width);
            int y1 = random.nextInt(height);
            //在指定的位置绘制干扰点
            //drawOval(int x, int y, int width, int height)
            //绘制椭圆的边框。得到一个圆或椭圆,它刚好能放入由 x、y、width 和 height 参数指定的矩形中。 
            //椭圆覆盖区域的宽度为 width + 1 像素,高度为 height + 1 像素。 
            //x - 要绘制椭圆的左上角的 x 坐标。
            //y - 要绘制椭圆的左上角的 y 坐标。
            //width - 要绘制椭圆的宽度。
            //height - 要绘制椭圆的高度。
            g.drawOval(x1, y1, 2, 2);
        }
        //重设画笔的颜色
        g.setColor(c);
        //释放此图形的上下文以及它使用的所有的系统资源
        g.dispose();
        //将创建的验证码中的字符记录到session中
        System.out.println("本次生成的验证码为"+sRand);
        request.getSession().setAttribute("safecode", sRand);
        //输出图像到页面中
        ImageIO.write(image, "JPEG", os);
    }

    //产生随机的字体的方法
    private Font getFont(){
        //创建random对象,用于生成随机数
        Random random = new Random();
        //创建自己数组,用于封装不同的字体对象
        Font[] font = new Font[5];
        int fontSize = 24;
        /*int[] arr = new int[5];
        ArrayList[] list = new ArrayList[5];*/
        font[0] = new Font("Ravie",Font.PLAIN,fontSize);
        font[1] = new Font("Antique Olive Compact",Font.PLAIN,fontSize);
        font[2] = new Font("Forte",Font.PLAIN,fontSize);
        font[3] = new Font("Wide Latin",Font.PLAIN,fontSize);
        font[4] = new Font("Gill Sans Ultra Bold",Font.PLAIN,fontSize);
        //使用随机数nextInt(5)方法生成0-5的的整数数字下标,然后返回该下标的随机数
        return font[random.nextInt(5)];
    }


}
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值