Merge remote branch 'jturney/jturney-framebuffer-resize-for-master'

This commit is contained in:
Keith Packard 2011-01-20 21:11:53 -08:00
commit 24ce650cf4
20 changed files with 1031 additions and 705 deletions

View File

@ -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_MULTIWINDOWEXTWM, [test "x$XWIN" = xyes && test "x$WINDOWSWM" = xyes])
AM_CONDITIONAL(XWIN_CLIPBOARD, [test "x$XWIN" = xyes]) AM_CONDITIONAL(XWIN_CLIPBOARD, [test "x$XWIN" = xyes])
AM_CONDITIONAL(XWIN_GLX_WINDOWS, [test "x$XWIN" = xyes && false]) AM_CONDITIONAL(XWIN_GLX_WINDOWS, [test "x$XWIN" = xyes && false])
AM_CONDITIONAL(XWIN_NATIVEGDI, [test "x$XWIN" = xyes && false]) AM_CONDITIONAL(XWIN_NATIVEGDI, [test "x$XWIN" = xyes])
AM_CONDITIONAL(XWIN_PRIMARYFB, [test "x$XWIN" = xyes && false]) AM_CONDITIONAL(XWIN_PRIMARYFB, [test "x$XWIN" = xyes])
AM_CONDITIONAL(XWIN_RANDR, [test "x$XWIN" = xyes]) AM_CONDITIONAL(XWIN_RANDR, [test "x$XWIN" = xyes])
AM_CONDITIONAL(XWIN_XV, [test "x$XWIN" = xyes && test "x$XV" = xyes]) AM_CONDITIONAL(XWIN_XV, [test "x$XWIN" = xyes && test "x$XV" = xyes])

View File

@ -755,6 +755,9 @@ winUseMsg (void)
"\t\t1 - Shadow GDI\n" "\t\t1 - Shadow GDI\n"
"\t\t2 - Shadow DirectDraw\n" "\t\t2 - Shadow DirectDraw\n"
"\t\t4 - Shadow DirectDraw4 Non-Locking\n" "\t\t4 - Shadow DirectDraw4 Non-Locking\n"
#ifdef XWIN_PRIMARYFB
"\t\t8 - Primary DirectDraw - obsolete\n"
#endif
#ifdef XWIN_NATIVEGDI #ifdef XWIN_NATIVEGDI
"\t\t16 - Native GDI - experimental\n" "\t\t16 - Native GDI - experimental\n"
#endif #endif
@ -823,6 +826,11 @@ winUseMsg (void)
"\tSpecify an optional refresh rate to use in fullscreen mode\n" "\tSpecify an optional refresh rate to use in fullscreen mode\n"
"\twith a DirectDraw engine.\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" ErrorF ("-rootless\n"
"\tRun the server in rootless mode.\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 1024x768@3 ; 3rd monitor size 1024x768\n"
"\t -screen 0 @1 ; on 1st monitor using its full resolution (the default)\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" ErrorF ("-silent-dup-error\n"
"\tIf another instance of " EXECUTABLE_NAME " with the same display number is running\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"); "\texit silently and don't display any error message.\n");

View File

@ -87,6 +87,7 @@ SRCS = InitInput.c \
winkeybd.c \ winkeybd.c \
winkeyhook.c \ winkeyhook.c \
winmisc.c \ winmisc.c \
winmonitors.c \
winmouse.c \ winmouse.c \
winmsg.c \ winmsg.c \
winmultiwindowclass.c \ winmultiwindowclass.c \

View File

@ -103,7 +103,7 @@ Examples:
.SH OPTIONS CONTROLLING THE APPEARANCE OF THE X SCREEN WINDOWS .SH OPTIONS CONTROLLING THE APPEARANCE OF THE X SCREEN WINDOWS
These parameters only apply to windowed mode screens i.e. not 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 .TP 8
.B "\-fullscreen" .B "\-fullscreen"
The X server window takes the full screen, covering completely the 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. This parameter is ignored when the \fB\-fullscreen\fP parameter is specified.
.TP 8 .TP 8
.B \-scrollbars .B \-scrollbars
In windowed mode, allow screens bigger than the \fIWindows\fP desktop. Alternative name for \fB\-resize=scrollbars\fP.
Moreover, if the window has decorations, one can now resize it.
This parameter is ignored when the \fB\-fullscreen\fP parameter is specified.
.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 .SH OPTIONS CONTROLLING WINDOWS INTEGRATION
.TP 8 .TP 8
@ -190,15 +232,27 @@ respectively).
.TP 8 .TP 8
.B "\-engine \fIengine_type_id\fP" .B "\-engine \fIengine_type_id\fP"
This option, which is intended for Cygwin/X developers, This option, which is intended for Cygwin/X developers,
overrides the server's automatically selected engine type. This overrides the server's automatically selected drawing engine type. This
parameter will be ignored if the specified engine type is not parameter will be ignored if the specified drawing engine type is not
supported on the current system. The supported engine type ids are 1 supported on the current system.
- Shadow GDI, 2 - Shadow DirectDraw, and 4 - Shadow DirectDraw Non-Locking.
Additionally, there are engines with type ids Default behavior is to select the drawing engine with optimum performance that
8 - Primary DirectDraw (obsolete) and 16 - Native GDI (experimental and barely functional).
Default behavior is to determine the engine with optimum performance that
supports the specified depth and window configuration. 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 .SH FULLSCREEN OPTIONS
.TP 8 .TP 8
.B "\-depth \fIdepth\fP" .B "\-depth \fIdepth\fP"
@ -322,12 +376,9 @@ X(__miscmansuffix__), Xserver(1), xdm(1), xinit(1), XWinrc(__filemansuffix__), s
.SH BUGS .SH BUGS
.I XWin .I XWin
and this man page still have many limitations. Some of the more obvious and this man page still have many limitations.
ones are:
.br The \fIXWin\fP software is continuously developing; it is therefore possible that
- 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
this man page is not up to date. It is always prudent to 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 look also at the output of \fIXWin -help\fP in order to
check the options that are operative. check the options that are operative.

View File

