经过艰辛万苦终于把验证码弄出点人样来了(其实还是在别人的基础上改过来的,呵呵)
这个验证码有两种使用方式,下面就分别介绍下:
(一)当作控件使用:
(二)当做一个类来调用:
如果觉得可以的话,就支持下啊
经过艰辛万苦终于把验证码弄出点人样来了(其实还是在别人的基础上改过来的,呵呵)
这个验证码有两种使用方式,下面就分别介绍下:
(一)当作控件使用:
第一步:
编译我提供的原代码, 然后,在Studio.net 2003工具栏上, 选择"添加/移除项", 选中编译好的dll文件。
第二步:
工具栏上就会多一个Web控件ValidateCode,做好一个Web窗体(我是做了个WEB用户控件),在Studio.net 2003开发界面上,直接把控件拖到WebForm上,就OK!
第三步:
在该控件的GraphicOK事件中获取,验证码的字符信息,用于和用户录入做比较!
第四步:
在网站的根目录下,建一个temp目录(也可以自己指定目录),用于存放验证码
最后一步:
在登陆页面你需要显示验证码的地方把第二步做好的那个WEB窗体或WEB用户控件嵌套进去就行了;
(二)当做一个类来调用:
为什么要做出这个用处呢,是因为我发现用上面的那种方法显示验证码时图片的位置会有点偏差。
第一步:
编译我提供的原代码, 然后,在Studio.net 2003工具栏上, 选择"添加/移除项", 选中编译好的dll文件。
第二步:
在登陆页面需要显示验证码的地方放个文本框,设置成只读型。
第三步:
在后台的Page_Load中添加下面的代码:
ValidateCode validatecode = new ValidateCode();
validatecode.TempImageURLPath = @"/WebApp/temp"; //虚拟路径
validatecode.TempImagePath = this.Page.MapPath(validatecode.TempImageURLPath); //绝对路径
validatecode.ChartType = GraphicType.Jpg; //图片类型
validatecode.ImageName = "ss.jpg"; //图片名称
validatecode.ChartWidth = 80; //图片宽度
validatecode.ChartHeight = 18; //图片高度
validatecode.GraphicImg(); //生成图片
this.ViewState["validatecode"] = validatecode.AuthenCode.ToString().Trim(); //获得验证码放到VIEWSTATE中用来验证,也可以放在session中
this.txt_validatecode.Attributes.Add("style","BACKGROUND-IMAGE: url("+ validatecode.TempImageURLPath + "/" + validatecode.ImageName +");width:80px;");
发现一个问题,如果照着红色代码写的话,后退时验证码不变,只有换种方式了,把前台的代码:
<asp:textbox id="txt_validatecode" Runat="server" CssClass="TextBox" style="width:60px" ReadOnly="True"></asp:textbox>
改成:

<IMG id=\'ValidImage\' align=\'absBottom\' border=\'0\' alt="请按图片上的字母输入验证码src=\'checknum.jsp\'"><SCRIPT>
document.Form1.ValidImage.src=\'temp/ss.jpg?\'+Math.random()</SCRIPT>
这样就可以了,不过你的图片名字也就固定死了,不过没关系,每次生成图片时会把相同的图片删掉的
第四步:
通过ValidateCode的属性AuthenCode可以获得具体的验证码,用于和用户录入做比较!
第五步:
当然还要建个文件夹用来存放图片。
两种方法都有了,想怎么用就怎么用,当然你也可以自己再添加些效果,比如现在里面就有个方法TwistImage()是用来产生正弦曲线Wave扭曲图片,不过还没用上。
图片,不用担心,代码会自动删除无用的图片!控件类:ValidateCode


using System;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.ComponentModel;
using System.IO;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Imaging;

namespace Freedom.FireGrass.WebControls


