Struts2 session获取验证码
本章节将向大家展示,如何通过struts2框架和session来制作一张图片验证码。还不会搭建struts2框架的博友请参照博文:
http://blog.csdn.net/xie_xiansheng/article/details/51116321进行项目框架搭建。
接下来,请看:
那么,如何生成验证码图片并打印出四位验证码呢?
请看ImageUtiel类:
public final class ImageUtil { private static final char[] chars = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I' }; private static final int SIZE = 4; private static final int LINES = 5; private static final int WIDTH = 80; private static final int HEIGHT = 40; private static final int FONT_SIZE = 30; /** * 生成验证码图片,封装与Map中。 其中Map的key是验证码,Map的value是验证码图片。 */ public static Map<String, BufferedImage> createImage() { StringBuffer sb = new StringBuffer(); BufferedImage image = new BufferedImage(WIDTH, HEIGHT,BufferedImage.TYPE_INT_RGB); Graphics graphic = image.getGraphics(); graphic.setColor(Color.LIGHT_GRAY); graphic.fillRect(0, 0, WIDTH, HEIGHT); Random ran = new Random(); // 画随机字符 //生成4位验证码,画出图片,保存图片验证码值到sb里面 for (int i = 1; i <= SIZE; i++) { int r = ran.nextInt(chars.length); graphic.setColor(getRandomColor()); graphic.setFont(new Font(null, Font.BOLD + Font.ITALIC, FONT_SIZE)); graphic.drawString(chars[r] + "", (i - 1) * WIDTH / SIZE,HEIGHT / 2+10); sb.append(chars[r]);// 将字符保存,存入Session } // 画干扰线 for (int i = 1; i <= LINES; i++) { graphic.setColor(getRandomColor()); graphic.drawLine(ran.nextInt(WIDTH), ran.nextInt(HEIGHT), ran .nextInt(WIDTH), ran.nextInt(HEIGHT)); } Map<String, BufferedImage> map = new HashMap<String, BufferedImage>(); map.put(sb.toString(), image); return map; } /** * 将图片转换为输入流 */ public static InputStream getInputStream(BufferedImage image) throws IOException { ByteArrayOutputStream bos = new ByteArrayOutputStream(); JPEGImageEncoder encoder = JPEGCodec.createJPEGEncoder(bos); encoder.encode(image); byte[] imageBts = bos.toByteArray(); InputStream in = new ByteArrayInputStream(imageBts); return in; } /** * 获取随机颜色 */ private static Color getRandomColor() { Random ran = new Random(); Color color = new Color(ran.nextInt(256), ran.nextInt(256), ran .nextInt(256)); return color; } }
然后,我们定义一个BaseAction,使其他所需要用到session的Action类均继承它,就可以获取到一个全局session
public class BaseAction implements SessionAware{ protected Map<String, Object> session; public void setSession(Map<String, Object> arg0) { this.session = arg0; } }
定义一个Action,来获取验证码和验证码图片,并将验证码图片转换成流输出
public class CreateImgAction extends BaseAction{ private InputStream imgSteam; public String execute(){ //获得验证码图片Map Map<String, BufferedImage> imgMap = ImageUtil.createImage(); //因为只有一个,遍历Map集,取出4位验证码 String imgCode = imgMap.keySet().iterator().next(); System.out.println(imgCode); //将验证码放入session,登录时验证 session.put("IMGCODE", imgCode); //根据验证码获取图片 BufferedImage img = imgMap.get(imgCode); try { //将验证码图片转换成流 imgSteam = ImageUtil.getInputStream(img); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } return "success"; } public InputStream getImgSteam() { return imgSteam; } public void setImgSteam(InputStream imgSteam) { this.imgSteam = imgSteam; } }
我们需要在struts.xml里定义一个<action>标签,当页面访问此标签的时候,可以获取验证码流,并显示在页面上
<pre name="code" class="html"> <action name="showImg" class="org.great.action.CreateImgAction" method="execute"> <result type="stream" name="success"> <param name="inputName">imgSteam</param> </result> </action>
<td>验证码:</td> <td> <img id="imgCode" src="" onclick="imgChange()"> <input type="text" name="code" maxlength="4" size="4" align="bottom"/> </td>
<script type="text/javascript"> function imgChange(){ document.getElementById("imgCode").src="showImg?time="+new Date().getTime(); } imgChange(); </script>
<span style="color:#ff0000;">src="showImg?time="+new Date().getTime();</span>
showImg后携带的时间参数是为了改变访问地址,以便每次访问都能获取一张新的验证码