c06_custom_polygon_example.cpp

Showing a custom polygon (asked on the list during Formal Review)

    //Boost.Geometry(akaGGL,GenericGeometryLibrary)

    //Copyright(c)2007-2012BarendGehrels,Amsterdam,theNetherlands.
    //Copyright(c)2008-2012BrunoLalande,Paris,France.
    //Copyright(c)2009-2012MateuszLoskot,London,UK.

    //Use,modificationanddistributionissubjecttotheBoostSoftwareLicense,
    //Version1.0.(SeeaccompanyingfileLICENSE_1_0.txtorcopyat
    //http://www.boost.org/LICENSE_1_0.txt)
    //
    //CustomPolygonExample
    #include<iostream>

    #include<boost/geometry/geometry.hpp>

    #include<boost/geometry/geometries/register/point.hpp>
    #include<boost/geometry/geometries/register/ring.hpp>

    structmy_point
    {
    my_point(doublean_x=0,doublean_y=0)
    :x(an_x)
    ,y(an_y)
    {}

    doublex,y;
    };

    structmy_ring:std::deque<my_point>
    {};

    //Defineastructofapolygon,havingalwaystwoholes
    //(ofcoursethiscanbeimplementeddifferently,usually
    //withavectorordeque,butitisjustanexampe)
    structmy_polygon
    {
    //requiredforapolygon:anouterring...
    my_ringboundary;
    //...andaBoost.Rangecompatibleinnerringcollection
    boost::array<my_ring,2>holes;

    //justforthesample
    std::stringname;

    my_polygon(std::stringconst&n=""):name(n){}
    };

    //Wecanconvenientlyusemacro'storegisterpointandring
    BOOST_GEOMETRY_REGISTER_POINT_2D(my_point,double,cs::cartesian,x,y)
    BOOST_GEOMETRY_REGISTER_RING(my_ring)

    //Thereiscurrentlynoregistrationmacroforpolygons
    //andbesidesthataboost::array<T,N>inamacrowould
    //beveryspecific,soweshowit"byhand":
    namespaceboost{namespacegeometry{namespacetraits
    {

    template<>structtag<my_polygon>{typedefpolygon_tagtype;};
    template<>structring_const_type<my_polygon>{typedefmy_ringconst&type;};
    template<>structring_mutable_type<my_polygon>{typedefmy_ring&type;};

    template<>structinterior_const_type<my_polygon>
    {
    typedefboost::array<my_ring,2>const&type;
    };

    template<>structinterior_mutable_type<my_polygon>
    {
    typedefboost::array<my_ring,2>&type;
    };

    template<>structexterior_ring<my_polygon>
    {
    staticmy_ring&get(my_polygon&p)
    {
    returnp.boundary;
    }

    staticmy_ringconst&get(my_polygonconst&p)
    {
    returnp.boundary;
    }
    };

    template<>structinterior_rings<my_polygon>
    {
    typedefboost::array<my_ring,2>holes_type;

    staticholes_type&get(my_polygon&p)
    {
    returnp.holes;
    }

    staticholes_typeconst&get(my_polygonconst&p)
    {
    returnp.holes;
    }
    };

    }}}//namespaceboost::geometry::traits

    intmain()
    {
    my_polygonp1("mypolygon");

    //Fillitthemy-way,triangle
    p1.boundary.push_back(my_point(2,0));
    p1.boundary.push_back(my_point(1,5));
    p1.boundary.push_back(my_point(7,6));
    p1.boundary.push_back(my_point(2,0));

    //Triangle
    p1.holes[0].push_back(my_point(2,1));
    p1.holes[0].push_back(my_point(2.4,2));
    p1.holes[0].push_back(my_point(1.9,2));
    p1.holes[0].push_back(my_point(2,1));

    //Box
    p1.holes[1].push_back(my_point(3,3));
    p1.holes[1].push_back(my_point(4,3));
    p1.holes[1].push_back(my_point(4,4));
    p1.holes[1].push_back(my_point(3,4));
    p1.holes[1].push_back(my_point(3,3));

    std::cout<<"Representationof"<<p1.name<<":"
    <<boost::geometry::dsv(p1)<<std::endl;
    std::cout<<"Areaof"<<p1.name<<":"
    <<boost::geometry::area(p1)<<std::endl;
    std::cout<<"Perimeterof"<<p1.name<<":"
    <<boost::geometry::perimeter(p1)<<std::endl;
    std::cout<<"Centroidof"<<p1.name<<":"
    <<boost::geometry::dsv(boost::geometry::return_centroid<my_point>(p1))<<std::endl;

    return0;
    }