本例演示使用VBScript对简单规则的图形验证码进行识别,先对图片进行二值化处理,此时图片成为了一张黑白图,然后对图片背景去噪,去除干扰像素,再对字符进行分离,最后把分离出的每个字符和标准字典进行对比,找出差异最小的,识别成功。
原始图片:
处理后的图片:
二值化后:
去噪后:
分离后:
运行效果:
'***************************************************************
'Written by D.L.
'***************************************************************
Option Explicit
'验证码图片本地磁盘保存名称
Const FILENAME_SAVE = "captcha.png"
Const FILENAME_SAVE2 = "captcha2.png"
'二值化时RGB阈值
Const g_R = &H80
Const g_G = &H80
Const g_B = &H80
Dim Standard '标准字符特征字典
Dim Width, Height '图像宽高
Dim Vector '图像的ARGB数据
Dim label '和Vector对应的标记
Dim nTimes '递归调用次数
Dim Ar '连通域面积
'根据网上查找的色彩心理学公式:
'$colorLevel = $r * 0.299 + $g * 0.587 + $b * 0.114;
'所以我们可以通过$grayLevel来判断此颜色的深浅,$grayLevel的值越小,则颜色越深。
Function colorLevel(r, g, b)
colorLevel = r * 0.299 + g * 0.587 + b * 0.114
End Function
'根据像素color得到ARGB分量
Function getARGB(ByVal color, ByRef a, ByRef r, ByRef g, ByRef b)
a = CByte(((color And &HFF000000) / 2 ^ (8 * 3)) And &HFF)
r = CByte((color And &HFF0000) / 2 ^ (8 * 2))
g = CByte(((color And &HFF00) / 2 ^ (8 * 1)) And &HFF)
b = CByte((color And &HFF) / 2 ^ (8 * 0))
End Function
'根据矩形坐标得到v中矩形区域的标记序列
Function getMarkSequenceFromRect(v, x1, y1, x2, y2)
Dim i, j
Dim strSeq: strSeq = ""
For j = y1 To y2
For i = x1 To x2
If (v((j - 1) * Width + i) = &HFF000000) Then
strSeq = strSeq & "■"
Else
strSeq = strSeq & "□"
End If
Next
strSeq = strSeq & vbNewLine
Next
getMarkSequenceFromRect = strSeq
End Function
'得到v的标记序列
Function getMarkSequence(v)
Dim i, j
Dim strSeq: strSeq = ""
For j = 1 To Height
For i = 1 To Width
If v((j - 1) * Width + i) = &HFF000000 Then
strSeq = strSeq & "■"
Else
strSeq = strSeq & "□"
End If
Next
strSeq = strSeq & vbNewLine
Next
getMarkSequence = strSeq
End Function
'二值化
Function binaryzation(v)
Dim i, j
Dim r, g, b, a
For i = 1 To Width
For j = i To v.Count Step Width
Call getARGB(v(j), a, r, g, b)
'Debug.Print r, g, b, a
'If colorLevel(r, g, b) < colorLevel(&H80, &H80, &H80) Then
If r < g_R And g < g_G And b < g_B Then
Vector(j) = &HFF000000
Else
Vector(j) = &HFFFFFFFF
End If
Next
Next
End Function
'参考:
'————————————————
'网页验证码识别实例VB.NET2019(二)_mengxiangde的博客-CSDN博客
'版权声明:本文为CSDN博主「mengxiangde」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
'原文链接:https://blog.csdn.net/mengxiangde/article/details/102980244
'
'八邻域去噪
Function denoise8Neighbours(v, number)
Dim x, y
Dim ix, iy
Dim c
'将边框标记为背景
' For X = 1 To Width '上下边取白色
' v(X)=&HFFFFFFFF
' v((Height-1)*Width+X)=&HFFFFFFFF
' Next
' For Y = 1 To Height'左右边取白色
' v((Y-1)*Width+1)=&HFFFFFFFF
' v((Y-1)*Width+Width)=&HFFFFFFFF
' Next
'逐点检测,判断某前景元素相邻的八个元素的颜色
For y = 1 To Height
For x = 1 To Width
c = 0
If v((y - 1) * Width + x) = &HFF000000 Then '黑点
'计算八邻域
For ix = x - 1 To x + 1
For iy = y - 1 To y + 1
If (ix >= 0 And ix <= Width - 1) And (iy >= 0 And iy <= Height - 1) Then
If ix = x And iy = y Then '自己
Else '左上、左、左下、上、下、右上、右、右下
If v((iy - 1) * Width + ix) = &HFF000000 Then c = c + 1 '发现黑点则计数+1
End If
End If
Next