[gimp] app: add new item class GimpCanvasRectangleGuides and use it



commit 4e6f43a890457415efb856883c29015a4bef310b
Author: Michael Natterer <mitch gimp org>
Date:   Sun May 22 22:09:09 2011 +0200

    app: add new item class GimpCanvasRectangleGuides and use it
    
    Removes a lot of code from the rectangle tool and fixes off-by-one
    drawing problems because in image coordinates, lines can't be aligned
    correctly with rectangles.

 app/display/Makefile.am                 |    2 +
 app/display/gimpcanvasrectangleguides.c |  431 +++++++++++++++++++++++++++++++
 app/display/gimpcanvasrectangleguides.h |   67 +++++
 app/tools/gimpdrawtool.c                |   22 ++
 app/tools/gimpdrawtool.h                |    6 +
 app/tools/gimprectangletool.c           |  154 +----------
 6 files changed, 542 insertions(+), 140 deletions(-)
---
diff --git a/app/display/Makefile.am b/app/display/Makefile.am
index c0b3fc6..de95d21 100644
--- a/app/display/Makefile.am
+++ b/app/display/Makefile.am
@@ -57,6 +57,8 @@ libappdisplay_a_sources = \
 	gimpcanvasproxygroup.h			\
 	gimpcanvasrectangle.c			\
 	gimpcanvasrectangle.h			\
+	gimpcanvasrectangleguides.c		\
+	gimpcanvasrectangleguides.h		\
 	gimpcanvassamplepoint.c			\
 	gimpcanvassamplepoint.h			\
 	gimpcanvastextcursor.c			\
