[gimp] app: pass the startup monitor to displays opened from the copmmand line



commit 8356003fa2abdf93b92c8f708d99edc756bcce10
Author: Michael Natterer <mitch gimp org>
Date:   Sat May 3 00:54:20 2014 +0200

    app: pass the startup monitor to displays opened from the copmmand line
    
    Change gimp_get_display_name() to also return the screen, and its
    implementation in the GUI to return the initial monitor during
    startup. Retrieve that information in app.c using a weird callback
    construct and pass the monitor to file_open_from_command_line().
    
    Half-related, add screen and monitor parameters to GimpDisplayShell
    and use these initial values for calculating the canvas's initial
    extents.
    
    The image windows still don't position themselves correctly though
    because we have no mechanism for that whatsoever just yet, but we now
    at least pass the needed monitor information to the right objects.

 app/app.c                            |   44 ++++++++++++++++++++++-----
 app/core/gimp-gui.c                  |   15 +++++----
 app/core/gimp-gui.h                  |    6 ++-
 app/display/gimpdisplay.c            |    4 ++-
 app/display/gimpdisplayshell.c       |   54 ++++++++++++++++++++++++++-------
 app/display/gimpdisplayshell.h       |    6 +++-
 app/gui/gui-vtable.c                 |   31 +++++++++++--------
 app/gui/gui-vtable.h                 |    8 ++++-
 app/gui/gui.c                        |   19 ++++++++++-
 app/plug-in/gimppluginmanager-call.c |    4 ++-
 10 files changed, 144 insertions(+), 47 deletions(-)
---
diff --git a/app/app.c b/app/app.c
index 7c621cd..609aa33 100644
--- a/app/app.c
+++ b/app/app.c
@@ -70,12 +70,20 @@
 
 /*  local prototypes  */
 
-static void       app_init_update_noop    (const gchar  *text1,
-                                           const gchar  *text2,
-                                           gdouble       percentage);
-static gboolean   app_exit_after_callback (Gimp         *gimp,
-                                           gboolean      kill_it,
-                                           GMainLoop   **loop);
+static void       app_init_update_noop       (const gchar        *text1,
+                                              const gchar        *text2,
+                                              gdouble             percentage);
+static void       app_restore_after_callback (Gimp               *gimp,
+                                              GimpInitStatusFunc  status_callback);
+static gboolean   app_exit_after_callback    (Gimp               *gimp,
+                                              gboolean            kill_it,
+                                              GMainLoop         **loop);
+
+
+/*  local variables  */
+
+static GObject *initial_screen  = NULL;
+static gint     initial_monitor = 0;
 
 
 /*  public functions  */
@@ -224,6 +232,14 @@ app_run (const gchar         *full_prog_name,
   /*  initialize lowlevel stuff  */
   gimp_gegl_init (gimp);
 
+  /*  Connect our restore_after callback before gui_init() connects
+   *  theirs, so ours runs first and can grab the initial monitor
+   *  before the GUI's restore_after callback resets it.
+   */
+  g_signal_connect_after (gimp, "restore",
+                          G_CALLBACK (app_restore_after_callback),
+                          NULL);
+
 #ifndef GIMP_CONSOLE_COMPILATION
   if (! no_interface)
     update_status_func = gui_init (gimp, no_splash);
@@ -262,8 +278,8 @@ app_run (const gchar         *full_prog_name,
         {
           if (run_loop)
             file_open_from_command_line (gimp, filenames[i], as_new,
-                                         NULL, /* FIXME monitor */
-                                         0 /* FIXME monitor */);
+                                         initial_screen,
+                                         initial_monitor);
         }
     }
 
@@ -298,6 +314,18 @@ app_init_update_noop (const gchar *text1,
   /*  deliberately do nothing  */
 }
 
