Revision: 76252
          http://sourceforge.net/p/brlcad/code/76252
Author:   starseeker
Date:     2020-07-01 19:52:20 +0000 (Wed, 01 Jul 2020)
Log Message:
-----------
Push the polygon logic down into libbg

Modified Paths:
--------------
    brlcad/trunk/include/bg/CMakeLists.txt
    brlcad/trunk/include/bg/polygon.h
    brlcad/trunk/include/dm/bview.h
    brlcad/trunk/include/dm/bview_util.h
    brlcad/trunk/include/ged/view.h
    brlcad/trunk/src/libbg/CMakeLists.txt
    brlcad/trunk/src/libdm/CMakeLists.txt
    brlcad/trunk/src/libged/polyclip.cpp
    brlcad/trunk/src/libtclcad/tclcad_obj.c

Added Paths:
-----------
    brlcad/trunk/include/bg/polygon_types.h
    brlcad/trunk/src/libbg/polygon_op.cpp

Removed Paths:
-------------
    brlcad/trunk/src/libdm/bview_polygon.cpp

Modified: brlcad/trunk/include/bg/CMakeLists.txt
===================================================================
--- brlcad/trunk/include/bg/CMakeLists.txt      2020-07-01 18:14:45 UTC (rev 
76251)
+++ brlcad/trunk/include/bg/CMakeLists.txt      2020-07-01 19:52:20 UTC (rev 
76252)
@@ -5,6 +5,7 @@
   lseg.h
   obr.h
   polygon.h
+  polygon_types.h
   spsr.h
   tri_pt.h
   tri_ray.h

Modified: brlcad/trunk/include/bg/polygon.h
===================================================================
--- brlcad/trunk/include/bg/polygon.h   2020-07-01 18:14:45 UTC (rev 76251)
+++ brlcad/trunk/include/bg/polygon.h   2020-07-01 19:52:20 UTC (rev 76252)
@@ -32,10 +32,55 @@
 
 #include "common.h"
 #include "vmath.h"
+#include "bn/tol.h"
 #include "bg/defines.h"
+#include "bg/polygon_types.h"
 
 __BEGIN_DECLS
 
+/* TODO - the following are operations originally from libged - ultimately need
+ * to better integrate these and the other polygon routines.  For now, trying
+ * to get all the related logic in the same place so it is clearer what we do
+ * and don't have, and make what we do have easier to reuse. */
+
+BG_EXPORT fastf_t
+bg_find_polygon_area(
+       struct bg_polygon *gpoly,
+       fastf_t sf,
+       matp_t model2view,
+       fastf_t size
+       );
+
+BG_EXPORT int
+bg_polygons_overlap(
+       struct bg_polygon *polyA,
+       struct bg_polygon *polyB,
+       matp_t model2view,
+       struct bn_tol *tol,
+       fastf_t iscale
+       );
+
+BG_EXPORT struct bg_polygon *
+bg_clip_polygon(
+       bg_clip_t op,
+               struct bg_polygon *subj,
+               struct bg_polygon *clip,
+               fastf_t sf,
+               matp_t model2view,
+               matp_t view2model
+       );
+
+BG_EXPORT struct bg_polygon *
+bg_clip_polygons(
+       bg_clip_t op,
+               struct bg_polygons *subj,
+               struct bg_polygons *clip,
+               fastf_t sf,
+               matp_t model2view,
+               matp_t view2model
+       );
+
+
 /********************************
  * Operations on 2D point types *
  ********************************/

Added: brlcad/trunk/include/bg/polygon_types.h
===================================================================
--- brlcad/trunk/include/bg/polygon_types.h                             (rev 0)
+++ brlcad/trunk/include/bg/polygon_types.h     2020-07-01 19:52:20 UTC (rev 
76252)
@@ -0,0 +1,77 @@
+/*                 P O L Y G O N _ T Y P E S. H
+ * BRL-CAD
+ *
+ * Copyright (c) 2004-2020 United States Government as represented by
+ * the U.S. Army Research Laboratory.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * version 2.1 as published by the Free Software Foundation.
+ *
+ * This library is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this file; see the file named COPYING for more
+ * information.
+ */
+
+/*----------------------------------------------------------------------*/
+/* @file polygon_types.h */
+/** @addtogroup polygon */
+/** @{ */
+
+/**
+ *  @brief Functions for working with polygons
+ */
+
+#ifndef BG_POLYGON_TYPES_H
+#define BG_POLYGON_TYPES_H
+
+#include "common.h"
+#include "vmath.h"
+
+__BEGIN_DECLS
+
+/* The following data types are originally from bview - we keep them
+ * separate here to maximize their ease of reuse */
+typedef enum { bg_Union, bg_Difference, bg_Intersection, bg_Xor } bg_clip_t;
+
+struct bg_poly_contour {
+    size_t    num_points;
+    point_t   *point;               /* in model coordinates */
+};
+
+struct bg_polygon {
+    size_t                  num_contours;
+    int                     *hole;
+    struct bg_poly_contour  *contour;
+
+    // TODO - in principle these shouldn't be here, but the libtclcad code uses
+    // them so it will take some thought to refactor them up from this
+    // container...
+    int                 gp_color[3];
+    int                 gp_line_width;          /* in pixels */
+    int                 gp_line_style;
+};
+
+struct bg_polygons {
+    size_t            num_polygons;
+    struct bg_polygon *polygon;
+};
+
+__END_DECLS
+
+#endif  /* BG_POLYGON_TYPES_H */
+/** @} */
+/*
+ * Local Variables:
+ * mode: C
+ * tab-width: 8
+ * indent-tabs-mode: t
+ * c-file-style: "stroustrup"
+ * End:
+ * ex: shiftwidth=4 tabstop=8
+ */


Property changes on: brlcad/trunk/include/bg/polygon_types.h
___________________________________________________________________
Added: svn:eol-style
## -0,0 +1 ##
+native
\ No newline at end of property
Added: svn:mime-type
## -0,0 +1 ##
+text/plain
\ No newline at end of property
Modified: brlcad/trunk/include/dm/bview.h
===================================================================
--- brlcad/trunk/include/dm/bview.h     2020-07-01 18:14:45 UTC (rev 76251)
+++ brlcad/trunk/include/dm/bview.h     2020-07-01 19:52:20 UTC (rev 76252)
@@ -36,6 +36,7 @@
 #include "bu/list.h"
 #include "bu/vls.h"
 #include "bu/observer.h"
+#include "bg/polygon_types.h"
 #include "vmath.h"
 
 /** @{ */
@@ -166,28 +167,7 @@
     point_t   *gdls_points;             /* in model coordinates */
 };
 
-typedef enum { gctUnion, gctDifference, gctIntersection, gctXor } ClipType;
-
 typedef struct {
-    size_t    gpc_num_points;
-    point_t   *gpc_point;               /* in model coordinates */
-} bview_poly_contour;
-
-typedef struct {
-    size_t              gp_num_contours;
-    int                 gp_color[3];
-    int                 gp_line_width;          /* in pixels */
-    int                 gp_line_style;
-    int                 *gp_hole;
-    bview_poly_contour    *gp_contour;
-} bview_polygon;
-
-typedef struct {
-    size_t      gp_num_polygons;
-    bview_polygon *gp_polygon;
-} bview_polygons;
-
-typedef struct {
     int                 gdps_draw;
     int                 gdps_moveAll;
     int                 gdps_color[3];
@@ -198,13 +178,13 @@
     size_t              gdps_curr_polygon_i;
     size_t              gdps_curr_point_i;
     point_t             gdps_prev_point;
-    ClipType            gdps_clip_type;
+    bg_clip_t           gdps_clip_type;
     fastf_t             gdps_scale;
     point_t             gdps_origin;
     mat_t               gdps_rotation;
     mat_t               gdps_view2model;
     mat_t               gdps_model2view;
-    bview_polygons      gdps_polygons;
+    struct bg_polygons  gdps_polygons;
     fastf_t             gdps_data_vZ;
 } bview_data_polygon_state;
 

Modified: brlcad/trunk/include/dm/bview_util.h
===================================================================
--- brlcad/trunk/include/dm/bview_util.h        2020-07-01 18:14:45 UTC (rev 
76251)
+++ brlcad/trunk/include/dm/bview_util.h        2020-07-01 19:52:20 UTC (rev 
76252)
@@ -38,15 +38,6 @@
 
 DM_EXPORT void bview_update(struct bview *gvp);
 
-
-
-DM_EXPORT fastf_t find_polygon_area(bview_polygon *gpoly, fastf_t sf, matp_t 
model2view, fastf_t size);
-DM_EXPORT int polygons_overlap(bview_polygon *polyA, bview_polygon *polyB, 
matp_t model2view, struct bn_tol *tol, fastf_t iscale);
-DM_EXPORT bview_polygon *
-clip_polygon(ClipType op, bview_polygon *subj, bview_polygon *clip, fastf_t 
sf, matp_t model2view, matp_t view2model);
-DM_EXPORT bview_polygon *
-clip_polygons(ClipType op, bview_polygons *subj, bview_polygons *clip, fastf_t 
sf, matp_t model2view, matp_t view2model);
-
 __END_DECLS
 
 /** @} */

Modified: brlcad/trunk/include/ged/view.h
===================================================================
--- brlcad/trunk/include/ged/view.h     2020-07-01 18:14:45 UTC (rev 76251)
+++ brlcad/trunk/include/ged/view.h     2020-07-01 19:52:20 UTC (rev 76252)
@@ -30,6 +30,7 @@
 
 #include "common.h"
 #include "ged/defines.h"
+#include "bg/polygon.h"
 #include "ged/view/adc.h"
 #include "ged/view/matrix.h"
 #include "ged/view/select.h"
@@ -148,12 +149,10 @@
  */
 GED_EXPORT extern int ged_set_uplotOutputMode(struct ged *gedp, int argc, 
const char *argv[]);
 
-GED_EXPORT extern bview_polygon *ged_clip_polygon(ClipType op, bview_polygon 
*subj, bview_polygon *clip, fastf_t sf, matp_t model2view, matp_t view2model);
-GED_EXPORT extern bview_polygon *ged_clip_polygons(ClipType op, bview_polygons 
*subj, bview_polygons *clip, fastf_t sf, matp_t model2view, matp_t view2model);
 GED_EXPORT extern int ged_export_polygon(struct ged *gedp, 
bview_data_polygon_state *gdpsp, size_t polygon_i, const char *sname);
-GED_EXPORT extern bview_polygon *ged_import_polygon(struct ged *gedp, const 
char *sname);
-GED_EXPORT extern int ged_polygons_overlap(struct ged *gedp, bview_polygon 
*polyA, bview_polygon *polyB);
-GED_EXPORT extern void ged_polygon_fill_segments(struct ged *gedp, 
bview_polygon *poly, vect2d_t vfilldir, fastf_t vfilldelta);
+GED_EXPORT extern struct bg_polygon *ged_import_polygon(struct ged *gedp, 
const char *sname);
+GED_EXPORT extern int ged_polygons_overlap(struct ged *gedp, struct bg_polygon 
*polyA, struct bg_polygon *polyB);
+GED_EXPORT extern void ged_polygon_fill_segments(struct ged *gedp, struct 
bg_polygon *poly, vect2d_t vfilldir, fastf_t vfilldelta);
 
 // TODO - this (and probably the grid logic too) belong at the libdm level - 
they're operating
 // on the bview, rather than the ged level data...

Modified: brlcad/trunk/src/libbg/CMakeLists.txt
===================================================================
--- brlcad/trunk/src/libbg/CMakeLists.txt       2020-07-01 18:14:45 UTC (rev 
76251)
+++ brlcad/trunk/src/libbg/CMakeLists.txt       2020-07-01 19:52:20 UTC (rev 
76252)
@@ -19,6 +19,7 @@
   lseg_pt.c
   obr.c
   polygon.c
+  polygon_op.cpp
   polygon_triangulate.cpp
   polygon_point_in.c
   spsr.c