diff --git a/app/display/gimpcanvasrectangleguides.c b/app/display/gimpcanvasrectangleguides.c
new file mode 100644
index 0000000..30dd831
--- /dev/null
+++ b/app/display/gimpcanvasrectangleguides.c
@@ -0,0 +1,431 @@
+/* GIMP - The GNU Image Manipulation Program
+ * Copyright (C) 1995 Spencer Kimball and Peter Mattis
+ *
+ * gimpcanvasrectangleguides.c
+ * Copyright (C) 2011 Michael Natterer <mitch gimp org>
+ *
+ * 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 3 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, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "config.h"
+
+#include <gegl.h>
+#include <gtk/gtk.h>
+
+#include "libgimpbase/gimpbase.h"
+#include "libgimpmath/gimpmath.h"
+
+#include "display-types.h"
+
+#include "gimpcanvasrectangleguides.h"
+#include "gimpdisplayshell.h"
+#include "gimpdisplayshell-transform.h"
+
+
+#define SQRT5 2.236067977
+
+
+enum
+{
+  PROP_0,
+  PROP_X,
+  PROP_Y,
+  PROP_WIDTH,
+  PROP_HEIGHT,
+  PROP_TYPE
+};
+
+
+typedef struct _GimpCanvasRectangleGuidesPrivate GimpCanvasRectangleGuidesPrivate;
+
+struct _GimpCanvasRectangleGuidesPrivate
+{
+  gdouble        x;
+  gdouble        y;
+  gdouble        width;
+  gdouble        height;
+  GimpGuidesType type;
+};
+
+#define GET_PRIVATE(rectangle) \
+        G_TYPE_INSTANCE_GET_PRIVATE (rectangle, \
+                                     GIMP_TYPE_CANVAS_RECTANGLE_GUIDES, \
+                                     GimpCanvasRectangleGuidesPrivate)
+
+
+/*  local function prototypes  */
+
+static void             gimp_canvas_rectangle_guides_set_property (GObject          *object,
+                                                                   guint             property_id,
+                                                                   const GValue     *value,
+                                                                   GParamSpec       *pspec);
+static void             gimp_canvas_rectangle_guides_get_property (GObject          *object,
+                                                                   guint             property_id,
+                                                                   GValue           *value,
+                                                                   GParamSpec       *pspec);
+static void             gimp_canvas_rectangle_guides_draw         (GimpCanvasItem   *item,
+                                                                   GimpDisplayShell *shell,
+                                                                   cairo_t          *cr);
+static cairo_region_t * gimp_canvas_rectangle_guides_get_extents  (GimpCanvasItem   *item,
+                                                                   GimpDisplayShell *shell);
+
+
+G_DEFINE_TYPE (GimpCanvasRectangleGuides, gimp_canvas_rectangle_guides,
+               GIMP_TYPE_CANVAS_ITEM)
+
+#define parent_class gimp_canvas_rectangle_guides_parent_class
+
+
+static void
+gimp_canvas_rectangle_guides_class_init (GimpCanvasRectangleGuidesClass *klass)
+{
+  GObjectClass        *object_class = G_OBJECT_CLASS (klass);
+  GimpCanvasItemClass *item_class   = GIMP_CANVAS_ITEM_CLASS (klass);
+
+  object_class->set_property = gimp_canvas_rectangle_guides_set_property;
+  object_class->get_property = gimp_canvas_rectangle_guides_get_property;
+
+  item_class->draw           = gimp_canvas_rectangle_guides_draw;
+  item_class->get_extents    = gimp_canvas_rectangle_guides_get_extents;
+
+  g_object_class_install_property (object_class, PROP_X,
+                                   g_param_spec_double ("x", NULL, NULL,
+                                                        -GIMP_MAX_IMAGE_SIZE,
+                                                        GIMP_MAX_IMAGE_SIZE, 0,
+                                                        GIMP_PARAM_READWRITE));
+
+  g_object_class_install_property (object_class, PROP_Y,
+                                   g_param_spec_double ("y", NULL, NULL,
+                                                        -GIMP_MAX_IMAGE_SIZE,
+                                                        GIMP_MAX_IMAGE_SIZE, 0,
+                                                        GIMP_PARAM_READWRITE));
+
+  g_object_class_install_property (object_class, PROP_WIDTH,
+                                   g_param_spec_double ("width", NULL, NULL,
+                                                        -GIMP_MAX_IMAGE_SIZE,
+                                                        GIMP_MAX_IMAGE_SIZE, 0,
+                                                        GIMP_PARAM_READWRITE));
+
+  g_object_class_install_property (object_class, PROP_HEIGHT,
+                                   g_param_spec_double ("height", NULL, NULL,
+                                                        -GIMP_MAX_IMAGE_SIZE,
+                                                        GIMP_MAX_IMAGE_SIZE, 0,
+                                                        GIMP_PARAM_READWRITE));
+
+  g_object_class_install_property (object_class, PROP_TYPE,
+                                   g_param_spec_enum ("type", NULL, NULL,
+                                                      GIMP_TYPE_GUIDES_TYPE,
+                                                      GIMP_GUIDES_NONE,
+                                                      GIMP_PARAM_READWRITE));
+
+  g_type_class_add_private (klass, sizeof (GimpCanvasRectangleGuidesPrivate));
+}
+
+static void
+gimp_canvas_rectangle_guides_init (GimpCanvasRectangleGuides *rectangle)
+{
+}
+
+static void
+gimp_canvas_rectangle_guides_set_property (GObject      *object,
+                                           guint         property_id,
+                                           const GValue *value,
+                                           GParamSpec   *pspec)
+{
+  GimpCanvasRectangleGuidesPrivate *private = GET_PRIVATE (object);
+
+  switch (property_id)
+    {
+    case PROP_X:
+      private->x = g_value_get_double (value);
+      break;
+    case PROP_Y:
+      private->y = g_value_get_double (value);
+      break;
+    case PROP_WIDTH:
+      private->width = g_value_get_double (value);
+      break;
+    case PROP_HEIGHT:
+      private->height = g_value_get_double (value);
+      break;
+    case PROP_TYPE:
+      private->type = g_value_get_enum (value);
+      break;
+
+    default:
+      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
+      break;
+    }
+}
+
+static void
+gimp_canvas_rectangle_guides_get_property (GObject    *object,
+                                           guint       property_id,
+                                           GValue     *value,
+                                           GParamSpec *pspec)
+{
+  GimpCanvasRectangleGuidesPrivate *private = GET_PRIVATE (object);
+
+  switch (property_id)
+    {
+    case PROP_X:
+      g_value_set_double (value, private->x);
+      break;
+    case PROP_Y:
+      g_value_set_double (value, private->y);
+      break;
+    case PROP_WIDTH:
+      g_value_set_double (value, private->width);
+      break;
+    case PROP_HEIGHT:
+      g_value_set_double (value, private->height);
+      break;
+    case PROP_TYPE:
+      g_value_set_enum (value, private->type);
+      break;
+
+    default:
+      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
+      break;
+    }
+}
+
+static void
+gimp_canvas_rectangle_guides_transform (GimpCanvasItem   *item,
+                                        GimpDisplayShell *shell,
+                                        gdouble          *x1,
+                                        gdouble          *y1,
+                                        gdouble          *x2,
+                                        gdouble          *y2)
+{
+  GimpCanvasRectangleGuidesPrivate *private = GET_PRIVATE (item);
+
+  gimp_display_shell_transform_xy_f (shell,
+                                     MIN (private->x,
+                                          private->x + private->width),
+                                     MIN (private->y,
+                                          private->y + private->height),
+                                     x1, y1);
+  gimp_display_shell_transform_xy_f (shell,
+                                     MAX (private->x,
+                                          private->x + private->width),
+                                     MAX (private->y,
+                                          private->y + private->height),
+                                     x2, y2);
+
+  *x1 = floor (*x1) + 0.5;
+  *y1 = floor (*y1) + 0.5;
+  *x2 = ceil (*x2) - 0.5;
+  *y2 = ceil (*y2) - 0.5;
+
+  *x2 = MAX (*x1, *x2);
+  *y2 = MAX (*y1, *y2);
+}
+
+static void
+gimp_canvas_rectangle_guides_draw (GimpCanvasItem   *item,
+                                   GimpDisplayShell *shell,
+                                   cairo_t          *cr)
+{
+  GimpCanvasRectangleGuidesPrivate *private = GET_PRIVATE (item);
+  gdouble                           x1, y1;
+  gdouble                           x2, y2;
+  gdouble                           x, y;
+
+  gimp_canvas_rectangle_guides_transform (item, shell, &x1, &y1, &x2, &y2);
+
+  switch (private->type)
+    {
+    case GIMP_GUIDES_NONE:
+      break;
+
+    case GIMP_GUIDES_CENTER_LINES:
+      y = floor ((y1 + y2) / 2) + 0.5;
+      cairo_move_to (cr, x1, y);
+      cairo_line_to (cr, x2, y);
+
+      x = floor ((x1 + x2) / 2) + 0.5;
+      cairo_move_to (cr, x, y1);
+      cairo_line_to (cr, x, y2);
+      break;
+
+    case GIMP_GUIDES_THIRDS:
+      y = floor ((2 * y1 + y2) / 3) + 0.5;
+      cairo_move_to (cr, x1, y);
+      cairo_line_to (cr, x2, y);
+
+      y = floor ((y1 + 2 * y2) / 3) + 0.5;
+      cairo_move_to (cr, x1, y);
+      cairo_line_to (cr, x2, y);
+
+      x = floor ((2 * x1 + x2) / 3) + 0.5;
+      cairo_move_to (cr, x, y1);
+      cairo_line_to (cr, x, y2);
+
+      x = floor ((x1 + 2 * x2) / 3) + 0.5;
+      cairo_move_to (cr, x, y1);
+      cairo_line_to (cr, x, y2);
+      break;
+
+    case GIMP_GUIDES_FIFTHS:
+      y = floor (y1 + (y2 - y1) / 5) + 0.5;
+      cairo_move_to (cr, x1, y);
+      cairo_line_to (cr, x2, y);
+
+      y = floor (y1 + 2 * (y2 - y1) / 5) + 0.5;
+      cairo_move_to (cr, x1, y);
+      cairo_line_to (cr, x2, y);
+
+      y = floor (y1 + 3 * (y2 - y1) / 5) + 0.5;
+      cairo_move_to (cr, x1, y);
+      cairo_line_to (cr, x2, y);
+
+      y = floor (y1 + 4 * (y2 - y1) / 5) + 0.5;
+      cairo_move_to (cr, x1, y);
+      cairo_line_to (cr, x2, y);
+
+      x = floor (x1 + (x2 - x1) / 5) + 0.5;
+      cairo_move_to (cr, x, y1);
+      cairo_line_to (cr, x, y2);
+
+      x = floor (x1 + 2 * (x2 - x1) / 5) + 0.5;
+      cairo_move_to (cr, x, y1);
+      cairo_line_to (cr, x, y2);
+
+      x = floor (x1 + 3 * (x2 - x1) / 5) + 0.5;
+      cairo_move_to (cr, x, y1);
+      cairo_line_to (cr, x, y2);
+
+      x = floor (x1 + 4 * (x2 - x1) / 5) + 0.5;
+      cairo_move_to (cr, x, y1);
+      cairo_line_to (cr, x, y2);
+      break;
+
+    case GIMP_GUIDES_GOLDEN:
+      y = floor ((2 * y1 + (1 + SQRT5) * y2) / (3 + SQRT5)) + 0.5;
+      cairo_move_to (cr, x1, y);
+      cairo_line_to (cr, x2, y);
+
+      y = floor (((1 + SQRT5) * y1 + 2 * y2) / (3 + SQRT5)) + 0.5;
+      cairo_move_to (cr, x1, y);
+      cairo_line_to (cr, x2, y);
+
+      x = floor ((2 * x1 + (1 + SQRT5) * x2) / (3 + SQRT5)) + 0.5;
+      cairo_move_to (cr, x, y1);
+      cairo_line_to (cr, x, y2);
+
+      x = floor (((1 + SQRT5) * x1 + 2 * x2) / (3 + SQRT5)) + 0.5;
+      cairo_move_to (cr, x, y1);
+      cairo_line_to (cr, x, y2);
+      break;
+
+    /* This code implements the method of diagonals discovered by
+     * Edwin Westhoff - see http://www.diagonalmethod.info/
+     */
+    case GIMP_GUIDES_DIAGONALS:
+      {
+        /* the side of the largest square that can be
+         * fitted in whole into the rectangle (x1, y1), (x2, y2)
+         */
+        const gdouble square_side = MIN (x2 - x1, y2 - y1);
+
+        /* diagonal from the top-left edge */
+        cairo_move_to (cr, x1, y1);
+        cairo_line_to (cr, x1 + square_side, y1 + square_side);
+
+        /* diagonal from the top-right edge */
+        cairo_move_to (cr, x2, y1);
+        cairo_line_to (cr, x2 - square_side, y1 + square_side);
+
+        /* diagonal from the bottom-left edge */
+        cairo_move_to (cr, x1, y2);
+        cairo_line_to (cr, x1 + square_side, y2 - square_side);
+
+        /* diagonal from the bottom-right edge */
+        cairo_move_to (cr, x2, y2);
+        cairo_line_to (cr, x2 - square_side, y2 - square_side);
+      }
+      break;
+    }
+
+  _gimp_canvas_item_stroke (item, cr);
+}
+
+static cairo_region_t *
+gimp_canvas_rectangle_guides_get_extents (GimpCanvasItem   *item,
+                                          GimpDisplayShell *shell)
+{
+  GimpCanvasRectangleGuidesPrivate *private = GET_PRIVATE (item);
+
+  if (private->type != GIMP_GUIDES_NONE)
+    {
+      cairo_rectangle_int_t rectangle;
+      gdouble               x, y;
+      gdouble               w, h;
+
+      gimp_canvas_rectangle_guides_transform (item, shell, &x, &y, &w, &h);
+
+      rectangle.x      = floor (x - 1.5);
+      rectangle.y      = floor (y - 1.5);
+      rectangle.width  = ceil (w + 3.0);
+      rectangle.height = ceil (h + 3.0);
+
+      return cairo_region_create_rectangle (&rectangle);
+    }
+
+  return NULL;
+}
+
+GimpCanvasItem *
+gimp_canvas_rectangle_guides_new (GimpDisplayShell *shell,
+                                  gdouble           x,
+                                  gdouble           y,
+                                  gdouble           width,
+                                  gdouble           height,
+                                  GimpGuidesType    type)
+{
+  g_return_val_if_fail (GIMP_IS_DISPLAY_SHELL (shell), NULL);
+
+  return g_object_new (GIMP_TYPE_CANVAS_RECTANGLE_GUIDES,
+                       "shell",  shell,
+                       "x",      x,
+                       "y",      y,
+                       "width",  width,
+                       "height", height,
+                       "type",   type,
+                       NULL);
+}
+
+void
+gimp_canvas_rectangle_guides_set (GimpCanvasItem *rectangle,
+                                  gdouble         x,
+                                  gdouble         y,
+                                  gdouble         width,
+                                  gdouble         height,
+                                  GimpGuidesType  type)
+{
+  g_return_if_fail (GIMP_IS_CANVAS_RECTANGLE_GUIDES (rectangle));
+
+  gimp_canvas_item_begin_change (rectangle);
+
+  g_object_set (rectangle,
+                "x",      x,
+                "y",      y,
+                "width",  width,
+                "height", height,
+                "type",   type,
+                NULL);
+
+  gimp_canvas_item_end_change (rectangle);
+}
diff --git a/app/display/gimpcanvasrectangleguides.h b/app/display/gimpcanvasrectangleguides.h
new file mode 100644
index 0000000..a76a67f
--- /dev/null
+++ b/app/display/gimpcanvasrectangleguides.h
@@ -0,0 +1,67 @@
+/* GIMP - The GNU Image Manipulation Program
+ * Copyright (C) 1995 Spencer Kimball and Peter Mattis
+ *
+ * gimpcanvasrectangleguides.h
+ * Copyright (C) 2011 Michael Natterer <mitch gimp org>
+ *
+ * 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 3 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, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef __GIMP_CANVAS_RECTANGLE_GUIDES_H__
+#define __GIMP_CANVAS_RECTANGLE_GUIDES_H__
+
+
+#include "gimpcanvasitem.h"
+
+
+#define GIMP_TYPE_CANVAS_RECTANGLE_GUIDES            (gimp_canvas_rectangle_guides_get_type ())
+#define GIMP_CANVAS_RECTANGLE_GUIDES(obj)            (G_TYPE_CHECK_INSTANCE_CAST ((obj), GIMP_TYPE_CANVAS_RECTANGLE_GUIDES, GimpCanvasRectangleGuides))
+#define GIMP_CANVAS_RECTANGLE_GUIDES_CLASS(klass)    (G_TYPE_CHECK_CLASS_CAST ((klass), GIMP_TYPE_CANVAS_RECTANGLE_GUIDES, GimpCanvasRectangleGuidesClass))
+#define GIMP_IS_CANVAS_RECTANGLE_GUIDES(obj)         (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GIMP_TYPE_CANVAS_RECTANGLE_GUIDES))
+#define GIMP_IS_CANVAS_RECTANGLE_GUIDES_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GIMP_TYPE_CANVAS_RECTANGLE_GUIDES))
+#define GIMP_CANVAS_RECTANGLE_GUIDES_GET_CLASS(obj)  (G_TYPE_INSTANCE_GET_CLASS ((obj), GIMP_TYPE_CANVAS_RECTANGLE_GUIDES, GimpCanvasRectangleGuidesClass))
+
+
+typedef struct _GimpCanvasRectangleGuides      GimpCanvasRectangleGuides;
+typedef struct _GimpCanvasRectangleGuidesClass GimpCanvasRectangleGuidesClass;
+
+struct _GimpCanvasRectangleGuides
+{
+  GimpCanvasItem  parent_instance;
+};
+
+struct _GimpCanvasRectangleGuidesClass
+{
+  GimpCanvasItemClass  parent_class;
+};
+
+
+GType            gimp_canvas_rectangle_guides_get_type (void) G_GNUC_CONST;
+
+GimpCanvasItem * gimp_canvas_rectangle_guides_new      (GimpDisplayShell *shell,
+                                                        gdouble           x,
+                                                        gdouble           y,
+                                                        gdouble           width,
+                                                        gdouble           height,
+                                                        GimpGuidesType    type);
+
+void             gimp_canvas_rectangle_guides_set      (GimpCanvasItem   *rectangle,
+                                                        gdouble           x,
+                                                        gdouble           y,
+                                                        gdouble           width,
+                                                        gdouble           height,
+                                                        GimpGuidesType    type);
+
+
+#endif /* __GIMP_CANVAS_RECTANGLE_GUIDES_H__ */
diff --git a/app/tools/gimpdrawtool.c b/app/tools/gimpdrawtool.c
index 77a764e..9433023 100644
--- a/app/tools/gimpdrawtool.c
+++ b/app/tools/gimpdrawtool.c
@@ -46,6 +46,7 @@
 #include "display/gimpcanvaspen.h"
 #include "display/gimpcanvaspolygon.h"
 #include "display/gimpcanvasrectangle.h"
