From 1b67742e4f7f61e887fc57bb4b18a47758d316cc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Michael=20Mur=C3=A9?= Date: Fri, 16 Jul 2010 22:37:25 +0200 Subject: [PATCH] gimpcage: add a function to compute the bounding box of the deformed cage. Computing of the coefficient is done accordingly. Update of the gegl op. Also add a wip function to compute if the cage is clockwise or not. --- app/core/gimpcage.c | 118 +++++++++++++++++++++++++++++++---- app/core/gimpcage.h | 3 +- app/gegl/gimpoperationcage.c | 12 ++-- 3 files changed, 112 insertions(+), 21 deletions(-) diff --git a/app/core/gimpcage.c b/app/core/gimpcage.c index c54e393c02..594e4c5e8d 100644 --- a/app/core/gimpcage.c +++ b/app/core/gimpcage.c @@ -24,16 +24,19 @@ #include #include +#include G_DEFINE_TYPE (GimpCage, gimp_cage, G_TYPE_OBJECT) #define parent_class gimp_cage_parent_class #define N_ITEMS_PER_ALLOC 10 +#define TEST_REVERSE_CAGE 0 static void gimp_cage_finalize (GObject *object); static void gimp_cage_reverse_cage_if_needed (GimpCage *gc); static void gimp_cage_compute_scaling_factor (GimpCage *gc); +static void gimp_cage_compute_bounding_box (GimpCage *gc); static void @@ -52,11 +55,6 @@ gimp_cage_init (GimpCage *self) self->cage_vertices = g_new(GimpVector2, self->cage_vertices_max); self->cage_vertices_d = g_new(GimpVector2, self->cage_vertices_max); self->scaling_factor = g_malloc (self->cage_vertices_max * sizeof(gfloat)); - - self->extent.x = 20; - self->extent.y = 20; - self->extent.height = 80; - self->extent.width = 80; self->cage_vertices_coef = NULL; self->cage_edges_coef = NULL; @@ -94,6 +92,12 @@ gimp_cage_compute_coefficient (GimpCage *gc) g_return_if_fail (GIMP_IS_CAGE (gc)); + gimp_cage_compute_bounding_box (gc); + + #if TEST_REVERSE_CAGE + gimp_cage_reverse_cage_if_needed (gc); + #endif + format = babl_format_n(babl_type("float"), gc->cage_vertice_number); @@ -107,14 +111,14 @@ gimp_cage_compute_coefficient (GimpCage *gc) gegl_buffer_destroy(gc->cage_edges_coef); } - gc->cage_vertices_coef = gegl_buffer_new(&gc->extent, format); - gc->cage_edges_coef = gegl_buffer_new(&gc->extent, format); + gc->cage_vertices_coef = gegl_buffer_new(&gc->bounding_box, format); + gc->cage_edges_coef = gegl_buffer_new(&gc->bounding_box, format); - gegl_buffer_clear(gc->cage_vertices_coef, &gc->extent); - gegl_buffer_clear(gc->cage_edges_coef, &gc->extent); + gegl_buffer_clear(gc->cage_vertices_coef, &gc->bounding_box); + gegl_buffer_clear(gc->cage_edges_coef, &gc->bounding_box); - i = gegl_buffer_iterator_new (gc->cage_vertices_coef, &gc->extent, format, GEGL_BUFFER_READWRITE); - edge = gegl_buffer_iterator_add (i, gc->cage_edges_coef, &gc->extent, format, GEGL_BUFFER_READWRITE); + i = gegl_buffer_iterator_new (gc->cage_vertices_coef, &gc->bounding_box, format, GEGL_BUFFER_READWRITE); + edge = gegl_buffer_iterator_add (i, gc->cage_edges_coef, &gc->bounding_box, format, GEGL_BUFFER_READWRITE); vertice = 0; //iterate on GeglBuffer @@ -351,6 +355,56 @@ gimp_cage_reverse_cage (GimpCage *gc) gimp_cage_compute_scaling_factor (gc); } +static void +gimp_cage_reverse_cage_if_needed (GimpCage *gc) +{ + gint i; + gdouble sum; + + g_return_if_fail (GIMP_IS_CAGE (gc)); + + sum = 0.0; + + /* we sum all the angles in the cage */ + for (i = 0; i < gc->cage_vertice_number ; i++) + { + GimpVector2 P1, P2, P3, P12, P23; + gdouble sign, angle; + + P1 = gc->cage_vertices[i]; + P2 = gc->cage_vertices[(i+1) % gc->cage_vertice_number]; + P3 = gc->cage_vertices[(i+2) % gc->cage_vertice_number]; + + P12.x = P2.x - P1.x; + P12.y = P2.y - P1.y; + P23.x = P3.x - P2.x; + P23.y = P3.y - P2.y; + + sign = P23.x * P12.x - P23.y * P12.y; + angle = acos( (P12.x * P23.x + P12.y * P23.y) / ( sqrt(P12.x * P12.x + P12.y * P12.y) * sqrt(P23.x * P23.x + P23.y * P23.y)) ); + + printf("sign: %f angle: %f sum: %f \n", sign, angle, sum); + + if (sign > 0) + { + sum += angle; + } + else + { + sum -= angle; + } + } + + printf("final sum: %f\n", sum); + + /* sum < 0 mean a cage defined clockwise, so we reverse it */ + if (sum < 0) + { + printf("reverse cage !\n"); + gimp_cage_reverse_cage (gc); + } +} + GimpVector2 gimp_cage_get_edge_normal (GimpCage *gc, gint edge_index) @@ -366,4 +420,46 @@ gimp_cage_get_edge_normal (GimpCage *gc, &gc->cage_vertices_d[edge_index]); return gimp_vector2_normal (&result); +} + +static void +gimp_cage_compute_bounding_box (GimpCage *gc) +{ + gint i; + + g_return_if_fail (GIMP_IS_CAGE (gc)); + g_return_if_fail (gc->cage_vertice_number >= 0); + + gc->bounding_box.x = gc->cage_vertices[0].x; + gc->bounding_box.y = gc->cage_vertices[0].y; + gc->bounding_box.height = 1; + gc->bounding_box.width = 1; + + for (i = 1; i < gc->cage_vertice_number; i++) + { + gdouble x,y; + + x = gc->cage_vertices[i].x; + y = gc->cage_vertices[i].y; + + if (x < gc->bounding_box.x) + { + gc->bounding_box.x = x; + } + + if (y < gc->bounding_box.y) + { + gc->bounding_box.y = y; + } + + if (x > gc->bounding_box.x + gc->bounding_box.width) + { + gc->bounding_box.width = x - gc->bounding_box.x; + } + + if (y > gc->bounding_box.y + gc->bounding_box.height) + { + gc->bounding_box.height = y - gc->bounding_box.y; + } + } } \ No newline at end of file diff --git a/app/core/gimpcage.h b/app/core/gimpcage.h index 8d65a8f066..07103b5b77 100644 --- a/app/core/gimpcage.h +++ b/app/core/gimpcage.h @@ -50,8 +50,7 @@ struct _GimpCage GeglBuffer *cage_edges_coef; gdouble *scaling_factor; - //test data - GeglRectangle extent; + GeglRectangle bounding_box; }; diff --git a/app/gegl/gimpoperationcage.c b/app/gegl/gimpoperationcage.c index 7117356229..339bbebe0c 100644 --- a/app/gegl/gimpoperationcage.c +++ b/app/gegl/gimpoperationcage.c @@ -69,7 +69,7 @@ gimp_operation_cage_init (GimpOperationCage *self) //FIXME: for test self->cage = g_object_new (GIMP_TYPE_CAGE, NULL); - #if 0 + #if 1 #if 1 gimp_cage_add_cage_point(self->cage, 70, 20); @@ -89,7 +89,7 @@ gimp_operation_cage_init (GimpOperationCage *self) #else - #if 1 + #if 0 gimp_cage_add_cage_point(self->cage, 160, 160); /* need reverse */ gimp_cage_add_cage_point(self->cage, 250, 160); gimp_cage_add_cage_point(self->cage, 250, 280); @@ -138,7 +138,7 @@ gimp_operation_cage_process (GeglOperation *operation, Babl *format_io = babl_format ("RGBA float"); Babl *format_coef = babl_format_n (babl_type ("float"), op_cage->cage->cage_vertice_number); - gint in, coef_vertices, coef_edges; + gint in, out, coef_vertices, coef_edges; gint i; GeglRectangle rect; GeglBufferIterator *it; @@ -146,10 +146,6 @@ gimp_operation_cage_process (GeglOperation *operation, rect.height = 1; rect.width = 1; - cage->extent.height = roi->height; - cage->extent.width = roi->width; - cage->extent.x = roi->x; - cage->extent.y = roi->y; gimp_cage_compute_coefficient (cage); it = gegl_buffer_iterator_new (in_buf, roi, format_io, GEGL_BUFFER_READ); @@ -207,7 +203,7 @@ gimp_operation_cage_process (GeglOperation *operation, format_io, source, GEGL_AUTO_ROWSTRIDE); - + source += 4; coef_v += cage->cage_vertice_number; coef_e += cage->cage_vertice_number;