To program in the Windows environment, it is sometimes helpful to find out the Microsoft Excel instance handle (hInst) or top-level window handle (hWnd). Two special functions, xlGetInst and xlGetHwnd, have been provided for this purpose. These functions require special care under Win32. This is because sizeof(HWND) on Win32 is a long but the field used to receive the HWND parameter in the XLOPER structure is a short. Consequently the high word of the actual Microsoft Excel HWND is truncated. To work around this problem call xlGetHwnd to get the low word of the actual hwnd, then iterate the list of top-level windows and look for a match with the returned low word. This code illustrates the technique:
typedef struct _EnumStruct {
HWND hwnd;
unsigned short wLoword;
} EnumStruct;
#define CLASS_NAME_BUFFER 50
/*
**
** Function: EnumProc
**
** Comments: Used to find the hWnd in the Win32 version of Excel.
** This is the callback routine that checks each hwnd.
**
** Arguments: hwnd - The hwnd of the window currently being looked at
** EnumStruct * - A structure containing loword of hwnd of
** interest and space to return full hwnd.
**
** Returns: BOOL - indicates success or failure
**
** Date Developer Action
** --------------------------------------------------------
*/
BOOL CALLBACK EnumProc(HWND hwnd, EnumStruct * pEnum)
{
// first check class of the window. Must be "XLMAIN"
char szClass[CLASS_NAME_BUFFER+1];
GetClassName(hwnd, szClass, CLASS_NAME_BUFFER);
if(!lstrcmpi(szClass, "XLMAIN"))
{
// if that is a match, check the loword of the window handle
if(LOWORD((DWORD)hwnd) == pEnum->wLoword)
{
pEnum->hwnd = hwnd;
return FALSE;
}
}
// no match continue the enumeration
return TRUE;
}
/*
**
** Function: GetHwnd
**
** Comments: Used to find the hWnd in the Win32 version of Excel.
** This routine sets up the callback and checks the results.
**
** Arguments: pHwnd - This is actually the returned hwnd
**
** Returns: BOOL - Indicating success or failure.
**
** Date Developer Action
** --------------------------------------------------------
*/
BOOL GetHwnd(HWND *pHwnd)
{
XLOPER x;
// Get the loword of the hwnd
if(Excel4(xlGetHwnd, &x, 0) == xlretSuccess)
{
EnumStruct enm;
// Set up the structure
enm.hwnd = NULL;
enm.wLoword = x.val.w;
// Start the enumeration
EnumWindows((WNDENUMPROC)EnumProc, (LPARAM) &enm);
// Check results
if(enm.hwnd != NULL)
{
*pHwnd = enm.hwnd;
return TRUE;
}
}
return FALSE;
}
While it is possible to obtain the instance handle, under Win32 it is not as useful as it was under Win16. The window handle is useful for creating child windows and custom Windows dialog boxes.