+#include "display/gimpcanvasrectangleguides.h"
 #include "display/gimpcanvassamplepoint.h"
 #include "display/gimpcanvastextcursor.h"
 #include "display/gimpcanvastransformpreview.h"
@@ -602,6 +603,27 @@ gimp_draw_tool_add_rectangle (GimpDrawTool *draw_tool,
 }
 
 GimpCanvasItem *
+gimp_draw_tool_add_rectangle_guides (GimpDrawTool   *draw_tool,
+                                     GimpGuidesType  type,
+                                     gdouble         x,
+                                     gdouble         y,
+                                     gdouble         width,
+                                     gdouble         height)
+{
+  GimpCanvasItem *item;
+
+  g_return_val_if_fail (GIMP_IS_DRAW_TOOL (draw_tool), NULL);
+
+  item = gimp_canvas_rectangle_guides_new (gimp_display_get_shell (draw_tool->display),
+                                           x, y, width, height, type);
+
+  gimp_draw_tool_add_item (draw_tool, item);
+  g_object_unref (item);
+
+  return item;
+}
+
+GimpCanvasItem *
 gimp_draw_tool_add_arc (GimpDrawTool *draw_tool,
                         gboolean      filled,
                         gdouble       x,
diff --git a/app/tools/gimpdrawtool.h b/app/tools/gimpdrawtool.h
index 84765a3..3c13568 100644
--- a/app/tools/gimpdrawtool.h
+++ b/app/tools/gimpdrawtool.h
@@ -121,6 +121,12 @@ GimpCanvasItem * gimp_draw_tool_add_rectangle        (GimpDrawTool     *draw_too
                                                       gdouble           y,
                                                       gdouble           width,
                                                       gdouble           height);
+GimpCanvasItem * gimp_draw_tool_add_rectangle_guides (GimpDrawTool     *draw_tool,
+                                                      GimpGuidesType    type,
+                                                      gdouble           x,
+                                                      gdouble           y,
+                                                      gdouble           width,
+                                                      gdouble           height);
 GimpCanvasItem * gimp_draw_tool_add_arc              (GimpDrawTool     *draw_tool,
                                                       gboolean          filled,
                                                       gdouble           x,
diff --git a/app/tools/gimprectangletool.c b/app/tools/gimprectangletool.c
index 14fb12b..c9d1ebb 100644
--- a/app/tools/gimprectangletool.c
+++ b/app/tools/gimprectangletool.c
@@ -69,7 +69,6 @@ enum
 #define MIN_HANDLE_SIZE         15
 #define NARROW_MODE_HANDLE_SIZE 15
 #define NARROW_MODE_THRESHOLD   45
-#define SQRT5                    2.236067977
 
 typedef enum
 {
@@ -210,7 +209,6 @@ static GimpRectangleToolPrivate *
 static void          gimp_rectangle_tool_start                (GimpRectangleTool        *rect_tool,
                                                                GimpDisplay              *display);
 static void          gimp_rectangle_tool_halt                 (GimpRectangleTool        *rect_tool);
-static void          gimp_rectangle_tool_draw_guides          (GimpDrawTool             *draw_tool);
 
 static void          gimp_rectangle_tool_update_options       (GimpRectangleTool        *rect_tool,
                                                                GimpDisplay              *display);
@@ -1708,15 +1706,19 @@ void
 gimp_rectangle_tool_draw (GimpDrawTool    *draw_tool,
                           GimpCanvasGroup *stroke_group)
 {
-  GimpTool                 *tool;
-  GimpRectangleToolPrivate *private;
-  gdouble                   x1, y1, x2, y2;
+  GimpTool                    *tool;
+  GimpRectangleToolPrivate    *private;
+  GimpRectangleOptions        *options;
+  GimpRectangleOptionsPrivate *options_private;
+  gdouble                      x1, y1, x2, y2;
 
   g_return_if_fail (GIMP_IS_RECTANGLE_TOOL (draw_tool));
   g_return_if_fail (stroke_group == NULL || GIMP_IS_CANVAS_GROUP (stroke_group));
 
-  tool    = GIMP_TOOL (draw_tool);
-  private = GIMP_RECTANGLE_TOOL_GET_PRIVATE (tool);
+  tool            = GIMP_TOOL (draw_tool);
+  private         = GIMP_RECTANGLE_TOOL_GET_PRIVATE (tool);
+  options         = GIMP_RECTANGLE_TOOL_GET_OPTIONS (tool);
+  options_private = GIMP_RECTANGLE_OPTIONS_GET_PRIVATE (options);
 
   gimp_rectangle_tool_get_public_rect (GIMP_RECTANGLE_TOOL (draw_tool),
                                        &x1, &y1, &x2, &y2);
@@ -1729,7 +1731,11 @@ gimp_rectangle_tool_draw (GimpDrawTool    *draw_tool,
 
   gimp_draw_tool_push_group (draw_tool, stroke_group);
 
-  gimp_rectangle_tool_draw_guides (draw_tool);
+  gimp_draw_tool_add_rectangle_guides (draw_tool,
+                                       options_private->guide,
+                                       x1, y1,
+                                       x2 - x1,
+                                       y2 - y1);
 
   gimp_draw_tool_add_rectangle (draw_tool, FALSE,
                                 x1, y1,
@@ -1847,138 +1853,6 @@ gimp_rectangle_tool_draw (GimpDrawTool    *draw_tool,
 }
 
 static void
-gimp_rectangle_tool_draw_guides (GimpDrawTool *draw_tool)
-{
-  GimpTool                    *tool = GIMP_TOOL (draw_tool);
-  GimpRectangleOptions        *options;
-  GimpRectangleOptionsPrivate *options_private;
-  gdouble                      x1, y1;
-  gdouble                      x2, y2;
-
-  options         = GIMP_RECTANGLE_TOOL_GET_OPTIONS (tool);
-  options_private = GIMP_RECTANGLE_OPTIONS_GET_PRIVATE (options);
-
-  gimp_rectangle_tool_get_public_rect (GIMP_RECTANGLE_TOOL (draw_tool),
-                                       &x1, &y1, &x2, &y2);
-
-  switch (options_private->guide)
-    {
-    case GIMP_GUIDES_NONE:
-      break;
-
-    case GIMP_GUIDES_CENTER_LINES:
-      gimp_draw_tool_add_line (draw_tool,
-                               x1, (y1 + y2) / 2,
-                               x2, (y1 + y2) / 2);
-
-      gimp_draw_tool_add_line (draw_tool,
-                               (x1 + x2) / 2, y1,
-                               (x1 + x2) / 2, y2);
-      break;
-
-    case GIMP_GUIDES_THIRDS:
-      gimp_draw_tool_add_line (draw_tool,
-                               x1, (2 * y1 + y2) / 3,
-                               x2, (2 * y1 + y2) / 3);
-      gimp_draw_tool_add_line (draw_tool,
-                               x1, (y1 + 2 * y2) / 3,
-                               x2, (y1 + 2 * y2) / 3);
-
-      gimp_draw_tool_add_line (draw_tool,
-                               (2 * x1 + x2) / 3, y1,
-                               (2 * x1 + x2) / 3, y2);
-      gimp_draw_tool_add_line (draw_tool,
-                               (x1 + 2 * x2) / 3, y1,
-                               (x1 + 2 * x2) / 3, y2);
-      break;
-
-    case GIMP_GUIDES_FIFTHS:
-      gimp_draw_tool_add_line (draw_tool,
-                               x1, y1 + (y2 - y1) / 5,
-                               x2, y1 + (y2 - y1) / 5);
-      gimp_draw_tool_add_line (draw_tool,
-                               x1, y1 + 2 * (y2 - y1) / 5,
-                               x2, y1 + 2 * (y2 - y1) / 5);
-      gimp_draw_tool_add_line (draw_tool,
-                               x1, y1 + 3 * (y2 - y1) / 5,
-                               x2, y1 + 3 * (y2 - y1) / 5);
-      gimp_draw_tool_add_line (draw_tool,
-                               x1, y1 + 4 * (y2 - y1) / 5,
-                               x2, y1 + 4 * (y2 - y1) / 5);
-
-      gimp_draw_tool_add_line (draw_tool,
-                               x1 + (x2 - x1) / 5, y1,
-                               x1 + (x2 - x1) / 5, y2);
-      gimp_draw_tool_add_line (draw_tool,
-                               x1 + 2 * (x2 - x1) / 5, y1,
-                               x1 + 2 * (x2 - x1) / 5, y2);
-      gimp_draw_tool_add_line (draw_tool,
-                               x1 + 3 * (x2 - x1) / 5, y1,
-                               x1 + 3 * (x2 - x1) / 5, y2);
-      gimp_draw_tool_add_line (draw_tool,
-                               x1 + 4 * (x2 - x1) / 5, y1,
-                               x1 + 4 * (x2 - x1) / 5, y2);
-      break;
-
-    case GIMP_GUIDES_GOLDEN:
-      gimp_draw_tool_add_line (draw_tool,
-                               x1,
-                               (2 * y1 + (1 + SQRT5) * y2) / (3 + SQRT5),
-                               x2,
-                               (2 * y1 + (1 + SQRT5) * y2) / (3 + SQRT5));
-      gimp_draw_tool_add_line (draw_tool,
-                               x1,
-                               ((1 + SQRT5) * y1 + 2 * y2) / (3 + SQRT5),
-                               x2,
-                               ((1 + SQRT5) * y1 + 2 * y2) / (3 + SQRT5));
-
-      gimp_draw_tool_add_line (draw_tool,
-                               (2 * x1 + (1 + SQRT5) * x2) / (3 + SQRT5),
-                               y1,
-                               (2 * x1 + (1 + SQRT5) * x2) / (3 + SQRT5),
-                               y2);
-      gimp_draw_tool_add_line (draw_tool,
-                               ((1 + SQRT5) * x1 + 2 * x2) / (3 + SQRT5),
-                               y1,
-                               ((1 + SQRT5) * x1 + 2 * x2) / (3 + SQRT5),
-                               y2);
-      break;
-
-    /* This code implements the method of diagonals discovered by
-     * Edwin Westhoff - see http://www.diagonalmethod.info/
-     */
-    case GIMP_GUIDES_DIAGONALS:
-      {
-        /* the side of the largest square that can be
-         * fitted in whole into the rectangle (x1, y1), (x2, y2)
-         */
-        const gdouble square_side = MIN (x2 - x1, y2 - y1);
-
-        /* diagonal from the top-left edge */
-        gimp_draw_tool_add_line (draw_tool,
-                                 x1, y1,
-                                 x1 + square_side, y1 + square_side);
-
-        /* diagonal from the top-right edge */
-        gimp_draw_tool_add_line (draw_tool,
-                                 x2, y1,
-                                 x2 - square_side, y1 + square_side);
-
-        /* diagonal from the bottom-left edge */
-        gimp_draw_tool_add_line (draw_tool,
-                                 x1, y2,
-                                 x1 + square_side, y2 - square_side);
-
-        /* diagonal from the bottom-right edge */
-        gimp_draw_tool_add_line (draw_tool,
-                                 x2, y2,
-                                 x2 - square_side, y2 - square_side);
-      }
-      break;
-    }
-}
-
-static void
 gimp_rectangle_tool_update_handle_sizes (GimpRectangleTool *rect_tool)
 {
   GimpTool                 *tool;



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