{

/**//// <summary>
/// ValidateCode 的摘要说明。
/// </summary>
public enum GraphicType

{
Jpg = 0,
Gif = 1,
Png = 2,
Bmp = 3,
}

//[ToolboxBitmap(@"D:\DotnetApp\ValidateCode\ValidateCode.bmp") ] //设置控件在工具箱上的图标
public class ValidateCode : System.Web.UI.WebControls.WebControl ,INamingContainer

{
private int pCodelen=5;
private int pChartWidth=13*5+5;
private int pChartHeight=25;
private string strRandName="validate.jpg";

private GraphicType pChartType;
private string pAuthenCode;

private string pTempImageURLPath="/WebApp/temp"; //当作控件用时使用虚拟路径
private string pTempImagePath=""; //当作方法来用时使用绝对路径
private string pAuthenImageFullname;
private string pAuthenImageFullURL;
//生成校验码的变量 start
private Bitmap validateImage;
private Graphics g;
//生成校验码的变量 End

private TextBox txt=new TextBox();
private System.Web.UI.WebControls.Image img= new System.Web.UI.WebControls.Image();


定义控件事件#region 定义控件事件
public delegate void GraphicCreated(object sender, EventArgs e);
public event EventHandler GraphicOK; //在校验图片生成结束以后触发

protected virtual void OnGraphicOK(object sender, EventArgs e)

{
if (GraphicOK != null)

{
//Invokes the delegates.
GraphicOK(sender, e);
}
}
#endregion

控件属性#region 控件属性
//生成校验码的长度
[Bindable(true),Browsable(true),Category("Appearance"),DefaultValue(true),Description("需要验证码的长度,建议在5~8位之间!")]
public int CodeLength

{
get

{
return pCodelen;
}

set

{
pCodelen = value;
}
}

//生成校验码图片的路径
[Bindable(true),Browsable(true),Category("Appearance"),DefaultValue(true),Description("当作控件使用时生成验证码图片的临时存放路径,要求必须是网站下的虚拟目录!")]
public string TempImageURLPath

{
get

{
return pTempImageURLPath;
}

set

{
pTempImageURLPath = value;
}
}

//生成校验码图片的路径
[Bindable(true),Browsable(true),Category("Appearance"),DefaultValue(true),Description("(非控件时使用)生成验证码图片的临时存放路径,要求必须是绝对路径!")]
public string TempImagePath

{
get

{
return pTempImagePath;
}

set

{
pTempImagePath = value;
}
}

//生成校验码图片的类型
[Bindable(true),Browsable(true),Category("Appearance"),DefaultValue(GraphicType.Jpg),Description("选择生成校验图文件的类型(Jpg;Gif;Png;Bmp)!")]
public GraphicType ChartType

{
get

{
return pChartType;
}

set

{
pChartType = value;
}
}


//生成校验码图片的宽度
public int ChartWidth

{
get

{
return pChartWidth;
}

set

{
pChartWidth = value;
}
}

//生成校验码图片的高度
public int ChartHeight

{
get

{
return pChartHeight;
}

set

{
pChartHeight = value;
}
}

//生成校验码图片的名称
public string ImageName

{
get

{
return strRandName;
}

set

{
strRandName = value;
}
}

//需要生成的校验码
public string AuthenCode

{
get

{
return pAuthenCode;
}

set

{
pAuthenCode = value;
}
}

#endregion


/**//// <summary>
/// 只生成图片
/// </summary>
public void GraphicImg()

{
if(pAuthenCode==null)
pAuthenCode=GetValidateCode();
//生成图片的全名,和全URL
MakeFileName();
GetRandomImage(pAuthenCode);
}


/**//// <summary>
/// 将此控件呈现给指定的输出参数。
/// </summary>
/// <param name="output"> 要写出到的 HTML 编写器 </param>
protected override void Render(HtmlTextWriter output)

{
System.Web.UI.WebControls.Image objImage;
//TextBox objTxt;
//绘制包含的控件
objImage = (System.Web.UI.WebControls.Image) Controls[0];
//objTxt = (TextBox) Controls[1];
if(pAuthenCode==null)
pAuthenCode=GetValidateCode();
OnGraphicOK(this,EventArgs.Empty );
//生成图片的全名,和全URL
MakeRandomFileName();

GetRandomImage(pAuthenCode);
objImage.ImageUrl=pAuthenImageFullURL;

objImage.RenderControl(output);
}


/**//// <summary>
/// 给控件添加子控件
/// </summary>
protected override void CreateChildControls( )

{
//Controls.Add(btn);
Controls.Add(img);
//Controls.Add(txt);
}


/**//// <summary>
/// 控件Load时候属性的初始化
/// </summary>
/// <param name="e"></param>
protected override void OnLoad(System.EventArgs e)

{
}


/**//// <summary>
/// 当作控件使用时生成图片名
/// </summary>
private void MakeRandomFileName()

{
//string strRandName=DateTime.Now.Ticks.ToString()+".jpg";
//string strRandName="validate.jpg";
TempImagePath=this.Page.MapPath(TempImageURLPath);
pAuthenImageFullname=TempImagePath+@"\"+strRandName;
pAuthenImageFullURL=TempImageURLPath+"/"+strRandName;
}


/**//// <summary>
/// 当作方法使用时生成图片名
/// </summary>
private void MakeFileName()

{
//string strRandName=DateTime.Now.Ticks.ToString()+".jpg";
//string strRandName="validate.jpg";
pAuthenImageFullname=TempImagePath+@"\"+strRandName;
pAuthenImageFullURL=TempImageURLPath+"/"+strRandName;
}


private void GetRandomImage(string strValidateCode)

{
//生成随即图片的全名,和全URL
//MakeRandomFileName();

EraseOldGraphic(); //删除过期的图片

validateImage = new Bitmap(pChartWidth, pChartHeight); // .Format24bppRgb);
//validateImage = new Bitmap(pChartWidth, pChartHeight, PixelFormat.Format24bppRgb); // .Format24bppRgb);
g = Graphics.FromImage(validateImage);
g.Clear(Color.LightGray) ;

//g.DrawString(strValidateCode , new Font("宋体",16,FontStyle.Bold),new SolidBrush(Color.DarkRed),new PointF(2,2));

// 1. 生成随机背景颜色
int nRed,nGreen,nBlue; // 背景的三元色
System.Random rd = new Random((int)System.DateTime.Now.Ticks);
nRed = rd.Next(255)%128+128;
nGreen = rd.Next(255)%128+128;
nBlue = rd.Next(255)%128+128;

// 2. 填充位图背景
g.FillRectangle(new SolidBrush(System.Drawing.Color.FromArgb(nRed,nGreen,nBlue))
,0
,0
,pChartWidth
,pChartHeight);


// 3. 绘制干扰线条,采用比背景略深一些的颜色
int nLines = 3;
System.Drawing.Pen pen = new System.Drawing.Pen(System.Drawing.Color.FromArgb(nRed-17,nGreen-17,nBlue-17),2);
for(int a =0;a<nLines;a++)

{
int x1 = rd.Next() % pChartWidth;
int y1 = rd.Next() % pChartHeight;
int x2 = rd.Next() % pChartWidth;
int y2 = rd.Next() % pChartHeight;
g.DrawLine(pen,x1,y1,x2,y2);
}

for(int i=0;i<strValidateCode.Length;i++)

{
Random r = new Random();
int x = (i*13 + r.Next(3));
int y = r.Next(2);

// 确定字体
System.Drawing.Font font = new System.Drawing.Font("Courier New",
12 + r.Next()%3,
System.Drawing.FontStyle.Bold);

PointF startPos=new PointF(x,y );
//PointF startPos=new PointF(r.Next(3,6)+(r.Next(12,14)*i ),r.Next(-1,2) );
g.DrawString(strValidateCode.Substring(i,1) , font, new SolidBrush(System.Drawing.Color.FromArgb(nRed-60+y*3,nGreen-60+y*3,nBlue-40+y*3)),startPos);
//g.DrawString(strValidateCode.Substring(i,1) , new Font("宋体",11,FontStyle.Italic),new SolidBrush(Color.Blue),startPos);
}

//g.FillRectangle(new LinearGradientBrush(new Point(0,0), new Point(120,30), Color.FromArgb(0,0,0,0),Color.FromArgb(255,255,255,255)),0,0,120,30);
switch(pChartType)

{
case GraphicType.Jpg:
EraseSameGraphic();
validateImage.Save(pAuthenImageFullname, ImageFormat.Jpeg);
break;
case GraphicType.Gif:
EraseSameGraphic();
validateImage.Save(pAuthenImageFullname, ImageFormat.Gif);
break;

case GraphicType.Png:
EraseSameGraphic();
validateImage.Save(pAuthenImageFullname, ImageFormat.Png);
break;
case GraphicType.Bmp:
EraseSameGraphic();
validateImage.Save(pAuthenImageFullname, ImageFormat.Bmp);
break;
default:
EraseSameGraphic();
validateImage.Save(pAuthenImageFullname, ImageFormat.Jpeg);
break;
}
validateImage.Dispose();

g.Dispose();
}


/**//// <summary>
/// 动态从数字和字母组成的元素中动态选择生成校验码
/// </summary>
private string GetValidateCode()

{

char[] s = new char[]
{\'0\',\'1\',\'2\',\'3\',\'4\',\'5\',\'6\',\'7\',\'8\',\'9\',\'a\',\'b\',\'c\',\'d\',\'e\',\'f\',\'g\',\'h\',\'i\',\'j\',\'k\',\'l\',\'m\',\'n\',\'o\',\'p\',\'q\',\'r\',\'s\',\'t\',\'u\',\'v\',\'w\',\'x\',\'y\',\'z\',\'A\',\'B\',\'C\',\'D\',\'E\',\'F\',\'G\',\'H\',\'I\',\'J\',\'K\',\'L\',\'M\',\'N\',\'O\',\'P\',\'Q\',\'R\',\'S\',\'T\',\'U\',\'V\',\'W\',\'X\',\'Y\',\'Z\'};
string num = "";
Random r = new Random();

//根据用户需要的长度来定义验证码的位数
for(int i = 0; i < CodeLength; i++)

{
num += s[r.Next(0, s.Length)].ToString();
}
return num;
}

private const double PI = 3.1415926535897932384626433832795;
private const double PI2 = 6.283185307179586476925286766559;


/**//// <summary>
/// 正弦曲线Wave扭曲图片
/// </summary>
/// <param name="srcBmp"></param>
/// <param name="bXDir"></param>
/// <param name="nMultValue">波形的幅度倍数</param>
/// <param name="dPhase">波形的起始相位,取值区间[0-2*PI)</param>
/// <returns></returns>
public System.Drawing.Bitmap TwistImage(Bitmap srcBmp,bool bXDir,double dMultValue,double dPhase)

{
System.Drawing.Bitmap destBmp = new Bitmap(srcBmp.Width,srcBmp.Height);

// 将位图背景填充为白色
System.Drawing.Graphics graph = System.Drawing.Graphics.FromImage(destBmp);
graph.FillRectangle(new SolidBrush(System.Drawing.Color.White),0,0,destBmp.Width,destBmp.Height);
graph.Dispose();
double dBaseAxisLen = bXDir ? (double)destBmp.Height : (double)destBmp.Width;

for(int i=0;i<destBmp.Width;i++)

{
for(int j=0;j<destBmp.Height;j++)

{
double dx = 0;
dx = bXDir ? (PI2*(double)j)/dBaseAxisLen : (PI2*(double)i)/dBaseAxisLen;
dx += dPhase;
double dy = Math.Sin(dx);

// 取得当前点的颜色
int nOldX = 0,nOldY = 0;
nOldX = bXDir ? i + (int)(dy*dMultValue) : i;
nOldY = bXDir ? j : j + (int)(dy*dMultValue);

System.Drawing.Color color = srcBmp.GetPixel(i,j);
if(nOldX >= 0 && nOldX < destBmp.Width
&& nOldY >=0 && nOldY < destBmp.Height)

{
destBmp.SetPixel(nOldX,nOldY,color);
}
}
}

return destBmp;
}


/**//// <summary>
/// 清除时间超过20秒的临时图片记录
/// </summary>
/// <returns>成功返回true,失败返回false</returns>
public bool EraseOldGraphic()

{

try

{
DirectoryInfo Dinfo=new DirectoryInfo(TempImagePath);
FileInfo[] FileSet;
if(Dinfo.Exists)

{
switch(pChartType)

{
case GraphicType.Jpg:
FileSet=Dinfo.GetFiles("*.jpg");
break;
case GraphicType.Gif:

FileSet=Dinfo.GetFiles("*.gif");
break;

case GraphicType.Png:

FileSet=Dinfo.GetFiles("*.png");
break;
case GraphicType.Bmp:

FileSet=Dinfo.GetFiles("*.bmp");
break;
default:
FileSet=Dinfo.GetFiles("*.jpg");
break;
}

foreach(FileInfo fileInfo in FileSet)

{
if(fileInfo.Exists)

{
DateTime dts=DateTime.Now;
DateTime dtc=fileInfo.CreationTime;

TimeSpan ts=dts-dtc;
if(ts.Seconds>20)

{
fileInfo.Delete();
}
}
}
}

return true;
}
catch(IOException ioe)

{
return false;
}
}


/**//// <summary>
/// 清除同名的临时图片记录
/// </summary>
/// <returns>成功返回true,失败返回false</returns>
public bool EraseSameGraphic()

{

try

{
DirectoryInfo Dinfo=new DirectoryInfo(TempImagePath);
FileInfo[] FileSet;
if(Dinfo.Exists)

{
switch(pChartType)

{
case GraphicType.Jpg:
FileSet=Dinfo.GetFiles(strRandName);
break;
case GraphicType.Gif:

FileSet=Dinfo.GetFiles(strRandName);
break;

case GraphicType.Png:

FileSet=Dinfo.GetFiles(strRandName);
break;
case GraphicType.Bmp:

FileSet=Dinfo.GetFiles(strRandName);
break;
default:
FileSet=Dinfo.GetFiles(strRandName);
break;
}

foreach(FileInfo fileInfo in FileSet)

{
if(fileInfo.Exists)

{
fileInfo.Delete();
}
}
}

return true;
}
catch(IOException ioe)

{
return false;
}
}
}
}
如果觉得可以的话,就多多支持啊!:)