Added: brlcad/trunk/src/libbg/polygon_op.cpp
===================================================================
--- brlcad/trunk/src/libbg/polygon_op.cpp                               (rev 0)
+++ brlcad/trunk/src/libbg/polygon_op.cpp       2020-07-01 19:52:20 UTC (rev 
76252)
@@ -0,0 +1,644 @@
+/*                 P O L Y G O N _ O P . C P P
+ * BRL-CAD
+ *
+ * Copyright (c) 2020 United States Government as represented by
+ * the U.S. Army Research Laboratory.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * version 2.1 as published by the Free Software Foundation.
+ *
+ * This library is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this file; see the file named COPYING for more
+ * information.
+ */
+/** @file polygon_op.cpp
+ *
+ * Routines for operating on polygons.
+ *
+ */
+
+#include "common.h"
+
+#include "clipper.hpp"
+
+#include "vmath.h"
+#include "bu/log.h"
+#include "bu/malloc.h"
+#include "bn/mat.h"
+#include "bn/plane.h"
+#include "bg/defines.h"
+#include "bg/polygon.h"
+
+fastf_t
+bg_find_polygon_area(struct bg_polygon *gpoly, fastf_t sf, matp_t model2view, 
fastf_t size)
+{
+    size_t j, k, n;
+    ClipperLib::Polygon poly;
+    fastf_t area = 0.0;
+
+    if (NEAR_ZERO(sf, SMALL_FASTF))
+        return 0.0;
+
+    for (j = 0; j < gpoly->num_contours; ++j) {
+        n = gpoly->contour[j].num_points;
+        poly.resize(n);
+        for (k = 0; k < n; k++) {
+            point_t vpoint;
+
+            /* Convert to view coordinates */
+            MAT4X3PNT(vpoint, model2view, gpoly->contour[j].point[k]);
+
+            poly[k].X = (ClipperLib::long64)(vpoint[X] * sf);
+            poly[k].Y = (ClipperLib::long64)(vpoint[Y] * sf);
+        }
+
+        area += (fastf_t)ClipperLib::Area(poly);
+    }
+
+    sf = 1.0/(sf*sf) * size * size;
+
+    return (area * sf);
+}
+
+
+typedef struct {
+    size_t      pc_num_points;
+    point2d_t   *pc_point;
+} poly_contour_2d;
+
+typedef struct {
+    size_t              p_num_contours;
+    int                 *p_hole;
+    poly_contour_2d     *p_contour;
+} polygon_2d;
+
+int
+bg_polygons_overlap(struct bg_polygon *polyA, struct bg_polygon *polyB, matp_t 
model2view, struct bn_tol *tol, fastf_t iscale)
+{
+    size_t i, j;
+    size_t beginA, endA, beginB, endB;
+    fastf_t tol_dist;
+    fastf_t tol_dist_sq;
+    fastf_t scale;
+    polygon_2d polyA_2d;
+    polygon_2d polyB_2d;
+    point2d_t pt_2d;
+    point_t A;
+    size_t winding = 0;
+    int ret = 0;
+
+    if (polyA->num_contours < 1 || polyA->contour[0].num_points < 1 ||
+       polyB->num_contours < 1 || polyB->contour[0].num_points < 1)
+       return 0;
+
+    tol_dist = (tol->dist > 0.0) ? tol->dist : BN_TOL_DIST;
+    tol_dist_sq = (tol->dist_sq > 0.0) ? tol->dist_sq : tol_dist * tol_dist;
+    scale = (iscale > (fastf_t)UINT16_MAX) ? iscale : (fastf_t)UINT16_MAX;
+
+    /* Project polyA and polyB onto the view plane */
+    polyA_2d.p_num_contours = polyA->num_contours;
+    polyA_2d.p_hole = (int *)bu_calloc(polyA->num_contours, sizeof(int), 
"p_hole");
+    polyA_2d.p_contour = (poly_contour_2d *)bu_calloc(polyA->num_contours, 
sizeof(poly_contour_2d), "p_contour");
+
+    for (i = 0; i < polyA->num_contours; ++i) {
+       polyA_2d.p_hole[i] = polyA->hole[i];
+       polyA_2d.p_contour[i].pc_num_points = polyA->contour[i].num_points;
+       polyA_2d.p_contour[i].pc_point = (point2d_t 
*)bu_calloc(polyA->contour[i].num_points, sizeof(point2d_t), "pc_point");
+
+       for (j = 0; j < polyA->contour[i].num_points; ++j) {
+           point_t vpoint;
+
+           MAT4X3PNT(vpoint, model2view, polyA->contour[i].point[j]);
+           VSCALE(vpoint, vpoint, scale);
+           V2MOVE(polyA_2d.p_contour[i].pc_point[j], vpoint);
+       }
+    }
+
+    polyB_2d.p_num_contours = polyB->num_contours;
+    polyB_2d.p_hole = (int *)bu_calloc(polyB->num_contours, sizeof(int), 
"p_hole");
+    polyB_2d.p_contour = (poly_contour_2d *)bu_calloc(polyB->num_contours, 
sizeof(poly_contour_2d), "p_contour");
+
+    for (i = 0; i < polyB->num_contours; ++i) {
+       polyB_2d.p_hole[i] = polyB->hole[i];
+       polyB_2d.p_contour[i].pc_num_points = polyB->contour[i].num_points;
+       polyB_2d.p_contour[i].pc_point = (point2d_t 
*)bu_calloc(polyB->contour[i].num_points, sizeof(point2d_t), "pc_point");
+
+       for (j = 0; j < polyB->contour[i].num_points; ++j) {
+           point_t vpoint;
+
+           MAT4X3PNT(vpoint, model2view, polyB->contour[i].point[j]);
+           VSCALE(vpoint, vpoint, scale);
+           V2MOVE(polyB_2d.p_contour[i].pc_point[j], vpoint);
+       }
+    }
+
+    /*
+     * Check every line segment of polyA against every line segment of polyB.
+     * If there are any intersecting line segments, there exists an overlap.
+     */
+    for (i = 0; i < polyA_2d.p_num_contours; ++i) {
+       for (beginA = 0; beginA < polyA_2d.p_contour[i].pc_num_points; 
++beginA) {
+           vect2d_t dirA;
+
+           if (beginA == polyA_2d.p_contour[i].pc_num_points-1)
+               endA = 0;
+           else
+               endA = beginA + 1;
+
+           V2SUB2(dirA, polyA_2d.p_contour[i].pc_point[endA], 
polyA_2d.p_contour[i].pc_point[beginA]);
+
+           for (j = 0; j < polyB_2d.p_num_contours; ++j) {
+               for (beginB = 0; beginB < polyB_2d.p_contour[j].pc_num_points; 
++beginB) {
+                   vect2d_t distvec;
+                   vect2d_t dirB;
+
+                   if (beginB == polyB_2d.p_contour[j].pc_num_points-1)
+                       endB = 0;
+                   else
+                       endB = beginB + 1;
+
+                   V2SUB2(dirB, polyB_2d.p_contour[j].pc_point[endB], 
polyB_2d.p_contour[j].pc_point[beginB]);
+
+                   if (bn_isect_lseg2_lseg2(distvec,
+                                            
polyA_2d.p_contour[i].pc_point[beginA], dirA,
+                                            
polyB_2d.p_contour[j].pc_point[beginB], dirB,
+                                            tol) == 1) {
+                       /* Check to see if intersection is near an end point */
+                       if (!NEAR_EQUAL(distvec[0], 0.0, tol_dist_sq) &&
+                           !NEAR_EQUAL(distvec[0], 1.0, tol_dist_sq) &&
+                           !NEAR_EQUAL(distvec[1], 0.0, tol_dist_sq) &&
+                           !NEAR_EQUAL(distvec[1], 1.0, tol_dist_sq)) {
+                           ret = 1;
+                           goto end;
+                       }
+                   }
+               }
+           }
+       }
+    }
+
+    for (i = 0; i < polyB_2d.p_num_contours; ++i) {
+       size_t npts_on_contour = 0;
+       size_t npts_outside = 0;
+
+       /* Skip holes */
+       if (polyB_2d.p_hole[i])
+           continue;
+
+       /* Check if all points in the current polygon B contour are inside A */
+       for (beginB = 0; beginB < polyB_2d.p_contour[i].pc_num_points; 
++beginB) {
+           winding = 0;
+           V2MOVE(pt_2d, polyB_2d.p_contour[i].pc_point[beginB]);
+           V2MOVE(A, pt_2d);
+           A[2] = 0.0;
+
+           for (j = 0; j < polyA_2d.p_num_contours; ++j) {
+               point_t B, C;
+               vect_t BmA, CmA;
+               vect_t vcross;
+
+               for (beginA = 0; beginA < polyA_2d.p_contour[j].pc_num_points; 
++beginA) {
+                   fastf_t dot;
+
+                   if (beginA == polyA_2d.p_contour[j].pc_num_points-1)
+                       endA = 0;
+                   else
+                       endA = beginA + 1;
+
+                   if (V2NEAR_EQUAL(polyA_2d.p_contour[j].pc_point[beginA], 
pt_2d, tol_dist_sq) ||
+                       V2NEAR_EQUAL(polyA_2d.p_contour[j].pc_point[endA], 
pt_2d, tol_dist_sq)) {
+                       /* pt_2d is the same as one of the end points, so count 
it */
+                       ++npts_on_contour;
+
+                       if (polyA_2d.p_hole[j])
+                           winding = 0;
+                       else
+                           winding = 1;
+
+                       goto endA;
+                   }
+
+                   if ((polyA_2d.p_contour[j].pc_point[beginA][1] <= pt_2d[1] 
&&
+                        polyA_2d.p_contour[j].pc_point[endA][1] > pt_2d[1])) {
+                       V2MOVE(B, polyA_2d.p_contour[j].pc_point[endA]);
+                       B[2] = 0.0;
+                       V2MOVE(C, polyA_2d.p_contour[j].pc_point[beginA]);
+                       C[2] = 0.0;
+                   } else if ((polyA_2d.p_contour[j].pc_point[endA][1] <= 
pt_2d[1] &&
+                               polyA_2d.p_contour[j].pc_point[beginA][1] > 
pt_2d[1])) {
+                       V2MOVE(B, polyA_2d.p_contour[j].pc_point[beginA]);
+                       B[2] = 0.0;
+                       V2MOVE(C, polyA_2d.p_contour[j].pc_point[endA]);
+                       C[2] = 0.0;
+                   } else {
+                       /* check if the point is on a horizontal edge */
+                       if 
(NEAR_EQUAL(polyA_2d.p_contour[j].pc_point[beginA][1],
+                                      polyA_2d.p_contour[j].pc_point[endA][1], 
tol_dist_sq) &&
+                           
NEAR_EQUAL(polyA_2d.p_contour[j].pc_point[beginA][1], pt_2d[1], tol_dist_sq) &&
+                           ((polyA_2d.p_contour[j].pc_point[beginA][0] <= 
pt_2d[0] &&
+                             polyA_2d.p_contour[j].pc_point[endA][0] >= 
pt_2d[0]) ||
+                            (polyA_2d.p_contour[j].pc_point[endA][0] <= 
pt_2d[0] &&
+                             polyA_2d.p_contour[j].pc_point[beginA][0] >= 
pt_2d[0]))) {
+                           ++npts_on_contour;
+
+                           if (polyA_2d.p_hole[j])
+                               winding = 0;
+                           else
+                               winding = 1;
+
+                           goto endA;
+                       }
+
+                       continue;
+                   }
+
+                   VSUB2(BmA, B, A);
+                   VSUB2(CmA, C, A);
+                   VUNITIZE(BmA);
+                   VUNITIZE(CmA);
+                   dot = VDOT(BmA, CmA);
+
+                   if (NEAR_EQUAL(dot, -1.0, tol_dist_sq) || NEAR_EQUAL(dot, 
1.0, tol_dist_sq)) {
+                       ++npts_on_contour;
+
+                       if (polyA_2d.p_hole[j])
+                           winding = 0;
+                       else
+                           winding = 0;
+
+                       goto endA;
+                   }
+
+                   VCROSS(vcross, BmA, CmA);
+
+                   if (vcross[2] > 0)
+                       ++winding;
+               }
+           }
+
+       endA:
+           /* found a point on a polygon B contour that's outside of polygon A 
*/
+           if (!(winding%2)) {
+               ++npts_outside;
+               if (npts_outside != npts_on_contour) {
+                   break;
+               }
+           }
+       }
+
+       /* found a B polygon contour that's completely inside polygon A */
+       if (winding%2 || (npts_outside != 0 &&
+                         npts_outside != polyB_2d.p_contour[i].pc_num_points &&
+                         npts_outside == npts_on_contour)) {
+           ret = 1;
+           goto end;
+       }
+    }
+
+    for (i = 0; i < polyA_2d.p_num_contours; ++i) {
+       size_t npts_on_contour = 0;
+       size_t npts_outside = 0;
+
+       /* Skip holes */
+       if (polyA_2d.p_hole[i])
+           continue;
+
+       /* Check if all points in the current polygon A contour are inside B */
+       for (beginA = 0; beginA < polyA_2d.p_contour[i].pc_num_points; 
++beginA) {
+           winding = 0;
+           V2MOVE(pt_2d, polyA_2d.p_contour[i].pc_point[beginA]);
+           V2MOVE(A, pt_2d);
+           A[2] = 0.0;
+
+           for (j = 0; j < polyB_2d.p_num_contours; ++j) {
+               point_t B, C;
+               vect_t BmA, CmA;
+               vect_t vcross;
+
+               for (beginB = 0; beginB < polyB_2d.p_contour[j].pc_num_points; 
++beginB) {
+                   fastf_t dot;
+
+                   if (beginB == polyB_2d.p_contour[j].pc_num_points-1)
+                       endB = 0;
+                   else
+                       endB = beginB + 1;
+
+                   if (V2NEAR_EQUAL(polyB_2d.p_contour[j].pc_point[beginB], 
pt_2d, tol_dist_sq) ||
+                       V2NEAR_EQUAL(polyB_2d.p_contour[j].pc_point[endB], 
pt_2d, tol_dist_sq)) {
+                       /* pt_2d is the same as one of the end points, so count 
it */
+
+                       if (polyB_2d.p_hole[j])
+                           winding = 0;
+                       else
+                           winding = 1;
+
+                       ++npts_on_contour;
+                       goto endB;
+                   }
+
+                   if ((polyB_2d.p_contour[j].pc_point[beginB][1] <= pt_2d[1] 
&&
+                        polyB_2d.p_contour[j].pc_point[endB][1] > pt_2d[1])) {
+                       V2MOVE(B, polyB_2d.p_contour[j].pc_point[endB]);
+                       B[2] = 0.0;
+                       V2MOVE(C, polyB_2d.p_contour[j].pc_point[beginB]);
+                       C[2] = 0.0;
+                   } else if ((polyB_2d.p_contour[j].pc_point[endB][1] <= 
pt_2d[1] &&
+                               polyB_2d.p_contour[j].pc_point[beginB][1] > 
pt_2d[1])) {
+                       V2MOVE(B, polyB_2d.p_contour[j].pc_point[beginB]);
+                       B[2] = 0.0;
+                       V2MOVE(C, polyB_2d.p_contour[j].pc_point[endB]);
+                       C[2] = 0.0;
+                   } else {
+                       /* check if the point is on a horizontal edge */
+                       if 
(NEAR_EQUAL(polyB_2d.p_contour[j].pc_point[beginB][1],
+                                      polyB_2d.p_contour[j].pc_point[endB][1], 
tol_dist_sq) &&
+                           
NEAR_EQUAL(polyB_2d.p_contour[j].pc_point[beginB][1], pt_2d[1], tol_dist_sq) &&
+                           ((polyB_2d.p_contour[j].pc_point[beginB][0] <= 
pt_2d[0] &&
+                             polyB_2d.p_contour[j].pc_point[endB][0] >= 
pt_2d[0]) ||
+                            (polyB_2d.p_contour[j].pc_point[endB][0] <= 
pt_2d[0] &&
+                             polyB_2d.p_contour[j].pc_point[beginB][0] >= 
pt_2d[0]))) {
+                           if (polyB_2d.p_hole[j])
+                               winding = 0;
+                           else
+                               winding = 1;
+
+                           ++npts_on_contour;
+
+                           goto endB;
+                       }
+
+                       continue;
+                   }
+
+                   VSUB2(BmA, B, A);
+                   VSUB2(CmA, C, A);
+                   VUNITIZE(BmA);
+                   VUNITIZE(CmA);
+                   dot = VDOT(BmA, CmA);
+
+                   if (NEAR_EQUAL(dot, -1.0, tol_dist_sq) || NEAR_EQUAL(dot, 
1.0, tol_dist_sq)) {
+                       if (polyB_2d.p_hole[j])
+                           winding = 0;
+                       else
+                           winding = 1;
+
+                       ++npts_on_contour;
+                       goto endB;
+                   }
+
+                   VCROSS(vcross, BmA, CmA);
+
+                   if (vcross[2] > 0)
+                       ++winding;
+               }
+           }
+
+       endB:
+           /* found a point on a polygon A contour that's outside of polygon B 
*/
+           if (!(winding%2)) {
+               ++npts_outside;
+               if (npts_outside != npts_on_contour) {
+                   break;
+               }
+           }
+       }
+
+       /* found an A polygon contour that's completely inside polygon B */
+       if (winding%2 || (npts_outside != 0 &&
+                         npts_outside != polyA_2d.p_contour[i].pc_num_points &&
+                         npts_outside == npts_on_contour)) {
+           ret = 1;
+           break;
+       } else
+           ret = 0;
+    }
+
+end:
+
+    for (i = 0; i < polyA->num_contours; ++i)
+       bu_free((void *)polyA_2d.p_contour[i].pc_point, "pc_point");
+    for (i = 0; i < polyB->num_contours; ++i)
+       bu_free((void *)polyB_2d.p_contour[i].pc_point, "pc_point");
+
+    bu_free((void *)polyA_2d.p_hole, "p_hole");
+    bu_free((void *)polyA_2d.p_contour, "p_contour");
+    bu_free((void *)polyB_2d.p_hole, "p_hole");
+    bu_free((void *)polyB_2d.p_contour, "p_contour");
+
+    return ret;
+}
+
+
+typedef struct {
+    ClipperLib::long64 x;
+    ClipperLib::long64 y;
+} clipper_vertex;
+
+
+static fastf_t
+load_polygon(ClipperLib::Clipper &clipper, ClipperLib::PolyType ptype, struct 
bg_polygon *gpoly, fastf_t sf, matp_t mat)
+{
+    size_t j, k, n;
+    ClipperLib::Polygon curr_poly;
+    fastf_t vZ = 1.0;
+
+    for (j = 0; j < gpoly->num_contours; ++j) {
+       n = gpoly->contour[j].num_points;
+       curr_poly.resize(n);
+       for (k = 0; k < n; k++) {
+           point_t vpoint;
+
+           /* Convert to view coordinates */
+           MAT4X3PNT(vpoint, mat, gpoly->contour[j].point[k]);
+           vZ = vpoint[Z];
+
+           curr_poly[k].X = (ClipperLib::long64)(vpoint[X] * sf);
+           curr_poly[k].Y = (ClipperLib::long64)(vpoint[Y] * sf);
+       }
+
+       try {
+           clipper.AddPolygon(curr_poly, ptype);
+       } catch (...) {
+           bu_log("Exception thrown by clipper\n");
+       }
+    }
+
+    return vZ;
+}
+
+static fastf_t
+load_polygons(ClipperLib::Clipper &clipper, ClipperLib::PolyType ptype, struct 
bg_polygons *subj, fastf_t sf, matp_t mat)
+{
+    size_t i;
+    fastf_t vZ = 1.0;
+
+    for (i = 0; i < subj->num_polygons; ++i)
+       vZ = load_polygon(clipper, ptype, &subj->polygon[i], sf, mat);
+
+    return vZ;
+}
+
+/*
+ * Process/extract the clipper_polys into a struct bg_polygon.
+ */
+static struct bg_polygon *
+extract(ClipperLib::ExPolygons &clipper_polys, fastf_t sf, matp_t mat, fastf_t 
vZ)
+{
+    size_t i, j, k, n;
+    size_t num_contours = 0;
+    struct bg_polygon *result_poly;
+
+    /* Count up the number of contours. */
+    for (i = 0; i < clipper_polys.size(); ++i)
+       /* Add the outer and the holes */
+       num_contours += clipper_polys[i].holes.size() + 1;
+
+    BU_ALLOC(result_poly, struct bg_polygon);
+    result_poly->num_contours = num_contours;
+
+    if (num_contours < 1)
+       return result_poly;
+
+    result_poly->hole = (int *)bu_calloc(num_contours, sizeof(int), "hole");
+    result_poly->contour = (struct bg_poly_contour *)bu_calloc(num_contours, 
sizeof(struct bg_poly_contour), "contour");
+
+    n = 0;
+    for (i = 0; i < clipper_polys.size(); ++i) {
+       point_t vpoint;
+
+       result_poly->hole[n] = 0;
+       result_poly->contour[n].num_points = clipper_polys[i].outer.size();
+       result_poly->contour[n].point =
+           (point_t *)bu_calloc(result_poly->contour[n].num_points,
+                                sizeof(point_t), "point");
+
+       for (j = 0; j < result_poly->contour[n].num_points; ++j) {
+           VSET(vpoint, (fastf_t)(clipper_polys[i].outer[j].X) * sf, 
(fastf_t)(clipper_polys[i].outer[j].Y) * sf, vZ);
+
+           /* Convert to model coordinates */
+           MAT4X3PNT(result_poly->contour[n].point[j], mat, vpoint);
+       }
+
+       ++n;
+       for (j = 0; j < clipper_polys[i].holes.size(); ++j) {
+           result_poly->hole[n] = 1;
+           result_poly->contour[n].num_points = 
clipper_polys[i].holes[j].size();
+           result_poly->contour[n].point =
+               (point_t *)bu_calloc(result_poly->contour[n].num_points,
+                                    sizeof(point_t), "point");
+
+           for (k = 0; k < result_poly->contour[n].num_points; ++k) {
+               VSET(vpoint, (fastf_t)(clipper_polys[i].holes[j][k].X) * sf, 
(fastf_t)(clipper_polys[i].holes[j][k].Y) * sf, vZ);
+
+               /* Convert to model coordinates */
+               MAT4X3PNT(result_poly->contour[n].point[k], mat, vpoint);
+           }
+
+           ++n;
+       }
+    }
+
+    return result_poly;
+}
+
+
+struct bg_polygon *
+bg_clip_polygon(bg_clip_t op, struct bg_polygon *subj, struct bg_polygon 
*clip, fastf_t sf, matp_t model2view, matp_t view2model)
+{
+    fastf_t inv_sf;
+    fastf_t vZ;
+    ClipperLib::Clipper clipper;
+    ClipperLib::ExPolygons result_clipper_polys;
+    ClipperLib::ClipType ctOp;
+
+    /* need to scale the points up/down and then convert to/from long64 */
+    /* need a matrix to rotate into a plane */
+    /* need the inverse of the matrix above to put things back after clipping 
*/
+
+    /* Load subject polygon into clipper */
+    load_polygon(clipper, ClipperLib::ptSubject, subj, sf, model2view);
+
+    /* Load clip polygon into clipper */
+    vZ = load_polygon(clipper, ClipperLib::ptClip, clip, sf, model2view);
+
+    /* Convert op from BRL-CAD to Clipper */
+    switch (op) {
+    case bg_Intersection:
+       ctOp = ClipperLib::ctIntersection;
+       break;
+    case bg_Union:
+       ctOp = ClipperLib::ctUnion;
+       break;
+    case bg_Difference:
+       ctOp = ClipperLib::ctDifference;
+       break;
+    default:
+       ctOp = ClipperLib::ctXor;
+       break;
+    }
+
+    /* Clip'em */
+    clipper.Execute(ctOp, result_clipper_polys, ClipperLib::pftEvenOdd, 
ClipperLib::pftEvenOdd);
+
+    inv_sf = 1.0/sf;
+    return extract(result_clipper_polys, inv_sf, view2model, vZ);
+}
+
+
+struct bg_polygon *
+bg_clip_polygons(bg_clip_t op, struct bg_polygons *subj, struct bg_polygons 
*clip, fastf_t sf, matp_t model2view, matp_t view2model)
+{
+    fastf_t inv_sf;
+    fastf_t vZ;
+    ClipperLib::Clipper clipper;
+    ClipperLib::ExPolygons result_clipper_polys;
+    ClipperLib::ClipType ctOp;
+
+    /* need to scale the points up/down and then convert to/from long64 */
+    /* need a matrix to rotate into a plane */
+    /* need the inverse of the matrix above to put things back after clipping 
*/
+
+    /* Load subject polygons into clipper */
+    load_polygons(clipper, ClipperLib::ptSubject, subj, sf, model2view);
+
+    /* Load clip polygons into clipper */
+    vZ = load_polygons(clipper, ClipperLib::ptClip, clip, sf, model2view);
+
+    /* Convert op from BRL-CAD to Clipper */
+    switch (op) {
+    case bg_Intersection:
+       ctOp = ClipperLib::ctIntersection;
+       break;
+    case bg_Union:
+       ctOp = ClipperLib::ctUnion;
+       break;
+    case bg_Difference:
+       ctOp = ClipperLib::ctDifference;
+       break;
+    default:
+       ctOp = ClipperLib::ctXor;
+       break;
+    }
+
+    /* Clip'em */
+    clipper.Execute(ctOp, result_clipper_polys, ClipperLib::pftEvenOdd, 
ClipperLib::pftEvenOdd);
+
+    inv_sf = 1.0/sf;
+    return extract(result_clipper_polys, inv_sf, view2model, vZ);
+}
+
+/*
+ * Local Variables:
+ * tab-width: 8
+ * mode: C
+ * indent-tabs-mode: t
+ * c-file-style: "stroustrup"
+ * End:
+ * ex: shiftwidth=4 tabstop=8
+ */


