[/============================================================================
  Boost.Geometry (aka GGL, Generic Geometry Library)

  Copyright (c) 2009-2012 Mateusz Loskot, London, UK.
  Copyright (c) 2009-2012 Barend Gehrels, Amsterdam, the Netherlands.
  Copyright (c) 2009-2012 Bruno Lalande, Paris, France.

  Use, modification and distribution is subject to the Boost Software License,
  Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
  http://www.boost.org/LICENSE_1_0.txt)
=============================================================================/]

[section:concept_polygon Polygon Concept]

[heading Description]
[concept Polygon..polygon]

['A polygon is a planar surface defined by one exterior boundary and zero or more interior boundaries]
(__ogc_sf__).

So the definition of a Boost.Geometry polygon differs a bit from e.g. Wiki, where a polygon does not have holes. A
polygon of Boost.Geometry is a polygon with or without holes.
['(A polygon without holes is a ['helper geometry] within Boost.Geometry, and referred to as a ring.)]

[heading Concept Definition]

The Polygon Concept is defined as following:

* there must be a specialization of `traits::tag` defining `polygon_tag` as type
* there must be a specialization of `traits::ring_mutable_type` defining the mutable types of its exterior and interior rings as type
* there must be a specialization of `traits::ring_const_type` defining the constant types of its exterior and interior rings as type
* `traits::ring_mutable_type` and `traits::ring_const_type` must fulfill the [link geometry.reference.concepts.concept_ring Ring Concept]
* there must be a specialization of `traits::interior_mutable_type` defining the mutable type of the collection of its interior rings as type;
* there must be a specialization of `traits::interior_const_type` defining the constant type of the collection of its interior rings as type;
    each of these collections itself must fulfill a Boost.Range Random Access Range Concept
* there must be a specialization of `traits::exterior_ring` with two functions named `get`, returning the exterior ring, one being const, the other being non const
* there must be a specialization of `traits::interior_rings` with two functions named `get`, returning the interior rings, one being const, the other being non const

[heading Rules]

Besides the Concepts, which are checks on compile-time, there are some other
rules that valid polygons must fulfill. This follows the opengeospatial rules (see link
above).

* Polygons are simple geometric objects (See also [@http://en.wikipedia.org/wiki/Simple_polygon wiki]
    but holes are allowed in __boost_geometry__ polygons).
* If the polygons underlying `ring_type` is defined as clockwise, the exterior
    ring must have the clockwise orientation, and any interior ring must be
    reversed w.r.t. the defined orientation (so: counter clockwise for clockwise exterior rings).
    If the `ring_type` is defined counter clockwise, it is vice versa.
* If the polygons underlying `ring_type` is defined as closed, all rings must be
    closed: the first point must be spatially equal to the last point.
* The interior is a connected point set.
* There should be no self intersections, but self tangencies (between
    exterior/interior rings) are allowed (as long as the interior is a connected
    point set.
* There should be no cut lines, spikes or punctures.
* The interior rings should be located within the exterior ring. Interior rings
    may not be located within each other.

The algorithms such as intersection, area, centroid, union, etc. do not check
validity. There will be an algorithm is_valid which checks for
validity against these rules, at runtime, and which can be called (by the library
user) before.

If the input is invalid, the output might be invalid too. For example: if a polygon
which should be closed is not closed, the area will be incorrect.

[heading Available Models]
* [link geometry.reference.models.model_polygon polygon]
* a Boost.Polygon polygon_with_holes_data (requires `#include boost/geometry/geometries/adapted/boost_polygon/polygon.hpp>`)

[endsect]
