예제 #1
0
static gboolean
gimp_undo_create_preview_idle (gpointer data)
{
  GimpUndoIdle *idle = data;

  if (idle->undo == gimp_undo_stack_peek (idle->undo->image->undo_stack))
    {
      gimp_undo_create_preview_private (idle->undo, idle->context);
    }

  idle->undo->preview_idle_id = 0;

  return FALSE;
}
static void
gimp_rectangle_select_tool_cancel (GimpRectangleTool *rectangle)
{
  GimpTool                       *tool;
  GimpRectangleSelectTool        *rect_sel_tool;
  GimpRectangleSelectToolPrivate *priv;

  tool          = GIMP_TOOL (rectangle);
  rect_sel_tool = GIMP_RECTANGLE_SELECT_TOOL (rectangle);
  priv          = GIMP_RECTANGLE_SELECT_TOOL_GET_PRIVATE (rect_sel_tool);

  if (tool->display)
    {
      GimpImage     *image      = gimp_display_get_image (tool->display);
      GimpUndoStack *undo_stack = gimp_image_get_undo_stack (image);
      GimpUndo      *undo       = gimp_undo_stack_peek (undo_stack);

      /* if we have an existing rectangle in the current display, then
       * we have already "executed", and need to undo at this point,
       * unless the user has done something in the meantime
       */
      if (undo && priv->undo == undo)
        {
          /* prevent this change from halting the tool */
          gimp_tool_control_push_preserve (tool->control, TRUE);

          gimp_image_undo (image);
          gimp_image_flush (image);

          gimp_tool_control_pop_preserve (tool->control);
        }
    }

  gimp_rectangle_select_tool_update_option_defaults (rect_sel_tool, TRUE);

  priv->undo = NULL;
  priv->redo = NULL;
}
static gboolean
gimp_rectangle_select_tool_rectangle_change_complete (GimpRectangleTool *rectangle)
{
  GimpTool                       *tool;
  GimpRectangleSelectTool        *rect_sel_tool;
  GimpRectangleSelectToolPrivate *priv;

  tool          = GIMP_TOOL (rectangle);
  rect_sel_tool = GIMP_RECTANGLE_SELECT_TOOL (tool);
  priv          = GIMP_RECTANGLE_SELECT_TOOL_GET_PRIVATE (rect_sel_tool);

  /* prevent change in selection from halting the tool */
  gimp_tool_control_push_preserve (tool->control, TRUE);

  if (tool->display && ! gimp_tool_control_is_active (tool->control))
    {
      GimpImage     *image      = gimp_display_get_image (tool->display);
      GimpUndoStack *undo_stack = gimp_image_get_undo_stack (image);
      GimpUndo      *undo       = gimp_undo_stack_peek (undo_stack);
      gint           x1, y1, x2, y2;

      /* if we got here via button release, we have already undone the
       * previous operation.  But if we got here by some other means,
       * we need to undo it now.
       */
      if (undo && priv->undo == undo)
        {
          gimp_image_undo (image);
          priv->undo = NULL;
        }

      g_object_get (rectangle,
                    "x1", &x1,
                    "y1", &y1,
                    "x2", &x2,
                    "y2", &y2,
                    NULL);

      if (gimp_rectangle_select_tool_select (rectangle, x1, y1, x2 - x1, y2 - y1))
        {
          /* save the undo that we got when executing, but only if
           * we actually selected something
           */
          priv->undo = gimp_undo_stack_peek (undo_stack);
          priv->redo = NULL;
        }

      if (! priv->use_saved_op)
        {
          GimpSelectionOptions *options;

          options = GIMP_SELECTION_TOOL_GET_OPTIONS (tool);

          /* remember the operation now in case we modify the rectangle */
          priv->operation    = options->operation;
          priv->use_saved_op = TRUE;
        }

      gimp_image_flush (image);
    }

  gimp_tool_control_pop_preserve (tool->control);

  gimp_rectangle_select_tool_update_option_defaults (rect_sel_tool, FALSE);

  return TRUE;
}
static void
gimp_rectangle_select_tool_button_release (GimpTool              *tool,
                                           const GimpCoords      *coords,
                                           guint32                time,
                                           GdkModifierType        state,
                                           GimpButtonReleaseType  release_type,
                                           GimpDisplay           *display)
{
  GimpRectangleSelectTool        *rect_sel_tool;
  GimpRectangleSelectToolPrivate *priv;
  GimpImage                      *image;

  rect_sel_tool = GIMP_RECTANGLE_SELECT_TOOL (tool);
  priv          = GIMP_RECTANGLE_SELECT_TOOL_GET_PRIVATE (rect_sel_tool);

  image = gimp_display_get_image (tool->display);

  gimp_tool_control_halt (tool->control);

  gimp_tool_pop_status (tool, display);
  gimp_display_shell_set_show_selection (gimp_display_get_shell (display),
                                         priv->saved_show_selection);

  /*
   * if the user has not moved the mouse, we need to redo the operation
   * that was undone on button press.
   */
  if (release_type == GIMP_BUTTON_RELEASE_CLICK)
    {
      GimpUndoStack *redo_stack = gimp_image_get_redo_stack (image);
      GimpUndo      *redo       = gimp_undo_stack_peek (redo_stack);

      if (redo && priv->redo == redo)
        {
          /* prevent this from halting the tool */
          gimp_tool_control_push_preserve (tool->control, TRUE);

          gimp_image_redo (image);
          priv->redo = NULL;

          gimp_tool_control_pop_preserve (tool->control);
        }
    }

  gimp_rectangle_tool_button_release (tool, coords, time, state, release_type,
                                      display);

  if (release_type == GIMP_BUTTON_RELEASE_CANCEL)
    {
      if (priv->redo)
        {
          /* prevent this from halting the tool */
          gimp_tool_control_push_preserve (tool->control, TRUE);

          gimp_image_redo (image);

          gimp_tool_control_pop_preserve (tool->control);
        }

      priv->use_saved_op = TRUE;  /* is this correct? */
    }

  priv->redo = NULL;
}
static void
gimp_rectangle_select_tool_button_press (GimpTool            *tool,
                                         const GimpCoords    *coords,
                                         guint32              time,
                                         GdkModifierType      state,
                                         GimpButtonPressType  press_type,
                                         GimpDisplay         *display)
{
  GimpRectangleTool              *rectangle;
  GimpRectangleSelectTool        *rect_sel_tool;
  GimpDisplayShell               *shell;
  GimpRectangleSelectToolPrivate *priv;
  GimpRectangleFunction           function;

  rectangle     = GIMP_RECTANGLE_TOOL (tool);
  rect_sel_tool = GIMP_RECTANGLE_SELECT_TOOL (tool);
  shell         = gimp_display_get_shell (display);
  priv          = GIMP_RECTANGLE_SELECT_TOOL_GET_PRIVATE (rect_sel_tool);

  if (tool->display && display != tool->display)
    {
      gimp_rectangle_tool_cancel (GIMP_RECTANGLE_TOOL (tool));
    }

  if (gimp_selection_tool_start_edit (GIMP_SELECTION_TOOL (tool),
                                      display, coords))
    {
      /* In some cases we want to finish the rectangle select tool
       * and hand over responsability to the selection tool
       */
      gimp_rectangle_tool_execute (rectangle);
      gimp_rectangle_tool_control (tool, GIMP_TOOL_ACTION_HALT, display);
      gimp_rectangle_select_tool_update_option_defaults (rect_sel_tool,
                                                         TRUE);
      return;
    }

  gimp_tool_control_activate (tool->control);

  priv->saved_show_selection = gimp_display_shell_get_show_selection (shell);

  /* if the shift or ctrl keys are down, we don't want to adjust, we
   * want to create a new rectangle, regardless of pointer loc */
  if (state & (gimp_get_extend_selection_mask () |
               gimp_get_modify_selection_mask ()))
    {
      gimp_rectangle_tool_set_function (rectangle,
                                        GIMP_RECTANGLE_TOOL_CREATING);
    }

  gimp_rectangle_tool_button_press (tool, coords, time, state, display);

  priv->press_x = coords->x;
  priv->press_y = coords->y;

  /* if we have an existing rectangle in the current display, then
   * we have already "executed", and need to undo at this point,
   * unless the user has done something in the meantime
   */
  function = gimp_rectangle_tool_get_function (rectangle);

  if (function == GIMP_RECTANGLE_TOOL_CREATING)
    {
      priv->use_saved_op = FALSE;
    }
  else
    {
      GimpImage      *image      = gimp_display_get_image (tool->display);
      GimpUndoStack  *undo_stack = gimp_image_get_undo_stack (image);
      GimpUndoStack  *redo_stack = gimp_image_get_redo_stack (image);
      GimpUndo       *undo;
      GimpChannelOps  operation;

      undo = gimp_undo_stack_peek (undo_stack);

      if (undo && priv->undo == undo)
        {
          /* prevent this change from halting the tool */
          gimp_tool_control_push_preserve (tool->control, TRUE);

          gimp_image_undo (image);

          gimp_tool_control_pop_preserve (tool->control);

          /* we will need to redo if the user cancels or executes */
          priv->redo = gimp_undo_stack_peek (redo_stack);
        }

      /* if the operation is "Replace", turn off the marching ants,
         because they are confusing */
      operation = gimp_rectangle_select_tool_get_operation (rect_sel_tool);

      if (operation == GIMP_CHANNEL_OP_REPLACE)
        gimp_display_shell_set_show_selection (shell, FALSE);
    }

  priv->undo = NULL;
}
예제 #6
0
void
edit_actions_update (GimpActionGroup *group,
                     gpointer         data)
{
  GimpImage    *image        = action_data_get_image (data);
  GimpDisplay  *display      = action_data_get_display (data);
  GimpDrawable *drawable     = NULL;
  gchar        *undo_name    = NULL;
  gchar        *redo_name    = NULL;
  gchar        *fade_name    = NULL;
  gboolean      writable     = FALSE;
  gboolean      children     = FALSE;
  gboolean      undo_enabled = FALSE;
  gboolean      fade_enabled = FALSE;

  if (image)
    {
      drawable = gimp_image_get_active_drawable (image);

      if (drawable)
        {
          writable = ! gimp_item_is_content_locked (GIMP_ITEM (drawable));

          if (gimp_viewable_get_children (GIMP_VIEWABLE (drawable)))
            children = TRUE;
        }

      undo_enabled = gimp_image_undo_is_enabled (image);

      if (undo_enabled)
        {
          GimpUndoStack *undo_stack = gimp_image_get_undo_stack (image);
          GimpUndoStack *redo_stack = gimp_image_get_redo_stack (image);
          GimpUndo      *undo       = gimp_undo_stack_peek (undo_stack);
          GimpUndo      *redo       = gimp_undo_stack_peek (redo_stack);
          const gchar   *tool_undo  = NULL;
          const gchar   *tool_redo  = NULL;

          if (display)
            {
              tool_undo = tool_manager_get_undo_desc_active (image->gimp,
                                                             display);
              tool_redo = tool_manager_get_redo_desc_active (image->gimp,
                                                             display);
            }

          if (tool_undo)
            undo_name = g_strdup_printf (_("_Undo %s"), tool_undo);
          else if (undo)
            undo_name = g_strdup_printf (_("_Undo %s"),
                                         gimp_object_get_name (undo));

          if (tool_redo)
            redo_name = g_strdup_printf (_("_Redo %s"), tool_redo);
          else if (redo)
            redo_name = g_strdup_printf (_("_Redo %s"),
                                         gimp_object_get_name (redo));

          undo = gimp_image_undo_get_fadeable (image);

          if (GIMP_IS_DRAWABLE_UNDO (undo) &&
              GIMP_DRAWABLE_UNDO (undo)->applied_buffer)
            {
              fade_enabled = TRUE;
            }

          if (fade_enabled)
            {
              fade_name =
                g_strdup_printf (_("_Fade %s..."),
                                 gimp_object_get_name (undo));
            }
        }
    }


#define SET_LABEL(action,label) \
        gimp_action_group_set_action_label (group, action, (label))
#define SET_SENSITIVE(action,condition) \
        gimp_action_group_set_action_sensitive (group, action, (condition) != 0)

  SET_LABEL ("edit-undo", undo_name ? undo_name : _("_Undo"));
  SET_LABEL ("edit-redo", redo_name ? redo_name : _("_Redo"));
  SET_LABEL ("edit-fade", fade_name ? fade_name : _("_Fade..."));

  SET_SENSITIVE ("edit-undo",        undo_enabled && undo_name);
  SET_SENSITIVE ("edit-redo",        undo_enabled && redo_name);
  SET_SENSITIVE ("edit-strong-undo", undo_enabled && undo_name);
  SET_SENSITIVE ("edit-strong-redo", undo_enabled && redo_name);
  SET_SENSITIVE ("edit-undo-clear",  undo_enabled && (undo_name || redo_name));
  SET_SENSITIVE ("edit-fade",        fade_enabled && fade_name);

  g_free (undo_name);
  g_free (redo_name);
  g_free (fade_name);

  SET_SENSITIVE ("edit-cut",                writable && !children);
  SET_SENSITIVE ("edit-copy",               drawable);
  SET_SENSITIVE ("edit-copy-visible",       image);
  SET_SENSITIVE ("edit-paste",              !image || (!drawable ||
                                                       (writable && !children)));
  SET_SENSITIVE ("edit-paste-as-new-layer", image);
  SET_SENSITIVE ("edit-paste-into",         image && (!drawable ||
                                                      (writable  && !children)));

  SET_SENSITIVE ("edit-named-cut",          writable && !children);
  SET_SENSITIVE ("edit-named-copy",         drawable);
  SET_SENSITIVE ("edit-named-copy-visible", drawable);
  SET_SENSITIVE ("edit-named-paste",        TRUE);

  SET_SENSITIVE ("edit-clear",              writable && !children);
  SET_SENSITIVE ("edit-fill-fg",            writable && !children);
  SET_SENSITIVE ("edit-fill-bg",            writable && !children);
  SET_SENSITIVE ("edit-fill-pattern",       writable && !children);

#undef SET_LABEL
#undef SET_SENSITIVE
}