生成图形验证码
Posted hhr-sun
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了生成图形验证码相关的知识,希望对你有一定的参考价值。
package com.cinc.ecmpusercenter.utils; import com.cinc.ecmpusercenter.exception.BasException; import com.thoughtworks.xstream.core.util.Base64Encoder; import javax.imageio.ImageIO; import java.awt.*; import java.awt.image.BufferedImage; import java.io.*; import java.util.Random; /** * @Author: hhr * @Despriction: 图片验证码生成 * @CreatedTime: 2019/7/30 8:58 * @ModifyBy: * @ModifyTime: * @ModifyDespriction: * @Version: V1.0.0 */ @SuppressWarnings("AlibabaCommentsMustBeJavadocFormat") public class Captcha // 图片的宽度 private int width = 120; // 图片的高度 private int height = 40; // 验证码字符个数 private int codeCount = 4; // 验证码干扰线数 private int lineCount = 50; // 验证码 private String code = null; // 验证码图片Buffer private BufferedImage buffImg = null; private char[] codeSequence = ‘A‘, ‘B‘, ‘C‘, ‘D‘, ‘E‘, ‘F‘, ‘G‘, ‘H‘, ‘I‘, ‘J‘, ‘K‘, ‘M‘, ‘N‘, ‘P‘, ‘Q‘, ‘R‘, ‘S‘, ‘T‘, ‘U‘, ‘V‘, ‘W‘, ‘X‘, ‘Y‘, ‘Z‘, ‘2‘, ‘3‘, ‘4‘, ‘5‘, ‘6‘, ‘7‘, ‘8‘, ‘9‘ ; // 生成随机数 private Random random = new Random(); public Captcha() this.createCode(); /** * 生成图片 * @param width 图片宽 * @param height 图片高 */ public Captcha(int width, int height) this.width = width; this.height = height; this.createCode(); /** * 生成图片 * @param width 图片宽 * @param height 图片高 * @param codeCount 字符个数 * @param lineCount 干扰线条数 */ public Captcha(int width, int height, int codeCount, int lineCount) this.width = width; this.height = height; this.codeCount = codeCount; this.lineCount = lineCount; this.createCode(); public void createCode() // 字体的高度 int codeX = 0; // 每个字符的宽度 int fontHeight = 0; fontHeight = height - 5; codeX = width / (codeCount + 3); // 图像buffer buffImg = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB); Graphics2D g = buffImg.createGraphics(); //将图像填充为白色,设置随机背景色 g.setColor(this.getRandomColor(0, 50)); g.fillRect(0, 0, width, height); //随机生成干扰线 g.setColor(this.getRandomColor(50, 100)); for (int i = 0; i < lineCount; i++) int x = random.nextInt(width); int y = random.nextInt(height); int xl = random.nextInt(width); int yl = random.nextInt(height); g.drawLine(x,y,xl,yl); // 创建字体 ImgFontByte imgFont = new ImgFontByte(); Font font = imgFont.getFont(fontHeight); g.setFont(font); StringBuffer randomCode = new StringBuffer(); // 随机产生验证码字符 for (int i = 0; i < codeCount; i++) String strRand = String.valueOf(codeSequence[random.nextInt(codeSequence.length)]); // 设置字体颜色 g.setColor(getRandomColor(100,250)); // 设置字体位置 g.drawString(strRand, (i + 1) * codeX, getRandomNumber(height / 2) + 25); randomCode.append(strRand); code = randomCode.toString(); /** 获取随机颜色 */ private Color getRandomColor(int bc,int fc) if (bc > 255) bc = 255; if (fc > 255) fc = 255; int r = getRandomNumber(fc - bc); int g = getRandomNumber(fc - bc); int b = getRandomNumber(fc - bc); return new Color(r, g, b); /** 获取随机数 */ private int getRandomNumber(int number) return random.nextInt(number); public void write(String path) throws IOException OutputStream sos = new FileOutputStream(path); this.write(sos); public void write(OutputStream sos) throws IOException ImageIO.write(buffImg, "png", sos); sos.close(); public BufferedImage getBuffImg() return this.buffImg; public String getCode() return this.code; /** 字体样式类 */ class ImgFontByte public Font getFont(int fontHeight) try Font baseFont = Font.createFont(Font.HANGING_BASELINE, new ByteArrayInputStream( hex2byte(getFontByteStr()))); return baseFont.deriveFont(Font.PLAIN, fontHeight); catch (Exception e) return new Font("Arial", Font.PLAIN, fontHeight); private byte[] hex2byte(String str) if (str == null) return null; str = str.trim(); int len = str.length(); if (len == 0 || len % 2 == 1) return null; byte[] b = new byte[len / 2]; try for (int i = 0; i < str.length(); i += 2) b[i / 2] = (byte) Integer.decode("0x" + str.substring(i, i + 2)).intValue(); return b; catch (Exception e) return null; // 字体文件的十六进制字符串 private String getFontByteStr() //防止报字符串长度过长错误,改为从配置文件读取 //return ReadFontByteProperties.getFontByteStr(); return "宋体"; /** * 验证 * @param localCode 后台保存的验证码 * @param upLoadCode 前台上送的验证码 * @return */ public boolean validateCode(String localCode,String upLoadCode) if (EmptyUtils.isStringEmpty(localCode) || EmptyUtils.isStringEmpty(upLoadCode)) throw new BasException("ERROR","验证码过期,请重试"); boolean flag = false; upLoadCode = upLoadCode.toUpperCase(); if (localCode.equals(upLoadCode)) flag = true; return flag; /** * 对BufferedImage进行base64转码 * @return * @throws IOException */ public String getEncodeBase64() throws IOException Base64Encoder encoder = new Base64Encoder(); ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); ImageIO.write(buffImg, "png", outputStream); byte[] bytes = outputStream.toByteArray(); String imageEncode = encoder.encode(bytes); return imageEncode;
以上是关于生成图形验证码的主要内容,如果未能解决你的问题,请参考以下文章