main: Add --virtual-monitor argument

Make it possible to create persintent virtual monitors using command
line argument. This will not be the only way to create virtual monitors,
the primary way will be using the screen cast API, but using command
line argumenst is convenient for debugging purposes.

Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1698>
This commit is contained in:
Jonas Ådahl 2021-01-26 23:04:37 +01:00 committed by Marge Bot
parent 51ff51c854
commit 005c49063d

View File

@ -76,6 +76,8 @@
#endif #endif
#include "backends/meta-backend-private.h" #include "backends/meta-backend-private.h"
#include "backends/meta-monitor-manager-private.h"
#include "backends/meta-virtual-monitor.h"
#include "backends/x11/cm/meta-backend-x11-cm.h" #include "backends/x11/cm/meta-backend-x11-cm.h"
#include "backends/x11/meta-backend-x11.h" #include "backends/x11/meta-backend-x11.h"
#include "clutter/clutter.h" #include "clutter/clutter.h"
@ -140,6 +142,10 @@ static GMainLoop *meta_main_loop = NULL;
static void prefs_changed_callback (MetaPreference pref, static void prefs_changed_callback (MetaPreference pref,
gpointer data); gpointer data);
#ifdef HAVE_NATIVE_BACKEND
static void release_virtual_monitors (void);
#endif
/** /**
* meta_print_compilation_info: * meta_print_compilation_info:
* *
@ -213,6 +219,13 @@ static gboolean opt_headless;
#endif #endif
static gboolean opt_x11; static gboolean opt_x11;
#ifdef HAVE_NATIVE_BACKEND
static gboolean opt_virtual_monitor_cb (const char *option_name,
const char *value,
gpointer data,
GError **error);
#endif
static GOptionEntry meta_options[] = { static GOptionEntry meta_options[] = {
{ {
"sm-disable", 0, 0, G_OPTION_ARG_NONE, "sm-disable", 0, 0, G_OPTION_ARG_NONE,
@ -286,6 +299,11 @@ static GOptionEntry meta_options[] = {
&opt_headless, &opt_headless,
N_("Run as a headless display server") N_("Run as a headless display server")
}, },
{
"virtual-monitor", 0, 0, G_OPTION_ARG_CALLBACK,
&opt_virtual_monitor_cb,
N_("Add persistent virtual monitor (WxH or WxH@R)")
},
#endif #endif
{ {
"x11", 0, 0, G_OPTION_ARG_NONE, "x11", 0, 0, G_OPTION_ARG_NONE,
@ -358,6 +376,10 @@ meta_finalize (void)
meta_wayland_finalize (); meta_wayland_finalize ();
#endif #endif
#ifdef HAVE_NATIVE_BACKEND
release_virtual_monitors ();
#endif
meta_release_backend (); meta_release_backend ();
} }
@ -458,6 +480,92 @@ check_for_wayland_session_type (void)
} }
#endif #endif
#ifdef HAVE_NATIVE_BACKEND
static GList *opt_virtual_monitor_infos = NULL;
static GList *persistent_virtual_monitors = NULL;
static gboolean
opt_virtual_monitor_cb (const char *option_name,
const char *value,
gpointer data,
GError **error)
{
int width, height;
float refresh_rate = 60.0;
if (sscanf (value, "%dx%d@%f",
&width, &height, &refresh_rate) == 3 ||
sscanf (value, "%dx%d",
&width, &height) == 2)
{
g_autofree char *serial = NULL;
MetaVirtualMonitorInfo *virtual_monitor;
serial = g_strdup_printf ("0x%.2x",
g_list_length (opt_virtual_monitor_infos));
virtual_monitor = meta_virtual_monitor_info_new (width,
height,
refresh_rate,
"MetaVendor",
"MetaVirtualMonitor",
serial);
opt_virtual_monitor_infos = g_list_append (opt_virtual_monitor_infos,
virtual_monitor);
return TRUE;
}
else
{
return FALSE;
}
}
static void
release_virtual_monitors (void)
{
g_list_free_full (persistent_virtual_monitors, g_object_unref);
persistent_virtual_monitors = NULL;
}
static void
add_persistent_virtual_monitors (void)
{
MetaBackend *backend = meta_get_backend ();
MetaMonitorManager *monitor_manager =
meta_backend_get_monitor_manager (backend);
GList *l;
for (l = opt_virtual_monitor_infos; l; l = l->next)
{
MetaVirtualMonitorInfo *info = l->data;
g_autoptr (GError) error = NULL;
MetaVirtualMonitor *virtual_monitor;
virtual_monitor =
meta_monitor_manager_create_virtual_monitor (monitor_manager,
info,
&error);
if (!virtual_monitor)
{
g_warning ("Failed to add virtual monitor: %s", error->message);
meta_exit (META_EXIT_ERROR);
}
persistent_virtual_monitors = g_list_append (persistent_virtual_monitors,
virtual_monitor);
}
if (opt_virtual_monitor_infos)
{
g_list_free_full (opt_virtual_monitor_infos,
(GDestroyNotify) meta_virtual_monitor_info_free);
opt_virtual_monitor_infos = NULL;
meta_monitor_manager_reload (monitor_manager);
}
}
#endif
/* /*
* Determine the compositor configuration, i.e. whether to run as a Wayland * Determine the compositor configuration, i.e. whether to run as a Wayland
* compositor, as well as what backend to use. * compositor, as well as what backend to use.
@ -751,6 +859,10 @@ meta_init (void)
g_array_free (_backend_property_values, TRUE); g_array_free (_backend_property_values, TRUE);
} }
#ifdef HAVE_NATIVE_BACKEND
add_persistent_virtual_monitors ();
#endif
meta_set_syncing (opt_sync || (g_getenv ("MUTTER_SYNC") != NULL)); meta_set_syncing (opt_sync || (g_getenv ("MUTTER_SYNC") != NULL));
if (opt_replace_wm) if (opt_replace_wm)