Property changes on: brlcad/trunk/src/libbg/polygon_op.cpp
___________________________________________________________________
Added: svn:eol-style
## -0,0 +1 ##
+native
\ No newline at end of property
Added: svn:mime-type
## -0,0 +1 ##
+text/plain
\ No newline at end of property
Modified: brlcad/trunk/src/libdm/CMakeLists.txt
===================================================================
--- brlcad/trunk/src/libdm/CMakeLists.txt       2020-07-01 18:14:45 UTC (rev 
76251)
+++ brlcad/trunk/src/libdm/CMakeLists.txt       2020-07-01 19:52:20 UTC (rev 
76252)
@@ -61,7 +61,6 @@
   adc.c
   asize.c
   axes.c
-  bview_polygon.cpp
   bview_util.c
   clip.c
   dm-generic.c

Deleted: brlcad/trunk/src/libdm/bview_polygon.cpp
===================================================================
--- brlcad/trunk/src/libdm/bview_polygon.cpp    2020-07-01 18:14:45 UTC (rev 
76251)
+++ brlcad/trunk/src/libdm/bview_polygon.cpp    2020-07-01 19:52:20 UTC (rev 
76252)
@@ -1,647 +0,0 @@
-/*               B V I E W _ P O L Y G O N . C P P
- * BRL-CAD
- *
- * Copyright (c) 2020 United States Government as represented by
- * the U.S. Army Research Laboratory.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public License
- * version 2.1 as published by the Free Software Foundation.
- *
- * This library is distributed in the hope that it will be useful, but
- * WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this file; see the file named COPYING for more
- * information.
- */
-/** @file bview_polygon.cpp
- *
- * Routines for dealing with bview polygons.
- *
- * TODO - these data types and routines really should be pushed
- * down to libbg...
- *
- */
-
-#include "common.h"
-
-#include "clipper.hpp"
-
-#include "vmath.h"
-#include "bu/log.h"
-#include "bu/malloc.h"
-#include "bn/mat.h"
-#include "bn/plane.h"
-#include "dm/defines.h"
-#include "dm/bview_util.h"
-
-fastf_t
-find_polygon_area(bview_polygon *gpoly, fastf_t sf, matp_t model2view, fastf_t 
size)
-{
-    size_t j, k, n;
-    ClipperLib::Polygon poly;
-    fastf_t area = 0.0;
-
-    if (NEAR_ZERO(sf, SMALL_FASTF))
-        return 0.0;
-
-    for (j = 0; j < gpoly->gp_num_contours; ++j) {
-        n = gpoly->gp_contour[j].gpc_num_points;
-        poly.resize(n);
-        for (k = 0; k < n; k++) {
-            point_t vpoint;
-
-            /* Convert to view coordinates */
-            MAT4X3PNT(vpoint, model2view, gpoly->gp_contour[j].gpc_point[k]);
-
-            poly[k].X = (ClipperLib::long64)(vpoint[X] * sf);
-            poly[k].Y = (ClipperLib::long64)(vpoint[Y] * sf);
-        }
-
-        area += (fastf_t)ClipperLib::Area(poly);
-    }
-
-    sf = 1.0/(sf*sf) * size * size;
-
-    return (area * sf);
-}
-
-
-typedef struct {
-    size_t      pc_num_points;
-    point2d_t   *pc_point;
-} poly_contour_2d;
-
-typedef struct {
-    size_t              p_num_contours;
-    int                 *p_hole;
-    poly_contour_2d     *p_contour;
-} polygon_2d;
-
-int
-polygons_overlap(bview_polygon *polyA, bview_polygon *polyB, matp_t 
model2view, struct bn_tol *tol, fastf_t iscale)
-{
-    size_t i, j;
-    size_t beginA, endA, beginB, endB;
-    fastf_t tol_dist;
-    fastf_t tol_dist_sq;
-    fastf_t scale;
-    polygon_2d polyA_2d;
-    polygon_2d polyB_2d;
-    point2d_t pt_2d;
-    point_t A;
-    size_t winding = 0;
-    int ret = 0;
-
-    if (polyA->gp_num_contours < 1 || polyA->gp_contour[0].gpc_num_points < 1 
||
-       polyB->gp_num_contours < 1 || polyB->gp_contour[0].gpc_num_points < 1)
-       return 0;
-
-    tol_dist = (tol->dist > 0.0) ? tol->dist : BN_TOL_DIST;
-    tol_dist_sq = (tol->dist_sq > 0.0) ? tol->dist_sq : tol_dist * tol_dist;
-    scale = (iscale > (fastf_t)UINT16_MAX) ? iscale : (fastf_t)UINT16_MAX;
-
-    /* Project polyA and polyB onto the view plane */
-    polyA_2d.p_num_contours = polyA->gp_num_contours;
-    polyA_2d.p_hole = (int *)bu_calloc(polyA->gp_num_contours, sizeof(int), 
"p_hole");
-    polyA_2d.p_contour = (poly_contour_2d *)bu_calloc(polyA->gp_num_contours, 
sizeof(poly_contour_2d), "p_contour");
-
-    for (i = 0; i < polyA->gp_num_contours; ++i) {
-       polyA_2d.p_hole[i] = polyA->gp_hole[i];
-       polyA_2d.p_contour[i].pc_num_points = 
polyA->gp_contour[i].gpc_num_points;
-       polyA_2d.p_contour[i].pc_point = (point2d_t 
*)bu_calloc(polyA->gp_contour[i].gpc_num_points, sizeof(point2d_t), "pc_point");
-
-       for (j = 0; j < polyA->gp_contour[i].gpc_num_points; ++j) {
-           point_t vpoint;
-
-           MAT4X3PNT(vpoint, model2view, polyA->gp_contour[i].gpc_point[j]);
-           VSCALE(vpoint, vpoint, scale);
-           V2MOVE(polyA_2d.p_contour[i].pc_point[j], vpoint);
-       }
-    }
-
-    polyB_2d.p_num_contours = polyB->gp_num_contours;
-    polyB_2d.p_hole = (int *)bu_calloc(polyB->gp_num_contours, sizeof(int), 
"p_hole");
-    polyB_2d.p_contour = (poly_contour_2d *)bu_calloc(polyB->gp_num_contours, 
sizeof(poly_contour_2d), "p_contour");
-
-    for (i = 0; i < polyB->gp_num_contours; ++i) {
-       polyB_2d.p_hole[i] = polyB->gp_hole[i];
-       polyB_2d.p_contour[i].pc_num_points = 
polyB->gp_contour[i].gpc_num_points;
-       polyB_2d.p_contour[i].pc_point = (point2d_t 
*)bu_calloc(polyB->gp_contour[i].gpc_num_points, sizeof(point2d_t), "pc_point");
-
-       for (j = 0; j < polyB->gp_contour[i].gpc_num_points; ++j) {
-           point_t vpoint;
-
-           MAT4X3PNT(vpoint, model2view, polyB->gp_contour[i].gpc_point[j]);
-           VSCALE(vpoint, vpoint, scale);
-           V2MOVE(polyB_2d.p_contour[i].pc_point[j], vpoint);
-       }
-    }
-
-    /*
-     * Check every line segment of polyA against every line segment of polyB.
-     * If there are any intersecting line segments, there exists an overlap.
-     */
-    for (i = 0; i < polyA_2d.p_num_contours; ++i) {
-       for (beginA = 0; beginA < polyA_2d.p_contour[i].pc_num_points; 
++beginA) {
-           vect2d_t dirA;
-
-           if (beginA == polyA_2d.p_contour[i].pc_num_points-1)
-               endA = 0;
-           else
-               endA = beginA + 1;
-
-           V2SUB2(dirA, polyA_2d.p_contour[i].pc_point[endA], 
polyA_2d.p_contour[i].pc_point[beginA]);
-
-           for (j = 0; j < polyB_2d.p_num_contours; ++j) {
-               for (beginB = 0; beginB < polyB_2d.p_contour[j].pc_num_points; 
++beginB) {
-                   vect2d_t distvec;
-                   vect2d_t dirB;
-
-                   if (beginB == polyB_2d.p_contour[j].pc_num_points-1)
-                       endB = 0;
-                   else
-                       endB = beginB + 1;
-
-                   V2SUB2(dirB, polyB_2d.p_contour[j].pc_point[endB], 
polyB_2d.p_contour[j].pc_point[beginB]);
-
-                   if (bn_isect_lseg2_lseg2(distvec,
-                                            
polyA_2d.p_contour[i].pc_point[beginA], dirA,
-                                            
polyB_2d.p_contour[j].pc_point[beginB], dirB,
-                                            tol) == 1) {
-                       /* Check to see if intersection is near an end point */
-                       if (!NEAR_EQUAL(distvec[0], 0.0, tol_dist_sq) &&
-                           !NEAR_EQUAL(distvec[0], 1.0, tol_dist_sq) &&
-                           !NEAR_EQUAL(distvec[1], 0.0, tol_dist_sq) &&
-                           !NEAR_EQUAL(distvec[1], 1.0, tol_dist_sq)) {
-                           ret = 1;
-                           goto end;
-                       }
-                   }
-               }
-           }
-       }
-    }
-
-    for (i = 0; i < polyB_2d.p_num_contours; ++i) {
-       size_t npts_on_contour = 0;
-       size_t npts_outside = 0;
-
-       /* Skip holes */
-       if (polyB_2d.p_hole[i])
-           continue;
-
-       /* Check if all points in the current polygon B contour are inside A */
-       for (beginB = 0; beginB < polyB_2d.p_contour[i].pc_num_points; 
++beginB) {
-           winding = 0;
-           V2MOVE(pt_2d, polyB_2d.p_contour[i].pc_point[beginB]);
-           V2MOVE(A, pt_2d);
-           A[2] = 0.0;
-
-           for (j = 0; j < polyA_2d.p_num_contours; ++j) {
-               point_t B, C;
-               vect_t BmA, CmA;
-               vect_t vcross;
-
-               for (beginA = 0; beginA < polyA_2d.p_contour[j].pc_num_points; 
++beginA) {
-                   fastf_t dot;
-
-                   if (beginA == polyA_2d.p_contour[j].pc_num_points-1)
-                       endA = 0;
-                   else
-                       endA = beginA + 1;
-
-                   if (V2NEAR_EQUAL(polyA_2d.p_contour[j].pc_point[beginA], 
pt_2d, tol_dist_sq) ||
-                       V2NEAR_EQUAL(polyA_2d.p_contour[j].pc_point[endA], 
pt_2d, tol_dist_sq)) {
-                       /* pt_2d is the same as one of the end points, so count 
it */
-                       ++npts_on_contour;
-
-                       if (polyA_2d.p_hole[j])
-                           winding = 0;
-                       else
-                           winding = 1;
-
-                       goto endA;
-                   }
-
-                   if ((polyA_2d.p_contour[j].pc_point[beginA][1] <= pt_2d[1] 
&&
-                        polyA_2d.p_contour[j].pc_point[endA][1] > pt_2d[1])) {
-                       V2MOVE(B, polyA_2d.p_contour[j].pc_point[endA]);
-                       B[2] = 0.0;
-                       V2MOVE(C, polyA_2d.p_contour[j].pc_point[beginA]);
-                       C[2] = 0.0;
-                   } else if ((polyA_2d.p_contour[j].pc_point[endA][1] <= 
pt_2d[1] &&
-                               polyA_2d.p_contour[j].pc_point[beginA][1] > 
pt_2d[1])) {
-                       V2MOVE(B, polyA_2d.p_contour[j].pc_point[beginA]);
-                       B[2] = 0.0;
-                       V2MOVE(C, polyA_2d.p_contour[j].pc_point[endA]);
-                       C[2] = 0.0;
-                   } else {
-                       /* check if the point is on a horizontal edge */
-                       if 
(NEAR_EQUAL(polyA_2d.p_contour[j].pc_point[beginA][1],
-                                      polyA_2d.p_contour[j].pc_point[endA][1], 
tol_dist_sq) &&
-                           
NEAR_EQUAL(polyA_2d.p_contour[j].pc_point[beginA][1], pt_2d[1], tol_dist_sq) &&
-                           ((polyA_2d.p_contour[j].pc_point[beginA][0] <= 
pt_2d[0] &&
-                             polyA_2d.p_contour[j].pc_point[endA][0] >= 
pt_2d[0]) ||
-                            (polyA_2d.p_contour[j].pc_point[endA][0] <= 
pt_2d[0] &&
-                             polyA_2d.p_contour[j].pc_point[beginA][0] >= 
pt_2d[0]))) {
-                           ++npts_on_contour;
-
-                           if (polyA_2d.p_hole[j])
-                               winding = 0;
-                           else
-                               winding = 1;
-
-                           goto endA;
-                       }
-
-                       continue;
-                   }
-
-                   VSUB2(BmA, B, A);
-                   VSUB2(CmA, C, A);
-                   VUNITIZE(BmA);
-                   VUNITIZE(CmA);
-                   dot = VDOT(BmA, CmA);
-
-                   if (NEAR_EQUAL(dot, -1.0, tol_dist_sq) || NEAR_EQUAL(dot, 
1.0, tol_dist_sq)) {
-                       ++npts_on_contour;
-
-                       if (polyA_2d.p_hole[j])
-                           winding = 0;
-                       else
-                           winding = 0;
-
-                       goto endA;
-                   }
-
-                   VCROSS(vcross, BmA, CmA);
-
-                   if (vcross[2] > 0)
-                       ++winding;
-               }
-           }
-
-       endA:
-           /* found a point on a polygon B contour that's outside of polygon A 
*/
-           if (!(winding%2)) {
-               ++npts_outside;
-               if (npts_outside != npts_on_contour) {
-                   break;
-               }
-           }
-       }
-
-       /* found a B polygon contour that's completely inside polygon A */
-       if (winding%2 || (npts_outside != 0 &&
-                         npts_outside != polyB_2d.p_contour[i].pc_num_points &&
-                         npts_outside == npts_on_contour)) {
-           ret = 1;
-           goto end;
-       }
-    }
-
-    for (i = 0; i < polyA_2d.p_num_contours; ++i) {
-       size_t npts_on_contour = 0;
-       size_t npts_outside = 0;
-
-       /* Skip holes */
-       if (polyA_2d.p_hole[i])
-           continue;
-
-       /* Check if all points in the current polygon A contour are inside B */
-       for (beginA = 0; beginA < polyA_2d.p_contour[i].pc_num_points; 
++beginA) {
-           winding = 0;
-           V2MOVE(pt_2d, polyA_2d.p_contour[i].pc_point[beginA]);
-           V2MOVE(A, pt_2d);
-           A[2] = 0.0;
-
-           for (j = 0; j < polyB_2d.p_num_contours; ++j) {
-               point_t B, C;
-               vect_t BmA, CmA;
-               vect_t vcross;
-
-               for (beginB = 0; beginB < polyB_2d.p_contour[j].pc_num_points; 
++beginB) {
-                   fastf_t dot;
-
-                   if (beginB == polyB_2d.p_contour[j].pc_num_points-1)
-                       endB = 0;
-                   else
-                       endB = beginB + 1;
-
-                   if (V2NEAR_EQUAL(polyB_2d.p_contour[j].pc_point[beginB], 
pt_2d, tol_dist_sq) ||
-                       V2NEAR_EQUAL(polyB_2d.p_contour[j].pc_point[endB], 
pt_2d, tol_dist_sq)) {
-                       /* pt_2d is the same as one of the end points, so count 
it */
-
-                       if (polyB_2d.p_hole[j])
-                           winding = 0;
-                       else
-                           winding = 1;
-
-                       ++npts_on_contour;
-                       goto endB;
-                   }
-
-                   if ((polyB_2d.p_contour[j].pc_point[beginB][1] <= pt_2d[1] 
&&
-                        polyB_2d.p_contour[j].pc_point[endB][1] > pt_2d[1])) {
-                       V2MOVE(B, polyB_2d.p_contour[j].pc_point[endB]);
-                       B[2] = 0.0;
-                       V2MOVE(C, polyB_2d.p_contour[j].pc_point[beginB]);
-                       C[2] = 0.0;
-                   } else if ((polyB_2d.p_contour[j].pc_point[endB][1] <= 
pt_2d[1] &&
-                               polyB_2d.p_contour[j].pc_point[beginB][1] > 
pt_2d[1])) {
-                       V2MOVE(B, polyB_2d.p_contour[j].pc_point[beginB]);
-                       B[2] = 0.0;
-                       V2MOVE(C, polyB_2d.p_contour[j].pc_point[endB]);
-                       C[2] = 0.0;
-                   } else {
-                       /* check if the point is on a horizontal edge */
-                       if 
(NEAR_EQUAL(polyB_2d.p_contour[j].pc_point[beginB][1],
-                                      polyB_2d.p_contour[j].pc_point[endB][1], 
tol_dist_sq) &&
-                           
NEAR_EQUAL(polyB_2d.p_contour[j].pc_point[beginB][1], pt_2d[1], tol_dist_sq) &&
-                           ((polyB_2d.p_contour[j].pc_point[beginB][0] <= 
pt_2d[0] &&
-                             polyB_2d.p_contour[j].pc_point[endB][0] >= 
pt_2d[0]) ||
-                            (polyB_2d.p_contour[j].pc_point[endB][0] <= 
pt_2d[0] &&
-                             polyB_2d.p_contour[j].pc_point[beginB][0] >= 
pt_2d[0]))) {
-                           if (polyB_2d.p_hole[j])
-                               winding = 0;
-                           else
-                               winding = 1;
-
-                           ++npts_on_contour;
-
-                           goto endB;
-                       }
-
-                       continue;
-                   }
-
-                   VSUB2(BmA, B, A);
-                   VSUB2(CmA, C, A);
-                   VUNITIZE(BmA);
-                   VUNITIZE(CmA);
-                   dot = VDOT(BmA, CmA);
-
-                   if (NEAR_EQUAL(dot, -1.0, tol_dist_sq) || NEAR_EQUAL(dot, 
1.0, tol_dist_sq)) {
-                       if (polyB_2d.p_hole[j])
-                           winding = 0;
-                       else
-                           winding = 1;
-
-                       ++npts_on_contour;
-                       goto endB;
-                   }
-
-                   VCROSS(vcross, BmA, CmA);
-
-                   if (vcross[2] > 0)
-                       ++winding;
-               }
-           }
-
-       endB:
-           /* found a point on a polygon A contour that's outside of polygon B 
*/
-           if (!(winding%2)) {
-               ++npts_outside;
-               if (npts_outside != npts_on_contour) {
-                   break;
-               }
-           }
-       }
-
-       /* found an A polygon contour that's completely inside polygon B */
-       if (winding%2 || (npts_outside != 0 &&
-                         npts_outside != polyA_2d.p_contour[i].pc_num_points &&
-                         npts_outside == npts_on_contour)) {
-           ret = 1;
-           break;
-       } else
-           ret = 0;
-    }
-
-end:
-
-    for (i = 0; i < polyA->gp_num_contours; ++i)
-       bu_free((void *)polyA_2d.p_contour[i].pc_point, "pc_point");
-    for (i = 0; i < polyB->gp_num_contours; ++i)
-       bu_free((void *)polyB_2d.p_contour[i].pc_point, "pc_point");
-
-    bu_free((void *)polyA_2d.p_hole, "p_hole");
-    bu_free((void *)polyA_2d.p_contour, "p_contour");
-    bu_free((void *)polyB_2d.p_hole, "p_hole");
-    bu_free((void *)polyB_2d.p_contour, "p_contour");
-
-    return ret;
-}
-
-
-typedef struct {
-    ClipperLib::long64 x;
-    ClipperLib::long64 y;
-} clipper_vertex;
-
-
-static fastf_t
-load_polygon(ClipperLib::Clipper &clipper, ClipperLib::PolyType ptype, 
bview_polygon *gpoly, fastf_t sf, matp_t mat)
-{
-    size_t j, k, n;
-    ClipperLib::Polygon curr_poly;
-    fastf_t vZ = 1.0;
-
-    for (j = 0; j < gpoly->gp_num_contours; ++j) {
-       n = gpoly->gp_contour[j].gpc_num_points;
-       curr_poly.resize(n);
-       for (k = 0; k < n; k++) {
-           point_t vpoint;
-
-           /* Convert to view coordinates */
-           MAT4X3PNT(vpoint, mat, gpoly->gp_contour[j].gpc_point[k]);
-           vZ = vpoint[Z];
-
-           curr_poly[k].X = (ClipperLib::long64)(vpoint[X] * sf);
-           curr_poly[k].Y = (ClipperLib::long64)(vpoint[Y] * sf);
-       }
-
-       try {
-           clipper.AddPolygon(curr_poly, ptype);
-       } catch (...) {
-           bu_log("Exception thrown by clipper\n");
-       }
-    }
-
-    return vZ;
-}
-
-static fastf_t
-load_polygons(ClipperLib::Clipper &clipper, ClipperLib::PolyType ptype, 
bview_polygons *subj, fastf_t sf, matp_t mat)
-{
-    size_t i;
-    fastf_t vZ = 1.0;
-
-    for (i = 0; i < subj->gp_num_polygons; ++i)
-       vZ = load_polygon(clipper, ptype, &subj->gp_polygon[i], sf, mat);
-
-    return vZ;
-}
-
-/*
- * Process/extract the clipper_polys into a bview_polygon.
- */
-static bview_polygon *
-extract(ClipperLib::ExPolygons &clipper_polys, fastf_t sf, matp_t mat, fastf_t 
vZ)
-{
-    size_t i, j, k, n;
-    size_t num_contours = 0;
-    bview_polygon *result_poly;
-
-    /* Count up the number of contours. */
-    for (i = 0; i < clipper_polys.size(); ++i)
-       /* Add the outer and the holes */
-       num_contours += clipper_polys[i].holes.size() + 1;
-
-    BU_ALLOC(result_poly, bview_polygon);
-    result_poly->gp_num_contours = num_contours;
-
-    if (num_contours < 1)
-       return result_poly;
-
-    result_poly->gp_hole = (int *)bu_calloc(num_contours, sizeof(int), 
"gp_hole");
-    result_poly->gp_contour = (bview_poly_contour *)bu_calloc(num_contours, 
sizeof(bview_poly_contour), "gp_contour");
-
-    n = 0;
-    for (i = 0; i < clipper_polys.size(); ++i) {
-       point_t vpoint;
-
-       result_poly->gp_hole[n] = 0;
-       result_poly->gp_contour[n].gpc_num_points = 
clipper_polys[i].outer.size();
-       result_poly->gp_contour[n].gpc_point =
-           (point_t *)bu_calloc(result_poly->gp_contour[n].gpc_num_points,
-                                sizeof(point_t), "gpc_point");
-
-       for (j = 0; j < result_poly->gp_contour[n].gpc_num_points; ++j) {
-           VSET(vpoint, (fastf_t)(clipper_polys[i].outer[j].X) * sf, 
(fastf_t)(clipper_polys[i].outer[j].Y) * sf, vZ);
-
-           /* Convert to model coordinates */
-           MAT4X3PNT(result_poly->gp_contour[n].gpc_point[j], mat, vpoint);
-       }
-
-       ++n;
-       for (j = 0; j < clipper_polys[i].holes.size(); ++j) {
-           result_poly->gp_hole[n] = 1;
-           result_poly->gp_contour[n].gpc_num_points = 
clipper_polys[i].holes[j].size();
-           result_poly->gp_contour[n].gpc_point =
-               (point_t *)bu_calloc(result_poly->gp_contour[n].gpc_num_points,
-                                    sizeof(point_t), "gpc_point");
-
-           for (k = 0; k < result_poly->gp_contour[n].gpc_num_points; ++k) {
-               VSET(vpoint, (fastf_t)(clipper_polys[i].holes[j][k].X) * sf, 
(fastf_t)(clipper_polys[i].holes[j][k].Y) * sf, vZ);
-
-               /* Convert to model coordinates */
-               MAT4X3PNT(result_poly->gp_contour[n].gpc_point[k], mat, vpoint);
-           }
-
-           ++n;
-       }
-    }
-
-    return result_poly;
-}
-
-
-bview_polygon *
-clip_polygon(ClipType op, bview_polygon *subj, bview_polygon *clip, fastf_t 
sf, matp_t model2view, matp_t view2model)
-{
-    fastf_t inv_sf;
-    fastf_t vZ;
-    ClipperLib::Clipper clipper;
-    ClipperLib::ExPolygons result_clipper_polys;
-    ClipperLib::ClipType ctOp;
-
-    /* need to scale the points up/down and then convert to/from long64 */
-    /* need a matrix to rotate into a plane */
-    /* need the inverse of the matrix above to put things back after clipping 
*/
-
-    /* Load subject polygon into clipper */
-    load_polygon(clipper, ClipperLib::ptSubject, subj, sf, model2view);
-
-    /* Load clip polygon into clipper */
-    vZ = load_polygon(clipper, ClipperLib::ptClip, clip, sf, model2view);
-
-    /* Convert op from BRL-CAD to Clipper */
-    switch (op) {
-    case gctIntersection:
-       ctOp = ClipperLib::ctIntersection;
-       break;
-    case gctUnion:
-       ctOp = ClipperLib::ctUnion;
-       break;
-    case gctDifference:
-       ctOp = ClipperLib::ctDifference;
-       break;
-    default:
-       ctOp = ClipperLib::ctXor;
-       break;
-    }
-
-    /* Clip'em */
-    clipper.Execute(ctOp, result_clipper_polys, ClipperLib::pftEvenOdd, 
ClipperLib::pftEvenOdd);
-
-    inv_sf = 1.0/sf;
-    return extract(result_clipper_polys, inv_sf, view2model, vZ);
-}
-
-
-bview_polygon *
-clip_polygons(ClipType op, bview_polygons *subj, bview_polygons *clip, fastf_t 
sf, matp_t model2view, matp_t view2model)
-{
-    fastf_t inv_sf;
-    fastf_t vZ;
-    ClipperLib::Clipper clipper;
-    ClipperLib::ExPolygons result_clipper_polys;
-    ClipperLib::ClipType ctOp;
-
-    /* need to scale the points up/down and then convert to/from long64 */
-    /* need a matrix to rotate into a plane */
-    /* need the inverse of the matrix above to put things back after clipping 
*/
-
-    /* Load subject polygons into clipper */
-    load_polygons(clipper, ClipperLib::ptSubject, subj, sf, model2view);
-
-    /* Load clip polygons into clipper */
-    vZ = load_polygons(clipper, ClipperLib::ptClip, clip, sf, model2view);
-
-    /* Convert op from BRL-CAD to Clipper */
-    switch (op) {
-    case gctIntersection:
-       ctOp = ClipperLib::ctIntersection;
-       break;
-    case gctUnion:
-       ctOp = ClipperLib::ctUnion;
-       break;
-    case gctDifference:
-       ctOp = ClipperLib::ctDifference;
-       break;
-    default:
-       ctOp = ClipperLib::ctXor;
-       break;
-    }
-
-    /* Clip'em */
-    clipper.Execute(ctOp, result_clipper_polys, ClipperLib::pftEvenOdd, 
ClipperLib::pftEvenOdd);
-
-    inv_sf = 1.0/sf;
-    return extract(result_clipper_polys, inv_sf, view2model, vZ);
-}
-
-/*
- * Local Variables:
- * tab-width: 8
- * mode: C
- * indent-tabs-mode: t
- * c-file-style: "stroustrup"
- * End:
- * ex: shiftwidth=4 tabstop=8
- */

