Sign in to follow this  
load_bitmap_file

Window Client Area and DX Viewport

Recommended Posts

Let's say I create a window using win32. I make it WS_OVERLAPPEDWINDOW and specify its width as 1024 x 768 in CreateWindow(). However, since I specified WS_OVERLAPPEDWINDOW instead of something like WS_POPUP, the titlebar and borders are actually considered part of the window width and height, meaning (0,0) refers to the top left pixel of the title bar rather than the top left pixel of the client area. So, I use AdjustWindowRect() to actually create a window with the specified 1024 x 768 client area. The total window size is now something like 1028 x 772. Next I create a Direct3D9 device passing in this window handle for hDeviceWindow, with BackBufferHeight and BackBufferWidth set to 0, which since my window is windowed (non-fullscreen), will set BackBufferHeight/BackBufferWidth to the client area of the window. After the creation of the Direct3D9 device, using Direct3D9::GetViewport I find that the viewport width and height are inexplicably set to 1020 x 743 respectively. Why would this happen? If I set the BackBufferHeight/BackBufferWidth explicitly to 1024 x 768, then everything renders "fine", except everything is extremely blurry, like D3D is scaling the picture or something. And if I try to fix the viewport using Direct3D9::SetViewport, specifying 1024 and 768 for the viewport's width and height respectively, all my rendered ID3DXSprite objects disappear. What the heck is going on? [sad]

Share this post


Link to post
Share on other sites
Could you post some code?

In particular covering how you're using AdjustWindowRect() in relation to CreateWindow().

Things to bear in mind (sorry if some are obvious):

- AdjustWindowRect() only adjusts the dimensions in a rectangle structure. It doesn't do anything to any windows you've already created or are about to create.

- The parameters passed to CreateWindow() are x,y,width,height and not left,top,right,bottom.

- The style passed to AdjustWindowRect() should be **exactly** the same as the style passed to CreateWindow().

- Make sure BOOL for menu is right for your window.


By way of demonstration (and sanity checking my own memory [wink]), I just modified the "Vertices" tutorial in the DirectX9 SDK to adjust the window rectangle:


RECT rc = {100,100, 100+300,100+300};
AdjustWindowRect( &rc, WS_OVERLAPPEDWINDOW, FALSE );

// Create the application's window
HWND hWnd = CreateWindow( "D3D Tutorial", "D3D Tutorial 02: Vertices",
WS_OVERLAPPEDWINDOW, rc.left, rc.top, rc.right-rc.left, rc.bottom-rc.top,
NULL, NULL, wc.hInstance, NULL );


As expected, a GetViewport() after device creation returns 300,300 for width and height.

Share this post


Link to post
Share on other sites
Quote:
Original post by S1CA
Could you post some code?


//adjust total window size for specified client area size
RECT clientArea = {0, 0, width, height};
//"flags" variable here is a DWORD containg the WS_STYLE stuff
AdjustWindowRect(&clientArea, flags, false);

m_handle = CreateWindow(name.c_str(), //name of Window class
name.c_str(), //name of title bar
flags, //Window graphic style
CW_USEDEFAULT, //Window x coordinate
CW_USEDEFAULT, //Window y coordinate
clientArea.right, //Window width
clientArea.bottom, //Window height
NULL, //"parent window" (NULL means desktop)
NULL, //menu name
instance, //Window instance
NULL); //value passed to Window (unused)


Quote:

Things to bear in mind (sorry if some are obvious):

- AdjustWindowRect() only adjusts the dimensions in a rectangle structure. It doesn't do anything to any windows you've already created or are about to create.

- The parameters passed to CreateWindow() are x,y,width,height and not left,top,right,bottom.

- The style passed to AdjustWindowRect() should be **exactly** the same as the style passed to CreateWindow().

- Make sure BOOL for menu is right for your window.


I think I have all this.

I double checked again, and it seems that AdjustWindowRect() function is simply not making the window large enough to meet the specified client area. I should have realized this earlier, but having the window adjusted to 1028 x 772 (from 1024 x 768) following AdjustWindowRect() is way too small. The title bar of the window alone is 20 vertical pixels high.

According to the docs you can't pass WS_OVERLAPPED as a flag; I was previously using WS_OVERLAPPEDWINDOW so I changed the "flags" DWORD to: WS_EX_TOPMOST | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME | WS_MINIMIZEBOX | WS_MAXIMIZEBOX | WS_VISIBLE but it still doesn't work. I even tried passing in true for a menu in the AdjustWindowRect(), but that didn't work either.

This throws Direct3D's backbuffer out of the picture, it's working correctly, it's just the window for some reason apparently isn't realizing that there's a big huge title bar taking up space.

If it makes any difference (and I'm thinking it really shouldn't), my machine is running XP with the themes service disabled, using windows classic.

Share this post


Link to post
Share on other sites
1) An illustrative example:
RECT rc = {100,100, 100+300,100+300}; // <-- BEFORE
AdjustWindowRect( &rc, WS_OVERLAPPEDWINDOW, FALSE );
...
rc = {77, 96, 404,404}; // <-- AFTER


See what AdjustWindowRect has done? [wink]

Your friend: "clientArea.right-clientArea.left"
Your friend: "clientArea.bottom-clientArea.top"

It'd be called AdjustWindowDimensions() if it only adjusted width and height [wink] (admittedly the use of the word 'size' in the docs could be clarified a bit).


2) I think WS_OVERLAPPED isn't allowed on its own, but WS_OVERLAPPEDWINDOW is, I'll have to check though.

Share this post


Link to post
Share on other sites
Quote:
Original post by S1CA
1) An illustrative example:
RECT rc = {100,100, 100+300,100+300}; // <-- BEFORE
AdjustWindowRect( &rc, WS_OVERLAPPEDWINDOW, FALSE );
...
rc = {77, 96, 404,404}; // <-- AFTER


See what AdjustWindowRect has done? [wink]

Your friend: "clientArea.right-clientArea.left"
Your friend: "clientArea.bottom-clientArea.top"

It'd be called AdjustWindowDimensions() if it only adjusted width and height [wink] (admittedly the use of the word 'size' in the docs could be clarified a bit).


Ooh! I assumed incorrectly about the adjusted RECT [disturbed]. clientArea.right - clientArea.left and clientArea.bottom - clientArea.top work fine. Thank you S1CA! [smile]


Quote:
2) I think WS_OVERLAPPED isn't allowed on its own, but WS_OVERLAPPEDWINDOW is, I'll have to check though.


Yeah, it does. Another wrong assumption on my part [smile]

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this