File gnome-control-center-bnc556000-bgo590823-randr-mirror-enable-monitor.diff of Package gnome-control-center

From 7d9f0be02c51500c229a29c86f309db5f236a625 Mon Sep 17 00:00:00 2001
From: Federico Mena Quintero <federico@novell.com>
Date: Wed, 9 Dec 2009 15:59:11 -0600
Subject: [PATCH 1/4] RANDR - automatically turn on outputs which support Mirror Screens

Previously, outputs could remain off if the user just selected Mirror Screens.
Now we automatically turn on all the outputs which support the clone mode,
to avoid extra work on the part of the user.

Signed-off-by: Federico Mena Quintero <federico@novell.com>
---
 capplets/display/xrandr-capplet.c |   79 +++++++++++++++++++++++++++++++++++++
 1 files changed, 79 insertions(+), 0 deletions(-)

diff --git a/capplets/display/xrandr-capplet.c b/capplets/display/xrandr-capplet.c
index 592c170..8eadf53 100644
--- a/capplets/display/xrandr-capplet.c
+++ b/capplets/display/xrandr-capplet.c
@@ -866,6 +866,69 @@ lay_out_outputs_horizontally (App *app)
 
 }
 
+/* FIXME: this function is copied from gnome-settings-daemon/plugins/xrandr/gsd-xrandr-manager.c.
+ * Do we need to put this function in gnome-desktop for public use?
+ */
+static gboolean
+get_clone_size (GnomeRRScreen *screen, int *width, int *height)
+{
+        GnomeRRMode **modes = gnome_rr_screen_list_clone_modes (screen);
+        int best_w, best_h;
+        int i;
+
+        best_w = 0;
+        best_h = 0;
+
+        for (i = 0; modes[i] != NULL; ++i) {
+                GnomeRRMode *mode = modes[i];
+                int w, h;
+
+                w = gnome_rr_mode_get_width (mode);
+                h = gnome_rr_mode_get_height (mode);
+
+                if (w * h > best_w * best_h) {
+                        best_w = w;
+                        best_h = h;
+                }
+        }
+
+        if (best_w > 0 && best_h > 0) {
+                if (width)
+                        *width = best_w;
+                if (height)
+                        *height = best_h;
+
+                return TRUE;
+        }
+
+        return FALSE;
+}
+
+static gboolean
+output_info_supports_mode (App *app, GnomeOutputInfo *info, int width, int height)
+{
+    GnomeRROutput *output;
+    GnomeRRMode **modes;
+    int i;
+
+    if (!info->connected)
+	return FALSE;
+
+    output = gnome_rr_screen_get_output_by_name (app->screen, info->name);
+    if (!output)
+	return FALSE;
+
+    modes = gnome_rr_output_list_modes (output);
+
+    for (i = 0; modes[i]; i++) {
+	if (gnome_rr_mode_get_width (modes[i]) == width
+	    && gnome_rr_mode_get_height (modes[i]) == height)
+	    return TRUE;
+    }
+
+    return FALSE;
+}
+
 static void
 on_clone_changed (GtkWidget *box, gpointer data)
 {
@@ -877,6 +940,7 @@ on_clone_changed (GtkWidget *box, gpointer data)
     if (app->current_configuration->clone)
     {
 	int i;
+	int width, height;
 
 	for (i = 0; app->current_configuration->outputs[i]; ++i)
 	{
@@ -886,6 +950,21 @@ on_clone_changed (GtkWidget *box, gpointer data)
 		break;
 	    }
 	}
+
+	/* Turn on all the connected screens that support the best clone mode.
+	 * The user may hit "Mirror Screens", but he shouldn't have to turn on
+	 * all the required outputs as well.
+	 */
+
+	get_clone_size (app->screen, &width, &height);
+
+	for (i = 0; app->current_configuration->outputs[i]; i++) {
+	    if (output_info_supports_mode (app, app->current_configuration->outputs[i], width, height)) {
+		app->current_configuration->outputs[i]->on = TRUE;
+		app->current_configuration->outputs[i]->width = width;
+		app->current_configuration->outputs[i]->height = height;
+	    }
+	}
     }
     else
     {
-- 
1.6.0.2


From fba1240fbf5abbe7348af2e992b1dd7a852fe6c8 Mon Sep 17 00:00:00 2001
From: Federico Mena Quintero <federico@novell.com>
Date: Thu, 10 Dec 2009 12:06:01 -0600
Subject: [PATCH 2/4] RANDR - Sensitize 'Mirror Screens' depending on whether mirror mode is actually supported

Previously it was always sensitive, even if there were not enough connected outputs
for mirroring, or if those those outputs didn't support the same resolution for
mirroring.

Signed-off-by: Federico Mena Quintero <federico@novell.com>
---
 capplets/display/xrandr-capplet.c |   70 ++++++++++++++++++++++++++++++++++---
 1 files changed, 65 insertions(+), 5 deletions(-)

diff --git a/capplets/display/xrandr-capplet.c b/capplets/display/xrandr-capplet.c
index 8eadf53..d1dda56 100644
--- a/capplets/display/xrandr-capplet.c
+++ b/capplets/display/xrandr-capplet.c
@@ -81,12 +81,15 @@ struct App
 };
 
 static void rebuild_gui (App *app);
