dialogs.c 16.6 KB
Newer Older
1
/* GIMP - The GNU Image Manipulation Program
2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
 * Copyright (C) 1995 Spencer Kimball and Peter Mattis
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
 */

#include "config.h"

#include <gtk/gtk.h>

23 24
#include "libgimpbase/gimpbase.h"
#include "libgimpconfig/gimpconfig.h"
25 26
#include "libgimpwidgets/gimpwidgets.h"

27
#include "dialogs-types.h"
28

Michael Natterer's avatar
Michael Natterer committed
29
#include "core/gimp.h"
30
#include "core/gimpcontext.h"
31
#include "core/gimplist.h"
32

33
#include "widgets/gimpdialogfactory.h"
34
#include "widgets/gimphelp-ids.h"
35
#include "widgets/gimpmenufactory.h"
36
#include "widgets/gimpsessioninfo.h"
37

38 39 40
#include "dialogs.h"
#include "dialogs-constructors.h"

41 42
#include "gimp-intl.h"

43

44 45 46
GimpDialogFactory *global_dialog_factory  = NULL;
GimpDialogFactory *global_dock_factory    = NULL;
GimpDialogFactory *global_toolbox_factory = NULL;
47
GimpDialogFactory *global_display_factory = NULL;
48

49 50
GimpContainer     *global_recent_docks    = NULL;

51

52
#define FOREIGN(id, singleton, remember_size) \
53
  { id, NULL, NULL, NULL, NULL, \
54
    NULL, 0, singleton,  TRUE, remember_size, FALSE }
55

56
#define TOPLEVEL(id, new_func, singleton, session_managed, remember_size) \
57 58 59 60
  { id, NULL, NULL, NULL, NULL, \
    new_func, 0, singleton, session_managed, remember_size, FALSE }


61
static const GimpDialogFactoryEntry toplevel_entries[] =
62
{
63
  /*  foreign toplevels without constructor  */
64
  FOREIGN ("gimp-brightness-contrast-tool-dialog", TRUE,  FALSE),
65
  FOREIGN ("gimp-color-balance-tool-dialog",       TRUE,  FALSE),
66 67 68 69
  FOREIGN ("gimp-color-picker-tool-dialog",        TRUE,  TRUE),
  FOREIGN ("gimp-colorize-tool-dialog",            TRUE,  FALSE),
  FOREIGN ("gimp-crop-tool-dialog",                TRUE,  FALSE),
  FOREIGN ("gimp-curves-tool-dialog",              TRUE,  TRUE),
70
  FOREIGN ("gimp-desaturate-tool-dialog",          TRUE,  FALSE),
71
  FOREIGN ("gimp-gegl-tool-dialog",                TRUE,  FALSE),
72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89
  FOREIGN ("gimp-hue-saturation-tool-dialog",      TRUE,  FALSE),
  FOREIGN ("gimp-levels-tool-dialog",              TRUE,  TRUE),
  FOREIGN ("gimp-measure-tool-dialog",             TRUE,  FALSE),
  FOREIGN ("gimp-posterize-tool-dialog",           TRUE,  FALSE),
  FOREIGN ("gimp-rotate-tool-dialog",              TRUE,  FALSE),
  FOREIGN ("gimp-scale-tool-dialog",               TRUE,  FALSE),
  FOREIGN ("gimp-shear-tool-dialog",               TRUE,  FALSE),
  FOREIGN ("gimp-text-tool-dialog",                TRUE,  TRUE),
  FOREIGN ("gimp-threshold-tool-dialog",           TRUE,  FALSE),
  FOREIGN ("gimp-perspective-tool-dialog",         TRUE,  FALSE),

  FOREIGN ("gimp-toolbox-color-dialog",            TRUE,  FALSE),
  FOREIGN ("gimp-gradient-editor-color-dialog",    TRUE,  FALSE),
  FOREIGN ("gimp-palette-editor-color-dialog",     TRUE,  FALSE),
  FOREIGN ("gimp-colormap-editor-color-dialog",    TRUE,  FALSE),

  FOREIGN ("gimp-controller-editor-dialog",        FALSE, TRUE),
  FOREIGN ("gimp-controller-action-dialog",        FALSE, TRUE),
90

91
  /*  ordinary toplevels  */
92 93 94 95 96 97 98 99
  TOPLEVEL ("gimp-image-new-dialog",
            dialogs_image_new_new,          FALSE, TRUE, FALSE),
  TOPLEVEL ("gimp-file-open-dialog",
            dialogs_file_open_new,          TRUE,  TRUE, TRUE),
  TOPLEVEL ("gimp-file-open-location-dialog",
            dialogs_file_open_location_new, FALSE, TRUE, FALSE),
  TOPLEVEL ("gimp-file-save-dialog",
            dialogs_file_save_new,          FALSE, TRUE, TRUE),
100 101

  /*  singleton toplevels  */
102
  TOPLEVEL ("gimp-preferences-dialog",
103 104 105
            dialogs_preferences_get,        TRUE, TRUE,  FALSE),
  TOPLEVEL ("gimp-keyboard-shortcuts-dialog",
            dialogs_keyboard_shortcuts_get, TRUE, TRUE,  TRUE),
106
  TOPLEVEL ("gimp-module-dialog",
107
            dialogs_module_get,             TRUE, TRUE,  TRUE),
108 109
  TOPLEVEL ("gimp-palette-import-dialog",
            dialogs_palette_import_get,     TRUE, TRUE,  TRUE),
110
  TOPLEVEL ("gimp-tips-dialog",
111
            dialogs_tips_get,               TRUE, FALSE, FALSE),
112
  TOPLEVEL ("gimp-about-dialog",
113
            dialogs_about_get,              TRUE, FALSE, FALSE),
114
  TOPLEVEL ("gimp-error-dialog",
115
            dialogs_error_get,              TRUE, FALSE, FALSE),
116
  TOPLEVEL ("gimp-close-all-dialog",
117
            dialogs_close_all_get,          TRUE, FALSE, FALSE),
118
  TOPLEVEL ("gimp-quit-dialog",
119
            dialogs_quit_get,               TRUE, FALSE, FALSE)
120 121
};