Modified: brlcad/trunk/src/libged/polyclip.cpp
===================================================================
--- brlcad/trunk/src/libged/polyclip.cpp        2020-07-01 18:14:45 UTC (rev 
76251)
+++ brlcad/trunk/src/libged/polyclip.cpp        2020-07-01 19:52:20 UTC (rev 
76252)
@@ -29,6 +29,7 @@
 #include "common.h"
 
 #include "bu/sort.h"
+#include "bg/polygon.h"
 #include "dm/bview_util.h"
 #include "ged.h"
 
@@ -48,12 +49,12 @@
     GED_CHECK_EXISTS(gedp, sname, LOOKUP_QUIET, GED_ERROR);
     RT_DB_INTERNAL_INIT(&internal);
 
-    if (polygon_i >= gdpsp->gdps_polygons.gp_num_polygons ||
-       gdpsp->gdps_polygons.gp_polygon[polygon_i].gp_num_contours < 1)
+    if (polygon_i >= gdpsp->gdps_polygons.num_polygons ||
+       gdpsp->gdps_polygons.polygon[polygon_i].num_contours < 1)
        return GED_ERROR;
 
-    for (j = 0; j < 
gdpsp->gdps_polygons.gp_polygon[polygon_i].gp_num_contours; ++j)
-       num_verts += 
gdpsp->gdps_polygons.gp_polygon[polygon_i].gp_contour[j].gpc_num_points;
+    for (j = 0; j < gdpsp->gdps_polygons.polygon[polygon_i].num_contours; ++j)
+       num_verts += 
gdpsp->gdps_polygons.polygon[polygon_i].contour[j].num_points;
 
     if (num_verts < 3)
        return GED_ERROR;
