再论安全验证码 - 实现数字、字母、中文混淆验证
这几天博客都被垃圾评论困扰着,于是就有了一个写一个验证码的想法。这个验证码主要是增加机器识别的难度,当前网上各种流行的验证码中,感觉动网的验证码比较优秀,比较不容易被机器识别。这个验证码方法能够自动生成中文、数字、字母的混合字符串,并且自动设置有效的验证码值。上图中的有效验证码值为“mejjh”,而图片全文为“mej的jh”,这样就可以有效地防止被机器识别出验证码了。我把动网里的验证码代码剥离出来,并作了一些易用性修改。
这几天博客都被垃圾评论困扰着,于是就有了一个写一个验证码的想法。这个验证码主要是增加机器识别的难度,当前网上各种流行的验证码中,感觉动网的验证码比较优秀,比较不容易被机器识别。
从动网官网下载了动网.net 1.1版本,用Reflector反编译它的源代码。
请先看动网验证码的截图:
系统自动生成中文、数字、字母的混合字符串,并且自动设置有效的验证码值。上图中的有效验证码值为“mejjh”,而图片全文为“mej的jh”,这样就可以有效地防止被机器识别出验证码了。
我把动网里的验证码代码剥离出来,并作了一些修改。
在动网源代码中,它生成的验证码参数设置是读取Request.QueryString值的,这里我们不再使用这种方式设置验证码,改用xml文件保存设置。
XML配置
<?xml version="1.0" encoding="utf-8" ?>
<config>
<!--背景色-->
<bgcolor value="LightBlue"/>
<!--粗体-->
<bold value="true" />
<!--前景色-->
<forecolor value="Blue" />
<!--字体-->
<fontfamily value="Arial, Helvetica, sans-serif,宋体" />
<!--字体大小-->
<fontsize value="20" />
<!--图片高度-->
<height value="70" />
<!--杂质-->
<impurity value="2" />
<!--斜体-->
<italic value="false" />
<!--图片宽度-->
<width value="180" />
<!--验证码字符个数-->
<number value="6" />
<!--可用的验证码值-->
<codetext>
<![CDATA[我人有的和主产不为这工要在地一上是中经以发了民同国木子123456789abcdefghijkmnpqrstuvwxyzABCDEFGHJKLMNPQRSTUVWXYZ]]>
</codetext>
</config>
<?xml version="1.0" encoding="utf-8" ?>
<config>
<!--背景色-->
<bgcolor value="LightBlue"/>
<!--粗体-->
<bold value="true" />
<!--前景色-->
<forecolor value="Blue" />
<!--字体-->
<fontfamily value="Arial, Helvetica, sans-serif,宋体" />
<!--字体大小-->
<fontsize value="20" />
<!--图片高度-->
<height value="70" />
<!--杂质-->
<impurity value="2" />
<!--斜体-->
<italic value="false" />
<!--图片宽度-->
<width value="180" />
<!--验证码字符个数-->
<number value="6" />
<!--可用的验证码值-->
<codetext>
<![CDATA[我人有的和主产不为这工要在地一上是中经以发了民同国木子123456789abcdefghijkmnpqrstuvwxyzABCDEFGHJKLMNPQRSTUVWXYZ]]>
</codetext>
</config>
再把xml文件的配置信息映射到一个类上:
XML配置类
/**//// <summary>
/// 验证码配置文件
/// </summary>
public class ValidateCodeConfig
{
属性#region 属性
private Color bgcolor;
/**//// <summary>
/// 背景色
/// </summary>
public Color BgColor
{
get { return bgcolor; }
set { bgcolor = value; }
}
private bool bold;
/**//// <summary>
/// 是否粗体
/// </summary>
public bool Bold
{
get { return bold; }
set { bold = value; }
}
private Color forecolor;
/**//// <summary>
/// 颜色
/// </summary>
public Color ForeColor
{
get { return forecolor; }
set { forecolor = value; }
}
private string fontFamily;
/**//// <summary>
/// 字体
/// </summary>
public string FontFamily
{
get { return fontFamily; }
set { fontFamily = value; }
}
private int fontSize;
/**//// <summary>
/// 字体大小
/// </summary>
public int FontSize
{
get { return fontSize; }
set { fontSize = value; }
}
private int height;
/**//// <summary>
/// 高度
/// </summary>
public int Height
{
get { return height; }
set
{
if (300 < value)
height = 300;
else
height = value;
}
}
private int impurity;
/**//// <summary>
/// 杂质
/// </summary>
public int Impurity
{
get { return impurity; }
set
{
if (30 < value)
impurity = 30;
else
impurity = value;
}
}
private bool italic;
/**//// <summary>
/// 斜体
/// </summary>
public bool Italic
{
get { return italic; }
set { italic = value; }
}
private int width;
/**//// <summary>
/// 宽度
/// </summary>
public int Width
{
get { return width; }
set
{
if (300 < value)
width = 300;
else
width = value;
}
}
private char[] codetext;
/**//// <summary>
/// 验证码字符
/// </summary>
public char[] CodeText
{
get { return codetext; }
set { codetext = value; }
}
private int number;
/**//// <summary>
/// 验证码字数
/// </summary>
public int Number
{
get { return number; }
set { number = value; }
}
#endregion
/**//// <summary>
/// 构造函数
/// </summary>
public ValidateCodeConfig()
{
LoadXMLOnInit();
}
/**//// <summary>
/// 加载config.xml配置
/// </summary>
private void LoadXMLOnInit()
{
XmlDocument doc = new XmlDocument();
doc.Load(HttpContext.Current.Server.MapPath("~/ValidateCode/config.xml"));
this.bgcolor = Color.FromName(doc.GetElementsByTagName("bgcolor").Item(0).Attributes["value"].Value);
this.bold = Boolean.Parse(doc.GetElementsByTagName("bold").Item(0).Attributes["value"].Value);
this.codetext = doc.GetElementsByTagName("codetext").Item(0).InnerText.ToCharArray();
this.fontFamily = doc.GetElementsByTagName("fontfamily").Item(0).Attributes["value"].Value;
this.fontSize = int.Parse(doc.GetElementsByTagName("fontsize").Item(0).Attributes["value"].Value);
this.forecolor = Color.FromName(doc.GetElementsByTagName("forecolor").Item(0).Attributes["value"].Value);
this.height = int.Parse(doc.GetElementsByTagName("height").Item(0).Attributes["value"].Value);
this.impurity = int.Parse(doc.GetElementsByTagName("impurity").Item(0).Attributes["value"].Value);
this.italic = Boolean.Parse(doc.GetElementsByTagName("italic").Item(0).Attributes["value"].Value);
this.width = int.Parse(doc.GetElementsByTagName("width").Item(0).Attributes["value"].Value);
this.number = int.Parse(doc.GetElementsByTagName("number").Item(0).Attributes["value"].Value);
}
}
/**//// <summary>
/// 验证码配置文件
/// </summary>
public class ValidateCodeConfig
{
属性#region 属性
private Color bgcolor;
/**//// <summary>
/// 背景色
/// </summary>
public Color BgColor
{
get { return bgcolor; }
set { bgcolor = value; }
}
private bool bold;
/**//// <summary>
/// 是否粗体
/// </summary>
public bool Bold
{
get { return bold; }
set { bold = value; }
}
private Color forecolor;
/**//// <summary>
/// 颜色
/// </summary>
public Color ForeColor
{
get { return forecolor; }
set { forecolor = value; }
}
private string fontFamily;
/**//// <summary>
/// 字体
/// </summary>
public string FontFamily
{
get { return fontFamily; }
set { fontFamily = value; }
}
private int fontSize;
/**//// <summary>
/// 字体大小
/// </summary>
public int FontSize
{
get { return fontSize; }
set { fontSize = value; }
}
private int height;
/**//// <summary>
/// 高度
/// </summary>
public int Height
{
get { return height; }
set
{
if (300 < value)
height = 300;
else
height = value;
}
}
private int impurity;
/**//// <summary>
/// 杂质
/// </summary>
public int Impurity
{
get { return impurity; }
set
{
if (30 < value)
impurity = 30;
else
impurity = value;
}
}
private bool italic;
/**//// <summary>
/// 斜体
/// </summary>
public bool Italic
{
get { return italic; }
set { italic = value; }
}
private int width;
/**//// <summary>
/// 宽度
/// </summary>
public int Width
{
get { return width; }
set
{
if (300 < value)
width = 300;
else
width = value;
}
}
private char[] codetext;
/**//// <summary>
/// 验证码字符
/// </summary>
public char[] CodeText
{
get { return codetext; }
set { codetext = value; }
}
private int number;
/**//// <summary>
/// 验证码字数
/// </summary>
public int Number
{
get { return number; }
set { number = value; }
}
#endregion
/**//// <summary>
/// 构造函数
/// </summary>
public ValidateCodeConfig()
{
LoadXMLOnInit();
}
/**//// <summary>
/// 加载config.xml配置
/// </summary>
private void LoadXMLOnInit()
{
XmlDocument doc = new XmlDocument();
doc.Load(HttpContext.Current.Server.MapPath("~/ValidateCode/config.xml"));
this.bgcolor = Color.FromName(doc.GetElementsByTagName("bgcolor").Item(0).Attributes["value"].Value);
this.bold = Boolean.Parse(doc.GetElementsByTagName("bold").Item(0).Attributes["value"].Value);
this.codetext = doc.GetElementsByTagName("codetext").Item(0).InnerText.ToCharArray();
this.fontFamily = doc.GetElementsByTagName("fontfamily").Item(0).Attributes["value"].Value;
this.fontSize = int.Parse(doc.GetElementsByTagName("fontsize").Item(0).Attributes["value"].Value);
this.forecolor = Color.FromName(doc.GetElementsByTagName("forecolor").Item(0).Attributes["value"].Value);
this.height = int.Parse(doc.GetElementsByTagName("height").Item(0).Attributes["value"].Value);
this.impurity = int.Parse(doc.GetElementsByTagName("impurity").Item(0).Attributes["value"].Value);
this.italic = Boolean.Parse(doc.GetElementsByTagName("italic").Item(0).Attributes["value"].Value);
this.width = int.Parse(doc.GetElementsByTagName("width").Item(0).Attributes["value"].Value);
this.number = int.Parse(doc.GetElementsByTagName("number").Item(0).Attributes["value"].Value);
}
}
在绘图方法中调用这个类,并为其设置缓存依赖:
为配置文件设置缓存依赖
/**//// <summary>
/// 为配置文件设置缓存依赖
/// </summary>
private void LoadConfig()
{
if (HttpRuntime.Cache["ValidateCodeConfig"] == null)
{
config = new ValidateCodeConfig();
CacheDependency dep = new CacheDependency(HttpContext.Current.Server.MapPath("~/ValidateCode/config.xml"));
HttpRuntime.Cache.Insert("ValidateCodeConfig", config, dep, DateTime.MaxValue,
TimeSpan.Zero);
}
else
{
config = (ValidateCodeConfig)HttpRuntime.Cache["ValidateCodeConfig"];
}
}
/**//// <summary>
/// 为配置文件设置缓存依赖
/// </summary>
private void LoadConfig()
{
if (HttpRuntime.Cache["ValidateCodeConfig"] == null)
{
config = new ValidateCodeConfig();
CacheDependency dep = new CacheDependency(HttpContext.Current.Server.MapPath("~/ValidateCode/config.xml"));
HttpRuntime.Cache.Insert("ValidateCodeConfig", config, dep, DateTime.MaxValue,
TimeSpan.Zero);
}
else
{
config = (ValidateCodeConfig)HttpRuntime.Cache["ValidateCodeConfig"];
}
}
之后,我们就可以开始写生成验证码的主要方法了:
验证码主要方法
/**//// <summary>
/// 验证码字体样式
/// </summary>
/// <returns></returns>
private FontStyle GetFontStyle()
{
if (config.Bold && config.Italic)
{
return (FontStyle.Italic | FontStyle.Bold);
}
if (config.Bold)
{
return FontStyle.Bold;
}
if (config.Italic)
{
return FontStyle.Italic;
}
return FontStyle.Regular;
}
private Bitmap GetneralCodeImage()
{
bool flag3;
Random random = new Random();
Bitmap image = new Bitmap(config.Width, config.Height);
Graphics graphics = Graphics.FromImage(image);
graphics.Clear(config.BgColor);
int length = Directory.GetFiles(Server.MapPath("~/ValidateCode/"), "*.gif").Length;
int backgroundfile = random.Next(1, length);
Brush brush = new TextureBrush(new Bitmap(Server.MapPath("~/ValidateCode/" + backgroundfile.ToString() + ".gif")));
Rectangle rect = new Rectangle(0, 0, config.Width, config.Height);
graphics.FillRectangle(brush, rect);
string[] strColorArray = new string[]
{
"#666666", "#003300", "#009900", "#330000", "#333300",
"#336600", "#660000", "#663300", "#666600", "#FF99FF",
"#FF33FF", "#CCCCFF", "#CC66FF", "#CC00FF", "#9999FF",
"#9933FF", "#9900FF", "#FF00FF", "#996633", "#CC3333",
"#FF3333", "#6633FF", "#0033FF", "#336666", "#CC9900",
"#6633CC", "#66FF66", "#009999", "#99CC00", "#615379",
"#E6649E", "#B5B495", "#73CEA7"
};
bool istop = random.Next(0, 2) == 0;
Pen pen = new Pen(ColorTranslator.FromHtml(strColorArray[random.Next(0, strColorArray.Length)]), 2f);
pen.DashStyle = DashStyle.Solid;
Point[] randomPointGroup = this.GetRandomPointGroup(istop);
for (int i = 0; i < randomPointGroup.Length; i += 2)
{
graphics.DrawLine(pen, randomPointGroup[i], randomPointGroup[i + 1]);
}
string input = "";
for (int j = 0; j < config.Number; j++)
{
input += config.CodeText[random.Next(config.CodeText.Length)].ToString();
}
string[] strArray2 = new string[config.Number + 1];
int index = 0;
Label_0313:
while (index != config.Number)
{
string str2 = strColorArray[random.Next(0, strColorArray.Length)];
strArray2[index] = str2;
index++;
for (int n = 0; n < strArray2.Length; n++)
{
if (strArray2[n] == str2)
{
goto Label_0313;
}
if (n == (strArray2.Length - 1))
{
strArray2[index] = str2;
index++;
}
}
}
char[] chArray2 = input.ToCharArray();
int num8 = random.Next(0, config.Number - 1);
string str3 = strArray2[num8];
int num9 = random.Next(0, config.Number - 2) + 1;
num9 = (num9 == 1) ? 2 : num9;
int[] numArray = new int[num9];
numArray[0] = num8;
for (int k = 1; k < num9; k++)
{
int num11 = random.Next(0, config.Number - 1);
bool flag2 = false;
for (int num12 = 0; num12 < k; num12++)
{
if (numArray[num12] == num11)
{
flag2 = true;
break;
}
}
if (!flag2)
{
numArray[k] = num11;
}
else
{
k--;
}
}
do
{
string str4 = strColorArray[random.Next(0, strColorArray.Length)];
flag3 = false;
for (int num13 = 0; num13 < strArray2.Length; num13++)
{
if (str4 == strArray2[num13])
{
flag3 = true;
break;
}
}
}
while (flag3);
string strRegexString = "";
string strRegexValidateType = "";
int intValidateType = random.Next(0, 3);
bool flag4 = false;
while (!flag4)
{
Match matchChinese;
Match matchLetter;
Match matchNumber;
switch (intValidateType)
{
case 0:
if (!Regex.IsMatch(input, @"[\u4e00-\u9fa5]+"))
{
goto Label_RandomCodeType;
}
flag4 = true;
strRegexValidateType = "中文字体";
matchChinese = Regex.Match(input, @"[\u4e00-\u9fa5]+", RegexOptions.Multiline | RegexOptions.IgnoreCase);
goto Label_ChineseRegexResult;
case 1:
if (!Regex.IsMatch(input, "[a-zA-Z]+"))
{
goto Label_RandomCodeType;
}
flag4 = true;
strRegexValidateType = "英文字母";
matchLetter = Regex.Match(input, "[a-zA-Z]+", RegexOptions.Multiline | RegexOptions.IgnoreCase);
goto Label_LetterRegexResult;
case 2:
if (!Regex.IsMatch(input, "[0-9]+"))
{
goto Label_RandomCodeType;
}
flag4 = true;
strRegexValidateType = "数字";
matchNumber = Regex.Match(input, "[0-9]+", RegexOptions.Multiline | RegexOptions.IgnoreCase);
goto Label_NumberRegexResult;
case 3:
if (Regex.IsMatch(input, @"[^\u4e00-\u9fa5|a-zA-Z|0-9]"))
{
flag4 = true;
strRegexValidateType = "特殊字符";
strRegexString = new Regex(@"[\u4e00-\u9fa5|a-zA-Z|0-9]+").Replace(input, "");
}
goto Label_RandomCodeType;
default:
goto Label_RandomCodeType;
}
Label_ChineseRegexSuccess:
strRegexString = strRegexString + matchChinese.Value;
matchChinese = matchChinese.NextMatch();
Label_ChineseRegexResult:
if (matchChinese.Success)
{
goto Label_ChineseRegexSuccess;
}
goto Label_RandomCodeType;
Label_LetterRegexSuccess:
strRegexString = strRegexString + matchLetter.Value;
matchLetter = matchLetter.NextMatch();
Label_LetterRegexResult:
if (matchLetter.Success)
{
goto Label_LetterRegexSuccess;
}
goto Label_RandomCodeType;
Label_NumberRegexSuccess:
strRegexString = strRegexString + matchNumber.Value;
matchNumber = matchNumber.NextMatch();
Label_NumberRegexResult:
if (matchNumber.Success)
{
goto Label_NumberRegexSuccess;
}
Label_RandomCodeType:
if (!flag4)
{
intValidateType = random.Next(0, 3);
}
}
int num16 = 0;
for (int m = 0; m < chArray2.Length; m++)
{
int num21;
int num18 = config.FontSize;
int num19 = (m == 0) ? 10 : 25;
num16 += num19;
int num20 = num16;
if (istop)
{
num21 = random.Next(15, config.Height - 35);
}
else
{
num21 = random.Next(0, config.Height - 45);
}
bool flag5 = false;
if ((((('.' != chArray2[m]) && ('_' != chArray2[m])) && (('*' != chArray2[m]) && ('`' != chArray2[m]))) && ((('~' != chArray2[m]) && ('.' != chArray2[m])) && ((',' != chArray2[m]) && ('\'' != chArray2[m])))) && ((('-' != chArray2[m]) && ('|' != chArray2[m])) && ('\\' != chArray2[m])))
{
char ch1 = chArray2[m];
}
graphics.DrawString(chArray2[m].ToString(), new Font(config.FontFamily, flag5 ? ((float)(num18 + 30)) : ((float)num18), flag5 ? FontStyle.Bold : this.GetFontStyle()), new SolidBrush(ColorTranslator.FromHtml(strArray2[m])), (float)num20, (float)num21);
}
graphics.DrawString("输入图中出现的", new Font("Verdana", 10f, FontStyle.Regular), new SolidBrush(ColorTranslator.FromHtml("#008000")), (2 == intValidateType) ? ((float)18) : ((float)4), istop ? ((float)2) : ((float)(config.Height - 16)));
graphics.DrawString(strRegexValidateType, new Font("Verdana", 10f, FontStyle.Bold), new SolidBrush(ColorTranslator.FromHtml("#FF0000")), (2 == intValidateType) ? ((float)126) : ((float)110), istop ? ((float)2) : ((float)(config.Height - 16)));
graphics.Dispose();
Response.Cookies.Add(new HttpCookie("ValidateCode", strRegexString.ToLower()));
return image;
}
/**//// <summary>
/// 杂质
/// </summary>
/// <param name="istop"></param>
/// <returns></returns>
private Point[] GetRandomPointGroup(bool istop)
{
Point[] pointArray = new Point[config.Impurity * 2];
for (int i = 0; i < pointArray.Length; i++)
{
int num2 = new Random().Next(10000000, 99999999);
int x = new Random((num2 / (i + 2)) * (i + 1)).Next(0, config.Width);
int y = new Random((num2 / (x + 2)) * (x + 1)).Next(istop ? 16 : 0, istop ? config.Height : (config.Height - 16));
pointArray[i] = new Point(x, y);
}
return pointArray;
}
/**//// <summary>
/// 验证码字体样式
/// </summary>
/// <returns></returns>
private FontStyle GetFontStyle()
{
if (config.Bold && config.Italic)
{
return (FontStyle.Italic | FontStyle.Bold);
}
if (config.Bold)
{
return FontStyle.Bold;
}
if (config.Italic)
{
return FontStyle.Italic;
}
return FontStyle.Regular;
}
private Bitmap GetneralCodeImage()
{
bool flag3;
Random random = new Random();
Bitmap image = new Bitmap(config.Width, config.Height);
Graphics graphics = Graphics.FromImage(image);
graphics.Clear(config.BgColor);
int length = Directory.GetFiles(Server.MapPath("~/ValidateCode/"), "*.gif").Length;
int backgroundfile = random.Next(1, length);
Brush brush = new TextureBrush(new Bitmap(Server.MapPath("~/ValidateCode/" + backgroundfile.ToString() + ".gif")));
Rectangle rect = new Rectangle(0, 0, config.Width, config.Height);
graphics.FillRectangle(brush, rect);
string[] strColorArray = new string[]
{
"#666666", "#003300", "#009900", "#330000", "#333300",
"#336600", "#660000", "#663300", "#666600", "#FF99FF",
"#FF33FF", "#CCCCFF", "#CC66FF", "#CC00FF", "#9999FF",
"#9933FF", "#9900FF", "#FF00FF", "#996633", "#CC3333",
"#FF3333", "#6633FF", "#0033FF", "#336666", "#CC9900",
"#6633CC", "#66FF66", "#009999", "#99CC00", "#615379",
"#E6649E", "#B5B495", "#73CEA7"
};
bool istop = random.Next(0, 2) == 0;
Pen pen = new Pen(ColorTranslator.FromHtml(strColorArray[random.Next(0, strColorArray.Length)]), 2f);
pen.DashStyle = DashStyle.Solid;
Point[] randomPointGroup = this.GetRandomPointGroup(istop);
for (int i = 0; i < randomPointGroup.Length; i += 2)
{
graphics.DrawLine(pen, randomPointGroup[i], randomPointGroup[i + 1]);
}
string input = "";
for (int j = 0; j < config.Number; j++)
{
input += config.CodeText[random.Next(config.CodeText.Length)].ToString();
}
string[] strArray2 = new string[config.Number + 1];
int index = 0;
Label_0313:
while (index != config.Number)
{
string str2 = strColorArray[random.Next(0, strColorArray.Length)];
strArray2[index] = str2;
index++;
for (int n = 0; n < strArray2.Length; n++)
{
if (strArray2[n] == str2)
{
goto Label_0313;
}
if (n == (strArray2.Length - 1))
{
strArray2[index] = str2;
index++;
}
}
}
char[] chArray2 = input.ToCharArray();
int num8 = random.Next(0, config.Number - 1);
string str3 = strArray2[num8];
int num9 = random.Next(0, config.Number - 2) + 1;
num9 = (num9 == 1) ? 2 : num9;
int[] numArray = new int[num9];
numArray[0] = num8;
for (int k = 1; k < num9; k++)
{
int num11 = random.Next(0, config.Number - 1);
bool flag2 = false;
for (int num12 = 0; num12 < k; num12++)
{
if (numArray[num12] == num11)
{
flag2 = true;
break;
}
}
if (!flag2)
{
numArray[k] = num11;
}
else
{
k--;
}
}
do
{
string str4 = strColorArray[random.Next(0, strColorArray.Length)];
flag3 = false;
for (int num13 = 0; num13 < strArray2.Length; num13++)
{
if (str4 == strArray2[num13])
{
flag3 = true;
break;
}
}
}
while (flag3);
string strRegexString = "";
string strRegexValidateType = "";
int intValidateType = random.Next(0, 3);
bool flag4 = false;
while (!flag4)
{
Match matchChinese;
Match matchLetter;
Match matchNumber;
switch (intValidateType)
{
case 0:
if (!Regex.IsMatch(input, @"[\u4e00-\u9fa5]+"))
{
goto Label_RandomCodeType;
}
flag4 = true;
strRegexValidateType = "中文字体";
matchChinese = Regex.Match(input, @"[\u4e00-\u9fa5]+", RegexOptions.Multiline | RegexOptions.IgnoreCase);
goto Label_ChineseRegexResult;
case 1:
if (!Regex.IsMatch(input, "[a-zA-Z]+"))
{
goto Label_RandomCodeType;
}
flag4 = true;
strRegexValidateType = "英文字母";
matchLetter = Regex.Match(input, "[a-zA-Z]+", RegexOptions.Multiline | RegexOptions.IgnoreCase);
goto Label_LetterRegexResult;
case 2:
if (!Regex.IsMatch(input, "[0-9]+"))
{
goto Label_RandomCodeType;
}
flag4 = true;
strRegexValidateType = "数字";
matchNumber = Regex.Match(input, "[0-9]+", RegexOptions.Multiline | RegexOptions.IgnoreCase);
goto Label_NumberRegexResult;
case 3:
if (Regex.IsMatch(input, @"[^\u4e00-\u9fa5|a-zA-Z|0-9]"))
{
flag4 = true;
strRegexValidateType = "特殊字符";
strRegexString = new Regex(@"[\u4e00-\u9fa5|a-zA-Z|0-9]+").Replace(input, "");
}
goto Label_RandomCodeType;
default:
goto Label_RandomCodeType;
}
Label_ChineseRegexSuccess:
strRegexString = strRegexString + matchChinese.Value;
matchChinese = matchChinese.NextMatch();
Label_ChineseRegexResult:
if (matchChinese.Success)
{
goto Label_ChineseRegexSuccess;
}
goto Label_RandomCodeType;
Label_LetterRegexSuccess:
strRegexString = strRegexString + matchLetter.Value;
matchLetter = matchLetter.NextMatch();
Label_LetterRegexResult:
if (matchLetter.Success)
{
goto Label_LetterRegexSuccess;
}
goto Label_RandomCodeType;
Label_NumberRegexSuccess:
strRegexString = strRegexString + matchNumber.Value;
matchNumber = matchNumber.NextMatch();
Label_NumberRegexResult:
if (matchNumber.Success)
{
goto Label_NumberRegexSuccess;
}
Label_RandomCodeType:
if (!flag4)
{
intValidateType = random.Next(0, 3);
}
}
int num16 = 0;
for (int m = 0; m < chArray2.Length; m++)
{
int num21;
int num18 = config.FontSize;
int num19 = (m == 0) ? 10 : 25;
num16 += num19;
int num20 = num16;
if (istop)
{
num21 = random.Next(15, config.Height - 35);
}
else
{
num21 = random.Next(0, config.Height - 45);
}
bool flag5 = false;
if ((((('.' != chArray2[m]) && ('_' != chArray2[m])) && (('*' != chArray2[m]) && ('`' != chArray2[m]))) && ((('~' != chArray2[m]) && ('.' != chArray2[m])) && ((',' != chArray2[m]) && ('\'' != chArray2[m])))) && ((('-' != chArray2[m]) && ('|' != chArray2[m])) && ('\\' != chArray2[m])))
{
char ch1 = chArray2[m];
}
graphics.DrawString(chArray2[m].ToString(), new Font(config.FontFamily, flag5 ? ((float)(num18 + 30)) : ((float)num18), flag5 ? FontStyle.Bold : this.GetFontStyle()), new SolidBrush(ColorTranslator.FromHtml(strArray2[m])), (float)num20, (float)num21);
}
graphics.DrawString("输入图中出现的", new Font("Verdana", 10f, FontStyle.Regular), new SolidBrush(ColorTranslator.FromHtml("#008000")), (2 == intValidateType) ? ((float)18) : ((float)4), istop ? ((float)2) : ((float)(config.Height - 16)));
graphics.DrawString(strRegexValidateType, new Font("Verdana", 10f, FontStyle.Bold), new SolidBrush(ColorTranslator.FromHtml("#FF0000")), (2 == intValidateType) ? ((float)126) : ((float)110), istop ? ((float)2) : ((float)(config.Height - 16)));
graphics.Dispose();
Response.Cookies.Add(new HttpCookie("ValidateCode", strRegexString.ToLower()));
return image;
}
/**//// <summary>
/// 杂质
/// </summary>
/// <param name="istop"></param>
/// <returns></returns>
private Point[] GetRandomPointGroup(bool istop)
{
Point[] pointArray = new Point[config.Impurity * 2];
for (int i = 0; i < pointArray.Length; i++)
{
int num2 = new Random().Next(10000000, 99999999);
int x = new Random((num2 / (i + 2)) * (i + 1)).Next(0, config.Width);
int y = new Random((num2 / (x + 2)) * (x + 1)).Next(istop ? 16 : 0, istop ? config.Height : (config.Height - 16));
pointArray[i] = new Point(x, y);
}
return pointArray;
}
最后,在Page_Load中调用上面的方法:
private void Page_Load(object sender, EventArgs e)
{
this.LoadConfig();
base.Response.ContentType = "image/gif";
this.GetneralCodeImage().Save(base.Response.OutputStream, ImageFormat.Gif);
}
{
this.LoadConfig();
base.Response.ContentType = "image/gif";
this.GetneralCodeImage().Save(base.Response.OutputStream, ImageFormat.Gif);
}
演示效果如图:
DEMO源码下载:http://www.box.net/shared/g324d08ivy