[gimp] app: cache bitmap brushes expensive hardness and disable dynamic change



commit 0c04275a32b923542c309c74744bba55bd838f6f
Author: Alexia Death <alexiadeath gmail com>
Date:   Sat Nov 26 19:10:57 2016 +0200

    app: cache bitmap brushes expensive hardness and disable dynamic change

 app/core/gimpbrush-private.h   |    8 ++-
 app/core/gimpbrush-transform.c |    2 +-
 app/core/gimpbrush.c           |  119 ++++++++++++++++++++++++++++++++++++++--
 app/core/gimpbrush.h           |    2 +
 app/paint/gimpbrushcore.c      |    7 ++
 5 files changed, 130 insertions(+), 8 deletions(-)
---
diff --git a/app/core/gimpbrush-private.h b/app/core/gimpbrush-private.h
index e9234eb..801a31b 100644
--- a/app/core/gimpbrush-private.h
+++ b/app/core/gimpbrush-private.h
@@ -21,8 +21,12 @@
 
 struct _GimpBrushPrivate
 {
-  GimpTempBuf    *mask;       /*  the actual mask                */
-  GimpTempBuf    *pixmap;     /*  optional pixmap data           */
+  GimpTempBuf    *mask;           /*  the actual mask                    */
+  GimpTempBuf    *blured_mask;    /*  blured actual mask cached          */
+  GimpTempBuf    *pixmap;         /*  optional pixmap data               */
+  GimpTempBuf    *blured_pixmap;  /*  optional pixmap data blured cache  */
+
+  gdouble         blur_hardness;
 
   gint            spacing;    /*  brush's spacing                */
   GimpVector2     x_axis;     /*  for calculating brush spacing  */
diff --git a/app/core/gimpbrush-transform.c b/app/core/gimpbrush-transform.c
index 15f2eec..7ed1388 100644
--- a/app/core/gimpbrush-transform.c
+++ b/app/core/gimpbrush-transform.c
@@ -33,7 +33,7 @@
 #include "gimptempbuf.h"
 
 
-#define MAX_BLUR_KERNEL 15
+#define MAX_BLUR_KERNEL 50
 
 
 /*  local function prototypes  */
diff --git a/app/core/gimpbrush.c b/app/core/gimpbrush.c
index 6c2e549..0ab6824 100644
--- a/app/core/gimpbrush.c
+++ b/app/core/gimpbrush.c
@@ -172,6 +172,8 @@ gimp_brush_init (GimpBrush *brush)
   brush->priv->x_axis.y =  0.0;
   brush->priv->y_axis.x =  0.0;
   brush->priv->y_axis.y = 15.0;
+
+  brush->priv->blur_hardness = 1.0;
 }
 
 static void
@@ -190,6 +192,17 @@ gimp_brush_finalize (GObject *object)
       gimp_temp_buf_unref (brush->priv->pixmap);
       brush->priv->pixmap = NULL;
     }
+  if (brush->priv->blured_mask)
+    {
+      gimp_temp_buf_unref (brush->priv->blured_mask);
+      brush->priv->blured_mask = NULL;
+    }
+
+  if (brush->priv->blured_pixmap)
+    {
+      gimp_temp_buf_unref (brush->priv->blured_pixmap);
+      brush->priv->blured_pixmap = NULL;
+    }
 
   if (brush->priv->mask_cache)
     {
@@ -415,6 +428,18 @@ gimp_brush_dirty (GimpData *data)
   if (brush->priv->boundary_cache)
     gimp_brush_cache_clear (brush->priv->boundary_cache);
 
+   if (brush->priv->blured_mask)
+    {
+      gimp_temp_buf_unref (brush->priv->blured_mask);
+      brush->priv->blured_mask = NULL;
+    }
+
+  if (brush->priv->blured_pixmap)
+    {
+      gimp_temp_buf_unref (brush->priv->blured_pixmap);
+      brush->priv->blured_pixmap = NULL;
+    }
+
   GIMP_DATA_CLASS (parent_class)->dirty (data);
 }
 
@@ -448,6 +473,18 @@ gimp_brush_real_end_use (GimpBrush *brush)
 
   g_object_unref (brush->priv->boundary_cache);
   brush->priv->boundary_cache = NULL;
