java验证码生成的基本流程

1.验证码的生成,我们能够看到是用Graphics对象画出来的。对象我们必须要获得Graphics对象

1-1、Graphics对象的获取,要通过BufferedImage获得

<span style="font-size:18px;">int width=100;//确定框框的大小
 int height=40;
 BufferedImage bfi =new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
 Graphics g=bfi.getGraphics();//获得Graphics对象就可以画图</span> 

1-2、一般的验证码背景框都是白色的

<span style="font-size:18px;"> //1,设置背景(白框框)
 g.setColor(Color.WHITE);//白色的画笔
 g.fillRect(0, 0, width, height);//画矩形矩形框框</span>

1-3、保存数据(后台验证使用)和设置字体样式(美观)

String str="";//保存数据
 Random rom=new Random();
 //设置字体的大写与粗
 g.setFont(new Font("a", Font.BOLD,20)); 

1-4、生成具体的数值,以及随机生成的颜色

for(int i=0;i<4;i++){
  int num=rom.nextInt(10);//生成的随机数
  g.setColor(new Color(rom.nextInt(256),rom.nextInt(256), rom.nextInt(256)));//设置画笔的颜色(随机)
  g.drawString(""+num, 20*i, 20+rom.nextInt(10));//画出线,x的位置每一之间增加20,y的坐标以20一条线,在线上或者是线下
  //PS:位置需要明确些,
 } 

1-5、一般的数字容易被其他软件直接识别出来,为了防黑。稍微加一点干扰线

//画出一些干扰线
 for (int i = 0; i < 10; i++) {
  g.setColor(new Color(rom.nextInt(256),rom.nextInt(256), rom.nextInt(256)));//设置画笔的颜色(随机)
  g.drawLine(rom.nextInt(100),rom.nextInt(40), rom.nextInt(100), rom.nextInt(40));//位置也是随机,x,y的值不要超过矩形框框
 } 

1-6、销毁Graphics对象和存储图片

<span style="white-space:pre"> </span>g.dispose();//销毁对象
 ImageIO.write(bfi, "JPEG", res.getOutputStream());//图片用字节流 直接得到 PS::: res是Servlet里面的。

这样验证码就生成了,那我们如何导入到前台去呢

2、具体实现
前台代码呈现():

<body>
  <h1>用户登录</h1><br/>
  用户名:<input type="text" name="nametext"/><br/>
  密 码:<input type="text" name="psd"/><br/>
  请输入验证码:<input type="text"/>
  <img <span style="color:#ff0000;">src="/IMG/immg" </span>id="aid"/><a href="javascript:flush()" >看不清</a>
 </body> 

src的地址来源就是从后台发过来的。路径是很有意思的。
2-1步骤
项目里面
myeclipse --> src -->new  Servlet 出现如下:

点击----》next 出现如下页面:

这个配置会自动到项目里面的web-INF文件夹里面web.xml。这个框框里面的值就是前台 src里面写的需要访问的路径,----> 点击完成就行了。
自动了。生成如下界面:

在这里就可写之前的代码。但是需要注意,我们必须通过覆盖这个方法才能有效:

protected void service(HttpServletRequest req, HttpServletResponse resp)//自动生成 输入 <span style="font-family: Arial, Helvetica, sans-serif;">service 补全,自动生成</span> 

  throws ServletException, IOException {
 // TODO Auto-generated method stub
 super.service(req, resp);
}

具体的代码如下:

package cn.hncu.com.servlet; 

import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.image.BufferedImage;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Random; 

import javax.imageio.ImageIO;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse; 

public class Imgdemo extends HttpServlet {
@Override
public void service(ServletRequest req, ServletResponse res)
  throws ServletException, IOException {
 int width=100;//确定框框的大小
 int height=40;
 BufferedImage bfi =new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
 Graphics g=bfi.getGraphics();//获得Graphics对象就可以画图
 //1,设置背景(白框框)
 g.setColor(Color.WHITE);//白色的画笔
 g.fillRect(0, 0, width, height);//画矩形矩形框框
 //2,具体生成随机数
 String str="";//保存数据
 Random rom=new Random();
 //设置字体的大写与粗
 g.setFont(new Font("a", Font.BOLD,20));
 //画出具体的图片 

 for(int i=0;i<4;i++){
  int num=rom.nextInt(10);//生成的随机数
  g.setColor(new Color(rom.nextInt(256),rom.nextInt(256), rom.nextInt(256)));//设置画笔的颜色(随机)
  g.drawString(""+num, 20*i, 20+rom.nextInt(10));//画出线,x的位置每一之间增加20,y的坐标以20一条线,在线上或者是线下
  //PS:位置需要明确些,
 }
 //画出一些干扰线
 for (int i = 0; i < 10; i++) {
  g.setColor(new Color(rom.nextInt(256),rom.nextInt(256), rom.nextInt(256)));//设置画笔的颜色(随机)
  g.drawLine(rom.nextInt(100),rom.nextInt(40), rom.nextInt(100), rom.nextInt(40));//位置也是随机,x,y的值不要超过矩形框框
 }
 g.dispose();
 ImageIO.write(bfi, "JPEG", res.getOutputStream());//图片用字节流 直接得到
}
}<span style="font-family: Arial, Helvetica, sans-serif; background-color: rgb(255, 255, 255);"> </span>

