From: Rémi Bernon rbernon@codeweavers.com
--- dlls/win32u/sysparams.c | 121 +++++++++++++++--------------------- dlls/winex11.drv/xinerama.c | 3 - dlls/winex11.drv/xrandr.c | 1 - 3 files changed, 51 insertions(+), 74 deletions(-)
diff --git a/dlls/win32u/sysparams.c b/dlls/win32u/sysparams.c index 988da5a7641..a617d613ffc 100644 --- a/dlls/win32u/sysparams.c +++ b/dlls/win32u/sysparams.c @@ -1294,10 +1294,8 @@ static BOOL write_source_to_registry( const struct source *source, HKEY *source_ return TRUE; }
-static void add_source( const char *name, UINT state_flags, void *param ) +static void add_source( struct device_manager_ctx *ctx, const char *name, UINT state_flags ) { - struct device_manager_ctx *ctx = param; - TRACE( "name %s, state_flags %#x\n", name, state_flags );
if (ctx->source_key) @@ -1324,6 +1322,19 @@ static void add_source( const char *name, UINT state_flags, void *param ) } }
+static void add_physical_source( const char *name, UINT state_flags, void *param ) +{ + struct device_manager_ctx *ctx = param; + + TRACE( "name %s, state_flags %#x\n", name, state_flags ); + + /* in virtual desktop mode, report all physical sources as detached */ + ctx->is_primary = !!(state_flags & DISPLAY_DEVICE_PRIMARY_DEVICE); + if (is_virtual_desktop()) state_flags &= ~(DISPLAY_DEVICE_ATTACHED_TO_DESKTOP | DISPLAY_DEVICE_PRIMARY_DEVICE); + + add_source( ctx, name, state_flags ); +} + static BOOL write_monitor_to_registry( struct monitor *monitor, const BYTE *edid, UINT edid_len ) { char buffer[1024], *tmp; @@ -1440,13 +1451,20 @@ static void add_monitor( const struct gdi_monitor *gdi_monitor, void *param ) static void add_mode( const DEVMODEW *mode, BOOL current, void *param ) { struct device_manager_ctx *ctx = param; - DEVMODEW nopos_mode; + DEVMODEW nopos_mode, detached_mode;
if (!ctx->gpu.source_count) { static const DWORD source_flags = DISPLAY_DEVICE_ATTACHED_TO_DESKTOP | DISPLAY_DEVICE_PRIMARY_DEVICE | DISPLAY_DEVICE_VGA_COMPATIBLE; TRACE( "adding default fake source\n" ); - add_source( "Default", source_flags, ctx ); + add_physical_source( "Default", source_flags, ctx ); + } + + if (ctx->is_primary && current) + { + ctx->primary_bpp = mode->dmBitsPerPel; + ctx->primary_width = mode->dmPelsWidth; + ctx->primary_height = mode->dmPelsHeight; }
nopos_mode = *mode; @@ -1454,13 +1472,20 @@ static void add_mode( const DEVMODEW *mode, BOOL current, void *param ) nopos_mode.dmPosition.y = 0; nopos_mode.dmFields &= ~DM_POSITION;
+ detached_mode = *mode; + detached_mode.dmPelsWidth = 0; + detached_mode.dmPelsHeight = 0; + + if (!(ctx->source.state_flags & DISPLAY_DEVICE_ATTACHED_TO_DESKTOP)) + mode = &detached_mode; + if (write_source_mode( ctx->source_key, ctx->source.mode_count, &nopos_mode )) { ctx->source.mode_count++; set_reg_value( ctx->source_key, mode_countW, REG_DWORD, &ctx->source.mode_count, sizeof(ctx->source.mode_count) ); if (current) { - if (!read_source_mode( ctx->source_key, ENUM_REGISTRY_SETTINGS, &nopos_mode )) + if (mode == &detached_mode || !read_source_mode( ctx->source_key, ENUM_REGISTRY_SETTINGS, &nopos_mode )) write_source_mode( ctx->source_key, ENUM_REGISTRY_SETTINGS, mode ); write_source_mode( ctx->source_key, ENUM_CURRENT_SETTINGS, mode ); } @@ -1470,7 +1495,7 @@ static void add_mode( const DEVMODEW *mode, BOOL current, void *param ) static const struct gdi_device_manager device_manager = { add_gpu, - add_source, + add_physical_source, add_monitor, add_mode, }; @@ -1783,12 +1808,6 @@ static BOOL default_update_display_devices( const struct gdi_device_manager *man return TRUE; }
-static BOOL update_display_devices( const struct gdi_device_manager *manager, BOOL force, struct device_manager_ctx *ctx ) -{ - if (user_driver->pUpdateDisplayDevices( manager, force, ctx )) return TRUE; - return default_update_display_devices( manager, force, ctx ); -} - /* parse the desktop size specification */ static BOOL parse_size( const WCHAR *size, unsigned int *width, unsigned int *height ) { @@ -1821,44 +1840,9 @@ static BOOL get_default_desktop_size( unsigned int *width, unsigned int *height return TRUE; }
-static void desktop_add_gpu( const struct gdi_gpu *gpu, void *param ) -{ -} - -static void desktop_add_source( const char *name, UINT state_flags, void *param ) -{ - struct device_manager_ctx *ctx = param; - ctx->is_primary = !!(state_flags & DISPLAY_DEVICE_PRIMARY_DEVICE); -} - -static void desktop_add_monitor( const struct gdi_monitor *monitor, void *param ) -{ -} - -static void desktop_add_mode( const DEVMODEW *mode, BOOL current, void *param ) -{ - struct device_manager_ctx *ctx = param; - - if (ctx->is_primary && current) - { - ctx->primary_bpp = mode->dmBitsPerPel; - ctx->primary_width = mode->dmPelsWidth; - ctx->primary_height = mode->dmPelsHeight; - } -} - -static const struct gdi_device_manager desktop_device_manager = -{ - desktop_add_gpu, - desktop_add_source, - desktop_add_monitor, - desktop_add_mode, -}; - -static BOOL desktop_update_display_devices( BOOL force, struct device_manager_ctx *ctx ) +static BOOL add_virtual_source( struct device_manager_ctx *ctx ) { static const DWORD source_flags = DISPLAY_DEVICE_ATTACHED_TO_DESKTOP | DISPLAY_DEVICE_PRIMARY_DEVICE | DISPLAY_DEVICE_VGA_COMPATIBLE; - static const struct gdi_gpu gpu; struct gdi_monitor monitor = {0}; static struct screen_size { @@ -1898,7 +1882,6 @@ static BOOL desktop_update_display_devices( BOOL force, struct device_manager_ct {2560, 1600} };
- struct device_manager_ctx desktop_ctx = {0}; UINT screen_width, screen_height, max_width, max_height; unsigned int depths[] = {8, 16, 0}; DEVMODEW current, mode = @@ -1908,13 +1891,9 @@ static BOOL desktop_update_display_devices( BOOL force, struct device_manager_ct }; UINT i, j;
- if (!force) return TRUE; - /* in virtual desktop mode, read the device list from the user driver but expose virtual devices */ - if (!update_display_devices( &desktop_device_manager, TRUE, &desktop_ctx )) return FALSE; - - max_width = desktop_ctx.primary_width; - max_height = desktop_ctx.primary_height; - depths[ARRAY_SIZE(depths) - 1] = desktop_ctx.primary_bpp; + max_width = ctx->primary_width; + max_height = ctx->primary_height; + depths[ARRAY_SIZE(depths) - 1] = ctx->primary_bpp;
if (!get_default_desktop_size( &screen_width, &screen_height )) { @@ -1922,13 +1901,12 @@ static BOOL desktop_update_display_devices( BOOL force, struct device_manager_ct screen_height = max_height; }
- add_gpu( &gpu, ctx ); - add_source( "Default", source_flags, ctx ); + add_source( ctx, "Virtual", source_flags ); if (!read_source_mode( ctx->source_key, ENUM_CURRENT_SETTINGS, ¤t )) { current = mode; current.dmFields |= DM_POSITION; - current.dmBitsPerPel = desktop_ctx.primary_bpp; + current.dmBitsPerPel = ctx->primary_bpp; current.dmPelsWidth = screen_width; current.dmPelsHeight = screen_height; } @@ -1973,13 +1951,24 @@ static BOOL desktop_update_display_devices( BOOL force, struct device_manager_ct return TRUE; }
+static BOOL update_display_devices( BOOL force, struct device_manager_ctx *ctx ) +{ + if (user_driver->pUpdateDisplayDevices( &device_manager, force, ctx )) + { + if (ctx->source_count && is_virtual_desktop()) return add_virtual_source( ctx ); + return TRUE; + } + + return default_update_display_devices( &device_manager, force, ctx ); +} + BOOL update_display_cache( BOOL force ) { static const WCHAR wine_service_station_name[] = {'_','_','w','i','n','e','s','e','r','v','i','c','e','_','w','i','n','s','t','a','t','i','o','n',0}; HWINSTA winstation = NtUserGetProcessWindowStation(); struct device_manager_ctx ctx = {0}; - BOOL was_virtual_desktop, ret; + BOOL ret; WCHAR name[MAX_PATH];
/* services do not have any adapters, only a virtual monitor */ @@ -1993,15 +1982,7 @@ BOOL update_display_cache( BOOL force ) return TRUE; }
- if ((was_virtual_desktop = is_virtual_desktop())) ret = TRUE; - else ret = update_display_devices( &device_manager, force, &ctx ); - - /* as update_display_devices calls the user driver, it starts explorer and may change the virtual desktop state */ - if (ret && is_virtual_desktop()) - { - reset_display_manager_ctx( &ctx ); - ret = desktop_update_display_devices( force || !was_virtual_desktop, &ctx ); - } + ret = update_display_devices( force, &ctx );
release_display_manager_ctx( &ctx ); if (!ret) WARN( "Failed to update display devices\n" ); diff --git a/dlls/winex11.drv/xinerama.c b/dlls/winex11.drv/xinerama.c index 426ea6c11d4..fbf80819204 100644 --- a/dlls/winex11.drv/xinerama.c +++ b/dlls/winex11.drv/xinerama.c @@ -344,9 +344,6 @@ void xinerama_init( unsigned int width, unsigned int height ) int i; RECT rect;
- if (is_virtual_desktop()) - return; - pthread_mutex_lock( &xinerama_mutex );
SetRect( &rect, 0, 0, width, height ); diff --git a/dlls/winex11.drv/xrandr.c b/dlls/winex11.drv/xrandr.c index 0e7b9a07818..002ab77c086 100644 --- a/dlls/winex11.drv/xrandr.c +++ b/dlls/winex11.drv/xrandr.c @@ -1662,7 +1662,6 @@ void X11DRV_XRandR_Init(void)
if (major) return; /* already initialized? */ if (!usexrandr) return; /* disabled in config */ - if (is_virtual_desktop()) return; if (!(ret = load_xrandr())) return; /* can't load the Xrandr library */
/* see if Xrandr is available */