122
#define DOCKABLE(id,name,blurb,stock_id,help_id,\
123
                 new_func,view_size,singleton) \
124
  { id, name, blurb, stock_id, help_id, \
125
    new_func, view_size, singleton, FALSE, FALSE, TRUE }
126 127

#define LISTGRID(id,name,blurb,stock_id,help_id,\
128
                 view_size) \
129
  { "gimp-"#id"-list", name, blurb, stock_id, help_id, \
130
    dialogs_##id##_list_view_new, view_size, FALSE, FALSE, FALSE, TRUE }, \
131
  { "gimp-"#id"-grid", name, blurb, stock_id, help_id, \
132
    dialogs_##id##_grid_view_new, view_size, FALSE, FALSE, FALSE, TRUE }
133

134
static const GimpDialogFactoryEntry dock_entries[] =
135
{
136
  /*  singleton dockables  */
137 138 139
  DOCKABLE ("gimp-tool-options",
            N_("Tool Options"), NULL, GIMP_STOCK_TOOL_OPTIONS,
            GIMP_HELP_TOOL_OPTIONS_DIALOG,
140
            dialogs_tool_options_new, 0, TRUE),
141 142 143
  DOCKABLE ("gimp-device-status",
            N_("Devices"), N_("Device Status"), GIMP_STOCK_DEVICE_STATUS,
            GIMP_HELP_DEVICE_STATUS_DIALOG,
144
            dialogs_device_status_new, 0, TRUE),
145 146 147
  DOCKABLE ("gimp-error-console",
            N_("Errors"), N_("Error Console"), GIMP_STOCK_WARNING,
            GIMP_HELP_ERRORS_DIALOG,
148 149
            dialogs_error_console_new, 0, TRUE),
  DOCKABLE ("gimp-cursor-view",
150 151
            N_("Pointer"), N_("Pointer Information"), GIMP_STOCK_CURSOR,
            GIMP_HELP_POINTER_INFO_DIALOG,
152
            dialogs_cursor_view_new, 0, TRUE),
153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174

  /*  list & grid views  */
  LISTGRID (image, N_("Images"), NULL, GIMP_STOCK_IMAGES,
            GIMP_HELP_IMAGE_DIALOG, GIMP_VIEW_SIZE_MEDIUM),
  LISTGRID (brush, N_("Brushes"), NULL, GIMP_STOCK_BRUSH,
            GIMP_HELP_BRUSH_DIALOG, GIMP_VIEW_SIZE_MEDIUM),
  LISTGRID (pattern, N_("Patterns"), NULL, GIMP_STOCK_PATTERN,
            GIMP_HELP_PATTERN_DIALOG, GIMP_VIEW_SIZE_MEDIUM),
  LISTGRID (gradient, N_("Gradients"), NULL, GIMP_STOCK_GRADIENT,
            GIMP_HELP_GRADIENT_DIALOG, GIMP_VIEW_SIZE_MEDIUM),
  LISTGRID (palette, N_("Palettes"), NULL, GIMP_STOCK_PALETTE,
            GIMP_HELP_PALETTE_DIALOG, GIMP_VIEW_SIZE_MEDIUM),
  LISTGRID (font, N_("Fonts"), NULL, GIMP_STOCK_FONT,
            GIMP_HELP_FONT_DIALOG, GIMP_VIEW_SIZE_MEDIUM),
  LISTGRID (tool, N_("Tools"), NULL, GIMP_STOCK_TOOLS,
            GIMP_HELP_TOOLS_DIALOG, GIMP_VIEW_SIZE_SMALL),
  LISTGRID (buffer, N_("Buffers"), NULL, GIMP_STOCK_BUFFER,
            GIMP_HELP_BUFFER_DIALOG, GIMP_VIEW_SIZE_MEDIUM),
  LISTGRID (document, N_("History"), N_("Document History"), GTK_STOCK_OPEN,
            GIMP_HELP_DOCUMENT_DIALOG, GIMP_VIEW_SIZE_LARGE),
  LISTGRID (template, N_("Templates"), N_("Image Templates"), GIMP_STOCK_TEMPLATE,
            GIMP_HELP_TEMPLATE_DIALOG, GIMP_VIEW_SIZE_SMALL),
175

176
  /*  image related  */
177 178 179 180 181 182 183 184 185 186 187 188 189
  DOCKABLE ("gimp-layer-list",
            N_("Layers"), NULL, GIMP_STOCK_LAYERS,
            GIMP_HELP_LAYER_DIALOG,
            dialogs_layer_list_view_new, 0, FALSE),
  DOCKABLE ("gimp-channel-list",
            N_("Channels"), NULL, GIMP_STOCK_CHANNELS,
            GIMP_HELP_CHANNEL_DIALOG,
            dialogs_channel_list_view_new, 0, FALSE),
  DOCKABLE ("gimp-vectors-list",
            N_("Paths"), NULL, GIMP_STOCK_PATHS,
            GIMP_HELP_PATH_DIALOG,
            dialogs_vectors_list_view_new, 0, FALSE),
  DOCKABLE ("gimp-indexed-palette",
190
            N_("Colormap"), NULL, GIMP_STOCK_COLORMAP,
191 192 193 194 195 196 197 198 199 200 201 202 203 204
            GIMP_HELP_INDEXED_PALETTE_DIALOG,
            dialogs_colormap_editor_new, 0, FALSE),
  DOCKABLE ("gimp-histogram-editor",
            N_("Histogram"), NULL, GIMP_STOCK_HISTOGRAM,
            GIMP_HELP_HISTOGRAM_DIALOG,
            dialogs_histogram_editor_new, 0, FALSE),
  DOCKABLE ("gimp-selection-editor",
            N_("Selection"), N_("Selection Editor"), GIMP_STOCK_SELECTION,
            GIMP_HELP_SELECTION_DIALOG,
            dialogs_selection_editor_new, 0, FALSE),
  DOCKABLE ("gimp-undo-history",
            N_("Undo"), N_("Undo History"), GIMP_STOCK_UNDO_HISTORY,
            GIMP_HELP_UNDO_DIALOG,
            dialogs_undo_editor_new, 0, FALSE),
205 206 207 208
  DOCKABLE ("gimp-sample-point-editor",
            N_("Sample Points"), N_("Sample Points"), GIMP_STOCK_SAMPLE_POINT,
            GIMP_HELP_SAMPLE_POINT_DIALOG,
            dialogs_sample_point_editor_new, 0, FALSE),
209

210
  /*  display related  */
211 212 213 214
  DOCKABLE ("gimp-navigation-view",
            N_("Navigation"), N_("Display Navigation"), GIMP_STOCK_NAVIGATION,
            GIMP_HELP_NAVIGATION_DIALOG,
            dialogs_navigation_editor_new, 0, FALSE),
215

216
  /*  editors  */
217 218 219 220
  DOCKABLE ("gimp-color-editor",
            N_("FG/BG"), N_("FG/BG Color"), GIMP_STOCK_DEFAULT_COLORS,
            GIMP_HELP_COLOR_DIALOG,
            dialogs_color_editor_new, 0, FALSE),
221

222
  /*  singleton editors  */
223 224 225 226 227 228 229 230 231 232 233 234
  DOCKABLE ("gimp-brush-editor",
            N_("Brush Editor"), NULL, GIMP_STOCK_BRUSH,
            GIMP_HELP_BRUSH_EDITOR_DIALOG,
            dialogs_brush_editor_get, 0, TRUE),
  DOCKABLE ("gimp-gradient-editor",
            N_("Gradient Editor"), NULL, GIMP_STOCK_GRADIENT,
            GIMP_HELP_GRADIENT_EDITOR_DIALOG,
            dialogs_gradient_editor_get, 0, TRUE),
  DOCKABLE ("gimp-palette-editor",
            N_("Palette Editor"), NULL, GIMP_STOCK_PALETTE,
            GIMP_HELP_PALETTE_EDITOR_DIALOG,
            dialogs_palette_editor_get, 0, TRUE)
235 236 237 238 239
};


/*  public functions  */

240
void
241 242
dialogs_init (Gimp            *gimp,
              GimpMenuFactory *menu_factory)
243
{
244 245
  gint i;

246
  g_return_if_fail (GIMP_IS_GIMP (gimp));
247
  g_return_if_fail (GIMP_IS_MENU_FACTORY (menu_factory));
248

Michael Natterer's avatar
Michael Natterer committed
249
  global_dialog_factory = gimp_dialog_factory_new ("toplevel",
250 251 252
                                                   gimp_get_user_context (gimp),
                                                   menu_factory,
                                                   NULL);
253

254 255
  global_toolbox_factory = gimp_dialog_factory_new ("toolbox",
                                                    gimp_get_user_context (gimp),
256
                                                    menu_factory,
257
                                                    dialogs_toolbox_get);
258 259
  gimp_dialog_factory_set_constructor (global_toolbox_factory,
                                       dialogs_dockable_constructor);
260

Michael Natterer's avatar
Michael Natterer committed
261
  global_dock_factory = gimp_dialog_factory_new ("dock",
262 263 264
                                                 gimp_get_user_context (gimp),
                                                 menu_factory,
                                                 dialogs_dock_new);
265 266
  gimp_dialog_factory_set_constructor (global_dock_factory,
                                       dialogs_dockable_constructor);
267

268 269 270 271 272
  global_display_factory = gimp_dialog_factory_new ("display",
                                                    gimp_get_user_context (gimp),
                                                    menu_factory,
                                                    NULL);

Michael Natterer's avatar
Michael Natterer committed
273
  for (i = 0; i < G_N_ELEMENTS (toplevel_entries); i++)
274
    gimp_dialog_factory_register_entry (global_dialog_factory,
275 276 277 278 279 280 281 282 283 284 285
                                        toplevel_entries[i].identifier,
                                        gettext (toplevel_entries[i].name),
                                        gettext (toplevel_entries[i].blurb),
                                        toplevel_entries[i].stock_id,
                                        toplevel_entries[i].help_id,
                                        toplevel_entries[i].new_func,
                                        toplevel_entries[i].view_size,
                                        toplevel_entries[i].singleton,
                                        toplevel_entries[i].session_managed,
                                        toplevel_entries[i].remember_size,
                                        toplevel_entries[i].remember_if_open);
286

Michael Natterer's avatar
Michael Natterer committed
287
  for (i = 0; i < G_N_ELEMENTS (dock_entries); i++)
288
    gimp_dialog_factory_register_entry (global_dock_factory,
289 290 291 292 293 294 295 296 297 298 299
                                        dock_entries[i].identifier,
                                        gettext (dock_entries[i].name),
                                        gettext (dock_entries[i].blurb),
                                        dock_entries[i].stock_id,
                                        dock_entries[i].help_id,
                                        dock_entries[i].new_func,
                                        dock_entries[i].view_size,
                                        dock_entries[i].singleton,
                                        dock_entries[i].session_managed,
                                        dock_entries[i].remember_size,
                                        dock_entries[i].remember_if_open);
300 301

  gimp_dialog_factory_register_entry (global_display_factory,
302
                                      "gimp-empty-image-window",
303 304 305 306 307 308 309 310
                                      NULL, NULL,
                                      NULL, NULL,
                                      NULL,
                                      -1,
                                      TRUE,
                                      TRUE,
                                      TRUE,
                                      FALSE);
311 312

  global_recent_docks = gimp_list_new (GIMP_TYPE_SESSION_INFO, FALSE);
313
}
314 315

void
Michael Natterer's avatar
Michael Natterer committed
316
dialogs_exit (Gimp *gimp)
317
{
318 319
  g_return_if_fail (GIMP_IS_GIMP (gimp));

320 321
  if (global_dialog_factory)
    {
322
      g_object_unref (global_dialog_factory);
323 324 325
      global_dialog_factory = NULL;
    }

326 327 328 329 330 331 332 333
  /*  destroy the "global_toolbox_factory" _before_ destroying the
   *  "global_dock_factory" because the "global_toolbox_factory" owns
   *  dockables which were created by the "global_dock_factory".  This
   *  way they are properly removed from the "global_dock_factory", which
   *  would complain about stale entries otherwise.
   */
  if (global_toolbox_factory)
    {
334
      g_object_unref (global_toolbox_factory);
335 336 337
      global_toolbox_factory = NULL;
    }

338 339
  if (global_dock_factory)
    {
340
      g_object_unref (global_dock_factory);
341 342
      global_dock_factory = NULL;
    }
343 344 345 346 347 348

  if (global_display_factory)
    {
      g_object_unref (global_display_factory);
      global_display_factory = NULL;
    }
349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379

  if (global_recent_docks)
    {
      g_object_unref (global_recent_docks);
      global_recent_docks = NULL;
    }
}

void
dialogs_load_recent_docks (Gimp *gimp)
{
  gchar  *filename;
  GError *error = NULL;

  g_return_if_fail (GIMP_IS_GIMP (gimp));

  filename = gimp_personal_rc_file ("dockrc");

  if (gimp->be_verbose)
    g_print ("Parsing '%s'\n", gimp_filename_to_utf8 (filename));

  if (! gimp_config_deserialize_file (GIMP_CONFIG (global_recent_docks),
                                      filename,
                                      NULL, &error))
    {
      if (error->code != GIMP_CONFIG_ERROR_OPEN_ENOENT)
        gimp_message (gimp, NULL, GIMP_MESSAGE_ERROR, "%s", error->message);

      g_clear_error (&error);
    }

380 381
  gimp_list_reverse (GIMP_LIST (global_recent_docks));

382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408
  g_free (filename);
}

void
dialogs_save_recent_docks (Gimp *gimp)
{
  gchar  *filename;
  GError *error = NULL;

  g_return_if_fail (GIMP_IS_GIMP (gimp));

  filename = gimp_personal_rc_file ("dockrc");

  if (gimp->be_verbose)
    g_print ("Writing '%s'\n", gimp_filename_to_utf8 (filename));

  if (! gimp_config_serialize_to_file (GIMP_CONFIG (global_recent_docks),
                                       filename,
                                       "recently closed docks",
                                       "end of recently closed docks",
                                       NULL, &error))
    {
      gimp_message (gimp, NULL, GIMP_MESSAGE_ERROR, "%s", error->message);
      g_clear_error (&error);
    }

  g_free (filename);
409
}
410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427

GtkWidget *
dialogs_get_toolbox (void)
{
  GList *list;

  g_return_val_if_fail (GIMP_IS_DIALOG_FACTORY (global_toolbox_factory), NULL);

  for (list = global_toolbox_factory->open_dialogs;
       list;
       list = g_list_next (list))
    {
      if (GTK_WIDGET_TOPLEVEL (list->data))
        return list->data;
    }

  return NULL;
}