Retrieving Error Information Following DLL Function Calls
Run-time errors that occur in DLL functions behave differently from run-time errors in Microsoft® Visual Basic® for Applications (VBA) in that no error message box is displayed. When a run-time error occurs, the DLL function returns some value that indicates an error occurred, but the error does not interrupt VBA code execution.
Some functions in the Microsoft® Windows® API store error information for run-time errors. If you are programming in C or C++, you can use the GetLastError function to retrieve information about the last error that occurred. From VBA, however, GetLastError might return inaccurate results. To get information about a DLL error from VBA, you can use the LastDLLError property of the VBA Err object. The LastDLLError property returns the number of the error that occurred.
Note To use the LastDLLError property, you must know which error numbers correspond with which errors. This information is not available in the Win32API.txt file, but it is available free of charge in the Microsoft Platform SDK, available on the Microsoft® Developer Network (MSDN®) Web site at https://msdn.microsoft.com/default.asp.
The following example shows how you can use the LastDLLError property after you have called a function in the Windows API. The PrintWindowCoordinates procedure takes a handle to a window and calls the GetWindowRect function. GetWindowRect fills the RECT data structure with the lengths of the sides of the rectangle that make up the window. If you pass an invalid handle, an error occurs, and the error number is available through the LastDLLError property.
Declare Function GetWindowRect Lib "user32" (ByVal hwnd As Long, _
lpRect As RECT) As Long
Type RECT
Left As Long
Top As Long
Right As Long
Bottom As Long
End Type
Const ERROR_INVALID_WINDOW_HANDLE As Long = 1400
Const ERROR_INVALID_WINDOW_HANDLE_DESCR As String = "Invalid window handle."
Sub PrintWindowCoordinates(hwnd As Long)
' Prints left, right, top, and bottom positions of a window in pixels.
Dim rectWindow As RECT
' Pass in window handle and empty the data structure.
' If function returns 0, an error occurred.
If GetWindowRect(hwnd, rectWindow) = 0 Then
' Check LastDLLError and display a dialog box if the error
' occurred because an invalid handle was passed.
If Err.LastDllError = ERROR_INVALID_WINDOW_HANDLE Then
MsgBox ERROR_INVALID_WINDOW_HANDLE_DESCR, _
Title:="Error!"
End If
Else
Debug.Print rectWindow.Bottom
Debug.Print rectWindow.Left
Debug.Print rectWindow.Right
Debug.Print rectWindow.Top
End If
End Sub
To get the coordinates for the active window, you can return the handle of the active window by using the GetActiveWindow function and pass that result to the procedure defined in the previous example. To use GetActiveWindow, include the following Declare statement:
Declare Function GetActiveWindow Lib "user32" () As Long
In the Immediate window, type the following:
? PrintWindowCoordinates(GetActiveWindow)
To generate an error message, call the procedure with a random long integer.
See Also
Calling DLL Functions | Argument Data Types | Returning Strings from DLL Functions | Passing User-Defined Types | Using the Any Data Type