+
+  if (brush->priv->blured_mask)
+    {
+      gimp_temp_buf_unref (brush->priv->blured_mask);
+      brush->priv->blured_mask = NULL;
+    }
+
+  if (brush->priv->blured_pixmap)
+    {
+      gimp_temp_buf_unref (brush->priv->blured_pixmap);
+      brush->priv->blured_pixmap = NULL;
+    }
 }
 
 static GimpBrush *
@@ -623,6 +660,7 @@ gimp_brush_transform_mask (GimpBrush *brush,
   const GimpTempBuf *mask;
   gint               width;
   gint               height;
+  gdouble            effective_hardness = hardness;
 
   g_return_val_if_fail (GIMP_IS_BRUSH (brush), NULL);
   g_return_val_if_fail (scale > 0.0, NULL);
@@ -646,11 +684,28 @@ gimp_brush_transform_mask (GimpBrush *brush,
         }
       else
         {
+          /* This code makes sure that brushes using blur for hardness
+           * (all of them but generated) are blurred once and no more.
+           * It also makes hardnes dynamics not work for these brushes.
+           * This is intentional. Confoliving for each stamp is too expensive.*/
+          if (! brush->priv->blured_mask && ! GIMP_IS_BRUSH_GENERATED(brush)){
+             brush->priv->blured_mask = GIMP_BRUSH_GET_CLASS (brush)->transform_mask (brush,
+                                                               1.0,
+                                                               1.0,
+                                                               0.0,
+                                                               hardness);
+             brush->priv->blur_hardness = hardness;
+          }
+
+          if (brush->priv->blured_mask) {
+            effective_hardness = 1.0; /*Hardness has already been applied*/
+          }
+
           mask = GIMP_BRUSH_GET_CLASS (brush)->transform_mask (brush,
                                                                scale,
                                                                aspect_ratio,
                                                                angle,
-                                                               hardness);
+                                                               effective_hardness);
         }
 
       if (op)
@@ -684,7 +739,7 @@ gimp_brush_transform_mask (GimpBrush *brush,
       gimp_brush_cache_add (brush->priv->mask_cache,
                             (gpointer) mask,
                             op, width, height,
-                            scale, aspect_ratio, angle, hardness);
+                            scale, aspect_ratio, angle, effective_hardness);
     }
 
   return mask;
@@ -701,6 +756,7 @@ gimp_brush_transform_pixmap (GimpBrush *brush,
   const GimpTempBuf *pixmap;
   gint               width;
   gint               height;
+  gdouble            effective_hardness = hardness;
 
   g_return_val_if_fail (GIMP_IS_BRUSH (brush), NULL);
   g_return_val_if_fail (brush->priv->pixmap != NULL, NULL);
@@ -725,11 +781,25 @@ gimp_brush_transform_pixmap (GimpBrush *brush,
         }
       else
         {
+         if (! brush->priv->blured_pixmap && ! GIMP_IS_BRUSH_GENERATED(brush))
+          {
+             brush->priv->blured_pixmap = GIMP_BRUSH_GET_CLASS (brush)->transform_mask (brush,
+                                                                      1.0,
+                                                                      1.0,
+                                                                      0.0,
+                                                                      hardness);
+             brush->priv->blur_hardness = hardness;
+           }
+
+          if (brush->priv->blured_pixmap) {
+            effective_hardness = 1.0; /*Hardness has already been applied*/
+          }
+
           pixmap = GIMP_BRUSH_GET_CLASS (brush)->transform_pixmap (brush,
                                                                    scale,
                                                                    aspect_ratio,
                                                                    angle,
-                                                                   hardness);
+                                                                   effective_hardness);
         }
 
       if (op)
@@ -762,7 +832,7 @@ gimp_brush_transform_pixmap (GimpBrush *brush,
       gimp_brush_cache_add (brush->priv->pixmap_cache,
                             (gpointer) pixmap,
                             op, width, height,
-                            scale, aspect_ratio, angle, hardness);
+                            scale, aspect_ratio, angle, effective_hardness);
     }
 
   return pixmap;