+static void on_clone_changed (GtkWidget *box, gpointer data);
 static void on_rate_changed (GtkComboBox *box, gpointer data);
 static gboolean output_overlaps (GnomeOutputInfo *output, GnomeRRConfig *config);
 static void select_current_output_from_dialog_position (App *app);
 static void monitor_on_off_toggled_cb (GtkToggleButton *toggle, gpointer data);
 static void get_geometry (GnomeOutputInfo *output, int *w, int *h);
 static void apply_configuration_returned_cb (DBusGProxy *proxy, DBusGProxyCall *call_id, void *data);
+static gboolean get_clone_size (GnomeRRScreen *screen, int *width, int *height);
+static gboolean output_info_supports_mode (App *app, GnomeOutputInfo *info, int width, int height);
 
 #define ROTATE_TABLET_KEY "/apps/gnome_settings_daemon/xrandr/rotate_tablet_with_monitor"
 
@@ -425,6 +428,67 @@ count_all_outputs (GnomeRRConfig *config)
 }
 #endif
 
+/* Computes whether "Mirror Screens" (clone mode) is supported based on these criteria:
+ *
+ * 1. There is an available size for cloning.
+ *
+ * 2. There are 2 or more connected outputs that support that size.
+ */
+static gboolean
+mirror_screens_is_supported (App *app)
+{
+    int clone_width, clone_height;
+    gboolean have_clone_size;
+    gboolean mirror_is_supported;
+
+    mirror_is_supported = FALSE;
+
+    have_clone_size = get_clone_size (app->screen, &clone_width, &clone_height);
+
+    if (have_clone_size) {
+	int i;
+	int num_outputs_with_clone_size;
+
+	num_outputs_with_clone_size = 0;
+
+	for (i = 0; app->current_configuration->outputs[i] != NULL; i++)
+	{
+	    GnomeOutputInfo *output = app->current_configuration->outputs[i];
+
+	    /* We count the connected outputs that support the clone size.  It
+	     * doesn't matter if those outputs aren't actually On currently; we
+	     * will turn them on in on_clone_changed().
+	     */
+	    if (output->connected && output_info_supports_mode (app, output, clone_width, clone_height))
+		num_outputs_with_clone_size++;
+	}
+
+	if (num_outputs_with_clone_size >= 2)
+	    mirror_is_supported = TRUE;
+    }
+
+    return mirror_is_supported;
+}
+
+static void
+rebuild_mirror_screens (App *app)
+{
+    gboolean mirror_is_active;
+    gboolean mirror_is_supported;
+
+    g_signal_handlers_block_by_func (app->clone_checkbox, G_CALLBACK (on_clone_changed), app);
+
+    mirror_is_active = app->current_configuration && app->current_configuration->clone;
+
+    /* If mirror_is_active, then it *must* be possible to turn mirroring off */
+    mirror_is_supported = mirror_is_active || mirror_screens_is_supported (app);
+    
+    gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (app->clone_checkbox), mirror_is_active);
+    gtk_widget_set_sensitive (app->clone_checkbox, mirror_is_supported);
+
+    g_signal_handlers_unblock_by_func (app->clone_checkbox, G_CALLBACK (on_clone_changed), app);
+}
+
 static void
 rebuild_current_monitor_label (App *app)
 {
@@ -605,6 +669,7 @@ rebuild_gui (App *app)
     g_debug ("rebuild gui, is on: %d", app->current_output->on);
 #endif
 
+    rebuild_mirror_screens (app);
     rebuild_current_monitor_label (app);
     rebuild_on_off_radios (app);
     rebuild_resolution_combo (app);
@@ -617,11 +682,6 @@ rebuild_gui (App *app)
     gtk_widget_set_sensitive (app->panel_checkbox, sensitive);
 
     app->ignore_gui_changes = FALSE;
-
-    if (app->current_configuration && app->current_configuration->clone)
-	gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (app->clone_checkbox), TRUE);
-    else
-	gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (app->clone_checkbox), FALSE);
 }
 
 static gboolean