@ -74,9 +74,6 @@
#endif #endif
#define WIN_DEFAULT_USER_GAVE_HEIGHT_AND_WIDTH FALSE #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 * Windows only supports 256 color palettes
*/ */
@ -276,8 +273,12 @@ static Atom func (void) { \
typedef Bool (*winAllocateFBProcPtr)(ScreenPtr); typedef Bool (*winAllocateFBProcPtr)(ScreenPtr);
typedef void (*winFreeFBProcPtr)(ScreenPtr);
typedef void (*winShadowUpdateProcPtr)(ScreenPtr, shadowBufPtr); typedef void (*winShadowUpdateProcPtr)(ScreenPtr, shadowBufPtr);
typedef Bool (*winInitScreenProcPtr)(ScreenPtr);
typedef Bool (*winCloseScreenProcPtr)(int, ScreenPtr); typedef Bool (*winCloseScreenProcPtr)(int, ScreenPtr);
typedef Bool (*winInitVisualsProcPtr)(ScreenPtr); typedef Bool (*winInitVisualsProcPtr)(ScreenPtr);
@ -315,6 +316,12 @@ typedef Bool (*winFinishCreateWindowsWindowProcPtr)(WindowPtr pWin);
typedef Bool (*winCreateScreenResourcesProc)(ScreenPtr); 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 * GC (graphics context) privates
@ -368,6 +375,15 @@ typedef struct {
miPointerSpriteFuncPtr spriteFuncs; miPointerSpriteFuncPtr spriteFuncs;
} winCursorRec; } winCursorRec;
/*
* Resize modes
*/
typedef enum {
notAllowed,
resizeWithScrollbars,
resizeWithRandr
} winResizeMode;
/* /*
* Screen information structure that we need before privates are available * Screen information structure that we need before privates are available
* in the server startup sequence. * in the server startup sequence.
@ -381,12 +397,12 @@ typedef struct
Bool fUserGaveHeightAndWidth; Bool fUserGaveHeightAndWidth;
DWORD dwScreen; DWORD dwScreen;
int iMonitor;
DWORD dwUserWidth; DWORD dwUserWidth;
DWORD dwUserHeight; DWORD dwUserHeight;
DWORD dwWidth; DWORD dwWidth;
DWORD dwHeight; DWORD dwHeight;
DWORD dwWidth_mm;
DWORD dwHeight_mm;
DWORD dwPaddedWidth; DWORD dwPaddedWidth;
/* Did the user specify a screen position? */ /* Did the user specify a screen position? */
@ -431,7 +447,7 @@ typedef struct
#endif #endif
Bool fMultipleMonitors; Bool fMultipleMonitors;
Bool fLessPointer; Bool fLessPointer;
Bool fScrollbars; winResizeMode iResizeMode;
Bool fNoTrayIcon; Bool fNoTrayIcon;
int iE3BTimeout; int iE3BTimeout;
/* Windows (Alt+F4) and Unix (Ctrl+Alt+Backspace) Killkey */ /* Windows (Alt+F4) and Unix (Ctrl+Alt+Backspace) Killkey */
@ -473,11 +489,6 @@ typedef struct _winPrivScreenRec
/* Handle to icons that must be freed */ /* Handle to icons that must be freed */
HICON hiconNotifyIcon; HICON hiconNotifyIcon;
/* Last width, height, and depth of the Windows display */
DWORD dwLastWindowsWidth;
DWORD dwLastWindowsHeight;
DWORD dwLastWindowsBitsPixel;
/* Palette management */ /* Palette management */
ColormapPtr pcmapInstalled; ColormapPtr pcmapInstalled;
@ -493,7 +504,8 @@ typedef struct _winPrivScreenRec
HDC hdcScreen; HDC hdcScreen;
HDC hdcShadow; HDC hdcShadow;
HWND hwndScreen; HWND hwndScreen;
BITMAPINFOHEADER *pbmih;
/* Privates used by shadow fb and primary fb DirectDraw servers */ /* Privates used by shadow fb and primary fb DirectDraw servers */
LPDIRECTDRAW pdd; LPDIRECTDRAW pdd;
LPDIRECTDRAWSURFACE2 pddsPrimary; LPDIRECTDRAWSURFACE2 pddsPrimary;
@ -543,7 +555,9 @@ typedef struct _winPrivScreenRec
/* Engine specific functions */ /* Engine specific functions */
winAllocateFBProcPtr pwinAllocateFB; winAllocateFBProcPtr pwinAllocateFB;
winFreeFBProcPtr pwinFreeFB;
winShadowUpdateProcPtr pwinShadowUpdate; winShadowUpdateProcPtr pwinShadowUpdate;
winInitScreenProcPtr pwinInitScreen;
winCloseScreenProcPtr pwinCloseScreen; winCloseScreenProcPtr pwinCloseScreen;
winInitVisualsProcPtr pwinInitVisuals; winInitVisualsProcPtr pwinInitVisuals;
winAdjustVideoModeProcPtr pwinAdjustVideoMode; winAdjustVideoModeProcPtr pwinAdjustVideoMode;
@ -588,6 +602,12 @@ typedef struct _winPrivScreenRec
SetShapeProcPtr SetShape; SetShapeProcPtr SetShape;
winCursorRec cursor; winCursorRec cursor;
#ifdef XWIN_NATIVEGDI
RealizeFontPtr RealizeFont;
UnrealizeFontPtr UnrealizeFont;
#endif
} winPrivScreenRec; } winPrivScreenRec;
@ -1451,6 +1471,18 @@ winInitCursor (ScreenPtr pScreen);
void void
winInitializeScreens(int maxscreens); 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 * END DDX and DIX Function Prototypes
*/ */

View File