前台代码:

<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<%
String path = request.getContextPath();
String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";
%> 

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
 <head>
 <base href="<%=basePath%>"> 

 <title>My JSP 'img.jsp' starting page</title> 

 <meta http-equiv="pragma" content="no-cache">
 <meta http-equiv="cache-control" content="no-cache">
 <meta http-equiv="expires" content="0">
 <meta http-equiv="keywords" content="keyword1,keyword2,keyword3">
 <meta http-equiv="description" content="This is my page">
 <!--
 <link rel="stylesheet" type="text/css" href="styles.css">
 -->
 <script type="text/javascript"> 

  function flush(){
  var text=document.getElementById("aid");
  var date =new Date();
  var tt=date.getTime();
  text.src="/IMG/immg?"+tt; 

  }
 </script> 

 </head> 

 <body>
  <h1>用户登录</h1><br/>
  用户名:<input type="text" name="nametext"/><br/>
  密 码:<input type="text" name="psd"/><br/>
  请输入验证码:<input type="text"/>
  <img src="/IMG/immg" id="aid"/><a href="javascript:flush()" >看不清</a>
 </body>
</html>

对于前台代码需要解释一下:
当我们的的验证码传过来看不清的时候需要刷新,而浏览器有自动记忆的功能,当没有新的参数传进来的时候,浏览器是不会刷新的,所以我们需要手动的去写一个js控制参数传,我们知道,只有时间是不会变化的,所有我们采用时间来作为参数传递。
PS:自己坑了一段时间的问题:验证码的路径问题。前端的“/”表示 tomcat目录,在项目内部,如web.xml中“/”表示该项目下。也就是说,他们两个的目录差了一层。

最后附上自己在测试的时候的代码以及修改数字形状的问题,如改成2D的效果更不错。都有很明显的记录。

package cn.hncu.com; 

import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.geom.AffineTransform;
import java.awt.image.BufferedImage;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Random; 

import javax.imageio.ImageIO; 

import org.junit.Test; 

public class Demoimg {
 @Test
 public void Test() throws Exception{
  String str="9988";
  int width=60;
  int height=30;
  //通过bufferedImage对象获得Graphics对象
  BufferedImage bfi=new BufferedImage(width, height, BufferedImage.TYPE_INT_BGR);
  Graphics g=bfi.getGraphics();
  g.drawString(str, 10,10);
  g.dispose();//类似于IO中的关流
  ImageIO.write(bfi , "JPEG", new FileOutputStream("F:\\ex\\a.jpg"));
  //bfi为画布,将画布写到文件中JPEG为指定文件格式
 } 

 @Test
 public void Test2() throws Exception{
  int width=100;
  int height=40;
  BufferedImage bfi =new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
  Graphics g=bfi.getGraphics();//获得Graphics对象就可以画图
  //1,设置背景(白框框)
  g.setColor(Color.WHITE);//白色的画笔
  g.fillRect(0, 0, width, height);
  //2,具体生成随机数
  String str="";//保存数据
  Random rom=new Random();
  //设置字体的大写与粗
  g.setFont(new Font("a", Font.BOLD,20));
  //画出具体的图片 

  for(int i=0;i<4;i++){
   int num=rom.nextInt(10);//生成的随机数
   g.setColor(new Color(rom.nextInt(256),rom.nextInt(256), rom.nextInt(256)));//设置画笔的颜色(随机)
   g.drawString(""+num, 20*i, 20+rom.nextInt(10));//画出线,x的位置每一之间增加20,y的坐标以20一条线,在线上或者是线下
   //PS:位置需要明确些,
  }
  //画出一些干扰线
  for (int i = 0; i < 10; i++) {
   g.setColor(new Color(rom.nextInt(256),rom.nextInt(256), rom.nextInt(256)));//设置画笔的颜色(随机)
   g.drawLine(rom.nextInt(100),rom.nextInt(40), rom.nextInt(100), rom.nextInt(40));//位置也是随机,x,y的值不要超过矩形框框
  }
  g.dispose();
  ImageIO.write(bfi, "JPEG", new FileOutputStream("F:\\ex\\b.jpg"));
 } 

 //画出可以变化的情况
 //字体能够旋转的验证码
 @Test
 public void Test3() throws IOException{
  int width=100;
  int height=40;
  BufferedImage bfi =new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
  Graphics g=bfi.getGraphics();
  Graphics2D g2d=(Graphics2D) g;
  Random rom =new Random();
  g2d.setColor(Color.WHITE);//设置画笔的颜色
  g2d.fillRect(0, 0, width, height);//画出一个白色的矩形
  g2d.setFont(new Font("a", Font.BOLD, 20));
  for(int i=0;i<4;i++){
   int num=rom.nextInt(10);
   //旋转,放缩
   AffineTransform aff=new AffineTransform();
   //aff.rotate(Math.random(), i*18, height-20);//旋转
   aff.scale(0.6+Math.random(), 0.6+Math.random());//缩放
   g2d.setColor(new Color(rom.nextInt(256),rom.nextInt(256),rom.nextInt(256)));
   g2d.setTransform(aff);
   g2d.drawString(""+num, i*18, height-25);
  }
  g2d.dispose();
  ImageIO.write(bfi, "JPEG", new FileOutputStream("F:\\ex\\c.jpg")); 

 }
} 

