|
全てのウィンドウとコントロールの情報を表示するサンプル(VB.NET)

|
<このサンプルの概要>
全てのウィンドウとコントロールの情報を表示するサンプルソースを作ってみました。
VB.NETのフォームにTreeViewを1つ追加してお試しください。
ステータスバー(msctls_statusbar32)の各パートの文字列を取得する関数はVB6版を参照ください。
VB6版はこちらです。
全てのウィンドウとコントロールの情報を表示するサンプル(VB6)
本サンプルのキーワードは以下のAPIです。
(1)EnumWindows
(2)EnumChildWindows
(3)GetClassName
(4)SendMessage
★標準モジュール(Module1.vb)
Module Module1
' APIの定義
Private Const WM_GETTEXT = &HD
Private Delegate Function D_EnumWindowsProc(ByVal hWnd As Integer, ByVal lParam As Integer) As Integer
Private Delegate Function D_EnumChildWindowsProc(ByVal hWnd As Integer, ByVal lParam As Integer) As Integer
Private Declare Function EnumWindows Lib "user32.dll" (ByVal lpEnumFunc As D_EnumWindowsProc, ByVal lParam As Integer) As Integer
Private Declare Function EnumChildWindows Lib "user32.dll" (ByVal hwndParent As Integer, ByVal lpEnumFunc As D_EnumChildWindowsProc, ByVal lParam As Integer) As Integer
Private Declare Function GetClassName Lib "user32.dll" Alias "GetClassNameA" (ByVal hWnd As Integer, ByVal lpClassName As Byte(), ByVal nMaxCount As Integer) As Integer
Private Declare Function SendMessage Lib "user32.dll" Alias "SendMessageA" (ByVal hWnd As Integer, ByVal wMsg As Integer, ByVal wParam As Integer, ByVal lParam As Byte()) As Integer
' コントロール毎の情報を設定するコレクション
Private colWindows As New Collection
' ウィンドウとコントロールを全て取得
Public Function GetAllWindows() As Collection
On Error Resume Next
Dim i As Long
Dim lngRet As Long
' コントロール毎の情報を設定するコレクション生成
colWindows = New Collection
GetAllWindows = colWindows
' トップレベルウィンドウを全て取得
lngRet = EnumWindows(AddressOf EnumWindowsProc, 0)
' 親ウィンドウに属するコントロールを全て取得
For i = 1 To colWindows.Count
lngRet = EnumChildWindows(colWindows.Item(i).Item(1)(0), AddressOf EnumChildWindowsProc, i)
Next i
End Function
' トップレベルウィンドウを全て取得
Public Function EnumWindowsProc(ByVal hWnd As Integer, ByVal lParam As Integer) As Integer
On Error Resume Next
Dim lngRet As Long
Dim bytClass As Byte() = New Byte(255) {}
Dim bytTitle As Byte() = New Byte(255) {}
Dim strClass As String
Dim strTitle As String
' クラス名取得
lngRet = GetClassName(hWnd, bytClass, 255)
strClass = StripNulls(bytClass)
' ウィンドウのタイトル取得
lngRet = SendMessage(hWnd, WM_GETTEXT, 255, bytTitle)
strTitle = StripNulls(bytTitle)
' 取得した情報を配列に設定
Dim strDa(2) As Object
strDa(0) = hWnd
strDa(1) = strClass
strDa(2) = strTitle
' 取得した情報をコレクションに設定
Dim colDa As New Collection
colDa.Add(strDa)
' トップレベルウィンドウ毎のコレクションに追加
colWindows.Add(colDa)
' リターン
EnumWindowsProc = 1
End Function
' 指定された親ウィンドウに属するコントロールを全て取得
Private Function EnumChildWindowsProc(ByVal hWnd As Integer, ByVal lParam As Integer) As Integer
On Error Resume Next
Dim lngRet As Long
Dim bytClass As Byte() = New Byte(255) {}
Dim bytTitle As Byte() = New Byte(255) {}
Dim strClass As String
Dim strTitle As String
' クラス名取得
lngRet = GetClassName(hWnd, bytClass, 255)
strClass = StripNulls(bytClass)
' ウィンドウのタイトル取得
lngRet = SendMessage(hWnd, WM_GETTEXT, 255, bytTitle)
strTitle = StripNulls(bytTitle)
' 取得した情報を配列に設定
Dim strDa(2) As Object
strDa(0) = hWnd
strDa(1) = strClass
strDa(2) = strTitle
' コントロール毎のコレクションに追加
colWindows.Item(lParam).Add(strDa)
' リターン
EnumChildWindowsProc = 1
End Function
' 文字列からNULL文字以降をカット
Private Function StripNulls(ByVal bytOrg As Byte()) As String
On Error Resume Next
Dim strOrg As String = System.Text.Encoding.GetEncoding("SHIFT-JIS").GetString(bytOrg)
If (InStr(strOrg, Chr(0)) > 0) Then
strOrg = Left(strOrg, InStr(strOrg, Chr(0)) - 1)
End If
StripNulls = strOrg
End Function
End Module
★フォームモジュール(Form1.vb)
Public Class Form1
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
Dim i As Long
Dim j As Long
Dim bytClass As Byte()
Dim bytTitle As Byte()
Dim bytSpace As Byte()
' ウィンドウとコントロールの全ての情報を取得
Dim colWindows As Collection
colWindows = GetAllWindows()
' 親ウィンドウ毎のコレクションループ
For i = 1 To colWindows.Count
' 子コントロール毎のコレクション取得
Dim colChilds As Collection
colChilds = colWindows.Item(i)
'If colChilds.Count >= 1 Then ' 全ての親ウィンドウを対象
If colChilds.Count > 1 Then ' 子コントロールを持つ物のみ対象
' 子コントロール毎のコレクションループ
Dim treeNodeTop As TreeNode = Nothing
For j = 1 To colChilds.Count
bytSpace = System.Text.Encoding.GetEncoding("SHIFT-JIS").GetBytes(New String(" ", 50))
' コレクションからクラス名取得
bytClass = System.Text.Encoding.GetEncoding("SHIFT-JIS").GetBytes(colChilds.Item(j)(1))
If bytClass.Length < 30 Then
Dim p As Integer = bytClass.Length
ReDim Preserve bytClass(bytClass.Length + bytSpace.Length - 1)
Array.Copy(bytSpace, 0, bytClass, p, bytSpace.Length)
ReDim Preserve bytClass(30 - 1)
End If
Dim strClass As String = System.Text.Encoding.GetEncoding("SHIFT-JIS").GetString(bytClass)
' コレクションから文字列取得
bytTitle = System.Text.Encoding.GetEncoding("SHIFT-JIS").GetBytes(colChilds.Item(j)(2))
If bytTitle.Length < 50 Then
Dim p As Integer = bytTitle.Length
ReDim Preserve bytTitle(bytTitle.Length + bytSpace.Length - 1)
Array.Copy(bytSpace, 0, bytTitle, p, bytSpace.Length)
ReDim Preserve bytTitle(50 - 1)
End If
Dim strTitle As String = System.Text.Encoding.GetEncoding("SHIFT-JIS").GetString(bytTitle)
If j = 1 Then
' 親ウィンドウの情報をツリービューへ追加
treeNodeTop = New TreeNode(strClass & " - " & strTitle)
TreeView1.Nodes.Add(treeNodeTop)
Else
' 子コントロールの情報をツリービューへ追加
Dim treeNodeSub As TreeNode = New TreeNode(strClass & " - " & strTitle)
treeNodeTop.Nodes.Add(treeNodeSub)
End If
Next j
End If
Next i
End Sub
End Class