windowsvbawinapiuser32

How to wait until a specific window is open?


I am writing a VBA program that needs to wait until a specific window is open.

I tried FindFindow from the user32.dll.
Even if I set the two parameters of the function to Null, I get a negative return, although in that case all windows should match.
Basically I don't get a result different from 0 for hwnd independent of how I call FindWindow.

Declare Function FindWindow Lib "user32" _
  (ByVal lpClassName As String, ByVal lpWindowName As String) As Long

Sub Main
    Dim hwnd As Long
    hwnd = FindWindow(vbNullString, vbNullString)
    If (hwnd = 0) Then MsgBox ("failure")
End Sub

Solutions to similar problems like How to use FindWindow to find a visible or invisible window with a partial name in VBA don't seem to work.


Solution

  • The problem is that vbNullString is a length 0 string, the same as "". When that is marshalled to the unmanaged code a non-null pointer to a null-terminated array of characters is passed. Because the length is 0 then a pointer to a null-terminator is passed. That's different from NULL which is the null pointer.

    I'm far from a VBA expert, but I think the solution is like so:

    Declare Function FindWindow Lib "user32" Alias "FindWindowA" _
        (ByRef lpClassName As Any, ByRef lpWindowName As Any) As Long
    

    If you want to call this passing NULL for both arguments do so like this:

    window = FindWindow(ByVal 0&, ByVal 0&)
    

    Alternatively, if you want to pass a string value do it like this:

    window = FindWindow(ByVal 0&, ByVal "Untitled - Notepad")