@@ -824,6 +894,10 @@ gimp_brush_get_mask (GimpBrush *brush)
   g_return_val_if_fail (brush != NULL, NULL);
   g_return_val_if_fail (GIMP_IS_BRUSH (brush), NULL);
 
+  if (brush->priv->blured_mask)
+    {
+      return brush->priv->blured_mask;
+    }
   return brush->priv->mask;
 }
 
@@ -833,14 +907,45 @@ gimp_brush_get_pixmap (GimpBrush *brush)
   g_return_val_if_fail (brush != NULL, NULL);
   g_return_val_if_fail (GIMP_IS_BRUSH (brush), NULL);
 
+  if(brush->priv->blured_pixmap)
+    {
+      return brush->priv->blured_pixmap;
+    }
   return brush->priv->pixmap;
 }
 
+void
+gimp_brush_flush_blur_caches (GimpBrush *brush)
+{
+  if (brush->priv->blured_mask)
+    {
+      gimp_temp_buf_unref (brush->priv->blured_mask);
+      brush->priv->blured_mask = NULL;
+    }
+
+  if (brush->priv->blured_pixmap)
+    {
+      gimp_temp_buf_unref (brush->priv->blured_pixmap);
+      brush->priv->blured_pixmap = NULL;
+    }
+}
+
+gdouble
+gimp_brush_get_blur_hardness (GimpBrush *brush)
+{
+  g_return_val_if_fail (GIMP_IS_BRUSH (brush), 0);
+
+  return brush->priv->blur_hardness;
+}
+
 gint
 gimp_brush_get_width (GimpBrush *brush)
 {
   g_return_val_if_fail (GIMP_IS_BRUSH (brush), 0);
-
+  if (brush->priv->blured_mask)
+    {
+      return gimp_temp_buf_get_width (brush->priv->blured_mask);
+    }
   return gimp_temp_buf_get_width (brush->priv->mask);
 }
 
@@ -849,6 +954,10 @@ gimp_brush_get_height (GimpBrush *brush)
 {
   g_return_val_if_fail (GIMP_IS_BRUSH (brush), 0);
 
+  if (brush->priv->blured_mask)
+  {
+    return gimp_temp_buf_get_height (brush->priv->blured_mask);
+  }
   return gimp_temp_buf_get_height (brush->priv->mask);
 }
 
diff --git a/app/core/gimpbrush.h b/app/core/gimpbrush.h
index 0bf353f..66ad4e6 100644
--- a/app/core/gimpbrush.h
+++ b/app/core/gimpbrush.h
@@ -141,5 +141,7 @@ void                   gimp_brush_set_spacing        (GimpBrush        *brush,
 GimpVector2            gimp_brush_get_x_axis         (GimpBrush        *brush);
 GimpVector2            gimp_brush_get_y_axis         (GimpBrush        *brush);
 
+void                   gimp_brush_flush_blur_caches  (GimpBrush        *brush);
+gdouble                gimp_brush_get_blur_hardness  (GimpBrush        *brush);
 
 #endif /* __GIMP_BRUSH_H__ */
diff --git a/app/paint/gimpbrushcore.c b/app/paint/gimpbrushcore.c
index ce1320e..7baef54 100644
--- a/app/paint/gimpbrushcore.c
+++ b/app/paint/gimpbrushcore.c
@@ -29,6 +29,7 @@
 #include "gegl/gimp-babl.h"
 
 #include "core/gimpbrush.h"
+#include "core/gimpbrushgenerated.h"
 #include "core/gimpdrawable.h"
 #include "core/gimpdynamics.h"
 #include "core/gimpdynamicsoutput.h"
@@ -413,6 +414,12 @@ gimp_brush_core_start (GimpPaintCore     *paint_core,
       return FALSE;
     }
 
+  if ((! GIMP_IS_BRUSH_GENERATED(core->main_brush)) &&
+      (core->hardness != gimp_brush_get_blur_hardness(core->main_brush)))
+  {
+    gimp_brush_flush_blur_caches(core->main_brush);
+  }
+
   if (GIMP_BRUSH_CORE_GET_CLASS (core)->handles_transforming_brush)
     {
       gimp_brush_core_eval_transform_dynamics (core,


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