Commit 320442a4 authored by Rémi Bernon's avatar Rémi Bernon Committed by Alexandre Julliard

win32u: Add all display device source modes at once.

parent ee0aad5c
......@@ -416,6 +416,18 @@ static void get_monitor_info_from_edid( struct edid_monitor_info *info, const un
}
}
static const char *debugstr_devmodew( const DEVMODEW *devmode )
{
char position[32] = {0};
if (devmode->dmFields & DM_POSITION) snprintf( position, sizeof(position), " at %s", wine_dbgstr_point( (POINT *)&devmode->dmPosition ) );
return wine_dbg_sprintf( "%ux%u %ubits %uHz rotated %u degrees %sstretched %sinterlaced%s",
(UINT)devmode->dmPelsWidth, (UINT)devmode->dmPelsHeight, (UINT)devmode->dmBitsPerPel,
(UINT)devmode->dmDisplayFrequency, (UINT)devmode->dmDisplayOrientation * 90,
devmode->dmDisplayFixedOutput == DMDFO_STRETCH ? "" : "un",
devmode->dmDisplayFlags & DM_INTERLACED ? "" : "non-",
position );
}
static BOOL write_source_mode( HKEY hkey, UINT index, const DEVMODEW *mode )
{
WCHAR bufferW[MAX_PATH] = {0};
......@@ -1432,27 +1444,24 @@ static void add_monitor( const struct gdi_monitor *gdi_monitor, void *param )
}
}
static void add_mode( const DEVMODEW *mode, BOOL current, void *param )
static void add_modes( const DEVMODEW *current, UINT modes_count, const DEVMODEW *modes, void *param )
{
struct device_manager_ctx *ctx = param;
DEVMODEW nopos_mode;
const DEVMODEW *mode;
DEVMODEW dummy;
nopos_mode = *mode;
nopos_mode.dmPosition.x = 0;
nopos_mode.dmPosition.y = 0;
nopos_mode.dmFields &= ~DM_POSITION;
TRACE( "current %s, modes_count %u, modes %p, param %p\n", debugstr_devmodew( current ), modes_count, modes, param );
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, &dummy ))
write_source_mode( ctx->source_key, ENUM_REGISTRY_SETTINGS, current );
write_source_mode( ctx->source_key, ENUM_CURRENT_SETTINGS, current );
for (mode = modes; modes_count; mode = NEXT_DEVMODEW(mode), modes_count--)
{
if (!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 );
}
TRACE( "mode: %s\n", debugstr_devmodew( mode ) );
if (write_source_mode( ctx->source_key, ctx->source.mode_count, mode )) ctx->source.mode_count++;
}
set_reg_value( ctx->source_key, mode_countW, REG_DWORD, &ctx->source.mode_count, sizeof(ctx->source.mode_count) );
}
static const struct gdi_device_manager device_manager =
......@@ -1460,7 +1469,7 @@ static const struct gdi_device_manager device_manager =
add_gpu,
add_source,
add_monitor,
add_mode,
add_modes,
};
static void reset_display_manager_ctx( struct device_manager_ctx *ctx )
......@@ -1711,15 +1720,6 @@ static BOOL update_display_cache_from_registry(void)
return ret;
}
static BOOL is_same_devmode( const DEVMODEW *a, const DEVMODEW *b )
{
return a->dmDisplayOrientation == b->dmDisplayOrientation &&
a->dmBitsPerPel == b->dmBitsPerPel &&
a->dmPelsWidth == b->dmPelsWidth &&
a->dmPelsHeight == b->dmPelsHeight &&
a->dmDisplayFrequency == b->dmDisplayFrequency;
}
static BOOL default_update_display_devices( const struct gdi_device_manager *manager, BOOL force, struct device_manager_ctx *ctx )
{
/* default implementation: expose an adapter and a monitor with a few standard modes,
......@@ -1744,7 +1744,6 @@ static BOOL default_update_display_devices( const struct gdi_device_manager *man
static const struct gdi_gpu gpu;
struct gdi_monitor monitor = {0};
DEVMODEW mode = {{0}};
UINT i;
if (!force) return TRUE;
......@@ -1762,11 +1761,7 @@ static BOOL default_update_display_devices( const struct gdi_device_manager *man
monitor.rc_work.bottom = mode.dmPelsHeight;
manager->add_monitor( &monitor, ctx );
for (i = 0; i < ARRAY_SIZE(modes); ++i)
{
if (is_same_devmode( modes + i, &mode )) manager->add_mode( &mode, TRUE, ctx );
else manager->add_mode( modes + i, FALSE, ctx );
}
manager->add_modes( &mode, ARRAY_SIZE(modes), modes, ctx );
return TRUE;
}
......@@ -1823,10 +1818,10 @@ static void desktop_add_monitor( const struct gdi_monitor *monitor, void *param
{
}
static void desktop_add_mode( const DEVMODEW *mode, BOOL current, void *param )
static void desktop_add_modes( const DEVMODEW *current, UINT modes_count, const DEVMODEW *modes, void *param )
{
struct device_manager_ctx *ctx = param;
if (ctx->is_primary && current) ctx->primary = *mode;
if (ctx->is_primary) ctx->primary = *current;
}
static const struct gdi_device_manager desktop_device_manager =
......@@ -1834,7 +1829,7 @@ static const struct gdi_device_manager desktop_device_manager =
desktop_add_gpu,
desktop_add_source,
desktop_add_monitor,
desktop_add_mode,
desktop_add_modes,
};
static BOOL desktop_update_display_devices( BOOL force, struct device_manager_ctx *ctx )
......@@ -1881,9 +1876,9 @@ static BOOL desktop_update_display_devices( BOOL force, struct device_manager_ct
};
struct device_manager_ctx desktop_ctx = {0};
UINT screen_width, screen_height, max_width, max_height;
UINT screen_width, screen_height, max_width, max_height, modes_count;
unsigned int depths[] = {8, 16, 0};
DEVMODEW current;
DEVMODEW current, *modes;
UINT i, j;
if (!force) return TRUE;
......@@ -1915,7 +1910,9 @@ static BOOL desktop_update_display_devices( BOOL force, struct device_manager_ct
monitor.rc_work.bottom = current.dmPelsHeight;
add_monitor( &monitor, ctx );
for (i = 0; i < ARRAY_SIZE(depths); ++i)
if (!(modes = malloc( ARRAY_SIZE(depths) * (ARRAY_SIZE(screen_sizes) + 2) * sizeof(*modes) ))) return FALSE;
for (modes_count = i = 0; i < ARRAY_SIZE(depths); ++i)
{
DEVMODEW mode =
{
......@@ -1932,25 +1929,24 @@ static BOOL desktop_update_display_devices( BOOL force, struct device_manager_ct
if (mode.dmPelsWidth > max_width || mode.dmPelsHeight > max_height) continue;
if (mode.dmPelsWidth == max_width && mode.dmPelsHeight == max_height) continue;
if (mode.dmPelsWidth == screen_width && mode.dmPelsHeight == screen_height) continue;
if (is_same_devmode( &mode, &current )) add_mode( &current, TRUE, ctx );
else add_mode( &mode, FALSE, ctx );
modes[modes_count++] = mode;
}
mode.dmPelsWidth = screen_width;
mode.dmPelsHeight = screen_height;
if (is_same_devmode( &mode, &current )) add_mode( &current, TRUE, ctx );
else add_mode( &mode, FALSE, ctx );
modes[modes_count++] = mode;
if (max_width != screen_width || max_height != screen_height)
{
mode.dmPelsWidth = max_width;
mode.dmPelsHeight = max_height;
if (is_same_devmode( &mode, &current )) add_mode( &current, TRUE, ctx );
else add_mode( &mode, FALSE, ctx );
modes[modes_count++] = mode;
}
}
add_modes( &current, modes_count, modes, ctx );
free( modes );
return TRUE;
}
......
......@@ -283,13 +283,17 @@ BOOL ANDROID_UpdateDisplayDevices( const struct gdi_device_manager *device_manag
const DEVMODEW mode =
{
.dmFields = DM_DISPLAYORIENTATION | DM_PELSWIDTH | DM_PELSHEIGHT | DM_BITSPERPEL |
DM_DISPLAYFLAGS | DM_DISPLAYFREQUENCY | DM_POSITION,
DM_DISPLAYFLAGS | DM_DISPLAYFREQUENCY,
.dmBitsPerPel = screen_bpp, .dmPelsWidth = screen_width, .dmPelsHeight = screen_height, .dmDisplayFrequency = 60,
};
DEVMODEW current = mode;
device_manager->add_gpu( &gpu, param );
device_manager->add_source( "Default", source_flags, param );
device_manager->add_monitor( &gdi_monitor, param );
device_manager->add_mode( &mode, TRUE, param );
current.dmFields |= DM_POSITION;
device_manager->add_modes( &current, 1, &mode, param );
force_display_devices_refresh = FALSE;
}
......
......@@ -1110,27 +1110,6 @@ static BOOL is_same_devmode(const DEVMODEW *a, const DEVMODEW *b)
a->dmDisplayFrequency == b->dmDisplayFrequency;
}
static const char *debugstr_devmodew(const DEVMODEW *devmode)
{
char position[32] = {0};
if (devmode->dmFields & DM_POSITION)
{
snprintf(position, sizeof(position), " at (%d,%d)",
(int)devmode->dmPosition.x, (int)devmode->dmPosition.y);
}
return wine_dbg_sprintf("%ux%u %ubits %uHz rotated %u degrees %sstretched %sinterlaced%s",
(unsigned int)devmode->dmPelsWidth,
(unsigned int)devmode->dmPelsHeight,
(unsigned int)devmode->dmBitsPerPel,
(unsigned int)devmode->dmDisplayFrequency,
(unsigned int)devmode->dmDisplayOrientation * 90,
devmode->dmDisplayFixedOutput == DMDFO_STRETCH ? "" : "un",
devmode->dmDisplayFlags & DM_INTERLACED ? "" : "non-",
position);
}
BOOL macdrv_UpdateDisplayDevices( const struct gdi_device_manager *device_manager, BOOL force, void *param )
{
struct macdrv_adapter *adapters, *adapter;
......@@ -1211,23 +1190,7 @@ BOOL macdrv_UpdateDisplayDevices( const struct gdi_device_manager *device_manage
}
if (!(modes = display_get_modes(adapter->id, &mode_count))) break;
TRACE("adapter: %#x, mode count: %d\n", adapter->id, mode_count);
/* Initialize modes */
for (mode = modes; mode < modes + mode_count; mode++)
{
if (is_same_devmode(mode, &current_mode))
{
TRACE("current mode: %s\n", debugstr_devmodew(&current_mode));
device_manager->add_mode( &current_mode, TRUE, param );
}
else
{
TRACE("mode: %s\n", debugstr_devmodew(mode));
device_manager->add_mode( mode, FALSE, param );
}
}
device_manager->add_modes( &current_mode, mode_count, modes, param );
free(modes);
macdrv_free_monitors(monitors);
}
......
......@@ -251,22 +251,28 @@ static void populate_devmode(struct wayland_output_mode *output_mode, DEVMODEW *
static void wayland_add_device_modes(const struct gdi_device_manager *device_manager,
void *param, struct output_info *output_info)
{
DEVMODEW *modes, current = {.dmSize = sizeof(current)};
struct wayland_output_mode *output_mode;
int modes_count = 0;
if (!(modes = malloc(output_info->output->modes_count * sizeof(*modes))))
return;
populate_devmode(output_info->output->current_mode, &current);
current.dmFields |= DM_POSITION;
current.dmPosition.x = output_info->x;
current.dmPosition.y = output_info->y;
RB_FOR_EACH_ENTRY(output_mode, &output_info->output->modes,
struct wayland_output_mode, entry)
{
DEVMODEW mode = {.dmSize = sizeof(mode)};
BOOL mode_is_current = output_mode == output_info->output->current_mode;
populate_devmode(output_mode, &mode);
if (mode_is_current)
{
mode.dmFields |= DM_POSITION;
mode.dmPosition.x = output_info->x;
mode.dmPosition.y = output_info->y;
}
device_manager->add_mode(&mode, mode_is_current, param);
modes[modes_count++] = mode;
}
device_manager->add_modes(&current, modes_count, modes, param);
free(modes);
}
/***********************************************************************
......
......@@ -97,6 +97,7 @@ static void wayland_output_state_add_mode(struct wayland_output_state *state,
mode->height = height;
mode->refresh = refresh;
rb_put(&state->modes, mode, &mode->entry);
state->modes_count++;
}
if (current) state->current_mode = mode;
......@@ -144,6 +145,7 @@ static void wayland_output_done(struct wayland_output *output)
}
rb_destroy(&output->pending.modes, wayland_output_mode_free_rb, NULL);
rb_init(&output->pending.modes, wayland_output_mode_cmp_rb);
output->pending.modes_count = 0;
}
if (output->pending_flags & WAYLAND_OUTPUT_CHANGED_NAME)
......@@ -321,7 +323,9 @@ BOOL wayland_output_create(uint32_t id, uint32_t version)
wl_list_init(&output->link);
rb_init(&output->pending.modes, wayland_output_mode_cmp_rb);
output->pending.modes_count = 0;
rb_init(&output->current.modes, wayland_output_mode_cmp_rb);
output->current.modes_count = 0;
/* Have a fallback while we don't have compositor given name. */
name_len = snprintf(NULL, 0, "WaylandOutput%d", next_output_id);
......
......@@ -142,6 +142,7 @@ struct wayland_output_mode
struct wayland_output_state
{
int modes_count;
struct rb_tree modes;
struct wayland_output_mode *current_mode;
char *name;
......
......@@ -494,25 +494,6 @@ BOOL X11DRV_DisplayDevices_SupportEventHandlers(void)
static BOOL force_display_devices_refresh;
static const char *debugstr_devmodew( const DEVMODEW *devmode )
{
char position[32] = {0};
if (devmode->dmFields & DM_POSITION)
{
snprintf( position, sizeof(position), " at (%d,%d)",
(int)devmode->dmPosition.x, (int)devmode->dmPosition.y );
}
return wine_dbg_sprintf( "%ux%u %ubits %uHz rotated %u degrees%s",
(unsigned int)devmode->dmPelsWidth,
(unsigned int)devmode->dmPelsHeight,
(unsigned int)devmode->dmBitsPerPel,
(unsigned int)devmode->dmDisplayFrequency,
(unsigned int)devmode->dmDisplayOrientation * 90,
position );
}
BOOL X11DRV_UpdateDisplayDevices( const struct gdi_device_manager *device_manager, BOOL force, void *param )
{
struct x11drv_adapter *adapters;
......@@ -520,7 +501,7 @@ BOOL X11DRV_UpdateDisplayDevices( const struct gdi_device_manager *device_manage
struct gdi_gpu *gpus;
INT gpu_count, adapter_count, monitor_count;
INT gpu, adapter, monitor;
DEVMODEW *modes, *mode;
DEVMODEW *modes;
UINT mode_count;
if (!force && !force_display_devices_refresh) return TRUE;
......@@ -566,26 +547,12 @@ BOOL X11DRV_UpdateDisplayDevices( const struct gdi_device_manager *device_manage
if (!settings_handler.get_id( devname, is_primary, &settings_id )) break;
settings_handler.get_current_mode( settings_id, &current_mode );
if (!settings_handler.get_modes( settings_id, EDS_ROTATEDMODE, &modes, &mode_count ))
continue;
for (mode = modes; mode_count; mode_count--)
{
if (is_same_devmode( mode, &current_mode ))
{
TRACE( "current mode: %s\n", debugstr_devmodew( &current_mode ) );
device_manager->add_mode( &current_mode, TRUE, param );
}
else
if (settings_handler.get_modes( settings_id, EDS_ROTATEDMODE, &modes, &mode_count ))
{
TRACE( "mode: %s\n", debugstr_devmodew( mode ) );
device_manager->add_mode( mode, FALSE, param );
}
mode = (DEVMODEW *)((char *)mode + sizeof(*modes) + modes[0].dmDriverExtra);
}
device_manager->add_modes( &current_mode, mode_count, modes, param );
settings_handler.free_modes( modes );
}
}
host_handler.free_adapters( adapters );
}
......
......@@ -262,7 +262,7 @@ struct gdi_device_manager
void (*add_gpu)( const struct gdi_gpu *gpu, void *param );
void (*add_source)( const char *name, UINT state_flags, void *param );
void (*add_monitor)( const struct gdi_monitor *monitor, void *param );
void (*add_mode)( const DEVMODEW *mode, BOOL current, void *param );
void (*add_modes)( const DEVMODEW *current, UINT modes_count, const DEVMODEW *modes, void *param );
};
#define WINE_DM_UNSUPPORTED 0x80000000
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment