1 /*
2  * Copyright (C) 2008-2010 Nick Schermer <nick@xfce.org>
3  *
4  * This program is free software; you can redistribute it and/or modify
5  * it under the terms of the GNU General Public License as published by
6  * the Free Software Foundation; either version 2 of the License, or
7  * (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License along
15  * with this program; if not, write to the Free Software Foundation, Inc.,
16  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
17  */
18 
19 #ifdef HAVE_CONFIG_H
20 #include <config.h>
21 #endif
22 
23 #ifdef HAVE_STDLIB_H
24 #include <stdlib.h>
25 #endif
26 
27 #include <libxfce4util/libxfce4util.h>
28 #include <libxfce4ui/libxfce4ui.h>
29 
30 #include <common/panel-private.h>
31 #include <common/panel-utils.h>
32 
33 #include <libxfce4panel/libxfce4panel.h>
34 #include <libxfce4panel/xfce-panel-plugin-provider.h>
35 
36 #include <panel/panel-window.h>
37 #include <panel/panel-application.h>
38 #include <panel/panel-dialogs.h>
39 #include <panel/panel-module.h>
40 #include <panel/panel-itembar.h>
41 #include <panel/panel-item-dialog.h>
42 #include <panel/panel-preferences-dialog.h>
43 #include <panel/panel-preferences-dialog-ui.h>
44 #include <panel/panel-plugin-external.h>
45 
46 #define PREFERENCES_HELP_URL "http://www.xfce.org"
47 
48 
49 
50 static void                     panel_preferences_dialog_finalize               (GObject                *object);
51 static void                     panel_preferences_dialog_response               (GtkWidget              *window,
52                                                                                  gint                    response_id,
53                                                                                  PanelPreferencesDialog *dialog);
54 static void                     panel_preferences_dialog_bindings_unbind        (PanelPreferencesDialog *dialog);
55 static void                     panel_preferences_dialog_bindings_add           (PanelPreferencesDialog *dialog,
56                                                                                  const gchar            *property1,
57                                                                                  const gchar            *property2,
58                                                                                  GBindingFlags           flags);
59 static void                     panel_preferences_dialog_bindings_update        (PanelPreferencesDialog *dialog);
60 static void                     panel_preferences_dialog_output_changed         (GtkComboBox            *combobox,
61                                                                                  PanelPreferencesDialog *dialog);
62 static void                     panel_preferences_dialog_autohide_changed       (GtkComboBox            *combobox,
63                                                                                  PanelPreferencesDialog *dialog);
64 static void                     panel_preferences_dialog_bg_style_changed       (PanelPreferencesDialog *dialog);
65 static void                     panel_preferences_dialog_bg_image_file_set      (GtkFileChooserButton   *button,
66                                                                                  PanelPreferencesDialog *dialog);
67 static void                     panel_preferences_dialog_bg_image_notified      (PanelPreferencesDialog *dialog);
68 static void                     panel_preferences_dialog_panel_combobox_changed (GtkComboBox            *combobox,
69                                                                                  PanelPreferencesDialog *dialog);
70 static gboolean                 panel_preferences_dialog_panel_combobox_rebuild (PanelPreferencesDialog *dialog,
71                                                                                  gint                    panel_id);
72 static void                     panel_preferences_dialog_panel_add              (GtkWidget              *widget,
73                                                                                  PanelPreferencesDialog *dialog);
74 static void                     panel_preferences_dialog_panel_remove           (GtkWidget              *widget,
75                                                                                  PanelPreferencesDialog *dialog);
76 static gboolean                 panel_preferences_dialog_icon_size_state_set    (GtkSwitch              *widget,
77                                                                                  gboolean                state,
78                                                                                  PanelPreferencesDialog *dialog);
79 static void                     panel_preferences_dialog_icon_size_changed      (GtkSpinButton          *button,
80                                                                                  PanelPreferencesDialog *dialog);
81 static void                     panel_preferences_dialog_compositing_clicked    (GtkButton              *button,
82                                                                                  gpointer                user_data);
83 static void                     panel_preferences_dialog_panel_switch           (GtkWidget              *widget,
84                                                                                  PanelPreferencesDialog *dialog);
85 static XfcePanelPluginProvider *panel_preferences_dialog_item_get_selected      (PanelPreferencesDialog *dialog,
86                                                                                  GtkTreeIter            *return_iter);
87 static void                     panel_preferences_dialog_item_store_rebuild     (GtkWidget              *itembar,
88                                                                                  PanelPreferencesDialog *dialog);
89 static void                     panel_preferences_dialog_item_move              (GtkWidget              *button,
90                                                                                  PanelPreferencesDialog *dialog);
91 static void                     panel_preferences_dialog_item_remove            (GtkWidget              *button,
92                                                                                  PanelPreferencesDialog *dialog);
93 static void                     panel_preferences_dialog_item_add               (GtkWidget              *button,
94                                                                                  PanelPreferencesDialog *dialog);
95 static void                     panel_preferences_dialog_item_properties        (GtkWidget              *button,
96                                                                                  PanelPreferencesDialog *dialog);
97 static void                     panel_preferences_dialog_item_about             (GtkWidget              *button,
98                                                                                  PanelPreferencesDialog *dialog);
99 static gboolean                 panel_preferences_dialog_treeview_clicked       (GtkTreeView            *treeview,
100                                                                                  GdkEventButton         *event,
101                                                                                  PanelPreferencesDialog *dialog);
102 static void                     panel_preferences_dialog_item_row_changed       (GtkTreeModel           *model,
103                                                                                  GtkTreePath            *path,
104                                                                                  GtkTreeIter            *iter,
105                                                                                  PanelPreferencesDialog *dialog);
106 static void                     panel_preferences_dialog_item_selection_changed (GtkTreeSelection       *selection,
107                                                                                  PanelPreferencesDialog *dialog);
108 
109 
110 
111 enum
112 {
113   ITEM_COLUMN_ICON_NAME,
114   ITEM_COLUMN_DISPLAY_NAME,
115   ITEM_COLUMN_TOOLTIP,
116   ITEM_COLUMN_PROVIDER,
117   N_ITEM_COLUMNS
118 };
119 
120 enum
121 {
122   OUTPUT_NAME,
123   OUTPUT_TITLE
124 };
125 
126 struct _PanelPreferencesDialogClass
127 {
128   GtkBuilderClass __parent__;
129 };
130 
131 struct _PanelPreferencesDialog
132 {
133   GtkBuilder  __parent__;
134 
135   PanelApplication *application;
136 
137   /* currently selected window in the selector */
138   PanelWindow      *active;
139 
140   /* GBinding's between dialog <-> window */
141   GSList           *bindings;
142 
143   /* store for the items list */
144   GtkListStore     *store;
145 
146   /* changed signal for the active panel's itembar */
147   gulong            items_changed_handler_id;
148 
149   /* background image watch */
150   gulong            bg_image_notify_handler_id;
151 
152   /* changed signal for the output selector */
153   gulong            output_changed_handler_id;
154 
155   /* plug in which the dialog is embedded */
156   GtkWidget        *socket_plug;
157 };
158 
159 
160 
161 G_DEFINE_TYPE (PanelPreferencesDialog, panel_preferences_dialog, GTK_TYPE_BUILDER)
162 
163 
164 
165 static PanelPreferencesDialog *dialog_singleton = NULL;
166 
167 
168 
169 static void
panel_preferences_dialog_class_init(PanelPreferencesDialogClass * klass)170 panel_preferences_dialog_class_init (PanelPreferencesDialogClass *klass)
171 {
172   GObjectClass *gobject_class;
173 
174   gobject_class = G_OBJECT_CLASS (klass);
175   gobject_class->finalize = panel_preferences_dialog_finalize;
176 }
177 
178 
179 
180 static void
panel_preferences_dialog_init(PanelPreferencesDialog * dialog)181 panel_preferences_dialog_init (PanelPreferencesDialog *dialog)
182 {
183   GObject           *window;
184   GObject           *object;
185   GObject           *info;
186   GObject           *treeview;
187   GtkTreeViewColumn *column;
188   GtkCellRenderer   *renderer;
189   GtkTreeSelection  *selection;
190   gchar             *path_old;
191   gchar             *path_new;
192   gchar             *xfwm4_tweaks;
193 
194   dialog->bindings = NULL;
195   dialog->application = panel_application_get ();
196 
197   /* block autohide */
198   panel_application_windows_blocked (dialog->application, TRUE);
199 
200   /* load the builder data into the object */
201   gtk_builder_add_from_string (GTK_BUILDER (dialog), panel_preferences_dialog_ui,
202                                panel_preferences_dialog_ui_length, NULL);
203 
204   /* get the dialog */
205   window = gtk_builder_get_object (GTK_BUILDER (dialog), "dialog");
206   panel_return_if_fail (GTK_IS_WIDGET (window));
207   g_signal_connect (G_OBJECT (window), "response",
208       G_CALLBACK (panel_preferences_dialog_response), dialog);
209 
210 #define connect_signal(name,detail_signal,c_handler) \
211   object = gtk_builder_get_object (GTK_BUILDER (dialog), name); \
212   panel_return_if_fail (G_IS_OBJECT (object)); \
213   g_signal_connect (G_OBJECT (object), detail_signal, G_CALLBACK (c_handler), dialog);
214 
215   /* panel selector buttons and combobox */
216   connect_signal ("panel-add", "clicked", panel_preferences_dialog_panel_add);
217   connect_signal ("panel-remove", "clicked", panel_preferences_dialog_panel_remove);
218   connect_signal ("panel-combobox", "changed", panel_preferences_dialog_panel_combobox_changed);
219 
220   /* check if xfce4-panel-profiles or panel-switch are installed and if either is show the button */
221   object = gtk_builder_get_object (GTK_BUILDER (dialog), "panel-profiles");
222   path_old = g_find_program_in_path ("xfpanel-switch");
223   path_new = g_find_program_in_path ("xfce4-panel-profiles");
224   if (path_new == NULL && path_old == NULL)
225     gtk_widget_hide (GTK_WIDGET (object));
226   g_free (path_old);
227   g_free (path_new);
228   connect_signal ("panel-switch", "clicked", panel_preferences_dialog_panel_switch);
229 
230   /* appearance tab */
231   object = gtk_builder_get_object (GTK_BUILDER (dialog), "background-style");
232   panel_return_if_fail (G_IS_OBJECT (object));
233   g_signal_connect_swapped (G_OBJECT (object), "changed",
234       G_CALLBACK (panel_preferences_dialog_bg_style_changed), dialog);
235 
236   /* icon size switch, handling enabling/disabling of custom icon sizes */
237   object = gtk_builder_get_object (GTK_BUILDER (dialog), "icon-size-spinbutton");
238   panel_return_if_fail (G_IS_OBJECT (object));
239   g_signal_connect (G_OBJECT (object), "value-changed",
240                     G_CALLBACK (panel_preferences_dialog_icon_size_changed), dialog);
241   object = gtk_builder_get_object (GTK_BUILDER (dialog), "icon-size-switch");
242   panel_return_if_fail (G_IS_OBJECT (object));
243   g_signal_connect (G_OBJECT (object), "state-set",
244                     G_CALLBACK (panel_preferences_dialog_icon_size_state_set), dialog);
245 
246   object = gtk_builder_get_object (GTK_BUILDER (dialog), "composited");
247   panel_return_if_fail (G_IS_OBJECT (object));
248   g_signal_connect_swapped (G_OBJECT (object), "notify::visible",
249       G_CALLBACK (panel_preferences_dialog_bg_style_changed), dialog);
250 
251   info = gtk_builder_get_object (GTK_BUILDER (dialog), "composited-info");
252   panel_return_if_fail (G_IS_OBJECT (info));
253   g_object_bind_property (G_OBJECT (object), "sensitive",
254                           G_OBJECT (info), "visible",
255                           G_BINDING_SYNC_CREATE | G_BINDING_INVERT_BOOLEAN);
256 
257   object = gtk_builder_get_object (GTK_BUILDER (dialog), "xfwm4-settings");
258   panel_return_if_fail (G_IS_OBJECT (object));
259   xfwm4_tweaks = g_find_program_in_path ("xfwm4-tweaks-settings");
260   gtk_widget_set_visible (GTK_WIDGET (object), xfwm4_tweaks != NULL);
261   g_free (xfwm4_tweaks);
262   g_signal_connect (G_OBJECT (object), "clicked",
263                     G_CALLBACK (panel_preferences_dialog_compositing_clicked), NULL);
264 
265   object = gtk_builder_get_object (GTK_BUILDER (dialog), "background-image");
266   panel_return_if_fail (GTK_IS_FILE_CHOOSER_BUTTON (object));
267   g_signal_connect (G_OBJECT (object), "file-set",
268     G_CALLBACK (panel_preferences_dialog_bg_image_file_set), dialog);
269 
270   /* items treeview and buttons */
271   connect_signal ("item-up", "clicked", panel_preferences_dialog_item_move);
272   connect_signal ("item-down", "clicked", panel_preferences_dialog_item_move);
273   connect_signal ("item-remove", "clicked", panel_preferences_dialog_item_remove);
274   connect_signal ("item-add", "clicked", panel_preferences_dialog_item_add);
275   connect_signal ("item-properties", "clicked", panel_preferences_dialog_item_properties);
276   connect_signal ("item-about", "clicked", panel_preferences_dialog_item_about);
277 
278   /* create store for panel items */
279   dialog->store = gtk_list_store_new (N_ITEM_COLUMNS,
280                                       G_TYPE_STRING, /* ITEM_COLUMN_ICON_NAME */
281                                       G_TYPE_STRING, /* ITEM_COLUMN_DISPLAY_NAME */
282                                       G_TYPE_STRING, /* ITEM_COLUMN_TOOLTIP */
283                                       G_TYPE_OBJECT); /* ITEM_COLUMN_PROVIDER */
284 
285   /* build tree for panel items */
286   treeview = gtk_builder_get_object (GTK_BUILDER (dialog), "item-treeview");
287   panel_return_if_fail (GTK_IS_WIDGET (treeview));
288   gtk_tree_view_set_model (GTK_TREE_VIEW (treeview), GTK_TREE_MODEL (dialog->store));
289   gtk_tree_view_set_tooltip_column (GTK_TREE_VIEW (treeview), ITEM_COLUMN_TOOLTIP);
290   g_signal_connect (G_OBJECT (treeview), "button-press-event",
291       G_CALLBACK (panel_preferences_dialog_treeview_clicked), dialog);
292 
293   gtk_tree_view_set_reorderable (GTK_TREE_VIEW (treeview), TRUE);
294   g_signal_connect (G_OBJECT (dialog->store), "row-changed",
295       G_CALLBACK (panel_preferences_dialog_item_row_changed), dialog);
296 
297   /* setup tree selection */
298   selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (treeview));
299   gtk_tree_selection_set_mode (selection, GTK_SELECTION_BROWSE);
300   g_signal_connect (G_OBJECT (selection), "changed",
301       G_CALLBACK (panel_preferences_dialog_item_selection_changed), dialog);
302 
303   /* icon renderer */
304   renderer = gtk_cell_renderer_pixbuf_new ();
305   column = gtk_tree_view_column_new_with_attributes ("", renderer, "icon-name",
306                                                      ITEM_COLUMN_ICON_NAME, NULL);
307   g_object_set (G_OBJECT (renderer), "stock-size", GTK_ICON_SIZE_LARGE_TOOLBAR, NULL);
308   gtk_tree_view_append_column (GTK_TREE_VIEW (treeview), column);
309 
310   /* text renderer */
311   renderer = gtk_cell_renderer_text_new ();
312   column = gtk_tree_view_column_new ();
313   gtk_tree_view_column_pack_start (column, renderer, TRUE);
314   gtk_tree_view_column_set_attributes (column, renderer, "markup",
315                                        ITEM_COLUMN_DISPLAY_NAME, NULL);
316   gtk_tree_view_append_column (GTK_TREE_VIEW (treeview), column);
317 
318   /* connect the output changed signal */
319   object = gtk_builder_get_object (GTK_BUILDER (dialog), "output-name");
320   panel_return_if_fail (GTK_IS_COMBO_BOX (object));
321   dialog->output_changed_handler_id =
322       g_signal_connect (G_OBJECT (object), "changed",
323                         G_CALLBACK (panel_preferences_dialog_output_changed),
324                         dialog);
325 
326   /* connect the autohide behavior changed signal */
327   object = gtk_builder_get_object (GTK_BUILDER (dialog), "autohide-behavior");
328   panel_return_if_fail (GTK_IS_COMBO_BOX (object));
329   g_signal_connect (G_OBJECT (object), "changed",
330       G_CALLBACK (panel_preferences_dialog_autohide_changed), dialog);
331 }
332 
333 
334 
335 static void
panel_preferences_dialog_finalize(GObject * object)336 panel_preferences_dialog_finalize (GObject *object)
337 {
338   PanelPreferencesDialog *dialog = PANEL_PREFERENCES_DIALOG (object);
339   GtkWidget              *itembar;
340 
341   /* unblock autohide */
342   panel_application_windows_blocked (dialog->application, FALSE);
343 
344   /* free bindings list */
345   g_slist_free (dialog->bindings);
346 
347   /* destroy possible pluggable dialog */
348   if (dialog->socket_plug != NULL)
349     gtk_widget_destroy (dialog->socket_plug);
350 
351   if (dialog->active != NULL)
352     {
353       if (dialog->items_changed_handler_id != 0)
354         {
355           /* disconnect changed signal */
356           itembar = gtk_bin_get_child (GTK_BIN (dialog->active));
357           g_signal_handler_disconnect (G_OBJECT (itembar),
358               dialog->items_changed_handler_id);
359         }
360 
361       if (dialog->bg_image_notify_handler_id != 0)
362         {
363           g_signal_handler_disconnect (G_OBJECT (dialog->active),
364               dialog->bg_image_notify_handler_id);
365         }
366     }
367 
368   /* deselect all windows */
369   if (!panel_item_dialog_visible ())
370     panel_application_window_select (dialog->application, NULL);
371 
372   g_object_unref (G_OBJECT (dialog->application));
373   g_object_unref (G_OBJECT (dialog->store));
374 
375   (*G_OBJECT_CLASS (panel_preferences_dialog_parent_class)->finalize) (object);
376 }
377 
378 
379 
380 static void
panel_preferences_dialog_response(GtkWidget * window,gint response_id,PanelPreferencesDialog * dialog)381 panel_preferences_dialog_response (GtkWidget              *window,
382                                    gint                    response_id,
383                                    PanelPreferencesDialog *dialog)
384 {
385   panel_return_if_fail (GTK_IS_DIALOG (window));
386   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
387 
388   if (G_UNLIKELY (response_id == 1))
389     {
390       panel_utils_show_help (GTK_WINDOW (window), "preferences", NULL);
391     }
392   else
393     {
394       gtk_widget_destroy (window);
395       g_object_unref (G_OBJECT (dialog));
396     }
397 }
398 
399 
400 
401 static void
panel_preferences_dialog_bindings_unbind(PanelPreferencesDialog * dialog)402 panel_preferences_dialog_bindings_unbind (PanelPreferencesDialog *dialog)
403 {
404   GSList *li;
405 
406   if (dialog->bindings != NULL)
407     {
408       /* remove all bindings */
409       for (li = dialog->bindings; li != NULL; li = li->next)
410         g_object_unref (G_OBJECT (li->data));
411 
412       g_slist_free (dialog->bindings);
413       dialog->bindings = NULL;
414     }
415 
416   /* disconnect image watch */
417   if (dialog->bg_image_notify_handler_id != 0)
418     {
419       if (dialog->active != NULL)
420         {
421           g_signal_handler_disconnect (G_OBJECT (dialog->active),
422               dialog->bg_image_notify_handler_id);
423         }
424 
425       dialog->bg_image_notify_handler_id = 0;
426     }
427 }
428 
429 
430 
431 static void
panel_preferences_dialog_bindings_add(PanelPreferencesDialog * dialog,const gchar * property1,const gchar * property2,GBindingFlags flags)432 panel_preferences_dialog_bindings_add (PanelPreferencesDialog *dialog,
433                                        const gchar            *property1,
434                                        const gchar            *property2,
435                                        GBindingFlags           flags)
436 {
437   GBinding *binding;
438   GObject  *object;
439 
440   /* get the object from the builder */
441   object = gtk_builder_get_object (GTK_BUILDER (dialog), property1);
442   panel_return_if_fail (G_IS_OBJECT (object));
443 
444   /* create the binding and prepend to the list */
445   binding = g_object_bind_property (G_OBJECT (dialog->active), property1, object, property2,
446                                     flags ? flags : G_BINDING_SYNC_CREATE | G_BINDING_BIDIRECTIONAL);
447   dialog->bindings = g_slist_prepend (dialog->bindings, binding);
448 }
449 
450 
451 
452 static void
panel_preferences_dialog_bindings_update(PanelPreferencesDialog * dialog)453 panel_preferences_dialog_bindings_update (PanelPreferencesDialog *dialog)
454 {
455   GdkDisplay  *display;
456   GdkMonitor  *monitor;
457   gint         n_monitors = 1;
458   GObject     *object;
459   GObject     *store;
460   gchar       *output_name = NULL;
461   gboolean     selector_visible = TRUE;
462   GtkTreeIter  iter;
463   gboolean     output_selected = FALSE;
464   gint         n = 0, i;
465   gchar       *name, *title;
466   gboolean     span_monitors_sensitive = FALSE;
467   gboolean     icon_size_set;
468 
469   /* leave when there is no active panel */
470   panel_return_if_fail (G_IS_OBJECT (dialog->active));
471   if (dialog->active == NULL)
472     return;
473 
474   /* hook up the bindings */
475   panel_preferences_dialog_bindings_add (dialog, "mode", "active", 0);
476   panel_preferences_dialog_bindings_add (dialog, "span-monitors", "active", 0);
477   panel_preferences_dialog_bindings_add (dialog, "position-locked", "active", 0);
478   panel_preferences_dialog_bindings_add (dialog, "autohide-behavior", "active", 0);
479   panel_preferences_dialog_bindings_add (dialog, "disable-struts", "active", 0);
480   panel_preferences_dialog_bindings_add (dialog, "size", "value", 0);
481   panel_preferences_dialog_bindings_add (dialog, "nrows", "value", 0);
482   panel_preferences_dialog_bindings_add (dialog, "length", "value", 0);
483   panel_preferences_dialog_bindings_add (dialog, "length-adjust", "active", 0);
484   panel_preferences_dialog_bindings_add (dialog, "enter-opacity", "value", 0);
485   panel_preferences_dialog_bindings_add (dialog, "leave-opacity", "value", 0);
486   panel_preferences_dialog_bindings_add (dialog, "composited", "sensitive", G_BINDING_SYNC_CREATE);
487   panel_preferences_dialog_bindings_add (dialog, "background-style", "active", 0);
488   panel_preferences_dialog_bindings_add (dialog, "background-rgba", "rgba", 0);
489   panel_preferences_dialog_bindings_add (dialog, "icon-size", "value", 0);
490   panel_preferences_dialog_bindings_add (dialog, "dark-mode", "active", 0);
491 
492   /* watch image changes from the panel */
493   dialog->bg_image_notify_handler_id = g_signal_connect_swapped (G_OBJECT (dialog->active),
494       "notify::background-image", G_CALLBACK (panel_preferences_dialog_bg_image_notified), dialog);
495   panel_preferences_dialog_bg_image_notified (dialog);
496 
497 
498   /* get run mode of the driver (multiple monitors or randr) */
499   display = gtk_widget_get_display (GTK_WIDGET (dialog->active));
500   n_monitors = gdk_display_get_n_monitors (display);
501 
502   /* update the output selector */
503   object = gtk_builder_get_object (GTK_BUILDER (dialog), "output-name");
504   panel_return_if_fail (GTK_IS_COMBO_BOX (object));
505 
506   g_signal_handler_block (G_OBJECT (object), dialog->output_changed_handler_id);
507 
508   store = gtk_builder_get_object (GTK_BUILDER (dialog), "output-store");
509   panel_return_if_fail (GTK_IS_LIST_STORE (store));
510   gtk_list_store_clear (GTK_LIST_STORE (store));
511 
512   g_object_get (G_OBJECT (dialog->active), "output-name", &output_name, NULL);
513 
514   if (n_monitors > 1 || !panel_str_is_empty (output_name))
515     {
516       gtk_list_store_insert_with_values (GTK_LIST_STORE (store), &iter, n++,
517                                          OUTPUT_NAME, "Automatic",
518                                          OUTPUT_TITLE, _("Automatic"), -1);
519       if (panel_str_is_empty (output_name) ||
520           g_strcmp0 (output_name, "Automatic") == 0)
521         {
522           gtk_combo_box_set_active_iter (GTK_COMBO_BOX (object), &iter);
523           output_selected = TRUE;
524           span_monitors_sensitive = TRUE;
525         }
526       gtk_list_store_insert_with_values (GTK_LIST_STORE (store), &iter, n++,
527                                          OUTPUT_NAME, "Primary",
528                                          OUTPUT_TITLE, _("Primary"), -1);
529       if (g_strcmp0 (output_name, "Primary") == 0)
530         {
531           gtk_combo_box_set_active_iter (GTK_COMBO_BOX (object), &iter);
532           output_selected = TRUE;
533           span_monitors_sensitive = FALSE;
534         }
535 
536       if (n_monitors >= 1)
537         {
538           for (i = 0; i < n_monitors; i++)
539             {
540               monitor = gdk_display_get_monitor(display, i);
541               name = g_strdup(gdk_monitor_get_model (monitor));
542               if (panel_str_is_empty (name))
543                 {
544                   g_free (name);
545 
546                   /* I18N: monitor name in the output selector */
547                   title = g_strdup_printf (_("Monitor %d"), i + 1);
548                   name = g_strdup_printf ("monitor-%d", i);
549                 }
550               else
551                 {
552                   /* use the randr name for the title */
553                   title = g_strdup (name);
554                 }
555 
556               gtk_list_store_insert_with_values (GTK_LIST_STORE (store), &iter, n++,
557                                                  OUTPUT_NAME, name,
558                                                  OUTPUT_TITLE, title, -1);
559               if (!output_selected
560                   && g_strcmp0 (name, output_name) == 0)
561                 {
562                   gtk_combo_box_set_active_iter  (GTK_COMBO_BOX (object), &iter);
563                   output_selected = TRUE;
564                 }
565 
566               g_free (name);
567               g_free (title);
568             }
569         }
570 
571       /* add the output from the config if still nothing has been selected */
572       if (!output_selected && !panel_str_is_empty (output_name))
573         {
574           gtk_list_store_insert_with_values (GTK_LIST_STORE (store), &iter, n++,
575                                              OUTPUT_NAME, output_name,
576                                              OUTPUT_TITLE, output_name, -1);
577           gtk_combo_box_set_active_iter  (GTK_COMBO_BOX (object), &iter);
578         }
579     }
580   else
581     {
582       /* hide the selector */
583       selector_visible = FALSE;
584       span_monitors_sensitive = TRUE;
585     }
586 
587   g_signal_handler_unblock (G_OBJECT (object), dialog->output_changed_handler_id);
588 
589   /* update visibility of the output selector */
590   object = gtk_builder_get_object (GTK_BUILDER (dialog), "output-label");
591   panel_return_if_fail (GTK_IS_WIDGET (object));
592   g_object_set (G_OBJECT (object), "visible", selector_visible, NULL);
593 
594   object = gtk_builder_get_object (GTK_BUILDER (dialog), "output-name");
595   panel_return_if_fail (GTK_IS_WIDGET (object));
596   g_object_set (G_OBJECT (object), "visible", selector_visible, NULL);
597 
598   /* monitor spanning is only active when no output is selected */
599   object = gtk_builder_get_object (GTK_BUILDER (dialog), "span-monitors");
600   panel_return_if_fail (GTK_IS_WIDGET (object));
601   gtk_widget_set_sensitive (GTK_WIDGET (object), span_monitors_sensitive);
602   g_object_set (G_OBJECT (object), "visible", n_monitors > 1, NULL);
603 
604   g_free (output_name);
605 
606   /* update sensitivity of "don't reserve space on borders" option */
607   object = gtk_builder_get_object (GTK_BUILDER (dialog), "autohide-behavior");
608   panel_return_if_fail (GTK_IS_COMBO_BOX (object));
609   panel_preferences_dialog_autohide_changed (GTK_COMBO_BOX (object), dialog);
610 
611   /* update visibility of the "icon-size" widgets */
612   object = gtk_builder_get_object (GTK_BUILDER (dialog), "icon-size-spinbutton");
613   panel_return_if_fail (G_IS_OBJECT (object));
614 
615   if (gtk_spin_button_get_value_as_int (GTK_SPIN_BUTTON (object)) == 0)
616     icon_size_set = FALSE;
617   else
618     icon_size_set = TRUE;
619 
620   object = gtk_builder_get_object (GTK_BUILDER (dialog), "icon-size-revealer");
621   panel_return_if_fail (G_IS_OBJECT (object));
622   gtk_revealer_set_reveal_child (GTK_REVEALER (object), icon_size_set);
623 
624   object = gtk_builder_get_object (GTK_BUILDER (dialog), "icon-size-switch");
625   panel_return_if_fail (G_IS_OBJECT (object));
626   gtk_switch_set_state (GTK_SWITCH (object), !icon_size_set);
627 }
628 
629 
630 
631 static void
panel_preferences_dialog_output_changed(GtkComboBox * combobox,PanelPreferencesDialog * dialog)632 panel_preferences_dialog_output_changed (GtkComboBox            *combobox,
633                                          PanelPreferencesDialog *dialog)
634 {
635   GtkTreeIter   iter;
636   GtkTreeModel *model;
637   gchar        *output_name = NULL;
638   GObject      *object;
639 
640   panel_return_if_fail (GTK_IS_COMBO_BOX (combobox));
641   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
642   panel_return_if_fail (PANEL_WINDOW (dialog->active));
643 
644   if (gtk_combo_box_get_active_iter (combobox, &iter))
645     {
646       model = gtk_combo_box_get_model (combobox);
647       gtk_tree_model_get (model, &iter, OUTPUT_NAME, &output_name, -1);
648       g_object_set (G_OBJECT (dialog->active), "output-name", output_name, NULL);
649 
650       /* monitor spanning does not work when an output is selected */
651       object = gtk_builder_get_object (GTK_BUILDER (dialog), "span-monitors");
652       panel_return_if_fail (GTK_IS_WIDGET (object));
653       if (output_name == NULL ||
654           g_strcmp0 ("Automatic", output_name) == 0)
655         gtk_widget_set_sensitive (GTK_WIDGET (object), TRUE);
656       else
657         gtk_widget_set_sensitive (GTK_WIDGET (object), FALSE);
658 
659       g_free (output_name);
660     }
661 }
662 
663 
664 
665 static void
panel_preferences_dialog_autohide_changed(GtkComboBox * combobox,PanelPreferencesDialog * dialog)666 panel_preferences_dialog_autohide_changed (GtkComboBox            *combobox,
667                                            PanelPreferencesDialog *dialog)
668 {
669   GObject *object;
670 
671   panel_return_if_fail (GTK_IS_COMBO_BOX (combobox));
672   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
673   panel_return_if_fail (PANEL_WINDOW (dialog->active));
674 
675   object = gtk_builder_get_object (GTK_BUILDER (dialog), "disable-struts");
676   panel_return_if_fail (GTK_IS_WIDGET (object));
677 
678   /* make "don't reserve space on borders" sensitive only when autohide is disabled */
679   if (gtk_combo_box_get_active (combobox) == 0)
680     gtk_widget_set_sensitive (GTK_WIDGET (object), TRUE);
681   else
682     gtk_widget_set_sensitive (GTK_WIDGET (object), FALSE);
683 }
684 
685 
686 
687 static void
panel_preferences_dialog_bg_style_changed(PanelPreferencesDialog * dialog)688 panel_preferences_dialog_bg_style_changed (PanelPreferencesDialog *dialog)
689 {
690   gint      active;
691   GObject  *object;
692   gboolean  composited;
693 
694   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
695   panel_return_if_fail (PANEL_WINDOW (dialog->active));
696 
697   object = gtk_builder_get_object (GTK_BUILDER (dialog), "background-style");
698   panel_return_if_fail (GTK_IS_COMBO_BOX (object));
699   active = gtk_combo_box_get_active (GTK_COMBO_BOX (object));
700 
701   object = gtk_builder_get_object (GTK_BUILDER (dialog), "background-rgba");
702   panel_return_if_fail (GTK_IS_WIDGET (object));
703   g_object_get (G_OBJECT (dialog->active), "composited", &composited, NULL);
704   gtk_color_chooser_set_use_alpha (GTK_COLOR_CHOOSER (object), composited);
705 
706   object = gtk_builder_get_object (GTK_BUILDER (dialog), "background-rgba-label");
707   panel_return_if_fail (GTK_IS_WIDGET (object));
708   g_object_set (G_OBJECT (object), "visible", active == 1, NULL);
709 
710   object = gtk_builder_get_object (GTK_BUILDER (dialog), "background-rgba");
711   panel_return_if_fail (GTK_IS_WIDGET (object));
712   g_object_set (G_OBJECT (object), "visible", active == 1, NULL);
713 
714   object = gtk_builder_get_object (GTK_BUILDER (dialog), "background-image-label");
715   panel_return_if_fail (GTK_IS_WIDGET (object));
716   g_object_set (G_OBJECT (object), "visible", active == 2, NULL);
717 
718   object = gtk_builder_get_object (GTK_BUILDER (dialog), "background-image");
719   panel_return_if_fail (GTK_IS_WIDGET (object));
720   g_object_set (G_OBJECT (object), "visible", active == 2, NULL);
721 }
722 
723 
724 
725 static void
panel_preferences_dialog_bg_image_file_set(GtkFileChooserButton * button,PanelPreferencesDialog * dialog)726 panel_preferences_dialog_bg_image_file_set (GtkFileChooserButton   *button,
727                                             PanelPreferencesDialog *dialog)
728 {
729   gchar *filename;
730 
731   panel_return_if_fail (GTK_IS_FILE_CHOOSER_BUTTON (button));
732   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
733   panel_return_if_fail (PANEL_IS_WINDOW (dialog->active));
734 
735   g_signal_handler_block (G_OBJECT (dialog->active),
736       dialog->bg_image_notify_handler_id);
737 
738   filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (button));
739   g_object_set (G_OBJECT (dialog->active), "background-image", filename, NULL);
740   g_free (filename);
741 
742   g_signal_handler_unblock (G_OBJECT (dialog->active),
743       dialog->bg_image_notify_handler_id);
744 }
745 
746 
747 
748 static void
panel_preferences_dialog_bg_image_notified(PanelPreferencesDialog * dialog)749 panel_preferences_dialog_bg_image_notified (PanelPreferencesDialog *dialog)
750 {
751   gchar   *filename;
752   GObject *button;
753 
754   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
755   panel_return_if_fail (PANEL_IS_WINDOW (dialog->active));
756 
757   button = gtk_builder_get_object (GTK_BUILDER (dialog), "background-image");
758   panel_return_if_fail (GTK_IS_FILE_CHOOSER_BUTTON (button));
759 
760   g_signal_handlers_block_by_func (G_OBJECT (button),
761       G_CALLBACK (panel_preferences_dialog_bg_image_file_set), dialog);
762 
763   g_object_get (G_OBJECT (dialog->active), "background-image", &filename, NULL);
764   gtk_file_chooser_set_filename (GTK_FILE_CHOOSER (button), filename != NULL ? filename : "");
765   g_free (filename);
766 
767   g_signal_handlers_unblock_by_func (G_OBJECT (button),
768       G_CALLBACK (panel_preferences_dialog_bg_image_file_set), dialog);
769 }
770 
771 
772 
773 static void
panel_preferences_dialog_panel_sensitive(PanelPreferencesDialog * dialog)774 panel_preferences_dialog_panel_sensitive (PanelPreferencesDialog *dialog)
775 {
776 
777   GObject  *object;
778   gboolean  locked = TRUE;
779   GSList   *windows;
780 
781   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
782 
783   if (G_LIKELY (dialog->active != NULL))
784     locked = panel_window_get_locked (dialog->active);
785 
786   object = gtk_builder_get_object (GTK_BUILDER (dialog), "panel-remove");
787   panel_return_if_fail (GTK_IS_WIDGET (object));
788   windows = panel_application_get_windows (dialog->application);
789   gtk_widget_set_sensitive (GTK_WIDGET (object),
790       !locked && g_slist_length (windows) > 1);
791 
792   object = gtk_builder_get_object (GTK_BUILDER (dialog), "panel-add");
793   panel_return_if_fail (GTK_IS_WIDGET (object));
794   gtk_widget_set_sensitive (GTK_WIDGET (object),
795       !panel_application_get_locked (dialog->application));
796 
797   object = gtk_builder_get_object (GTK_BUILDER (dialog), "notebook");
798   panel_return_if_fail (GTK_IS_WIDGET (object));
799   gtk_widget_set_sensitive (GTK_WIDGET (object), !locked);
800 
801   object = gtk_builder_get_object (GTK_BUILDER (dialog), "item-add");
802   panel_return_if_fail (GTK_IS_WIDGET (object));
803   gtk_widget_set_sensitive (GTK_WIDGET (object), !locked);
804 }
805 
806 
807 
808 static void
panel_preferences_dialog_panel_combobox_changed(GtkComboBox * combobox,PanelPreferencesDialog * dialog)809 panel_preferences_dialog_panel_combobox_changed (GtkComboBox            *combobox,
810                                                  PanelPreferencesDialog *dialog)
811 {
812   gint          panel_id;
813   GtkWidget    *itembar;
814   GtkTreeModel *model;
815   GtkTreeIter   iter;
816 
817   panel_return_if_fail (GTK_IS_COMBO_BOX (combobox));
818   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
819 
820   /* disconnect signal we used to monitor changes in the itembar */
821   if (dialog->active != NULL && dialog->items_changed_handler_id != 0)
822     {
823       itembar = gtk_bin_get_child (GTK_BIN (dialog->active));
824       g_signal_handler_disconnect (G_OBJECT (itembar), dialog->items_changed_handler_id);
825     }
826 
827   /* remove all the active bindings */
828   panel_preferences_dialog_bindings_unbind (dialog);
829 
830   /* set the selected window */
831   if (gtk_combo_box_get_active_iter (combobox, &iter))
832     {
833       model = gtk_combo_box_get_model (combobox);
834       gtk_tree_model_get (model, &iter, 0, &panel_id, -1);
835 
836       dialog->active = panel_application_get_window (dialog->application, panel_id);
837     }
838   else
839     {
840       dialog->active = NULL;
841     }
842 
843   panel_application_window_select (dialog->application, dialog->active);
844 
845   if (G_LIKELY (dialog->active != NULL))
846     {
847       itembar = gtk_bin_get_child (GTK_BIN (dialog->active));
848       dialog->items_changed_handler_id =
849           g_signal_connect (G_OBJECT (itembar), "changed",
850                             G_CALLBACK (panel_preferences_dialog_item_store_rebuild),
851                             dialog);
852 
853       /* rebind the dialog bindings */
854       panel_preferences_dialog_bindings_update (dialog);
855 
856       /* update the items treeview */
857       panel_preferences_dialog_item_store_rebuild (itembar, dialog);
858     }
859 
860   panel_preferences_dialog_panel_sensitive (dialog);
861 }
862 
863 
864 
865 static gboolean
panel_preferences_dialog_panel_combobox_rebuild(PanelPreferencesDialog * dialog,gint panel_id)866 panel_preferences_dialog_panel_combobox_rebuild (PanelPreferencesDialog *dialog,
867                                                  gint                    panel_id)
868 {
869   GObject     *store, *combo;
870   gint         i;
871   GSList      *windows, *li;
872   gchar       *name;
873   gint         id;
874   GtkTreeIter  iter;
875   gboolean     selected = FALSE;
876 
877   /* get the combo box and model */
878   store = gtk_builder_get_object (GTK_BUILDER (dialog), "panel-store");
879   panel_return_val_if_fail (GTK_IS_LIST_STORE (store), FALSE);
880   combo = gtk_builder_get_object (GTK_BUILDER (dialog), "panel-combobox");
881   panel_return_val_if_fail (GTK_IS_COMBO_BOX (combo), FALSE);
882 
883   /* block signal */
884   g_signal_handlers_block_by_func (combo,
885       panel_preferences_dialog_panel_combobox_changed, dialog);
886 
887   /* empty the combo box */
888   gtk_list_store_clear (GTK_LIST_STORE (store));
889 
890   /* add new names */
891   windows = panel_application_get_windows (dialog->application);
892   for (li = windows, i = 0; li != NULL; li = li->next, i++)
893     {
894       /* I18N: panel combo box in the preferences dialog */
895       id = panel_window_get_id (li->data);
896       name = g_strdup_printf (_("Panel %d"), id);
897       gtk_list_store_insert_with_values (GTK_LIST_STORE (store), &iter, i,
898                                          0, id, 1, name, -1);
899       g_free (name);
900 
901       if (id == panel_id)
902         {
903           /* select panel id */
904           gtk_combo_box_set_active_iter (GTK_COMBO_BOX (combo), &iter);
905           selected = TRUE;
906         }
907     }
908 
909   /* unblock signal */
910   g_signal_handlers_unblock_by_func (combo,
911       panel_preferences_dialog_panel_combobox_changed, dialog);
912 
913   if (selected)
914     panel_preferences_dialog_panel_combobox_changed (GTK_COMBO_BOX (combo), dialog);
915 
916   panel_preferences_dialog_panel_sensitive (dialog);
917 
918   return selected;
919 }
920 
921 
922 
923 static void
panel_preferences_dialog_panel_add(GtkWidget * widget,PanelPreferencesDialog * dialog)924 panel_preferences_dialog_panel_add (GtkWidget              *widget,
925                                     PanelPreferencesDialog *dialog)
926 {
927   PanelWindow *window;
928   gint         panel_id;
929 
930   /* create new window */
931   window = panel_application_new_window (dialog->application,
932       gtk_widget_get_screen (widget), -1, TRUE);
933 
934   /* block autohide */
935   panel_window_freeze_autohide (window);
936 
937   /* show window */
938   gtk_widget_show (GTK_WIDGET (window));
939 
940   /* rebuild the selector */
941   panel_id = panel_window_get_id (window);
942   panel_preferences_dialog_panel_combobox_rebuild (dialog, panel_id);
943 }
944 
945 
946 
947 static void
panel_preferences_dialog_panel_remove(GtkWidget * widget,PanelPreferencesDialog * dialog)948 panel_preferences_dialog_panel_remove (GtkWidget              *widget,
949                                        PanelPreferencesDialog *dialog)
950 {
951   gint       idx;
952   GtkWidget *toplevel;
953   GSList    *windows;
954   gint       n_windows;
955 
956   /* leave if the window is locked */
957   if (panel_window_get_locked (dialog->active))
958     return;
959 
960   toplevel = gtk_widget_get_toplevel (widget);
961   if (xfce_dialog_confirm (GTK_WINDOW (toplevel), "list-remove", _("_Remove"),
962           _("The panel and plugin configurations will be permanently removed"),
963           _("Are you sure you want to remove panel %d?"),
964           panel_window_get_id (dialog->active)))
965     {
966       /* release the bindings */
967       panel_preferences_dialog_bindings_unbind (dialog);
968 
969       /* get position of the panel */
970       windows = panel_application_get_windows (dialog->application);
971       idx = g_slist_index (windows, dialog->active);
972       n_windows = g_slist_length (windows) - 2;
973 
974       /* remove the panel, plugins and configuration */
975       panel_application_remove_window (dialog->application,
976                                        dialog->active);
977       dialog->active = NULL;
978 
979       /* rebuild the selector */
980       panel_preferences_dialog_panel_combobox_rebuild (dialog, CLAMP (idx, 0, n_windows));
981     }
982 }
983 
984 
985 
986 static gboolean
panel_preferences_dialog_icon_size_state_set(GtkSwitch * widget,gboolean state,PanelPreferencesDialog * dialog)987 panel_preferences_dialog_icon_size_state_set (GtkSwitch              *widget,
988                                               gboolean                state,
989                                               PanelPreferencesDialog *dialog)
990 {
991   GObject   *spinbutton, *revealer;
992 
993   panel_return_val_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog), FALSE);
994   spinbutton = gtk_builder_get_object (GTK_BUILDER (dialog), "icon-size-spinbutton");
995   panel_return_val_if_fail (G_IS_OBJECT (spinbutton), FALSE);
996   revealer = gtk_builder_get_object (GTK_BUILDER (dialog), "icon-size-revealer");
997   panel_return_val_if_fail (G_IS_OBJECT (revealer), FALSE);
998 
999   /* we set the icon-size to 0 for auto-handling */
1000   if (state)
1001     {
1002       gtk_spin_button_set_value (GTK_SPIN_BUTTON (spinbutton), 0.0);
1003     }
1004   else
1005     {
1006       /* if the setting is initially enabled we start at the low default of 16px */
1007       if (gtk_spin_button_get_value (GTK_SPIN_BUTTON (spinbutton)) == 0)
1008         gtk_spin_button_set_value (GTK_SPIN_BUTTON (spinbutton), 16.0);
1009     }
1010 
1011   gtk_revealer_set_reveal_child (GTK_REVEALER (revealer), !state);
1012   gtk_switch_set_state (GTK_SWITCH (widget), state);
1013 
1014   return TRUE;
1015 }
1016 
1017 
1018 
1019 static void
panel_preferences_dialog_icon_size_changed(GtkSpinButton * button,PanelPreferencesDialog * dialog)1020 panel_preferences_dialog_icon_size_changed (GtkSpinButton          *button,
1021                                             PanelPreferencesDialog *dialog)
1022 {
1023   GObject   *object;
1024 
1025   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
1026   object = gtk_builder_get_object (GTK_BUILDER (dialog), "icon-size-switch");
1027   panel_return_if_fail (G_IS_OBJECT (object));
1028 
1029   /* 0 means the setting is disabled (icon-size-switch's state == true) so the lower value
1030      of the spinbutton has to be 0. however, we want to set 16px as the reasonable lower limit for icons. */
1031   if (gtk_spin_button_get_value_as_int (button) < 16
1032       && gtk_switch_get_state (GTK_SWITCH (object)))
1033       gtk_spin_button_set_value (button, 16.0);
1034 }
1035 
1036 
1037 
1038 static void
panel_preferences_dialog_compositing_clicked(GtkButton * button,gpointer user_data)1039 panel_preferences_dialog_compositing_clicked (GtkButton *button, gpointer user_data)
1040 {
1041   gchar    *command;
1042   GAppInfo *app_info = NULL;
1043   GError   *error = NULL;
1044 
1045   command = g_find_program_in_path ("xfwm4-tweaks-settings");
1046   if (command != NULL)
1047     app_info = g_app_info_create_from_commandline (command, "Window Manager Tweaks", G_APP_INFO_CREATE_NONE, &error);
1048   g_free (command);
1049 
1050   if (error != NULL)
1051     {
1052       g_warning ("Could not find application %s", error->message);
1053       g_error_free (error);
1054       return;
1055     }
1056 
1057   if (app_info != NULL && !g_app_info_launch (app_info, NULL, NULL, &error))
1058     {
1059       g_warning ("Could not launch the application %s", error->message);
1060       g_error_free (error);
1061     }
1062 }
1063 
1064 
1065 
1066 static void
panel_preferences_dialog_panel_switch(GtkWidget * widget,PanelPreferencesDialog * dialog)1067 panel_preferences_dialog_panel_switch (GtkWidget *widget, PanelPreferencesDialog *dialog)
1068 {
1069   GtkWidget *toplevel;
1070   gchar     *path_old;
1071   gchar     *path_new;
1072 
1073   path_old = g_find_program_in_path ("xfpanel-switch");
1074   path_new = g_find_program_in_path ("xfce4-panel-profiles");
1075   if (path_old == NULL && path_new == NULL)
1076     return;
1077 
1078   /* close the preferences dialog */
1079   toplevel = gtk_widget_get_toplevel (widget);
1080   panel_preferences_dialog_response (toplevel, 0, dialog);
1081 
1082   /* first try the new name of the executable, then the old */
1083   if (path_new)
1084     g_spawn_command_line_async (path_new, NULL);
1085   else if (path_old)
1086     g_spawn_command_line_async (path_old, NULL);
1087 
1088   g_free (path_old);
1089   g_free (path_new);
1090 }
1091 
1092 
1093 
1094 static XfcePanelPluginProvider *
panel_preferences_dialog_item_get_selected(PanelPreferencesDialog * dialog,GtkTreeIter * return_iter)1095 panel_preferences_dialog_item_get_selected (PanelPreferencesDialog *dialog,
1096                                             GtkTreeIter            *return_iter)
1097 {
1098   GObject                 *treeview;
1099   XfcePanelPluginProvider *provider = NULL;
1100   GtkTreeModel            *model;
1101   GtkTreeIter              iter;
1102   GtkTreeSelection        *selection;
1103 
1104   panel_return_val_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog), NULL);
1105 
1106   /* get the treeview selection */
1107   treeview = gtk_builder_get_object (GTK_BUILDER (dialog), "item-treeview");
1108   panel_return_val_if_fail (GTK_IS_WIDGET (treeview), NULL);
1109   selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (treeview));
1110 
1111   /* get the selection item */
1112   if (gtk_tree_selection_get_selected (selection, &model, &iter))
1113     {
1114       /* get the selected provider */
1115       gtk_tree_model_get (model, &iter, ITEM_COLUMN_PROVIDER, &provider, -1);
1116       panel_return_val_if_fail (XFCE_IS_PANEL_PLUGIN_PROVIDER (provider), NULL);
1117 
1118       if (return_iter)
1119         *return_iter = iter;
1120     }
1121 
1122   return provider;
1123 }
1124 
1125 
1126 
1127 static void
panel_preferences_dialog_item_store_rebuild(GtkWidget * itembar,PanelPreferencesDialog * dialog)1128 panel_preferences_dialog_item_store_rebuild (GtkWidget              *itembar,
1129                                              PanelPreferencesDialog *dialog)
1130 {
1131   GList                   *items, *li;
1132   guint                    i;
1133   PanelModule             *module;
1134   gchar                   *tooltip, *display_name;
1135   XfcePanelPluginProvider *selected_provider;
1136   GtkTreeIter              iter;
1137   GtkTreePath             *path;
1138   GObject                 *treeview;
1139 
1140   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
1141   panel_return_if_fail (GTK_IS_LIST_STORE (dialog->store));
1142   panel_return_if_fail (PANEL_IS_ITEMBAR (itembar));
1143 
1144   /* memorize selected item */
1145   selected_provider = panel_preferences_dialog_item_get_selected (dialog, NULL);
1146 
1147   gtk_list_store_clear (dialog->store);
1148 
1149   g_signal_handlers_block_by_func (G_OBJECT (dialog->store),
1150       G_CALLBACK (panel_preferences_dialog_item_row_changed), dialog);
1151 
1152   /* add items to the store */
1153   items = gtk_container_get_children (GTK_CONTAINER (itembar));
1154   for (li = items, i = 0; li != NULL; li = li->next, i++)
1155     {
1156       /* get the panel module from the plugin */
1157       module = panel_module_get_from_plugin_provider (li->data);
1158 
1159       if (PANEL_IS_PLUGIN_EXTERNAL (li->data))
1160         {
1161           /* I18N: append (external) in the preferences dialog if the plugin
1162            * runs external */
1163           display_name = g_strdup_printf (_("%s <span color=\"grey\" size=\"small\">(external)</span>"),
1164                                           panel_module_get_display_name (module));
1165 
1166           /* I18N: tooltip in preferences dialog when hovering an item in the list
1167            * for external plugins */
1168           tooltip = g_strdup_printf (_("Internal name: %s-%d\n"
1169                                        "PID: %d"),
1170                                      xfce_panel_plugin_provider_get_name (li->data),
1171                                      xfce_panel_plugin_provider_get_unique_id (li->data),
1172                                      panel_plugin_external_get_pid (PANEL_PLUGIN_EXTERNAL (li->data)));
1173         }
1174       else
1175         {
1176           display_name = g_strdup (panel_module_get_display_name (module));
1177 
1178           /* I18N: tooltip in preferences dialog when hovering an item in the list
1179            * for internal plugins */
1180           tooltip = g_strdup_printf (_("Internal name: %s-%d"),
1181                                      xfce_panel_plugin_provider_get_name (li->data),
1182                                      xfce_panel_plugin_provider_get_unique_id (li->data));
1183         }
1184 
1185       gtk_list_store_insert_with_values (dialog->store, &iter, i,
1186                                          ITEM_COLUMN_ICON_NAME,
1187                                          panel_module_get_icon_name (module),
1188                                          ITEM_COLUMN_DISPLAY_NAME,
1189                                          display_name,
1190                                          ITEM_COLUMN_TOOLTIP,
1191                                          tooltip,
1192                                          ITEM_COLUMN_PROVIDER, li->data, -1);
1193 
1194       /* reconstruct selection */
1195       if (selected_provider == li->data)
1196         {
1197           path = gtk_tree_model_get_path (GTK_TREE_MODEL (dialog->store), &iter);
1198           treeview = gtk_builder_get_object (GTK_BUILDER (dialog), "item-treeview");
1199           if (GTK_IS_WIDGET (treeview))
1200             gtk_tree_view_set_cursor (GTK_TREE_VIEW (treeview), path, NULL, FALSE);
1201           gtk_tree_path_free (path);
1202         }
1203 
1204       g_free (tooltip);
1205       g_free (display_name);
1206     }
1207 
1208   g_list_free (items);
1209 
1210   g_signal_handlers_unblock_by_func (G_OBJECT (dialog->store),
1211       G_CALLBACK (panel_preferences_dialog_item_row_changed), dialog);
1212 }
1213 
1214 
1215 
1216 static void
panel_preferences_dialog_item_move(GtkWidget * button,PanelPreferencesDialog * dialog)1217 panel_preferences_dialog_item_move (GtkWidget              *button,
1218                                     PanelPreferencesDialog *dialog)
1219 {
1220   GObject                 *treeview, *object;
1221   GtkTreeSelection        *selection;
1222   GtkTreeIter              iter_a, iter_b;
1223   XfcePanelPluginProvider *provider;
1224   GtkWidget               *itembar;
1225   gint                     position;
1226   gint                     direction;
1227   GtkTreePath             *path;
1228 
1229   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
1230 
1231   /* direction */
1232   object = gtk_builder_get_object (GTK_BUILDER (dialog), "item-up");
1233   panel_return_if_fail (GTK_IS_WIDGET (object));
1234   direction = G_OBJECT (button) == object ? -1 : 1;
1235 
1236   provider = panel_preferences_dialog_item_get_selected (dialog, &iter_a);
1237   if (G_LIKELY (provider != NULL))
1238     {
1239       /* get the provider position on the panel */
1240       itembar = gtk_bin_get_child (GTK_BIN (dialog->active));
1241       position = panel_itembar_get_child_index (PANEL_ITEMBAR (itembar),
1242                                                 GTK_WIDGET (provider));
1243       path = gtk_tree_model_get_path (GTK_TREE_MODEL (dialog->store), &iter_a);
1244 
1245       if (G_LIKELY (position != -1))
1246         {
1247           /* block the changed signal */
1248           g_signal_handler_block (G_OBJECT (itembar), dialog->items_changed_handler_id);
1249 
1250           /* move the item on the panel */
1251           panel_itembar_reorder_child (PANEL_ITEMBAR (itembar),
1252                                        GTK_WIDGET (provider),
1253                                        position + direction);
1254 
1255           /* save the new ids */
1256           panel_application_save_window (dialog->application,
1257                                          dialog->active,
1258                                          SAVE_PLUGIN_IDS);
1259 
1260           /* unblock the changed signal */
1261           g_signal_handler_unblock (G_OBJECT (itembar), dialog->items_changed_handler_id);
1262 
1263           /* move the item up or down in the list */
1264           if (direction == 1)
1265             {
1266               /* swap the items in the list */
1267               iter_b = iter_a;
1268               if (gtk_tree_model_iter_next (GTK_TREE_MODEL (dialog->store), &iter_b))
1269                 {
1270                   gtk_list_store_swap (dialog->store, &iter_a, &iter_b);
1271                   gtk_tree_path_next (path);
1272                 }
1273             }
1274           else
1275             {
1276               /* get the previous item in the list */
1277               if (gtk_tree_path_prev (path))
1278                 {
1279                   /* swap the items in the list */
1280                   gtk_tree_model_get_iter (GTK_TREE_MODEL (dialog->store), &iter_b, path);
1281                   gtk_list_store_swap (dialog->store, &iter_a, &iter_b);
1282                 }
1283             }
1284 
1285           /* fake update the selection */
1286           treeview = gtk_builder_get_object (GTK_BUILDER (dialog), "item-treeview");
1287           panel_return_if_fail (GTK_IS_WIDGET (treeview));
1288           selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (treeview));
1289           panel_preferences_dialog_item_selection_changed (selection, dialog);
1290 
1291           /* make the new selected position visible if moved out of area */
1292           gtk_tree_view_scroll_to_cell (GTK_TREE_VIEW (treeview), path, NULL, FALSE, 0, 0);
1293           gtk_tree_view_set_cursor (GTK_TREE_VIEW (treeview), path, NULL, FALSE);
1294 
1295         }
1296       gtk_tree_path_free (path);
1297     }
1298 }
1299 
1300 
1301 
1302 static void
panel_preferences_dialog_item_remove(GtkWidget * button,PanelPreferencesDialog * dialog)1303 panel_preferences_dialog_item_remove (GtkWidget              *button,
1304                                       PanelPreferencesDialog *dialog)
1305 {
1306   XfcePanelPluginProvider *provider;
1307   GtkWidget               *widget, *toplevel;
1308   PanelModule             *module;
1309 
1310   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
1311 
1312   provider = panel_preferences_dialog_item_get_selected (dialog, NULL);
1313   if (G_LIKELY (provider != NULL))
1314     {
1315       module = panel_module_get_from_plugin_provider (provider);
1316 
1317       /* create question dialog (same code is also in xfce-panel-plugin.c) */
1318       toplevel = gtk_widget_get_toplevel (button);
1319       widget = gtk_message_dialog_new (GTK_WINDOW (toplevel), GTK_DIALOG_MODAL,
1320                                        GTK_MESSAGE_QUESTION, GTK_BUTTONS_NONE,
1321                                        _("Are you sure that you want to remove \"%s\"?"),
1322                                        panel_module_get_display_name (module));
1323       gtk_message_dialog_format_secondary_text (GTK_MESSAGE_DIALOG (widget),
1324                                                 _("If you remove the item from the panel, "
1325                                                   "it is permanently lost."));
1326       gtk_dialog_add_buttons (GTK_DIALOG (widget), _("_Cancel"), GTK_RESPONSE_NO,
1327                               _("_Remove"), GTK_RESPONSE_YES, NULL);
1328       gtk_dialog_set_default_response (GTK_DIALOG (widget), GTK_RESPONSE_NO);
1329 
1330       /* run the dialog */
1331       if (gtk_dialog_run (GTK_DIALOG (widget)) == GTK_RESPONSE_YES)
1332         {
1333           gtk_widget_hide (widget);
1334           xfce_panel_plugin_provider_emit_signal (provider, PROVIDER_SIGNAL_REMOVE_PLUGIN);
1335         }
1336 
1337       gtk_widget_destroy (widget);
1338     }
1339 }
1340 
1341 
1342 
1343 static void
panel_preferences_dialog_item_add(GtkWidget * button,PanelPreferencesDialog * dialog)1344 panel_preferences_dialog_item_add (GtkWidget              *button,
1345                                    PanelPreferencesDialog *dialog)
1346 {
1347   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
1348 
1349   panel_item_dialog_show (dialog->active);
1350 }
1351 
1352 
1353 
1354 static void
panel_preferences_dialog_item_properties(GtkWidget * button,PanelPreferencesDialog * dialog)1355 panel_preferences_dialog_item_properties (GtkWidget              *button,
1356                                           PanelPreferencesDialog *dialog)
1357 {
1358   XfcePanelPluginProvider *provider;
1359 
1360   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
1361 
1362   provider = panel_preferences_dialog_item_get_selected (dialog, NULL);
1363   if (G_LIKELY (provider != NULL))
1364     xfce_panel_plugin_provider_show_configure (provider);
1365 }
1366 
1367 
1368 
1369 static void
panel_preferences_dialog_item_about(GtkWidget * button,PanelPreferencesDialog * dialog)1370 panel_preferences_dialog_item_about (GtkWidget              *button,
1371                                      PanelPreferencesDialog *dialog)
1372 {
1373   XfcePanelPluginProvider *provider;
1374 
1375   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
1376 
1377   provider = panel_preferences_dialog_item_get_selected (dialog, NULL);
1378   if (G_LIKELY (provider != NULL))
1379     xfce_panel_plugin_provider_show_about (provider);
1380 }
1381 
1382 
1383 
1384 static gboolean
panel_preferences_dialog_treeview_clicked(GtkTreeView * treeview,GdkEventButton * event,PanelPreferencesDialog * dialog)1385 panel_preferences_dialog_treeview_clicked (GtkTreeView            *treeview,
1386                                            GdkEventButton         *event,
1387                                            PanelPreferencesDialog *dialog)
1388 {
1389   gint x, y;
1390 
1391   panel_return_val_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog), FALSE);
1392   panel_return_val_if_fail (GTK_IS_TREE_VIEW (treeview), FALSE);
1393 
1394   gtk_tree_view_convert_widget_to_bin_window_coords (treeview,
1395                                                      event->x, event->y,
1396                                                      &x, &y);
1397 
1398   /* open preferences on double-click on a row */
1399   if (event->type == GDK_2BUTTON_PRESS
1400       && event->button == 1
1401       && gtk_tree_view_get_path_at_pos (treeview, x, y, NULL, NULL, NULL, NULL))
1402     {
1403       panel_preferences_dialog_item_properties (NULL, dialog);
1404       return TRUE;
1405     }
1406 
1407   return FALSE;
1408 }
1409 
1410 
1411 
1412 static void
panel_preferences_dialog_item_row_changed(GtkTreeModel * model,GtkTreePath * path,GtkTreeIter * iter,PanelPreferencesDialog * dialog)1413 panel_preferences_dialog_item_row_changed (GtkTreeModel           *model,
1414                                            GtkTreePath            *path,
1415                                            GtkTreeIter            *iter,
1416                                            PanelPreferencesDialog *dialog)
1417 {
1418   XfcePanelPluginProvider *provider = NULL;
1419   gint                     position;
1420   GtkWidget               *itembar;
1421   gint                     store_position;
1422 
1423   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
1424   panel_return_if_fail (GTK_TREE_MODEL (dialog->store) == model);
1425   panel_return_if_fail (PANEL_IS_WINDOW (dialog->active));
1426 
1427   /* get the changed row */
1428   gtk_tree_model_get (model, iter, ITEM_COLUMN_PROVIDER, &provider, -1);
1429   panel_return_if_fail (XFCE_IS_PANEL_PLUGIN_PROVIDER (provider));
1430   store_position = gtk_tree_path_get_indices (path)[0];
1431 
1432   /* actual position on the panel */
1433   itembar = gtk_bin_get_child (GTK_BIN (dialog->active));
1434   position = panel_itembar_get_child_index (PANEL_ITEMBAR (itembar),
1435                                             GTK_WIDGET (provider));
1436 
1437   /* correct position in the list */
1438   if (position < store_position)
1439     store_position--;
1440 
1441   /* move the item on the panel */
1442   if (position != store_position)
1443     {
1444       panel_itembar_reorder_child (PANEL_ITEMBAR (itembar),
1445                                    GTK_WIDGET (provider),
1446                                    store_position);
1447 
1448       panel_application_save_window (dialog->application,
1449                                      dialog->active,
1450                                      SAVE_PLUGIN_IDS);
1451     }
1452 }
1453 
1454 
1455 
1456 static void
panel_preferences_dialog_item_selection_changed(GtkTreeSelection * selection,PanelPreferencesDialog * dialog)1457 panel_preferences_dialog_item_selection_changed (GtkTreeSelection       *selection,
1458                                                  PanelPreferencesDialog *dialog)
1459 {
1460   XfcePanelPluginProvider *provider;
1461   GtkWidget               *itembar;
1462   gint                     position;
1463   gint                     items;
1464   gboolean                 active;
1465   GObject                 *object;
1466   guint                    i;
1467   const gchar             *button_names[] = { "item-remove", "item-up",
1468                                               "item-down", "item-about",
1469                                               "item-properties" };
1470 
1471   panel_return_if_fail (PANEL_IS_PREFERENCES_DIALOG (dialog));
1472 
1473   provider = panel_preferences_dialog_item_get_selected (dialog, NULL);
1474   if (G_LIKELY (provider != NULL))
1475     {
1476       /* get the current position and the items on the bar */
1477       itembar = gtk_bin_get_child (GTK_BIN (dialog->active));
1478       position = panel_itembar_get_child_index (PANEL_ITEMBAR (itembar), GTK_WIDGET (provider));
1479       items = panel_itembar_get_n_children (PANEL_ITEMBAR (itembar)) - 1;
1480 
1481       /* update sensitivity of buttons */
1482       object = gtk_builder_get_object (GTK_BUILDER (dialog), "item-up");
1483       panel_return_if_fail (GTK_IS_WIDGET (object));
1484       gtk_widget_set_sensitive (GTK_WIDGET (object), !!(position > 0 && position <= items));
1485 
1486       object = gtk_builder_get_object (GTK_BUILDER (dialog), "item-down");
1487       panel_return_if_fail (GTK_IS_WIDGET (object));
1488       gtk_widget_set_sensitive (GTK_WIDGET (object), !!(position >= 0 && position < items));
1489 
1490       object = gtk_builder_get_object (GTK_BUILDER (dialog), "item-remove");
1491       panel_return_if_fail (GTK_IS_WIDGET (object));
1492       gtk_widget_set_sensitive (GTK_WIDGET (object), TRUE);
1493 
1494       object = gtk_builder_get_object (GTK_BUILDER (dialog), "item-properties");
1495       panel_return_if_fail (GTK_IS_WIDGET (object));
1496       active = xfce_panel_plugin_provider_get_show_configure (provider);
1497       gtk_widget_set_sensitive (GTK_WIDGET (object), active);
1498 
1499       object = gtk_builder_get_object (GTK_BUILDER (dialog), "item-about");
1500       panel_return_if_fail (GTK_IS_WIDGET (object));
1501       active = xfce_panel_plugin_provider_get_show_about (provider);
1502       gtk_widget_set_sensitive (GTK_WIDGET (object), active);
1503     }
1504   else
1505     {
1506       /* make all items insensitive, except for the add button */
1507       for (i = 0; i < G_N_ELEMENTS (button_names); i++)
1508         {
1509           object = gtk_builder_get_object (GTK_BUILDER (dialog), button_names[i]);
1510           panel_return_if_fail (GTK_IS_WIDGET (object));
1511           gtk_widget_set_sensitive (GTK_WIDGET (object), FALSE);
1512         }
1513     }
1514 }
1515 
1516 
1517 
1518 static void
panel_preferences_dialog_plug_deleted(GtkWidget * plug)1519 panel_preferences_dialog_plug_deleted (GtkWidget *plug)
1520 {
1521   g_signal_handlers_disconnect_by_func (G_OBJECT (plug),
1522       G_CALLBACK (panel_preferences_dialog_plug_deleted), NULL);
1523 
1524   g_object_unref (G_OBJECT (dialog_singleton));
1525 }
1526 
1527 
1528 
1529 static void
panel_preferences_dialog_show_internal(PanelWindow * active,Window socket_window)1530 panel_preferences_dialog_show_internal (PanelWindow *active,
1531                                         Window       socket_window)
1532 {
1533   gint         panel_id = 0;
1534   GObject     *window, *combo;
1535   GdkScreen   *screen;
1536   GSList      *windows;
1537   GtkWidget   *plug;
1538   GObject     *plug_child;
1539   GtkWidget   *content_area;
1540 
1541   panel_return_if_fail (active == NULL || PANEL_IS_WINDOW (active));
1542 
1543   /* check if not the entire application is locked */
1544   if (panel_dialogs_kiosk_warning ())
1545     return;
1546 
1547   if (dialog_singleton == NULL)
1548     {
1549       /* create new dialog singleton */
1550       dialog_singleton = g_object_new (PANEL_TYPE_PREFERENCES_DIALOG, NULL);
1551       g_object_add_weak_pointer (G_OBJECT (dialog_singleton), (gpointer) &dialog_singleton);
1552     }
1553 
1554   if (active == NULL)
1555     {
1556       /* select first window */
1557       windows = panel_application_get_windows (dialog_singleton->application);
1558       if (windows != NULL)
1559         active = g_slist_nth_data (windows, 0);
1560     }
1561 
1562   /* select the active window in the dialog */
1563   combo = gtk_builder_get_object (GTK_BUILDER (dialog_singleton), "panel-combobox");
1564   panel_return_if_fail (GTK_IS_WIDGET (combo));
1565   panel_id = panel_window_get_id (active);
1566   if (!panel_preferences_dialog_panel_combobox_rebuild (dialog_singleton, panel_id))
1567     gtk_combo_box_set_active (GTK_COMBO_BOX (combo), 0);
1568 
1569   window = gtk_builder_get_object (GTK_BUILDER (dialog_singleton), "dialog");
1570   panel_return_if_fail (GTK_IS_WIDGET (window));
1571   plug_child = gtk_builder_get_object (GTK_BUILDER (dialog_singleton), "plug-child");
1572   panel_return_if_fail (GTK_IS_WIDGET (plug_child));
1573 
1574   /* check if we need to remove the window from the plug */
1575   if (dialog_singleton->socket_plug != NULL)
1576     {
1577       panel_return_if_fail (GTK_IS_PLUG (dialog_singleton->socket_plug));
1578 
1579       /* move the vbox to the dialog */
1580       content_area = gtk_dialog_get_content_area (GTK_DIALOG (window));
1581       xfce_widget_reparent (GTK_WIDGET (plug_child), content_area);
1582       gtk_widget_show (GTK_WIDGET (plug_child));
1583 
1584       /* destroy the plug */
1585       plug = dialog_singleton->socket_plug;
1586       dialog_singleton->socket_plug = NULL;
1587 
1588       g_signal_handlers_disconnect_by_func (G_OBJECT (plug),
1589           G_CALLBACK (panel_preferences_dialog_plug_deleted), NULL);
1590       gtk_widget_destroy (plug);
1591     }
1592 
1593   if (socket_window == 0)
1594     {
1595       /* show the dialog on the same screen as the panel */
1596       if (G_LIKELY (active != NULL))
1597         screen = gtk_widget_get_screen (GTK_WIDGET (active));
1598       else
1599         screen = gdk_screen_get_default ();
1600       gtk_window_set_screen (GTK_WINDOW (window), screen);
1601 
1602       gtk_window_present (GTK_WINDOW (window));
1603       panel_application_take_dialog (dialog_singleton->application, GTK_WINDOW (window));
1604     }
1605   else
1606     {
1607       /* hide window */
1608       gtk_widget_hide (GTK_WIDGET (window));
1609 
1610       /* create a new plug */
1611       plug = gtk_plug_new (socket_window);
1612       g_signal_connect (G_OBJECT (plug), "delete-event",
1613           G_CALLBACK (panel_preferences_dialog_plug_deleted), NULL);
1614       dialog_singleton->socket_plug = plug;
1615       gtk_widget_show (plug);
1616 
1617       /* move the vbox in the plug */
1618       xfce_widget_reparent (GTK_WIDGET (plug_child), plug);
1619       gtk_widget_show (GTK_WIDGET (plug_child));
1620     }
1621 }
1622 
1623 
1624 
1625 void
panel_preferences_dialog_show(PanelWindow * active)1626 panel_preferences_dialog_show (PanelWindow *active)
1627 {
1628   panel_return_if_fail (active == NULL || PANEL_IS_WINDOW (active));
1629   panel_preferences_dialog_show_internal (active, 0);
1630 }
1631 
1632 
1633 
1634 void
panel_preferences_dialog_show_from_id(gint panel_id,Window socket_window)1635 panel_preferences_dialog_show_from_id (gint         panel_id,
1636                                        Window       socket_window)
1637 {
1638   PanelApplication *application;
1639   PanelWindow      *window;
1640 
1641   application = panel_application_get ();
1642   window = panel_application_get_window (application, panel_id);
1643   panel_preferences_dialog_show_internal (window, socket_window);
1644   g_object_unref (G_OBJECT (application));
1645 }
1646 
1647 
1648 
1649 gboolean
panel_preferences_dialog_visible(void)1650 panel_preferences_dialog_visible (void)
1651 {
1652   return !!(dialog_singleton != NULL);
1653 }
1654