+static void
+app_restore_after_callback (Gimp               *gimp,
+                            GimpInitStatusFunc  status_callback)
+{
+  /*  Getting the display name for a -1 display returns the initial
+   *  monitor during startup. Need to call this from a restore_after
+   *  callback, because before restore(), the GUI can't return anything,
+   *  after after restore() the initial monitor gets reset.
+   */
+  g_free (gimp_get_display_name (gimp, -1, &initial_screen, &initial_monitor));
+}
+
 static gboolean
 app_exit_after_callback (Gimp       *gimp,
                          gboolean    kill_it,
diff --git a/app/core/gimp-gui.c b/app/core/gimp-gui.c
index 27e1c05..71ff90c 100644
--- a/app/core/gimp-gui.c
+++ b/app/core/gimp-gui.c
@@ -214,17 +214,20 @@ gimp_get_program_class (Gimp *gimp)
 }
 
 gchar *
-gimp_get_display_name (Gimp *gimp,
-                       gint  display_ID,
-                       gint *monitor_number)
+gimp_get_display_name (Gimp     *gimp,
+                       gint      display_ID,
+                       GObject **screen,
+                       gint     *monitor)
 {
   g_return_val_if_fail (GIMP_IS_GIMP (gimp), NULL);
-  g_return_val_if_fail (monitor_number != NULL, NULL);
+  g_return_val_if_fail (screen != NULL, NULL);
+  g_return_val_if_fail (monitor != NULL, NULL);
 
   if (gimp->gui.get_display_name)
-    return gimp->gui.get_display_name (gimp, display_ID, monitor_number);
+    return gimp->gui.get_display_name (gimp, display_ID, screen, monitor);
 
-  *monitor_number = 0;
+  *screen  = NULL;
+  *monitor = 0;
 
   return NULL;
 }
diff --git a/app/core/gimp-gui.h b/app/core/gimp-gui.h
index be6225c..9d371f2 100644
--- a/app/core/gimp-gui.h
+++ b/app/core/gimp-gui.h
@@ -44,7 +44,8 @@ struct _GimpGui
   const gchar  * (* get_program_class)     (Gimp                *gimp);
   gchar        * (* get_display_name)      (Gimp                *gimp,
                                             gint                 display_ID,
-                                            gint                *monitor_number);
+                                            GObject            **screen,
+                                            gint                *monitor);
   guint32        (* get_user_time)         (Gimp                *gimp);
 
   const gchar  * (* get_theme_dir)         (Gimp                *gimp);
@@ -144,7 +145,8 @@ void           gimp_free_progress         (Gimp                *gimp,
 const gchar  * gimp_get_program_class     (Gimp                *gimp);
 gchar        * gimp_get_display_name      (Gimp                *gimp,
                                            gint                 display_ID,
-                                           gint                *monitor_number);
+                                           GObject            **screen,
+                                           gint                *monitor);
 guint32        gimp_get_user_time         (Gimp                *gimp);
 const gchar  * gimp_get_theme_dir         (Gimp                *gimp);
 
diff --git a/app/display/gimpdisplay.c b/app/display/gimpdisplay.c
index c94b8ab..06b8abe 100644
--- a/app/display/gimpdisplay.c
+++ b/app/display/gimpdisplay.c
@@ -453,7 +453,9 @@ gimp_display_new (Gimp              *gimp,
 
   /*  create the shell for the image  */
   private->shell = gimp_display_shell_new (display, unit, scale,
-                                           popup_manager);
+                                           popup_manager,
+                                           screen,
+                                           monitor);
 
   shell = gimp_display_get_shell (display);
 
diff --git a/app/display/gimpdisplayshell.c b/app/display/gimpdisplayshell.c
index 8e97261..ee78cd9 100644
--- a/app/display/gimpdisplayshell.c
+++ b/app/display/gimpdisplayshell.c
@@ -96,6 +96,8 @@ enum
 {
   PROP_0,
   PROP_POPUP_MANAGER,
+  PROP_INITIAL_SCREEN,
+  PROP_INITIAL_MONITOR,
   PROP_DISPLAY,
   PROP_UNIT,
   PROP_TITLE,
@@ -257,6 +259,20 @@ gimp_display_shell_class_init (GimpDisplayShellClass *klass)
                                                         GIMP_PARAM_READWRITE |
                                                         G_PARAM_CONSTRUCT_ONLY));
 