@@ -90,14 +91,14 @@
     MAT4X3PNT(sketch_ip->V, gdpsp->gdps_view2model, vorigin);
 
     n = 0;
-    for (j = 0; j < 
gdpsp->gdps_polygons.gp_polygon[polygon_i].gp_num_contours; ++j) {
+    for (j = 0; j < gdpsp->gdps_polygons.polygon[polygon_i].num_contours; ++j) 
{
        size_t cstart = n;
 
-       for (k = 0; k < 
gdpsp->gdps_polygons.gp_polygon[polygon_i].gp_contour[j].gpc_num_points; ++k) {
+       for (k = 0; k < 
gdpsp->gdps_polygons.polygon[polygon_i].contour[j].num_points; ++k) {
            point_t vpt;
            vect_t vdiff;
 
-           MAT4X3PNT(vpt, gdpsp->gdps_model2view, 
gdpsp->gdps_polygons.gp_polygon[polygon_i].gp_contour[j].gpc_point[k]);
+           MAT4X3PNT(vpt, gdpsp->gdps_model2view, 
gdpsp->gdps_polygons.polygon[polygon_i].contour[j].point[k]);
            VSUB2(vdiff, vpt, vorigin);
            VSCALE(vdiff, vdiff, gdpsp->gdps_scale);
            V2MOVE(sketch_ip->verts[n], vdiff);
@@ -143,7 +144,7 @@
     struct bu_list head;
 };
 
-bview_polygon *
+struct bg_polygon *
 ged_import_polygon(struct ged *gedp, const char *sname)
 {
     size_t j, n;
@@ -155,15 +156,15 @@
     struct segment_node *all_segment_nodes;
     struct segment_node *curr_snode;
     struct contour_node *curr_cnode;
-    bview_polygon *gpp;
+    struct bg_polygon *gpp;
 
     if (wdb_import_from_path(gedp->ged_result_str, &intern, sname, 
gedp->ged_wdbp) == GED_ERROR)
-       return (bview_polygon *)0;
+       return (struct bg_polygon *)0;
 
     sketch_ip = (rt_sketch_internal *)intern.idb_ptr;
     if (sketch_ip->vert_count < 3 || sketch_ip->curve.count < 1) {
        rt_db_free_internal(&intern);
-       return (bview_polygon *)0;
+       return (struct bg_polygon *)0;
     }
 
     all_segment_nodes = (struct segment_node 
*)bu_calloc(sketch_ip->curve.count, sizeof(struct segment_node), 
"all_segment_nodes");
@@ -225,10 +226,10 @@
        }
     }
 
-    BU_ALLOC(gpp, bview_polygon);
-    gpp->gp_num_contours = ncontours;
-    gpp->gp_hole = (int *)bu_calloc(ncontours, sizeof(int), "gp_hole");
-    gpp->gp_contour = (bview_poly_contour *)bu_calloc(ncontours, 
sizeof(bview_poly_contour), "gp_contour");
+    BU_ALLOC(gpp, struct bg_polygon);
+    gpp->num_contours = ncontours;
+    gpp->hole = (int *)bu_calloc(ncontours, sizeof(int), "gp_hole");
+    gpp->contour = (struct bg_poly_contour *)bu_calloc(ncontours, 
sizeof(struct bg_poly_contour), "gp_contour");
 
     j = 0;
     while (BU_LIST_NON_EMPTY(&HeadContourNodes)) {
@@ -243,8 +244,8 @@
        for (BU_LIST_FOR(curr_snode, segment_node, &curr_cnode->head))
            ++npoints;
 
-       gpp->gp_contour[j].gpc_num_points = npoints;
-       gpp->gp_contour[j].gpc_point = (point_t *)bu_calloc(npoints, 
sizeof(point_t), "gpc_point");
+       gpp->contour[j].num_points = npoints;
+       gpp->contour[j].point = (point_t *)bu_calloc(npoints, sizeof(point_t), 
"gpc_point");
 
        while (BU_LIST_NON_EMPTY(&curr_cnode->head)) {
            curr_snode = BU_LIST_FIRST(segment_node, &curr_cnode->head);
@@ -253,7 +254,7 @@
            curr_lsg = (struct line_seg *)curr_snode->segment;
 
            /* Convert from UV space to model space */
-           VJOIN2(gpp->gp_contour[j].gpc_point[k], sketch_ip->V,
+           VJOIN2(gpp->contour[j].point[k], sketch_ip->V,
                   sketch_ip->verts[curr_lsg->start][0], sketch_ip->u_vec,
                   sketch_ip->verts[curr_lsg->start][1], sketch_ip->v_vec);
            ++k;
@@ -285,12 +286,12 @@
 
 
 int
-ged_polygons_overlap(struct ged *gedp, bview_polygon *polyA, bview_polygon 
*polyB)
+ged_polygons_overlap(struct ged *gedp, struct bg_polygon *polyA, struct 
bg_polygon *polyB)
 {
     GED_CHECK_DATABASE_OPEN(gedp, GED_ERROR);
     GED_CHECK_VIEW(gedp, GED_ERROR);
 
-    return polygons_overlap(polyA, polyB, gedp->ged_gvp->gv_model2view, 
&gedp->ged_wdbp->wdb_tol, gedp->ged_gvp->gv_scale);
+    return bg_polygons_overlap(polyA, polyB, gedp->ged_gvp->gv_model2view, 
&gedp->ged_wdbp->wdb_tol, gedp->ged_gvp->gv_scale);
 }
 
 HIDDEN int
@@ -312,7 +313,7 @@
 
 
 void
-ged_polygon_fill_segments(struct ged *gedp, bview_polygon *poly, vect2d_t 
vfilldir, fastf_t vfilldelta)
+ged_polygon_fill_segments(struct ged *gedp, struct bg_polygon *poly, vect2d_t 
vfilldir, fastf_t vfilldelta)
 {
     size_t i, j;
     fastf_t vx, vy, vZ = 0.0;
@@ -334,7 +335,7 @@
     /* initialize result */
     bu_vls_trunc(gedp->ged_result_str, 0);
 
-    if (poly->gp_num_contours < 1 || poly->gp_contour[0].gpc_num_points < 3)
+    if (poly->num_contours < 1 || poly->contour[0].num_points < 3)
        return;
 
     if (vfilldelta < 0)
@@ -344,19 +345,19 @@
     final_isect2 = (point2d_t *)bu_calloc(isectSize, sizeof(point2d_t), 
"final_isect2");
 
     /* Project poly onto the view plane */
-    poly_2d.p_num_contours = poly->gp_num_contours;
-    poly_2d.p_hole = (int *)bu_calloc(poly->gp_num_contours, sizeof(int), 
"p_hole");
-    poly_2d.p_contour = (poly_contour_2d *)bu_calloc(poly->gp_num_contours, 
sizeof(poly_contour_2d), "p_contour");
+    poly_2d.p_num_contours = poly->num_contours;
+    poly_2d.p_hole = (int *)bu_calloc(poly->num_contours, sizeof(int), 
"p_hole");
+    poly_2d.p_contour = (poly_contour_2d *)bu_calloc(poly->num_contours, 
sizeof(poly_contour_2d), "p_contour");
 
-    for (i = 0; i < poly->gp_num_contours; ++i) {
-       poly_2d.p_hole[i] = poly->gp_hole[i];
-       poly_2d.p_contour[i].pc_num_points = poly->gp_contour[i].gpc_num_points;
-       poly_2d.p_contour[i].pc_point = (point2d_t 
*)bu_calloc(poly->gp_contour[i].gpc_num_points, sizeof(point2d_t), "pc_point");
+    for (i = 0; i < poly->num_contours; ++i) {
+       poly_2d.p_hole[i] = poly->hole[i];
+       poly_2d.p_contour[i].pc_num_points = poly->contour[i].num_points;
+       poly_2d.p_contour[i].pc_point = (point2d_t 
*)bu_calloc(poly->contour[i].num_points, sizeof(point2d_t), "pc_point");
 
-       for (j = 0; j < poly->gp_contour[i].gpc_num_points; ++j) {
+       for (j = 0; j < poly->contour[i].num_points; ++j) {
            point_t vpoint;
 
-           MAT4X3PNT(vpoint, gedp->ged_gvp->gv_model2view, 
poly->gp_contour[i].gpc_point[j]);
+           MAT4X3PNT(vpoint, gedp->ged_gvp->gv_model2view, 
poly->contour[i].point[j]);
            V2MOVE(poly_2d.p_contour[i].pc_point[j], vpoint);
            vZ = vpoint[Z];
        }

Modified: brlcad/trunk/src/libtclcad/tclcad_obj.c
===================================================================
--- brlcad/trunk/src/libtclcad/tclcad_obj.c     2020-07-01 18:14:45 UTC (rev 
76251)
+++ brlcad/trunk/src/libtclcad/tclcad_obj.c     2020-07-01 19:52:20 UTC (rev 
76252)
@@ -3713,55 +3713,55 @@
 
 /* These functions should be macros */
 HIDDEN void
-to_polygon_free(bview_polygon *gpp)
+to_polygon_free(struct bg_polygon *gpp)
 {
     register size_t j;
 
-    if (gpp->gp_num_contours == 0)
+    if (gpp->num_contours == 0)
        return;
 
-    for (j = 0; j < gpp->gp_num_contours; ++j)
-       if (gpp->gp_contour[j].gpc_num_points > 0)
-           bu_free((void *)gpp->gp_contour[j].gpc_point, "gp_contour points");
+    for (j = 0; j < gpp->num_contours; ++j)
+       if (gpp->contour[j].num_points > 0)
+           bu_free((void *)gpp->contour[j].point, "contour points");
 
-    bu_free((void *)gpp->gp_contour, "gp_contour");
-    bu_free((void *)gpp->gp_hole, "gp_hole");
-    gpp->gp_num_contours = 0;
+    bu_free((void *)gpp->contour, "contour");
+    bu_free((void *)gpp->hole, "hole");
+    gpp->num_contours = 0;
 }
 
 
 HIDDEN void
-to_polygons_free(bview_polygons *gpp)
+to_polygons_free(struct bg_polygons *gpp)
 {
     register size_t i;
 
-    if (gpp->gp_num_polygons == 0)
+    if (gpp->num_polygons == 0)
        return;
 
-    for (i = 0; i < gpp->gp_num_polygons; ++i) {
-       to_polygon_free(&gpp->gp_polygon[i]);
+    for (i = 0; i < gpp->num_polygons; ++i) {
+       to_polygon_free(&gpp->polygon[i]);
     }
 
-    bu_free((void *)gpp->gp_polygon, "data polygons");
-    gpp->gp_polygon = (bview_polygon *)0;
-    gpp->gp_num_polygons = 0;
+    bu_free((void *)gpp->polygon, "data polygons");
+    gpp->polygon = (struct bg_polygon *)0;
+    gpp->num_polygons = 0;
 }
 
 
 HIDDEN int
-to_extract_contours_av(Tcl_Interp *interp, struct ged *gedp, struct 
ged_dm_view *gdvp, bview_polygon *gpp, size_t contour_ac, const char 
**contour_av, int mode, int vflag)
+to_extract_contours_av(Tcl_Interp *interp, struct ged *gedp, struct 
ged_dm_view *gdvp, struct bg_polygon *gpp, size_t contour_ac, const char 
**contour_av, int mode, int vflag)
 {
     register size_t j = 0, k = 0;
 
-    gpp->gp_num_contours = contour_ac;
-    gpp->gp_hole = NULL;
-    gpp->gp_contour = NULL;
+    gpp->num_contours = contour_ac;
+    gpp->hole = NULL;
+    gpp->contour = NULL;
 
     if (contour_ac == 0)
        return GED_OK;
 
-    gpp->gp_hole = (int *)bu_calloc(contour_ac, sizeof(int), "gp_hole");
-    gpp->gp_contour = (bview_poly_contour *)bu_calloc(contour_ac, 
sizeof(bview_poly_contour), "gp_contour");
+    gpp->hole = (int *)bu_calloc(contour_ac, sizeof(int), "hole");
+    gpp->contour = (struct bg_poly_contour *)bu_calloc(contour_ac, 
sizeof(struct bg_poly_contour), "contour");
 
     for (j = 0; j < contour_ac; ++j) {
        int ac;
@@ -3783,8 +3783,8 @@
            return GED_ERROR;
        }
 
-       gpp->gp_contour[j].gpc_num_points = point_ac - 1;
-       gpp->gp_contour[j].gpc_point = (point_t *)bu_calloc(point_ac, 
sizeof(point_t), "gpc_point");
+       gpp->contour[j].num_points = point_ac - 1;
+       gpp->contour[j].point = (point_t *)bu_calloc(point_ac, sizeof(point_t), 
"point");
 
        if (bu_sscanf(point_av[0], "%d", &hole) != 1) {
            bu_vls_printf(gedp->ged_result_str, "contour %zu, point %zu: bad 
hole flag - %s\n",
@@ -3792,7 +3792,7 @@
            Tcl_Free((char *)point_av);
            return GED_ERROR;
        }
-       gpp->gp_hole[j] = hole;
+       gpp->hole[j] = hole;
 
        for (k = 1; k < point_ac; ++k) {
            double pt[ELEMENTS_PER_POINT]; /* must be double for scanf */
@@ -3805,9 +3805,9 @@
            }
 
            if (vflag) {
-               MAT4X3PNT(gpp->gp_contour[j].gpc_point[k-1], 
gdvp->gdv_view->gv_view2model, pt);
+               MAT4X3PNT(gpp->contour[j].point[k-1], 
gdvp->gdv_view->gv_view2model, pt);
            } else {
-               VMOVE(gpp->gp_contour[j].gpc_point[k-1], pt);
+               VMOVE(gpp->contour[j].point[k-1], pt);
            }
 
        }
@@ -3825,8 +3825,11 @@
     register size_t i;
     int ac;
 
-    gdpsp->gdps_polygons.gp_num_polygons = polygon_ac;
-    gdpsp->gdps_polygons.gp_polygon = (bview_polygon *)bu_calloc(polygon_ac, 
sizeof(bview_polygon), "data polygons");
+    gdpsp->gdps_polygons.num_polygons = polygon_ac;
+    gdpsp->gdps_polygons.polygon = (struct bg_polygon *)bu_calloc(polygon_ac, 
sizeof(struct bg_polygon), "data polygons");
+    for (i = 0; i < polygon_ac; ++i) {
+       // TODO - allocate properties containers for each polygon
+    }
 
     for (i = 0; i < polygon_ac; ++i) {
        size_t contour_ac;
@@ -3839,12 +3842,12 @@
        }
        contour_ac = ac;
 
-       if (to_extract_contours_av(interp, gedp, gdvp, 
&gdpsp->gdps_polygons.gp_polygon[i], contour_ac, contour_av, mode, vflag) != 
GED_OK) {
+       if (to_extract_contours_av(interp, gedp, gdvp, 
&gdpsp->gdps_polygons.polygon[i], contour_ac, contour_av, mode, vflag) != 
GED_OK) {
            Tcl_Free((char *)contour_av);
            return GED_ERROR;
        }
 
-       VMOVE(gdpsp->gdps_polygons.gp_polygon[i].gp_color, gdpsp->gdps_color);
+       VMOVE(gdpsp->gdps_polygons.polygon[i].gp_color, gdpsp->gdps_color);
        if (contour_ac)
            Tcl_Free((char *)contour_av);
     }
@@ -3965,7 +3968,7 @@
        if (argc == 3) {
            size_t i;
 
-           if (bu_sscanf(argv[2], "%zu", &i) != 1 || i > 
gdpsp->gdps_polygons.gp_num_polygons)
+           if (bu_sscanf(argv[2], "%zu", &i) != 1 || i > 
gdpsp->gdps_polygons.num_polygons)
                goto bad;
 
            gdpsp->gdps_target_polygon_i = i;
@@ -3985,10 +3988,10 @@
        if (argc == 3) {
            int op;
 
-           if (bu_sscanf(argv[2], "%d", &op) != 1 || op > gctXor)
+           if (bu_sscanf(argv[2], "%d", &op) != 1 || op > bg_Xor)
                goto bad;
 
-           gdpsp->gdps_clip_type = (ClipType)op;
+           gdpsp->gdps_clip_type = (bg_clip_t)op;
 
            return GED_OK;
        }
@@ -4054,11 +4057,11 @@
        if (argc == 3) {
            /* Get the color for polygon i */
            if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-               i >= gdpsp->gdps_polygons.gp_num_polygons)
+               i >= gdpsp->gdps_polygons.num_polygons)
                goto bad;
 
            bu_vls_printf(gedp->ged_result_str, "%d %d %d",
-                         V3ARGS(gdpsp->gdps_polygons.gp_polygon[i].gp_color));
+                         V3ARGS(gdpsp->gdps_polygons.polygon[i].gp_color));
 
            return GED_OK;
        }
@@ -4068,7 +4071,7 @@
 
 
            if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-               i >= gdpsp->gdps_polygons.gp_num_polygons)
+               i >= gdpsp->gdps_polygons.num_polygons)
                goto bad;
 
            /* set background color */
@@ -4084,7 +4087,7 @@
                goto bad;
 
            /* Set the color for polygon i */
-           VSET(gdpsp->gdps_polygons.gp_polygon[i].gp_color, r, g, b);
+           VSET(gdpsp->gdps_polygons.polygon[i].gp_color, r, g, b);
 
            to_refresh_view(gdvp);
            return GED_OK;
@@ -4123,8 +4126,8 @@
                goto bad;
 
            /* Set the color for all polygons */
-           for (i = 0; i < gdpsp->gdps_polygons.gp_num_polygons; ++i) {
-               VSET(gdpsp->gdps_polygons.gp_polygon[i].gp_color, r, g, b);
+           for (i = 0; i < gdpsp->gdps_polygons.num_polygons; ++i) {
+               VSET(gdpsp->gdps_polygons.polygon[i].gp_color, r, g, b);
            }
 
            /* Set the default polygon color */
@@ -4147,10 +4150,10 @@
        if (argc == 3) {
            /* Get the line width for polygon i */
            if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-               i >= gdpsp->gdps_polygons.gp_num_polygons)
+               i >= gdpsp->gdps_polygons.num_polygons)
                goto bad;
 
-           bu_vls_printf(gedp->ged_result_str, "%d", 
gdpsp->gdps_polygons.gp_polygon[i].gp_line_width);
+           bu_vls_printf(gedp->ged_result_str, "%d", 
gdpsp->gdps_polygons.polygon[i].gp_line_width);
 
            return GED_OK;
        }
@@ -4159,7 +4162,7 @@
            int line_width;
 
            if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-               i >= gdpsp->gdps_polygons.gp_num_polygons)
+               i >= gdpsp->gdps_polygons.num_polygons)
                goto bad;
 
            if (bu_sscanf(argv[3], "%d", &line_width) != 1)
@@ -4168,7 +4171,7 @@
            if (line_width < 0)
                line_width = 0;
 
-           gdpsp->gdps_polygons.gp_polygon[i].gp_line_width = line_width;
+           gdpsp->gdps_polygons.polygon[i].gp_line_width = line_width;
 
            to_refresh_view(gdvp);
            return GED_OK;
@@ -4199,8 +4202,8 @@
                line_width = 0;
 
            /* Set the line width for all polygons */
-           for (i = 0; i < gdpsp->gdps_polygons.gp_num_polygons; ++i) {
-               gdpsp->gdps_polygons.gp_polygon[i].gp_line_width = line_width;
+           for (i = 0; i < gdpsp->gdps_polygons.num_polygons; ++i) {
+               gdpsp->gdps_polygons.polygon[i].gp_line_width = line_width;
            }
 
            /* Set the default line width */
@@ -4223,10 +4226,10 @@
        if (argc == 3) {
            /* Get the line style for polygon i */
            if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-               i >= gdpsp->gdps_polygons.gp_num_polygons)
+               i >= gdpsp->gdps_polygons.num_polygons)
                goto bad;
 
-           bu_vls_printf(gedp->ged_result_str, "%d", 
gdpsp->gdps_polygons.gp_polygon[i].gp_line_style);
+           bu_vls_printf(gedp->ged_result_str, "%d", 
gdpsp->gdps_polygons.polygon[i].gp_line_style);
 
            return GED_OK;
        }
@@ -4235,7 +4238,7 @@
            int line_style;
 
            if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-               i >= gdpsp->gdps_polygons.gp_num_polygons)
+               i >= gdpsp->gdps_polygons.num_polygons)
                goto bad;
 
            if (bu_sscanf(argv[3], "%d", &line_style) != 1)
@@ -4243,9 +4246,9 @@
 
 
            if (line_style <= 0)
-               gdpsp->gdps_polygons.gp_polygon[i].gp_line_style = 0;
+               gdpsp->gdps_polygons.polygon[i].gp_line_style = 0;
            else
-               gdpsp->gdps_polygons.gp_polygon[i].gp_line_style = 1;
+               gdpsp->gdps_polygons.polygon[i].gp_line_style = 1;
 
            to_refresh_view(gdvp);
            return GED_OK;
@@ -4278,8 +4281,8 @@
                line_style = 1;
 
            /* Set the line width for all polygons */
-           for (i = 0; i < gdpsp->gdps_polygons.gp_num_polygons; ++i) {
-               gdpsp->gdps_polygons.gp_polygon[i].gp_line_style = line_style;
+           for (i = 0; i < gdpsp->gdps_polygons.num_polygons; ++i) {
+               gdpsp->gdps_polygons.polygon[i].gp_line_style = line_style;
            }
 
            /* Set the default line style */
@@ -4314,21 +4317,21 @@
            }
            contour_ac = ac;
 
-           i = gdpsp->gdps_polygons.gp_num_polygons;
-           ++gdpsp->gdps_polygons.gp_num_polygons;
-           gdpsp->gdps_polygons.gp_polygon = (bview_polygon 
*)bu_realloc(gdpsp->gdps_polygons.gp_polygon,
-                                                                         
gdpsp->gdps_polygons.gp_num_polygons * sizeof(bview_polygon),
-                                                                         
"realloc gp_polygon");
+           i = gdpsp->gdps_polygons.num_polygons;
+           ++gdpsp->gdps_polygons.num_polygons;
+           gdpsp->gdps_polygons.polygon = (struct bg_polygon 
*)bu_realloc(gdpsp->gdps_polygons.polygon,
+                                                                         
gdpsp->gdps_polygons.num_polygons * sizeof(struct bg_polygon),
+                                                                         
"realloc polygon");
 
-           if (to_extract_contours_av(interp, gedp, gdvp, 
&gdpsp->gdps_polygons.gp_polygon[i],
+           if (to_extract_contours_av(interp, gedp, gdvp, 
&gdpsp->gdps_polygons.polygon[i],
                                       contour_ac, contour_av, 
gdvp->gdv_view->gv_mode, 0) != GED_OK) {
                Tcl_Free((char *)contour_av);
                return GED_ERROR;
            }
 
-           VMOVE(gdpsp->gdps_polygons.gp_polygon[i].gp_color, 
gdpsp->gdps_color);
-           gdpsp->gdps_polygons.gp_polygon[i].gp_line_style = 
gdpsp->gdps_line_style;
-           gdpsp->gdps_polygons.gp_polygon[i].gp_line_width = 
gdpsp->gdps_line_width;
+           VMOVE(gdpsp->gdps_polygons.polygon[i].gp_color, gdpsp->gdps_color);
+           gdpsp->gdps_polygons.polygon[i].gp_line_style = 
gdpsp->gdps_line_style;
+           gdpsp->gdps_polygons.polygon[i].gp_line_width = 
gdpsp->gdps_line_width;
 
            Tcl_Free((char *)contour_av);
 
@@ -4345,7 +4348,7 @@
     if (BU_STR_EQUAL(argv[1], "clip")) {
        size_t i, j;
        int op;
-       bview_polygon *gpp;
+       struct bg_polygon *gpp;
 
        if (argc > 5)
            goto bad;
@@ -4352,7 +4355,7 @@
 
        if (argc > 2) {
            if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-               i >= gdpsp->gdps_polygons.gp_num_polygons)
+               i >= gdpsp->gdps_polygons.num_polygons)
                goto bad;
        } else
            i = gdpsp->gdps_target_polygon_i;
@@ -4359,10 +4362,10 @@
 
        if (argc > 3) {
            if (bu_sscanf(argv[3], "%zu", &j) != 1 ||
-               j >= gdpsp->gdps_polygons.gp_num_polygons)
+               j >= gdpsp->gdps_polygons.num_polygons)
                goto bad;
        } else
-           j = gdpsp->gdps_polygons.gp_num_polygons - 1; /* Default - use last 
polygon as the clip polygon */
+           j = gdpsp->gdps_polygons.num_polygons - 1; /* Default - use last 
polygon as the clip polygon */
 
        /* Nothing to do */
        if (i == j)
@@ -4370,36 +4373,36 @@
 
        if (argc != 5)
            op = gdpsp->gdps_clip_type;
-       else if (bu_sscanf(argv[4], "%d", &op) != 1 || op > gctXor)
+       else if (bu_sscanf(argv[4], "%d", &op) != 1 || op > bg_Xor)
            goto bad;
 
-       gpp = clip_polygon((ClipType)op,
-                              &gdpsp->gdps_polygons.gp_polygon[i],
-                              &gdpsp->gdps_polygons.gp_polygon[j],
+       gpp = bg_clip_polygon((bg_clip_t)op,
+                              &gdpsp->gdps_polygons.polygon[i],
+                              &gdpsp->gdps_polygons.polygon[j],
                               CLIPPER_MAX,
                               gdpsp->gdps_model2view,
                               gdpsp->gdps_view2model);
 
        /* Free the target polygon */
-       to_polygon_free(&gdpsp->gdps_polygons.gp_polygon[i]);
+       to_polygon_free(&gdpsp->gdps_polygons.polygon[i]);
 
        /* When using defaults, the clip polygon is assumed to be temporary and 
is removed after clipping */
        if (argc == 2) {
            /* Free the clip polygon */
-           to_polygon_free(&gdpsp->gdps_polygons.gp_polygon[j]);
+           to_polygon_free(&gdpsp->gdps_polygons.polygon[j]);
 
            /* No longer need space for the clip polygon */
-           --gdpsp->gdps_polygons.gp_num_polygons;
-           gdpsp->gdps_polygons.gp_polygon = (bview_polygon 
*)bu_realloc(gdpsp->gdps_polygons.gp_polygon,
-                                                                         
gdpsp->gdps_polygons.gp_num_polygons * sizeof(bview_polygon),
-                                                                         
"realloc gp_polygon");
+           --gdpsp->gdps_polygons.num_polygons;
+           gdpsp->gdps_polygons.polygon = (struct bg_polygon 
*)bu_realloc(gdpsp->gdps_polygons.polygon,
+                                                                         
gdpsp->gdps_polygons.num_polygons * sizeof(struct bg_polygon),
+                                                                         
"realloc polygon");
        }
 
        /* Replace the target polygon with the newly clipped polygon. */
        /* Not doing a struct copy to avoid overwriting the color, line width 
and line style. */
-       gdpsp->gdps_polygons.gp_polygon[i].gp_num_contours = 
gpp->gp_num_contours;
-       gdpsp->gdps_polygons.gp_polygon[i].gp_hole = gpp->gp_hole;
-       gdpsp->gdps_polygons.gp_polygon[i].gp_contour = gpp->gp_contour;
+       gdpsp->gdps_polygons.polygon[i].num_contours = gpp->num_contours;
+       gdpsp->gdps_polygons.polygon[i].hole = gpp->hole;
+       gdpsp->gdps_polygons.polygon[i].contour = gpp->contour;
 
        /* Free the clipped polygon container */
        bu_free((void *)gpp, "clip gpp");
@@ -4420,7 +4423,7 @@
            goto bad;
 
        if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-           i >= gdpsp->gdps_polygons.gp_num_polygons)
+           i >= gdpsp->gdps_polygons.num_polygons)
            goto bad;
 
        if ((ret = ged_export_polygon(gedp, gdpsp, i, argv[3])) != GED_OK)
