summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKeith Packard <keithp@keithp.com>2011-01-20 21:11:53 -0800
committerKeith Packard <keithp@keithp.com>2011-01-20 21:11:53 -0800
commit24ce650cf4f0c6fa72faecd38c53d40703e6c959 (patch)
tree819bd145f19183f9eeda93de650cd3be14a8a6e9
parentbbdf81a056be0ea645da17a642dad5eadef3a906 (diff)
parent09fd010902fad56735b8069b1becb80d85bd6a35 (diff)
Merge remote branch 'jturney/jturney-framebuffer-resize-for-master'
-rw-r--r--configure.ac4
-rw-r--r--hw/xwin/InitOutput.c13
-rw-r--r--hw/xwin/Makefile.am1
-rw-r--r--hw/xwin/man/XWin.man85
-rw-r--r--hw/xwin/win.h56
-rw-r--r--hw/xwin/wincreatewnd.c48
-rw-r--r--hw/xwin/windialogs.c13
-rw-r--r--hw/xwin/winmonitors.c92
-rw-r--r--hw/xwin/winmonitors.h14
-rw-r--r--hw/xwin/winnativegdi.c37
-rw-r--r--hw/xwin/winpfbdd.c108
-rw-r--r--hw/xwin/winprocarg.c131
-rw-r--r--hw/xwin/winrandr.c302
-rw-r--r--hw/xwin/winscrinit.c66
-rw-r--r--hw/xwin/winshaddd.c164
-rw-r--r--hw/xwin/winshadddnl.c152
-rw-r--r--hw/xwin/winshadgdi.c124
-rw-r--r--hw/xwin/winvalargs.c8
-rw-r--r--hw/xwin/winwindow.c1
-rw-r--r--hw/xwin/winwndproc.c307
20 files changed, 1026 insertions, 700 deletions
diff --git a/configure.ac b/configure.ac
index 45286eaf4..120321e7c 100644
--- a/configure.ac
+++ b/configure.ac
@@ -1903,8 +1903,8 @@ AM_CONDITIONAL(XWIN_MULTIWINDOW, [test "x$XWIN" = xyes])
AM_CONDITIONAL(XWIN_MULTIWINDOWEXTWM, [test "x$XWIN" = xyes && test "x$WINDOWSWM" = xyes])
AM_CONDITIONAL(XWIN_CLIPBOARD, [test "x$XWIN" = xyes])
AM_CONDITIONAL(XWIN_GLX_WINDOWS, [test "x$XWIN" = xyes && false])
-AM_CONDITIONAL(XWIN_NATIVEGDI, [test "x$XWIN" = xyes && false])
-AM_CONDITIONAL(XWIN_PRIMARYFB, [test "x$XWIN" = xyes && false])
+AM_CONDITIONAL(XWIN_NATIVEGDI, [test "x$XWIN" = xyes])
+AM_CONDITIONAL(XWIN_PRIMARYFB, [test "x$XWIN" = xyes])
AM_CONDITIONAL(XWIN_RANDR, [test "x$XWIN" = xyes])
AM_CONDITIONAL(XWIN_XV, [test "x$XWIN" = xyes && test "x$XV" = xyes])
diff --git a/hw/xwin/InitOutput.c b/hw/xwin/InitOutput.c
index 38a658d77..7faed0170 100644
--- a/hw/xwin/InitOutput.c
+++ b/hw/xwin/InitOutput.c
@@ -755,6 +755,9 @@ winUseMsg (void)
"\t\t1 - Shadow GDI\n"
"\t\t2 - Shadow DirectDraw\n"
"\t\t4 - Shadow DirectDraw4 Non-Locking\n"
+#ifdef XWIN_PRIMARYFB
+ "\t\t8 - Primary DirectDraw - obsolete\n"
+#endif
#ifdef XWIN_NATIVEGDI
"\t\t16 - Native GDI - experimental\n"
#endif
@@ -823,6 +826,11 @@ winUseMsg (void)
"\tSpecify an optional refresh rate to use in fullscreen mode\n"
"\twith a DirectDraw engine.\n");
+ ErrorF ("-resize=none|scrollbars|randr"
+ "\tIn windowed mode, [don't] allow resizing of the window. 'scrollbars'\n"
+ "\tmode gives the window scrollbars as needed, 'randr' mode uses the RANR\n"
+ "\textension to resize the X screen.\n");
+
ErrorF ("-rootless\n"
"\tRun the server in rootless mode.\n");
@@ -836,11 +844,6 @@ winUseMsg (void)
"\t -screen 0 1024x768@3 ; 3rd monitor size 1024x768\n"
"\t -screen 0 @1 ; on 1st monitor using its full resolution (the default)\n");
- ErrorF ("-scrollbars\n"
- "\tIn windowed mode, allow screens bigger than the Windows desktop.\n"
- "\tMoreover, if the window has decorations, one can now resize\n"
- "\tit.\n");
-
ErrorF ("-silent-dup-error\n"
"\tIf another instance of " EXECUTABLE_NAME " with the same display number is running\n"
"\texit silently and don't display any error message.\n");
diff --git a/hw/xwin/Makefile.am b/hw/xwin/Makefile.am
index f6a75df2c..ce2edb2e6 100644
--- a/hw/xwin/Makefile.am
+++ b/hw/xwin/Makefile.am
@@ -87,6 +87,7 @@ SRCS = InitInput.c \
winkeybd.c \
winkeyhook.c \
winmisc.c \
+ winmonitors.c \
winmouse.c \
winmsg.c \
winmultiwindowclass.c \
diff --git a/hw/xwin/man/XWin.man b/hw/xwin/man/XWin.man
index 51268f69a..e7933c9c8 100644
--- a/hw/xwin/man/XWin.man
+++ b/hw/xwin/man/XWin.man
@@ -103,7 +103,7 @@ Examples:
.SH OPTIONS CONTROLLING THE APPEARANCE OF THE X SCREEN WINDOWS
These parameters only apply to windowed mode screens i.e. not
-in \fB-multwindow\fP or \fB-rootless\fP mode
+in \fB-multiwindow\fP or \fB-rootless\fP mode.
.TP 8
.B "\-fullscreen"
The X server window takes the full screen, covering completely the
@@ -115,10 +115,52 @@ etc.
This parameter is ignored when the \fB\-fullscreen\fP parameter is specified.
.TP 8
.B \-scrollbars
-In windowed mode, allow screens bigger than the \fIWindows\fP desktop.
-Moreover, if the window has decorations, one can now resize it.
-This parameter is ignored when the \fB\-fullscreen\fP parameter is specified.
+Alternative name for \fB\-resize=scrollbars\fP.
+
+.SH OPTIONS CONTROLLING RESIZE BEHAVIOUR
+.TP 8
+.B \-resize[=none|scrollbars|randr]
+Select the resize mode of an X screen.
+
+.RS
+.IP \fB\-resize=none\fP 8
+(default). The screen is not resizable.
+
+In windowed mode, if the window has decorations, a fixed frame is used.
+
+.IP \fB\-resize=scrollbars\fP 8
+The screen window is resizeable, but the screen is not resizable.
+
+In windowed mode, if the window has decorations, a resizing frame is used.
+Scrollbars are drawn when needed to allow the entire X screen
+to viewed by adjusting them.
+
+This also permits screens bigger than the \fIWindows\fP virtual desktop to be used.
+
+This parameter is ignored in \fB-multiwindow\fP or \fB-rootless\fP mode.
+Alternative name is \fB\-scrollbars\fP.
+
+.IP \fB\-resize=randr\fP 8
+The screen is resizable and the screen window is resizeable.
+In windowed mode, if the window has decorations, a resizing frame is used.
+
+Resizing the \fIWindows\fP window will use the RANDR extension to change
+the size of the X screen. Likewise, changing the size of
+the X screen using the RANDR extension will cause the size
+of the \fIWindows\fP window containing the X screen to be changed.
+
+In \fB-multiwindow\fP or \fB-rootless\fP mode, if the X screen is
+of the same dimensions as a Windows monitor or the virtual desktop,
+the X server will respond to the WM_DISPLAYCHANGED sent when those
+dimensions change by resizing the X screen. Changing the size
+of the X screen using the RANDR extension is not permitted.
+
+The maximum dimensions of the screen are the dimensions of the \fIWindows\fP virtual desktop.
+
+.IP \fB\--resize\fP 8
+on its own is equivalent to \fB\--resize=randr\fP
+.RE
.SH OPTIONS CONTROLLING WINDOWS INTEGRATION
.TP 8
@@ -190,15 +232,27 @@ respectively).
.TP 8
.B "\-engine \fIengine_type_id\fP"
This option, which is intended for Cygwin/X developers,
-overrides the server's automatically selected engine type. This
-parameter will be ignored if the specified engine type is not
-supported on the current system. The supported engine type ids are 1
-- Shadow GDI, 2 - Shadow DirectDraw, and 4 - Shadow DirectDraw Non-Locking.
-Additionally, there are engines with type ids
-8 - Primary DirectDraw (obsolete) and 16 - Native GDI (experimental and barely functional).
-Default behavior is to determine the engine with optimum performance that
+overrides the server's automatically selected drawing engine type. This
+parameter will be ignored if the specified drawing engine type is not
+supported on the current system.
+
+Default behavior is to select the drawing engine with optimum performance that
supports the specified depth and window configuration.
+The engine type ids are:
+.RS
+.IP 1 4
+Shadow GDI
+.IP 2 4
+Shadow DirectDraw
+.IP 4 4
+Shadow DirectDraw Non-Locking
+.IP 8 4
+Primary DirectDraw (unsupported, obsolete)
+.IP 16 4
+Native GDI (unsupported, experimental and barely functional)
+.RE
+
.SH FULLSCREEN OPTIONS
.TP 8
.B "\-depth \fIdepth\fP"
@@ -322,12 +376,9 @@ X(__miscmansuffix__), Xserver(1), xdm(1), xinit(1), XWinrc(__filemansuffix__), s
.SH BUGS
.I XWin
-and this man page still have many limitations. Some of the more obvious
-ones are:
-.br
-- The display mode can not be changed once the X server has started.
-.br
-- The \fIXWin\fP software is continuously developing; it is therefore possible that
+and this man page still have many limitations.
+
+The \fIXWin\fP software is continuously developing; it is therefore possible that
this man page is not up to date. It is always prudent to
look also at the output of \fIXWin -help\fP in order to
check the options that are operative.
diff --git a/hw/xwin/win.h b/hw/xwin/win.h
index 44307813c..3f40fdbe0 100644
--- a/hw/xwin/win.h
+++ b/hw/xwin/win.h
@@ -74,9 +74,6 @@
#endif
#define WIN_DEFAULT_USER_GAVE_HEIGHT_AND_WIDTH FALSE
-#define WIN_DIB_MAXIMUM_SIZE 0x08000000 /* 16 MB on Windows 95, 98, Me */
-#define WIN_DIB_MAXIMUM_SIZE_MB (WIN_DIB_MAXIMUM_SIZE / 8 / 1024 / 1024)
-
/*
* Windows only supports 256 color palettes
*/
@@ -276,8 +273,12 @@ static Atom func (void) { \
typedef Bool (*winAllocateFBProcPtr)(ScreenPtr);
+typedef void (*winFreeFBProcPtr)(ScreenPtr);
+
typedef void (*winShadowUpdateProcPtr)(ScreenPtr, shadowBufPtr);
+typedef Bool (*winInitScreenProcPtr)(ScreenPtr);
+
typedef Bool (*winCloseScreenProcPtr)(int, ScreenPtr);
typedef Bool (*winInitVisualsProcPtr)(ScreenPtr);
@@ -315,6 +316,12 @@ typedef Bool (*winFinishCreateWindowsWindowProcPtr)(WindowPtr pWin);
typedef Bool (*winCreateScreenResourcesProc)(ScreenPtr);
+#ifdef XWIN_NATIVEGDI
+/* Typedefs for native GDI wrappers */
+typedef Bool (*RealizeFontPtr) (ScreenPtr pScreen, FontPtr pFont);
+typedef Bool (*UnrealizeFontPtr)(ScreenPtr pScreen, FontPtr pFont);
+#endif
+
/*
* GC (graphics context) privates
@@ -369,6 +376,15 @@ typedef struct {
} winCursorRec;
/*
+ * Resize modes
+ */
+typedef enum {
+ notAllowed,
+ resizeWithScrollbars,
+ resizeWithRandr
+} winResizeMode;
+
+/*
* Screen information structure that we need before privates are available
* in the server startup sequence.
*/
@@ -381,12 +397,12 @@ typedef struct
Bool fUserGaveHeightAndWidth;
DWORD dwScreen;
+
+ int iMonitor;
DWORD dwUserWidth;
DWORD dwUserHeight;
DWORD dwWidth;
DWORD dwHeight;
- DWORD dwWidth_mm;
- DWORD dwHeight_mm;
DWORD dwPaddedWidth;
/* Did the user specify a screen position? */
@@ -431,7 +447,7 @@ typedef struct
#endif
Bool fMultipleMonitors;
Bool fLessPointer;
- Bool fScrollbars;
+ winResizeMode iResizeMode;
Bool fNoTrayIcon;
int iE3BTimeout;
/* Windows (Alt+F4) and Unix (Ctrl+Alt+Backspace) Killkey */
@@ -473,11 +489,6 @@ typedef struct _winPrivScreenRec
/* Handle to icons that must be freed */
HICON hiconNotifyIcon;
- /* Last width, height, and depth of the Windows display */
- DWORD dwLastWindowsWidth;
- DWORD dwLastWindowsHeight;
- DWORD dwLastWindowsBitsPixel;
-
/* Palette management */
ColormapPtr pcmapInstalled;
@@ -493,7 +504,8 @@ typedef struct _winPrivScreenRec
HDC hdcScreen;
HDC hdcShadow;
HWND hwndScreen;
-
+ BITMAPINFOHEADER *pbmih;
+
/* Privates used by shadow fb and primary fb DirectDraw servers */
LPDIRECTDRAW pdd;
LPDIRECTDRAWSURFACE2 pddsPrimary;
@@ -543,7 +555,9 @@ typedef struct _winPrivScreenRec
/* Engine specific functions */
winAllocateFBProcPtr pwinAllocateFB;
+ winFreeFBProcPtr pwinFreeFB;
winShadowUpdateProcPtr pwinShadowUpdate;
+ winInitScreenProcPtr pwinInitScreen;
winCloseScreenProcPtr pwinCloseScreen;
winInitVisualsProcPtr pwinInitVisuals;
winAdjustVideoModeProcPtr pwinAdjustVideoMode;
@@ -588,6 +602,12 @@ typedef struct _winPrivScreenRec
SetShapeProcPtr SetShape;
winCursorRec cursor;
+
+#ifdef XWIN_NATIVEGDI
+ RealizeFontPtr RealizeFont;
+ UnrealizeFontPtr UnrealizeFont;
+#endif
+
} winPrivScreenRec;
@@ -1452,6 +1472,18 @@ void
winInitializeScreens(int maxscreens);
/*
+ * winrandr.c
+ */
+Bool
+winRandRInit (ScreenPtr pScreen);
+void
+winDoRandRScreenSetSize (ScreenPtr pScreen,
+ CARD16 width,
+ CARD16 height,
+ CARD32 mmWidth,
+ CARD32 mmHeight);
+
+/*
* END DDX and DIX Function Prototypes
*/
diff --git a/hw/xwin/wincreatewnd.c b/hw/xwin/wincreatewnd.c
index 0c342e1ae..755373965 100644
--- a/hw/xwin/wincreatewnd.c
+++ b/hw/xwin/wincreatewnd.c
@@ -192,7 +192,7 @@ winCreateBoundingWindowWindowed (ScreenPtr pScreen)
fForceShowWindow = TRUE;
}
dwWindowStyle |= WS_CAPTION;
- if (pScreenInfo->fScrollbars)
+ if (pScreenInfo->iResizeMode != notAllowed)
dwWindowStyle |= WS_THICKFRAME | WS_MAXIMIZEBOX;
}
else
@@ -233,6 +233,22 @@ winCreateBoundingWindowWindowed (ScreenPtr pScreen)
iPosY = rcWorkArea.top;
}
+ /* Clean up the scrollbars flag, if necessary */
+ if ((!pScreenInfo->fDecoration
+#ifdef XWIN_MULTIWINDOWEXTWM
+ || pScreenInfo->fMWExtWM
+#endif
+ || pScreenInfo->fRootless
+#ifdef XWIN_MULTIWINDOW
+ || pScreenInfo->fMultiWindow
+#endif
+ )
+ && (pScreenInfo->iResizeMode == resizeWithScrollbars))
+ {
+ /* We cannot have scrollbars if we do not have a window border */
+ pScreenInfo->iResizeMode = notAllowed;
+ }
+
/* Did the user specify a height and width? */
if (pScreenInfo->fUserGaveHeightAndWidth)
{
@@ -256,12 +272,12 @@ winCreateBoundingWindowWindowed (ScreenPtr pScreen)
#if CYGDEBUG
winDebug ("winCreateBoundingWindowWindowed - Window has decoration\n");
#endif
- /* Are we using scrollbars? */
- if (pScreenInfo->fScrollbars)
+
+ /* Are we resizable */
+ if (pScreenInfo->iResizeMode != notAllowed)
{
#if CYGDEBUG
- winDebug ("winCreateBoundingWindowWindowed - Window has "
- "scrollbars\n");
+ winDebug ("winCreateBoundingWindowWindowed - Window is resizable\n");
#endif
iWidth += 2 * GetSystemMetrics (SM_CXSIZEFRAME);
@@ -271,8 +287,7 @@ winCreateBoundingWindowWindowed (ScreenPtr pScreen)
else
{
#if CYGDEBUG
- winDebug ("winCreateBoundingWindowWindowed - Window does not have "
- "scrollbars\n");
+ winDebug ("winCreateBoundingWindowWindowed - Window is not resizable\n");
#endif
iWidth += 2 * GetSystemMetrics (SM_CXFIXEDFRAME);
@@ -296,22 +311,7 @@ winCreateBoundingWindowWindowed (ScreenPtr pScreen)
}
}
- /* Clean up the scrollbars flag, if necessary */
- if ((!pScreenInfo->fDecoration
-#ifdef XWIN_MULTIWINDOWEXTWM
- || pScreenInfo->fMWExtWM
-#endif
- || pScreenInfo->fRootless
-#ifdef XWIN_MULTIWINDOW
- || pScreenInfo->fMultiWindow
-#endif
- )
- && pScreenInfo->fScrollbars)
- {
- /* We cannot have scrollbars if we do not have a window border */
- pScreenInfo->fScrollbars = FALSE;
- }
-
+ /* Make sure window is no bigger than work area */
if (TRUE
#ifdef XWIN_MULTIWINDOWEXTWM
&& !pScreenInfo->fMWExtWM
@@ -396,7 +396,7 @@ winCreateBoundingWindowWindowed (ScreenPtr pScreen)
rcClient.bottom, rcClient.top);
/* We adjust the visual size if the user did not specify it */
- if (!(pScreenInfo->fScrollbars && pScreenInfo->fUserGaveHeightAndWidth))
+ if (!((pScreenInfo->iResizeMode == resizeWithScrollbars) && pScreenInfo->fUserGaveHeightAndWidth))
{
/*
* User did not give a height and width with scrollbars enabled,
diff --git a/hw/xwin/windialogs.c b/hw/xwin/windialogs.c
index 679b3fab5..c3a149762 100644
--- a/hw/xwin/windialogs.c
+++ b/hw/xwin/windialogs.c
@@ -482,11 +482,11 @@ winChangeDepthDlgProc (HWND hwndDialog, UINT message,
#if CYGDEBUG
winDebug ("winChangeDepthDlgProc - WM_INITDIALOG - orig bpp: %d, "
- "last bpp: %d\n",
+ "current bpp: %d\n",
s_pScreenInfo->dwBPP,
- s_pScreenPriv->dwLastWindowsBitsPixel);
+ GetDeviceCaps(s_pScreenPriv->hdcScreen, BITSPIXEL));
#endif
-
+
winInitDialog( hwndDialog );
return TRUE;
@@ -494,14 +494,13 @@ winChangeDepthDlgProc (HWND hwndDialog, UINT message,
case WM_DISPLAYCHANGE:
#if CYGDEBUG
winDebug ("winChangeDepthDlgProc - WM_DISPLAYCHANGE - orig bpp: %d, "
- "last bpp: %d, new bpp: %d\n",
+ "new bpp: %d\n",
s_pScreenInfo->dwBPP,
- s_pScreenPriv->dwLastWindowsBitsPixel,
- wParam);
+ GetDeviceCaps(s_pScreenPriv->hdcScreen, BITSPIXEL));
#endif
/* Dismiss the dialog if the display returns to the original depth */
- if (wParam == s_pScreenInfo->dwBPP)
+ if (GetDeviceCaps(s_pScreenPriv->hdcScreen, BITSPIXEL) == s_pScreenInfo->dwBPP)
{
ErrorF ("winChangeDelthDlgProc - wParam == s_pScreenInfo->dwBPP\n");
diff --git a/hw/xwin/winmonitors.c b/hw/xwin/winmonitors.c
new file mode 100644
index 000000000..63af803d0
--- /dev/null
+++ b/hw/xwin/winmonitors.c
@@ -0,0 +1,92 @@
+/*
+
+Copyright 1993, 1998 The Open Group
+Copyright (C) Colin Harrison 2005-2008
+
+Permission to use, copy, modify, distribute, and sell this software and its
+documentation for any purpose is hereby granted without fee, provided that
+the above copyright notice appear in all copies and that both that
+copyright notice and this permission notice appear in supporting
+documentation.
+
+The above copyright notice and this permission notice shall be included
+in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
+OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+IN NO EVENT SHALL THE OPEN GROUP BE LIABLE FOR ANY CLAIM, DAMAGES OR
+OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
+ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+OTHER DEALINGS IN THE SOFTWARE.
+
+Except as contained in this notice, the name of The Open Group shall
+not be used in advertising or otherwise to promote the sale, use or
+other dealings in this Software without prior written authorization
+from The Open Group.
+
+*/
+
+
+#include "win.h"
+#include "winmonitors.h"
+
+/*
+ * getMonitorInfo - callback function used to return information from the enumeration of monitors attached
+ */
+
+static
+wBOOL CALLBACK getMonitorInfo(HMONITOR hMonitor, HDC hdc, LPRECT rect, LPARAM _data)
+{
+ struct GetMonitorInfoData* data = (struct GetMonitorInfoData*)_data;
+ // only get data for monitor number specified in <data>
+ data->monitorNum++;
+ if (data->monitorNum == data->requestedMonitor)
+ {
+ data->bMonitorSpecifiedExists = TRUE;
+ data->monitorOffsetX = rect->left;
+ data->monitorOffsetY = rect->top;
+ data->monitorHeight = rect->bottom - rect->top;
+ data->monitorWidth = rect->right - rect->left;
+ return FALSE;
+ }
+ return TRUE;
+}
+
+typedef wBOOL (*ENUMDISPLAYMONITORSPROC)(HDC,LPCRECT,MONITORENUMPROC,LPARAM);
+ENUMDISPLAYMONITORSPROC _EnumDisplayMonitors;
+
+wBOOL CALLBACK getMonitorInfo(HMONITOR hMonitor, HDC hdc, LPRECT rect, LPARAM _data);
+
+Bool QueryMonitor(int index, struct GetMonitorInfoData *data)
+{
+ /* Load EnumDisplayMonitors from DLL */
+ HMODULE user32;
+ FARPROC func;
+ user32 = LoadLibrary("user32.dll");
+ if (user32 == NULL)
+ {
+ winW32Error(2, "Could not open user32.dll");
+ return FALSE;
+ }
+ func = GetProcAddress(user32, "EnumDisplayMonitors");
+ if (func == NULL)
+ {
+ winW32Error(2, "Could not resolve EnumDisplayMonitors: ");
+ return FALSE;
+ }
+ _EnumDisplayMonitors = (ENUMDISPLAYMONITORSPROC)func;
+
+ /* prepare data */
+ if (data == NULL)
+ return FALSE;
+ memset(data, 0, sizeof(*data));
+ data->requestedMonitor = index;
+
+ /* query information */
+ _EnumDisplayMonitors(NULL, NULL, getMonitorInfo, (LPARAM) data);
+
+ /* cleanup */
+ FreeLibrary(user32);
+ return TRUE;
+}
diff --git a/hw/xwin/winmonitors.h b/hw/xwin/winmonitors.h
new file mode 100644
index 000000000..180566b00
--- /dev/null
+++ b/hw/xwin/winmonitors.h
@@ -0,0 +1,14 @@
+
+/* data returned for monitor information */
+struct GetMonitorInfoData {
+ int requestedMonitor;
+ int monitorNum;
+ Bool bUserSpecifiedMonitor;
+ Bool bMonitorSpecifiedExists;
+ int monitorOffsetX;
+ int monitorOffsetY;
+ int monitorHeight;
+ int monitorWidth;
+};
+
+Bool QueryMonitor(int index, struct GetMonitorInfoData *data);
diff --git a/hw/xwin/winnativegdi.c b/hw/xwin/winnativegdi.c
index b8d2d351b..4d7afe898 100644
--- a/hw/xwin/winnativegdi.c
+++ b/hw/xwin/winnativegdi.c
@@ -92,6 +92,18 @@ winAllocateFBNativeGDI (ScreenPtr pScreen)
return TRUE;
}
+static void
+winFreeFBNativeGDI (ScreenPtr pScreen)
+{
+ FatalError ("winFreeFBNativeGDI\n");
+}
+
+
+static Bool
+winInitScreenNativeGDI(ScreenPtr pScreen)
+{
+ FatalError ("winInitScreenNativeGDI\n");
+}
/*
* We wrap whatever CloseScreen procedure was specified by fb;
@@ -289,28 +301,9 @@ winAdjustVideoModeNativeGDI (ScreenPtr pScreen)
break;
}
- /* GDI cannot change the screen depth */
- if (pScreenInfo->dwBPP == WIN_DEFAULT_BPP)
- {
- /* No -depth parameter passed, let the user know the depth being used */
- ErrorF ("winAdjustVideoModeNativeGDI - Using Windows display "
- "depth of %d bits per pixel, %d depth\n",
- (int) dwBPP, (int) pScreenInfo->dwDepth);
+ /* GDI cannot change the screen depth, so we'll use GDI's depth */
+ pScreenInfo->dwBPP = dwBPP;
- /* Use GDI's depth */
- pScreenInfo->dwBPP = dwBPP;
- }
- else if (dwBPP != pScreenInfo->dwBPP)
- {
- /* Warn user if GDI depth is different than -depth parameter */
- ErrorF ("winAdjustVideoModeNativeGDI - Command line bpp: %d, "\
- "using bpp: %d\n",
- (int) pScreenInfo->dwBPP, (int) dwBPP);
-
- /* We'll use GDI's depth */
- pScreenInfo->dwBPP = dwBPP;
- }
-
/* Release our DC */
ReleaseDC (NULL, hdc);
@@ -506,7 +499,9 @@ winSetEngineFunctionsNativeGDI (ScreenPtr pScreen)
/* Set our pointers */
pScreenPriv->pwinAllocateFB = winAllocateFBNativeGDI;
+ pScreenPriv->pwinFreeFB = winFreeFBNativeGDI;
pScreenPriv->pwinShadowUpdate = winShadowUpdateNativeGDI;
+ pScreenPriv->pwinInitScreen = winInitScreenNativeGDI;
pScreenPriv->pwinCloseScreen = winCloseScreenNativeGDI;
pScreenPriv->pwinInitVisuals = winInitVisualsNativeGDI;
pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModeNativeGDI;
diff --git a/hw/xwin/winpfbdd.c b/hw/xwin/winpfbdd.c
index 7859c6b19..c0bca71e3 100644
--- a/hw/xwin/winpfbdd.c
+++ b/hw/xwin/winpfbdd.c
@@ -233,6 +233,45 @@ winAllocateFBPrimaryDD (ScreenPtr pScreen)
return TRUE;
}
+static void
+winFreeFBPrimaryDD (ScreenPtr pScreen)
+{
+ winScreenPriv(pScreen);
+ winScreenInfo *pScreenInfo = pScreenPriv->pScreenInfo;
+
+ /* Free the offscreen surface, if there is one */
+ if (pScreenPriv->pddsOffscreen)
+ {
+ IDirectDrawSurface2_Unlock (pScreenPriv->pddsOffscreen, NULL);
+ IDirectDrawSurface2_Release (pScreenPriv->pddsOffscreen);
+ pScreenPriv->pddsOffscreen = NULL;
+ }
+
+ /* Release the primary surface, if there is one */
+ if (pScreenPriv->pddsPrimary)
+ {
+ IDirectDrawSurface2_Unlock (pScreenPriv->pddsPrimary, NULL);
+ IDirectDrawSurface2_Release (pScreenPriv->pddsPrimary);
+ pScreenPriv->pddsPrimary = NULL;
+ }
+
+ /* Free the DirectDraw object, if there is one */
+ if (pScreenPriv->pdd)
+ {
+ IDirectDraw2_RestoreDisplayMode (pScreenPriv->pdd);
+ IDirectDraw2_Release (pScreenPriv->pdd);
+ pScreenPriv->pdd = NULL;
+ }
+
+ /* Invalidate the ScreenInfo's fb pointer */
+ pScreenInfo->pfb = NULL;
+}
+
+static Bool
+winInitScreenPrimaryDD(ScreenPtr pScreen)
+{
+ return winAllocateFBPrimaryDD(pScreen);
+}
/*
* Call the wrapped CloseScreen function.
@@ -260,29 +299,7 @@ winCloseScreenPrimaryDD (int nIndex, ScreenPtr pScreen)
/* Delete the window property */
RemoveProp (pScreenPriv->hwndScreen, WIN_SCR_PROP);
- /* Free the offscreen surface, if there is one */
- if (pScreenPriv->pddsOffscreen)
- {
- IDirectDrawSurface2_Unlock (pScreenPriv->pddsOffscreen, NULL);
- IDirectDrawSurface2_Release (pScreenPriv->pddsOffscreen);
- pScreenPriv->pddsOffscreen = NULL;
- }
-
- /* Release the primary surface, if there is one */
- if (pScreenPriv->pddsPrimary)
- {
- IDirectDrawSurface2_Unlock (pScreenPriv->pddsPrimary, NULL);
- IDirectDrawSurface2_Release (pScreenPriv->pddsPrimary);
- pScreenPriv->pddsPrimary = NULL;
- }
-
- /* Free the DirectDraw object, if there is one */
- if (pScreenPriv->pdd)
- {
- IDirectDraw2_RestoreDisplayMode (pScreenPriv->pdd);
- IDirectDraw2_Release (pScreenPriv->pdd);
- pScreenPriv->pdd = NULL;
- }
+ winFreeFBPrimaryDD(pScreen);
/* Delete tray icon, if we have one */
if (!pScreenInfo->fNoTrayIcon)
@@ -305,9 +322,6 @@ winCloseScreenPrimaryDD (int nIndex, ScreenPtr pScreen)
/* Kill our screeninfo's pointer to the screen */
pScreenInfo->pScreen = NULL;
- /* Invalidate the ScreenInfo's fb pointer */
- pScreenInfo->pfb = NULL;
-
/* Free the screen privates for this screen */
free ((pointer) pScreenPriv);
@@ -422,33 +436,13 @@ winAdjustVideoModePrimaryDD (ScreenPtr pScreen)
dwBPP = GetDeviceCaps (hdc, BITSPIXEL);
/* DirectDraw can only change the depth in fullscreen mode */
- if (pScreenInfo->dwBPP == WIN_DEFAULT_BPP)
+ if (!(pScreenInfo->fFullScreen &&
+ (pScreenInfo->dwBPP != WIN_DEFAULT_BPP)))
{
- /* No -depth parameter passed, let the user know the depth being used */
- ErrorF ("winAdjustVideoModePrimaryDD - Using Windows display "
- "depth of %d bits per pixel\n", (int) dwBPP);
-
- /* Use GDI's depth */
+ /* Otherwise, We'll use GDI's depth */
pScreenInfo->dwBPP = dwBPP;
}
- else if (pScreenInfo->fFullScreen
- && pScreenInfo->dwBPP != dwBPP)
- {
- /* FullScreen, and GDI depth differs from -depth parameter */
- ErrorF ("winAdjustVideoModePrimaryDD - FullScreen, using command "
- "line depth: %d\n", (int) pScreenInfo->dwBPP);
- }
- else if (dwBPP != pScreenInfo->dwBPP)
- {
- /* Windowed, and GDI depth differs from -depth parameter */
- ErrorF ("winAdjustVideoModePrimaryDD - Windowed, command line "
- "depth: %d, using depth: %d\n",
- (int) pScreenInfo->dwBPP, (int) dwBPP);
- /* We'll use GDI's depth */
- pScreenInfo->dwBPP = dwBPP;
- }
-
/* Release our DC */
ReleaseDC (NULL, hdc);
@@ -653,8 +647,9 @@ winSetEngineFunctionsPrimaryDD (ScreenPtr pScreen)
/* Set our pointers */
pScreenPriv->pwinAllocateFB = winAllocateFBPrimaryDD;
- pScreenPriv->pwinShadowUpdate
- = (winShadowUpdateProcPtr) (void (*)(void))NoopDDA;
+ pScreenPriv->pwinFreeFB = winFreeFBPrimaryDD;
+ pScreenPriv->pwinShadowUpdate = (winShadowUpdateProcPtr) (void (*)(void))NoopDDA;
+ pScreenPriv->pwinInitScreen = winInitScreenPrimaryDD;
pScreenPriv->pwinCloseScreen = winCloseScreenPrimaryDD;
pScreenPriv->pwinInitVisuals = winInitVisualsPrimaryDD;
pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModePrimaryDD;
@@ -663,10 +658,17 @@ winSetEngineFunctionsPrimaryDD (ScreenPtr pScreen)
else
pScreenPriv->pwinCreateBoundingWindow = winCreateBoundingWindowWindowed;
pScreenPriv->pwinFinishScreenInit = winFinishScreenInitFB;
- pScreenPriv->pwinBltExposedRegions
- = (winBltExposedRegionsProcPtr) (void (*)(void))NoopDDA;
+ pScreenPriv->pwinBltExposedRegions = (winBltExposedRegionsProcPtr) (void (*)(void))NoopDDA;
pScreenPriv->pwinActivateApp = winActivateAppPrimaryDD;
+ pScreenPriv->pwinRedrawScreen = NULL;
+ pScreenPriv->pwinRealizeInstalledPalette = NULL;
+ pScreenPriv->pwinInstallColormap = NULL;
+ pScreenPriv->pwinStoreColors = NULL;
+ pScreenPriv->pwinCreateColormap = NULL;
+ pScreenPriv->pwinDestroyColormap = NULL;
pScreenPriv->pwinHotKeyAltTab = winHotKeyAltTabPrimaryDD;
+ pScreenPriv->pwinCreatePrimarySurface = (winCreatePrimarySurfaceProcPtr) (void (*)(void))NoopDDA;
+ pScreenPriv->pwinReleasePrimarySurface = (winReleasePrimarySurfaceProcPtr) (void (*)(void))NoopDDA;
#ifdef XWIN_MULTIWINDOW
pScreenPriv->pwinFinishCreateWindowsWindow =
(winFinishCreateWindowsWindowProcPtr) (void (*)(void))NoopDDA;
diff --git a/hw/xwin/winprocarg.c b/hw/xwin/winprocarg.c
index 1ce5c2dca..ddfe1f5b7 100644
--- a/hw/xwin/winprocarg.c
+++ b/hw/xwin/winprocarg.c
@@ -35,6 +35,7 @@ from The Open Group.
#include "win.h"
#include "winconfig.h"
#include "winmsg.h"
+#include "winmonitors.h"
/*
* References to external symbols
@@ -44,55 +45,6 @@ from The Open Group.
extern Bool g_fUnicodeClipboard;
extern Bool g_fClipboard;
#endif
-/* globals required by callback function for monitor information */
-struct GetMonitorInfoData {
- int requestedMonitor;
- int monitorNum;
- Bool bUserSpecifiedMonitor;
- Bool bMonitorSpecifiedExists;
- int monitorOffsetX;
- int monitorOffsetY;
- int monitorHeight;
- int monitorWidth;
-};
-
-typedef wBOOL (*ENUMDISPLAYMONITORSPROC)(HDC,LPCRECT,MONITORENUMPROC,LPARAM);
-ENUMDISPLAYMONITORSPROC _EnumDisplayMonitors;
-
-wBOOL CALLBACK getMonitorInfo(HMONITOR hMonitor, HDC hdc, LPRECT rect, LPARAM _data);
-
-static Bool QueryMonitor(int index, struct GetMonitorInfoData *data)
-{
- /* Load EnumDisplayMonitors from DLL */
- HMODULE user32;
- FARPROC func;
- user32 = LoadLibrary("user32.dll");
- if (user32 == NULL)
- {
- winW32Error(2, "Could not open user32.dll");
- return FALSE;
- }
- func = GetProcAddress(user32, "EnumDisplayMonitors");
- if (func == NULL)
- {
- winW32Error(2, "Could not resolve EnumDisplayMonitors: ");
- return FALSE;
- }
- _EnumDisplayMonitors = (ENUMDISPLAYMONITORSPROC)func;
-
- /* prepare data */
- if (data == NULL)
- return FALSE;
- memset(data, 0, sizeof(*data));
- data->requestedMonitor = index;
-
- /* query information */
- _EnumDisplayMonitors(NULL, NULL, getMonitorInfo, (LPARAM) data);
-
- /* cleanup */
- FreeLibrary(user32);
- return TRUE;
-}
/*
* Function prototypes
@@ -143,6 +95,7 @@ winInitializeScreenDefaults(void)
if (monitorResolution == 0)
monitorResolution = WIN_DEFAULT_DPI;
+ defaultScreenInfo.iMonitor = 1;
defaultScreenInfo.dwWidth = dwWidth;
defaultScreenInfo.dwHeight = dwHeight;
defaultScreenInfo.dwUserWidth = dwWidth;
@@ -171,11 +124,9 @@ winInitializeScreenDefaults(void)
#endif
defaultScreenInfo.fMultipleMonitors = FALSE;
defaultScreenInfo.fLessPointer = FALSE;
- defaultScreenInfo.fScrollbars = FALSE;
+ defaultScreenInfo.iResizeMode = notAllowed;
defaultScreenInfo.fNoTrayIcon = FALSE;
defaultScreenInfo.iE3BTimeout = WIN_E3B_OFF;
- defaultScreenInfo.dwWidth_mm = (dwWidth / WIN_DEFAULT_DPI) * 25.4;
- defaultScreenInfo.dwHeight_mm = (dwHeight / WIN_DEFAULT_DPI) * 25.4;
defaultScreenInfo.fUseWinKillKey = WIN_DEFAULT_WIN_KILL;
defaultScreenInfo.fUseUnixKillKey = WIN_DEFAULT_UNIX_KILL;
defaultScreenInfo.fIgnoreInput = FALSE;
@@ -368,6 +319,7 @@ ddxProcessArgument (int argc, char *argv[], int i)
iArgsProcessed = 3;
g_ScreenInfo[nScreenNum].fUserGaveHeightAndWidth = FALSE;
g_ScreenInfo[nScreenNum].fUserGavePosition = TRUE;
+ g_ScreenInfo[nScreenNum].iMonitor = iMonitor;
g_ScreenInfo[nScreenNum].dwWidth = data.monitorWidth;
g_ScreenInfo[nScreenNum].dwHeight = data.monitorHeight;
g_ScreenInfo[nScreenNum].dwUserWidth = data.monitorWidth;
@@ -420,6 +372,7 @@ ddxProcessArgument (int argc, char *argv[], int i)
"Querying monitors is not supported on NT4 and Win95\n");
} else if (data.bMonitorSpecifiedExists == TRUE)
{
+ g_ScreenInfo[nScreenNum].iMonitor = iMonitor;
g_ScreenInfo[nScreenNum].dwInitialX += data.monitorOffsetX;
g_ScreenInfo[nScreenNum].dwInitialY += data.monitorOffsetY;
}
@@ -449,6 +402,7 @@ ddxProcessArgument (int argc, char *argv[], int i)
{
winErrorFVerb (2, "ddxProcessArgument - screen - Found Valid ``@Monitor'' = %d arg\n", iMonitor);
g_ScreenInfo[nScreenNum].fUserGavePosition = TRUE;
+ g_ScreenInfo[nScreenNum].iMonitor = iMonitor;
g_ScreenInfo[nScreenNum].dwInitialX = data.monitorOffsetX;
g_ScreenInfo[nScreenNum].dwInitialY = data.monitorOffsetY;
}
@@ -500,17 +454,6 @@ ddxProcessArgument (int argc, char *argv[], int i)
g_ScreenInfo[nScreenNum].fUserGaveHeightAndWidth = FALSE;
}
- /* Calculate the screen width and height in millimeters */
- if (g_ScreenInfo[nScreenNum].fUserGaveHeightAndWidth)
- {
- g_ScreenInfo[nScreenNum].dwWidth_mm
- = (g_ScreenInfo[nScreenNum].dwWidth
- / monitorResolution) * 25.4;
- g_ScreenInfo[nScreenNum].dwHeight_mm
- = (g_ScreenInfo[nScreenNum].dwHeight
- / monitorResolution) * 25.4;
- }
-
/* Flag that this screen was explicity specified by the user */
g_ScreenInfo[nScreenNum].fExplicitScreen = TRUE;
@@ -717,12 +660,51 @@ ddxProcessArgument (int argc, char *argv[], int i)
*/
if (IS_OPTION ("-scrollbars"))
{
- screenInfoPtr->fScrollbars = TRUE;
+
+ screenInfoPtr->iResizeMode = resizeWithScrollbars;
/* Indicate that we have processed this argument */
return 1;
}
+ /*
+ * Look for the '-resize' argument
+ */
+ if (IS_OPTION ("-resize") || IS_OPTION ("-noresize") ||
+ (strncmp(argv[i], "-resize=",strlen("-resize=")) == 0))
+ {
+ winResizeMode mode;
+
+ if (IS_OPTION ("-resize"))
+ mode = resizeWithRandr;
+ else if (IS_OPTION ("-noresize"))
+ mode = notAllowed;
+ else if (strncmp(argv[i], "-resize=",strlen("-resize=")) == 0)
+ {
+ char *option = argv[i] + strlen("-resize=");
+ if (strcmp(option, "randr") == 0)
+ mode = resizeWithRandr;
+ else if (strcmp(option, "scrollbars") == 0)
+ mode = resizeWithScrollbars;
+ else if (strcmp(option, "none") == 0)
+ mode = notAllowed;
+ else
+ {
+ ErrorF ("ddxProcessArgument - resize - Invalid resize mode %s\n", option);
+ return 0;
+ }
+ }
+ else
+ {
+ ErrorF ("ddxProcessArgument - resize - Invalid resize option %s\n", argv[i]);
+ return 0;
+ }
+
+ screenInfoPtr->iResizeMode = mode;
+
+ /* Indicate that we have processed this argument */
+ return 1;
+ }
#ifdef XWIN_CLIPBOARD
/*
@@ -1233,24 +1215,3 @@ winLogVersionInfo (void)
ErrorF ("%s\n\n", BUILDERSTRING);
ErrorF ("Contact: %s\n", BUILDERADDR);
}
-
-/*
- * getMonitorInfo - callback function used to return information from the enumeration of monitors attached
- */
-
-wBOOL CALLBACK getMonitorInfo(HMONITOR hMonitor, HDC hdc, LPRECT rect, LPARAM _data)
-{
- struct GetMonitorInfoData* data = (struct GetMonitorInfoData*)_data;
- // only get data for monitor number specified in <data>
- data->monitorNum++;
- if (data->monitorNum == data->requestedMonitor)
- {
- data->bMonitorSpecifiedExists = TRUE;
- data->monitorOffsetX = rect->left;
- data->monitorOffsetY = rect->top;
- data->monitorHeight = rect->bottom - rect->top;
- data->monitorWidth = rect->right - rect->left;
- return FALSE;
- }
- return TRUE;
-}
diff --git a/hw/xwin/winrandr.c b/hw/xwin/winrandr.c
index 7b5b1359c..248404800 100644
--- a/hw/xwin/winrandr.c
+++ b/hw/xwin/winrandr.c
@@ -1,8 +1,9 @@
/*
*Copyright (C) 2001-2004 Harold L Hunt II All Rights Reserved.
+ *Copyright (C) 2009-2010 Jon TURNEY
*
*Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
+ *a copy of this software and associated documentation files (the
*"Software"), to deal in the Software without restriction, including
*without limitation the rights to use, copy, modify, merge, publish,
*distribute, sublicense, and/or sell copies of the Software, and to
@@ -20,101 +21,280 @@
*CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
*WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*
- *Except as contained in this notice, the name of Harold L Hunt II
+ *Except as contained in this notice, the name of the author(s)
*shall not be used in advertising or otherwise to promote the sale, use
*or other dealings in this Software without prior written authorization
- *from Harold L Hunt II.
+ *from the author(s)
*
* Authors: Harold L Hunt II
+ * Jon TURNEY
*/
#ifdef HAVE_XWIN_CONFIG_H
#include <xwin-config.h>
#endif
#include "win.h"
+#include "mivalidate.h" // for union _Validate used by windowstr.h
+
+#ifndef RANDR_12_INTERFACE
+#error X server must have RandR 1.2 interface
+#endif
/*
- * Local prototypes
+ * Answer queries about the RandR features supported.
*/
static Bool
-winRandRGetInfo (ScreenPtr pScreen, Rotation *pRotations);
+winRandRGetInfo (ScreenPtr pScreen, Rotation *pRotations)
+{
+ winDebug ("winRandRGetInfo ()\n");
-static Bool
-winRandRSetConfig (ScreenPtr pScreen,
- Rotation rotateKind,
- int rate,
- RRScreenSizePtr pSize);
+ /* Don't support rotations */
+ *pRotations = RR_Rotate_0;
-Bool
-winRandRInit (ScreenPtr pScreen);
+ /*
+ The screen doesn't have to be limited to the actual
+ monitor size (we can have scrollbars :-), so what is
+ the upper limit?
+ */
+ RRScreenSetSizeRange(pScreen, 0, 0, 4096, 4096);
+
+ return TRUE;
+}
/*
- * Answer queries about the RandR features supported.
+ Copied from the xfree86 DDX
+
+ Why can't this be in DIX?
+ Does union _Validate vary depending on DDX??
*/
+static void
+xf86SetRootClip (ScreenPtr pScreen, Bool enable)
+{
+ WindowPtr pWin = pScreen->root;
+ WindowPtr pChild;
+ Bool WasViewable = (Bool)(pWin->viewable);
+ Bool anyMarked = FALSE;
+ WindowPtr pLayerWin;
+ BoxRec box;
-static Bool
-winRandRGetInfo (ScreenPtr pScreen, Rotation *pRotations)
+ if (WasViewable)
+ {
+ for (pChild = pWin->firstChild; pChild; pChild = pChild->nextSib)
+ {
+ (void) (*pScreen->MarkOverlappedWindows)(pChild,
+ pChild,
+ &pLayerWin);
+ }
+ (*pScreen->MarkWindow) (pWin);
+ anyMarked = TRUE;
+ if (pWin->valdata)
+ {
+ if (HasBorder (pWin))
+ {
+ RegionPtr borderVisible;
+
+ borderVisible = REGION_CREATE(pScreen, NullBox, 1);
+ REGION_SUBTRACT(pScreen, borderVisible,
+ &pWin->borderClip, &pWin->winSize);
+ pWin->valdata->before.borderVisible = borderVisible;
+ }
+ pWin->valdata->before.resized = TRUE;
+ }
+ }
+
+ /*
+ * Use REGION_BREAK to avoid optimizations in ValidateTree
+ * that assume the root borderClip can't change well, normally
+ * it doesn't...)
+ */
+ if (enable)
+ {
+ box.x1 = 0;
+ box.y1 = 0;
+ box.x2 = pScreen->width;
+ box.y2 = pScreen->height;
+ REGION_INIT (pScreen, &pWin->winSize, &box, 1);
+ REGION_INIT (pScreen, &pWin->borderSize, &box, 1);
+ if (WasViewable)
+ REGION_RESET(pScreen, &pWin->borderClip, &box);
+ pWin->drawable.width = pScreen->width;
+ pWin->drawable.height = pScreen->height;
+ REGION_BREAK (pWin->drawable.pScreen, &pWin->clipList);
+ }
+ else
+ {
+ REGION_EMPTY(pScreen, &pWin->borderClip);
+ REGION_BREAK (pWin->drawable.pScreen, &pWin->clipList);
+ }
+
+ ResizeChildrenWinSize (pWin, 0, 0, 0, 0);
+
+ if (WasViewable)
+ {
+ if (pWin->firstChild)
+ {
+ anyMarked |= (*pScreen->MarkOverlappedWindows)(pWin->firstChild,
+ pWin->firstChild,
+ (WindowPtr *)NULL);
+ }
+ else
+ {
+ (*pScreen->MarkWindow) (pWin);
+ anyMarked = TRUE;
+ }
+
+
+ if (anyMarked)
+ (*pScreen->ValidateTree)(pWin, NullWindow, VTOther);
+ }
+
+ if (WasViewable)
+ {
+ if (anyMarked)
+ (*pScreen->HandleExposures)(pWin);
+ if (anyMarked && pScreen->PostValidateTree)
+ (*pScreen->PostValidateTree)(pWin, NullWindow, VTOther);
+ }
+ if (pWin->realized)
+ WindowsRestructured ();
+ FlushAllOutput ();
+}
+
+/*
+
+*/
+void
+winDoRandRScreenSetSize (ScreenPtr pScreen,
+ CARD16 width,
+ CARD16 height,
+ CARD32 mmWidth,
+ CARD32 mmHeight)
{
winScreenPriv(pScreen);
- winScreenInfo *pScreenInfo = pScreenPriv->pScreenInfo;
- int n;
- Rotation rotateKind;
- RRScreenSizePtr pSize;
+ winScreenInfo *pScreenInfo = pScreenPriv->pScreenInfo;
+ WindowPtr pRoot = pScreen->root;
- winDebug ("winRandRGetInfo ()\n");
+ // Prevent screen updates while we change things around
+ xf86SetRootClip(pScreen, FALSE);
- /* Don't support rotations, yet */
- *pRotations = RR_Rotate_0;
+ /* Update the screen size as requested */
+ pScreenInfo->dwWidth = width;
+ pScreenInfo->dwHeight = height;
- /* Bail if no depth has a visual associated with it */
- for (n = 0; n < pScreen->numDepths; n++)
- if (pScreen->allowedDepths[n].numVids)
- break;
- if (n == pScreen->numDepths)
- return FALSE;
+ /* Reallocate the framebuffer used by the drawing engine */
+ (*pScreenPriv->pwinFreeFB)(pScreen);
+ if (!(*pScreenPriv->pwinAllocateFB)(pScreen))
+ {
+ ErrorF ("winDoRandRScreenSetSize - Could not reallocate framebuffer\n");
+ }
- /* Only one allowed rotation for now */
- rotateKind = RR_Rotate_0;
+ pScreen->width = width;
+ pScreen->height = height;
+ pScreen->mmWidth = mmWidth;
+ pScreen->mmHeight = mmHeight;
- /*
- * Register supported sizes. This can be called many times, but
- * we only support one size for now.
- */
- pSize = RRRegisterSize (pScreen,
- pScreenInfo->dwWidth,
- pScreenInfo->dwHeight,
- pScreenInfo->dwWidth_mm,
- pScreenInfo->dwHeight_mm);
-
- /* Tell RandR what the current config is */
- RRSetCurrentConfig (pScreen,
- rotateKind,
- 0, /* refresh rate, not needed */
- pSize);
-
- return TRUE;
-}
+ /* Update the screen pixmap to point to the new framebuffer */
+ winUpdateFBPointer(pScreen, pScreenInfo->pfb);
+
+ // pScreen->devPrivate == pScreen->GetScreenPixmap(screen) ?
+ // resize the root window
+ //pScreen->ResizeWindow(pRoot, 0, 0, width, height, NULL);
+ // does this emit a ConfigureNotify??
+ // Restore the ability to update screen, now with new dimensions
+ xf86SetRootClip(pScreen, TRUE);
+
+ // and arrange for it to be repainted
+ miPaintWindow(pRoot, &pRoot->borderClip, PW_BACKGROUND);
+
+ /* Indicate that a screen size change took place */
+ RRScreenSizeNotify(pScreen);
+}
/*
- * Respond to resize/rotate request from either X Server or X client app
+ * Respond to resize request
*/
-
-static Bool
-winRandRSetConfig (ScreenPtr pScreen,
- Rotation rotateKind,
- int rate,
- RRScreenSizePtr pSize)
+static
+Bool
+winRandRScreenSetSize (ScreenPtr pScreen,
+ CARD16 width,
+ CARD16 height,
+ CARD16 pixWidth,
+ CARD16 pixHeight,
+ CARD32 mmWidth,
+ CARD32 mmHeight)
{
- winDebug ("winRandRSetConfig ()\n");
+ winScreenPriv(pScreen);
+ winScreenInfo *pScreenInfo = pScreenPriv->pScreenInfo;
+
+ winDebug ("winRandRScreenSetSize ()\n");
+
+ /*
+ It doesn't currently make sense to allow resize in fullscreen mode
+ (we'd actually have to list the supported resolutions)
+ */
+ if (pScreenInfo->fFullScreen)
+ {
+ ErrorF ("winRandRScreenSetSize - resize not supported in fullscreen mode\n");
+ return FALSE;
+ }
+
+ /*
+ Client resize requests aren't allowed in rootless modes, even if
+ the X screen is monitor or virtual desktop size, we'd need to
+ resize the native display size
+ */
+ if (FALSE
+#ifdef XWIN_MULTIWINDOWEXTWM
+ || pScreenInfo->fMWExtWM
+#endif
+ || pScreenInfo->fRootless
+#ifdef XWIN_MULTIWINDOW
+ || pScreenInfo->fMultiWindow
+#endif
+ )
+ {
+ ErrorF ("winRandRScreenSetSize - resize not supported in rootless modes\n");
+ return FALSE;
+ }
+
+ winDoRandRScreenSetSize(pScreen, width, height, mmWidth, mmHeight);
+
+ /* Cause the native window for the screen to resize itself */
+ {
+ DWORD dwStyle, dwExStyle;
+ RECT rcClient;
+
+ rcClient.left = 0;
+ rcClient.top = 0;
+ rcClient.right = width;
+ rcClient.bottom = height;
+
+ ErrorF ("winRandRScreenSetSize new client area w: %d h: %d\n", width, height);
+
+ /* Get the Windows window style and extended style */
+ dwExStyle = GetWindowLongPtr(pScreenPriv->hwndScreen, GWL_EXSTYLE);
+ dwStyle = GetWindowLongPtr(pScreenPriv->hwndScreen, GWL_STYLE);
+
+ /*
+ * Calculate the window size needed for the given client area
+ * adjusting for any decorations it will have
+ */
+ AdjustWindowRectEx(&rcClient, dwStyle, FALSE, dwExStyle);
+
+ ErrorF ("winRandRScreenSetSize new window area w: %ld h: %ld\n", rcClient.right-rcClient.left, rcClient.bottom-rcClient.top);
+
+ SetWindowPos(pScreenPriv->hwndScreen, NULL,
+ 0, 0, rcClient.right-rcClient.left, rcClient.bottom-rcClient.top,
+ SWP_NOZORDER | SWP_NOMOVE);
+ }
return TRUE;
}
-
/*
* Initialize the RandR layer.
*/
@@ -122,8 +302,7 @@ winRandRSetConfig (ScreenPtr pScreen,
Bool
winRandRInit (ScreenPtr pScreen)
{
- rrScrPrivPtr pRRScrPriv;
-
+ rrScrPrivPtr pRRScrPriv;
winDebug ("winRandRInit ()\n");
if (!RRScreenInit (pScreen))
@@ -135,7 +314,10 @@ winRandRInit (ScreenPtr pScreen)
/* Set some RandR function pointers */
pRRScrPriv = rrGetScrPriv (pScreen);
pRRScrPriv->rrGetInfo = winRandRGetInfo;
- pRRScrPriv->rrSetConfig = winRandRSetConfig;
+ pRRScrPriv->rrSetConfig = NULL;
+ pRRScrPriv->rrScreenSetSize = winRandRScreenSetSize;
+ pRRScrPriv->rrCrtcSet = NULL;
+ pRRScrPriv->rrCrtcSetGamma = NULL;
return TRUE;
}
diff --git a/hw/xwin/winscrinit.c b/hw/xwin/winscrinit.c
index 21036f46c..691237e6f 100644
--- a/hw/xwin/winscrinit.c
+++ b/hw/xwin/winscrinit.c
@@ -69,10 +69,6 @@ winMWExtWMProcs = {
* Prototypes
*/
-Bool
-winRandRInit (ScreenPtr pScreen);
-
-
/*
* Local functions
*/
@@ -95,6 +91,7 @@ winScreenInit (int index,
winScreenInfoPtr pScreenInfo = &g_ScreenInfo[index];
winPrivScreenPtr pScreenPriv;
HDC hdc;
+ DWORD dwInitialBPP;
#if CYGDEBUG || YES
winDebug ("winScreenInit - dwWidth: %ld dwHeight: %ld\n",
@@ -130,13 +127,30 @@ winScreenInit (int index,
return FALSE;
}
- /* Adjust the video mode for our engine type */
+ /* Horribly misnamed function: Allow engine to adjust BPP for screen */
+ dwInitialBPP = pScreenInfo->dwBPP;
+
if (!(*pScreenPriv->pwinAdjustVideoMode) (pScreen))
{
ErrorF ("winScreenInit - winAdjustVideoMode () failed\n");
return FALSE;
}
+ if (dwInitialBPP == WIN_DEFAULT_BPP)
+ {
+ /* No -depth parameter was passed, let the user know the depth being used */
+ ErrorF ("winScreenInit - Using Windows display depth of %d bits per pixel\n", (int) pScreenInfo->dwBPP);
+ }
+ else if (dwInitialBPP != pScreenInfo->dwBPP)
+ {
+ /* Warn user if engine forced a depth different to -depth parameter */
+ ErrorF ("winScreenInit - Command line depth of %d bpp overidden by engine, using %d bpp\n", (int) dwInitialBPP, (int) pScreenInfo->dwBPP);
+ }
+ else
+ {
+ ErrorF ("winScreenInit - Using command line depth of %d bpp\n", (int) pScreenInfo->dwBPP);
+ }
+
/* Check for supported display depth */
if (!(WIN_SUPPORTED_BPPS & (1 << (pScreenInfo->dwBPP - 1))))
{
@@ -155,13 +169,20 @@ winScreenInit (int index,
* Check that all monitors have the same display depth if we are using
* multiple monitors
*/
- if (pScreenInfo->fMultipleMonitors
+ if (pScreenInfo->fMultipleMonitors
&& !GetSystemMetrics (SM_SAMEDISPLAYFORMAT))
{
ErrorF ("winScreenInit - Monitors do not all have same pixel format / "
- "display depth.\n"
- "Using primary display only.\n");
- pScreenInfo->fMultipleMonitors = FALSE;
+ "display depth.\n");
+ if (pScreenInfo->dwEngine == WIN_SERVER_SHADOW_GDI)
+ {
+ ErrorF ("winScreenInit - Performance may suffer off primary display.\n");
+ }
+ else
+ {
+ ErrorF ("winScreenInit - Using primary display only.\n");
+ pScreenInfo->fMultipleMonitors = FALSE;
+ }
}
/* Create display window */
@@ -175,13 +196,9 @@ winScreenInit (int index,
/* Get a device context */
hdc = GetDC (pScreenPriv->hwndScreen);
- /* Store the initial height, width, and depth of the display */
/* Are we using multiple monitors? */
if (pScreenInfo->fMultipleMonitors)
{
- pScreenPriv->dwLastWindowsWidth = GetSystemMetrics (SM_CXVIRTUALSCREEN);
- pScreenPriv->dwLastWindowsHeight = GetSystemMetrics (SM_CYVIRTUALSCREEN);
-
/*
* In this case, some of the defaults set in
* winInitializeScreenDefaults() are not correct ...
@@ -190,30 +207,14 @@ winScreenInit (int index,
{
pScreenInfo->dwWidth = GetSystemMetrics (SM_CXVIRTUALSCREEN);
pScreenInfo->dwHeight = GetSystemMetrics (SM_CYVIRTUALSCREEN);
- pScreenInfo->dwWidth_mm = (pScreenInfo->dwWidth /
- WIN_DEFAULT_DPI) * 25.4;
- pScreenInfo->dwHeight_mm = (pScreenInfo->dwHeight /
- WIN_DEFAULT_DPI) * 25.4;
}
}
- else
- {
- pScreenPriv->dwLastWindowsWidth = GetSystemMetrics (SM_CXSCREEN);
- pScreenPriv->dwLastWindowsHeight = GetSystemMetrics (SM_CYSCREEN);
- }
-
- /* Save the original bits per pixel */
- pScreenPriv->dwLastWindowsBitsPixel = GetDeviceCaps (hdc, BITSPIXEL);
/* Release the device context */
ReleaseDC (pScreenPriv->hwndScreen, hdc);
/* Clear the visuals list */
miClearVisualTypes ();
-
- /* Set the padded screen width */
- pScreenInfo->dwPaddedWidth = PixmapBytePad (pScreenInfo->dwWidth,
- pScreenInfo->dwBPP);
/* Call the engine dependent screen initialization procedure */
if (!((*pScreenPriv->pwinFinishScreenInit) (index, pScreen, argc, argv)))
@@ -279,14 +280,15 @@ winFinishScreenInitFB (int index,
#endif
/* Create framebuffer */
- if (!(*pScreenPriv->pwinAllocateFB) (pScreen))
+ if (!(*pScreenPriv->pwinInitScreen) (pScreen))
{
ErrorF ("winFinishScreenInitFB - Could not allocate framebuffer\n");
return FALSE;
}
/*
- * Grab the number of bits that are used to represent color in each pixel.
+ * Calculate the number of bits that are used to represent color in each pixel,
+ * the color depth for the screen
*/
if (pScreenInfo->dwBPP == 8)
pScreenInfo->dwDepth = 8;
@@ -294,7 +296,7 @@ winFinishScreenInitFB (int index,
pScreenInfo->dwDepth = winCountBits (pScreenPriv->dwRedMask)
+ winCountBits (pScreenPriv->dwGreenMask)
+ winCountBits (pScreenPriv->dwBlueMask);
-
+
winErrorFVerb (2, "winFinishScreenInitFB - Masks: %08x %08x %08x\n",
(unsigned int) pScreenPriv->dwRedMask,
(unsigned int) pScreenPriv->dwGreenMask,
diff --git a/hw/xwin/winshaddd.c b/hw/xwin/winshaddd.c
index 4e284b9c1..00d7a379f 100644
--- a/hw/xwin/winshaddd.c
+++ b/hw/xwin/winshaddd.c
@@ -239,9 +239,6 @@ winAllocateFBShadowDD (ScreenPtr pScreen)
winDebug ("winAllocateFBShadowDD - Created a clipper\n");
#endif
- /* Get a device context for the screen */
- pScreenPriv->hdcScreen = GetDC (pScreenPriv->hwndScreen);
-
/* Attach the clipper to our display window */
ddrval = IDirectDrawClipper_SetHWnd (pScreenPriv->pddcPrimary,
0,
@@ -503,6 +500,48 @@ winAllocateFBShadowDD (ScreenPtr pScreen)
return TRUE;
}
+static void
+winFreeFBShadowDD (ScreenPtr pScreen)
+{
+ winScreenPriv(pScreen);
+ winScreenInfo *pScreenInfo = pScreenPriv->pScreenInfo;
+
+ /* Free the shadow surface, if there is one */
+ if (pScreenPriv->pddsShadow)
+ {
+ IDirectDrawSurface2_Unlock (pScreenPriv->pddsShadow, NULL);
+ IDirectDrawSurface2_Release (pScreenPriv->pddsShadow);
+ pScreenPriv->pddsShadow = NULL;
+ }
+
+ /* Detach the clipper from the primary surface and release the primary surface, if there is one */
+ winReleasePrimarySurfaceShadowDD(pScreen);
+
+ /* Release the clipper object */
+ if (pScreenPriv->pddcPrimary)
+ {
+ IDirectDrawClipper_Release (pScreenPriv->pddcPrimary);
+ pScreenPriv->pddcPrimary = NULL;
+ }
+
+ /* Free the DirectDraw2 object, if there is one */
+ if (pScreenPriv->pdd2)
+ {
+ IDirectDraw2_RestoreDisplayMode (pScreenPriv->pdd2);
+ IDirectDraw2_Release (pScreenPriv->pdd2);
+ pScreenPriv->pdd2 = NULL;
+ }
+
+ /* Free the DirectDraw object, if there is one */
+ if (pScreenPriv->pdd)
+ {
+ IDirectDraw_Release (pScreenPriv->pdd);
+ pScreenPriv->pdd = NULL;
+ }
+
+ /* Invalidate the ScreenInfo's fb pointer */
+ pScreenInfo->pfb = NULL;
+}
/*
* Transfer the damaged regions of the shadow framebuffer to the display.
@@ -529,6 +568,10 @@ winShadowUpdateDD (ScreenPtr pScreen,
if ((!pScreenPriv->fActive && pScreenInfo->fFullScreen)
|| pScreenPriv->fBadDepth) return;
+ /* Return immediately if we didn't get needed surfaces */
+ if (!pScreenPriv->pddsPrimary || !pScreenPriv->pddsShadow)
+ return;
+
/* Get the origin of the window in the screen coords */
ptOrigin.x = pScreenInfo->dwXOffset;
ptOrigin.y = pScreenInfo->dwYOffset;
@@ -647,25 +690,20 @@ winShadowUpdateDD (ScreenPtr pScreen,
"%s file to " BUILDERADDR "\n", g_pszLogFile);
/* Location of shadow framebuffer has changed */
- pScreenInfo->pfb = pScreenPriv->pddsdShadow->lpSurface;
-
- /* Update the screen pixmap */
- if (!(*pScreen->ModifyPixmapHeader)(pScreen->devPrivate,
- pScreen->width,
- pScreen->height,
- pScreen->rootDepth,
- BitsPerPixel (pScreen->rootDepth),
- PixmapBytePad (pScreenInfo->dwStride,
- pScreenInfo->dwBPP),
- pScreenInfo->pfb))
- {
- ErrorF ("winShadowUpdateDD - Bits changed, could not "
- "notify fb.\n");
- return;
- }
+ winUpdateFBPointer(pScreen, pScreenPriv->pddsdShadow->lpSurface);
}
}
+static Bool
+winInitScreenShadowDD (ScreenPtr pScreen)
+{
+ winScreenPriv(pScreen);
+
+ /* Get a device context for the screen */
+ pScreenPriv->hdcScreen = GetDC (pScreenPriv->hwndScreen);
+
+ return winAllocateFBShadowDD(pScreen);
+}
/*
* Call the wrapped CloseScreen function.
@@ -692,58 +730,18 @@ winCloseScreenShadowDD (int nIndex, ScreenPtr pScreen)
WIN_UNWRAP(CloseScreen);
fReturn = (*pScreen->CloseScreen) (nIndex, pScreen);
+ winFreeFBShadowDD(pScreen);
+
/* Free the screen DC */
ReleaseDC (pScreenPriv->hwndScreen, pScreenPriv->hdcScreen);
/* Delete the window property */
RemoveProp (pScreenPriv->hwndScreen, WIN_SCR_PROP);
- /* Free the shadow surface, if there is one */
- if (pScreenPriv->pddsShadow)
- {
- IDirectDrawSurface2_Unlock (pScreenPriv->pddsShadow, NULL);
- IDirectDrawSurface2_Release (pScreenPriv->pddsShadow);
- pScreenPriv->pddsShadow = NULL;
- }
-
- /* Detach the clipper from the primary surface and release the clipper. */
- if (pScreenPriv->pddcPrimary)
- {
- /* Detach the clipper */
- IDirectDrawSurface2_SetClipper (pScreenPriv->pddsPrimary,
- NULL);
-
- /* Release the clipper object */
- IDirectDrawClipper_Release (pScreenPriv->pddcPrimary);
- pScreenPriv->pddcPrimary = NULL;
- }
-
- /* Release the primary surface, if there is one */
- if (pScreenPriv->pddsPrimary)
- {
- IDirectDrawSurface2_Release (pScreenPriv->pddsPrimary);
- pScreenPriv->pddsPrimary = NULL;
- }
-
- /* Free the DirectDraw2 object, if there is one */
- if (pScreenPriv->pdd2)
- {
- IDirectDraw2_RestoreDisplayMode (pScreenPriv->pdd2);
- IDirectDraw2_Release (pScreenPriv->pdd2);
- pScreenPriv->pdd2 = NULL;
- }
-
- /* Free the DirectDraw object, if there is one */
- if (pScreenPriv->pdd)
- {
- IDirectDraw_Release (pScreenPriv->pdd);
- pScreenPriv->pdd = NULL;
- }
-
/* Delete tray icon, if we have one */
if (!pScreenInfo->fNoTrayIcon)
winDeleteNotifyIcon (pScreenPriv);
-
+
/* Free the exit confirmation dialog box, if it exists */
if (g_hDlgExit != NULL)
{
@@ -766,9 +764,6 @@ winCloseScreenShadowDD (int nIndex, ScreenPtr pScreen)
/* Kill our screeninfo's pointer to the screen */
pScreenInfo->pScreen = NULL;
- /* Invalidate the ScreenInfo's fb pointer */
- pScreenInfo->pfb = NULL;
-
/* Free the screen privates for this screen */
free ((pointer) pScreenPriv);
@@ -909,43 +904,12 @@ winAdjustVideoModeShadowDD (ScreenPtr pScreen)
dwBPP = GetDeviceCaps (hdc, BITSPIXEL);
/* DirectDraw can only change the depth in fullscreen mode */
- if (pScreenInfo->dwBPP == WIN_DEFAULT_BPP)
+ if (!(pScreenInfo->fFullScreen &&
+ (pScreenInfo->dwBPP != WIN_DEFAULT_BPP)))
{
- /* No -depth parameter passed, let the user know the depth being used */
- ErrorF ("winAdjustVideoModeShadowDD - Using Windows display "
- "depth of %d bits per pixel\n", (int) dwBPP);
-
- /* Use GDI's depth */
+ /* Otherwise, We'll use GDI's depth */
pScreenInfo->dwBPP = dwBPP;
}
- else if (pScreenInfo->fFullScreen
- && pScreenInfo->dwBPP != dwBPP)
- {
- /* FullScreen, and GDI depth differs from -depth parameter */
- ErrorF ("winAdjustVideoModeShadowDD - FullScreen, using command line "
- "bpp: %d\n", (int) pScreenInfo->dwBPP);
- }
- else if (dwBPP != pScreenInfo->dwBPP)
- {
- /* Windowed, and GDI depth differs from -depth parameter */
- ErrorF ("winAdjustVideoModeShadowDD - Windowed, command line bpp: "
- "%d, using bpp: %d\n", (int) pScreenInfo->dwBPP, (int) dwBPP);
-
- /* We'll use GDI's depth */
- pScreenInfo->dwBPP = dwBPP;
- }
-
- /* See if the shadow bitmap will be larger than the DIB size limit */
- if (pScreenInfo->dwWidth * pScreenInfo->dwHeight * pScreenInfo->dwBPP
- >= WIN_DIB_MAXIMUM_SIZE)
- {
- ErrorF ("winAdjustVideoModeShadowDD - Requested DirectDraw surface "
- "will be larger than %d MB. The surface may fail to be "
- "allocated on Windows 95, 98, or Me, due to a %d MB limit in "
- "DIB size. This limit does not apply to Windows NT/2000, and "
- "this message may be ignored on those platforms.\n",
- WIN_DIB_MAXIMUM_SIZE_MB, WIN_DIB_MAXIMUM_SIZE_MB);
- }
/* Release our DC */
ReleaseDC (NULL, hdc);
@@ -1370,7 +1334,9 @@ winSetEngineFunctionsShadowDD (ScreenPtr pScreen)
/* Set our pointers */
pScreenPriv->pwinAllocateFB = winAllocateFBShadowDD;
+ pScreenPriv->pwinFreeFB = winFreeFBShadowDD;
pScreenPriv->pwinShadowUpdate = winShadowUpdateDD;
+ pScreenPriv->pwinInitScreen = winInitScreenShadowDD;
pScreenPriv->pwinCloseScreen = winCloseScreenShadowDD;
pScreenPriv->pwinInitVisuals = winInitVisualsShadowDD;
pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModeShadowDD;
diff --git a/hw/xwin/winshadddnl.c b/hw/xwin/winshadddnl.c
index 82fe4be36..0a0b4ae13 100644
--- a/hw/xwin/winshadddnl.c
+++ b/hw/xwin/winshadddnl.c
@@ -237,6 +237,10 @@ winAllocateFBShadowDDNL (ScreenPtr pScreen)
pScreenInfo->dwWidth, pScreenInfo->dwHeight, pScreenInfo->dwDepth);
#endif
+ /* Set the padded screen width */
+ pScreenInfo->dwPaddedWidth = PixmapBytePad (pScreenInfo->dwWidth,
+ pScreenInfo->dwBPP);
+
/* Allocate memory for our shadow surface */
lpSurface = malloc (pScreenInfo->dwPaddedWidth * pScreenInfo->dwHeight);
if (lpSurface == NULL)
@@ -266,9 +270,6 @@ winAllocateFBShadowDDNL (ScreenPtr pScreen)
winDebug ("winAllocateFBShadowDDNL - Created a clipper\n");
#endif
- /* Get a device context for the screen */
- pScreenPriv->hdcScreen = GetDC (pScreenPriv->hwndScreen);
-
/* Attach the clipper to our display window */
ddrval = IDirectDrawClipper_SetHWnd (pScreenPriv->pddcPrimary,
0,
@@ -530,6 +531,49 @@ winAllocateFBShadowDDNL (ScreenPtr pScreen)
return TRUE;
}
+static void
+winFreeFBShadowDDNL(ScreenPtr pScreen)
+{
+ winScreenPriv(pScreen);
+ winScreenInfo *pScreenInfo = pScreenPriv->pScreenInfo;
+
+ /* Free the shadow surface, if there is one */
+ if (pScreenPriv->pddsShadow4)
+ {
+ IDirectDrawSurface4_Release (pScreenPriv->pddsShadow4);
+ free (pScreenInfo->pfb);
+ pScreenInfo->pfb = NULL;
+ pScreenPriv->pddsShadow4 = NULL;
+ }
+
+ /* Detach the clipper from the primary surface and release the primary surface, if there is one */
+ winReleasePrimarySurfaceShadowDDNL(pScreen);
+
+ /* Release the clipper object */
+ if (pScreenPriv->pddcPrimary)
+ {
+ IDirectDrawClipper_Release (pScreenPriv->pddcPrimary);
+ pScreenPriv->pddcPrimary = NULL;
+ }
+
+ /* Free the DirectDraw4 object, if there is one */
+ if (pScreenPriv->pdd4)
+ {
+ IDirectDraw4_RestoreDisplayMode (pScreenPriv->pdd4);
+ IDirectDraw4_Release (pScreenPriv->pdd4);
+ pScreenPriv->pdd4 = NULL;
+ }
+
+ /* Free the DirectDraw object, if there is one */
+ if (pScreenPriv->pdd)
+ {
+ IDirectDraw_Release (pScreenPriv->pdd);
+ pScreenPriv->pdd = NULL;
+ }
+
+ /* Invalidate the ScreenInfo's fb pointer */
+ pScreenInfo->pfb = NULL;
+}
#if defined(XWIN_MULTIWINDOW) || defined(XWIN_MULTIWINDOWEXTWM)
/*
@@ -605,6 +649,10 @@ winShadowUpdateDDNL (ScreenPtr pScreen,
if ((!pScreenPriv->fActive && pScreenInfo->fFullScreen)
|| pScreenPriv->fBadDepth) return;
+ /* Return immediately if we didn't get needed surfaces */
+ if (!pScreenPriv->pddsPrimary4 || !pScreenPriv->pddsShadow4)
+ return;
+
/* Get the origin of the window in the screen coords */
ptOrigin.x = pScreenInfo->dwXOffset;
ptOrigin.y = pScreenInfo->dwYOffset;
@@ -720,6 +768,16 @@ winShadowUpdateDDNL (ScreenPtr pScreen,
}
}
+static Bool
+winInitScreenShadowDDNL(ScreenPtr pScreen)
+{
+ winScreenPriv(pScreen);
+
+ /* Get a device context for the screen */
+ pScreenPriv->hdcScreen = GetDC (pScreenPriv->hwndScreen);
+
+ return winAllocateFBShadowDDNL(pScreen);
+}
/*
* Call the wrapped CloseScreen function.
@@ -746,55 +804,14 @@ winCloseScreenShadowDDNL (int nIndex, ScreenPtr pScreen)
WIN_UNWRAP(CloseScreen);
fReturn = (*pScreen->CloseScreen) (nIndex, pScreen);
+ winFreeFBShadowDDNL(pScreen);
+
/* Free the screen DC */
ReleaseDC (pScreenPriv->hwndScreen, pScreenPriv->hdcScreen);
/* Delete the window property */
RemoveProp (pScreenPriv->hwndScreen, WIN_SCR_PROP);
- /* Free the shadow surface, if there is one */
- if (pScreenPriv->pddsShadow4)
- {
- IDirectDrawSurface4_Release (pScreenPriv->pddsShadow4);
- free (pScreenInfo->pfb);
- pScreenInfo->pfb = NULL;
- pScreenPriv->pddsShadow4 = NULL;
- }
-
- /* Detach the clipper from the primary surface and release the clipper. */
- if (pScreenPriv->pddcPrimary)
- {
- /* Detach the clipper */
- IDirectDrawSurface4_SetClipper (pScreenPriv->pddsPrimary4,
- NULL);
-
- /* Release the clipper object */
- IDirectDrawClipper_Release (pScreenPriv->pddcPrimary);
- pScreenPriv->pddcPrimary = NULL;
- }
-
- /* Release the primary surface, if there is one */
- if (pScreenPriv->pddsPrimary4)
- {
- IDirectDrawSurface4_Release (pScreenPriv->pddsPrimary4);
- pScreenPriv->pddsPrimary4 = NULL;
- }
-
- /* Free the DirectDraw4 object, if there is one */
- if (pScreenPriv->pdd4)
- {
- IDirectDraw4_RestoreDisplayMode (pScreenPriv->pdd4);
- IDirectDraw4_Release (pScreenPriv->pdd4);
- pScreenPriv->pdd4 = NULL;
- }
-
- /* Free the DirectDraw object, if there is one */
- if (pScreenPriv->pdd)
- {
- IDirectDraw_Release (pScreenPriv->pdd);
- pScreenPriv->pdd = NULL;
- }
-
/* Delete tray icon, if we have one */
if (!pScreenInfo->fNoTrayIcon)
winDeleteNotifyIcon (pScreenPriv);
@@ -821,9 +838,6 @@ winCloseScreenShadowDDNL (int nIndex, ScreenPtr pScreen)
/* Kill our screeninfo's pointer to the screen */
pScreenInfo->pScreen = NULL;
- /* Invalidate the ScreenInfo's fb pointer */
- pScreenInfo->pfb = NULL;
-
/* Free the screen privates for this screen */
free ((pointer) pScreenPriv);
@@ -964,45 +978,13 @@ winAdjustVideoModeShadowDDNL (ScreenPtr pScreen)
dwBPP = GetDeviceCaps (hdc, BITSPIXEL);
/* DirectDraw can only change the depth in fullscreen mode */
- if (pScreenInfo->dwBPP == WIN_DEFAULT_BPP)
+ if (!(pScreenInfo->fFullScreen &&
+ (pScreenInfo->dwBPP != WIN_DEFAULT_BPP)))
{
- /* No -depth parameter passed, let the user know the depth being used */
- winErrorFVerb (2, "winAdjustVideoModeShadowDDNL - Using Windows display "
- "depth of %d bits per pixel\n", (int) dwBPP);
-
- /* Use GDI's depth */
+ /* Otherwise, We'll use GDI's depth */
pScreenInfo->dwBPP = dwBPP;
}
- else if (pScreenInfo->fFullScreen
- && pScreenInfo->dwBPP != dwBPP)
- {
- /* FullScreen, and GDI depth differs from -depth parameter */
- winErrorFVerb (2, "winAdjustVideoModeShadowDDNL - FullScreen, using command "
- "line bpp: %d\n", (int) pScreenInfo->dwBPP);
- }
- else if (dwBPP != pScreenInfo->dwBPP)
- {
- /* Windowed, and GDI depth differs from -depth parameter */
- winErrorFVerb (2, "winAdjustVideoModeShadowDDNL - Windowed, command line "
- "bpp: %d, using bpp: %d\n",
- (int) pScreenInfo->dwBPP, (int) dwBPP);
- /* We'll use GDI's depth */
- pScreenInfo->dwBPP = dwBPP;
- }
-
- /* See if the shadow bitmap will be larger than the DIB size limit */
- if (pScreenInfo->dwWidth * pScreenInfo->dwHeight * pScreenInfo->dwBPP
- >= WIN_DIB_MAXIMUM_SIZE)
- {
- winErrorFVerb (1, "winAdjustVideoModeShadowDDNL - Requested DirectDraw surface "
- "will be larger than %d MB. The surface may fail to be "
- "allocated on Windows 95, 98, or Me, due to a %d MB limit in "
- "DIB size. This limit does not apply to Windows NT/2000, and "
- "this message may be ignored on those platforms.\n",
- WIN_DIB_MAXIMUM_SIZE_MB, WIN_DIB_MAXIMUM_SIZE_MB);
- }
-
/* Release our DC */
ReleaseDC (NULL, hdc);
@@ -1382,7 +1364,9 @@ winSetEngineFunctionsShadowDDNL (ScreenPtr pScreen)
/* Set our pointers */
pScreenPriv->pwinAllocateFB = winAllocateFBShadowDDNL;
+ pScreenPriv->pwinFreeFB = winFreeFBShadowDDNL;
pScreenPriv->pwinShadowUpdate = winShadowUpdateDDNL;
+ pScreenPriv->pwinInitScreen = winInitScreenShadowDDNL;
pScreenPriv->pwinCloseScreen = winCloseScreenShadowDDNL;
pScreenPriv->pwinInitVisuals = winInitVisualsShadowDDNL;
pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModeShadowDDNL;
diff --git a/hw/xwin/winshadgdi.c b/hw/xwin/winshadgdi.c
index 4971851e5..499037656 100644
--- a/hw/xwin/winshadgdi.c
+++ b/hw/xwin/winshadgdi.c
@@ -338,37 +338,20 @@ winAllocateFBShadowGDI (ScreenPtr pScreen)
{
winScreenPriv(pScreen);
winScreenInfo *pScreenInfo = pScreenPriv->pScreenInfo;
- BITMAPINFOHEADER *pbmih = NULL;
DIBSECTION dibsection;
Bool fReturn = TRUE;
- /* Get device contexts for the screen and shadow bitmap */
- pScreenPriv->hdcScreen = GetDC (pScreenPriv->hwndScreen);
- pScreenPriv->hdcShadow = CreateCompatibleDC (pScreenPriv->hdcScreen);
-
- /* Allocate bitmap info header */
- pbmih = (BITMAPINFOHEADER*) malloc (sizeof (BITMAPINFOHEADER)
- + 256 * sizeof (RGBQUAD));
- if (pbmih == NULL)
- {
- ErrorF ("winAllocateFBShadowGDI - malloc () failed\n");
- return FALSE;
- }
-
- /* Query the screen format */
- fReturn = winQueryScreenDIBFormat (pScreen, pbmih);
-
/* Describe shadow bitmap to be created */
- pbmih->biWidth = pScreenInfo->dwWidth;
- pbmih->biHeight = -pScreenInfo->dwHeight;
-
+ pScreenPriv->pbmih->biWidth = pScreenInfo->dwWidth;
+ pScreenPriv->pbmih->biHeight = -pScreenInfo->dwHeight;
+
ErrorF ("winAllocateFBShadowGDI - Creating DIB with width: %d height: %d "
"depth: %d\n",
- (int) pbmih->biWidth, (int) -pbmih->biHeight, pbmih->biBitCount);
+ (int) pScreenPriv->pbmih->biWidth, (int) -pScreenPriv->pbmih->biHeight, pScreenPriv->pbmih->biBitCount);
/* Create a DI shadow bitmap with a bit pointer */
pScreenPriv->hbmpShadow = CreateDIBSection (pScreenPriv->hdcScreen,
- (BITMAPINFO *) pbmih,
+ (BITMAPINFO *) pScreenPriv->pbmih,
DIB_RGB_COLORS,
(VOID**) &pScreenInfo->pfb,
NULL,
@@ -449,25 +432,6 @@ winAllocateFBShadowGDI (ScreenPtr pScreen)
(int) pScreenInfo->dwStride);
#endif
- /* See if the shadow bitmap will be larger than the DIB size limit */
- if (pScreenInfo->dwWidth * pScreenInfo->dwHeight * pScreenInfo->dwBPP
- >= WIN_DIB_MAXIMUM_SIZE)
- {
- ErrorF ("winAllocateFBShadowGDI - Requested DIB (bitmap) "
- "will be larger than %d MB. The surface may fail to be "
- "allocated on Windows 95, 98, or Me, due to a %d MB limit in "
- "DIB size. This limit does not apply to Windows NT/2000, and "
- "this message may be ignored on those platforms.\n",
- WIN_DIB_MAXIMUM_SIZE_MB, WIN_DIB_MAXIMUM_SIZE_MB);
- }
-
- /* Determine our color masks */
- if (!winQueryRGBBitsAndMasks (pScreen))
- {
- ErrorF ("winAllocateFBShadowGDI - winQueryRGBBitsAndMasks failed\n");
- return FALSE;
- }
-
#ifdef XWIN_MULTIWINDOW
/* Redraw all windows */
if (pScreenInfo->fMultiWindow)
@@ -477,6 +441,18 @@ winAllocateFBShadowGDI (ScreenPtr pScreen)
return fReturn;
}
+static void
+winFreeFBShadowGDI (ScreenPtr pScreen)
+{
+ winScreenPriv(pScreen);
+ winScreenInfo *pScreenInfo = pScreenPriv->pScreenInfo;
+
+ /* Free the shadow bitmap */
+ DeleteObject (pScreenPriv->hbmpShadow);
+
+ /* Invalidate the ScreenInfo's fb pointer */
+ pScreenInfo->pfb = NULL;
+}
/*
* Blit the damaged regions of the shadow fb to the screen
@@ -602,6 +578,41 @@ winShadowUpdateGDI (ScreenPtr pScreen,
}
+static Bool
+winInitScreenShadowGDI (ScreenPtr pScreen)
+{
+ winScreenPriv(pScreen);
+
+ /* Get device contexts for the screen and shadow bitmap */
+ pScreenPriv->hdcScreen = GetDC (pScreenPriv->hwndScreen);
+ pScreenPriv->hdcShadow = CreateCompatibleDC (pScreenPriv->hdcScreen);
+
+ /* Allocate bitmap info header */
+ pScreenPriv->pbmih = (BITMAPINFOHEADER*) malloc (sizeof (BITMAPINFOHEADER)
+ + 256 * sizeof (RGBQUAD));
+ if (pScreenPriv->pbmih == NULL)
+ {
+ ErrorF ("winInitScreenShadowGDI - malloc () failed\n");
+ return FALSE;
+ }
+
+ /* Query the screen format */
+ if (!winQueryScreenDIBFormat (pScreen, pScreenPriv->pbmih))
+ {
+ ErrorF ("winInitScreenShadowGDI - winQueryScreenDIBFormat failed\n");
+ return FALSE;
+ }
+
+ /* Determine our color masks */
+ if (!winQueryRGBBitsAndMasks (pScreen))
+ {
+ ErrorF ("winInitScreenShadowGDI - winQueryRGBBitsAndMasks failed\n");
+ return FALSE;
+ }
+
+ return winAllocateFBShadowGDI(pScreen);
+}
+
/* See Porting Layer Definition - p. 33 */
/*
* We wrap whatever CloseScreen procedure was specified by fb;
@@ -632,9 +643,8 @@ winCloseScreenShadowGDI (int nIndex, ScreenPtr pScreen)
/* Free the shadow DC; which allows the bitmap to be freed */
DeleteDC (pScreenPriv->hdcShadow);
-
- /* Free the shadow bitmap */
- DeleteObject (pScreenPriv->hbmpShadow);
+
+ winFreeFBShadowGDI(pScreen);
/* Free the screen DC */
ReleaseDC (pScreenPriv->hwndScreen, pScreenPriv->hdcScreen);
@@ -665,9 +675,6 @@ winCloseScreenShadowGDI (int nIndex, ScreenPtr pScreen)
/* Invalidate our screeninfo's pointer to the screen */
pScreenInfo->pScreen = NULL;
- /* Invalidate the ScreenInfo's fb pointer */
- pScreenInfo->pfb = NULL;
-
/* Free the screen privates for this screen */
free ((pointer) pScreenPriv);
@@ -791,26 +798,9 @@ winAdjustVideoModeShadowGDI (ScreenPtr pScreen)
/* Query GDI for current display depth */
dwBPP = GetDeviceCaps (hdc, BITSPIXEL);
- /* GDI cannot change the screen depth */
- if (pScreenInfo->dwBPP == WIN_DEFAULT_BPP)
- {
- /* No -depth parameter passed, let the user know the depth being used */
- ErrorF ("winAdjustVideoModeShadowGDI - Using Windows display "
- "depth of %d bits per pixel\n", (int) dwBPP);
+ /* GDI cannot change the screen depth, so always use GDI's depth */
+ pScreenInfo->dwBPP = dwBPP;
- /* Use GDI's depth */
- pScreenInfo->dwBPP = dwBPP;
- }
- else if (dwBPP != pScreenInfo->dwBPP)
- {
- /* Warn user if GDI depth is different than -depth parameter */
- ErrorF ("winAdjustVideoModeShadowGDI - Command line bpp: %d, "\
- "using bpp: %d\n", (int) pScreenInfo->dwBPP, (int) dwBPP);
-
- /* We'll use GDI's depth */
- pScreenInfo->dwBPP = dwBPP;
- }
-
/* Release our DC */
ReleaseDC (NULL, hdc);
hdc = NULL;
@@ -1235,7 +1225,9 @@ winSetEngineFunctionsShadowGDI (ScreenPtr pScreen)
/* Set our pointers */
pScreenPriv->pwinAllocateFB = winAllocateFBShadowGDI;
+ pScreenPriv->pwinFreeFB = winFreeFBShadowGDI;
pScreenPriv->pwinShadowUpdate = winShadowUpdateGDI;
+ pScreenPriv->pwinInitScreen = winInitScreenShadowGDI;
pScreenPriv->pwinCloseScreen = winCloseScreenShadowGDI;
pScreenPriv->pwinInitVisuals = winInitVisualsShadowGDI;
pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModeShadowGDI;
diff --git a/hw/xwin/winvalargs.c b/hw/xwin/winvalargs.c
index 357d3d70a..04db777b0 100644
--- a/hw/xwin/winvalargs.c
+++ b/hw/xwin/winvalargs.c
@@ -154,8 +154,8 @@ winValidateArgs (void)
/* Check for !fullscreen and any fullscreen-only parameters */
if (!g_ScreenInfo[i].fFullScreen
- && (g_ScreenInfo[i].dwRefreshRate != WIN_DEFAULT_BPP
- || g_ScreenInfo[i].dwBPP != WIN_DEFAULT_REFRESH))
+ && (g_ScreenInfo[i].dwRefreshRate != WIN_DEFAULT_REFRESH
+ || g_ScreenInfo[i].dwBPP != WIN_DEFAULT_BPP))
{
ErrorF ("winValidateArgs - -refresh and -depth are only valid "
"with -fullscreen.\n");
@@ -164,12 +164,12 @@ winValidateArgs (void)
/* Check for fullscreen and any non-fullscreen parameters */
if (g_ScreenInfo[i].fFullScreen
- && (g_ScreenInfo[i].fScrollbars
+ && ((g_ScreenInfo[i].iResizeMode != notAllowed)
|| !g_ScreenInfo[i].fDecoration
|| g_ScreenInfo[i].fLessPointer))
{
ErrorF ("winValidateArgs - -fullscreen is invalid with "
- "-scrollbars, -nodecoration, or -lesspointer.\n");
+ "-scrollbars, -resize, -nodecoration, or -lesspointer.\n");
return FALSE;
}
}
diff --git a/hw/xwin/winwindow.c b/hw/xwin/winwindow.c
index 783760f4b..7975d71a9 100644
--- a/hw/xwin/winwindow.c
+++ b/hw/xwin/winwindow.c
@@ -58,6 +58,7 @@ winReshapeRootless (WindowPtr pWin);
Bool
winCreateWindowNativeGDI (WindowPtr pWin)
{
+ Bool fResult = TRUE;
ScreenPtr pScreen = pWin->drawable.pScreen;
winWindowPriv(pWin);
winScreenPriv(pScreen);
diff --git a/hw/xwin/winwndproc.c b/hw/xwin/winwndproc.c
index 6d2270a20..bccd6f9f2 100644
--- a/hw/xwin/winwndproc.c
+++ b/hw/xwin/winwndproc.c
@@ -40,6 +40,7 @@
#include "winprefs.h"
#include "winconfig.h"
#include "winmsg.h"
+#include "winmonitors.h"
#include "inputstr.h"
/*
@@ -148,6 +149,13 @@ winWindowProc (HWND hwnd, UINT message,
return 0;
case WM_DISPLAYCHANGE:
+ /*
+ WM_DISPLAYCHANGE seems to be sent when the monitor layout or
+ any monitor's resolution or depth changes, but it's lParam and
+ wParam always indicate the resolution and bpp for the primary
+ monitor (so ignore that as we could be on any monitor...)
+ */
+
/* We cannot handle a display mode change during initialization */
if (s_pScreenInfo == NULL)
FatalError ("winWindowProc - WM_DISPLAYCHANGE - The display "
@@ -167,150 +175,153 @@ winWindowProc (HWND hwnd, UINT message,
#endif
))
{
- /*
- * Store the new display dimensions and depth.
- * We do this here for future compatibility in case we
- * ever allow switching from fullscreen to windowed mode.
- */
- s_pScreenPriv->dwLastWindowsWidth = GetSystemMetrics (SM_CXSCREEN);
- s_pScreenPriv->dwLastWindowsHeight = GetSystemMetrics (SM_CYSCREEN);
- s_pScreenPriv->dwLastWindowsBitsPixel
- = GetDeviceCaps (s_pScreenPriv->hdcScreen, BITSPIXEL);
break;
}
-
- ErrorF ("winWindowProc - WM_DISPLAYCHANGE - orig bpp: %d, last bpp: %d, "
- "new bpp: %d\n",
- (int) s_pScreenInfo->dwBPP,
- (int) s_pScreenPriv->dwLastWindowsBitsPixel,
- wParam);
ErrorF ("winWindowProc - WM_DISPLAYCHANGE - new width: %d "
- "new height: %d\n",
- LOWORD (lParam), HIWORD (lParam));
-
- /*
- * TrueColor --> TrueColor depth changes are disruptive for:
- * Windowed:
- * Shadow DirectDraw
- * Shadow DirectDraw Non-Locking
- * Primary DirectDraw
- *
- * TrueColor --> TrueColor depth changes are non-optimal for:
- * Windowed:
- * Shadow GDI
- *
- * FullScreen:
- * Shadow GDI
- *
- * TrueColor --> PseudoColor or vice versa are disruptive for:
- * Windowed:
- * Shadow DirectDraw
- * Shadow DirectDraw Non-Locking
- * Primary DirectDraw
- * Shadow GDI
- */
+ "new height: %d new bpp: %d\n",
+ LOWORD (lParam), HIWORD (lParam), wParam);
/*
* Check for a disruptive change in depth.
* We can only display a message for a disruptive depth change,
* we cannot do anything to correct the situation.
*/
- if ((s_pScreenInfo->dwBPP != wParam)
- && (s_pScreenInfo->dwEngine == WIN_SERVER_SHADOW_DD
- || s_pScreenInfo->dwEngine == WIN_SERVER_SHADOW_DDNL
+ /*
+ XXX: maybe we need to check if GetSystemMetrics(SM_SAMEDISPLAYFORMAT)
+ has changed as well...
+ */
+ if (s_pScreenInfo->dwBPP != GetDeviceCaps (s_pScreenPriv->hdcScreen, BITSPIXEL))
+ {
+ if ((s_pScreenInfo->dwEngine == WIN_SERVER_SHADOW_DD
+ || s_pScreenInfo->dwEngine == WIN_SERVER_SHADOW_DDNL
#ifdef XWIN_PRIMARYFB
- || s_pScreenInfo->dwEngine == WIN_SERVER_PRIMARY_DD
+ || s_pScreenInfo->dwEngine == WIN_SERVER_PRIMARY_DD
#endif
- ))
- {
- /* Cannot display the visual until the depth is restored */
- ErrorF ("winWindowProc - Disruptive change in depth\n");
-
- /* Display Exit dialog */
- winDisplayDepthChangeDialog (s_pScreenPriv);
-
- /* Flag that we have an invalid screen depth */
- s_pScreenPriv->fBadDepth = TRUE;
-
- /* Minimize the display window */
- ShowWindow (hwnd, SW_MINIMIZE);
- }
+ ))
+ {
+ /* Cannot display the visual until the depth is restored */
+ ErrorF ("winWindowProc - Disruptive change in depth\n");
+
+ /* Display depth change dialog */
+ winDisplayDepthChangeDialog (s_pScreenPriv);
+
+ /* Flag that we have an invalid screen depth */
+ s_pScreenPriv->fBadDepth = TRUE;
+
+ /* Minimize the display window */
+ ShowWindow (hwnd, SW_MINIMIZE);
+ }
+ else
+ {
+ /* For GDI, performance may suffer until original depth is restored */
+ ErrorF ("winWindowProc - Performance may be non-optimal after change in depth\n");
+ }
+ }
else
- {
- /* Flag that we have a valid screen depth */
- s_pScreenPriv->fBadDepth = FALSE;
- }
-
+ {
+ /* Flag that we have a valid screen depth */
+ s_pScreenPriv->fBadDepth = FALSE;
+ }
+
/*
- * Check for a change in display dimensions.
- * We can simply recreate the same-sized primary surface when
- * the display dimensions change.
- */
- if (s_pScreenPriv->dwLastWindowsWidth != LOWORD (lParam)
- || s_pScreenPriv->dwLastWindowsHeight != HIWORD (lParam))
+ If we could cheaply check if this WM_DISPLAYCHANGE change
+ affects the monitor(s) which this X screen is displayed on
+ then we should do so here. For the moment, assume it does.
+ (this is probably usually the case so that might be an
+ overoptimization)
+ */
{
/*
- * NOTE: The non-DirectDraw engines set the ReleasePrimarySurface
- * and CreatePrimarySurface function pointers to point
- * to the no operation function, NoopDDA. This allows us
- * to blindly call these functions, even if they are not
- * relevant to the current engine (e.g., Shadow GDI).
- */
-
-#if CYGDEBUG
- winDebug ("winWindowProc - WM_DISPLAYCHANGE - Dimensions changed\n");
-#endif
-
- /* Release the old primary surface */
- (*s_pScreenPriv->pwinReleasePrimarySurface) (s_pScreen);
-
-#if CYGDEBUG
- winDebug ("winWindowProc - WM_DISPLAYCHANGE - Released "
- "primary surface\n");
+ In rootless modes which are monitor or virtual desktop size
+ use RandR to resize the X screen
+ */
+ if ((!s_pScreenInfo->fUserGaveHeightAndWidth) &&
+ (s_pScreenInfo->iResizeMode == resizeWithRandr) &&
+ (FALSE
+#ifdef XWIN_MULTIWINDOWEXTWM
+ || s_pScreenInfo->fMWExtWM
#endif
-
- /* Create the new primary surface */
- (*s_pScreenPriv->pwinCreatePrimarySurface) (s_pScreen);
-
-#if CYGDEBUG
- winDebug ("winWindowProc - WM_DISPLAYCHANGE - Recreated "
- "primary surface\n");
+ || s_pScreenInfo->fRootless
+#ifdef XWIN_MULTIWINDOW
+ || s_pScreenInfo->fMultiWindow
#endif
-
-#if 0
- /* Multi-Window mode uses RandR for resizes */
- if (s_pScreenInfo->fMultiWindow)
+ ))
{
- RRSetScreenConfig ();
+ DWORD dwWidth, dwHeight;
+
+ if (s_pScreenInfo->fMultipleMonitors)
+ {
+ /* resize to new virtual desktop size */
+ dwWidth = GetSystemMetrics(SM_CXVIRTUALSCREEN);
+ dwHeight = GetSystemMetrics(SM_CYVIRTUALSCREEN);
+ }
+ else
+ {
+ /* resize to new size of specified monitor */
+ struct GetMonitorInfoData data;
+ if (QueryMonitor(s_pScreenInfo->iMonitor, &data))
+ {
+ if (data.bMonitorSpecifiedExists == TRUE)
+ {
+ dwWidth = data.monitorWidth;
+ dwHeight = data.monitorHeight;
+ /*
+ XXX: monitor may have changed position,
+ so we might need to update xinerama data
+ */
+ }
+ else
+ {
+ ErrorF ("Monitor number %d no longer exists!\n", s_pScreenInfo->iMonitor);
+ }
+ }
+ }
+
+ /*
+ XXX: probably a small bug here: we don't compute the work area
+ and allow for task bar
+
+ XXX: generally, we don't allow for the task bar being moved after
+ the server is started
+ */
+
+ /* Set screen size to match new size, if it is different to current */
+ if ((s_pScreenInfo->dwWidth != dwWidth) ||
+ (s_pScreenInfo->dwHeight != dwHeight))
+ {
+ winDoRandRScreenSetSize(s_pScreen,
+ dwWidth,
+ dwHeight,
+ (dwWidth * 25.4) / monitorResolution,
+ (dwHeight * 25.4) / monitorResolution);
+ }
}
-#endif
- }
- else
- {
-#if CYGDEBUG
- winDebug ("winWindowProc - WM_DISPLAYCHANGE - Dimensions did not "
- "change\n");
-#endif
+ else
+ {
+ /*
+ * We can simply recreate the same-sized primary surface when
+ * the display dimensions change.
+ */
+
+ /*
+ * NOTE: The non-DirectDraw engines set the ReleasePrimarySurface
+ * and CreatePrimarySurface function pointers to point
+ * to the no operation function, NoopDDA. This allows us
+ * to blindly call these functions, even if they are not
+ * relevant to the current engine (e.g., Shadow GDI).
+ */
+
+ winDebug ("winWindowProc - WM_DISPLAYCHANGE - Releasing and recreating primary surface\n");
+
+ /* Release the old primary surface */
+ (*s_pScreenPriv->pwinReleasePrimarySurface) (s_pScreen);
+
+ /* Create the new primary surface */
+ (*s_pScreenPriv->pwinCreatePrimarySurface) (s_pScreen);
+ }
}
- /* Store the new display dimensions and depth */
- if (s_pScreenInfo->fMultipleMonitors)
- {
- s_pScreenPriv->dwLastWindowsWidth
- = GetSystemMetrics (SM_CXVIRTUALSCREEN);
- s_pScreenPriv->dwLastWindowsHeight
- = GetSystemMetrics (SM_CYVIRTUALSCREEN);
- }
- else
- {
- s_pScreenPriv->dwLastWindowsWidth
- = GetSystemMetrics (SM_CXSCREEN);
- s_pScreenPriv->dwLastWindowsHeight
- = GetSystemMetrics (SM_CYSCREEN);
- }
- s_pScreenPriv->dwLastWindowsBitsPixel
- = GetDeviceCaps (s_pScreenPriv->hdcScreen, BITSPIXEL);
break;
case WM_SIZE:
@@ -323,8 +334,8 @@ winWindowProc (HWND hwnd, UINT message,
winDebug ("winWindowProc - WM_SIZE\n");
#endif
- /* Break if we do not use scrollbars */
- if (!s_pScreenInfo->fScrollbars
+ /* Break if we do not allow resizing */
+ if ((s_pScreenInfo->iResizeMode == notAllowed)
|| !s_pScreenInfo->fDecoration
#ifdef XWIN_MULTIWINDOWEXTWM
|| s_pScreenInfo->fMWExtWM
@@ -340,6 +351,17 @@ winWindowProc (HWND hwnd, UINT message,
if (wParam == SIZE_MINIMIZED)
return 0;
+ ErrorF ("winWindowProc - WM_SIZE - new client area w: %d h: %d\n",
+ LOWORD (lParam), HIWORD (lParam));
+
+ if (s_pScreenInfo->iResizeMode == resizeWithRandr)
+ {
+ /* Actual resizing is done on WM_EXITSIZEMOVE */
+ return 0;
+ }
+
+ /* Otherwise iResizeMode == resizeWithScrollbars */
+
/*
* Get the size of the whole window, including client area,
* scrollbars, and non-client area decorations (caption, borders).
@@ -357,10 +379,6 @@ winWindowProc (HWND hwnd, UINT message,
iWidth = rcWindow.right - rcWindow.left;
iHeight = rcWindow.bottom - rcWindow.top;
- ErrorF ("winWindowProc - WM_SIZE - window w: %d h: %d, "
- "new client area w: %d h: %d\n",
- iWidth, iHeight, LOWORD (lParam), HIWORD (lParam));
-
/* Subtract the frame size from the window size. */
iWidth -= 2 * GetSystemMetrics (SM_CXSIZEFRAME);
iHeight -= (2 * GetSystemMetrics (SM_CYSIZEFRAME)
@@ -416,6 +434,37 @@ winWindowProc (HWND hwnd, UINT message,
}
return 0;
+ case WM_ENTERSIZEMOVE:
+ ErrorF("winWindowProc - WM_ENTERSIZEMOVE\n");
+ break;
+
+ case WM_EXITSIZEMOVE:
+ ErrorF("winWindowProc - WM_EXITSIZEMOVE\n");
+
+ if (s_pScreenInfo->iResizeMode == resizeWithRandr)
+ {
+ /* Set screen size to match new client area, if it is different to current */
+ RECT rcClient;
+ DWORD dwWidth, dwHeight;
+
+ GetClientRect (hwnd, &rcClient);
+ dwWidth = rcClient.right - rcClient.left;
+ dwHeight = rcClient.bottom - rcClient.top;
+
+ if ((s_pScreenInfo->dwWidth != dwWidth) ||
+ (s_pScreenInfo->dwHeight != dwHeight))
+ {
+ /* mm = dots * (25.4 mm / inch) / (dots / inch) */
+ winDoRandRScreenSetSize(s_pScreen,
+ dwWidth,
+ dwHeight,
+ (dwWidth * 25.4) / monitorResolution,
+ (dwHeight * 25.4) / monitorResolution);
+ }
+ }
+
+ break;
+
case WM_VSCROLL:
{
SCROLLINFO si;
@@ -599,7 +648,7 @@ winWindowProc (HWND hwnd, UINT message,
/* Can't do anything without screen info */
if (s_pScreenInfo == NULL
- || !s_pScreenInfo->fScrollbars
+ || (s_pScreenInfo->iResizeMode != resizeWithScrollbars)
|| s_pScreenInfo->fFullScreen
|| !s_pScreenInfo->fDecoration
#ifdef XWIN_MULTIWINDOWEXTWM