[gegl] alpha-inpaint: fixed non integer sampling, and tidy properties



commit 81c5ba43dad274f98b07e2f08f41a5dedb3a8693
Author: Øyvind Kolås <pippin gimp org>
Date:   Wed Jul 3 15:29:15 2019 +0200

    alpha-inpaint: fixed non integer sampling, and tidy properties
    
    Remove some properties that are becoming unneeded with changes in internals.

 operations/workshop/inpaint.c      | 87 +++++------------------------------
 operations/workshop/pixel-duster.h | 92 ++++----------------------------------
 2 files changed, 20 insertions(+), 159 deletions(-)
---
diff --git a/operations/workshop/inpaint.c b/operations/workshop/inpaint.c
index a9307d5d9..2492dc060 100644
--- a/operations/workshop/inpaint.c
+++ b/operations/workshop/inpaint.c
@@ -30,16 +30,13 @@
 property_int (seek_distance, "seek radius", 5)
   value_range (1, 512)
 
-property_int (min_neigh, "min neigh", 3)
-  value_range (0, 4)
-
 property_int (min_iter, "min iter", 100)
   value_range (1, 512)
 
 property_int (max_iter, "max iter", 2000)
   value_range (1, 40000)
 
-property_int (improvement_iters, "improvement iters", 2)
+property_int (improvement_iters, "improvement iters", 3)
 
 property_double (chance_try, "try chance", 0.33)
   value_range (0.0, 1.0)
@@ -48,34 +45,27 @@ property_double (chance_retry, "retry chance", 1.0)
   value_range (0.0, 1.0)
   ui_steps    (0.01, 0.1)
 
-property_double (ring_gap,    "ring gap", 1.3)
-  value_range (0.0, 8.0)
-  ui_steps    (0.1, 0.2)
-
-property_double (ring_gamma, "ring gamma", 1.4)
-  value_range (0.0, 4.0)
-  ui_steps    (0.1, 0.2)
 property_double (ring_twist, "ring twist", 0.0)
   value_range (0.0, 1.0)
   ui_steps    (0.01, 0.2)
 
-property_double (ring_gap1,    "ring gap1", 1.2)
-  value_range (0.0, 8.0)
+property_double (ring_gap1,    "ring gap1", 1.3)
+  value_range (0.0, 16.0)
   ui_steps    (0.25, 0.25)
 
 property_double (ring_gap2,    "ring gap2", 2.5)
-  value_range (0.0, 8.0)
+  value_range (0.0, 16.0)
   ui_steps    (0.25, 0.25)
 
-property_double (ring_gap3,    "ring gap3", 3.5)
-  value_range (0.0, 8.0)
+property_double (ring_gap3,    "ring gap3", 3.7)
+  value_range (0.0, 16.0)
   ui_steps    (0.25, 0.25)
 
-property_double (ring_gap4,    "ring gap4", 4.5)
-  value_range (0.0, 8.0)
+property_double (ring_gap4,    "ring gap4", 5.5)
+  value_range (0.0, 16.0)
   ui_steps    (0.25, 0.25)
 
-property_double (metric_dist_powk, "metric dist powk", 2.0)
+property_double (metric_dist_powk, "metric dist powk", 1.5)
   value_range (0.0, 10.0)
   ui_steps    (0.1, 1.0)
 
@@ -91,11 +81,6 @@ property_double (metric_cohesion, "metric cohesion", 0.004)
   value_range (0.0, 10.0)
   ui_steps    (0.2, 0.2)
 
-property_double (scale, "enlarge as well as inpaint 1.0 does nothing", 1.0)
-  value_range (0.0, 10.0)
-  ui_steps    (0.5, 0.5)
-
-
 #else
 
 #define GEGL_OP_FILTER
@@ -126,30 +111,6 @@ prepare (GeglOperation *operation)
   gegl_operation_set_format (operation, "output", format);
 }
 
