1
0
Fork 0

tgChopPolygon() called a really simplistic polygon partitioner for large

polygons.  This was to bail us out of the overwhelming memory requirments
when using the default polygon clipping routines on really large polygons.
However, the simplistic polygon partitioner did not handle holes.
Unfortunately, several TG utilities were calling this function with polygons
that did contain holes with potentially mixed results.

I renamed this function tgChopBigSimplePolygon() and created a new
tgChopNormalPolygon() which should be used by most utilities unless you
really know what you are doing.

This has some performance implications, but achieves more correct results.
This commit is contained in:
curt 2004-05-17 20:42:42 +00:00
parent 7358eb3f09
commit 7de22d8ef2
2 changed files with 88 additions and 6 deletions

View file

@ -149,8 +149,82 @@ static void clip_and_write_poly( string root, long int p_index, AreaType area,
// process polygon shape (chop up along tile boundaries and write each // process polygon shape (chop up along tile boundaries and write each
// polygon piece to a file) // polygon piece to a file)
void tgChopPolygon( const string& path, AreaType area, void tgChopNormalPolygon( const string& path, AreaType area,
const TGPolygon& shape, bool preserve3d ) const TGPolygon& shape, bool preserve3d )
{
Point3D min, max, p;
// point2d min, max;
long int index;
int i, j;
// bail out immediately if polygon is empty
if ( shape.contours() == 0 ) {
return;
}
min = Point3D( 200.0 );
max = Point3D( -200.0 );
// find min/max of polygon
for ( i = 0; i < shape.contours(); i++ ) {
for ( j = 0; j < shape.contour_size(i); j++ ) {
p = shape.get_pt( i, j );
if ( p.x() < min.x() ) { min.setx( p.x() ); }
if ( p.y() < min.y() ) { min.sety( p.y() ); }
if ( p.x() > max.x() ) { max.setx( p.x() ); }
if ( p.y() > max.y() ) { max.sety( p.y() ); }
}
}
// get next polygon index
index = poly_index_next();
SG_LOG( SG_GENERAL, SG_DEBUG, " min = " << min << " max = " << max );
// find buckets for min, and max points of convex hull.
// note to self: self, you should think about checking for
// polygons that span the date line
SGBucket b_min( min.x(), min.y() );
SGBucket b_max( max.x(), max.y() );
SG_LOG( SG_GENERAL, SG_DEBUG, " Bucket min = " << b_min );
SG_LOG( SG_GENERAL, SG_DEBUG, " Bucket max = " << b_max );
if ( b_min == b_max ) {
// shape entirely contained in a single bucket, write and bail
clip_and_write_poly( path, index, area, b_min, shape, preserve3d );
return;
}
SGBucket b_cur;
int dx, dy;
sgBucketDiff(b_min, b_max, &dx, &dy);
SG_LOG( SG_GENERAL, SG_INFO,
" polygon spans tile boundaries" );
SG_LOG( SG_GENERAL, SG_DEBUG, " dx = " << dx
<< " dy = " << dy );
if ( (dx > 2880) || (dy > 1440) )
throw sg_exception("something is really wrong in split_polygon()!!!!");
// write each out polygon for each bucket
for ( j = 0; j <= dy; ++j ) {
for ( i = 0; i <= dx; ++i ) {
b_cur = sgBucketOffset(min.x(), min.y(), i, j);
clip_and_write_poly( path, index, area, b_cur, shape,
preserve3d );
}
}
}
// process polygon shape (chop up along tile boundaries and write each
// polygon piece to a file) This has a front end to a crude clipper
// that doesn't handle holes so beware. This routine is appropriate
// for breaking down really huge structures if needed.
void tgChopBigSimplePolygon( const string& path, AreaType area,
const TGPolygon& shape, bool preserve3d )
{ {
Point3D min, max, p; Point3D min, max, p;
// point2d min, max; // point2d min, max;
@ -268,7 +342,7 @@ void tgChopPolygon( const string& path, AreaType area,
bottom_clip = horizontal_clip( shape, clip_line, Below ); bottom_clip = horizontal_clip( shape, clip_line, Below );
} }
tgChopPolygon( path, area, bottom_clip, preserve3d ); tgChopBigSimplePolygon( path, area, bottom_clip, preserve3d );
} }
{ {
@ -297,6 +371,6 @@ void tgChopPolygon( const string& path, AreaType area,
top_clip = horizontal_clip( shape, clip_line, Above ); top_clip = horizontal_clip( shape, clip_line, Above );
} }
tgChopPolygon( path, area, top_clip, preserve3d ); tgChopBigSimplePolygon( path, area, top_clip, preserve3d );
} }
} }

View file

@ -33,8 +33,16 @@
// process polygon shape (chop up along tile boundaries and write each // process polygon shape (chop up along tile boundaries and write each
// polygon piece to a file) // polygon piece to a file)
void tgChopPolygon( const string& path, AreaType area, void tgChopNormalPolygon( const string& path, AreaType area,
const TGPolygon& shape, bool preserve3d ); const TGPolygon& shape, bool preserve3d );
// process polygon shape (chop up along tile boundaries and write each
// polygon piece to a file) This has a front end to a crude clipper
// that doesn't handle holes so beware. This routine is appropriate
// for breaking down really huge structures if needed.
void tgChopBigSimplePolygon( const string& path, AreaType area,
const TGPolygon& shape, bool preserve3d );
#endif // _TG_CHOP_HXX #endif // _TG_CHOP_HXX