Example #1
0
void
action_message (GimpDisplay *display,
                GObject     *object,
                const gchar *format,
                ...)
{
  GimpDisplayShell *shell     = gimp_display_get_shell (display);
  GimpStatusbar    *statusbar = gimp_display_shell_get_statusbar (shell);
  const gchar      *icon_name = NULL;
  va_list           args;

  if (GIMP_IS_TOOL_OPTIONS (object))
    {
      GimpToolInfo *tool_info = GIMP_TOOL_OPTIONS (object)->tool_info;

      icon_name = gimp_viewable_get_icon_name (GIMP_VIEWABLE (tool_info));
    }
  else if (GIMP_IS_VIEWABLE (object))
    {
      icon_name = gimp_viewable_get_icon_name (GIMP_VIEWABLE (object));
    }

  va_start (args, format);
  gimp_statusbar_push_temp_valist (statusbar, GIMP_MESSAGE_INFO,
                                   icon_name, format, args);
  va_end (args);
}
Example #2
0
GtkWidget *
gimp_view_new_full (GimpContext  *context,
                    GimpViewable *viewable,
                    gint          width,
                    gint          height,
                    gint          border_width,
                    gboolean      is_popup,
                    gboolean      clickable,
                    gboolean      show_popup)
{
    GtkWidget *view;

    g_return_val_if_fail (context == NULL || GIMP_IS_CONTEXT (context), NULL);
    g_return_val_if_fail (GIMP_IS_VIEWABLE (viewable), NULL);

    view = gimp_view_new_full_by_types (context,
                                        GIMP_TYPE_VIEW,
                                        G_TYPE_FROM_INSTANCE (viewable),
                                        width, height, border_width,
                                        is_popup, clickable, show_popup);

    if (view)
        gimp_view_set_viewable (GIMP_VIEW (view), viewable);

    gimp_view_renderer_remove_idle (GIMP_VIEW (view)->renderer);

    return view;
}
Example #3
0
void
gimp_action_group_set_action_viewable (GimpActionGroup *group,
                                       const gchar     *action_name,
                                       GimpViewable    *viewable)
{
  GtkAction *action;

  g_return_if_fail (GIMP_IS_ACTION_GROUP (group));
  g_return_if_fail (action_name != NULL);
  g_return_if_fail (viewable == NULL || GIMP_IS_VIEWABLE (viewable));

  action = gtk_action_group_get_action (GTK_ACTION_GROUP (group), action_name);

  if (! action)
    {
      g_warning ("%s: Unable to set viewable of action "
                 "which doesn't exist: %s",
                 G_STRFUNC, action_name);
      return;
    }

  if (! GIMP_IS_ACTION (action))
    {
      g_warning ("%s: Unable to set \"viewable\" of action "
                 "which is not a GimpAction: %s",
                 G_STRFUNC, action_name);
      return;
    }

  g_object_set (action, "viewable", viewable, NULL);
}
gboolean
gimp_view_popup_show (GtkWidget      *widget,
                      GdkEventButton *bevent,
                      GimpContext    *context,
                      GimpViewable   *viewable,
                      gint            view_width,
                      gint            view_height,
                      gboolean        dot_for_dot)
{
  GimpViewPopup *popup;
  gint           popup_width;
  gint           popup_height;

  g_return_val_if_fail (GTK_IS_WIDGET (widget), FALSE);
  g_return_val_if_fail (bevent != NULL, FALSE);
  g_return_val_if_fail (context == NULL || GIMP_IS_CONTEXT (context), FALSE);
  g_return_val_if_fail (GIMP_IS_VIEWABLE (viewable), FALSE);

  if (! gimp_viewable_get_popup_size (viewable,
                                      view_width,
                                      view_height,
                                      dot_for_dot,
                                      &popup_width,
                                      &popup_height))
    return FALSE;

  popup = g_slice_new0 (GimpViewPopup);

  popup->widget       = widget;
  popup->context      = context;
  popup->viewable     = viewable;
  popup->popup_width  = popup_width;
  popup->popup_height = popup_height;
  popup->dot_for_dot  = dot_for_dot;
  popup->button       = bevent->button;
  popup->button_x     = bevent->x_root;
  popup->button_y     = bevent->y_root;

  g_signal_connect (widget, "button-release-event",
                    G_CALLBACK (gimp_view_popup_button_release),
                    popup);
  g_signal_connect (widget, "unmap",
                    G_CALLBACK (gimp_view_popup_unmap),
                    popup);
  g_signal_connect (widget, "drag-begin",
                    G_CALLBACK (gimp_view_popup_drag_begin),
                    popup);

  popup->timeout_id = g_timeout_add (VIEW_POPUP_DELAY,
                                     (GSourceFunc) gimp_view_popup_timeout,
                                     popup);

  g_object_set_data_full (G_OBJECT (widget), "gimp-view-popup", popup,
                          (GDestroyNotify) gimp_view_popup_hide);

  gtk_grab_add (widget);

  return TRUE;
}
Example #5
0
void
gimp_view_set_viewable (GimpView     *view,
                        GimpViewable *viewable)
{
    g_return_if_fail (GIMP_IS_VIEW (view));
    g_return_if_fail (viewable == NULL || GIMP_IS_VIEWABLE (viewable));

    if (viewable == view->viewable)
        return;

    g_signal_emit (view, view_signals[SET_VIEWABLE], 0, view->viewable, viewable);
}
Example #6
0
GtkWidget *
gimp_viewable_dialog_new (GimpViewable *viewable,
                          GimpContext  *context,
                          const gchar  *title,
                          const gchar  *role,
                          const gchar  *icon_name,
                          const gchar  *desc,
                          GtkWidget    *parent,
                          GimpHelpFunc  help_func,
                          const gchar  *help_id,
                          ...)
{
  GimpViewableDialog *dialog;
  va_list             args;

  g_return_val_if_fail (viewable == NULL || GIMP_IS_VIEWABLE (viewable), NULL);
  g_return_val_if_fail (context == NULL || GIMP_IS_CONTEXT (context), NULL);
  g_return_val_if_fail (title != NULL, NULL);
  g_return_val_if_fail (role != NULL, NULL);
  g_return_val_if_fail (parent == NULL || GTK_IS_WIDGET (parent), NULL);

  if (! viewable)
    g_warning ("Use of GimpViewableDialog with a NULL viewable is depecrated!");

  dialog = g_object_new (GIMP_TYPE_VIEWABLE_DIALOG,
                         "viewable",    viewable,
                         "context",     context,
                         "title",       title,
                         "role",        role,
                         "help-func",   help_func,
                         "help-id",     help_id,
                         "icon-name",   icon_name,
                         "description", desc,
                         "parent",      parent,
                         NULL);

  va_start (args, help_id);
  gimp_dialog_add_buttons_valist (GIMP_DIALOG (dialog), args);
  va_end (args);

  return GTK_WIDGET (dialog);
}
Example #7
0
GtkWidget *
resize_dialog_new (GimpViewable       *viewable,
                   GimpContext        *context,
                   const gchar        *title,
                   const gchar        *role,
                   GtkWidget          *parent,
                   GimpHelpFunc        help_func,
                   const gchar        *help_id,
                   GimpUnit            unit,
                   GimpResizeCallback  callback,
                   gpointer            user_data)
{
  GtkWidget    *dialog;
  GtkWidget    *main_vbox;
  GtkWidget    *vbox;
  GtkWidget    *abox;
  GtkWidget    *frame;
  GtkWidget    *button;
  GtkWidget    *spinbutton;
  GtkWidget    *entry;
  GtkObject    *adjustment;
  GdkPixbuf    *pixbuf;
  ResizeDialog *private;
  GimpImage    *image = NULL;
  const gchar  *text  = NULL;
  gint          width, height;
  gdouble       xres, yres;

  g_return_val_if_fail (GIMP_IS_VIEWABLE (viewable), NULL);
  g_return_val_if_fail (GIMP_IS_CONTEXT (context), NULL);
  g_return_val_if_fail (callback != NULL, NULL);

  if (GIMP_IS_IMAGE (viewable))
    {
      image = GIMP_IMAGE (viewable);

      width  = gimp_image_get_width (image);
      height = gimp_image_get_height (image);

      text = _("Canvas Size");
    }
  else if (GIMP_IS_ITEM (viewable))
    {
      GimpItem *item = GIMP_ITEM (viewable);

      image = gimp_item_get_image (item);

      width  = gimp_item_width (item);
      height = gimp_item_height (item);

      text = _("Layer Size");
    }
  else
    {
      g_return_val_if_reached (NULL);
    }

  dialog = gimp_viewable_dialog_new (viewable, context,
                                     title, role, GIMP_STOCK_RESIZE, title,
                                     parent,
                                     help_func, help_id,

                                     GIMP_STOCK_RESET,  RESPONSE_RESET,
                                     GTK_STOCK_CANCEL,  GTK_RESPONSE_CANCEL,
                                     GIMP_STOCK_RESIZE, GTK_RESPONSE_OK,

                                     NULL);

  gtk_window_set_resizable (GTK_WINDOW (dialog), FALSE);

  gtk_dialog_set_alternative_button_order (GTK_DIALOG (dialog),
                                           RESPONSE_RESET,
                                           GTK_RESPONSE_OK,
                                           GTK_RESPONSE_CANCEL,
                                           -1);

  private = g_slice_new0 (ResizeDialog);
static gboolean
gimp_container_tree_view_drop_status (GimpContainerTreeView    *tree_view,
                                      GdkDragContext           *context,
                                      gint                      x,
                                      gint                      y,
                                      guint                     time,
                                      GtkTreePath             **return_path,
                                      GdkAtom                  *return_atom,
                                      GimpDndType              *return_src_type,
                                      GimpViewable            **return_src,
                                      GimpViewable            **return_dest,
                                      GtkTreeViewDropPosition  *return_pos)
{
  GimpViewable            *src_viewable  = NULL;
  GimpViewable            *dest_viewable = NULL;
  GtkTreePath             *drop_path     = NULL;
  GtkTargetList           *target_list;
  GdkAtom                  target_atom;
  GimpDndType              src_type;
  GtkTreeViewDropPosition  drop_pos      = GTK_TREE_VIEW_DROP_BEFORE;
  GdkDragAction            drag_action   = 0;

  if (! gimp_container_view_get_container (GIMP_CONTAINER_VIEW (tree_view)) ||
      ! gimp_container_view_get_reorderable (GIMP_CONTAINER_VIEW (tree_view)))
    goto drop_impossible;

  target_list = gtk_drag_dest_get_target_list (GTK_WIDGET (tree_view->view));
  target_atom = gtk_drag_dest_find_target (GTK_WIDGET (tree_view->view),
                                           context, target_list);
  if (! gtk_target_list_find (target_list, target_atom, &src_type))
    goto drop_impossible;

  switch (src_type)
    {
    case GIMP_DND_TYPE_URI_LIST:
    case GIMP_DND_TYPE_TEXT_PLAIN:
    case GIMP_DND_TYPE_NETSCAPE_URL:
    case GIMP_DND_TYPE_COLOR:
    case GIMP_DND_TYPE_SVG:
    case GIMP_DND_TYPE_SVG_XML:
    case GIMP_DND_TYPE_COMPONENT:
    case GIMP_DND_TYPE_PIXBUF:
      break;

    default:
      {
        GtkWidget *src_widget = gtk_drag_get_source_widget (context);

        if (! src_widget)
          goto drop_impossible;

        src_viewable = gimp_dnd_get_drag_data (src_widget);

        if (! GIMP_IS_VIEWABLE (src_viewable))
          goto drop_impossible;
      }
      break;
    }

  if (gtk_tree_view_get_path_at_pos (tree_view->view, x, y,
                                     &drop_path, NULL, NULL, NULL))
    {
      GimpViewRenderer *renderer;
      GtkTreeIter       iter;
      GdkRectangle      cell_area;

      gtk_tree_model_get_iter (tree_view->model, &iter, drop_path);

      gtk_tree_model_get (tree_view->model, &iter,
                          GIMP_CONTAINER_TREE_STORE_COLUMN_RENDERER, &renderer,
                          -1);

      dest_viewable = renderer->viewable;

      g_object_unref (renderer);

      gtk_tree_view_get_cell_area (tree_view->view, drop_path, NULL, &cell_area);

      if (gimp_viewable_get_children (dest_viewable))
        {
          if (gtk_tree_view_row_expanded (tree_view->view, drop_path))
            {
              if (y >= (cell_area.y + cell_area.height / 2))
                drop_pos = GTK_TREE_VIEW_DROP_INTO_OR_AFTER;
              else
                drop_pos = GTK_TREE_VIEW_DROP_BEFORE;
            }
          else
            {
              if (y >= (cell_area.y + 2 * (cell_area.height / 3)))
                drop_pos = GTK_TREE_VIEW_DROP_AFTER;
              else if (y <= (cell_area.y + cell_area.height / 3))
                drop_pos = GTK_TREE_VIEW_DROP_BEFORE;
              else
                drop_pos = GTK_TREE_VIEW_DROP_INTO_OR_AFTER;
            }
        }
      else
        {
          if (y >= (cell_area.y + cell_area.height / 2))
            drop_pos = GTK_TREE_VIEW_DROP_AFTER;
          else
            drop_pos = GTK_TREE_VIEW_DROP_BEFORE;
        }
    }
  else
    {
      GtkTreeIter iter;
      gint        n_children;

      n_children = gtk_tree_model_iter_n_children (tree_view->model, NULL);

      if (n_children > 0 &&
          gtk_tree_model_iter_nth_child (tree_view->model, &iter,
                                         NULL, n_children - 1))
        {
          GimpViewRenderer *renderer;

          gtk_tree_model_get (tree_view->model, &iter,
                              GIMP_CONTAINER_TREE_STORE_COLUMN_RENDERER,
                              &renderer,
                              -1);

          drop_path     = gtk_tree_model_get_path (tree_view->model, &iter);
          dest_viewable = renderer->viewable;
          drop_pos      = GTK_TREE_VIEW_DROP_AFTER;

          g_object_unref (renderer);
        }
    }

  if (dest_viewable || tree_view->priv->dnd_drop_to_empty)
    {
      if (GIMP_CONTAINER_TREE_VIEW_GET_CLASS (tree_view)->drop_possible (tree_view,
                                                                         src_type,
                                                                         src_viewable,
                                                                         dest_viewable,
                                                                         drop_path,
                                                                         drop_pos,
                                                                         &drop_pos,
                                                                         &drag_action))
        {
          gdk_drag_status (context, drag_action, time);

          if (return_path)
            *return_path = drop_path;
          else
            gtk_tree_path_free (drop_path);

          if (return_atom)
            *return_atom = target_atom;

          if (return_src)
            *return_src = src_viewable;

          if (return_dest)
            *return_dest = dest_viewable;

          if (return_pos)
            *return_pos = drop_pos;

          return TRUE;
        }

      gtk_tree_path_free (drop_path);
    }

 drop_impossible:

  gdk_drag_status (context, 0, time);

  return FALSE;
}
Example #9
0
void
gimp_viewable_dialog_set_viewable (GimpViewableDialog *dialog,
                                   GimpViewable       *viewable,
                                   GimpContext        *context)
{
  g_return_if_fail (GIMP_IS_VIEWABLE_DIALOG (dialog));
  g_return_if_fail (viewable == NULL || GIMP_IS_VIEWABLE (viewable));
  g_return_if_fail (context == NULL || GIMP_IS_CONTEXT (context));

  dialog->context = context;

  if (dialog->view)
    {
      GimpViewable *old_viewable = GIMP_VIEW (dialog->view)->viewable;

      if (viewable == old_viewable)
        {
          gimp_view_renderer_set_context (GIMP_VIEW (dialog->view)->renderer,
                                          context);
          return;
        }

      gtk_widget_destroy (dialog->view);

      if (old_viewable)
        {
          g_signal_handlers_disconnect_by_func (old_viewable,
                                                gimp_viewable_dialog_name_changed,
                                                dialog);

          g_signal_handlers_disconnect_by_func (old_viewable,
                                                gimp_viewable_dialog_close,
                                                dialog);
        }
    }

  if (viewable)
    {
      GtkWidget *box;

      g_signal_connect_object (viewable,
                               GIMP_VIEWABLE_GET_CLASS (viewable)->name_changed_signal,
                               G_CALLBACK (gimp_viewable_dialog_name_changed),
                               dialog,
                               0);

      box = gtk_widget_get_parent (dialog->icon);

      dialog->view = gimp_view_new (context, viewable, 32, 1, TRUE);
      gtk_box_pack_end (GTK_BOX (box), dialog->view, FALSE, FALSE, 2);
      gtk_widget_show (dialog->view);

      g_object_add_weak_pointer (G_OBJECT (dialog->view),
                                 (gpointer) &dialog->view);

      gimp_viewable_dialog_name_changed (GIMP_OBJECT (viewable), dialog);

      if (GIMP_IS_ITEM (viewable))
        {
          g_signal_connect_object (viewable, "removed",
                                   G_CALLBACK (gimp_viewable_dialog_close),
                                   dialog,
                                   G_CONNECT_SWAPPED);
        }
      else
        {
          g_signal_connect_object (viewable, "disconnect",
                                   G_CALLBACK (gimp_viewable_dialog_close),
                                   dialog,
                                   G_CONNECT_SWAPPED);
        }
    }
}
Example #10
0
void
gimp_edit_get_paste_offset (GimpImage    *image,
                            GimpDrawable *drawable,
                            GimpObject   *paste,
                            gint          viewport_x,
                            gint          viewport_y,
                            gint          viewport_width,
                            gint          viewport_height,
                            gint         *offset_x,
                            gint         *offset_y)
{
  gint     image_width;
  gint     image_height;
  gint     width;
  gint     height;
  gboolean clamp_to_image = TRUE;

  g_return_if_fail (GIMP_IS_IMAGE (image));
  g_return_if_fail (drawable == NULL || GIMP_IS_DRAWABLE (drawable));
  g_return_if_fail (drawable == NULL ||
                    gimp_item_is_attached (GIMP_ITEM (drawable)));
  g_return_if_fail (GIMP_IS_VIEWABLE (paste));
  g_return_if_fail (offset_x != NULL);
  g_return_if_fail (offset_y != NULL);

  image_width  = gimp_image_get_width  (image);
  image_height = gimp_image_get_height (image);

  gimp_viewable_get_size (GIMP_VIEWABLE (paste), &width, &height);

  if (viewport_width  == image_width &&
      viewport_height == image_height)
    {
      /* if the whole image is visible, act as if there was no viewport */

      viewport_x      = 0;
      viewport_y      = 0;
      viewport_width  = 0;
      viewport_height = 0;
    }

  if (drawable)
    {
      /*  if pasting to a drawable  */

      GimpContainer *children;
      gint           off_x, off_y;
      gint           target_x, target_y;
      gint           target_width, target_height;
      gint           paste_x, paste_y;
      gint           paste_width, paste_height;
      gboolean       have_mask;

      have_mask = ! gimp_channel_is_empty (gimp_image_get_mask (image));

      gimp_item_get_offset (GIMP_ITEM (drawable), &off_x, &off_y);

      children = gimp_viewable_get_children (GIMP_VIEWABLE (drawable));

      if (children && gimp_container_get_n_children (children) == 0)
        {
          /* treat empty layer groups as image-sized, use the selection
           * as target
           */
          gimp_item_bounds (GIMP_ITEM (gimp_image_get_mask (image)),
                            &target_x, &target_y,
                            &target_width, &target_height);
        }
      else
        {
          gimp_item_mask_intersect (GIMP_ITEM (drawable),
                                    &target_x, &target_y,
                                    &target_width, &target_height);
        }

      if (! have_mask         &&    /* if we have no mask */
          viewport_width  > 0 &&    /* and we have a viewport */
          viewport_height > 0 &&
          (width  < target_width || /* and the paste is smaller than the target */
           height < target_height) &&

          /* and the viewport intersects with the target */
          gimp_rectangle_intersect (viewport_x, viewport_y,
                                    viewport_width, viewport_height,
                                    off_x, off_y, /* target_x,y are 0 */
                                    target_width, target_height,
                                    &paste_x, &paste_y,
                                    &paste_width, &paste_height))
        {
          /*  center on the viewport  */

          *offset_x = paste_x + (paste_width - width)  / 2;
          *offset_y = paste_y + (paste_height- height) / 2;
        }
      else
        {
          /*  otherwise center on the target  */

          *offset_x = off_x + target_x + (target_width  - width)  / 2;
          *offset_y = off_y + target_y + (target_height - height) / 2;

          /*  and keep it that way  */
          clamp_to_image = FALSE;
        }
    }
  else if (viewport_width  > 0 &&  /* if we have a viewport */
           viewport_height > 0 &&
           (width  < image_width || /* and the paste is       */
            height < image_height)) /* smaller than the image */
    {
      /*  center on the viewport  */

      *offset_x = viewport_x + (viewport_width  - width)  / 2;
      *offset_y = viewport_y + (viewport_height - height) / 2;
    }
  else
    {
      /*  otherwise center on the image  */

      *offset_x = (image_width  - width)  / 2;
      *offset_y = (image_height - height) / 2;

      /*  and keep it that way  */
      clamp_to_image = FALSE;
    }

  if (clamp_to_image)
    {
      /*  Ensure that the pasted layer is always within the image, if it
       *  fits and aligned at top left if it doesn't. (See bug #142944).
       */
      *offset_x = MIN (*offset_x, image_width  - width);
      *offset_y = MIN (*offset_y, image_height - height);
      *offset_x = MAX (*offset_x, 0);
      *offset_y = MAX (*offset_y, 0);
    }
}
Example #11
0
void
gimp_view_renderer_set_viewable (GimpViewRenderer *renderer,
                                 GimpViewable     *viewable)
{
  g_return_if_fail (GIMP_IS_VIEW_RENDERER (renderer));
  g_return_if_fail (viewable == NULL || GIMP_IS_VIEWABLE (viewable));

  if (viewable)
    g_return_if_fail (g_type_is_a (G_TYPE_FROM_INSTANCE (viewable),
                                   renderer->viewable_type));

  if (viewable == renderer->viewable)
    return;

  if (renderer->surface)
    {
      cairo_surface_destroy (renderer->surface);
      renderer->surface = NULL;
    }

  if (renderer->pixbuf)
    {
      g_object_unref (renderer->pixbuf);
      renderer->pixbuf = NULL;
    }

  gimp_view_renderer_transform_free (renderer);

  if (renderer->viewable)
    {
      g_object_weak_unref (G_OBJECT (renderer->viewable),
                           (GWeakNotify) gimp_view_renderer_weak_notify,
                           renderer);

      g_signal_handlers_disconnect_by_func (renderer->viewable,
                                            G_CALLBACK (gimp_view_renderer_invalidate),
                                            renderer);

      g_signal_handlers_disconnect_by_func (renderer->viewable,
                                            G_CALLBACK (gimp_view_renderer_size_changed),
                                            renderer);

      if (GIMP_IS_COLOR_MANAGED (renderer->viewable))
        g_signal_handlers_disconnect_by_func (renderer->viewable,
                                              G_CALLBACK (gimp_view_renderer_profile_changed),
                                              renderer);
    }

  renderer->viewable = viewable;

  if (renderer->viewable)
    {
      g_object_weak_ref (G_OBJECT (renderer->viewable),
                         (GWeakNotify) gimp_view_renderer_weak_notify,
                         renderer);

      g_signal_connect_swapped (renderer->viewable,
                                "invalidate-preview",
                                G_CALLBACK (gimp_view_renderer_invalidate),
                                renderer);

      g_signal_connect_swapped (renderer->viewable,
                                "size-changed",
                                G_CALLBACK (gimp_view_renderer_size_changed),
                                renderer);

      if (GIMP_IS_COLOR_MANAGED (renderer->viewable))
        g_signal_connect_swapped (renderer->viewable,
                                  "profile-changed",
                                  G_CALLBACK (gimp_view_renderer_profile_changed),
                                  renderer);

      if (renderer->size != -1)
        gimp_view_renderer_set_size (renderer, renderer->size,
                                     renderer->border_width);

      gimp_view_renderer_invalidate (renderer);
    }
  else
    {
      gimp_view_renderer_update_idle (renderer);
    }
}
Example #12
0
GtkWidget *
gimp_color_dialog_new (GimpViewable      *viewable,
                       GimpContext       *context,
                       const gchar       *title,
                       const gchar       *stock_id,
                       const gchar       *desc,
                       GtkWidget         *parent,
                       GimpDialogFactory *dialog_factory,
                       const gchar       *dialog_identifier,
                       const GimpRGB     *color,
                       gboolean           wants_updates,
                       gboolean           show_alpha)
{
  GimpColorDialog *dialog;
  const gchar     *role;

  g_return_val_if_fail (viewable == NULL || GIMP_IS_VIEWABLE (viewable), NULL);
  g_return_val_if_fail (context == NULL || GIMP_IS_CONTEXT (context), NULL);
  g_return_val_if_fail (GTK_IS_WIDGET (parent), NULL);
  g_return_val_if_fail (dialog_factory == NULL ||
                        GIMP_IS_DIALOG_FACTORY (dialog_factory), NULL);
  g_return_val_if_fail (dialog_factory == NULL || dialog_identifier != NULL,
                        NULL);
  g_return_val_if_fail (color != NULL, NULL);

  if (! context)
    g_warning ("gimp_color_dialog_new() called with a NULL context");

  role = dialog_identifier ? dialog_identifier : "gimp-color-selector";

  dialog = g_object_new (GIMP_TYPE_COLOR_DIALOG,
                         "title",       title,
                         "role",        role,
                         "help-func",   gimp_color_dialog_help_func,
                         "help-id",     GIMP_HELP_COLOR_DIALOG,
                         "stock-id",    stock_id,
                         "description", desc,
                         "parent",      parent,
                         NULL);

  if (viewable)
    {
      gimp_viewable_dialog_set_viewable (GIMP_VIEWABLE_DIALOG (dialog),
                                         viewable, context);
    }
  else
    {
      GtkWidget *parent;

      parent = gtk_widget_get_parent (GIMP_VIEWABLE_DIALOG (dialog)->icon);
      parent = gtk_widget_get_parent (parent);

      gtk_widget_hide (parent);
    }

  dialog->wants_updates = wants_updates;

  if (dialog_factory)
    gimp_dialog_factory_add_foreign (dialog_factory, dialog_identifier,
                                     GTK_WIDGET (dialog));

  gimp_color_selection_set_show_alpha (GIMP_COLOR_SELECTION (dialog->selection),
                                       show_alpha);

  if (context)
    {
      g_object_set_data (G_OBJECT (context->gimp->config->color_management),
                         "gimp-context", context);

      gimp_color_selection_set_config (GIMP_COLOR_SELECTION (dialog->selection),
                                       context->gimp->config->color_management);

      g_object_set_data (G_OBJECT (context->gimp->config->color_management),
                         "gimp-context", NULL);
    }

  gimp_color_selection_set_color (GIMP_COLOR_SELECTION (dialog->selection),
                                  color);
  gimp_color_selection_set_old_color (GIMP_COLOR_SELECTION (dialog->selection),
                                      color);

  return GTK_WIDGET (dialog);
}