+  g_object_class_install_property (object_class, PROP_INITIAL_SCREEN,
+                                   g_param_spec_object ("initial-screen",
+                                                        NULL, NULL,
+                                                        GDK_TYPE_SCREEN,
+                                                        GIMP_PARAM_READWRITE |
+                                                        G_PARAM_CONSTRUCT_ONLY));
+
+  g_object_class_install_property (object_class, PROP_INITIAL_MONITOR,
+                                   g_param_spec_int ("initial-monitor",
+                                                     NULL, NULL,
+                                                     0, 16, 0,
+                                                     GIMP_PARAM_READWRITE |
+                                                     G_PARAM_CONSTRUCT_ONLY));
+
   g_object_class_install_property (object_class, PROP_DISPLAY,
                                    g_param_spec_object ("display", NULL, NULL,
                                                         GIMP_TYPE_DISPLAY,
@@ -370,7 +386,6 @@ gimp_display_shell_constructed (GObject *object)
   GtkWidget             *lower_hbox;
   GtkWidget             *inner_table;
   GtkWidget             *gtk_image;
-  GdkScreen             *screen;
   GtkAction             *action;
   gint                   image_width;
   gint                   image_height;
@@ -402,12 +417,10 @@ gimp_display_shell_constructed (GObject *object)
 
   shell->dot_for_dot = config->default_dot_for_dot;
 
-  screen = gtk_widget_get_screen (GTK_WIDGET (shell));
-
   if (config->monitor_res_from_gdk)
     {
-      gimp_get_monitor_resolution (screen, /* FIXME monitor */
-                                   0, /* FIXME monitor */
+      gimp_get_monitor_resolution (shell->initial_screen,
+                                   shell->initial_monitor,
                                    &shell->monitor_xres, &shell->monitor_yres);
     }
   else
@@ -908,6 +921,12 @@ gimp_display_shell_set_property (GObject      *object,
     case PROP_POPUP_MANAGER:
       shell->popup_manager = g_value_get_object (value);
       break;
+    case PROP_INITIAL_SCREEN:
+      shell->initial_screen = g_value_get_object (value);
+      break;
+    case PROP_INITIAL_MONITOR:
+      shell->initial_monitor = g_value_get_int (value);
+      break;
     case PROP_DISPLAY:
       shell->display = g_value_get_object (value);
       break;
@@ -947,6 +966,12 @@ gimp_display_shell_get_property (GObject    *object,
     case PROP_POPUP_MANAGER:
       g_value_set_object (value, shell->popup_manager);
       break;
+    case PROP_INITIAL_SCREEN:
+      g_value_set_object (value, shell->initial_screen);
+      break;
+    case PROP_INITIAL_MONITOR:
+      g_value_set_int (value, shell->initial_monitor);
+      break;
     case PROP_DISPLAY:
       g_value_set_object (value, shell->display);
       break;
@@ -1176,18 +1201,23 @@ gimp_display_shell_transform_overlay (GimpDisplayShell *shell,
 /*  public functions  */
 
 GtkWidget *
-gimp_display_shell_new (GimpDisplay       *display,
-                        GimpUnit           unit,
-                        gdouble            scale,
-                        GimpUIManager     *popup_manager)
+gimp_display_shell_new (GimpDisplay   *display,
+                        GimpUnit       unit,
+                        gdouble        scale,
+                        GimpUIManager *popup_manager,
+                        GdkScreen     *screen,
+                        gint           monitor)
 {
   g_return_val_if_fail (GIMP_IS_DISPLAY (display), NULL);
   g_return_val_if_fail (GIMP_IS_UI_MANAGER (popup_manager), NULL);
+  g_return_val_if_fail (GDK_IS_SCREEN (screen), NULL);
 
   return g_object_new (GIMP_TYPE_DISPLAY_SHELL,
-                       "popup-manager", popup_manager,
-                       "display",       display,
-                       "unit",          unit,
+                       "popup-manager",   popup_manager,
+                       "initial-screen",  screen,
+                       "initial-monitor", monitor,
+                       "display",         display,
+                       "unit",            unit,
                        NULL);
 }
 
diff --git a/app/display/gimpdisplayshell.h b/app/display/gimpdisplayshell.h
index e5074bb..d459b8a 100644
--- a/app/display/gimpdisplayshell.h
+++ b/app/display/gimpdisplayshell.h
@@ -52,6 +52,8 @@ struct _GimpDisplayShell
   GimpDisplay       *display;
 
   GimpUIManager     *popup_manager;
+  GdkScreen         *initial_screen;
+  gint               initial_monitor;
 
   GimpDisplayOptions *options;
   GimpDisplayOptions *fullscreen_options;
@@ -214,7 +216,9 @@ GType             gimp_display_shell_get_type      (void) G_GNUC_CONST;
 GtkWidget       * gimp_display_shell_new           (GimpDisplay        *display,
                                                     GimpUnit            unit,
                                                     gdouble             scale,
-                                                    GimpUIManager      *popup_manager);
+                                                    GimpUIManager      *popup_manager,
+                                                    GdkScreen          *screen,
+                                                    gint                monitor);
 
 void              gimp_display_shell_add_overlay   (GimpDisplayShell   *shell,
                                                     GtkWidget          *child,
diff --git a/app/gui/gui-vtable.c b/app/gui/gui-vtable.c
index b964876..426e94b 100644
--- a/app/gui/gui-vtable.c
+++ b/app/gui/gui-vtable.c
@@ -72,6 +72,7 @@
 
 #include "menus/menus.h"
 
+#include "gui.h"
 #include "gui-message.h"
 #include "gui-vtable.h"
 #include "themes.h"
@@ -92,7 +93,8 @@ static void           gui_help                  (Gimp                *gimp,
 static const gchar  * gui_get_program_class     (Gimp                *gimp);
 static gchar        * gui_get_display_name      (Gimp                *gimp,
                                                  gint                 display_ID,
-                                                 gint                *monitor_number);
+                                                 GObject            **screen,
+                                                 gint                *monitor);
 static guint32        gui_get_user_time         (Gimp                *gimp);
 static const gchar  * gui_get_theme_dir         (Gimp                *gimp);
 static GimpObject   * gui_get_window_strategy   (Gimp                *gimp);
@@ -233,13 +235,13 @@ gui_get_program_class (Gimp *gimp)
 }
 
 static gchar *
-gui_get_display_name (Gimp *gimp,
-                      gint  display_ID,
-                      gint *monitor_number)
+gui_get_display_name (Gimp     *gimp,
+                      gint      display_ID,
+                      GObject **screen,
+                      gint     *monitor)
 {
-  GimpDisplay *display = NULL;
-  GdkScreen   *screen;
-  gint         monitor;
+  GimpDisplay *display   = NULL;
+  GdkScreen   *my_screen = NULL;
 
   if (display_ID > 0)
     display = gimp_display_get_by_ID (gimp, display_ID);
@@ -249,18 +251,21 @@ gui_get_display_name (Gimp *gimp,
       GimpDisplayShell *shell  = gimp_display_get_shell (display);
       GdkWindow        *window = gtk_widget_get_window (GTK_WIDGET (shell));
 
-      screen  = gtk_widget_get_screen (GTK_WIDGET (shell));
-      monitor = gdk_screen_get_monitor_at_window (screen, window);
+      my_screen = gtk_widget_get_screen (GTK_WIDGET (shell));
+      *monitor = gdk_screen_get_monitor_at_window (my_screen, window);
     }
   else
     {
-      monitor = gimp_get_monitor_at_pointer (&screen);
+      *monitor = gui_get_initial_monitor (gimp, &my_screen);
+
+      if (*monitor == -1)
+        *monitor = gimp_get_monitor_at_pointer (&my_screen);
     }
 
-  *monitor_number = monitor;
+  *screen = G_OBJECT (my_screen);
 
-  if (screen)
-    return gdk_screen_make_display_name (screen);
+  if (my_screen)
+    return gdk_screen_make_display_name (my_screen);
 
   return NULL;
 }
diff --git a/app/gui/gui-vtable.h b/app/gui/gui-vtable.h
index d0108c3..b23f0db 100644
--- a/app/gui/gui-vtable.h
+++ b/app/gui/gui-vtable.h
@@ -19,7 +19,13 @@
 #define __GUI_VTABLE_H__
 
 
-void   gui_vtable_init (Gimp *gimp);
+void   gui_vtable_init        (Gimp       *gimp);
+
+/*  this function lives in gui.c but must only be used from gui-vtable.c;
+ *  also, gui.h can't contain any Gdk types.
+ */
+gint  gui_get_initial_monitor (Gimp       *gimp,
+                               GdkScreen **screen);
 
 
 #endif /* __GUI_VTABLE_H__ */
diff --git a/app/gui/gui.c b/app/gui/gui.c
index 0ad2b70..25f96b2 100644
--- a/app/gui/gui.c
+++ b/app/gui/gui.c
@@ -141,7 +141,7 @@ static Gimp             *the_gui_gimp     = NULL;
 static GimpUIManager    *image_ui_manager = NULL;
 static GimpUIConfigurer *ui_configurer    = NULL;
 static GdkScreen        *initial_screen   = NULL;
-static gint              initial_monitor  = 0;
+static gint              initial_monitor  = -1;
 
 
 /*  public functions  */
@@ -264,6 +264,18 @@ gui_init (Gimp     *gimp,
   return status_callback;
 }
 
+gint
+gui_get_initial_monitor (Gimp       *gimp,
+                         GdkScreen **screen)
+{
+  g_return_val_if_fail (GIMP_IS_GIMP (gimp), 0);
+  g_return_val_if_fail (screen != NULL, 0);
+
+  *screen = initial_screen;
+
+  return initial_monitor;
+}
+
 
 /*  private functions  */
 
@@ -300,7 +312,6 @@ gui_sanity_check (void)
   return NULL;
 }
 
-
 static void
 gui_help_func (const gchar *help_id,
                gpointer     help_data)
@@ -595,6 +606,10 @@ gui_restore_after_callback (Gimp               *gimp,
 
   /*  indicate that the application has finished loading  */
   gdk_notify_startup_complete ();
+
+  /*  clear startup monitor variables  */
+  initial_screen  = NULL;
+  initial_monitor = -1;
 }
 
 static gboolean
diff --git a/app/plug-in/gimppluginmanager-call.c b/app/plug-in/gimppluginmanager-call.c
index c16adf6..a85112e 100644
--- a/app/plug-in/gimppluginmanager-call.c
+++ b/app/plug-in/gimppluginmanager-call.c
@@ -161,6 +161,7 @@ gimp_plug_in_manager_call_run (GimpPlugInManager   *manager,
       GPConfig           config;
       GPProcRun          proc_run;
       gint               display_ID;
+      GObject           *screen;
       gint               monitor;
 
       if (! gimp_plug_in_open (plug_in, GIMP_PLUG_IN_CALL_RUN, FALSE))
@@ -203,7 +204,8 @@ gimp_plug_in_manager_call_run (GimpPlugInManager   *manager,
       config.app_name         = (gchar *) g_get_application_name ();
       config.wm_class         = (gchar *) gimp_get_program_class (manager->gimp);
       config.display_name     = gimp_get_display_name (manager->gimp,
-                                                       display_ID, &monitor);
+                                                       display_ID,
+                                                       &screen, &monitor);
       config.monitor_number   = monitor;
       config.timestamp        = gimp_get_user_time (manager->gimp);
 


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]