java生成验证码

来源:互联网 发布:手机安易数据恢复软件 编辑:程序博客网 时间:2024/03/29 14:38

思路:

1、生成固定大小的图片

2、得到图片的画笔,从而可以对图片进行一些操作

3、在图片上写一些随机的数字,画一些随机的线条或是一些随机的点

4、保存图片。

 

package com.demo.imageauthcode;import java.awt.Color;import java.awt.Font;import java.awt.Graphics;import java.awt.image.BufferedImage;import java.io.File;import java.io.FileNotFoundException;import java.io.FileOutputStream;import java.io.IOException;import java.io.OutputStream;import java.util.Random;import com.sun.image.codec.jpeg.ImageFormatException;import com.sun.image.codec.jpeg.JPEGCodec;import com.sun.image.codec.jpeg.JPEGImageEncoder;public class ValidateCode {//生成图片的高度和宽度private static final int IMAGEHEIGHT = 20;private static final int IMAGEWIDTH = 48;Random r = new Random();public static void main(String[] args) {ValidateCode i = new ValidateCode();i.generateImage();}/** * 根据随机数生成图片 * */public void generateImage(){//图片宽度与高度还有格式BufferedImage image = new BufferedImage(IMAGEWIDTH, IMAGEHEIGHT, BufferedImage.TYPE_INT_RGB);//得到图片上的画笔Graphics g = image.getGraphics();//画笔的背影颜色g.setColor(Color.gray);g.fillRect(0, 0, IMAGEWIDTH, IMAGEHEIGHT);//画笔颜色和字体g.setColor(Color.white);g.setFont(new Font("宋体",Font.PLAIN,12));char c;String randomStr = this.getRandomStr();for(int i=0;i<4;i++){c = randomStr.charAt(i);g.drawString(c+"", i*10+8, IMAGEHEIGHT/4*3);}//画点this.getRandomPoints(g, IMAGEHEIGHT, IMAGEWIDTH);this.getRandomPoints(g, IMAGEHEIGHT, IMAGEWIDTH);this.getRandomPoints(g, IMAGEHEIGHT, IMAGEWIDTH);//画线g.setColor(Color.blue);this.getRandomLines(g, IMAGEHEIGHT, IMAGEWIDTH);this.getRandomLines(g, IMAGEWIDTH, IMAGEHEIGHT);//保存图片OutputStream out = null;try {out = new FileOutputStream(new File("D:\\test.jpg"));} catch (FileNotFoundException e) {e.printStackTrace();}//JPG编码器JPEGImageEncoder encoder=JPEGCodec.createJPEGEncoder(out);try {encoder.encode(image);} catch (ImageFormatException e) {e.printStackTrace();} catch (IOException e) {e.printStackTrace();}try {out.close();} catch (IOException e) {e.printStackTrace();}}/** *  * 生成一个长度为4的,带有大小写字母和数字的字符串 *  * 思路:一共四位字母,每个字母有62(数字0-9,小写字母a-z,大写字母A-Z)中可能 * 所以可以规定0-9就为数字,10-36为小写字母,37-62为大写字母 *  * */public String getRandomStr(){StringBuffer str = new StringBuffer();Random r  = new Random();for(int i=0;i<4;i++){int t = r.nextInt(62);if(t<10){str.append(t);}else if(t>=10 && t<=36){str.append((char)(t+87));}else{str.append((char)(t+28));}}System.out.println(str);return str.toString();}/** *  * 画一些随机的线条 * */public void getRandomLines(Graphics g,int h,int w){int x1= r.nextInt(h);int y1 = r.nextInt(w);int x2 = r.nextInt(w);int y2 = r.nextInt(h);g.drawLine(x1, y1, x2, y2);}/** * 画一些随机的点 * */public void getRandomPoints(Graphics g,int h,int w){int x = r.nextInt(h);int y = r.nextInt(w);g.drawString(".", x, y);}}


 在JSP页面中的应用如下

首先是个提交表单,样子长这个样

代码如下

<%@ page language="java" import="java.util.*" pageEncoding="utf-8"%><!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"><html>  <head>    <title>My JSP 'index.jsp' starting page</title>  </head>  <body>  <form action="validate.jsp" method="post">  <input type="text" name="inputCode" />  <img src="code.jsp">  <br/>  <input type="submit" value="提交"/>  </form>  </body></html>


代码中img包含的页面就是生成验证码的页面,代码如下

<%@ page language="java" contentType="text/html; charset=ISO-8859-1"pageEncoding="utf-8"import="java.util.*,java.io.*,java.awt.*,java.awt.image.*,com.sun.image.codec.jpeg.*"%><!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"><%String s ="";int c = 0;c = (new Random()).nextInt(9999);if(c<1000)c+=1000;s = c+"";session.setAttribute("validateCode",s);response.setContentType("image/gif");//图片宽度与高度还有格式BufferedImage image = new BufferedImage(48, 20, BufferedImage.TYPE_INT_RGB);//得到图片上的画笔Graphics g = image.getGraphics();//画笔的背影颜色g.setColor(Color.gray);g.fillRect(0, 0, 48, 20);//画笔颜色和字体g.setColor(Color.white);g.setFont(new Font("宋体",Font.PLAIN,12));for(int i=0;i<4;i++){char ch = s.charAt(i);g.drawString(ch+"", i*10+8, 15);}OutputStream outputstream = response.getOutputStream();JPEGImageEncoder encoder=JPEGCodec.createJPEGEncoder(outputstream);encoder.encode(image);outputstream.close();out.clear();out = pageContext.pushBody(); %>


最后还有一个判断是否正确的页面,代码如下。

<%@ page language="java" import="java.util.*" pageEncoding="utf-8"%><!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"><html>  <head>  </head>  <body>  <%  String inputCode = request.getParameter("inputCode");  String validateCode = (String)session.getAttribute("validateCode");  if(inputCode.equals(validateCode))  {  out.println("right");  }else{  out.println("wrong");  out.println("<a href=\"javascript:history.go(-1)\">返回</a>");  }   %>  </body></html>