[gimp/goat-invasion] app: port GimpDrawableUndo, GimpDrawable::push_undo() and ::swap_tiles()



commit 890c4e1a5795a7c39b297af8f8c1af772a572710
Author: Michael Natterer <mitch gimp org>
Date:   Thu Mar 22 14:13:17 2012 +0100

    app: port GimpDrawableUndo, GimpDrawable::push_undo() and ::swap_tiles()
    
    which gets rid of the manual implementation of sparse undo buffers,
    but GEGL will take care of proper COW here soo enough.

 app/core/gimpchannel.c          |    8 +--
 app/core/gimpdrawable-combine.c |    8 +-
 app/core/gimpdrawable.c         |  122 +++++++++++---------------------------
 app/core/gimpdrawable.h         |   14 ++---
 app/core/gimpdrawableundo.c     |   48 ++++++----------
 app/core/gimpdrawableundo.h     |    3 +-
 app/core/gimpimage-undo-push.c  |   20 +------
 app/core/gimpimage-undo-push.h  |    3 +-
 app/core/gimpimagemap.c         |   13 ++--
 app/core/gimplayer.c            |    8 +-
 app/paint/gimppaintcore.c       |   34 ++++++++++-
 app/text/gimptextlayer.c        |    8 +--
 12 files changed, 115 insertions(+), 174 deletions(-)
