Boost logo

Boost Users :

Subject: [Boost-users] [geometry] Buffer (with strategy) to offset polygons
From: Olivier Tournaire (olitour_at_[hidden])
Date: 2014-08-11 17:41:18


Dear all,

I have used successfully the buffering algorithm to offset a shapefile of
2D polygons. However, there are 4 polygons (amongst nearly 4000) in my SHP
does are not successfully processed. They do not have topology or
orientation errors.

I use GDAL 1.9 to read the SHP, boost 1.56 precompiled binaries from
sourceforge on a 64bit windows 7. If someone is willing to have a look at
the problem, I can share the files and the code I use. Here is a quick
overview:

    typedef double coordinate_type;
    typedef boost::geometry::model::d2::point_xy<coordinate_type>
point_xy_type;
    typedef boost::geometry::model::polygon<point_xy_type> polygon_type;
    boost::geometry::strategy::buffer::end_flat end_strategy;
    boost::geometry::strategy::buffer::point_square point_strategy;
    boost::geometry::strategy::buffer::side_straight side_strategy;

    boost::geometry::strategy::buffer::distance_symmetric<coordinate_type>
distance_strategy(buffer_distance);
    boost::geometry::strategy::buffer::join_miter
join_strategy(buffer_distance);

                polygon_type p;
                boost::geometry::model::multi_polygon<polygon_type> result;

                // Build a polygon_type from OGRPolygon
                OGRLinearRing* exteriorRing = polygon->getExteriorRing();
                for(int i=0;i<exteriorRing->getNumPoints();++i)
                {
                    OGRPoint pt;
                    exteriorRing->getPoint(i,&pt);

                    p.outer().push_back( point_xy_type(pt.getX(),
pt.getY()) );
                }
                for(int i=0;i<polygon->getNumInteriorRings();++i)
                {
                    OGRLinearRing* interiorRing =
polygon->getInteriorRing(i);
                    polygon_type::ring_type ring;

                    for(int j=0;j<interiorRing->getNumPoints();++j)
                    {
                        OGRPoint pt;
                        interiorRing->getPoint(j,&pt);

                        ring.push_back( point_xy_type(pt.getX(), pt.getY())
);
                    }
                    p.inners().push_back(ring);
                }

                boost::geometry::buffer(p, result, distance_strategy,
side_strategy, join_strategy, end_strategy, point_strategy);

                if(result.size() == 0)
                {
                    int indexID = feature->GetFieldIndex("ID");
                    cout << "No result build for polygon with ID " <<
feature->GetFieldAsString(indexID) << endl;
                }
                else
                {
                    typedef
boost::geometry::strategy::distance::pythagoras<coordinate_type>
pythagoras_distance_strategy;
                    typedef
boost::geometry::strategy::distance::projected_point<coordinate_type,
pythagoras_distance_strategy> projected_point_strategy;

boost::geometry::strategy::simplify::douglas_peucker<point_xy_type,
projected_point_strategy> dp;

                    OGRPolygon poly;

                    for(size_t i=0;i<result.size();++i)
                    {
                        polygon_type result_i = result[i];
                        polygon_type result_i_simplified;

                        boost::geometry::simplify(result_i,
result_i_simplified, 0.1, dp);

                        {
                            OGRLinearRing ring;
                            for(size_t
j=0;j<result_i_simplified.outer().size();++j)
                                ring.addPoint(
result_i_simplified.outer()[j].x(), result_i_simplified.outer()[j].y() );
                            poly.addRing(&ring);
                        }

                        {
                            OGRLinearRing ring;
                            for(size_t
j=0;j<result_i_simplified.inners().size();++j)
                            {
                                for(size_t
k=0;k<result_i_simplified.inners()[j].size();++k)
                                {
                                    ring.addPoint(
result_i_simplified.inners()[j][k].x(),
result_i_simplified.inners()[j][k].y() );
                                }
                                poly.addRing(&ring);
                            }
                        }
                    }

Note that I use a simplification algorithm after buffering to remove
colinear points.

Hope you could help.

Best regards,

Olivier



Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net