-- 
1.6.0.2


From 284edaf990394432ffccd231f383c732beb21ca2 Mon Sep 17 00:00:00 2001
From: Federico Mena Quintero <federico@novell.com>
Date: Thu, 10 Dec 2009 12:09:24 -0600
Subject: [PATCH 3/4] RANDR - Desensitize the on/off radio buttons if we are in Mirror Screens mode

This makes it even more obvious that you don't need to turn on
individual outputs for Mirror Screens to work properly.

It also means that we don't support "combined" setups like two mirrored
screens and one extended screen.  It seems that the majority of people only care about a few cases:

  - Laptop plus projector or monitor showing the same thing.
  - Computer plus secondary monitor(s) with an extended desktop.
  - Laptop plus docking station with external monitor only (built-in LCD turned off).

For more exotic combinations, people can use the xrandr(1) tool.

Signed-off-by: Federico Mena Quintero <federico@novell.com>
---
 capplets/display/xrandr-capplet.c |   12 +++++-------
 1 files changed, 5 insertions(+), 7 deletions(-)

diff --git a/capplets/display/xrandr-capplet.c b/capplets/display/xrandr-capplet.c
index d1dda56..883f6c4 100644
--- a/capplets/display/xrandr-capplet.c
+++ b/capplets/display/xrandr-capplet.c
@@ -550,7 +550,11 @@ rebuild_on_off_radios (App *app)
     g_signal_handlers_block_by_func (app->monitor_on_radio, G_CALLBACK (monitor_on_off_toggled_cb), app);
     g_signal_handlers_block_by_func (app->monitor_off_radio, G_CALLBACK (monitor_on_off_toggled_cb), app);
 
-    if (app->current_output)
+    sensitive = FALSE;
+    on_active = FALSE;
+    off_active = FALSE;
+
+    if (!app->current_configuration->clone && app->current_output)
     {
 	if (count_active_outputs (app) > 1 || !app->current_output->on)
 	    sensitive = TRUE;
@@ -560,12 +564,6 @@ rebuild_on_off_radios (App *app)
 	on_active = app->current_output->on;
 	off_active = !on_active;
     }
-    else
-    {
-	sensitive = FALSE;
-	on_active = FALSE;
-	off_active = FALSE;
-    }
 
     gtk_widget_set_sensitive (app->monitor_on_radio, sensitive);
     gtk_widget_set_sensitive (app->monitor_off_radio, sensitive);
-- 
1.6.0.2


From 685e6c47dfc31c2a8b27899dea7acbfbf3bd7147 Mon Sep 17 00:00:00 2001
From: Federico Mena Quintero <federico@novell.com>
Date: Fri, 11 Dec 2009 11:36:27 -0600
Subject: [PATCH 4/4] RANDR - Show 'Mirror Screens' in the monitor label, not a random monitor's name

Signed-off-by: Federico Mena Quintero <federico@novell.com>
---
 capplets/display/xrandr-capplet.c |    6 +++++-
 1 files changed, 5 insertions(+), 1 deletions(-)

diff --git a/capplets/display/xrandr-capplet.c b/capplets/display/xrandr-capplet.c
index 883f6c4..8c04d13 100644
--- a/capplets/display/xrandr-capplet.c
+++ b/capplets/display/xrandr-capplet.c
@@ -499,7 +499,11 @@ rebuild_current_monitor_label (App *app)
 
 	if (app->current_output)
 	{
-	    str = g_strdup_printf (_("<b>Monitor: %s</b>"), app->current_output->display_name);
+	    if (app->current_configuration->clone)
+		str = g_strdup_printf ("<b>%s</b>", _("Mirror Screens"));
+	    else
+		str = g_strdup_printf (_("<b>Monitor: %s</b>"), app->current_output->display_name);
+
 	    free_str = TRUE;
 	    gnome_rr_labeler_get_color_for_output (app->labeler, app->current_output, &color);
 	    use_color = TRUE;
-- 
1.6.0.2

openSUSE Build Service is sponsored by