Skip to main content
gamedev.net
🔒 Locked

CreateWindow - RECTs not matching!

Started by brekehan Mar 28, 2009 at 2:12 AM 5 replies 1.2k views
Original Post
brekehan
brekehan
My window bounds and client area is not matching the parameters I pass to the CreateWindowEx function! I haven't had any trouble until I changed two things: 1) I am creating my directx window on the second monitor 2) I switched window styles so that when I go from fullscreen to windowed mode I don't have to change the window style or recreate the window every time. Is there some problem with creating a window that is larger than the desktop resolution? I did that so the client area matches the desired resolution, so when DXGI switches from windowed to fullscreen I get the desired resolution. The caption makes the window larger than the desktop of course. I didn't think that was a problem. I tried this requesting a window with a client size of 1280 x 1024 I have two monitors both at 1280 x 1024 resolution I created the window and centered it on the second monitor The result window client I got had a bounding box of: top 0 bottom 1009 // The bottom should have been 1024! left 0 right 1280 The result window I got had a bounding box of: top -13 bottom 1023 // The bottom should have been 1038! left 1276 right 2564 Why is it sizing itself? Can anyone explain what happened? I don't have any sizing code in the windows message procedure at all. I don't have anything between these two methods. GFXApplication is derived from BaseWindow.

