With a the help of some Windows functions, you can use a loop to "wait" until your "Progress" window is closed.
The API functions must be placed at the top of a module (or better yet, keep it tidy by putting this in it's own module.)
Option Explicit
Private Declare Function FindWindow Lib "User32" Alias "FindWindowA" (ByVal lpClassName As String, ByVal lpWindowName As String) As Long
Private Declare Function GetWindowText Lib "User32" Alias "GetWindowTextA" (ByVal hWnd As Long, ByVal lpString As String, ByVal cch As Long) As Long
Private Declare Function GetWindowTextLength Lib "User32" Alias "GetWindowTextLengthA" (ByVal hWnd As Long) As Long
Private Declare Function GetWindow Lib "User32" (ByVal hWnd As Long, ByVal wCmd As Long) As Long
Private Declare Function IsWindowVisible Lib "User32" (ByVal hWnd As Long) As Boolean
Sub WaitForWindowToClose(winCaption As String)
'pauses code execution until no window caption (title) matches [winCaption]
Dim lhWndP As Long, sStr As String
Dim foundWindow As Boolean, startTime As Single
'loop through all windows
lhWndP = FindWindow(vbNullString, vbNullString)
Do While lhWndP <> 0
sStr = String(GetWindowTextLength(lhWndP) + 1, Chr$(0))
GetWindowText lhWndP, sStr, Len(sStr)
'check if this window is a match
If InStr(1, sStr, winCaption, vbTextCompare) > 0 Then
Debug.Print "Found Window: " & sStr & " (#" & lhWndP & ")"
foundWindow = True
Exit Do
End If
lhWndP = GetWindow(lhWndP, 2)
Loop
If Not foundWindow Then
Debug.Print "Window '" & winCaption & "' not found."
Exit Sub
End If
'check if window still exists
Do While FindWindow(vbNullString, sStr) <> 0 And IsWindowVisible(lhWndP)
'pause for a quarter second before checking again
startTime = Timer
Do While Timer < startTime + 0.25
DoEvents
Loop
Loop
Debug.Print "Window no longer exists."
End Sub
Example Usage:
WaitForWindowToClose "progress"
...pauses execution of code until there is no open window with progress
in its' title bar.
The procedure looks for case-insensitive, partial matches, because window captions are not always what they appear to be.
This shouldn't be an issue unless you have another window open with a similar caption to the one you're waiting for. For example, progress
could refer to your printer's progress window, or a browser window called "Progressive Insurance".
Troubleshooting:
The following procedures aren't necessary for operation of the above, but I figured I'd include them anyway, for troubleshooting purposes (ie., in case you're having trouble identifying your printer's progress window).
Usage should be self-explanatory:
Sub ListAllVisibleWindows()
'Lists all named, visible windows in the Immediate Window
Dim lhWndP As Long, sStr As String
lhWndP = FindWindow(vbNullString, vbNullString)
Do While lhWndP <> 0
x = x + 1
sStr = String(GetWindowTextLength(lhWndP) + 1, Chr$(0))
If Len(sStr) > 1 And IsWindowVisible(lhWndP) Then
GetWindowText lhWndP, sStr, Len(sStr)
Debug.Print "#" & x, lhWndP, sStr
End If
lhWndP = GetWindow(lhWndP, 2)
Loop
End Sub
Public Function IsWindowOpen(winCaption As String) As Boolean
'returns TRUE if winCaption is a partial match for an existing window
Dim lhWndP As Long, sStr As String
lhWndP = FindWindow(vbNullString, vbNullString)
Do While lhWndP <> 0
sStr = String(GetWindowTextLength(lhWndP) + 1, Chr$(0))
GetWindowText lhWndP, sStr, Len(sStr)
If InStr(1, sStr, winCaption, vbTextCompare) > 0 Then
Debug.Print "Found Window: " & sStr & " (#" & lhWndP & ")"
IsWindowOpen = True
Exit Do
End If
lhWndP = GetWindow(lhWndP, 2)
Loop
End Function
(Code was adapted from here.)