@@ -4434,27 +4437,27 @@
      * Import sketch_name and append
      */
     if (BU_STR_EQUAL(argv[1], "import")) {
-       bview_polygon *gpp;
+       struct bg_polygon *gpp;
        size_t i;
 
        if (argc != 3)
            goto bad;
 
-       if ((gpp = ged_import_polygon(gedp, argv[2])) == (bview_polygon *)0) {
+       if ((gpp = ged_import_polygon(gedp, argv[2])) == (struct bg_polygon 
*)0) {
            bu_vls_printf(gedp->ged_result_str, "%s: failed to import sketch 
%s", argv[0], argv[2]);
            return GED_ERROR;
        }
 
-       i = gdpsp->gdps_polygons.gp_num_polygons;
-       ++gdpsp->gdps_polygons.gp_num_polygons;
-       gdpsp->gdps_polygons.gp_polygon = (bview_polygon 
*)bu_realloc(gdpsp->gdps_polygons.gp_polygon,
-                                                                     
gdpsp->gdps_polygons.gp_num_polygons * sizeof(bview_polygon),
-                                                                     "realloc 
gp_polygon");
+       i = gdpsp->gdps_polygons.num_polygons;
+       ++gdpsp->gdps_polygons.num_polygons;
+       gdpsp->gdps_polygons.polygon = (struct bg_polygon 
*)bu_realloc(gdpsp->gdps_polygons.polygon,
+                                                                     
gdpsp->gdps_polygons.num_polygons * sizeof(struct bg_polygon),
+                                                                     "realloc 
polygon");
 
-       gdpsp->gdps_polygons.gp_polygon[i] = *gpp;  /* struct copy */
-       VMOVE(gdpsp->gdps_polygons.gp_polygon[i].gp_color, gdpsp->gdps_color);
-       gdpsp->gdps_polygons.gp_polygon[i].gp_line_style = 
gdpsp->gdps_line_style;
-       gdpsp->gdps_polygons.gp_polygon[i].gp_line_width = 
gdpsp->gdps_line_width;
+       gdpsp->gdps_polygons.polygon[i] = *gpp;  /* struct copy */
+       VMOVE(gdpsp->gdps_polygons.polygon[i].gp_color, gdpsp->gdps_color);
+       gdpsp->gdps_polygons.polygon[i].gp_line_style = gdpsp->gdps_line_style;
+       gdpsp->gdps_polygons.polygon[i].gp_line_width = gdpsp->gdps_line_width;
 
        to_refresh_view(gdvp);
        return GED_OK;
@@ -4469,7 +4472,7 @@
            goto bad;
 
        if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-           i >= gdpsp->gdps_polygons.gp_num_polygons)
+           i >= gdpsp->gdps_polygons.num_polygons)
            goto bad;
 
        if (bu_sscanf(argv[3], "%lf %lf", &vdir[X], &vdir[Y]) != 2) {
@@ -4482,7 +4485,7 @@
            goto bad;
        }
 
-       ged_polygon_fill_segments(gedp, &gdpsp->gdps_polygons.gp_polygon[i], 
vdir, vdelta);
+       ged_polygon_fill_segments(gedp, &gdpsp->gdps_polygons.polygon[i], vdir, 
vdelta);
 
        return GED_OK;
     }
@@ -4499,10 +4502,10 @@
            goto bad;
 
        if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-           i >= gdpsp->gdps_polygons.gp_num_polygons)
+           i >= gdpsp->gdps_polygons.num_polygons)
            goto bad;
 
