【事務職が頑張るExcel・VBA】子ウィンドウを取得してみよう
今回の目標
ウィンドウテキストからハンドル値を取得し、さらに子のウィンドウのハンドル値を取得、列挙してみよう♪
使用関数一覧
Private Declare PtrSafe Function FindWindow Lib "user32" Alias "FindWindowA" (ByVal className As String, ByVal windowText As String) As Long
Private Declare PtrSafe Function EnumChildWindows Lib "user32" (ByVal hwnd As LongPtr, ByVal callBackProc As LongPtr, ByRef lparam As LongPtr) As LongPtr
メイン関数
Public Sub スタート()
Dim i As LongPtr
'ウィンドウテキストからハンドル値取得
Dim hwnd As LongPtr: hwnd = FindWindow(vbNullString, Cells(2, 1))
'ハンドルから子ウィンドウを列挙する
If hwnd <> 0 Then i = EnumChildWindows(hwnd, AddressOf コールバック関数だよ, 0)
End Sub
セルA2に入力された文字列でFindWindowを使ってハンドルを探し、0以外が見つかったらEnumChildWindowを実行しよう♪
EnumChildWindowは第一引数の子のハンドルが見つかるたびにコールバック関数を実行してくれる。
コールバック関数
Public Function コールバック関数だよ(ByVal hwnd As LongPtr, ByRef lparam As LongPtr) As LongPtr
'取得できたハンドルをセルに反映
Cells(2 + lparam, 2) = hwnd
'行管理用にインクリメント
lparam = lparam + 1
コールバック関数だよ = True
End Function
この関数が呼ばれると第一引数に子のハンドル値が渡されて実行されるため、今回はそれをそのままセルに入力してあげよう。
セルをクリアする関数を作って♪
'セルの削除
Public Sub cellClear()
Dim max_row As Long
max_row = Cells(Rows.count, 2).End(xlUp).Row
If max_row >= 2 Then Range("B2:B" & max_row).Value = ""
End Sub
連続で実行するとセルに前の情報が残るため毎回削除するような関数を作って入れておく。
完成(/・ω・)/
ボタンを作って標準モジュールの「スタート」を登録すると完成。
子のハンドルが取得できた♪