//-----------------------------------------------------------------------------
void GFXApplication::Init(HINSTANCE instance, const DisplayMode & displayMode)
{
   // Adjust and validate the display mode
   m_displayMode = displayMode;

   if( !m_displayModeEnumerator.AdjustDisplayMode(m_displayMode) )
   {
      throw BaseException("Invalid display mode", 
                  "void GFXApplication::Init(HINSTANCE instance, const DisplayMode & displayMode)",
                  "GFXApplication.cpp");
   }
      
   // Set the window's style
   m_style = WS_OVERLAPPED | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME | WS_MINIMIZEBOX | WS_MAXIMIZEBOX | WS_VISIBLE;

   // Adjust the window rectangle such that the client area will be the desired width and height
   RECT windowBounds;
   windowBounds.left   = 0;
   windowBounds.top    = 0;
   windowBounds.right  = displayMode.m_resolution.m_width;   // Debugger shows 1280
   windowBounds.bottom = displayMode.m_resolution.m_height;  // Debugger shows 1024
   
   AdjustWindowRectEx(&windowBounds, m_style, false, m_extendedStyle);  // Debugger shows top -23 bottom 1028 left -4 right 1284

   // Center the window rectangle in the desktop it will be displayed on
   RECT     desktop       = m_displayModeEnumerator.GetDesktopCoords(m_displayMode.m_adapterIndex, m_displayMode.m_monitorIndex); // Debugger shows top 0 bottom 1024 left 1280 right 2560
   unsigned desktopWidth  = desktop.right  - desktop.left;           // Debugger shows 1280
   unsigned desktopHeight = desktop.bottom - desktop.top;            // Debugger shows 1024
   unsigned windowWidth   = windowBounds.right  - windowBounds.left; // Debugger shows 1288
   unsigned windowHeight  = windowBounds.bottom - windowBounds.top;  // Debugger shows 1051
   
   windowBounds.left   = desktopWidth  / 2 - windowWidth  / 2 + desktop.left; // Debugger shows 1276
   windowBounds.top    = desktopHeight / 2 - windowHeight / 2 + desktop.top;  // Debugger shows -13 (I realize I cut half a pixel, it shouldnt matter)
   windowBounds.right  = windowBounds.left + windowWidth;                     // Debugger shows 2564
   windowBounds.bottom = windowBounds.top  + windowHeight;                    // Debugger shows 1038

   // Create the window
   BaseWindow::Init(instance,
                    NULL,
                    NULL,
                    windowBounds.left,
                    windowBounds.top,
                    windowBounds.right  - windowBounds.left,
                    windowBounds.bottom - windowBounds.top);


   RECT rect;
   GetClientRect(m_hwnd, ▭); // Debugger shows top 0 bottom 1009 left 0 right 1280, why 1009!? It should be 1024!
   GetWindowRect(m_hwnd, ▭); // Debugger shows top -13 bottom 1023 left 1276 right 2564, why 1023!? It should be 1038!

   // Snip the rest


//-----------------------------------------------------------------------------
void BaseWindow::Init(HINSTANCE instance, HWND parent, HMENU menu, int x, int y, int width, int height)
{
   m_wndclass.lpszClassName = m_className.c_str();
   m_wndclass.hInstance     = instance;
    
   // If this window class has been already registered, this call will fail
   if( !RegisterClassEx(&m_wndclass) )
   {
      throw BaseException("Failed to register BaseWindow class with OS",
         "void BaseWindow::Init(HINSTANCE instance, HWND parent, HMENU menu, int x, int y, int width, int height)",
         "BaseWindow.cpp");
   }

   m_hwnd = CreateWindowEx(m_extendedStyle,
                           m_className.c_str(),
                           m_title.c_str(),
                           m_style, 
                           x,
                           y,
                           width,
                           height,
                           parent,
                           menu,
                           instance,
                           static_cast<void*>(this));

   if( !m_hwnd )
   {
      DWORD err = GetLastError();

      throw BaseException("Failed to create window",
         "void BaseWindow::Init(HINSTANCE instance, HWND parent, HMENU menu, int x, int y, int width, int height)",
         "BaseWindow.cpp");
   }
}

MJP
MJP
The width and height passed to CreateWindowEx do not specify the dimensions of the client area, the specify the dimensions of the window. The client area will be smaller unless you specify a window style with no non-client areas.

To figure out how big your window needs to be, use AdjustWindowRectEx.
brekehan
brekehan
Quote:
Original post by MJP
The width and height passed to CreateWindowEx do not specify the dimensions of the client area, the specify the dimensions of the window. The client area will be smaller unless you specify a window style with no non-client areas.

To figure out how big your window needs to be, use AdjustWindowRectEx.


I know that. I made a call to AdjustWindowRectEx. It is in the code I posted.

The dimensions passed to CreateWindowEx are:

1276
-13
2564
1038

The window should be the same dimensions. However, the window I got is:

1276
-13
2564
1023

These values are in the comments of the code already.
That isn't the problem.

Amr0
Amr0
I don't feel like reading all this (sorry), but my guess is you're trying to create a window which is larger than the desktop which, if I'm not mistaken, is not allowed. If you're attempting to create a fullscreen window, I remember the reading somewhere that the right way to do it is to set the window dimentions to those of the desktop and remove the caption and borders (WS_CAPTION and WS_BORDER) so the window contains nothing but the client area. Hope this helps.
brekehan
brekehan
Quote:
Original post by hikikomori-san
I don't feel like reading all this (sorry), but my guess is you're trying to create a window which is larger than the desktop which, if I'm not mistaken, is not allowed. If you're attempting to create a fullscreen window, I remember the reading somewhere that the right way to do it is to set the window dimentions to those of the desktop and remove the caption and borders (WS_CAPTION and WS_BORDER) so the window contains nothing but the client area. Hope this helps.


Yes, this is what I figure. However, if you do that and then transition from fullscreen to windowed mode. You have no way of moving, resizing, minimizing or maximixing the window, because it will have no caption.

I don't suppose there is a way to add style to an already created window without screwing up the dimensions or having to recreate it?
megamoscha
megamoscha
It is possible. Use SetWindowLongPtr with GWL_style or GWL_EXstyle with the second parameter and the third must be the new style.

Edit:
Don't know why GWL_* is messed but you must make everything uppercase.
Heres the link to the function reference.
Amr0
Amr0
megamoscha is right. You can change the style of a window any time. I'm writing an editor with a type of window which changes style when it's docked and restored the old style when it's undocked to allow the user to move it around. Here is the code I use:
VOID ModifyWindowStyle( HWND hWnd, DWORD flagsToDisable, DWORD flagsToEnable ){	DWORD style = GetWindowLong( hWnd, GWL_STYLE );	SetWindowLong( hWnd, GWL_STYLE, (style & ~flagsToDisable) | flagsToEnable );}BOOL AGenericPane::OnDock(){	// Get its size before it is docked so we can restore that size when it is undocked.	RECT rWindow;	GetWindowRect( hWnd, &rWindow );	undockedSize.cx = RECTWIDTH(rWindow);	undockedSize.cy = RECTHEIGHT(rWindow);	ModifyWindowStyle( hWnd,		WS_POPUP | WS_SYSMENU | WS_THICKFRAME | WS_CAPTION,		WS_CHILD );	SetParent( hWnd, hDockHost );	docked = TRUE;        // ... rest of method.}BOOL AGenericPane::OnUndock(){	docked = FALSE;	ModifyWindowStyle( hWnd,		WS_CHILD,		WS_POPUP | WS_SYSMENU | WS_CAPTION | WS_THICKFRAME );	SetParent( hWnd, NULL );	MoveWindow( hWnd, 0, 0, undockedSize.cx, undockedSize.cy, TRUE );	return TRUE;}


Hmm, now that I think about it, this particular issue was covered in a good tutorial made by EvilSteve about Direct3D in a section about toggling fullscreen mode. I think it was.. umm.. wait.. aha, here it is: clicksy.

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.