-static void scaled_copy (PixelDuster *duster,
-                         GeglBuffer *in,
-                         GeglBuffer *out,
-                         gfloat      scale)
-{
-  GeglRectangle rect;
-  const Babl *format = babl_format ("RGBA float");
-  gint x, y;
-
-  rect = *gegl_buffer_get_extent (in);
-  for (y = 0; y < rect.height; y++)
-    for (x = 0; x < rect.width; x++)
-      {
-        float rgba[4];
-        gegl_sampler_get (duster->in_sampler_f, x, y, NULL,
-                          &rgba[0], 0);
-        {
-          GeglRectangle r = {x * scale, y * scale, 1, 1};
-          gegl_buffer_set (out, &r, 0, format, &rgba[0], 0);
-        }
-      }
-}
-
-
 static gboolean
 process (GeglOperation       *operation,
          GeglBuffer          *input,
@@ -162,20 +123,15 @@ process (GeglOperation       *operation,
   GeglRectangle out_rect = *gegl_buffer_get_extent (output);
   PixelDuster    *duster = pixel_duster_new (input, input, output, &in_rect, &out_rect,
                                              o->seek_distance,
-                                             o->min_neigh,
                                              o->min_iter,
                                              o->max_iter,
                                              o->chance_try,
                                              o->chance_retry,
-                                             o->scale, // scale_x
-                                             o->scale, // scale_y
                                              o->improvement_iters,
-                                             o->ring_gap,
                                              o->ring_gap1,
                                              o->ring_gap2,
                                              o->ring_gap3,
                                              o->ring_gap4,
-                                             o->ring_gamma,
                                              o->ring_twist,
                                              o->metric_dist_powk,
                                              o->metric_empty_hay_score,
@@ -183,10 +139,7 @@ process (GeglOperation       *operation,
                                              o->metric_cohesion/1000.0,
                                              operation);
 
-  if (o->scale > 0.9999 && o->scale < 1.0001)
-    gegl_buffer_copy (input, NULL, GEGL_ABYSS_NONE, output, NULL);
-  else
-    scaled_copy (duster, input, output, o->scale);
+  gegl_buffer_copy (input, NULL, GEGL_ABYSS_NONE, output, NULL);
 
   pixel_duster_add_probes_for_transparent (duster);
 
@@ -234,23 +187,6 @@ operation_process (GeglOperation        *operation,
                                    gegl_operation_context_get_level (context));
 }
 
-static GeglRectangle
-get_bounding_box (GeglOperation *operation)
-{
-  GeglProperties *o      = GEGL_PROPERTIES (operation);
-  GeglRectangle *res = gegl_operation_source_get_bounding_box (operation, "input");
-  GeglRectangle result = {0,0,100,100};
-  if (res)
-    result = *res;
-  result.x = 0;
-  result.y = 0;
-  result.width  *= o->scale;
-  result.height *= o->scale;
-
-  return result;
-}
-
-
 static void
 gegl_op_class_init (GeglOpClass *klass)
 {
@@ -263,11 +199,10 @@ gegl_op_class_init (GeglOpClass *klass)
   filter_class->process                    = process;
   operation_class->prepare                 = prepare;
   operation_class->process                 = operation_process;
-  operation_class->get_bounding_box        = get_bounding_box;
   operation_class->get_required_for_output = get_required_for_output;
   operation_class->get_cached_region       = get_cached_region;
   operation_class->opencl_support          = FALSE;
-  operation_class->threaded                = FALSE;
+  operation_class->threaded                = TRUE;
 
   gegl_operation_class_set_keys (operation_class,
       "name",        "gegl:alpha-inpaint",
diff --git a/operations/workshop/pixel-duster.h b/operations/workshop/pixel-duster.h
index d9e4f52eb..060c87117 100644
--- a/operations/workshop/pixel-duster.h
+++ b/operations/workshop/pixel-duster.h
@@ -51,20 +51,14 @@ typedef struct
   GeglSampler   *ref_sampler_f;
   GeglSampler   *out_sampler_f;
   int            seek_radius;
-  int            minimum_neighbors;
   int            minimum_iterations;
   int            maximum_iterations;
   int            max_age;
   float          try_chance;
   float          retry_chance;
-  float          scale_x;
-  float          scale_y;
 
-  float          ring_gap;
   float          ring_gaps[8];
 
-
-  float          ring_gamma;
   float          ring_twist;
 
   float          metric_dist_powk;
@@ -85,7 +79,7 @@ typedef struct
 } PixelDuster;
 
 
-#define RINGS                   3   // increments works up to 7-8 with no adver
+#define RINGS                   4   // increments works up to 7-8 with no adver
 #define RAYS                    12 // good values for testing 6 8 10 12 16
 #define NEIGHBORHOOD            (RINGS*RAYS+1)
 
@@ -103,7 +97,6 @@ struct _Probe {
   int     target_x;
   int     target_y;
   Probe  *neighbors[8];     // cached from coords and iterating all
-  int     target_neighbors; // cached computation
   int     age;              // not really needed
   float   old_score;        // should be on stack
   float   score;
@@ -138,12 +131,8 @@ static void init_order(PixelDuster *duster)
   for (int circleno = 1; circleno < RINGS; circleno++)
   for (float angleno = 0; angleno < RAYS; angleno++)
   {
-    float mag;
+    float mag = duster->ring_gaps[circleno];
     float x, y;
-    if (duster->ring_gaps[circleno] > 0.0)
-      mag = duster->ring_gaps[circleno];
-    else 
-      mag = pow(duster->ring_gap * (circleno + 1), duster->ring_gamma);
 
     x = cosf ((angleno / RAYS + duster->ring_twist*circleno) * M_PI * 2) * mag;
     y = sinf ((angleno / RAYS + duster->ring_twist*circleno) * M_PI * 2) * mag;
@@ -155,7 +144,7 @@ static void init_order(PixelDuster *duster)
 }
 }
 
-static void duster_idx_to_x_y (PixelDuster *duster, int index, int *x, int *y)
+static void duster_idx_to_x_y (PixelDuster *duster, int index, float *x, float *y)
 {
   *x =  duster->order[index][0];
   *y =  duster->order[index][1];
@@ -168,20 +157,15 @@ static PixelDuster * pixel_duster_new (GeglBuffer *reference,
                                        const GeglRectangle *in_rect,
                                        const GeglRectangle *out_rect,
                                        int         seek_radius,
-                                       int         minimum_neighbors,
                                        int         minimum_iterations,
                                        int         maximum_iterations,
                                        float       try_chance,
                                        float       retry_chance,
-                                       float       scale_x,
-                                       float       scale_y,
                                        int         improvement_iterations,
-                                       float       ring_gap,
                                        float       ring_gap1,
                                        float       ring_gap2,
                                        float       ring_gap3,
                                        float       ring_gap4,
-                                       float       ring_gamma,
                                        float       ring_twist,
                                        float       metric_dist_powk,
                                        float       metric_empty_hay_score,
@@ -195,7 +179,6 @@ static PixelDuster * pixel_duster_new (GeglBuffer *reference,
   ret->input       = input;
   ret->output      = output;
   ret->seek_radius = seek_radius;
-  ret->minimum_neighbors  = minimum_neighbors;
   ret->minimum_iterations = minimum_iterations;
   ret->maximum_iterations = maximum_iterations;
   ret->try_chance   = try_chance;
@@ -210,14 +193,10 @@ static PixelDuster * pixel_duster_new (GeglBuffer *reference,
   ret->min_x = 10000;
   ret->min_y = 10000;
   ret->max_age = improvement_iterations;
-  ret->ring_gap = ring_gap;
-  ret->ring_gamma = ring_gamma;
   ret->ring_twist = ring_twist;
 
   ret->in_rect  = *in_rect;
   ret->out_rect = *out_rect;
-  ret->scale_x  = scale_x;
-  ret->scale_y  = scale_y;
   ret->metric_dist_powk = metric_dist_powk;
   ret->metric_empty_hay_score = metric_empty_hay_score;
   ret->metric_empty_needle_score = metric_empty_needle_score;
@@ -296,7 +275,7 @@ static void extract_site (PixelDuster *duster, GeglBuffer *buffer, double x, dou
 
   for (int i = 0; i < NEIGHBORHOOD; i++)
   {
-    int dx, dy;
+    float dx, dy;
     duster_idx_to_x_y (duster, i, &dx, &dy);
     gegl_sampler_get (sampler_f, x + dx * scale, y + dy * scale, NULL, &dst[i*4], 0);
   }
@@ -436,70 +415,19 @@ add_probe (PixelDuster *duster, int target_x, int target_y)
 
   probe->target_x = target_x;
   probe->target_y = target_y;
-  probe->source_x = target_x / duster->scale_x;
-  probe->source_y = target_y / duster->scale_y;
+  probe->source_x = target_x;
+  probe->source_y = target_y;
   probe->score   = INITIAL_SCORE;
   g_hash_table_insert (duster->probes_ht,
                        xy2offset(target_x, target_y), probe);
   return probe;
 }
 
-static int
-probe_rel_is_set (PixelDuster *duster, GeglBuffer *output, Probe *probe, int rel_x, int rel_y)
-{
-#if 1
-  static const Babl *format = NULL;
-  guchar pix[4];
-  if (!format) format = babl_format ("R'G'B'A u8");
-  gegl_buffer_sample (output, probe->target_x + rel_x, probe->target_y + rel_y, NULL, &pix[0], format, 
GEGL_SAMPLER_NEAREST, 0);
-  return pix[3] > 5;
-#else
-  Probe *neighbor_probe = g_hash_table_lookup (duster->probes_ht,
-        xy2offset(probe->target_x + rel_x, probe->target_y + rel_y));
-  if (!neighbor_probe || neighbor_probe->age)
-    return 1;
-  return 0;
-#endif
-}
-
 static inline void probe_push (PixelDuster *duster, Probe *probe)
 {
 }
 
 
-#define ret_if_good     if (found >=min) goto ret;
-
-static int
-probe_neighbors (PixelDuster *duster, GeglBuffer *output, Probe *probe, int min)
-{
-  int found = 0;
-  found = probe->target_neighbors;
-
-  ret_if_good
-
-  found = 0;
-
-  if (probe_rel_is_set (duster, output, probe, -1, 0)) found ++;
-  ret_if_good
-  if (probe_rel_is_set (duster, output, probe,  1, 0)) found ++;
-  ret_if_good
-  if (probe_rel_is_set (duster, output, probe,  0, 1)) found ++;
-  ret_if_good
-  if (probe_rel_is_set (duster, output, probe,  0, -1)) found ++;
-  ret_if_good
-  if (probe_rel_is_set (duster, output, probe,  1, 1)) found ++;
-  ret_if_good
-  if (probe_rel_is_set (duster, output, probe, -1,-1)) found ++;
-  ret_if_good
-  if (probe_rel_is_set (duster, output, probe,  1,-1)) found ++;
-  ret_if_good
-  if (probe_rel_is_set (duster, output, probe, -1, 1)) found ++;
-
-ret:
-  probe->target_neighbors = found;
-  return found;
-}
-
 static gfloat *ensure_hay (PixelDuster *duster, int x, int y)
 {
   gfloat *hay = NULL;
@@ -806,9 +734,7 @@ static inline void pixel_duster_fill (PixelDuster *duster)
 
     if (probe->score == INITIAL_SCORE || try_replace)
     {
-      if ((rand()%100)/100.0 < duster->try_chance &&
-              probe_neighbors (duster, duster->output, probe, duster->minimum_neighbors) >=
-              duster->minimum_neighbors)
+      if ((rand()%100)/100.0 < duster->try_chance)
       {
         probe_improve (duster, probe);
       }
@@ -816,9 +742,9 @@ static inline void pixel_duster_fill (PixelDuster *duster)
   }
 
   if (duster->op)
-    gegl_operation_progress (duster->op, 0.2 + (total-missing) * 0.8 / total,
+    gegl_operation_progress (duster->op, (total-missing) * 1.0 / total,
                              "finding suitable pixels");
-#if 1
+#if 0
 
   fprintf (stderr, "\r%i/%i %2.2f run#:%i  ", total-missing, total, (total-missing) * 100.0 / total, runs);
 #endif


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