-       area = find_polygon_area(&gdpsp->gdps_polygons.gp_polygon[i], 
CLIPPER_MAX,
+       area = bg_find_polygon_area(&gdpsp->gdps_polygons.polygon[i], 
CLIPPER_MAX,
                                     gdpsp->gdps_model2view, gdpsp->gdps_scale);
        bu_vls_printf(gedp->ged_result_str, "%lf", area);
 
@@ -4521,14 +4524,14 @@
            goto bad;
 
        if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-           i >= gdpsp->gdps_polygons.gp_num_polygons)
+           i >= gdpsp->gdps_polygons.num_polygons)
            goto bad;
 
        if (bu_sscanf(argv[3], "%zu", &j) != 1 ||
-           j >= gdpsp->gdps_polygons.gp_num_polygons)
+           j >= gdpsp->gdps_polygons.num_polygons)
            goto bad;
 
-       ret = ged_polygons_overlap(gedp, &gdpsp->gdps_polygons.gp_polygon[i], 
&gdpsp->gdps_polygons.gp_polygon[j]);
+       ret = ged_polygons_overlap(gedp, &gdpsp->gdps_polygons.polygon[i], 
&gdpsp->gdps_polygons.polygon[j]);
        bu_vls_printf(gedp->ged_result_str, "%d", ret);
 
        return GED_OK;
@@ -4549,19 +4552,19 @@
        else
            vflag = 1;
        if (argc == 2) {
-           for (i = 0; i < gdpsp->gdps_polygons.gp_num_polygons; ++i) {
+           for (i = 0; i < gdpsp->gdps_polygons.num_polygons; ++i) {
                bu_vls_printf(gedp->ged_result_str, " {");
 
-               for (j = 0; j < 
gdpsp->gdps_polygons.gp_polygon[i].gp_num_contours; ++j) {
-                   bu_vls_printf(gedp->ged_result_str, " {%d ", 
gdpsp->gdps_polygons.gp_polygon[i].gp_hole[j]);
+               for (j = 0; j < gdpsp->gdps_polygons.polygon[i].num_contours; 
++j) {
+                   bu_vls_printf(gedp->ged_result_str, " {%d ", 
gdpsp->gdps_polygons.polygon[i].hole[j]);
 
-                   for (k = 0; k < 
gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_num_points; ++k) {
+                   for (k = 0; k < 
gdpsp->gdps_polygons.polygon[i].contour[j].num_points; ++k) {
                        point_t pt;
 
                        if (vflag) {
-                           MAT4X3PNT(pt, gdvp->gdv_view->gv_model2view, 
gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point[k]);
+                           MAT4X3PNT(pt, gdvp->gdv_view->gv_model2view, 
gdpsp->gdps_polygons.polygon[i].contour[j].point[k]);
                        } else {
-                           VMOVE(pt, 
gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point[k]);
+                           VMOVE(pt, 
gdpsp->gdps_polygons.polygon[i].contour[j].point[k]);
                        }
 
                        bu_vls_printf(gedp->ged_result_str, " {%lf %lf %lf} ", 
V3ARGS(pt));
@@ -4615,13 +4618,13 @@
        int ac;
        size_t contour_ac;
        const char **contour_av;
-       bview_polygon gp;
+       struct bg_polygon gp;
 
        if (argc != 4)
            goto bad;
 
        if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-           i >= gdpsp->gdps_polygons.gp_num_polygons)
+           i >= gdpsp->gdps_polygons.num_polygons)
            goto bad;
 
        /* Split the polygon in argv[3] into contours */
@@ -4637,12 +4640,12 @@
            return GED_ERROR;
        }
 
-       to_polygon_free(&gdpsp->gdps_polygons.gp_polygon[i]);
+       to_polygon_free(&gdpsp->gdps_polygons.polygon[i]);
 
        /* Not doing a struct copy to avoid overwriting the color, line width 
and line style. */
-       gdpsp->gdps_polygons.gp_polygon[i].gp_num_contours = gp.gp_num_contours;
-       gdpsp->gdps_polygons.gp_polygon[i].gp_hole = gp.gp_hole;
-       gdpsp->gdps_polygons.gp_polygon[i].gp_contour = gp.gp_contour;
+       gdpsp->gdps_polygons.polygon[i].num_contours = gp.num_contours;
+       gdpsp->gdps_polygons.polygon[i].hole = gp.hole;
+       gdpsp->gdps_polygons.polygon[i].contour = gp.contour;
 
        to_refresh_view(gdvp);
        return GED_OK;
@@ -4660,22 +4663,22 @@
            goto bad;
 
        if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-           i >= gdpsp->gdps_polygons.gp_num_polygons)
+           i >= gdpsp->gdps_polygons.num_polygons)
            goto bad;
 
        if (bu_sscanf(argv[3], "%zu", &j) != 1 ||
-           j >= gdpsp->gdps_polygons.gp_polygon[i].gp_num_contours)
+           j >= gdpsp->gdps_polygons.polygon[i].num_contours)
            goto bad;
 
        if (bu_sscanf(argv[4], "%lf %lf %lf", &pt[X], &pt[Y], &pt[Z]) != 3)
            goto bad;
 
-       k = gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_num_points;
-       ++gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_num_points;
-       gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point = (point_t 
*)bu_realloc(gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point,
-                                                                               
           gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_num_points * 
sizeof(point_t),
-                                                                               
           "realloc gpc_point");
-       VMOVE(gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point[k], 
pt);
+       k = gdpsp->gdps_polygons.polygon[i].contour[j].num_points;
+       ++gdpsp->gdps_polygons.polygon[i].contour[j].num_points;
+       gdpsp->gdps_polygons.polygon[i].contour[j].point = (point_t 
*)bu_realloc(gdpsp->gdps_polygons.polygon[i].contour[j].point,
+                                                                               
           gdpsp->gdps_polygons.polygon[i].contour[j].num_points * 
sizeof(point_t),
+                                                                               
           "realloc point");
+       VMOVE(gdpsp->gdps_polygons.polygon[i].contour[j].point[k], pt);
        to_refresh_view(gdvp);
        return GED_OK;
     }
@@ -4691,18 +4694,18 @@
            goto bad;
 
        if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-           i >= gdpsp->gdps_polygons.gp_num_polygons)
+           i >= gdpsp->gdps_polygons.num_polygons)
            goto bad;
 
        if (bu_sscanf(argv[3], "%zu", &j) != 1 ||
-           j >= gdpsp->gdps_polygons.gp_polygon[i].gp_num_contours)
+           j >= gdpsp->gdps_polygons.polygon[i].num_contours)
            goto bad;
 
        if (bu_sscanf(argv[4], "%zu", &k) != 1 ||
-           k >= 
gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_num_points)
+           k >= gdpsp->gdps_polygons.polygon[i].contour[j].num_points)
            goto bad;
 
