diff --git a/libweston/vertex-clipping.c b/libweston/vertex-clipping.c index 1ef840b9..319b35ee 100644 --- a/libweston/vertex-clipping.c +++ b/libweston/vertex-clipping.c @@ -291,13 +291,21 @@ clip_polygon_bottom(struct clip_context *ctx, const struct polygon8 *src, return ctx->vertices - dst; } -/* General purpose polygon clipping algorithm based on Sutherland-Hodgman: +/* General purpose clipping function. Compute the boundary vertices of the + * intersection of a 'polygon' and a clipping 'box'. 'polygon' points to an + * array of 4 vertices defining a convex polygon of any winding order. 'box' + * points to an array of 2 vertices where the values of the 1st vertex are less + * than or equal to the values of the 2nd vertex. Up to 8 resulting vertices, + * using 'polygon' winding order, are written to 'vertices'. The return value is + * the number of vertices created. + * + * Based on Sutherland-Hodgman algorithm: * https://www.codeguru.com/cplusplus/polygon-clipping/ */ -WESTON_EXPORT_FOR_TESTS int -clipper_clip(const struct clipper_vertex polygon[4], - const struct clipper_vertex box[2], - struct clipper_vertex *restrict vertices) +static int +clip(const struct clipper_vertex polygon[4], + const struct clipper_vertex box[2], + struct clipper_vertex *restrict vertices) { struct clip_context ctx; struct polygon8 p, tmp; @@ -386,7 +394,7 @@ clipper_quad_clip(struct clipper_quad *quad, /* Then use our general purpose clipping algorithm: */ - n = clipper_clip(quad->polygon, box, vertices); + n = clip(quad->polygon, box, vertices); if (n < 3) return 0; diff --git a/libweston/vertex-clipping.h b/libweston/vertex-clipping.h index 1308fecc..a88ff5c8 100644 --- a/libweston/vertex-clipping.h +++ b/libweston/vertex-clipping.h @@ -39,20 +39,6 @@ struct clipper_quad { bool axis_aligned; }; -/* - * General purpose clipping function. Compute the boundary vertices of the - * intersection of a 'polygon' and a clipping 'box'. 'polygon' points to an - * array of 4 vertices defining a convex polygon of any winding order. 'box' - * points to an array of 2 vertices where the values of the 1st vertex are less - * than or equal to the values of the 2nd vertex. Up to 8 resulting vertices, - * using 'polygon' winding order, are written to 'vertices'. The return value is - * the number of vertices created. - */ -int -clipper_clip(const struct clipper_vertex polygon[4], - const struct clipper_vertex box[2], - struct clipper_vertex *restrict vertices); - /* * Initialize a 'quad' clipping context. 'polygon' points to an array of 4 * vertices defining a convex quadrilateral of any winding order. Call diff --git a/tests/vertex-clip-test.c b/tests/vertex-clip-test.c index bea3be30..8983d2eb 100644 --- a/tests/vertex-clip-test.c +++ b/tests/vertex-clip-test.c @@ -77,94 +77,6 @@ assert_vertices(const struct clipper_vertex *clipped, int clipped_n, } } -/* clipper_clip() tests: */ - -static const struct vertex_clip_test_data clip_expected_data[] = { - /* Quad inside box. */ - { - .box = BOX (50.0f, 50.0f, 100.0f, 100.0f), - .polygon = QUAD(51.0f, 51.0f, 99.0f, 99.0f), - .clipped = QUAD(51.0f, 51.0f, 99.0f, 99.0f), - .clipped_n = 4, - }, - - /* Quad bottom edge outside of box. */ - { - .box = BOX (50.0f, 50.0f, 100.0f, 100.0f), - .polygon = QUAD(51.0f, 51.0f, 99.0f, 101.0f), - .clipped = QUAD(51.0f, 51.0f, 99.0f, 100.0f), - .clipped_n = 4, - }, - - /* Quad top edge outside of box. */ - { - .box = BOX (50.0f, 50.0f, 100.0f, 100.0f), - .polygon = QUAD(51.0f, 49.0f, 99.0f, 99.0f), - .clipped = QUAD(51.0f, 50.0f, 99.0f, 99.0f), - .clipped_n = 4, - }, - - /* Quad left edge outside of box. */ - { - .box = BOX (50.0f, 50.0f, 100.0f, 100.0f), - .polygon = QUAD(49.0f, 51.0f, 99.0f, 99.0f), - .clipped = QUAD(50.0f, 51.0f, 99.0f, 99.0f), - .clipped_n = 4, - }, - - /* Quad right edge outside of box. */ - { - .box = BOX (50.0f, 50.0f, 100.0f, 100.0f), - .polygon = QUAD(51.0f, 51.0f, 101.0f, 99.0f), - .clipped = QUAD(51.0f, 51.0f, 100.0f, 99.0f), - .clipped_n = 4, - }, - - /* Rotated quad with edges adjacent to box corners. */ - { - .box = BOX(50.0f, 50.0f, 100.0f, 100.0f), - .polygon = {{ 25.0f, 75.0f}, {75.0f, 25.0f}, - {125.0f, 75.0f}, {75.0f, 125.0f}}, - .clipped = QUAD(50.0f, 50.0f, 100.0f, 100.0f), - .clipped_n = 4, - }, - - /* Rotated quad with edges cutting out box corners. */ - { - .box = BOX(50.0f, 50.0f, 100.0f, 100.0f), - .polygon = {{ 37.5f, 75.0f}, { 75.0f, 37.5f}, - {112.5f, 75.0f}, { 75.0f, 112.5f}}, - .clipped = {{ 62.5f, 50.0f}, { 87.5f, 50.0f}, - {100.0f, 62.5f}, {100.0f, 87.5f}, - { 87.5f, 100.0f}, { 62.5f, 100.0f}, - { 50.0f, 87.5f}, { 50.0f, 62.5f}}, - .clipped_n = 8, - }, - - /* Same as above using counter-clockwise winding. */ - { - .box = BOX(50.0f, 50.0f, 100.0f, 100.0f), - .polygon = {{ 37.5f, 75.0f}, { 75.0f, 112.5f}, - {112.5f, 75.0f}, { 75.0f, 37.5f}}, - .clipped = {{ 62.5f, 50.0f}, { 50.0f, 62.5f}, - { 50.0f, 87.5f}, { 62.5f, 100.0f}, - { 87.5f, 100.0f}, {100.0f, 87.5f}, - {100.0f, 62.5f}, { 87.5f, 50.0f}}, - .clipped_n = 8, - }, -}; - -TEST_P(clip_expected, clip_expected_data) -{ - struct vertex_clip_test_data *tdata = data; - struct clipper_vertex clipped[8]; - int clipped_n; - - clipped_n = clipper_clip(tdata->polygon, tdata->box, clipped); - - assert_vertices(clipped, clipped_n, tdata->clipped, tdata->clipped_n); -} - /* clipper_quad_clip() tests: */ static const struct vertex_clip_test_data quad_clip_expected_data[] = { @@ -661,6 +573,89 @@ static const struct vertex_clip_test_data quad_clip_expected_data[] = { .clipped_n = 4, }, + /* General purpose clipper tests: */ + + /* Quad inside box. */ + { + .aligned = false, + .box = BOX (50.0f, 50.0f, 100.0f, 100.0f), + .polygon = QUAD(51.0f, 51.0f, 99.0f, 99.0f), + .clipped = QUAD(51.0f, 51.0f, 99.0f, 99.0f), + .clipped_n = 4, + }, + + /* Quad bottom edge outside of box. */ + { + .aligned = false, + .box = BOX (50.0f, 50.0f, 100.0f, 100.0f), + .polygon = QUAD(51.0f, 51.0f, 99.0f, 101.0f), + .clipped = QUAD(51.0f, 51.0f, 99.0f, 100.0f), + .clipped_n = 4, + }, + + /* Quad top edge outside of box. */ + { + .aligned = false, + .box = BOX (50.0f, 50.0f, 100.0f, 100.0f), + .polygon = QUAD(51.0f, 49.0f, 99.0f, 99.0f), + .clipped = QUAD(51.0f, 50.0f, 99.0f, 99.0f), + .clipped_n = 4, + }, + + /* Quad left edge outside of box. */ + { + .aligned = false, + .box = BOX (50.0f, 50.0f, 100.0f, 100.0f), + .polygon = QUAD(49.0f, 51.0f, 99.0f, 99.0f), + .clipped = QUAD(50.0f, 51.0f, 99.0f, 99.0f), + .clipped_n = 4, + }, + + /* Quad right edge outside of box. */ + { + .aligned = false, + .box = BOX (50.0f, 50.0f, 100.0f, 100.0f), + .polygon = QUAD(51.0f, 51.0f, 101.0f, 99.0f), + .clipped = QUAD(51.0f, 51.0f, 100.0f, 99.0f), + .clipped_n = 4, + }, + + /* Rotated quad with edges adjacent to box corners. */ + { + .aligned = false, + .box = BOX(50.0f, 50.0f, 100.0f, 100.0f), + .polygon = {{ 25.0f, 75.0f}, {75.0f, 25.0f}, + {125.0f, 75.0f}, {75.0f, 125.0f}}, + .clipped = QUAD(50.0f, 50.0f, 100.0f, 100.0f), + .clipped_n = 4, + }, + + /* Rotated quad with edges cutting out box corners. */ + { + .aligned = false, + .box = BOX(50.0f, 50.0f, 100.0f, 100.0f), + .polygon = {{ 37.5f, 75.0f}, { 75.0f, 37.5f}, + {112.5f, 75.0f}, { 75.0f, 112.5f}}, + .clipped = {{ 62.5f, 50.0f}, { 87.5f, 50.0f}, + {100.0f, 62.5f}, {100.0f, 87.5f}, + { 87.5f, 100.0f}, { 62.5f, 100.0f}, + { 50.0f, 87.5f}, { 50.0f, 62.5f}}, + .clipped_n = 8, + }, + + /* Same as above using counter-clockwise winding. */ + { + .aligned = false, + .box = BOX(50.0f, 50.0f, 100.0f, 100.0f), + .polygon = {{ 37.5f, 75.0f}, { 75.0f, 112.5f}, + {112.5f, 75.0f}, { 75.0f, 37.5f}}, + .clipped = {{ 62.5f, 50.0f}, { 50.0f, 62.5f}, + { 50.0f, 87.5f}, { 62.5f, 100.0f}, + { 87.5f, 100.0f}, {100.0f, 87.5f}, + {100.0f, 62.5f}, { 87.5f, 50.0f}}, + .clipped_n = 8, + }, + /* Miscellaneous cases: */ /* Box intersects entire same size aligned quad. */