A dialog I'm working on isn't displaying, using:
CWnd::CreateDlgIndirect(LPCDLGTEMPLATE lpDialogTemplate,CWnd* pParentWnd, HINSTANCE hInst)
The call to CreateDlgIndirect is in a lon-used base-class, which effectively takes the IDD of the dialog template in the resource file - it works fine for many other dialogs but I can't see what's different in my dialog. My dialog works fine when created in a more normal way, but I have to use the base class as it has loads of other functionality built in.
What I find when trawling through CWnd::CreateDlgIndirect in dlgcore.cpp, is that the plain Win32 API call开发者_运维百科 is failing:
hWnd = ::CreateDialogIndirect(hInst, lpDialogTemplate,pParentWnd->GetSafeHwnd(), AfxDlgProc);
I can't step into that function for some reason, so all I see is the HWND is NULL.
Can anyone suggest what kind of problems might be causing this? I compared the two dialog resource templates and their properties are the same.
edit: I have one custom control on the dialog. When I remove this, it works. No idea why, what difference might this make?
One of the more obscure ways for CreateDialogXXX to fail is for a child control on the dialog to fail creation. Usually because the application has not initialized the common controls library before attempting to effect the dialog creation. See InitCommonControlsEx
One way to check this is to open the dialog in the resource editor, go to the dialog's properties, and find and turn on the DS_NOFAILCREATE
flag. Usually called something obscure like "No Fail Create". Or add the DS_NOFAILCREATE
directly to your dialog template in memory. This will allow the dialog to show, and the culprit should be evident by its absence.
In the case that the child control is an actual custom control - well the custom window class is either not registered correctly, or at all. Check the HINSTANCE used in registration - unless the CS_GLOBAL flag is specified, window classes are identified by (hInstance, ClassName) - this prevents window classes using the same name in different dlls conflicting.
A custom CWnd derived control fails, if you use the wrong HINSTANCE. When using a satelite DLL for the language resources, here's what I had to change:
// ----------------------------------------- //
// RegisterWndClass
// ----------------------------------------- //
/*static*/ BOOL MyCtrl::RegisterWndClass() {
WNDCLASS windowclass = {0};
// !! THIS IS THE IMPORTANT PART: !!
HINSTANCE hInst = AfxGetResourceHandle(); // NOT AfxGetInstanceHandle();
if(!(::GetClassInfo(hInst, MYCTRL_CLASSNAME, &windowclass))) {
//If not then we have to register the new class
windowclass.style = CS_DBLCLKS | CS_HREDRAW | CS_VREDRAW;
windowclass.lpfnWndProc = ::DefWindowProc;
windowclass.cbClsExtra = windowclass.cbWndExtra = 0;
windowclass.hInstance = hInst;
windowclass.hIcon = NULL;
windowclass.hCursor = AfxGetApp()->LoadStandardCursor(IDC_IBEAM);
windowclass.hbrBackground = ::GetSysColorBrush(COLOR_WINDOW);
windowclass.lpszMenuName = NULL;
windowclass.lpszClassName = MYCTRL_CLASSNAME;
if(!AfxRegisterClass(&windowclass)) {
AfxThrowResourceException();
return FALSE;
}
}
return TRUE;
}
精彩评论