以上就是关于java生成验证码的基本流程,还附带了自己亲自的测试的代码,希望这些都能帮到大家。

(0)

相关推荐

  • Java仿12306图片验证码

    由于要做一个新项目,所以打算做一个简单的图片验证码. 先说说思路吧:在服务端,从一个文件夹里面找出8张图片,再把8张图片合并成一张大图,在8个小图里面随机生成一个要用户验证的图片分类,如小狗.啤酒等.在前端,访问这个页面时,把图片加载上去,用户在图片上选择提示所需要的图片,当用户点登陆时,根据用户选择的所有坐标判断所选的图片是不是实际上的验证图片. 先放两张效果图: 为了让文件查找比较简单,在图片文件结构上可以这样: 这样方便生成用户要选择的Key图片,和取出8张小图合并成大图. 上代码:这是选

  • java实用验证码的实现代码

    本文为大家分享了java实用验证码的实现代码,供大家参考,具体内容如下 1.ValidCode      package validImg; import java.awt.Color; import java.io.IOException; import java.util.Random; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http

  • java图片验证码生成教程详解

    首先,我们先来看本地如何生成图片验证码的,再来写输出到网页的验证码如何实现. 先来看最简单的-实现的功能是,将一个字符串变成图片写入到文件中 实现代码: package cn.hncu.img; import java.awt.Graphics; import java.awt.image.BufferedImage; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOE

  • java生成图片验证码实例代码

    关于java图片验证码的文章最近更新了不少,帮助大家掌握java验证码的生成技术,下文为大家分享了java生成图片验证码最简单的方法,供大家参考. 现在各行业在定制系统时都会考虑到机器注册,现在最有效的方式就是输入验证.现在的验证方式有很多种: 一.问题验证,其实也是图片验证,在图片上生成问题,然后输入框输入答案. 二.图片验证,输入图片上展示的文字信息. 三.短信验证,比较繁杂,用户也不怎么喜欢. 四.还有就是百度最新的验证方式.图片上生成文字,然后出现一个文字点击框,选择你在验证图片上看到的

  • 基于JAVA的短信验证码api调用代码实例

    本文实例为大家分享了JAVA的短信验证码api调用代码,供大家参考,具体内容如下 import java.io.BufferedReader; import java.io.DataOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.io.UnsupportedEncodingException; import jav

  • Java实现验证码具体代码(图片、汉字)

    本文为大家分享两个实例,相信大家一定会喜欢. 实例1:随机生成验证码图片并将之输出为一个png文件 效果图: import java.awt.Color; import java.awt.Font; import java.awt.Graphics; import java.awt.image.BufferedImage; import java.io.File; import java.io.IOException; import java.util.Random; import javax.

  • Javaweb开发中通过Servlet生成验证码图片

    一.BufferedImage类介绍 生成验证码图片主要用到了一个BufferedImage类,如下: 创建一个DrawImage Servlet,用来生成验证码图片 package gacl.response.study; import java.awt.Color; import java.awt.Font; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.image.BufferedImage; i

  • java下使用kaptcha生成验证码

    kaptcha是一个简单好用的验证码生成工具,通过配置,可以自己定义验证码大小.颜色.显示的字符等等.下面就来讲一下如何使用kaptcha生成验证码以及在服务器端取出验证码进行校验. 一.搭建测试环境 1.1.创建Web测试项目 新建一个Web项目,并将kaptcha-2.3.2.jar放在项目的WEB-INF/lib目录下,如下图所示: 1.2.在web.xml文件配置生成验证码的KaptchaServlet KaptchaServlet的详细配置如下: <?xml version="1

  • Java版仿QQ验证码风格图片验证码

    本文为大家分享了Java版仿QQ验证码风格图片验证码,具体内容如下 功能包括:自定义图片尺寸和字符长度,随机背景颜色和字符颜色,随机字符偏移角度,字符平滑边缘,干扰线,噪点,背景扭曲. 本来想做字符扭曲的,不知道怎的先生成文字再扭曲就报错了,先就这样吧,希望有高手能帮助修正一下. 需要说明的是之所以有几分像QQ的验证码感觉是因为这个Algerian字体,如果系统没有的话需要自行安装,百度搜字体名能下载到,丢系统Fonts文件夹就行. 效果图: package hh.com.util; impor

  • java验证码生成具体代码

    本文实例为大家分享了java验证码生成的示例代码,供大家参考,具体内容如下 package com.gonvan.component.captcha; import java.awt.*; import java.awt.image.BufferedImage; import java.io.IOException; import java.util.HashMap; import java.util.Map; import java.util.Random; import javax.imag

随机推荐