-       bu_vls_printf(gedp->ged_result_str, "%lf %lf %lf", 
V3ARGS(gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point[k]));
+       bu_vls_printf(gedp->ged_result_str, "%lf %lf %lf", 
V3ARGS(gdpsp->gdps_polygons.polygon[i].contour[j].point[k]));
        return GED_OK;
     }
 
@@ -4718,21 +4721,21 @@
            goto bad;
 
        if (bu_sscanf(argv[2], "%zu", &i) != 1 ||
-           i >= gdpsp->gdps_polygons.gp_num_polygons)
+           i >= gdpsp->gdps_polygons.num_polygons)
            goto bad;
 
        if (bu_sscanf(argv[3], "%zu", &j) != 1 ||
-           j >= gdpsp->gdps_polygons.gp_polygon[i].gp_num_contours)
+           j >= gdpsp->gdps_polygons.polygon[i].num_contours)
            goto bad;
 
        if (bu_sscanf(argv[4], "%zu", &k) != 1 ||
-           k >= 
gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_num_points)
+           k >= gdpsp->gdps_polygons.polygon[i].contour[j].num_points)
            goto bad;
 
        if (bu_sscanf(argv[5], "%lf %lf %lf", &pt[X], &pt[Y], &pt[Z]) != 3)
            goto bad;
 
-       VMOVE(gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point[k], 
pt);
+       VMOVE(gdpsp->gdps_polygons.polygon[i].contour[j].point[k], pt);
        to_refresh_view(gdvp);
        return GED_OK;
     }
@@ -4861,9 +4864,9 @@
            goto bad;
 
        /* Silently ignore */
-       if (i >= gdpsp->gdps_polygons.gp_num_polygons ||
-           j >= gdpsp->gdps_polygons.gp_polygon[i].gp_num_contours ||
-           k >= 
gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_num_points)
+       if (i >= gdpsp->gdps_polygons.num_polygons ||
+           j >= gdpsp->gdps_polygons.polygon[i].num_contours ||
+           k >= gdpsp->gdps_polygons.polygon[i].contour[j].num_points)
            return GED_OK;
 
        /* This section is for moving more than a single point on a contour */
@@ -4871,9 +4874,9 @@
            point_t old_mpoint, new_mpoint;
            vect_t diff;
 
-           VMOVE(old_mpoint, 
gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point[k]);
+           VMOVE(old_mpoint, 
gdpsp->gdps_polygons.polygon[i].contour[j].point[k]);
 
-           MAT4X3PNT(vpoint, gdvp->gdv_view->gv_model2view, 
gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point[k]);
+           MAT4X3PNT(vpoint, gdvp->gdv_view->gv_model2view, 
gdpsp->gdps_polygons.polygon[i].contour[j].point[k]);
            vpoint[X] = vx;
            vpoint[Y] = vy;
            MAT4X3PNT(new_mpoint, gdvp->gdv_view->gv_view2model, vpoint);
@@ -4882,11 +4885,11 @@
            /* Move all polygons and all their respective contours. */
            if (gdpsp->gdps_moveAll) {
                size_t p, c;
-               for (p = 0; p < gdpsp->gdps_polygons.gp_num_polygons; ++p) {
-                   for (c = 0; c < 
gdpsp->gdps_polygons.gp_polygon[p].gp_num_contours; ++c) {
-                       for (k = 0; k < 
gdpsp->gdps_polygons.gp_polygon[p].gp_contour[c].gpc_num_points; ++k) {
-                           
VADD2(gdpsp->gdps_polygons.gp_polygon[p].gp_contour[c].gpc_point[k],
-                                 
gdpsp->gdps_polygons.gp_polygon[p].gp_contour[c].gpc_point[k],
+               for (p = 0; p < gdpsp->gdps_polygons.num_polygons; ++p) {
+                   for (c = 0; c < 
gdpsp->gdps_polygons.polygon[p].num_contours; ++c) {
+                       for (k = 0; k < 
gdpsp->gdps_polygons.polygon[p].contour[c].num_points; ++k) {
+                           
VADD2(gdpsp->gdps_polygons.polygon[p].contour[c].point[k],
+                                 
gdpsp->gdps_polygons.polygon[p].contour[c].point[k],
                                  diff);
                        }
                    }
@@ -4893,18 +4896,18 @@
                }
            } else {
                /* Move only the contour. */
-               for (k = 0; k < 
gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_num_points; ++k) {
-                   
VADD2(gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point[k],
-                         
gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point[k],
+               for (k = 0; k < 
gdpsp->gdps_polygons.polygon[i].contour[j].num_points; ++k) {
+                   VADD2(gdpsp->gdps_polygons.polygon[i].contour[j].point[k],
+                         gdpsp->gdps_polygons.polygon[i].contour[j].point[k],
                          diff);
                }
            }
        } else {
            /* This section is for moving a single point on a contour */
-           MAT4X3PNT(vpoint, gdvp->gdv_view->gv_model2view, 
gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point[k]);
+           MAT4X3PNT(vpoint, gdvp->gdv_view->gv_model2view, 
gdpsp->gdps_polygons.polygon[i].contour[j].point[k]);
            vpoint[X] = vx;
            vpoint[Y] = vy;
-           
MAT4X3PNT(gdpsp->gdps_polygons.gp_polygon[i].gp_contour[j].gpc_point[k], 
gdvp->gdv_view->gv_view2model, vpoint);
+           MAT4X3PNT(gdpsp->gdps_polygons.polygon[i].contour[j].point[k], 
gdvp->gdv_view->gv_view2model, vpoint);
        }
 
        to_refresh_view(gdvp);
@@ -5553,18 +5556,18 @@
 
     /* check for polygon points */
     if (gdvp->gdv_view->gv_data_polygons.gdps_draw &&
-       gdvp->gdv_view->gv_data_polygons.gdps_polygons.gp_num_polygons) {
+       gdvp->gdv_view->gv_data_polygons.gdps_polygons.num_polygons) {
        register size_t si, sj, sk;
 
        bview_data_polygon_state *gdpsp = &gdvp->gdv_view->gv_data_polygons;
 
-       for (si = 0; si < gdpsp->gdps_polygons.gp_num_polygons; ++si)
-           for (sj = 0; sj < 
gdpsp->gdps_polygons.gp_polygon[si].gp_num_contours; ++sj)
-               for (sk = 0; sk < 
gdpsp->gdps_polygons.gp_polygon[si].gp_contour[sj].gpc_num_points; ++sk) {
+       for (si = 0; si < gdpsp->gdps_polygons.num_polygons; ++si)
+           for (sj = 0; sj < gdpsp->gdps_polygons.polygon[si].num_contours; 
++sj)
+               for (sk = 0; sk < 
gdpsp->gdps_polygons.polygon[si].contour[sj].num_points; ++sk) {
                    fastf_t minX, maxX;
                    fastf_t minY, maxY;
 
-                   MAT4X3PNT(vpoint, gdvp->gdv_view->gv_model2view, 
gdpsp->gdps_polygons.gp_polygon[si].gp_contour[sj].gpc_point[sk]);
+                   MAT4X3PNT(vpoint, gdvp->gdv_view->gv_model2view, 
gdpsp->gdps_polygons.polygon[si].contour[sj].point[sk]);
                    minX = vpoint[X] - tol;
                    maxX = vpoint[X] + tol;
                    minY = vpoint[Y] - tol;
@@ -5578,7 +5581,7 @@
                            top_i = si;
                            top_j = sj;
                            top_k = sk;
-                           VMOVE(top_point, 
gdpsp->gdps_polygons.gp_polygon[si].gp_contour[sj].gpc_point[sk]);
+                           VMOVE(top_point, 
gdpsp->gdps_polygons.polygon[si].contour[sj].point[sk]);
                            found_top = 1;
                        }
                    }
@@ -12113,10 +12116,10 @@
     av[2] = bu_vls_addr(&plist);
     av[3] = (char *)0;
 
-    if (gdpsp->gdps_polygons.gp_num_polygons == gdpsp->gdps_target_polygon_i)
+    if (gdpsp->gdps_polygons.num_polygons == gdpsp->gdps_target_polygon_i)
        gdpsp->gdps_curr_polygon_i = gdpsp->gdps_target_polygon_i;
     else
-       gdpsp->gdps_curr_polygon_i = gdpsp->gdps_polygons.gp_num_polygons;
+       gdpsp->gdps_curr_polygon_i = gdpsp->gdps_polygons.num_polygons;
 
     (void)to_data_polygons_func(interp, gedp, gdvp, ac, (const char **)av);
     bu_vls_free(&plist);
@@ -12257,10 +12260,10 @@
        struct bu_vls plist = BU_VLS_INIT_ZERO;
        struct bu_vls bindings = BU_VLS_INIT_ZERO;
 
-       if (gdpsp->gdps_polygons.gp_num_polygons == 
gdpsp->gdps_target_polygon_i)
+       if (gdpsp->gdps_polygons.num_polygons == gdpsp->gdps_target_polygon_i)
            gdpsp->gdps_curr_polygon_i = gdpsp->gdps_target_polygon_i;
        else
-           gdpsp->gdps_curr_polygon_i = gdpsp->gdps_polygons.gp_num_polygons;
+           gdpsp->gdps_curr_polygon_i = gdpsp->gdps_polygons.num_polygons;
 
        gdpsp->gdps_cflag = 1;
        gdpsp->gdps_curr_point_i = 1;
@@ -12544,10 +12547,10 @@
     av[2] = bu_vls_addr(&plist);
     av[3] = (char *)0;
 
-    if (gdpsp->gdps_polygons.gp_num_polygons == gdpsp->gdps_target_polygon_i)
+    if (gdpsp->gdps_polygons.num_polygons == gdpsp->gdps_target_polygon_i)
        gdpsp->gdps_curr_polygon_i = gdpsp->gdps_target_polygon_i;
     else
-       gdpsp->gdps_curr_polygon_i = gdpsp->gdps_polygons.gp_num_polygons;
+       gdpsp->gdps_curr_polygon_i = gdpsp->gdps_polygons.num_polygons;
 
     (void)to_data_polygons_func(interp, gedp, gdvp, ac, (const char **)av);
     bu_vls_free(&plist);
@@ -12715,10 +12718,10 @@
     av[2] = bu_vls_addr(&plist);
     av[3] = (char *)0;
 
-    if (gdpsp->gdps_polygons.gp_num_polygons == gdpsp->gdps_target_polygon_i)
+    if (gdpsp->gdps_polygons.num_polygons == gdpsp->gdps_target_polygon_i)
        gdpsp->gdps_curr_polygon_i = gdpsp->gdps_target_polygon_i;
     else
-       gdpsp->gdps_curr_polygon_i = gdpsp->gdps_polygons.gp_num_polygons;
+       gdpsp->gdps_curr_polygon_i = gdpsp->gdps_polygons.num_polygons;
 
     (void)to_data_polygons_func(interp, gedp, gdvp, ac, (const char **)av);
     bu_vls_free(&plist);
@@ -15323,35 +15326,35 @@
        \
        /* set color */ \
        (void)dm_set_fg((_dmp), \
-                       (_gdpsp)->gdps_polygons.gp_polygon[_i].gp_color[0], \
-                       (_gdpsp)->gdps_polygons.gp_polygon[_i].gp_color[1], \
-                       (_gdpsp)->gdps_polygons.gp_polygon[_i].gp_color[2], \
+                       (_gdpsp)->gdps_polygons.polygon[_i].gp_color[0], \
+                       (_gdpsp)->gdps_polygons.polygon[_i].gp_color[1], \
+                       (_gdpsp)->gdps_polygons.polygon[_i].gp_color[2], \
                        1, 1.0);                                        \
        \
-       for (_j = 0; _j < 
(_gdpsp)->gdps_polygons.gp_polygon[_i].gp_num_contours; ++_j) { \
-           size_t _last = 
(_gdpsp)->gdps_polygons.gp_polygon[_i].gp_contour[_j].gpc_num_points-1; \
+       for (_j = 0; _j < (_gdpsp)->gdps_polygons.polygon[_i].num_contours; 
++_j) { \
+           size_t _last = 
(_gdpsp)->gdps_polygons.polygon[_i].contour[_j].num_points-1; \
            int _line_style; \
            \
            /* always draw holes using segmented lines */ \
-           if ((_gdpsp)->gdps_polygons.gp_polygon[_i].gp_hole[_j]) { \
+           if ((_gdpsp)->gdps_polygons.polygon[_i].hole[_j]) { \
                _line_style = 1; \
            } else { \
-               _line_style = 
(_gdpsp)->gdps_polygons.gp_polygon[_i].gp_line_style; \
+               _line_style = 
(_gdpsp)->gdps_polygons.polygon[_i].gp_line_style; \
            } \
            \
            /* set the linewidth and linestyle for polygon i, contour j */      
\
            (void)dm_set_line_attr((_dmp), \
-                                  
(_gdpsp)->gdps_polygons.gp_polygon[_i].gp_line_width, \
+                                  
(_gdpsp)->gdps_polygons.polygon[_i].gp_line_width, \
                                   _line_style); \
            \
            (void)dm_draw_lines_3d((_dmp),                              \
-                                  
(_gdpsp)->gdps_polygons.gp_polygon[_i].gp_contour[_j].gpc_num_points, \
-                                  
(_gdpsp)->gdps_polygons.gp_polygon[_i].gp_contour[_j].gpc_point, 1); \
+                                  
(_gdpsp)->gdps_polygons.polygon[_i].contour[_j].num_points, \
+                                  
(_gdpsp)->gdps_polygons.polygon[_i].contour[_j].point, 1); \
            \
            if (_mode != TCLCAD_POLY_CONTOUR_MODE || _i != _last_poly || 
(_gdpsp)->gdps_cflag == 0) { \
                (void)dm_draw_line_3d((_dmp),                           \
-                                     
(_gdpsp)->gdps_polygons.gp_polygon[_i].gp_contour[_j].gpc_point[_last], \
-                                     
(_gdpsp)->gdps_polygons.gp_polygon[_i].gp_contour[_j].gpc_point[0]); \
+                                     
(_gdpsp)->gdps_polygons.polygon[_i].contour[_j].point[_last], \
+                                     
(_gdpsp)->gdps_polygons.polygon[_i].contour[_j].point[0]); \
            } \
        }}
 
@@ -15363,14 +15366,14 @@
     int saveLineWidth;
     int saveLineStyle;
 
-    if (gdpsp->gdps_polygons.gp_num_polygons < 1)
+    if (gdpsp->gdps_polygons.num_polygons < 1)
        return;
 
     saveLineWidth = dm_get_linewidth(dmp);
     saveLineStyle = dm_get_linestyle(dmp);
 
-    last_poly = gdpsp->gdps_polygons.gp_num_polygons - 1;
-    for (i = 0; i < gdpsp->gdps_polygons.gp_num_polygons; ++i) {
+    last_poly = gdpsp->gdps_polygons.num_polygons - 1;
+    for (i = 0; i < gdpsp->gdps_polygons.num_polygons; ++i) {
        if (i == gdpsp->gdps_target_polygon_i)
            continue;
 

This was sent by the SourceForge.net collaborative development platform, the 
world's largest Open Source development site.



_______________________________________________
BRL-CAD Source Commits mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/brlcad-commits

Reply via email to