---
diff --git a/app/core/gimpchannel.c b/app/core/gimpchannel.c
index afc3240..2a03c2a 100644
--- a/app/core/gimpchannel.c
+++ b/app/core/gimpchannel.c
@@ -164,8 +164,7 @@ static void      gimp_channel_set_buffer     (GimpDrawable        *drawable,
                                               gint                 offset_y);
 static GeglNode * gimp_channel_get_node      (GimpItem            *item);
 static void      gimp_channel_swap_pixels    (GimpDrawable        *drawable,
-                                              TileManager         *tiles,
-                                              gboolean             sparse,
+                                              GeglBuffer          *buffer,
                                               gint                 x,
                                               gint                 y,
                                               gint                 width,
@@ -934,8 +933,7 @@ gimp_channel_get_node (GimpItem *item)
 
 static void
 gimp_channel_swap_pixels (GimpDrawable *drawable,
-                          TileManager  *tiles,
-                          gboolean      sparse,
+                          GeglBuffer   *buffer,
                           gint          x,
                           gint          y,
                           gint          width,
@@ -943,7 +941,7 @@ gimp_channel_swap_pixels (GimpDrawable *drawable,
 {
   gimp_drawable_invalidate_boundary (drawable);
 
-  GIMP_DRAWABLE_CLASS (parent_class)->swap_pixels (drawable, tiles, sparse,
+  GIMP_DRAWABLE_CLASS (parent_class)->swap_pixels (drawable, buffer,
                                                    x, y, width, height);
 
   GIMP_CHANNEL (drawable)->bounds_known = FALSE;
diff --git a/app/core/gimpdrawable-combine.c b/app/core/gimpdrawable-combine.c
index b2e8a8b..1e4f26c 100644
--- a/app/core/gimpdrawable-combine.c
+++ b/app/core/gimpdrawable-combine.c
@@ -101,9 +101,9 @@ gimp_drawable_real_apply_region (GimpDrawable         *drawable,
       GimpDrawableUndo *undo;
 
       gimp_drawable_push_undo (drawable, undo_desc,
+                               NULL,
                                x1, y1,
-                               x2 - x1, y2 - y1,
-                               NULL, FALSE);
+                               x2 - x1, y2 - y1);
 
       undo = GIMP_DRAWABLE_UNDO (gimp_image_undo_get_fadeable (image));
 
@@ -258,9 +258,9 @@ gimp_drawable_real_replace_region (GimpDrawable *drawable,
   /*  If the calling procedure specified an undo step...  */
   if (push_undo)
     gimp_drawable_push_undo (drawable, undo_desc,
+                             NULL,
                              x1, y1,
-                             x2 - x1, y2 - y1,
-                             NULL, FALSE);
+                             x2 - x1, y2 - y1);
 
   /* configure the pixel regions */
   pixel_region_init (&src1PR, gimp_drawable_get_tiles (drawable),
diff --git a/app/core/gimpdrawable.c b/app/core/gimpdrawable.c
index 48c62e7..fa002f6 100644
--- a/app/core/gimpdrawable.c
+++ b/app/core/gimpdrawable.c
@@ -152,15 +152,13 @@ static GeglNode * gimp_drawable_get_node           (GimpItem          *item);
 
 static void       gimp_drawable_real_push_undo     (GimpDrawable      *drawable,
                                                     const gchar       *undo_desc,
-                                                    TileManager       *tiles,
-                                                    gboolean           sparse,
+                                                    GeglBuffer        *buffer,
                                                     gint               x,
                                                     gint               y,
                                                     gint               width,
                                                     gint               height);
 static void       gimp_drawable_real_swap_pixels   (GimpDrawable      *drawable,
-                                                    TileManager       *tiles,
-                                                    gboolean           sparse,
+                                                    GeglBuffer        *buffer,
                                                     gint               x,
                                                     gint               y,
                                                     gint               width,
@@ -864,95 +862,57 @@ gimp_drawable_get_node (GimpItem *item)
 static void
 gimp_drawable_real_push_undo (GimpDrawable *drawable,
                               const gchar  *undo_desc,
-                              TileManager  *tiles,
-                              gboolean      sparse,
+                              GeglBuffer   *buffer,
                               gint          x,
                               gint          y,
                               gint          width,
                               gint          height)
 {
-  gboolean new_tiles = FALSE;
-
-  if (! tiles)
+  if (! buffer)
     {
-      GeglBuffer *dest_buffer;
-
-      tiles = tile_manager_new (width, height, gimp_drawable_bytes (drawable));
-
-      dest_buffer = gimp_tile_manager_create_buffer (tiles,
-                                                     gimp_drawable_get_format (drawable));
+      buffer = gimp_gegl_buffer_new (GIMP_GEGL_RECT (0, 0, width, height),
+                                     gimp_drawable_get_format (drawable));
 
       gegl_buffer_copy (gimp_drawable_get_buffer (drawable),
-                        GIMP_GEGL_RECT (x,y,width,height),
-                        dest_buffer, GIMP_GEGL_RECT (0,0,0,0));
-
-      g_object_unref (dest_buffer);
-
-      new_tiles = TRUE;
+                        GIMP_GEGL_RECT (x, y, width, height),
+                        buffer,
+                        GIMP_GEGL_RECT (0, 0, 0, 0));
+    }
+  else
+    {
+      g_object_ref (buffer);
     }
 
   gimp_image_undo_push_drawable (gimp_item_get_image (GIMP_ITEM (drawable)),
                                  undo_desc, drawable,
-                                 tiles, sparse,
+                                 buffer,
                                  x, y, width, height);
 
-  if (new_tiles)
-    tile_manager_unref (tiles);
+  g_object_unref (buffer);
 }
 
 static void
 gimp_drawable_real_swap_pixels (GimpDrawable *drawable,
-                                TileManager  *tiles,
-                                gboolean      sparse,
+                                GeglBuffer   *buffer,
                                 gint          x,
                                 gint          y,
                                 gint          width,
                                 gint          height)
 {
-  if (sparse)
-    {
-      gint i, j;
-
-      for (i = y; i < (y + height); i += (TILE_HEIGHT - (i % TILE_HEIGHT)))
-        {
-          for (j = x; j < (x + width); j += (TILE_WIDTH - (j % TILE_WIDTH)))
-            {
-              Tile *src_tile;
-              Tile *dest_tile;
-
-              src_tile = tile_manager_get_tile (tiles, j, i, FALSE, FALSE);
-
-              if (tile_is_valid (src_tile))
-                {
-                  /* swap tiles, not pixels! */
-
-                  src_tile = tile_manager_get_tile (tiles,
-                                                    j, i, TRUE, FALSE /*TRUE*/);
-                  dest_tile = tile_manager_get_tile (gimp_drawable_get_tiles (drawable),
-                                                     j, i, TRUE, FALSE /* TRUE */);
+  GeglBuffer *tmp;
 
-                  tile_manager_map_tile (tiles,
-                                         j, i, dest_tile);
-                  tile_manager_map_tile (gimp_drawable_get_tiles (drawable),
-                                         j, i, src_tile);
-
-                  tile_release (dest_tile, FALSE);
-                  tile_release (src_tile, FALSE);
-                }
-            }
-        }
-    }
-  else
-    {
-      PixelRegion PR1, PR2;
+  tmp = gimp_gegl_buffer_dup (buffer);
 
-      pixel_region_init (&PR1, tiles,
-                         0, 0, width, height, TRUE);
-      pixel_region_init (&PR2, gimp_drawable_get_tiles (drawable),
-                         x, y, width, height, TRUE);
+  gegl_buffer_copy (gimp_drawable_get_buffer (drawable),
+                    GIMP_GEGL_RECT (x, y, width, height),
+                    buffer,
+                    GIMP_GEGL_RECT (0, 0, 0, 0));
+  gegl_buffer_copy (tmp,
+                    GIMP_GEGL_RECT (0, 0, width, height),
+                    gimp_drawable_get_buffer (drawable),
+                    GIMP_GEGL_RECT (x, y, 0, 0));
 
-      swap_region (&PR1, &PR2);
-    }
+  g_object_unref (tmp);
 
   gimp_drawable_update (drawable, x, y, width, height);
 }
@@ -1568,49 +1528,39 @@ gimp_drawable_get_mode_node (GimpDrawable *drawable)
 
 void
 gimp_drawable_swap_pixels (GimpDrawable *drawable,
-                           TileManager  *tiles,
-                           gboolean      sparse,
+                           GeglBuffer   *buffer,
                            gint          x,
                            gint          y,
                            gint          width,
                            gint          height)
 {
   g_return_if_fail (GIMP_IS_DRAWABLE (drawable));
-  g_return_if_fail (tiles != NULL);
+  g_return_if_fail (GEGL_IS_BUFFER (buffer));
 
-  GIMP_DRAWABLE_GET_CLASS (drawable)->swap_pixels (drawable, tiles, sparse,
+  GIMP_DRAWABLE_GET_CLASS (drawable)->swap_pixels (drawable, buffer,
                                                    x, y, width, height);
 }
 
 void
 gimp_drawable_push_undo (GimpDrawable *drawable,
                          const gchar  *undo_desc,
+                         GeglBuffer   *buffer,
                          gint          x,
                          gint          y,
                          gint          width,
-                         gint          height,
-                         TileManager  *tiles,
-                         gboolean      sparse)
+                         gint          height)
 {
   GimpItem *item;
 
   g_return_if_fail (GIMP_IS_DRAWABLE (drawable));
-  g_return_if_fail (sparse == FALSE || tiles != NULL);
+  g_return_if_fail (buffer == NULL || GEGL_IS_BUFFER (buffer));
 
   item = GIMP_ITEM (drawable);
 
   g_return_if_fail (gimp_item_is_attached (item));
-  g_return_if_fail (sparse == FALSE ||
-                    tile_manager_width (tiles) == gimp_item_get_width (item));
-  g_return_if_fail (sparse == FALSE ||
-                    tile_manager_height (tiles) == gimp_item_get_height (item));
-
-#if 0
-  g_printerr ("gimp_drawable_push_undo (%s, %d, %d, %d, %d)\n",
-              sparse ? "TRUE" : "FALSE", x, y, width, height);
-#endif
 
-  if (! gimp_rectangle_intersect (x, y,
+  if (! buffer &&
+      ! gimp_rectangle_intersect (x, y,
                                   width, height,
                                   0, 0,
                                   gimp_item_get_width (item),
@@ -1622,7 +1572,7 @@ gimp_drawable_push_undo (GimpDrawable *drawable,
     }
 
   GIMP_DRAWABLE_GET_CLASS (drawable)->push_undo (drawable, undo_desc,
-                                                 tiles, sparse,
+                                                 buffer,
                                                  x, y, width, height);
 }
 
diff --git a/app/core/gimpdrawable.h b/app/core/gimpdrawable.h
index 42f3443..26a4097 100644
--- a/app/core/gimpdrawable.h
+++ b/app/core/gimpdrawable.h
@@ -97,15 +97,13 @@ struct _GimpDrawableClass
                                            gint                  offset_y);
   void          (* push_undo)             (GimpDrawable         *drawable,
                                            const gchar          *undo_desc,
-                                           TileManager          *tiles,
-                                           gboolean              sparse,
+                                           GeglBuffer           *buffer,
                                            gint                  x,
                                            gint                  y,
                                            gint                  width,
                                            gint                  height);
   void          (* swap_pixels)           (GimpDrawable         *drawable,
-                                           TileManager          *tiles,
-                                           gboolean              sparse,
+                                           GeglBuffer           *buffer,
                                            gint                  x,
                                            gint                  y,
                                            gint                  width,
@@ -195,8 +193,7 @@ GeglNode      * gimp_drawable_get_source_node    (GimpDrawable       *drawable);
 GeglNode      * gimp_drawable_get_mode_node      (GimpDrawable       *drawable);
 
 void            gimp_drawable_swap_pixels        (GimpDrawable       *drawable,
-                                                  TileManager        *tiles,
-                                                  gboolean            sparse,
+                                                  GeglBuffer         *buffer,
                                                   gint                x,
                                                   gint                y,
                                                   gint                width,
@@ -204,12 +201,11 @@ void            gimp_drawable_swap_pixels        (GimpDrawable       *drawable,
 
 void            gimp_drawable_push_undo          (GimpDrawable       *drawable,
                                                   const gchar        *undo_desc,
+                                                  GeglBuffer         *buffer,
                                                   gint                x,
                                                   gint                y,
                                                   gint                width,
-                                                  gint                height,
-                                                  TileManager        *tiles,
-                                                  gboolean            sparse);
+                                                  gint                height);
 
 void            gimp_drawable_fill               (GimpDrawable       *drawable,
                                                   const GimpRGB      *color,
diff --git a/app/core/gimpdrawableundo.c b/app/core/gimpdrawableundo.c
index 231f42d..7340707 100644
--- a/app/core/gimpdrawableundo.c
+++ b/app/core/gimpdrawableundo.c
@@ -25,6 +25,7 @@
 
 #include "base/tile-manager.h"
 
+#include "gimp-utils.h"
 #include "gimpimage.h"
 #include "gimpdrawable.h"
 #include "gimpdrawableundo.h"
@@ -33,8 +34,7 @@
 enum
 {
   PROP_0,
-  PROP_TILES,
-  PROP_SPARSE,
+  PROP_BUFFER,
   PROP_X,
   PROP_Y,
   PROP_WIDTH,
@@ -83,17 +83,11 @@ gimp_drawable_undo_class_init (GimpDrawableUndoClass *klass)
   undo_class->pop                = gimp_drawable_undo_pop;
   undo_class->free               = gimp_drawable_undo_free;
 
-  g_object_class_install_property (object_class, PROP_TILES,
-                                   g_param_spec_boxed ("tiles", NULL, NULL,
-                                                       GIMP_TYPE_TILE_MANAGER,
-                                                       GIMP_PARAM_READWRITE |
-                                                       G_PARAM_CONSTRUCT_ONLY));
-
-  g_object_class_install_property (object_class, PROP_SPARSE,
-                                   g_param_spec_boolean ("sparse", NULL, NULL,
-                                                         FALSE,
-                                                         GIMP_PARAM_READWRITE |
-                                                         G_PARAM_CONSTRUCT_ONLY));
+  g_object_class_install_property (object_class, PROP_BUFFER,
+                                   g_param_spec_object ("buffer", NULL, NULL,
+                                                        GEGL_TYPE_BUFFER,
+                                                        GIMP_PARAM_READWRITE |
+                                                        G_PARAM_CONSTRUCT_ONLY));
 
   g_object_class_install_property (object_class, PROP_X,
                                    g_param_spec_int ("x", NULL, NULL,
@@ -134,7 +128,7 @@ gimp_drawable_undo_constructed (GObject *object)
     G_OBJECT_CLASS (parent_class)->constructed (object);
 
   g_assert (GIMP_IS_DRAWABLE (GIMP_ITEM_UNDO (object)->item));
-  g_assert (drawable_undo->tiles != NULL);
+  g_assert (drawable_undo->buffer != NULL);
 }
 
 static void
@@ -147,11 +141,8 @@ gimp_drawable_undo_set_property (GObject      *object,
 
   switch (property_id)
     {
-    case PROP_TILES:
-      drawable_undo->tiles = g_value_dup_boxed (value);
-      break;
-    case PROP_SPARSE:
-      drawable_undo->sparse = g_value_get_boolean (value);
+    case PROP_BUFFER:
+      drawable_undo->buffer = g_value_dup_object (value);
       break;
     case PROP_X:
       drawable_undo->x = g_value_get_int (value);
@@ -182,11 +173,8 @@ gimp_drawable_undo_get_property (GObject    *object,
 
   switch (property_id)
     {
-    case PROP_TILES:
-      g_value_set_boxed (value, drawable_undo->tiles);
-      break;
-    case PROP_SPARSE:
-      g_value_set_boolean (value, drawable_undo->sparse);
+    case PROP_BUFFER:
+      g_value_set_object (value, drawable_undo->buffer);
       break;
     case PROP_X:
       g_value_set_int (value, drawable_undo->x);
@@ -214,8 +202,7 @@ gimp_drawable_undo_get_memsize (GimpObject *object,
   GimpDrawableUndo *drawable_undo = GIMP_DRAWABLE_UNDO (object);
   gint64            memsize       = 0;
 
-  memsize += tile_manager_get_memsize (drawable_undo->tiles,
-                                       drawable_undo->sparse);
+  memsize += gimp_gegl_buffer_get_memsize (drawable_undo->buffer);
 
   return memsize + GIMP_OBJECT_CLASS (parent_class)->get_memsize (object,
                                                                   gui_size);
@@ -231,8 +218,7 @@ gimp_drawable_undo_pop (GimpUndo            *undo,
   GIMP_UNDO_CLASS (parent_class)->pop (undo, undo_mode, accum);
 
   gimp_drawable_swap_pixels (GIMP_DRAWABLE (GIMP_ITEM_UNDO (undo)->item),
-                             drawable_undo->tiles,
-                             drawable_undo->sparse,
+                             drawable_undo->buffer,
                              drawable_undo->x,
                              drawable_undo->y,
                              drawable_undo->width,
@@ -245,10 +231,10 @@ gimp_drawable_undo_free (GimpUndo     *undo,
 {
   GimpDrawableUndo *drawable_undo = GIMP_DRAWABLE_UNDO (undo);
 
-  if (drawable_undo->tiles)
+  if (drawable_undo->buffer)
     {
-      tile_manager_unref (drawable_undo->tiles);
-      drawable_undo->tiles = NULL;
+      g_object_unref (drawable_undo->buffer);
+      drawable_undo->buffer = NULL;
     }
 
   if (drawable_undo->src2_tiles)
diff --git a/app/core/gimpdrawableundo.h b/app/core/gimpdrawableundo.h
index 871d670..a16c7b1 100644
--- a/app/core/gimpdrawableundo.h
+++ b/app/core/gimpdrawableundo.h
@@ -36,8 +36,7 @@ struct _GimpDrawableUndo
 {
   GimpItemUndo  parent_instance;
 
-  TileManager  *tiles;
-  gboolean      sparse;
+  GeglBuffer   *buffer;
   gint          x;
   gint          y;
   gint          width;
diff --git a/app/core/gimpimage-undo-push.c b/app/core/gimpimage-undo-push.c
index 4d8ba4f..6a4c161 100644
--- a/app/core/gimpimage-undo-push.c
+++ b/app/core/gimpimage-undo-push.c
@@ -23,8 +23,6 @@
 
 #include "core-types.h"
 
-#include "base/tile-manager.h"
-
 #include "gimp.h"
 #include "gimpchannelpropundo.h"
 #include "gimpchannelundo.h"
@@ -211,8 +209,7 @@ GimpUndo *
 gimp_image_undo_push_drawable (GimpImage    *image,
                                const gchar  *undo_desc,
                                GimpDrawable *drawable,
-                               TileManager  *tiles,
-                               gboolean      sparse,
+                               GeglBuffer   *buffer,
                                gint          x,
                                gint          y,
                                gint          width,
@@ -222,28 +219,17 @@ gimp_image_undo_push_drawable (GimpImage    *image,
 
   g_return_val_if_fail (GIMP_IS_IMAGE (image), NULL);
   g_return_val_if_fail (GIMP_IS_DRAWABLE (drawable), NULL);
-  g_return_val_if_fail (tiles != NULL, NULL);
-  g_return_val_if_fail (sparse == TRUE ||
-                        tile_manager_width (tiles) == width, NULL);
-  g_return_val_if_fail (sparse == TRUE ||
-                        tile_manager_height (tiles) == height, NULL);
+  g_return_val_if_fail (GEGL_IS_BUFFER (buffer), NULL);
 
   item = GIMP_ITEM (drawable);
 
   g_return_val_if_fail (gimp_item_is_attached (item), NULL);
-  g_return_val_if_fail (sparse == FALSE ||
-                        tile_manager_width (tiles) == gimp_item_get_width (item),
-                        NULL);
-  g_return_val_if_fail (sparse == FALSE ||
-                        tile_manager_height (tiles) == gimp_item_get_height (item),
-                        NULL);
 
   return gimp_image_undo_push (image, GIMP_TYPE_DRAWABLE_UNDO,
                                GIMP_UNDO_DRAWABLE, undo_desc,
                                GIMP_DIRTY_ITEM | GIMP_DIRTY_DRAWABLE,
                                "item",   item,
-                               "tiles",  tiles,
-                               "sparse", sparse,
+                               "buffer", buffer,
                                "x",      x,
                                "y",      y,
                                "width",  width,
diff --git a/app/core/gimpimage-undo-push.h b/app/core/gimpimage-undo-push.h
index 90b4b3b..31a2a8a 100644
--- a/app/core/gimpimage-undo-push.h
+++ b/app/core/gimpimage-undo-push.h
@@ -59,8 +59,7 @@ GimpUndo * gimp_image_undo_push_sample_point        (GimpImage     *image,
 GimpUndo * gimp_image_undo_push_drawable            (GimpImage     *image,
                                                      const gchar   *undo_desc,
                                                      GimpDrawable  *drawable,
-                                                     TileManager   *tiles,
-                                                     gboolean       sparse,
+                                                     GeglBuffer    *buffer,
                                                      gint           x,
                                                      gint           y,
                                                      gint           width,
diff --git a/app/core/gimpimagemap.c b/app/core/gimpimagemap.c
index 6f091da..280a2a6 100644
--- a/app/core/gimpimagemap.c
+++ b/app/core/gimpimagemap.c
@@ -579,15 +579,16 @@ gimp_image_map_commit (GimpImageMap *image_map)
   /*  Register an undo step  */
   if (image_map->undo_tiles)
     {
-      gint x      = image_map->undo_offset_x;
-      gint y      = image_map->undo_offset_y;
-      gint width  = tile_manager_width  (image_map->undo_tiles);
-      gint height = tile_manager_height (image_map->undo_tiles);
+      GeglBuffer *buffer = gimp_image_map_get_buffer (GIMP_PICKABLE (image_map));
+      gint        x      = image_map->undo_offset_x;
+      gint        y      = image_map->undo_offset_y;
+      gint        width  = gegl_buffer_get_width  (buffer);
+      gint        height = gegl_buffer_get_height (buffer);
 
       gimp_drawable_push_undo (image_map->drawable,
                                image_map->undo_desc,
-                               x, y, width, height,
-                               image_map->undo_tiles, FALSE);
+                               buffer,
+                               x, y, width, height);
 
       tile_manager_unref (image_map->undo_tiles);
       image_map->undo_tiles = NULL;
diff --git a/app/core/gimplayer.c b/app/core/gimplayer.c
index cadaf77..ac3e387 100644
--- a/app/core/gimplayer.c
+++ b/app/core/gimplayer.c
@@ -1369,10 +1369,10 @@ gimp_layer_create_mask (const GimpLayer *layer,
 
               gimp_drawable_push_undo (drawable,
                                        C_("undo-type", "Transfer Alpha to Mask"),
+                                       NULL,
                                        0, 0,
                                        gimp_item_get_width  (item),
-                                       gimp_item_get_height (item),
-                                       NULL, FALSE);
+                                       gimp_item_get_height (item));
 
               set_alpha = gegl_node_new_child (NULL,
                                                "operation", "gimp:set-alpha",
@@ -1565,10 +1565,10 @@ gimp_layer_apply_mask (GimpLayer         *layer,
 
       if (push_undo)
         gimp_drawable_push_undo (GIMP_DRAWABLE (layer), NULL,
+                                 NULL,
                                  0, 0,
                                  gimp_item_get_width  (item),
-                                 gimp_item_get_height (item),
-                                 NULL, FALSE);
+                                 gimp_item_get_height (item));
 
       /*  Combine the current layer's alpha channel and the mask  */
       mask_buffer = gimp_drawable_get_buffer (GIMP_DRAWABLE (mask));
diff --git a/app/paint/gimppaintcore.c b/app/paint/gimppaintcore.c
index c6d3183..cfda565 100644
--- a/app/paint/gimppaintcore.c
+++ b/app/paint/gimppaintcore.c
@@ -33,6 +33,8 @@
 
 #include "paint-funcs/paint-funcs.h"
 
+#include "gegl/gimp-gegl-utils.h"
+
 #include "core/gimp.h"
 #include "core/gimp-utils.h"
 #include "core/gimpdrawable.h"
@@ -456,16 +458,42 @@ gimp_paint_core_finish (GimpPaintCore *core,
 
   if (push_undo)
     {
+      GeglBuffer *src;
+      GeglBuffer *buffer;
+
       gimp_image_undo_group_start (image, GIMP_UNDO_GROUP_PAINT,
                                    core->undo_desc);
 
       GIMP_PAINT_CORE_GET_CLASS (core)->push_undo (core, image, NULL);
 
+      /*  set undo blocks  */
+      gimp_paint_core_validate_undo_tiles (core, drawable,
+                                           core->x1,
+                                           core->y1,
+                                           core->x2 - core->x1,
+                                           core->y2 - core->y1);
+
+      src = gimp_tile_manager_create_buffer (core->undo_tiles,
+                                             gimp_drawable_get_format (drawable));
+      buffer = gimp_gegl_buffer_new (GIMP_GEGL_RECT (0, 0,
+                                                     core->x2 - core->x1,
+                                                     core->y2 - core->y1),
+                                     gimp_drawable_get_format (drawable));
+
+      gegl_buffer_copy (src,
+                        GIMP_GEGL_RECT (core->x1, core->y1,
+                                        core->x2 - core->x1,
+                                        core->y2 - core->y1),
+                        buffer,
+                        GIMP_GEGL_RECT (0, 0, 0, 0));
+
       gimp_drawable_push_undo (drawable, NULL,
+                               buffer,
                                core->x1, core->y1,
-                               core->x2 - core->x1, core->y2 - core->y1,
-                               core->undo_tiles,
-                               TRUE);
+                               core->x2 - core->x1, core->y2 - core->y1);
+
+      g_object_unref (src);
+      g_object_unref (buffer);
 
       gimp_image_undo_group_end (image);
     }
diff --git a/app/text/gimptextlayer.c b/app/text/gimptextlayer.c
index c1ec117..ea46cca 100644
--- a/app/text/gimptextlayer.c
+++ b/app/text/gimptextlayer.c
@@ -91,8 +91,7 @@ static void       gimp_text_layer_set_buffer     (GimpDrawable    *drawable,
                                                   gint             offset_y);
 static void       gimp_text_layer_push_undo      (GimpDrawable    *drawable,
                                                   const gchar     *undo_desc,
-                                                  TileManager     *tiles,
-                                                  gboolean         sparse,
+                                                  GeglBuffer      *buffer,
                                                   gint             x,
                                                   gint             y,
                                                   gint             width,
@@ -334,8 +333,7 @@ gimp_text_layer_set_buffer (GimpDrawable *drawable,
 static void
 gimp_text_layer_push_undo (GimpDrawable *drawable,
                            const gchar  *undo_desc,
-                           TileManager  *tiles,
-                           gboolean      sparse,
+                           GeglBuffer   *buffer,
                            gint          x,
                            gint          y,
                            gint          width,
@@ -348,7 +346,7 @@ gimp_text_layer_push_undo (GimpDrawable *drawable,
     gimp_image_undo_group_start (image, GIMP_UNDO_GROUP_DRAWABLE, undo_desc);
 
   GIMP_DRAWABLE_CLASS (parent_class)->push_undo (drawable, undo_desc,
-                                                 tiles, sparse,
+                                                 buffer,
                                                  x, y, width, height);
 
   if (! layer->modified)



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