Index: trunk/src/obj_poly.c =================================================================== --- trunk/src/obj_poly.c (revision 30832) +++ trunk/src/obj_poly.c (revision 30833) @@ -204,6 +204,78 @@ pcb_r_insert_entry(layer->polygon_tree, (pcb_box_t *) polygon); } +int pcb_poly_is_valid(pcb_poly_t *p) +{ + pcb_pline_t *contour = NULL; + pcb_polyarea_t *np1 = NULL, *np = NULL; + pcb_cardinal_t n; + pcb_vector_t v; + int res = 1; + + np1 = np = pcb_polyarea_create(); + if (np == NULL) + return 0; + + /* first make initial polygon contour */ + for (n = 0; n < p->PointN; n++) { + /* No current contour? Make a new one starting at point */ + /* (or) Add point to existing contour */ + + v[0] = p->Points[n].X; + v[1] = p->Points[n].Y; + if (contour == NULL) { + if ((contour = pcb_poly_contour_new(v)) == NULL) + goto err; + } + else { + pcb_poly_vertex_include(contour->head->prev, pcb_poly_node_create(v)); + } + + /* Is current point last in contour? If so process it. */ + if (n == p->PointN - 1) { + pcb_poly_contour_pre(contour, pcb_true); + + if (contour->Count == 0) { + pcb_poly_contours_free(&contour); + goto err; + } + + { /* count number of not-on-the-same-line vertices to make sure there's more than 2*/ + pcb_vnode_t *cur; + int r = 0; + + cur = contour->head; + do { + r++; + } while ((cur = cur->next) != contour->head); + if (r < 3) { + pcb_poly_contours_free(&contour); + goto err; + } + } + + /* make sure it is a positive contour (outer) or negative (hole) */ + if (contour->Flags.orient != PCB_PLF_DIR) { + pcb_poly_contour_inv(contour); + } + + pcb_polyarea_contour_include(np, contour); + if (contour->Count == 0) + goto err; + contour = NULL; + + if (!pcb_poly_valid(np)) + res = 0; + } + } + pcb_polyarea_free(&np1); + return res; + + err:; + pcb_polyarea_free(&np1); + return 0; +} + /*** undoable mirror ***/ static const char core_poly_cookie[] = "core-poly"; Index: trunk/src/obj_poly.h =================================================================== --- trunk/src/obj_poly.h (revision 30832) +++ trunk/src/obj_poly.h (revision 30833) @@ -95,6 +95,10 @@ double pcb_poly_area(const pcb_poly_t *poly); +/* Returns whether p is valid, without ever asserting */ +int pcb_poly_is_valid(pcb_poly_t *p); + + /* called from main.c to free some caches */ void pcb_poly_uninit(void); Index: trunk/src_plugins/io_bxl/read.c =================================================================== --- trunk/src_plugins/io_bxl/read.c (revision 30832) +++ trunk/src_plugins/io_bxl/read.c (revision 30833) @@ -482,85 +482,12 @@ pcb_poly_point_new(ctx->state.poly, x + ctx->state.origin_x, y + ctx->state.origin_y); } -static int poly_is_valid(pcb_poly_t *p) -{ - pcb_pline_t *contour = NULL; - pcb_polyarea_t *np1 = NULL, *np = NULL; - pcb_cardinal_t n; - pcb_vector_t v; - int res = 1; - - np1 = np = pcb_polyarea_create(); - if (np == NULL) - return 0; - - /* first make initial polygon contour */ - for (n = 0; n < p->PointN; n++) { - /* No current contour? Make a new one starting at point */ - /* (or) Add point to existing contour */ - - v[0] = p->Points[n].X; - v[1] = p->Points[n].Y; - if (contour == NULL) { - if ((contour = pcb_poly_contour_new(v)) == NULL) - goto err; - } - else { - pcb_poly_vertex_include(contour->head->prev, pcb_poly_node_create(v)); - } - - /* Is current point last in contour? If so process it. */ - if (n == p->PointN - 1) { - pcb_poly_contour_pre(contour, pcb_true); - - if (contour->Count == 0) { - pcb_poly_contours_free(&contour); - goto err; - } - - { /* count number of not-on-the-same-line vertices to make sure there's more than 2*/ - pcb_vnode_t *cur; - int r = 0; - - cur = contour->head; - do { - r++; - } while ((cur = cur->next) != contour->head); - if (r < 3) { - pcb_poly_contours_free(&contour); - goto err; - } - } - - /* make sure it is a positive contour (outer) or negative (hole) */ - if (contour->Flags.orient != PCB_PLF_DIR) { - pcb_poly_contour_inv(contour); - } - - pcb_polyarea_contour_include(np, contour); - if (contour->Count == 0) - goto err; - contour = NULL; - - if (!pcb_poly_valid(np)) - res = 0; - } - } - pcb_polyarea_free(&np1); - return res; - - err:; - pcb_polyarea_free(&np1); - return 0; -} - - void pcb_bxl_poly_end(pcb_bxl_ctx_t *ctx) { SKIP; assert(ctx->state.poly != NULL); - if (poly_is_valid(ctx->state.poly)) { + if (pcb_poly_is_valid(ctx->state.poly)) { pcb_add_poly_on_layer(ctx->state.layer, ctx->state.poly); /* pcb_poly_init_clip(ctx->subc->data, ctx->state.layer, ctx->state.poly);*/ }