@ -192,7 +192,7 @@ winCreateBoundingWindowWindowed (ScreenPtr pScreen)
fForceShowWindow = TRUE; fForceShowWindow = TRUE;
} }
dwWindowStyle |= WS_CAPTION; dwWindowStyle |= WS_CAPTION;
if (pScreenInfo->fScrollbars) if (pScreenInfo->iResizeMode != notAllowed)
dwWindowStyle |= WS_THICKFRAME | WS_MAXIMIZEBOX; dwWindowStyle |= WS_THICKFRAME | WS_MAXIMIZEBOX;
} }
else else
@ -233,6 +233,22 @@ winCreateBoundingWindowWindowed (ScreenPtr pScreen)
iPosY = rcWorkArea.top; 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? */ /* Did the user specify a height and width? */
if (pScreenInfo->fUserGaveHeightAndWidth) if (pScreenInfo->fUserGaveHeightAndWidth)
{ {
@ -256,12 +272,12 @@ winCreateBoundingWindowWindowed (ScreenPtr pScreen)
#if CYGDEBUG #if CYGDEBUG
winDebug ("winCreateBoundingWindowWindowed - Window has decoration\n"); winDebug ("winCreateBoundingWindowWindowed - Window has decoration\n");
#endif #endif
/* Are we using scrollbars? */
if (pScreenInfo->fScrollbars) /* Are we resizable */
if (pScreenInfo->iResizeMode != notAllowed)
{ {
#if CYGDEBUG #if CYGDEBUG
winDebug ("winCreateBoundingWindowWindowed - Window has " winDebug ("winCreateBoundingWindowWindowed - Window is resizable\n");
"scrollbars\n");
#endif #endif
iWidth += 2 * GetSystemMetrics (SM_CXSIZEFRAME); iWidth += 2 * GetSystemMetrics (SM_CXSIZEFRAME);
@ -271,8 +287,7 @@ winCreateBoundingWindowWindowed (ScreenPtr pScreen)
else else
{ {
#if CYGDEBUG #if CYGDEBUG
winDebug ("winCreateBoundingWindowWindowed - Window does not have " winDebug ("winCreateBoundingWindowWindowed - Window is not resizable\n");
"scrollbars\n");
#endif #endif
iWidth += 2 * GetSystemMetrics (SM_CXFIXEDFRAME); iWidth += 2 * GetSystemMetrics (SM_CXFIXEDFRAME);
@ -296,22 +311,7 @@ winCreateBoundingWindowWindowed (ScreenPtr pScreen)
} }
} }
/* Clean up the scrollbars flag, if necessary */ /* Make sure window is no bigger than work area */
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;
}
if (TRUE if (TRUE
#ifdef XWIN_MULTIWINDOWEXTWM #ifdef XWIN_MULTIWINDOWEXTWM
&& !pScreenInfo->fMWExtWM && !pScreenInfo->fMWExtWM
@ -396,7 +396,7 @@ winCreateBoundingWindowWindowed (ScreenPtr pScreen)
rcClient.bottom, rcClient.top); rcClient.bottom, rcClient.top);
/* We adjust the visual size if the user did not specify it */ /* 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, * User did not give a height and width with scrollbars enabled,

View File

@ -482,11 +482,11 @@ winChangeDepthDlgProc (HWND hwndDialog, UINT message,
#if CYGDEBUG #if CYGDEBUG
winDebug ("winChangeDepthDlgProc - WM_INITDIALOG - orig bpp: %d, " winDebug ("winChangeDepthDlgProc - WM_INITDIALOG - orig bpp: %d, "
"last bpp: %d\n", "current bpp: %d\n",
s_pScreenInfo->dwBPP, s_pScreenInfo->dwBPP,
s_pScreenPriv->dwLastWindowsBitsPixel); GetDeviceCaps(s_pScreenPriv->hdcScreen, BITSPIXEL));
#endif #endif
winInitDialog( hwndDialog ); winInitDialog( hwndDialog );
return TRUE; return TRUE;
@ -494,14 +494,13 @@ winChangeDepthDlgProc (HWND hwndDialog, UINT message,
case WM_DISPLAYCHANGE: case WM_DISPLAYCHANGE:
#if CYGDEBUG #if CYGDEBUG
winDebug ("winChangeDepthDlgProc - WM_DISPLAYCHANGE - orig bpp: %d, " winDebug ("winChangeDepthDlgProc - WM_DISPLAYCHANGE - orig bpp: %d, "
"last bpp: %d, new bpp: %d\n", "new bpp: %d\n",
s_pScreenInfo->dwBPP, s_pScreenInfo->dwBPP,
s_pScreenPriv->dwLastWindowsBitsPixel, GetDeviceCaps(s_pScreenPriv->hdcScreen, BITSPIXEL));
wParam);
#endif #endif
/* Dismiss the dialog if the display returns to the original depth */ /* 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"); ErrorF ("winChangeDelthDlgProc - wParam == s_pScreenInfo->dwBPP\n");

92
hw/xwin/winmonitors.c Normal file
View File

@ -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;
}

14
hw/xwin/winmonitors.h Normal file
View File

@ -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);

View File

@ -92,6 +92,18 @@ winAllocateFBNativeGDI (ScreenPtr pScreen)
return TRUE; 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; * We wrap whatever CloseScreen procedure was specified by fb;
@ -289,28 +301,9 @@ winAdjustVideoModeNativeGDI (ScreenPtr pScreen)
break; break;
} }
/* GDI cannot change the screen depth */ /* GDI cannot change the screen depth, so we'll use GDI's depth */
if (pScreenInfo->dwBPP == WIN_DEFAULT_BPP) pScreenInfo->dwBPP = dwBPP;
{
/* 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);
/* 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 */ /* Release our DC */
ReleaseDC (NULL, hdc); ReleaseDC (NULL, hdc);
@ -506,7 +499,9 @@ winSetEngineFunctionsNativeGDI (ScreenPtr pScreen)
/* Set our pointers */ /* Set our pointers */
pScreenPriv->pwinAllocateFB = winAllocateFBNativeGDI; pScreenPriv->pwinAllocateFB = winAllocateFBNativeGDI;
pScreenPriv->pwinFreeFB = winFreeFBNativeGDI;
pScreenPriv->pwinShadowUpdate = winShadowUpdateNativeGDI; pScreenPriv->pwinShadowUpdate = winShadowUpdateNativeGDI;
pScreenPriv->pwinInitScreen = winInitScreenNativeGDI;
pScreenPriv->pwinCloseScreen = winCloseScreenNativeGDI; pScreenPriv->pwinCloseScreen = winCloseScreenNativeGDI;
pScreenPriv->pwinInitVisuals = winInitVisualsNativeGDI; pScreenPriv->pwinInitVisuals = winInitVisualsNativeGDI;
pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModeNativeGDI; pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModeNativeGDI;

View File

@ -233,6 +233,45 @@ winAllocateFBPrimaryDD (ScreenPtr pScreen)
return TRUE; 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. * Call the wrapped CloseScreen function.
@ -260,29 +299,7 @@ winCloseScreenPrimaryDD (int nIndex, ScreenPtr pScreen)
/* Delete the window property */ /* Delete the window property */
RemoveProp (pScreenPriv->hwndScreen, WIN_SCR_PROP); RemoveProp (pScreenPriv->hwndScreen, WIN_SCR_PROP);
/* Free the offscreen surface, if there is one */ winFreeFBPrimaryDD(pScreen);
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;
}
/* Delete tray icon, if we have one */ /* Delete tray icon, if we have one */
if (!pScreenInfo->fNoTrayIcon) if (!pScreenInfo->fNoTrayIcon)
@ -305,9 +322,6 @@ winCloseScreenPrimaryDD (int nIndex, ScreenPtr pScreen)
/* Kill our screeninfo's pointer to the screen */ /* Kill our screeninfo's pointer to the screen */
pScreenInfo->pScreen = NULL; pScreenInfo->pScreen = NULL;
/* Invalidate the ScreenInfo's fb pointer */
pScreenInfo->pfb = NULL;
/* Free the screen privates for this screen */ /* Free the screen privates for this screen */
free ((pointer) pScreenPriv); free ((pointer) pScreenPriv);
@ -422,33 +436,13 @@ winAdjustVideoModePrimaryDD (ScreenPtr pScreen)
dwBPP = GetDeviceCaps (hdc, BITSPIXEL); dwBPP = GetDeviceCaps (hdc, BITSPIXEL);
/* DirectDraw can only change the depth in fullscreen mode */ /* 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 */ /* Otherwise, We'll use GDI's depth */
ErrorF ("winAdjustVideoModePrimaryDD - Using Windows display "
"depth of %d bits per pixel\n", (int) dwBPP);
/* Use GDI's depth */
pScreenInfo->dwBPP = dwBPP; 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 */ /* Release our DC */
ReleaseDC (NULL, hdc); ReleaseDC (NULL, hdc);
@ -653,8 +647,9 @@ winSetEngineFunctionsPrimaryDD (ScreenPtr pScreen)
/* Set our pointers */ /* Set our pointers */
pScreenPriv->pwinAllocateFB = winAllocateFBPrimaryDD; pScreenPriv->pwinAllocateFB = winAllocateFBPrimaryDD;
pScreenPriv->pwinShadowUpdate pScreenPriv->pwinFreeFB = winFreeFBPrimaryDD;
= (winShadowUpdateProcPtr) (void (*)(void))NoopDDA; pScreenPriv->pwinShadowUpdate = (winShadowUpdateProcPtr) (void (*)(void))NoopDDA;
pScreenPriv->pwinInitScreen = winInitScreenPrimaryDD;
pScreenPriv->pwinCloseScreen = winCloseScreenPrimaryDD; pScreenPriv->pwinCloseScreen = winCloseScreenPrimaryDD;
pScreenPriv->pwinInitVisuals = winInitVisualsPrimaryDD; pScreenPriv->pwinInitVisuals = winInitVisualsPrimaryDD;
pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModePrimaryDD; pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModePrimaryDD;
@ -663,10 +658,17 @@ winSetEngineFunctionsPrimaryDD (ScreenPtr pScreen)
else else
pScreenPriv->pwinCreateBoundingWindow = winCreateBoundingWindowWindowed; pScreenPriv->pwinCreateBoundingWindow = winCreateBoundingWindowWindowed;
pScreenPriv->pwinFinishScreenInit = winFinishScreenInitFB; pScreenPriv->pwinFinishScreenInit = winFinishScreenInitFB;
pScreenPriv->pwinBltExposedRegions pScreenPriv->pwinBltExposedRegions = (winBltExposedRegionsProcPtr) (void (*)(void))NoopDDA;
= (winBltExposedRegionsProcPtr) (void (*)(void))NoopDDA;
pScreenPriv->pwinActivateApp = winActivateAppPrimaryDD; 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->pwinHotKeyAltTab = winHotKeyAltTabPrimaryDD;
pScreenPriv->pwinCreatePrimarySurface = (winCreatePrimarySurfaceProcPtr) (void (*)(void))NoopDDA;
pScreenPriv->pwinReleasePrimarySurface = (winReleasePrimarySurfaceProcPtr) (void (*)(void))NoopDDA;
#ifdef XWIN_MULTIWINDOW #ifdef XWIN_MULTIWINDOW
pScreenPriv->pwinFinishCreateWindowsWindow = pScreenPriv->pwinFinishCreateWindowsWindow =
(winFinishCreateWindowsWindowProcPtr) (void (*)(void))NoopDDA; (winFinishCreateWindowsWindowProcPtr) (void (*)(void))NoopDDA;

View File

@ -35,6 +35,7 @@ from The Open Group.
#include "win.h" #include "win.h"
#include "winconfig.h" #include "winconfig.h"
#include "winmsg.h" #include "winmsg.h"
#include "winmonitors.h"
/* /*
* References to external symbols * References to external symbols
@ -44,55 +45,6 @@ from The Open Group.
extern Bool g_fUnicodeClipboard; extern Bool g_fUnicodeClipboard;
extern Bool g_fClipboard; extern Bool g_fClipboard;
#endif #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 * Function prototypes
@ -143,6 +95,7 @@ winInitializeScreenDefaults(void)
if (monitorResolution == 0) if (monitorResolution == 0)
monitorResolution = WIN_DEFAULT_DPI; monitorResolution = WIN_DEFAULT_DPI;
defaultScreenInfo.iMonitor = 1;
defaultScreenInfo.dwWidth = dwWidth; defaultScreenInfo.dwWidth = dwWidth;
defaultScreenInfo.dwHeight = dwHeight; defaultScreenInfo.dwHeight = dwHeight;
defaultScreenInfo.dwUserWidth = dwWidth; defaultScreenInfo.dwUserWidth = dwWidth;
@ -171,11 +124,9 @@ winInitializeScreenDefaults(void)
#endif #endif
defaultScreenInfo.fMultipleMonitors = FALSE; defaultScreenInfo.fMultipleMonitors = FALSE;
defaultScreenInfo.fLessPointer = FALSE; defaultScreenInfo.fLessPointer = FALSE;
defaultScreenInfo.fScrollbars = FALSE; defaultScreenInfo.iResizeMode = notAllowed;
defaultScreenInfo.fNoTrayIcon = FALSE; defaultScreenInfo.fNoTrayIcon = FALSE;
defaultScreenInfo.iE3BTimeout = WIN_E3B_OFF; 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.fUseWinKillKey = WIN_DEFAULT_WIN_KILL;
defaultScreenInfo.fUseUnixKillKey = WIN_DEFAULT_UNIX_KILL; defaultScreenInfo.fUseUnixKillKey = WIN_DEFAULT_UNIX_KILL;
defaultScreenInfo.fIgnoreInput = FALSE; defaultScreenInfo.fIgnoreInput = FALSE;
@ -368,6 +319,7 @@ ddxProcessArgument (int argc, char *argv[], int i)
iArgsProcessed = 3; iArgsProcessed = 3;
g_ScreenInfo[nScreenNum].fUserGaveHeightAndWidth = FALSE; g_ScreenInfo[nScreenNum].fUserGaveHeightAndWidth = FALSE;
g_ScreenInfo[nScreenNum].fUserGavePosition = TRUE; g_ScreenInfo[nScreenNum].fUserGavePosition = TRUE;
g_ScreenInfo[nScreenNum].iMonitor = iMonitor;
g_ScreenInfo[nScreenNum].dwWidth = data.monitorWidth; g_ScreenInfo[nScreenNum].dwWidth = data.monitorWidth;
g_ScreenInfo[nScreenNum].dwHeight = data.monitorHeight; g_ScreenInfo[nScreenNum].dwHeight = data.monitorHeight;
g_ScreenInfo[nScreenNum].dwUserWidth = data.monitorWidth; 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"); "Querying monitors is not supported on NT4 and Win95\n");
} else if (data.bMonitorSpecifiedExists == TRUE) } else if (data.bMonitorSpecifiedExists == TRUE)
{ {
g_ScreenInfo[nScreenNum].iMonitor = iMonitor;
g_ScreenInfo[nScreenNum].dwInitialX += data.monitorOffsetX; g_ScreenInfo[nScreenNum].dwInitialX += data.monitorOffsetX;
g_ScreenInfo[nScreenNum].dwInitialY += data.monitorOffsetY; 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); winErrorFVerb (2, "ddxProcessArgument - screen - Found Valid ``@Monitor'' = %d arg\n", iMonitor);
g_ScreenInfo[nScreenNum].fUserGavePosition = TRUE; g_ScreenInfo[nScreenNum].fUserGavePosition = TRUE;
g_ScreenInfo[nScreenNum].iMonitor = iMonitor;
g_ScreenInfo[nScreenNum].dwInitialX = data.monitorOffsetX; g_ScreenInfo[nScreenNum].dwInitialX = data.monitorOffsetX;
g_ScreenInfo[nScreenNum].dwInitialY = data.monitorOffsetY; g_ScreenInfo[nScreenNum].dwInitialY = data.monitorOffsetY;
} }
@ -500,17 +454,6 @@ ddxProcessArgument (int argc, char *argv[], int i)
g_ScreenInfo[nScreenNum].fUserGaveHeightAndWidth = FALSE; 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 */ /* Flag that this screen was explicity specified by the user */
g_ScreenInfo[nScreenNum].fExplicitScreen = TRUE; g_ScreenInfo[nScreenNum].fExplicitScreen = TRUE;
@ -717,12 +660,51 @@ ddxProcessArgument (int argc, char *argv[], int i)
*/ */
if (IS_OPTION ("-scrollbars")) if (IS_OPTION ("-scrollbars"))
{ {
screenInfoPtr->fScrollbars = TRUE;
screenInfoPtr->iResizeMode = resizeWithScrollbars;
/* Indicate that we have processed this argument */ /* Indicate that we have processed this argument */
return 1; 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 #ifdef XWIN_CLIPBOARD
/* /*
@ -1233,24 +1215,3 @@ winLogVersionInfo (void)
ErrorF ("%s\n\n", BUILDERSTRING); ErrorF ("%s\n\n", BUILDERSTRING);
ErrorF ("Contact: %s\n", BUILDERADDR); 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;
}

View File

@ -1,8 +1,9 @@
/* /*
*Copyright (C) 2001-2004 Harold L Hunt II All Rights Reserved. *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 *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 *"Software"), to deal in the Software without restriction, including
*without limitation the rights to use, copy, modify, merge, publish, *without limitation the rights to use, copy, modify, merge, publish,
*distribute, sublicense, and/or sell copies of the Software, and to *distribute, sublicense, and/or sell copies of the Software, and to
@ -20,35 +21,24 @@
*CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION *CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
*WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. *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 *shall not be used in advertising or otherwise to promote the sale, use
*or other dealings in this Software without prior written authorization *or other dealings in this Software without prior written authorization
*from Harold L Hunt II. *from the author(s)
* *
* Authors: Harold L Hunt II * Authors: Harold L Hunt II
* Jon TURNEY
*/ */
#ifdef HAVE_XWIN_CONFIG_H #ifdef HAVE_XWIN_CONFIG_H
#include <xwin-config.h> #include <xwin-config.h>
#endif #endif
#include "win.h" #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
* Local prototypes #endif
*/
static Bool
winRandRGetInfo (ScreenPtr pScreen, Rotation *pRotations);
static Bool
winRandRSetConfig (ScreenPtr pScreen,
Rotation rotateKind,
int rate,
RRScreenSizePtr pSize);
Bool
winRandRInit (ScreenPtr pScreen);
/* /*
@ -58,63 +48,253 @@ winRandRInit (ScreenPtr pScreen);
static Bool static Bool
winRandRGetInfo (ScreenPtr pScreen, Rotation *pRotations) winRandRGetInfo (ScreenPtr pScreen, Rotation *pRotations)
{ {
winScreenPriv(pScreen);
winScreenInfo *pScreenInfo = pScreenPriv->pScreenInfo;
int n;
Rotation rotateKind;
RRScreenSizePtr pSize;
winDebug ("winRandRGetInfo ()\n"); winDebug ("winRandRGetInfo ()\n");
/* Don't support rotations, yet */ /* Don't support rotations */
*pRotations = RR_Rotate_0; *pRotations = RR_Rotate_0;
/* 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;
/* Only one allowed rotation for now */
rotateKind = RR_Rotate_0;
/* /*
* Register supported sizes. This can be called many times, but The screen doesn't have to be limited to the actual
* we only support one size for now. monitor size (we can have scrollbars :-), so what is
*/ the upper limit?
pSize = RRRegisterSize (pScreen, */
pScreenInfo->dwWidth, RRScreenSetSizeRange(pScreen, 0, 0, 4096, 4096);
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; return TRUE;
} }
/* /*
* Respond to resize/rotate request from either X Server or X client app Copied from the xfree86 DDX
*/
static Bool Why can't this be in DIX?
winRandRSetConfig (ScreenPtr pScreen, Does union _Validate vary depending on DDX??
Rotation rotateKind, */
int rate, static void
RRScreenSizePtr pSize) xf86SetRootClip (ScreenPtr pScreen, Bool enable)
{ {
winDebug ("winRandRSetConfig ()\n"); WindowPtr pWin = pScreen->root;
WindowPtr pChild;
Bool WasViewable = (Bool)(pWin->viewable);
Bool anyMarked = FALSE;
WindowPtr pLayerWin;
BoxRec box;
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;
WindowPtr pRoot = pScreen->root;
// Prevent screen updates while we change things around
xf86SetRootClip(pScreen, FALSE);
/* Update the screen size as requested */
pScreenInfo->dwWidth = width;
pScreenInfo->dwHeight = height;
/* Reallocate the framebuffer used by the drawing engine */
(*pScreenPriv->pwinFreeFB)(pScreen);
if (!(*pScreenPriv->pwinAllocateFB)(pScreen))
{
ErrorF ("winDoRandRScreenSetSize - Could not reallocate framebuffer\n");
}
pScreen->width = width;
pScreen->height = height;
pScreen->mmWidth = mmWidth;
pScreen->mmHeight = mmHeight;
/* 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 request
*/
static
Bool
winRandRScreenSetSize (ScreenPtr pScreen,
CARD16 width,
CARD16 height,
CARD16 pixWidth,
CARD16 pixHeight,
CARD32 mmWidth,
CARD32 mmHeight)
{
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; return TRUE;
} }
/* /*
* Initialize the RandR layer. * Initialize the RandR layer.
*/ */
@ -122,8 +302,7 @@ winRandRSetConfig (ScreenPtr pScreen,
Bool Bool
winRandRInit (ScreenPtr pScreen) winRandRInit (ScreenPtr pScreen)
{ {
rrScrPrivPtr pRRScrPriv; rrScrPrivPtr pRRScrPriv;
winDebug ("winRandRInit ()\n"); winDebug ("winRandRInit ()\n");
if (!RRScreenInit (pScreen)) if (!RRScreenInit (pScreen))
@ -135,7 +314,10 @@ winRandRInit (ScreenPtr pScreen)
/* Set some RandR function pointers */ /* Set some RandR function pointers */
pRRScrPriv = rrGetScrPriv (pScreen); pRRScrPriv = rrGetScrPriv (pScreen);
pRRScrPriv->rrGetInfo = winRandRGetInfo; pRRScrPriv->rrGetInfo = winRandRGetInfo;
pRRScrPriv->rrSetConfig = winRandRSetConfig; pRRScrPriv->rrSetConfig = NULL;
pRRScrPriv->rrScreenSetSize = winRandRScreenSetSize;
pRRScrPriv->rrCrtcSet = NULL;
pRRScrPriv->rrCrtcSetGamma = NULL;
return TRUE; return TRUE;
} }

View File

@ -69,10 +69,6 @@ winMWExtWMProcs = {
* Prototypes * Prototypes
*/ */
Bool
winRandRInit (ScreenPtr pScreen);
/* /*
* Local functions * Local functions
*/ */
@ -95,6 +91,7 @@ winScreenInit (int index,
winScreenInfoPtr pScreenInfo = &g_ScreenInfo[index]; winScreenInfoPtr pScreenInfo = &g_ScreenInfo[index];
winPrivScreenPtr pScreenPriv; winPrivScreenPtr pScreenPriv;
HDC hdc; HDC hdc;
DWORD dwInitialBPP;
#if CYGDEBUG || YES #if CYGDEBUG || YES
winDebug ("winScreenInit - dwWidth: %ld dwHeight: %ld\n", winDebug ("winScreenInit - dwWidth: %ld dwHeight: %ld\n",
@ -130,13 +127,30 @@ winScreenInit (int index,
return FALSE; 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)) if (!(*pScreenPriv->pwinAdjustVideoMode) (pScreen))
{ {
ErrorF ("winScreenInit - winAdjustVideoMode () failed\n"); ErrorF ("winScreenInit - winAdjustVideoMode () failed\n");
return FALSE; 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 */ /* Check for supported display depth */
if (!(WIN_SUPPORTED_BPPS & (1 << (pScreenInfo->dwBPP - 1)))) 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 * Check that all monitors have the same display depth if we are using
* multiple monitors * multiple monitors
*/ */
if (pScreenInfo->fMultipleMonitors if (pScreenInfo->fMultipleMonitors
&& !GetSystemMetrics (SM_SAMEDISPLAYFORMAT)) && !GetSystemMetrics (SM_SAMEDISPLAYFORMAT))
{ {
ErrorF ("winScreenInit - Monitors do not all have same pixel format / " ErrorF ("winScreenInit - Monitors do not all have same pixel format / "
"display depth.\n" "display depth.\n");
"Using primary display only.\n"); if (pScreenInfo->dwEngine == WIN_SERVER_SHADOW_GDI)
pScreenInfo->fMultipleMonitors = FALSE; {
ErrorF ("winScreenInit - Performance may suffer off primary display.\n");
}
else
{
ErrorF ("winScreenInit - Using primary display only.\n");
pScreenInfo->fMultipleMonitors = FALSE;
}
} }
/* Create display window */ /* Create display window */
@ -175,13 +196,9 @@ winScreenInit (int index,
/* Get a device context */ /* Get a device context */
hdc = GetDC (pScreenPriv->hwndScreen); hdc = GetDC (pScreenPriv->hwndScreen);
/* Store the initial height, width, and depth of the display */
/* Are we using multiple monitors? */ /* Are we using multiple monitors? */
if (pScreenInfo->fMultipleMonitors) if (pScreenInfo->fMultipleMonitors)
{ {
pScreenPriv->dwLastWindowsWidth = GetSystemMetrics (SM_CXVIRTUALSCREEN);
pScreenPriv->dwLastWindowsHeight = GetSystemMetrics (SM_CYVIRTUALSCREEN);
/* /*
* In this case, some of the defaults set in * In this case, some of the defaults set in
* winInitializeScreenDefaults() are not correct ... * winInitializeScreenDefaults() are not correct ...
@ -190,30 +207,14 @@ winScreenInit (int index,
{ {
pScreenInfo->dwWidth = GetSystemMetrics (SM_CXVIRTUALSCREEN); pScreenInfo->dwWidth = GetSystemMetrics (SM_CXVIRTUALSCREEN);
pScreenInfo->dwHeight = GetSystemMetrics (SM_CYVIRTUALSCREEN); 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 */ /* Release the device context */
ReleaseDC (pScreenPriv->hwndScreen, hdc); ReleaseDC (pScreenPriv->hwndScreen, hdc);
/* Clear the visuals list */ /* Clear the visuals list */
miClearVisualTypes (); miClearVisualTypes ();
/* Set the padded screen width */
pScreenInfo->dwPaddedWidth = PixmapBytePad (pScreenInfo->dwWidth,
pScreenInfo->dwBPP);
/* Call the engine dependent screen initialization procedure */ /* Call the engine dependent screen initialization procedure */
if (!((*pScreenPriv->pwinFinishScreenInit) (index, pScreen, argc, argv))) if (!((*pScreenPriv->pwinFinishScreenInit) (index, pScreen, argc, argv)))
@ -279,14 +280,15 @@ winFinishScreenInitFB (int index,
#endif #endif
/* Create framebuffer */ /* Create framebuffer */
if (!(*pScreenPriv->pwinAllocateFB) (pScreen)) if (!(*pScreenPriv->pwinInitScreen) (pScreen))
{ {
ErrorF ("winFinishScreenInitFB - Could not allocate framebuffer\n"); ErrorF ("winFinishScreenInitFB - Could not allocate framebuffer\n");
return FALSE; 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) if (pScreenInfo->dwBPP == 8)
pScreenInfo->dwDepth = 8; pScreenInfo->dwDepth = 8;
@ -294,7 +296,7 @@ winFinishScreenInitFB (int index,
pScreenInfo->dwDepth = winCountBits (pScreenPriv->dwRedMask) pScreenInfo->dwDepth = winCountBits (pScreenPriv->dwRedMask)
+ winCountBits (pScreenPriv->dwGreenMask) + winCountBits (pScreenPriv->dwGreenMask)
+ winCountBits (pScreenPriv->dwBlueMask); + winCountBits (pScreenPriv->dwBlueMask);
winErrorFVerb (2, "winFinishScreenInitFB - Masks: %08x %08x %08x\n", winErrorFVerb (2, "winFinishScreenInitFB - Masks: %08x %08x %08x\n",
(unsigned int) pScreenPriv->dwRedMask, (unsigned int) pScreenPriv->dwRedMask,
(unsigned int) pScreenPriv->dwGreenMask, (unsigned int) pScreenPriv->dwGreenMask,

View File

@ -239,9 +239,6 @@ winAllocateFBShadowDD (ScreenPtr pScreen)
winDebug ("winAllocateFBShadowDD - Created a clipper\n"); winDebug ("winAllocateFBShadowDD - Created a clipper\n");
#endif #endif
/* Get a device context for the screen */
pScreenPriv->hdcScreen = GetDC (pScreenPriv->hwndScreen);
/* Attach the clipper to our display window */ /* Attach the clipper to our display window */
ddrval = IDirectDrawClipper_SetHWnd (pScreenPriv->pddcPrimary, ddrval = IDirectDrawClipper_SetHWnd (pScreenPriv->pddcPrimary,
0, 0,
@ -503,6 +500,48 @@ winAllocateFBShadowDD (ScreenPtr pScreen)
return TRUE; 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. * Transfer the damaged regions of the shadow framebuffer to the display.
@ -529,6 +568,10 @@ winShadowUpdateDD (ScreenPtr pScreen,
if ((!pScreenPriv->fActive && pScreenInfo->fFullScreen) if ((!pScreenPriv->fActive && pScreenInfo->fFullScreen)
|| pScreenPriv->fBadDepth) return; || 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 */ /* Get the origin of the window in the screen coords */
ptOrigin.x = pScreenInfo->dwXOffset; ptOrigin.x = pScreenInfo->dwXOffset;
ptOrigin.y = pScreenInfo->dwYOffset; ptOrigin.y = pScreenInfo->dwYOffset;
@ -647,25 +690,20 @@ winShadowUpdateDD (ScreenPtr pScreen,
"%s file to " BUILDERADDR "\n", g_pszLogFile); "%s file to " BUILDERADDR "\n", g_pszLogFile);
/* Location of shadow framebuffer has changed */ /* Location of shadow framebuffer has changed */
pScreenInfo->pfb = pScreenPriv->pddsdShadow->lpSurface; winUpdateFBPointer(pScreen, 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;
}
} }
} }
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. * Call the wrapped CloseScreen function.
@ -692,58 +730,18 @@ winCloseScreenShadowDD (int nIndex, ScreenPtr pScreen)
WIN_UNWRAP(CloseScreen); WIN_UNWRAP(CloseScreen);
fReturn = (*pScreen->CloseScreen) (nIndex, pScreen); fReturn = (*pScreen->CloseScreen) (nIndex, pScreen);
winFreeFBShadowDD(pScreen);
/* Free the screen DC */ /* Free the screen DC */
ReleaseDC (pScreenPriv->hwndScreen, pScreenPriv->hdcScreen); ReleaseDC (pScreenPriv->hwndScreen, pScreenPriv->hdcScreen);
/* Delete the window property */ /* Delete the window property */
RemoveProp (pScreenPriv->hwndScreen, WIN_SCR_PROP); 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 */ /* Delete tray icon, if we have one */
if (!pScreenInfo->fNoTrayIcon) if (!pScreenInfo->fNoTrayIcon)
winDeleteNotifyIcon (pScreenPriv); winDeleteNotifyIcon (pScreenPriv);
/* Free the exit confirmation dialog box, if it exists */ /* Free the exit confirmation dialog box, if it exists */
if (g_hDlgExit != NULL) if (g_hDlgExit != NULL)
{ {
@ -766,9 +764,6 @@ winCloseScreenShadowDD (int nIndex, ScreenPtr pScreen)
/* Kill our screeninfo's pointer to the screen */ /* Kill our screeninfo's pointer to the screen */
pScreenInfo->pScreen = NULL; pScreenInfo->pScreen = NULL;
/* Invalidate the ScreenInfo's fb pointer */
pScreenInfo->pfb = NULL;
/* Free the screen privates for this screen */ /* Free the screen privates for this screen */
free ((pointer) pScreenPriv); free ((pointer) pScreenPriv);
@ -909,43 +904,12 @@ winAdjustVideoModeShadowDD (ScreenPtr pScreen)
dwBPP = GetDeviceCaps (hdc, BITSPIXEL); dwBPP = GetDeviceCaps (hdc, BITSPIXEL);
/* DirectDraw can only change the depth in fullscreen mode */ /* 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 */ /* Otherwise, We'll use GDI's depth */
ErrorF ("winAdjustVideoModeShadowDD - Using Windows display "
"depth of %d bits per pixel\n", (int) dwBPP);
/* Use GDI's depth */
pScreenInfo->dwBPP = dwBPP; 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 */ /* Release our DC */
ReleaseDC (NULL, hdc); ReleaseDC (NULL, hdc);
@ -1370,7 +1334,9 @@ winSetEngineFunctionsShadowDD (ScreenPtr pScreen)
/* Set our pointers */ /* Set our pointers */
pScreenPriv->pwinAllocateFB = winAllocateFBShadowDD; pScreenPriv->pwinAllocateFB = winAllocateFBShadowDD;
pScreenPriv->pwinFreeFB = winFreeFBShadowDD;
pScreenPriv->pwinShadowUpdate = winShadowUpdateDD; pScreenPriv->pwinShadowUpdate = winShadowUpdateDD;
pScreenPriv->pwinInitScreen = winInitScreenShadowDD;
pScreenPriv->pwinCloseScreen = winCloseScreenShadowDD; pScreenPriv->pwinCloseScreen = winCloseScreenShadowDD;
pScreenPriv->pwinInitVisuals = winInitVisualsShadowDD; pScreenPriv->pwinInitVisuals = winInitVisualsShadowDD;
pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModeShadowDD; pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModeShadowDD;

View File

@ -237,6 +237,10 @@ winAllocateFBShadowDDNL (ScreenPtr pScreen)
pScreenInfo->dwWidth, pScreenInfo->dwHeight, pScreenInfo->dwDepth); pScreenInfo->dwWidth, pScreenInfo->dwHeight, pScreenInfo->dwDepth);
#endif #endif
/* Set the padded screen width */
pScreenInfo->dwPaddedWidth = PixmapBytePad (pScreenInfo->dwWidth,
pScreenInfo->dwBPP);
/* Allocate memory for our shadow surface */ /* Allocate memory for our shadow surface */
lpSurface = malloc (pScreenInfo->dwPaddedWidth * pScreenInfo->dwHeight); lpSurface = malloc (pScreenInfo->dwPaddedWidth * pScreenInfo->dwHeight);
if (lpSurface == NULL) if (lpSurface == NULL)
@ -266,9 +270,6 @@ winAllocateFBShadowDDNL (ScreenPtr pScreen)
winDebug ("winAllocateFBShadowDDNL - Created a clipper\n"); winDebug ("winAllocateFBShadowDDNL - Created a clipper\n");
#endif #endif
/* Get a device context for the screen */
pScreenPriv->hdcScreen = GetDC (pScreenPriv->hwndScreen);
/* Attach the clipper to our display window */ /* Attach the clipper to our display window */
ddrval = IDirectDrawClipper_SetHWnd (pScreenPriv->pddcPrimary, ddrval = IDirectDrawClipper_SetHWnd (pScreenPriv->pddcPrimary,
0, 0,
@ -530,6 +531,49 @@ winAllocateFBShadowDDNL (ScreenPtr pScreen)
return TRUE; 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) #if defined(XWIN_MULTIWINDOW) || defined(XWIN_MULTIWINDOWEXTWM)
/* /*
@ -605,6 +649,10 @@ winShadowUpdateDDNL (ScreenPtr pScreen,
if ((!pScreenPriv->fActive && pScreenInfo->fFullScreen) if ((!pScreenPriv->fActive && pScreenInfo->fFullScreen)
|| pScreenPriv->fBadDepth) return; || 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 */ /* Get the origin of the window in the screen coords */
ptOrigin.x = pScreenInfo->dwXOffset; ptOrigin.x = pScreenInfo->dwXOffset;
ptOrigin.y = pScreenInfo->dwYOffset; 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. * Call the wrapped CloseScreen function.
@ -746,55 +804,14 @@ winCloseScreenShadowDDNL (int nIndex, ScreenPtr pScreen)
WIN_UNWRAP(CloseScreen); WIN_UNWRAP(CloseScreen);
fReturn = (*pScreen->CloseScreen) (nIndex, pScreen); fReturn = (*pScreen->CloseScreen) (nIndex, pScreen);
winFreeFBShadowDDNL(pScreen);
/* Free the screen DC */ /* Free the screen DC */
ReleaseDC (pScreenPriv->hwndScreen, pScreenPriv->hdcScreen); ReleaseDC (pScreenPriv->hwndScreen, pScreenPriv->hdcScreen);
/* Delete the window property */ /* Delete the window property */
RemoveProp (pScreenPriv->hwndScreen, WIN_SCR_PROP); 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 */ /* Delete tray icon, if we have one */
if (!pScreenInfo->fNoTrayIcon) if (!pScreenInfo->fNoTrayIcon)
winDeleteNotifyIcon (pScreenPriv); winDeleteNotifyIcon (pScreenPriv);
@ -821,9 +838,6 @@ winCloseScreenShadowDDNL (int nIndex, ScreenPtr pScreen)
/* Kill our screeninfo's pointer to the screen */ /* Kill our screeninfo's pointer to the screen */
pScreenInfo->pScreen = NULL; pScreenInfo->pScreen = NULL;
/* Invalidate the ScreenInfo's fb pointer */
pScreenInfo->pfb = NULL;
/* Free the screen privates for this screen */ /* Free the screen privates for this screen */
free ((pointer) pScreenPriv); free ((pointer) pScreenPriv);
@ -964,45 +978,13 @@ winAdjustVideoModeShadowDDNL (ScreenPtr pScreen)
dwBPP = GetDeviceCaps (hdc, BITSPIXEL); dwBPP = GetDeviceCaps (hdc, BITSPIXEL);
/* DirectDraw can only change the depth in fullscreen mode */ /* 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 */ /* Otherwise, We'll use GDI's depth */
winErrorFVerb (2, "winAdjustVideoModeShadowDDNL - Using Windows display "
"depth of %d bits per pixel\n", (int) dwBPP);
/* 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; 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 */ /* Release our DC */
ReleaseDC (NULL, hdc); ReleaseDC (NULL, hdc);
@ -1382,7 +1364,9 @@ winSetEngineFunctionsShadowDDNL (ScreenPtr pScreen)
/* Set our pointers */ /* Set our pointers */
pScreenPriv->pwinAllocateFB = winAllocateFBShadowDDNL; pScreenPriv->pwinAllocateFB = winAllocateFBShadowDDNL;
pScreenPriv->pwinFreeFB = winFreeFBShadowDDNL;
pScreenPriv->pwinShadowUpdate = winShadowUpdateDDNL; pScreenPriv->pwinShadowUpdate = winShadowUpdateDDNL;
pScreenPriv->pwinInitScreen = winInitScreenShadowDDNL;
pScreenPriv->pwinCloseScreen = winCloseScreenShadowDDNL; pScreenPriv->pwinCloseScreen = winCloseScreenShadowDDNL;
pScreenPriv->pwinInitVisuals = winInitVisualsShadowDDNL; pScreenPriv->pwinInitVisuals = winInitVisualsShadowDDNL;
pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModeShadowDDNL; pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModeShadowDDNL;

View File

@ -338,37 +338,20 @@ winAllocateFBShadowGDI (ScreenPtr pScreen)
{ {
winScreenPriv(pScreen); winScreenPriv(pScreen);
winScreenInfo *pScreenInfo = pScreenPriv->pScreenInfo; winScreenInfo *pScreenInfo = pScreenPriv->pScreenInfo;
BITMAPINFOHEADER *pbmih = NULL;
DIBSECTION dibsection; DIBSECTION dibsection;
Bool fReturn = TRUE; 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 */ /* Describe shadow bitmap to be created */
pbmih->biWidth = pScreenInfo->dwWidth; pScreenPriv->pbmih->biWidth = pScreenInfo->dwWidth;
pbmih->biHeight = -pScreenInfo->dwHeight; pScreenPriv->pbmih->biHeight = -pScreenInfo->dwHeight;
ErrorF ("winAllocateFBShadowGDI - Creating DIB with width: %d height: %d " ErrorF ("winAllocateFBShadowGDI - Creating DIB with width: %d height: %d "
"depth: %d\n", "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 */ /* Create a DI shadow bitmap with a bit pointer */
pScreenPriv->hbmpShadow = CreateDIBSection (pScreenPriv->hdcScreen, pScreenPriv->hbmpShadow = CreateDIBSection (pScreenPriv->hdcScreen,
(BITMAPINFO *) pbmih, (BITMAPINFO *) pScreenPriv->pbmih,
DIB_RGB_COLORS, DIB_RGB_COLORS,
(VOID**) &pScreenInfo->pfb, (VOID**) &pScreenInfo->pfb,
NULL, NULL,
@ -449,25 +432,6 @@ winAllocateFBShadowGDI (ScreenPtr pScreen)
(int) pScreenInfo->dwStride); (int) pScreenInfo->dwStride);
#endif #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 #ifdef XWIN_MULTIWINDOW
/* Redraw all windows */ /* Redraw all windows */
if (pScreenInfo->fMultiWindow) if (pScreenInfo->fMultiWindow)
@ -477,6 +441,18 @@ winAllocateFBShadowGDI (ScreenPtr pScreen)
return fReturn; 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 * 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 */ /* See Porting Layer Definition - p. 33 */
/* /*
* We wrap whatever CloseScreen procedure was specified by fb; * 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 */ /* Free the shadow DC; which allows the bitmap to be freed */
DeleteDC (pScreenPriv->hdcShadow); DeleteDC (pScreenPriv->hdcShadow);
/* Free the shadow bitmap */ winFreeFBShadowGDI(pScreen);
DeleteObject (pScreenPriv->hbmpShadow);
/* Free the screen DC */ /* Free the screen DC */
ReleaseDC (pScreenPriv->hwndScreen, pScreenPriv->hdcScreen); ReleaseDC (pScreenPriv->hwndScreen, pScreenPriv->hdcScreen);
@ -665,9 +675,6 @@ winCloseScreenShadowGDI (int nIndex, ScreenPtr pScreen)
/* Invalidate our screeninfo's pointer to the screen */ /* Invalidate our screeninfo's pointer to the screen */
pScreenInfo->pScreen = NULL; pScreenInfo->pScreen = NULL;
/* Invalidate the ScreenInfo's fb pointer */
pScreenInfo->pfb = NULL;
/* Free the screen privates for this screen */ /* Free the screen privates for this screen */
free ((pointer) pScreenPriv); free ((pointer) pScreenPriv);
@ -791,26 +798,9 @@ winAdjustVideoModeShadowGDI (ScreenPtr pScreen)
/* Query GDI for current display depth */ /* Query GDI for current display depth */
dwBPP = GetDeviceCaps (hdc, BITSPIXEL); dwBPP = GetDeviceCaps (hdc, BITSPIXEL);
/* GDI cannot change the screen depth */ /* GDI cannot change the screen depth, so always use GDI's depth */
if (pScreenInfo->dwBPP == WIN_DEFAULT_BPP) pScreenInfo->dwBPP = dwBPP;
{
/* 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);
/* 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 */ /* Release our DC */
ReleaseDC (NULL, hdc); ReleaseDC (NULL, hdc);
hdc = NULL; hdc = NULL;
@ -1235,7 +1225,9 @@ winSetEngineFunctionsShadowGDI (ScreenPtr pScreen)
/* Set our pointers */ /* Set our pointers */
pScreenPriv->pwinAllocateFB = winAllocateFBShadowGDI; pScreenPriv->pwinAllocateFB = winAllocateFBShadowGDI;
pScreenPriv->pwinFreeFB = winFreeFBShadowGDI;
pScreenPriv->pwinShadowUpdate = winShadowUpdateGDI; pScreenPriv->pwinShadowUpdate = winShadowUpdateGDI;
pScreenPriv->pwinInitScreen = winInitScreenShadowGDI;
pScreenPriv->pwinCloseScreen = winCloseScreenShadowGDI; pScreenPriv->pwinCloseScreen = winCloseScreenShadowGDI;
pScreenPriv->pwinInitVisuals = winInitVisualsShadowGDI; pScreenPriv->pwinInitVisuals = winInitVisualsShadowGDI;
pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModeShadowGDI; pScreenPriv->pwinAdjustVideoMode = winAdjustVideoModeShadowGDI;

View File

@ -154,8 +154,8 @@ winValidateArgs (void)
/* Check for !fullscreen and any fullscreen-only parameters */ /* Check for !fullscreen and any fullscreen-only parameters */
if (!g_ScreenInfo[i].fFullScreen if (!g_ScreenInfo[i].fFullScreen
&& (g_ScreenInfo[i].dwRefreshRate != WIN_DEFAULT_BPP && (g_ScreenInfo[i].dwRefreshRate != WIN_DEFAULT_REFRESH
|| g_ScreenInfo[i].dwBPP != WIN_DEFAULT_REFRESH)) || g_ScreenInfo[i].dwBPP != WIN_DEFAULT_BPP))
{ {
ErrorF ("winValidateArgs - -refresh and -depth are only valid " ErrorF ("winValidateArgs - -refresh and -depth are only valid "
"with -fullscreen.\n"); "with -fullscreen.\n");
@ -164,12 +164,12 @@ winValidateArgs (void)
/* Check for fullscreen and any non-fullscreen parameters */ /* Check for fullscreen and any non-fullscreen parameters */
if (g_ScreenInfo[i].fFullScreen if (g_ScreenInfo[i].fFullScreen
&& (g_ScreenInfo[i].fScrollbars && ((g_ScreenInfo[i].iResizeMode != notAllowed)
|| !g_ScreenInfo[i].fDecoration || !g_ScreenInfo[i].fDecoration
|| g_ScreenInfo[i].fLessPointer)) || g_ScreenInfo[i].fLessPointer))
{ {
ErrorF ("winValidateArgs - -fullscreen is invalid with " ErrorF ("winValidateArgs - -fullscreen is invalid with "
"-scrollbars, -nodecoration, or -lesspointer.\n"); "-scrollbars, -resize, -nodecoration, or -lesspointer.\n");
return FALSE; return FALSE;
} }
} }

View File

@ -58,6 +58,7 @@ winReshapeRootless (WindowPtr pWin);
Bool Bool
winCreateWindowNativeGDI (WindowPtr pWin) winCreateWindowNativeGDI (WindowPtr pWin)
{ {
Bool fResult = TRUE;
ScreenPtr pScreen = pWin->drawable.pScreen; ScreenPtr pScreen = pWin->drawable.pScreen;
winWindowPriv(pWin); winWindowPriv(pWin);
winScreenPriv(pScreen); winScreenPriv(pScreen);

View File

@ -40,6 +40,7 @@
#include "winprefs.h" #include "winprefs.h"
#include "winconfig.h" #include "winconfig.h"
#include "winmsg.h" #include "winmsg.h"
#include "winmonitors.h"
#include "inputstr.h" #include "inputstr.h"
/* /*
@ -148,6 +149,13 @@ winWindowProc (HWND hwnd, UINT message,
return 0; return 0;
case WM_DISPLAYCHANGE: 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 */ /* We cannot handle a display mode change during initialization */
if (s_pScreenInfo == NULL) if (s_pScreenInfo == NULL)
FatalError ("winWindowProc - WM_DISPLAYCHANGE - The display " FatalError ("winWindowProc - WM_DISPLAYCHANGE - The display "
@ -167,150 +175,153 @@ winWindowProc (HWND hwnd, UINT message,
#endif #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; 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 " ErrorF ("winWindowProc - WM_DISPLAYCHANGE - new width: %d "
"new height: %d\n", "new height: %d new bpp: %d\n",
LOWORD (lParam), HIWORD (lParam)); LOWORD (lParam), HIWORD (lParam), wParam);
/*
* 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
*/
/* /*
* Check for a disruptive change in depth. * Check for a disruptive change in depth.
* We can only display a message for a disruptive depth change, * We can only display a message for a disruptive depth change,
* we cannot do anything to correct the situation. * 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
#ifdef XWIN_PRIMARYFB
|| 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);
}
else
{
/* Flag that we have a valid screen depth */
s_pScreenPriv->fBadDepth = FALSE;
}
/* /*
* Check for a change in display dimensions. XXX: maybe we need to check if GetSystemMetrics(SM_SAMEDISPLAYFORMAT)
* We can simply recreate the same-sized primary surface when has changed as well...
* the display dimensions change. */
*/ if (s_pScreenInfo->dwBPP != GetDeviceCaps (s_pScreenPriv->hdcScreen, BITSPIXEL))
if (s_pScreenPriv->dwLastWindowsWidth != LOWORD (lParam) {
|| s_pScreenPriv->dwLastWindowsHeight != HIWORD (lParam)) 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
#endif
))
{
/* 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;
}
/*
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 In rootless modes which are monitor or virtual desktop size
* and CreatePrimarySurface function pointers to point use RandR to resize the X screen
* to the no operation function, NoopDDA. This allows us */
* to blindly call these functions, even if they are not if ((!s_pScreenInfo->fUserGaveHeightAndWidth) &&
* relevant to the current engine (e.g., Shadow GDI). (s_pScreenInfo->iResizeMode == resizeWithRandr) &&
*/ (FALSE
#ifdef XWIN_MULTIWINDOWEXTWM
#if CYGDEBUG || s_pScreenInfo->fMWExtWM
winDebug ("winWindowProc - WM_DISPLAYCHANGE - Dimensions changed\n");
#endif #endif
|| s_pScreenInfo->fRootless
/* Release the old primary surface */ #ifdef XWIN_MULTIWINDOW
(*s_pScreenPriv->pwinReleasePrimarySurface) (s_pScreen); || s_pScreenInfo->fMultiWindow
#if CYGDEBUG
winDebug ("winWindowProc - WM_DISPLAYCHANGE - Released "
"primary surface\n");
#endif #endif
))
/* Create the new primary surface */
(*s_pScreenPriv->pwinCreatePrimarySurface) (s_pScreen);
#if CYGDEBUG
winDebug ("winWindowProc - WM_DISPLAYCHANGE - Recreated "
"primary surface\n");
#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
} {
else /*
{ * We can simply recreate the same-sized primary surface when
#if CYGDEBUG * the display dimensions change.
winDebug ("winWindowProc - WM_DISPLAYCHANGE - Dimensions did not " */
"change\n");
#endif /*
* 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; break;
case WM_SIZE: case WM_SIZE:
@ -323,8 +334,8 @@ winWindowProc (HWND hwnd, UINT message,
winDebug ("winWindowProc - WM_SIZE\n"); winDebug ("winWindowProc - WM_SIZE\n");
#endif #endif
/* Break if we do not use scrollbars */ /* Break if we do not allow resizing */
if (!s_pScreenInfo->fScrollbars if ((s_pScreenInfo->iResizeMode == notAllowed)
|| !s_pScreenInfo->fDecoration || !s_pScreenInfo->fDecoration
#ifdef XWIN_MULTIWINDOWEXTWM #ifdef XWIN_MULTIWINDOWEXTWM
|| s_pScreenInfo->fMWExtWM || s_pScreenInfo->fMWExtWM
@ -340,6 +351,17 @@ winWindowProc (HWND hwnd, UINT message,
if (wParam == SIZE_MINIMIZED) if (wParam == SIZE_MINIMIZED)
return 0; 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, * Get the size of the whole window, including client area,
* scrollbars, and non-client area decorations (caption, borders). * scrollbars, and non-client area decorations (caption, borders).
@ -357,10 +379,6 @@ winWindowProc (HWND hwnd, UINT message,
iWidth = rcWindow.right - rcWindow.left; iWidth = rcWindow.right - rcWindow.left;
iHeight = rcWindow.bottom - rcWindow.top; 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. */ /* Subtract the frame size from the window size. */
iWidth -= 2 * GetSystemMetrics (SM_CXSIZEFRAME); iWidth -= 2 * GetSystemMetrics (SM_CXSIZEFRAME);
iHeight -= (2 * GetSystemMetrics (SM_CYSIZEFRAME) iHeight -= (2 * GetSystemMetrics (SM_CYSIZEFRAME)
@ -416,6 +434,37 @@ winWindowProc (HWND hwnd, UINT message,
} }
return 0; 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: case WM_VSCROLL:
{ {
SCROLLINFO si; SCROLLINFO si;
@ -599,7 +648,7 @@ winWindowProc (HWND hwnd, UINT message,
/* Can't do anything without screen info */ /* Can't do anything without screen info */
if (s_pScreenInfo == NULL if (s_pScreenInfo == NULL
|| !s_pScreenInfo->fScrollbars || (s_pScreenInfo->iResizeMode != resizeWithScrollbars)
|| s_pScreenInfo->fFullScreen || s_pScreenInfo->fFullScreen
|| !s_pScreenInfo->fDecoration || !s_pScreenInfo->fDecoration
#ifdef XWIN_MULTIWINDOWEXTWM #ifdef XWIN_MULTIWINDOWEXTWM