pouët.net

Go to bottom

Win32 API coding: A Wrapper class for Window Creation

category: general [glöplog]
anyone here had problems with DialogBoxIndirectParam?

I try make a dialogbox with this function.

I have no plans on using a .rc script, little because the free version of Visual Studio Express has not enabled the resource editor, but mostly because i want to make dynamic allocated dialogboxes in runtime.

I've tried DLGTEMPLATE and DLGTEMPLATEEX. It seems that DLGTEMPLATEEX is the one that works without the app crashing.

The Window Procedure of the dialogbox is not interesting since its not run (one question is why it doesnt run?).

MSDN says:
If the function fails for any other reason, the return value is –1.

That's what i get, but GetLastError says that The operation completed successfully. So I guess things are right so far..

If it returns successfully even though it returns -1 what have i lost? something in the DLGTEMPLATEEX struct? The funny thing is that the dialogbox window-proc doesnt get called, but at first the dialogbox doesnt show on screen.

Any suggestions?

This is the inmate of the template struct: (i've tried different values though)

tmp2.dlgVer = 0xffff;
tmp2.signature = 1;
tmp2.helpID = 0;
tmp2.exStyle = 0;
tmp2.style = WS_CHILD | DS_CENTER | WS_MINIMIZEBOX | WS_MAXIMIZEBOX | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME;
tmp2.x = 0;
tmp2.y = 0;
tmp2.cx = 320;
tmp2.cy = 120;
tmp2.menu = 0;
tmp2.cDlgItems = 0;
tmp2.windowClass = "dialog class";
tmp2.title = "My Dialog";
tmp2.pointsize = 12;
tmp2.weight = 12;
tmp2.bItalic = FALSE;
tmp2.font = NULL;//"Times New Roman";
added on the 2009-02-16 18:25:38 by rudi rudi
afair the DLGPROC dialog message handling function has a different signature to the WNDPROC one. check that.
added on the 2009-02-16 19:50:19 by raer raer
If the dialog box you're trying to create is modal, DialogBoxIndirect ist ok. Else use CreateDialogIndirect.

And:
Quote:

dlgVer
Specifies the version number of the extended dialog box template. This member must be 1.
added on the 2009-02-16 20:02:16 by raer raer
rare: i changed it, but nothing happens.

i found out that the structure needs to be global, so then the non-extended structure works fine.

_result = DialogBoxIndirectParam(hInstance, (LPCDLGTEMPLATE)&tmp1, hwnd, (DLGPROC)ModalDialogProc, (LPARAM)0);

im not sure if the casting is doing the right thing. ive seen it been use somewhere else, but im not sure if it is safe.

anyway since the non-extended works fine i think go for that solution, if not ill be back :p


added on the 2009-02-16 20:30:35 by rudi rudi
oh typoe, the tmp1 is actually tmp2, for the extended version.
added on the 2009-02-16 20:31:43 by rudi rudi
&ModalDialogProc
added on the 2009-02-16 20:47:39 by raer raer
The documentation for DLGTEMPLATEEX states that:

* The menu, windowClass, title, and typeface arrays must be aligned on WORD boundaries. You do not.
* If you specify character strings in the menu, windowClass, title, and typeface arrays, you must use Unicode strings. At least your menu setting is for sure no null terminated unicode string.

I'd suggest you'd look at the sample provided in this section of Using Dialog Boxes and work your way from there.

Cheers
added on the 2009-02-17 00:39:21 by Paralax Paralax
L"textext"/_TEXT("textext") is your friend. And yeah, RTFD and check your stuff...
added on the 2009-02-17 09:55:51 by raer raer
ah yes, the other strings would'nt have worked either as you're literally building an in memory representation of your dialog and not just setting pointers. anyways, the documentation is a good starting point before making a dialog builder class out of the API which I'd suggest you may want to end at later.
added on the 2009-02-18 02:47:51 by Paralax Paralax
i dont have time nor motivation to code such a dialog builder class right now, im using the non-extenden structure because it works quite fine as it is now. i seem to forget what problems i had with it earlier, but ive hacked my way around the problems. the only itchy thing is that i have to re-set the dialog's width and height, because the CreateDialog function dont seem to use the cx and cy variables from the template to create the window.
added on the 2009-02-18 17:47:01 by rudi rudi
but as said i just use SetWindowPos to change the sizes. if i look quite closely i see that the window changes size during the creation of the dialogs. and some other dialogs get painted over. but i just redraw the dialogs afterwards.
added on the 2009-02-18 17:48:41 by rudi rudi
I've created a window dialog with window style "child". I cannot enter any characters in an edit box in the window. But it works well if I change the style to "overlapped". Why is it so? What can I do if I really need to use the style "child"?

If i preset the focus of the edit box it works, but i cannot click on other editboxes to recieve the focus. Any Ideas?
added on the 2009-03-27 01:11:31 by rudi rudi
the latter "the" = "their"
added on the 2009-03-27 01:14:17 by rudi rudi
rydi: use WS_POPUP instead of WS_CHILD.

http://support.microsoft.com/kb/230587
added on the 2009-03-27 08:48:36 by Jcl Jcl
Jcl: thanks for the info, but its not a satisfactory alternative. i found out that if i remove the WS_CAPTION style it works. but i want the caption as well. i'll trying to work some way around the problem.
added on the 2009-03-27 11:50:36 by rudi rudi
I just want to find out a way to implement this solution:
I create the window as usuall with the WS_CHILD style, but after the creating I use the function SetWindowLong to remove the caption:
Code:SetWindowLong(hwnd, GWL_STYLE, WS_CHILD | WS_VISIBLE | WS_SYSMENU | WS_BORDER);
then I use SetWindowPos to change the position of the window. I think the client area is bigger so i can change the size with SetWindowPos as well, but i can leave it for a fake caption. I wonder if there's an easy way to redraw the caption on top..
added on the 2009-03-27 12:16:42 by rudi rudi
Check the WM_NCxxx (non-clinent area) messages.
http://msdn.microsoft.com/en-us/library/ms632633(VS.85).aspx or WM_NCCALCSIZE and WM_NCPAINT.
added on the 2009-03-27 12:32:18 by raer raer
And search for "wm_paint nonclient area" on google... :/
added on the 2009-03-27 12:47:21 by raer raer
okay, ive tried to draw in the non-client area to test, but it won't work.

this is what i do in the WM_NCPAINT:

hdc = GetDCEx(hwnd, (HRGN)w, DCX_WINDOW|DCX_INTERSECTRGN);

From GetLastError i get: "The parameter is incorrect."
however if i make my own region (using CreateRectRgn) it says that the operation returned Successfully. It still wont draw anything in the non-client area.
added on the 2009-03-27 14:16:20 by rudi rudi
You may be getting the wrong region then.
Have you tried this: http://www.catch22.net/tuts/tips#UndocumentedGetDCEx
?
And this: http://www.experts-exchange.com/Programming/Languages/CPP/Q_21565833.html
?
added on the 2009-03-27 14:40:54 by raer raer
yes, i've tried the first one without any luck. I can't see the solution on the second, so.. :/
added on the 2009-03-27 14:45:19 by rudi rudi
Have you tried using GetWindowDC?

The answer was:
Quote:

WM_PAINT has must need to be used in some cases of refressing. because some action need to be performed on dc before bringing up your refreshment(drawing) and after bringing up also.

I understood your criteria, that the painting has need to be done only when window is get activated or clicked in non-client area, that is bringing up the window to top. wm_activate and wm_ncpaint also calls wm_paint after the calling the above messages, that's why your drawings get vanished when you are placing the code in wm_activate or wm_ncpaint.
better place the code in wm_paint, with certain conditions flagged in wm_ncpaint or wm_activate.

(.e) set gflag=1 in wm_ncpaint or wm_activate. place the if(gflag==1) in wm_paint and do your operations and set gflag=0 inside wm_paint.
added on the 2009-03-27 14:50:56 by raer raer
yep, ive tried GetWindowDC. gonna try doing it in WM_PAINT then.
added on the 2009-03-27 15:12:09 by rudi rudi
i found it!! it actually works now!

BeginPaint caused it to be drawn in the client area.
When I removed it, it worked to draw in the non-client area.

Also I called OnNCPaint in OnPaint for it to always draw.

Thanks for the help.
added on the 2009-03-27 15:25:37 by rudi rudi

login

Go to top