$include_dir="/home/hyper-archives/boost-commit/include"; include("$include_dir/msg-header.inc") ?>
Subject: [Boost-commit] svn:boost r77061 - in trunk/boost/geometry/extensions: algorithms/buffer strategies
From: barend.gehrels_at_[hidden]
Date: 2012-02-18 05:07:22
Author: barendgehrels
Date: 2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
New Revision: 77061
URL: http://svn.boost.org/trac/boost/changeset/77061
Log:
Boost.Geometry Substantial progress on buffer
Added:
   trunk/boost/geometry/extensions/algorithms/buffer/buffer_inserter.hpp   (contents, props changed)
   trunk/boost/geometry/extensions/algorithms/buffer/buffered_piece_collection.hpp   (contents, props changed)
   trunk/boost/geometry/extensions/algorithms/buffer/buffered_ring.hpp   (contents, props changed)
Removed:
   trunk/boost/geometry/extensions/algorithms/buffer/linestring_buffer.hpp
   trunk/boost/geometry/extensions/algorithms/buffer/polygon_buffer.hpp
   trunk/boost/geometry/extensions/algorithms/buffer/range_buffer.hpp
   trunk/boost/geometry/extensions/algorithms/buffer/sectionalizing_buffer.hpp
   trunk/boost/geometry/extensions/algorithms/buffer/segmenting_buffer.hpp
   trunk/boost/geometry/extensions/algorithms/buffer/splitting_buffer.hpp
   trunk/boost/geometry/extensions/algorithms/buffer/traversing_buffer.hpp
Text files modified: 
   trunk/boost/geometry/extensions/algorithms/buffer/buffer_appender.hpp |    46 ------------                            
   trunk/boost/geometry/extensions/strategies/buffer.hpp                 |   143 ++++++--------------------------------- 
   2 files changed, 24 insertions(+), 165 deletions(-)
Modified: trunk/boost/geometry/extensions/algorithms/buffer/buffer_appender.hpp
==============================================================================
--- trunk/boost/geometry/extensions/algorithms/buffer/buffer_appender.hpp	(original)
+++ trunk/boost/geometry/extensions/algorithms/buffer/buffer_appender.hpp	2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
@@ -29,29 +29,15 @@
 // Appends points to an output range (always a ring).
 // On the way, special points can be marked, and marked points
 // forming a hooklet, loop, curve, curl, or how you call it are checked on intersections.
-template
-    <
-        typename Range
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-        , typename Mapper
-#endif
-    >
+template<typename Range>
 class buffer_appender
 {
 public :
     typedef Range range_type;
     typedef typename geometry::point_type<Range>::type point_type;
 
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-    Mapper const& m_mapper;
-    inline buffer_appender(Range& r, Mapper const& mapper)
-        : m_range(r)
-        , m_mapper(mapper)
-#else
     inline buffer_appender(Range& r)
         : m_range(r)
-#endif
-
     {}
 
     inline void append(point_type const& point)
@@ -83,9 +69,6 @@
     inline void append_begin_hooklet(point_type const& point)
     {
         DEBUG("begin hooklet");
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-        const_cast<Mapper&>(m_mapper).map(point, "fill:rgb(0,0,192);", 3);
-#endif
 
         check(point);
 
@@ -99,9 +82,6 @@
     inline void append_end_hooklet(point_type const& point)
     {
         DEBUG("end hooklet");
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-        const_cast<Mapper&>(m_mapper).map(point, "fill:rgb(0,0,255);", 4);
-#endif
 
         do_append(point);
     }
@@ -177,12 +157,6 @@
             }
         }
 
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-        if (! m_pieces.empty() && m_pieces.back().end > m_pieces.back().begin)
-        {
-            const_cast<Mapper&>(m_mapper).map(point, "fill:rgb(0,255,0);", 4);
-        }
-#endif
     }
 
     inline bool calculate_ip(point_type const& point, piece const& the_piece)
@@ -193,14 +167,6 @@
             return false;
         }
 
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-        const_cast<Mapper&>(m_mapper).map(point, "fill:rgb(255,0,0);", 4);
-        for (int i = the_piece.begin; i <= the_piece.end && i < n; i++)
-        {
-            //const_cast<Mapper&>(m_mapper).map(m_range[i], "fill:rgb(0,255,255);", 3);
-        }
-#endif
-
         segment_type segment1(m_previous_point, point);
 
         // Walk backwards through list (chance is higher to have IP at the end)
@@ -215,11 +181,6 @@
                 if (get_valid_split(is.intersections[0], i + 1, split_off))
                 {
                     add_ip(is.intersections[0], i + 1, the_piece, split_off);
-
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                    const_cast<Mapper&>(m_mapper).map(is.intersections[0], "fill:rgb(255,0,255);", 4);
-                    const_cast<Mapper&>(m_mapper).map(split_off, "fill:none;stroke:rgb(255,0,0);stroke-width:2");
-#endif
                 }
 
                 return true;
@@ -253,11 +214,6 @@
 
                         add_ip(is.intersections[0], the_piece.begin + 1, the_piece, split_off);
 
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                        const_cast<Mapper&>(m_mapper).map(is.intersections[0], "fill:rgb(255,255,0);", 4);
-                        const_cast<Mapper&>(m_mapper).map(m_range[the_piece.begin], "fill:rgb(255,192,0);", 4);
-                        const_cast<Mapper&>(m_mapper).map(split_off, "fill:none;stroke:rgb(255,192,0);stroke-width:2");
-#endif
                         return true;
                     }
 
Added: trunk/boost/geometry/extensions/algorithms/buffer/buffer_inserter.hpp
==============================================================================
--- (empty file)
+++ trunk/boost/geometry/extensions/algorithms/buffer/buffer_inserter.hpp	2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
@@ -0,0 +1,324 @@
+// Boost.Geometry (aka GGL, Generic Geometry Library)
+
+// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
+
+// 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)
+
+#ifndef BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_BUFFER_INSERTER_HPP
+#define BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_BUFFER_INSERTER_HPP
+
+#include <cstddef>
+
+#include <boost/numeric/conversion/cast.hpp>
+
+#include <boost/range.hpp>
+#include <boost/typeof/typeof.hpp>
+
+#include <boost/geometry/core/exterior_ring.hpp>
+#include <boost/geometry/core/interior_rings.hpp>
+
+#include <boost/geometry/extensions/strategies/buffer_side.hpp>
+#include <boost/geometry/extensions/algorithms/buffer/buffered_piece_collection.hpp>
+#include <boost/geometry/extensions/algorithms/buffer/line_line_intersection.hpp>
+
+
+namespace boost { namespace geometry
+{
+
+#ifndef DOXYGEN_NO_DETAIL
+namespace detail { namespace buffer
+{
+
+
+template
+<
+    typename RingOutput,
+    typename Tag
+>
+struct buffer_range
+{
+    typedef typename point_type<RingOutput>::type output_point_type;
+    typedef typename coordinate_type<RingOutput>::type coordinate_type;
+    typedef model::referring_segment<output_point_type const> segment_type;
+
+    template
+    <
+        typename Collection,
+        typename Iterator,
+        typename DistanceStrategy,
+        typename JoinStrategy
+    >
+    static inline void iterate(Collection& collection,
+                Iterator begin, Iterator end,
+                buffer_side_selector side,
+                DistanceStrategy const& distance,
+                JoinStrategy const& join_strategy
+            )
+    {
+        output_point_type previous_p1, previous_p2;
+        output_point_type first_p1, first_p2;
+
+        bool first = true;
+
+        Iterator it = begin;
+        for (Iterator prev = it++; it != end; ++it)
+        {
+            if (! detail::equals::equals_point_point(*prev, *it))
+            {
+                // Generate a block along (left or right of) the segment
+
+                // Simulate a vector d (dx,dy)
+                coordinate_type dx = get<0>(*it) - get<0>(*prev);
+                coordinate_type dy = get<1>(*it) - get<1>(*prev);
+
+                // For normalization [0,1] (=dot product d.d, sqrt)
+                coordinate_type length = sqrt(dx * dx + dy * dy);
+
+                // Because coordinates are not equal, length should not be zero
+                BOOST_ASSERT((! geometry::math::equals(length, 0)));
+
+                // Generate the normalized perpendicular p, to the left (ccw)
+                coordinate_type px = -dy / length;
+                coordinate_type py = dx / length;
+
+                output_point_type p1, p2;
+
+                coordinate_type d = distance.apply(*prev, *it, side);
+
+                set<0>(p2, get<0>(*it) + px * d);
+                set<1>(p2, get<1>(*it) + py * d);
+
+                set<0>(p1, get<0>(*prev) + px * d);
+                set<1>(p1, get<1>(*prev) + py * d);
+
+                std::vector<output_point_type> range_out;
+                if (! first)
+                {
+                    output_point_type p;
+                    segment_type s1(p1, p2);
+                    segment_type s2(previous_p1, previous_p2);
+
+                    if (line_line_intersection<output_point_type, segment_type>::apply(s1, s2, p))
+                    {
+                        join_strategy.apply(p, *prev, previous_p2, p1,
+                                    distance.apply(*prev, *it, side),
+                                    range_out);
+                    }
+                }
+                else
+                {
+                    first = false;
+                    first_p1 = p1;
+                    first_p2 = p2;
+                }
+                if (! range_out.empty())
+                {
+                    collection.add_piece(*prev, range_out);
+                    range_out.clear();
+                }
+                collection.add_piece(*prev, *it, p1, p2);
+
+                previous_p1 = p1;
+                previous_p2 = p2;
+                prev = it;
+            }
+        }
+
+        // Might be replaced by specialization
+        if(boost::is_same<Tag, ring_tag>::value)
+        {
+            // Generate closing corner
+            output_point_type p;
+            segment_type s1(previous_p1, previous_p2);
+            segment_type s2(first_p1, first_p2);
+            line_line_intersection<output_point_type, segment_type>::apply(s1, s2, p);
+
+            std::vector<output_point_type> range_out;
+            join_strategy.apply(p, *begin, previous_p2, first_p1,
+                distance.apply(*(end - 1), *begin, side),
+                range_out);
+            if (! range_out.empty())
+            {
+                collection.add_piece(*begin, range_out);
+            }
+
+            // Buffer is closed automatically by last closing corner (NOT FOR OPEN POLYGONS - TODO)
+        }
+    }
+};
+
+}} // namespace detail::buffer
+#endif // DOXYGEN_NO_DETAIL
+
+
+#ifndef DOXYGEN_NO_DISPATCH
+namespace dispatch
+{
+
+template
+<
+    typename Tag,
+    typename RingInput,
+    typename RingOutput
+>
+struct buffer_inserter
+{};
+
+
+template
+<
+    typename RingInput,
+    typename RingOutput
+>
+struct buffer_inserter<ring_tag, RingInput, RingOutput>
+    : public detail::buffer::buffer_range
+        <
+            RingOutput, 
+            ring_tag
+        >
+{
+
+    template
+    <
+        typename Collection, typename DistanceStrategy, typename JoinStrategy
+    >
+    static inline void apply(RingInput const& ring,
+            Collection& collection,
+            DistanceStrategy const& distance,
+            JoinStrategy const& join_strategy)
+    {
+        iterate(collection, boost::begin(ring), boost::end(ring),
+                buffer_side_left,
+                distance, join_strategy);
+    }
+};
+
+
+template
+<
+    typename Linestring,
+    typename Polygon
+>
+struct buffer_inserter<linestring_tag, Linestring, Polygon>
+    : public detail::buffer::buffer_range
+        <
+            typename ring_type<Polygon>::type, 
+            linestring_tag
+        >
+{
+
+    template<typename Collection, typename DistanceStrategy, typename JoinStrategy>
+    static inline void apply(Linestring const& linestring, Collection& collection,
+            DistanceStrategy const& distance,
+            JoinStrategy const& join_strategy)
+    {
+        collection.add_input();
+        iterate(collection, boost::begin(linestring), boost::end(linestring),
+                buffer_side_left,
+                distance, join_strategy);
+
+        iterate(collection, boost::rbegin(linestring), boost::rend(linestring),
+                buffer_side_right,
+                distance, join_strategy);
+
+    }
+};
+
+
+template
+<
+    typename PolygonInput,
+    typename PolygonOutput
+>
+struct buffer_inserter<polygon_tag, PolygonInput, PolygonOutput>
+{
+
+    template <typename Collection, typename DistanceStrategy, typename JoinStrategy>
+    static inline void apply(PolygonInput const& polygon, Collection& collection,
+            DistanceStrategy const& distance,
+            JoinStrategy const& join_strategy)
+    {
+
+        typedef typename ring_type<PolygonInput>::type input_ring_type;
+        typedef typename ring_type<PolygonOutput>::type output_ring_type;
+
+        typedef buffer_inserter<ring_tag, input_ring_type, output_ring_type> policy;
+
+        {
+            collection.add_input();
+
+            policy::apply(exterior_ring(polygon), collection,
+                    distance, join_strategy);
+        }
+
+        typename interior_return_type<PolygonInput const>::type rings
+                    = interior_rings(polygon);
+        for (BOOST_AUTO_TPL(it, boost::begin(rings)); it != boost::end(rings); ++it)
+        {
+            output_ring_type ring;
+
+            collection.add_input();
+
+            policy::apply(*it, collection, distance, join_strategy);
+        }
+
+    }
+};
+
+
+} // namespace dispatch
+#endif // DOXYGEN_NO_DISPATCH
+
+
+template
+<
+    typename GeometryOutput,
+    typename GeometryInput,
+    typename OutputIterator,
+    typename DistanceStrategy,
+    typename JoinStrategy
+#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
+    , typename Mapper
+#endif
+>
+inline void buffer_inserter(GeometryInput const& geometry_input, OutputIterator out,
+        DistanceStrategy const& distance_strategy, JoinStrategy const& join_strategy
+#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
+            , Mapper& mapper
+#endif
+    )
+{
+    detail::buffer::buffered_piece_collection<typename geometry::ring_type<GeometryOutput>::type> collection;
+
+    dispatch::buffer_inserter
+        <
+            typename tag<GeometryInput>::type, 
+            GeometryInput, 
+            GeometryOutput
+        >::apply(geometry_input, collection, distance_strategy, join_strategy);
+
+    collection.get_turns(geometry_input);
+
+#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
+    collection.map_offsetted(mapper);
+#endif
+
+    collection.discard_points();
+    collection.enrich();
+    collection.traverse();
+
+#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
+    //collection.map<geometry::polygon_tag>(mapper);
+    collection.map_turns(mapper);
+    collection.map_traverse(mapper);
+#endif
+
+    collection.assign<GeometryOutput>(out);
+}
+
+
+}} // namespace boost::geometry
+
+#endif // BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_BUFFER_INSERTER_HPP
Added: trunk/boost/geometry/extensions/algorithms/buffer/buffered_piece_collection.hpp
==============================================================================
--- (empty file)
+++ trunk/boost/geometry/extensions/algorithms/buffer/buffered_piece_collection.hpp	2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
@@ -0,0 +1,657 @@
+// Boost.Geometry (aka GGL, Generic Geometry Library)
+
+// Copyright (c) 2012 Barend Gehrels, Amsterdam, the Netherlands.
+
+// 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)
+
+#ifndef BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_BUFFERED_PIECE_COLLECTION_HPP
+#define BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_BUFFERED_PIECE_COLLECTION_HPP
+
+#include <cstddef>
+
+#include <boost/range.hpp>
+
+#include <boost/geometry/core/coordinate_type.hpp>
+#include <boost/geometry/core/point_type.hpp>
+
+#include <boost/geometry/algorithms/equals.hpp>
+#include <boost/geometry/algorithms/covered_by.hpp>
+#include <boost/geometry/extensions/strategies/buffer_side.hpp>
+
+#include <boost/geometry/algorithms/detail/overlay/turn_info.hpp>
+#include <boost/geometry/algorithms/detail/overlay/enrichment_info.hpp>
+#include <boost/geometry/algorithms/detail/overlay/traversal_info.hpp>
+
+#include <boost/geometry/extensions/algorithms/buffer/buffered_ring.hpp>
+
+
+
+
+namespace boost { namespace geometry
+{
+
+
+#ifndef DOXYGEN_NO_DETAIL
+namespace detail { namespace buffer
+{
+
+
+class backtrack_for_buffer
+{
+public :
+    typedef detail::overlay::backtrack_state state_type;
+
+    template <typename Operation, typename Rings, typename Turns, typename Geometry>
+    static inline void apply(std::size_t size_at_start, 
+                Rings& rings, typename boost::range_value<Rings>::type& ring,
+                Turns& turns, Operation& operation,
+                std::string const& reason,
+                Geometry const& ,
+                Geometry const& ,
+                state_type& state
+                )
+    {
+std::cout << "WARNING " << reason << std::endl;
+
+        // TODO this is a copy of dissolve, check this for buffer
+        state.m_good = false;
+        
+        // Make bad output clean
+        rings.resize(size_at_start);
+        ring.clear();
+
+        // Reject this as a starting point
+        operation.visited.set_rejected();
+
+        // And clear all visit info
+        clear_visit_info(turns);
+    }
+};
+
+enum intersection_location_type
+{
+    location_ok, inside_buffer, inside_original
+};
+
+
+// Shoould follow traversal-turn-concept (enrichment, visit structure)
+// and adds index in piece vector to find it back
+template <typename Point>
+struct buffer_turn_operation : public detail::overlay::traversal_turn_operation<Point>
+{
+    int piece_index;
+
+    inline buffer_turn_operation()
+        : piece_index(-1)
+    {}
+};
+
+// Add an "intersection_location_type" which gets true for all intersection points lying inside the buffer or original polygon
+template <typename Point>
+struct buffer_turn_info : public detail::overlay::turn_info<Point, buffer_turn_operation<Point> >
+{
+    intersection_location_type location;
+
+    inline buffer_turn_info()
+        : location(location_ok)
+    {}
+};
+
+
+template <typename Ring>
+struct buffered_piece_collection
+{
+    typedef typename geometry::point_type<Ring>::type Point;
+    typedef typename strategy::side::services::default_strategy<typename cs_tag<Point>::type>::type side;
+
+    enum piece_type
+    {
+        buffered_segment, buffered_join
+    };
+
+    template <typename Turn>
+    struct redundant_turn
+    {
+        inline bool operator()(Turn const& turn) const
+        {
+            return turn.location != location_ok;
+        }
+    };
+
+    struct piece
+    {
+        piece_type type;
+        int index;
+        segment_identifier seg_id;
+
+        // -----------------------------------------------------------------
+        // type=buffered_segment:
+
+        // This buffered_segment (2 points of the original)
+        Point p1, p2;
+
+        // The buffered buffered_segment (offsetted with certain distance to left/right)
+        Point b1, b2;
+
+        // -----------------------------------------------------------------
+        // type=buffered_join
+        Point p;
+
+        // Corner next to this buffered_segment (so connected to p2 and b2).
+        // In case p2 is a concave point, corner is empty
+        Ring corner; // TODO redundant
+
+        // Filled for both:
+        typedef geometry::model::linestring<Point> buffered_vector_type;
+
+        buffered_vector_type offseted_segment;
+    };
+
+    typedef std::vector<piece> piece_vector;
+    piece_vector all_pieces;
+    buffered_ring_collection<buffered_ring<Ring> > offsetted_rings;
+    buffered_ring_collection<Ring> traversed_rings;
+    segment_identifier current_segment_id;
+
+    typedef std::vector<buffer_turn_info<Point> > turn_vector_type;
+    typedef detail::overlay::get_turn_info
+        <
+            Point, Point, buffer_turn_info<Point>,
+            detail::overlay::calculate_distance_policy
+        > turn_policy;
+    turn_vector_type turn_vector;
+
+
+
+    inline buffered_piece_collection()
+    {}
+
+
+    inline bool within_piece(buffer_turn_info<Point> const& turn, piece const& pc) const
+    {
+        bool const collinear =
+            turn.operations[0].operation == detail::overlay::operation_continue
+            && turn.operations[0].operation == detail::overlay::operation_continue;
+
+        // For now: use within, using built-up corner (which will be redundant later)
+
+        // Because pieces are always concave we only have to verify if it is left of all segments.
+        // As soon as it is right of one, we can quit. This is faster than the normal within,
+        // and we don't have to build up the polygon.
+        if (collinear)
+        {
+            // ONLY for the outer-boundary: return within
+            return geometry::within(turn.point, pc.corner);
+        }
+
+        return geometry::covered_by(turn.point, pc.corner);
+    }
+
+    // Checks if an intersection point is within one of all pieces
+    // (but skip the pieces of which this intersection point is the result
+    inline bool is_wrong(buffer_turn_info<Point> const& turn, piece const& piece1, piece const& piece2) const
+    {
+        // We might do this using partition.
+        typename std::vector<piece>::const_iterator it;
+        for (it = boost::begin(all_pieces);
+            it != boost::end(all_pieces);
+            ++it)
+        {
+            if (it->index != piece1.index && it->index != piece2.index)
+            {
+                if (within_piece(turn, *it))
+                {
+                    return true;
+                }
+            }
+        }
+
+        return false;
+
+    }
+
+    inline bool is_neighbor(piece const& piece1, piece const& piece2) const
+    {
+        if (std::abs(piece1.index - piece2.index) == 1)
+        {
+            return true;
+        }
+
+        int const b = boost::size(all_pieces) - 1; // back
+        return (piece1.index == 0 && piece2.index == b)
+            || (piece1.index == b && piece2.index == 0)
+            ;
+    }
+
+    inline bool skip_neighbor(piece const& piece1, piece const& piece2) const
+    {
+        return piece1.type != piece2.type && is_neighbor(piece1, piece2);
+    }
+
+    template <typename Iterator>
+    inline Point next_point(piece const& piece, Iterator it) const
+    {
+        // Next point in current offseted:
+        Iterator next = it;
+        ++next;
+        if (next != boost::end(piece.offseted_segment))
+        {
+            return *next;
+        }
+
+        // TODO: check if there is a second point (there should be one)
+        // Second point from next piece:
+        int next_index = piece.index + 1;
+        if (next_index >= boost::size(all_pieces))
+        {
+            next_index = 0;
+        }
+        return piece.offseted_segment[1];
+    }
+
+    inline void calculate_turns(piece const& piece1, piece const& piece2)
+    {
+        buffer_turn_info<Point> the_model;
+        the_model.operations[0].piece_index = piece1.index;
+        the_model.operations[0].seg_id = piece1.seg_id;
+
+        // TODO use partition
+        typedef typename boost::range_iterator<typename piece::buffered_vector_type const>::type iterator;
+        iterator it1 = boost::begin(piece1.offseted_segment);
+        for (iterator prev1 = it1++; 
+                it1 != boost::end(piece1.offseted_segment); 
+                prev1 = it1++, the_model.operations[0].seg_id.segment_index++)
+        {
+            the_model.operations[1].piece_index = piece2.index;
+            the_model.operations[1].seg_id = piece2.seg_id;
+
+            iterator it2 = boost::begin(piece2.offseted_segment);
+            for (iterator prev2 = it2++; 
+                    it2 != boost::end(piece2.offseted_segment); 
+                    prev2 = it2++, the_model.operations[1].seg_id.segment_index++)
+            {
+                // Revert (this is used more often - should be common function TODO)
+                the_model.operations[0].other_id = the_model.operations[1].seg_id;
+                the_model.operations[1].other_id = the_model.operations[0].seg_id;
+
+
+                turn_vector_type turns; // TEMPORARY in the end we can add directly to turn_vector
+                turn_policy::apply(*prev1, *it1, next_point(piece1, it1),
+                                    *prev2, *it2, next_point(piece2, it2),
+                                    the_model, std::back_inserter(turns));
+
+                // Add buffered_segment identifier info
+                for (typename boost::range_iterator<turn_vector_type>::type it =
+                    boost::begin(turns); it != boost::end(turns); ++it)
+                {
+                    // TODO: much later in partition.
+                    if (is_wrong(*it, piece1, piece2))
+                    {
+                        it->location = inside_buffer;
+                    }
+                    turn_vector.push_back(*it);
+                }
+            }
+        }
+    }
+
+    template <typename Geometry>
+    inline void check_remaining_points(Geometry const& input_geometry)
+    {
+        // TODO: this should be done as a collection-of-points, for performance
+        for (typename boost::range_iterator<turn_vector_type>::type it =
+            boost::begin(turn_vector); it != boost::end(turn_vector); ++it)
+        {
+            if (it->location == location_ok)
+            {
+                if (geometry::covered_by(it->point, input_geometry))
+                {
+                    it->location = inside_original;
+                }
+            }
+        }
+    }
+
+
+    template <typename Geometry>
+    inline void get_turns(Geometry const& input_geometry)
+    {
+        for(typename piece_vector::const_iterator it1 = boost::begin(all_pieces);
+            it1 != boost::end(all_pieces);
+            ++it1)
+        {
+            for(typename piece_vector::const_iterator it2 = it1 + 1;
+                it2 != boost::end(all_pieces);
+                ++it2)
+            {
+                if (! skip_neighbor(*it1, *it2))
+                {
+                    calculate_turns(*it1, *it2);
+                }
+            }
+        }
+        if (boost::is_same<typename tag_cast<typename tag<Geometry>::type, areal_tag>::type, areal_tag>())
+        {
+            check_remaining_points(input_geometry);
+        }
+
+        calculate_discarded();
+    }
+
+    inline void add_input()
+    {
+        int const n = offsetted_rings.size();
+        current_segment_id.source_index = 0;
+        current_segment_id.multi_index = n;
+        current_segment_id.ring_index = -1;
+        current_segment_id.segment_index = 0;
+
+        offsetted_rings.resize(n + 1);
+    }
+
+    inline void add_point(Point const& p)
+    {
+        BOOST_ASSERT
+            (
+                boost::size(offsetted_rings) > 0
+            );
+
+        current_segment_id.segment_index++;
+        offsetted_rings.back().push_back(p);
+    }
+
+
+    inline piece& add_piece(piece_type type, bool decrease_by_one)
+    {
+        piece pc;
+        pc.type = type;
+        pc.index = boost::size(all_pieces);
+        pc.seg_id = current_segment_id;
+
+        std::size_t const n = boost::size(offsetted_rings.back());
+
+        pc.seg_id.segment_index = decrease_by_one ? n - 1 : n;
+
+        all_pieces.push_back(pc);
+        return all_pieces.back();
+    }
+
+
+    inline void add_piece(Point const& p1, Point const& p2, 
+            Point const& b1, Point const& b2)
+    {
+        bool const last_type_join = ! all_pieces.empty() 
+                && all_pieces.back().type != buffered_segment;
+
+        piece& pc = add_piece(buffered_segment, last_type_join);
+
+        pc.p1 = p1;
+        pc.p2 = p2;
+        pc.b1 = b1;
+        pc.b2 = b2;
+
+        // If it follows the same piece-type point both should be added.
+        // There should be two intersections later and it should be discarded.
+        // But for need it to calculate intersections
+        if (! last_type_join)
+        {
+            add_point(b1);
+        }
+        add_point(b2);
+
+        // TEMPORARY
+        pc.corner.push_back(p1);
+        pc.corner.push_back(b1);
+        pc.corner.push_back(b2);
+        pc.corner.push_back(p2);
+        pc.corner.push_back(p1);
+        // END TEMPORARY
+
+        pc.offseted_segment.push_back(b1);
+        pc.offseted_segment.push_back(b2);
+    }
+
+    template <typename Corner>
+    inline void add_piece(Point const& p, Corner const& corner)
+    {
+        piece& pc = add_piece(buffered_join, true);
+
+        pc.p = p;
+
+        pc.corner.push_back(p);// TEMPORARY
+        bool first = true;
+        for (typename Corner::const_iterator it = boost::begin(corner);
+            it != boost::end(corner);
+            ++it)
+        {
+            bool add = true;
+            if (first)
+            {
+                // Only for very first one, add first. In all other cases it is shared with previous.
+                add = offsetted_rings.back().empty();
+                first = false;
+            }
+            if (add)
+            {
+                add_point(*it);
+            }
+            pc.corner.push_back(*it); // TEMPORARY
+            pc.offseted_segment.push_back(*it); // REDUNDANT
+        }
+        pc.corner.push_back(p);// TEMPORARY
+    }
+
+    inline void enrich()
+    {
+        typedef typename strategy::side::services::default_strategy
+        <
+            typename cs_tag<Ring>::type
+        >::type side_strategy_type;
+
+        enrich_intersection_points<false, false>(turn_vector,
+                    detail::overlay::operation_union,
+                    offsetted_rings, offsetted_rings,
+                    side_strategy_type());
+    }
+
+    // Discards all rings which do have not-OK intersection points only.
+    // Those can never be traversed and should not be part of the output.
+    inline void calculate_discarded()
+    {
+        for (typename boost::range_iterator<turn_vector_type const>::type it =
+            boost::begin(turn_vector); it != boost::end(turn_vector); ++it)
+        {
+            if (it->location != location_ok)
+            {
+                offsetted_rings[it->operations[0].seg_id.multi_index].has_discarded_intersections = true;
+                offsetted_rings[it->operations[1].seg_id.multi_index].has_discarded_intersections = true;
+            }
+            else
+            {
+                offsetted_rings[it->operations[0].seg_id.multi_index].has_accepted_intersections = true;
+                offsetted_rings[it->operations[1].seg_id.multi_index].has_accepted_intersections = true;
+            }
+        }
+    }
+                    
+    inline void discard_points()
+    {
+        // Erase all points being inside
+        turn_vector.erase(
+            std::remove_if(boost::begin(turn_vector), boost::end(turn_vector), redundant_turn<buffer_turn_info<Point> >()),
+            boost::end(turn_vector));
+
+    }
+
+    inline void traverse()
+    {
+        typedef detail::overlay::traverse
+            <
+                false, false, 
+                buffered_ring_collection<buffered_ring<Ring > >, buffered_ring_collection<buffered_ring<Ring > >,
+                backtrack_for_buffer
+            > traverser;
+
+        traversed_rings.clear();
+        traverser::apply(offsetted_rings, offsetted_rings,
+                        detail::overlay::operation_union,
+                        turn_vector, traversed_rings);
+    }
+
+    template <typename GeometryOutput, typename OutputIterator>
+    inline OutputIterator assign(OutputIterator out)
+    {
+        typedef detail::overlay::ring_properties<Point> properties;
+
+        std::map<ring_identifier, properties> selected;
+
+        // Select all rings which do not have any self-intersection (other ones should be traversed)
+        int index = 0;
+        for(typename buffered_ring_collection<buffered_ring<Ring> >::const_iterator it = boost::begin(offsetted_rings);
+            it != boost::end(offsetted_rings);
+            ++it, ++index)
+        {
+            if (! it->has_intersections())
+            {
+                ring_identifier id(0, index, -1);
+                selected[id] = properties(*it, true);
+            }
+        }
+
+        // Select all created rings
+        index = 0;
+        for (typename boost::range_iterator<buffered_ring_collection<Ring> const>::type
+                it = boost::begin(traversed_rings);
+                it != boost::end(traversed_rings);
+                ++it, ++index)
+        {
+            ring_identifier id(2, index, -1);
+            selected[id] = properties(*it, true);
+        }
+
+        detail::overlay::assign_parents(offsetted_rings, traversed_rings, selected);
+        return detail::overlay::add_rings<GeometryOutput>(selected, offsetted_rings, traversed_rings, out);
+    }
+
+#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
+
+    template <typename Mapper>
+    inline void map_turns(Mapper& mapper)
+    {
+        int index = 0;
+        for (typename boost::range_iterator<turn_vector_type>::type it =
+            boost::begin(turn_vector); it != boost::end(turn_vector); ++it)
+        {
+            std::string fill = "fill:rgb(0,255,0);";
+            switch(it->location)
+            {
+                case inside_buffer : fill = "fill:rgb(255,0,0);"; break;
+                case inside_original : fill = "fill:rgb(0,0,255);"; break;
+            }
+            mapper.map(it->point, fill, 6);
+            std::ostringstream out;
+            //out << it->operations[0].piece_index << "/" << it->operations[1].piece_index;
+            out << " " <<  all_pieces[it->operations[0].piece_index].seg_id.segment_index
+                 << "+" << all_pieces[it->operations[1].piece_index].seg_id.segment_index;
+            //out << " " <<  all_pieces[it->operations[0].piece_index].index_in_all_points
+            //     << "," << all_pieces[it->operations[1].piece_index].index_in_all_points;
+            //out << " " <<  it->operations[0].seg_id.segment_index
+            //     << "|" << it->operations[1].seg_id.segment_index;
+            out << ":" << operation_char(it->operations[0].operation);
+            mapper.text(it->point, out.str(), "fill:rgb(0,0,0);font-family='Arial';", 5, 5);
+        }
+    }
+
+    template <typename Tag, typename Mapper>
+    inline void map(Mapper& mapper)
+    {
+        for(typename piece_vector::const_iterator it = boost::begin(all_pieces);
+            it != boost::end(all_pieces);
+            ++it)
+        {
+            if (it->type == buffered_segment)
+            {
+                geometry::model::ring<Point> ring;
+                ring.push_back(it->p1);
+                ring.push_back(it->b1);
+                ring.push_back(it->b2);
+                ring.push_back(it->p2);
+                ring.push_back(it->p1);
+
+                if(boost::is_same<Tag, ring_tag>::value || boost::is_same<Tag, polygon_tag>::value)
+                {
+                    mapper.map(ring, "opacity:0.3;fill:rgb(255,128,0);stroke:rgb(0,0,0);stroke-width:1");
+                }
+                else if(boost::is_same<Tag, linestring_tag>::value)
+                {
+                    mapper.map(ring, "opacity:0.3;fill:rgb(0,255,0);stroke:rgb(0,0,0);stroke-width:1");
+                }
+            }
+            else
+            {
+                mapper.map(it->corner, "opacity:0.3;fill:rgb(255,0,0);stroke:rgb(0,0,0);stroke-width:1");
+            }
+
+
+            // Put starting segment_index in centroid
+            Point centroid;
+            geometry::centroid(it->corner, centroid);
+            std::ostringstream out;
+            out << it->seg_id.segment_index;
+            mapper.text(centroid, out.str(), "fill:rgb(255,0,0);font-family='Arial';", 5, 5);
+
+        }
+
+        int index = 0;
+        for (typename boost::range_iterator<std::vector<Point> >::type it =
+            boost::begin(offsetted_rings.front()); it != boost::end(offsetted_rings.front()); ++it)
+        {
+            mapper.map(*it, "fill:rgb(0,0,0);", 2);
+            std::ostringstream out;
+            out << index++;
+            mapper.text(*it, out.str(), "fill:rgb(0,0,255);font-family='Arial';", -5, -5);
+        }
+
+    }
+
+    template <typename Mapper>
+    inline void map_traverse(Mapper& mapper)
+    {
+        for(typename buffered_ring_collection<Ring>::const_iterator it = boost::begin(traversed_rings);
+            it != boost::end(traversed_rings);
+            ++it)
+        {
+            mapper.map(*it, "opacity:0.4;fill:none;stroke:rgb(0,255,0);stroke-width:8");
+        }
+    }
+
+    template <typename Mapper>
+    inline void map_offsetted(Mapper& mapper)
+    {
+        for(typename buffered_ring_collection<buffered_ring<Ring> >::const_iterator it = boost::begin(offsetted_rings);
+            it != boost::end(offsetted_rings);
+            ++it)
+        {
+            if (it->discarded())
+            {
+                mapper.map(*it, "opacity:0.4;fill:none;stroke:rgb(255,0,0);stroke-width:8");
+            }
+            else
+            {
+                mapper.map(*it, "opacity:0.4;fill:none;stroke:rgb(0,0,255);stroke-width:8");
+            }
+        }
+    }
+#endif
+};
+
+
+}} // namespace detail::buffer
+#endif // DOXYGEN_NO_DETAIL
+
+
+}} // namespace boost::geometry
+
+#endif // BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_BUFFERED_PIECE_COLLECTION_HPP
Added: trunk/boost/geometry/extensions/algorithms/buffer/buffered_ring.hpp
==============================================================================
--- (empty file)
+++ trunk/boost/geometry/extensions/algorithms/buffer/buffered_ring.hpp	2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
@@ -0,0 +1,260 @@
+// Boost.Geometry (aka GGL, Generic Geometry Library)
+
+// Copyright (c) 2012 Barend Gehrels, Amsterdam, the Netherlands.
+
+// 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)
+
+#ifndef BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_BUFFERED_RING
+#define BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_BUFFERED_RING
+
+#include <cstddef>
+
+#include <boost/range.hpp>
+
+#include <boost/geometry/core/coordinate_type.hpp>
+#include <boost/geometry/core/point_type.hpp>
+
+#include <boost/geometry/algorithms/equals.hpp>
+#include <boost/geometry/algorithms/covered_by.hpp>
+#include <boost/geometry/extensions/strategies/buffer_side.hpp>
+
+#include <boost/geometry/algorithms/detail/overlay/turn_info.hpp>
+#include <boost/geometry/algorithms/detail/overlay/enrichment_info.hpp>
+#include <boost/geometry/algorithms/detail/overlay/traversal_info.hpp>
+
+#include <boost/geometry/multi/algorithms/detail/overlay/copy_segments.hpp>
+#include <boost/geometry/multi/algorithms/detail/overlay/copy_segment_point.hpp>
+#include <boost/geometry/multi/algorithms/within.hpp>
+
+
+
+namespace boost { namespace geometry
+{
+
+#ifndef DOXYGEN_NO_DETAIL
+namespace detail { namespace buffer
+{
+
+struct buffered_ring_collection_tag : polygonal_tag, multi_tag
+{};
+    
+
+template <typename Ring>
+struct buffered_ring : public Ring
+{
+    bool has_discarded_intersections;
+    bool has_accepted_intersections;
+    inline buffered_ring()
+        : has_accepted_intersections(false)
+        , has_discarded_intersections(false)
+    {}
+
+    inline bool discarded() const
+    {
+        return has_discarded_intersections && ! has_accepted_intersections;
+    }
+    inline bool has_intersections() const
+    {
+        return has_discarded_intersections || has_accepted_intersections;
+    }
+};
+
+// This is a collection now special for overlay (needs vector of rings)
+template <typename Ring>
+struct buffered_ring_collection : public std::vector<Ring>
+{
+};
+
+}} // namespace detail::buffer
+#endif // DOXYGEN_NO_DETAIL
+
+
+
+// Register the types
+namespace traits
+{
+
+
+template <typename Ring>
+struct tag<detail::buffer::buffered_ring<Ring> >
+{
+    typedef ring_tag type;
+};
+
+
+template <typename Ring>
+struct point_order<detail::buffer::buffered_ring<Ring> >
+{
+    static const order_selector value = geometry::point_order<Ring>::value;
+};
+
+
+template <typename Ring>
+struct closure<detail::buffer::buffered_ring<Ring> >
+{
+    static const closure_selector value = geometry::closure<Ring>::value;
+};
+
+
+template <typename Ring>
+struct point_type<detail::buffer::buffered_ring_collection<Ring> >
+{
+    typedef typename geometry::point_type<Ring>::type type;
+};
+
+template <typename Ring>
+struct tag<detail::buffer::buffered_ring_collection<Ring> >
+{
+    typedef detail::buffer::buffered_ring_collection_tag type;
+};
+
+
+} // namespace traits
+
+namespace core_dispatch
+{
+
+template <typename Ring>
+struct ring_type
+<
+    detail::buffer::buffered_ring_collection_tag,
+    detail::buffer::buffered_ring_collection<Ring> 
+>
+{
+    typedef Ring type;
+};
+    
+}
+
+namespace dispatch
+{
+
+template
+<
+    typename MultiRing,
+    bool Reverse,
+    typename SegmentIdentifier,
+    typename PointOut
+>
+struct copy_segment_point
+    <
+        detail::buffer::buffered_ring_collection_tag,
+        MultiRing,
+        Reverse,
+        SegmentIdentifier,
+        PointOut
+    >
+    : detail::copy_segments::copy_segment_point_multi
+        <
+            MultiRing,
+            SegmentIdentifier,
+            PointOut,
+            detail::copy_segments::copy_segment_point_range
+                <
+                    typename boost::range_value<MultiRing>::type,
+                    Reverse,
+                    SegmentIdentifier,
+                    PointOut
+                >
+        >
+{};
+
+
+template
+<
+    typename MultiRing,
+    bool Reverse,
+    typename SegmentIdentifier,
+    typename RangeOut
+>
+struct copy_segments
+    <
+        detail::buffer::buffered_ring_collection_tag,
+        MultiRing,
+        Reverse,
+        SegmentIdentifier,
+        RangeOut
+    >
+    : detail::copy_segments::copy_segments_multi
+        <
+            MultiRing,
+            SegmentIdentifier,
+            RangeOut,
+            detail::copy_segments::copy_segments_ring
+                <
+                    typename boost::range_value<MultiRing>::type,
+                    Reverse,
+                    SegmentIdentifier,
+                    RangeOut
+                >
+        >
+{};
+
+
+
+template <typename Point, typename MultiGeometry>
+struct within
+<
+    Point, 
+    MultiGeometry, 
+    point_tag, 
+    detail::buffer::buffered_ring_collection_tag
+>
+{
+    template <typename Strategy>
+    static inline bool apply(Point const& point, 
+                MultiGeometry const& multi, Strategy const& strategy)
+    {
+        return detail::within::geometry_multi_within_code
+            <
+                Point,
+                MultiGeometry,
+                Strategy,
+                detail::within::point_in_ring
+                        <
+                            Point,
+                            typename boost::range_value<MultiGeometry>::type,
+                            //iterate_forward,
+                            //closed,
+                            order_as_direction
+                                <
+                                    geometry::point_order<MultiGeometry>::value
+                                >::value,
+                            geometry::closure<MultiGeometry>::value,
+                            Strategy
+                        >
+            >::apply(point, multi, strategy) == 1;
+    }
+};
+
+
+} // namespace dispatch
+
+namespace detail { namespace overlay
+{
+
+template<>
+struct get_ring<detail::buffer::buffered_ring_collection_tag>
+{
+    template<typename MultiGeometry>
+    static inline typename ring_type<MultiGeometry>::type const& apply(
+                ring_identifier const& id,
+                MultiGeometry const& multi_ring)
+    {
+        BOOST_ASSERT
+            (
+                id.multi_index >= 0
+                && id.multi_index < boost::size(multi_ring)
+            );
+        return get_ring<ring_tag>::apply(id, multi_ring[id.multi_index]);
+    }
+};
+
+}}
+
+
+}} // namespace boost::geometry
+
+#endif // BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_BUFFERED_RING
Deleted: trunk/boost/geometry/extensions/algorithms/buffer/linestring_buffer.hpp
==============================================================================
--- trunk/boost/geometry/extensions/algorithms/buffer/linestring_buffer.hpp	2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
+++ (empty file)
@@ -1,100 +0,0 @@
-// Boost.Geometry (aka GGL, Generic Geometry Library)
-
-// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
-
-// 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)
-
-#ifndef BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_LINESTRING_BUFFER_HPP
-#define BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_LINESTRING_BUFFER_HPP
-
-#include <cstddef>
-
-#include <boost/numeric/conversion/cast.hpp>
-
-#include <boost/range.hpp>
-
-#include <boost/geometry/extensions/strategies/buffer_side.hpp>
-
-#include <boost/geometry/extensions/algorithms/buffer/buffer_appender.hpp>
-#include <boost/geometry/extensions/algorithms/buffer/range_buffer.hpp>
-
-
-namespace boost { namespace geometry
-{
-
-
-#ifndef DOXYGEN_NO_DETAIL
-namespace detail { namespace buffer
-{
-
-template
-<
-    typename Linestring,
-    typename Polygon,
-    typename DistanceStrategy,
-    typename JoinStrategy
->
-struct linestring_buffer 
-    : public range_buffer
-        <
-            typename ring_type<Polygon>::type, 
-            DistanceStrategy, 
-            JoinStrategy,
-            linestring_tag
-        >
-{
-
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-    template<typename Mapper>
-#endif
-    static inline void apply(Linestring const& linestring, Polygon& buffered,
-            DistanceStrategy const& distance,
-            JoinStrategy const& join_strategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-            , Mapper& mapper
-#endif
-            )
-    {
-        buffer_appender
-            <
-                typename geometry::ring_type<Polygon>::type
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                , Mapper
-#endif
-            > appender
-            (
-                geometry::exterior_ring(buffered)
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                , mapper
-#endif
-            );
-
-        iterate(appender, boost::begin(linestring), boost::end(linestring),
-            buffer_side_left,
-            distance, join_strategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-            , mapper
-#endif
-            );
-
-        iterate(appender, boost::rbegin(linestring), boost::rend(linestring),
-            buffer_side_right,
-            distance, join_strategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-            , mapper
-#endif
-            );
-
-    }
-};
-
-
-}} // namespace detail::buffer
-#endif // DOXYGEN_NO_DETAIL
-
-
-}} // namespace boost::geometry
-
-#endif // BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_LINESTRING_BUFFER_HPP
Deleted: trunk/boost/geometry/extensions/algorithms/buffer/polygon_buffer.hpp
==============================================================================
--- trunk/boost/geometry/extensions/algorithms/buffer/polygon_buffer.hpp	2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
+++ (empty file)
@@ -1,159 +0,0 @@
-// Boost.Geometry (aka GGL, Generic Geometry Library)
-
-// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
-
-// 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)
-
-#ifndef BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_POLYGON_BUFFER_HPP
-#define BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_POLYGON_BUFFER_HPP
-
-#include <cstddef>
-
-#include <boost/numeric/conversion/cast.hpp>
-
-#include <boost/range.hpp>
-#include <boost/typeof/typeof.hpp>
-
-#include <boost/geometry/core/exterior_ring.hpp>
-#include <boost/geometry/core/interior_rings.hpp>
-
-#include <boost/geometry/extensions/strategies/buffer_side.hpp>
-#include <boost/geometry/extensions/algorithms/buffer/buffer_appender.hpp>
-#include <boost/geometry/extensions/algorithms/buffer/range_buffer.hpp>
-
-
-namespace boost { namespace geometry
-{
-
-
-#ifndef DOXYGEN_NO_DETAIL
-namespace detail { namespace buffer
-{
-
-
-template
-<
-    typename RingInput,
-    typename RingOutput,
-    typename DistanceStrategy,
-    typename JoinStrategy
->
-struct ring_buffer
-    : public range_buffer
-        <
-            RingOutput, 
-            DistanceStrategy, 
-            JoinStrategy,
-            ring_tag
-        >
-{
-
-    template
-    <
-        typename BufferAppender
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-        , typename Mapper
-#endif
-    >
-    static inline void apply(RingInput const& ring,
-            BufferAppender& appender,
-            DistanceStrategy const& distance,
-            JoinStrategy const& join_strategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-            , Mapper& mapper
-#endif
-            )
-    {
-        iterate(appender, boost::begin(ring), boost::end(ring),
-                buffer_side_left,
-                distance, join_strategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-            , mapper
-#endif
-            );
-    }
-};
-
-
-
-template
-<
-    typename PolygonInput,
-    typename PolygonOutput,
-    typename DistanceStrategy,
-    typename JoinStrategy
->
-struct polygon_buffer
-{
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-    template <typename Mapper>
-#endif
-    static inline void apply(PolygonInput const& polygon, PolygonOutput& buffered,
-            DistanceStrategy const& distance,
-            JoinStrategy const& join_strategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-            , Mapper& mapper
-#endif
-            )
-    {
-        geometry::clear(buffered);
-
-        typedef typename ring_type<PolygonInput>::type input_ring_type;
-        typedef typename ring_type<PolygonOutput>::type output_ring_type;
-
-        typedef buffer_appender
-            <
-                output_ring_type
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                , Mapper
-#endif
-            > appender_type;
-
-        typedef ring_buffer<input_ring_type, output_ring_type, DistanceStrategy, JoinStrategy> policy;
-
-        {
-            appender_type appender(geometry::exterior_ring(buffered)
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                    , mapper
-#endif
-                );
-            policy::apply(exterior_ring(polygon), appender,
-                    distance, join_strategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                    , mapper
-#endif
-                    );
-        }
-
-        typename interior_return_type<PolygonInput const>::type rings
-                    = interior_rings(polygon);
-        for (BOOST_AUTO_TPL(it, boost::begin(rings)); it != boost::end(rings); ++it)
-        {
-            output_ring_type ring;
-
-            appender_type appender(ring
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                , mapper
-#endif
-                );
-
-            policy::apply(*it, appender, distance, join_strategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                , mapper
-#endif
-                );
-            interior_rings(buffered).push_back(ring);
-        }
-    }
-};
-
-
-}} // namespace detail::buffer
-#endif // DOXYGEN_NO_DETAIL
-
-
-}} // namespace boost::geometry
-
-#endif // BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_POLYGON_BUFFER_HPP
Deleted: trunk/boost/geometry/extensions/algorithms/buffer/range_buffer.hpp
==============================================================================
--- trunk/boost/geometry/extensions/algorithms/buffer/range_buffer.hpp	2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
+++ (empty file)
@@ -1,199 +0,0 @@
-// Boost.Geometry (aka GGL, Generic Geometry Library)
-
-// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
-
-// 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)
-
-#ifndef BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_RANGE_BUFFER_HPP
-#define BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_RANGE_BUFFER_HPP
-
-#include <cstddef>
-
-#include <boost/range.hpp>
-
-#include <boost/geometry/core/coordinate_type.hpp>
-#include <boost/geometry/core/point_type.hpp>
-
-#include <boost/geometry/extensions/strategies/buffer_side.hpp>
-
-#include <boost/geometry/extensions/algorithms/buffer/line_line_intersection.hpp>
-
-#include <boost/geometry/geometries/segment.hpp>
-
-
-namespace boost { namespace geometry
-{
-
-
-#ifndef DOXYGEN_NO_DETAIL
-namespace detail { namespace buffer
-{
-
-template
-<
-    typename RingOutput,
-    typename DistanceStrategy,
-    typename JoinStrategy,
-    typename Tag
->
-struct range_buffer
-{
-    typedef typename point_type<RingOutput>::type output_point_type;
-    typedef typename coordinate_type<RingOutput>::type coordinate_type;
-    typedef model::referring_segment<output_point_type const> segment_type;
-
-    template
-    <
-        typename BufferAppender,
-        typename Iterator
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-        , typename Mapper
-#endif
-    >
-    static inline void iterate(BufferAppender& appender,
-                Iterator begin, Iterator end,
-                buffer_side_selector side,
-                DistanceStrategy const& distance,
-                JoinStrategy const& join_strategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                , Mapper& mapper
-#endif
-            )
-    {
-        output_point_type previous_p1, previous_p2;
-        output_point_type first_p1, first_p2;
-
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-        int index = 0;
-#endif
-
-        bool first = true;
-
-        Iterator it = begin;
-        for (Iterator prev = it++; it != end; ++it)
-        {
-            if (! detail::equals::equals_point_point(*prev, *it))
-            {
-                // Generate a block along (left or right of) the segment
-
-                // Simulate a vector d (dx,dy)
-                coordinate_type dx = get<0>(*it) - get<0>(*prev);
-                coordinate_type dy = get<1>(*it) - get<1>(*prev);
-
-                // For normalization [0,1] (=dot product d.d, sqrt)
-                coordinate_type length = sqrt(dx * dx + dy * dy);
-
-                // Because coordinates are not equal, length should not be zero
-                BOOST_ASSERT((! geometry::math::equals(length, 0)));
-
-                // Generate the normalized perpendicular p, to the left (ccw)
-                coordinate_type px = -dy / length;
-                coordinate_type py = dx / length;
-
-                output_point_type p1, p2;
-
-                coordinate_type d = distance.apply(*prev, *it, side);
-
-                set<0>(p2, get<0>(*it) + px * d);
-                set<1>(p2, get<1>(*it) + py * d);
-
-                set<0>(p1, get<0>(*prev) + px * d);
-                set<1>(p1, get<1>(*prev) + py * d);
-
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                {
-                    RingOutput block;
-                    block.push_back(*prev);
-                    block.push_back(*it);
-                    block.push_back(p2);
-                    block.push_back(p1);
-                    block.push_back(*prev);
-
-                    if(boost::is_same<Tag, ring_tag>::value)
-                    {
-                        mapper.map(block, "opacity:0.4;fill:rgb(255,128,0);stroke:rgb(0,0,0);stroke-width:1");
-                    }
-                    else if(boost::is_same<Tag, linestring_tag>::value)
-                    {
-                        mapper.map(block, "opacity:0.4;fill:rgb(0,255,0);stroke:rgb(0,0,0);stroke-width:1");
-                    }
-                }
-#endif
-
-                if (! first)
-                {
-                    output_point_type p;
-                    segment_type s1(p1, p2);
-                    segment_type s2(previous_p1, previous_p2);
-                    if (line_line_intersection<output_point_type, segment_type>::apply(s1, s2, p))
-                    {
-                        join_strategy.apply(p, *prev, previous_p2, p1,
-                                    distance.apply(*prev, *it, side),
-                                    appender);
-
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                        {
-                            //mapper.map(p, "fill:rgb(0,0,0);", 3);
-
-                            //std::ostringstream out;
-                            //out << index++;
-                            //mapper.text(p, out.str(), "fill:rgb(0,0,0);font-family='Arial';", 5, 5);
-                        }
-#endif
-                    }
-                }
-                else
-                {
-                    first = false;
-                    first_p1 = p1;
-                    first_p2 = p2;
-
-                    appender.append(p1);
-                }
-
-                previous_p1 = p1;
-                previous_p2 = p2;
-                prev = it;
-            }
-        }
-
-        // Might be replaced by specialization
-        if(boost::is_same<Tag, linestring_tag>::value)
-        {
-            appender.append(previous_p2);
-        }
-        else if(boost::is_same<Tag, ring_tag>::value)
-        {
-            // Generate closing corner
-            output_point_type p;
-            segment_type s1(previous_p1, previous_p2);
-            segment_type s2(first_p1, first_p2);
-            line_line_intersection<output_point_type, segment_type>::apply(s1, s2, p);
-
-            join_strategy.apply(p, *begin, previous_p2, first_p1,
-                distance.apply(*(end - 1), *begin, side),
-                appender);
-
-            // Buffer is closed automatically by last closing corner (NOT FOR OPEN POLYGONS - TODO)
-
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-            {
-                //mapper.map(p, "fill:rgb(0,0,0);", 3);
-                //std::ostringstream out;
-                //out << index++;
-                //mapper.text(p, out.str(), "fill:rgb(0,0,0);font-family='Arial';", 5, 5);
-            }
-#endif
-        }
-    }
-};
-
-}} // namespace detail::buffer
-#endif // DOXYGEN_NO_DETAIL
-
-
-}} // namespace boost::geometry
-
-#endif // BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_RANGE_BUFFER_HPP
Deleted: trunk/boost/geometry/extensions/algorithms/buffer/sectionalizing_buffer.hpp
==============================================================================
--- trunk/boost/geometry/extensions/algorithms/buffer/sectionalizing_buffer.hpp	2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
+++ (empty file)
@@ -1,167 +0,0 @@
-// Boost.Geometry (aka GGL, Generic Geometry Library)
-
-// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
-
-// 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)
-
-#ifndef BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_SECTIONALIZING_BUFFER_HPP
-#define BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_SECTIONALIZING_BUFFER_HPP
-
-#include <cstddef>
-
-#include <boost/foreach.hpp>
-#include <boost/numeric/conversion/cast.hpp>
-
-#include <boost/range/functions.hpp>
-#include <boost/range/metafunctions.hpp>
-
-#include <boost/geometry/core/point_type.hpp>
-
-#include <boost/geometry/extensions/strategies/buffer_side.hpp>
-#include <boost/geometry/extensions/algorithms/detail/buffer/intersecting_inserter.hpp>
-#include <boost/geometry/extensions/algorithms/detail/buffer/linestring_buffer.hpp>
-#include <boost/geometry/extensions/algorithms/detail/buffer/line_line_intersection.hpp>
-
-#include <boost/geometry/algorithms/detail/sections/range_by_section.hpp>
-#include <boost/geometry/algorithms/detail/sections/sectionalize.hpp>
-
-#include <boost/geometry/extensions/algorithms/dissolve.hpp>
-
-
-
-namespace boost { namespace geometry
-{
-
-
-#ifndef DOXYGEN_NO_DETAIL
-namespace detail { namespace buffer
-{
-
-
-
-template
-<
-    typename GeometryOut, typename Geometry,
-    typename DistanceStrategy,
-    typename JoinStrategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-    , typename Mapper
-#endif
->
-void sectionalizing_buffer(Geometry const& geometry,
-    std::vector<GeometryOut>& buffered,
-    DistanceStrategy const& distance_strategy,
-    JoinStrategy const& join_strategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-    , Mapper& mapper
-#endif
-    )
-{
-    typedef typename point_type<Geometry>::type point_type;
-    typedef geometry::box<point_type> box_type;
-    typedef geometry::sections<box_type, 2> sections_type;
-    typedef typename geometry::ring_type<GeometryOut>::type ring_type;
-
-    // TEMPORARY
-    typedef intersecting_inserter
-        <
-            std::vector<GeometryOut>
-        > inserter_type;
-
-
-    sections_type sections;
-    geometry::sectionalize(geometry, sections);
-
-
-
-    // Buffer all sections separately, and put them in a temporary vector
-    std::vector<GeometryOut> buffered_sections;
-    BOOST_FOREACH(typename sections_type::value_type const& section, sections)
-    {
-        if (! section.duplicate)
-        {
-            typedef typename boost::range_iterator
-                <
-                    typename geometry::detail::range_type<Geometry>::type const
-                >::type iterator_type;
-
-
-            inserter_type inserter(buffered_sections);
-
-            iterator_type begin, end;
-            typedef std::pair<iterator_type, iterator_type> section_range;
-
-TODO: UPDATE: get _ section IS OBSOLETE NOW AND DISCARDED.
-TAKE range_by_section AND ADD section.begin_index/section.end_index
-
-            geometry::get _ section(geometry, section, begin, end); // get_section is DISCARDED
-            geometry::detail::buffer::linestring_buffer
-                <
-                    section_range, ring_type, DistanceStrategy, JoinStrategy
-                >::apply(std::make_pair(begin, end), inserter,
-                            distance_strategy,
-                            join_strategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-                            , mapper
-#endif
-                            );
-        }
-    }
-
-    // IF there are bowl-like shapes, there can still be self-intersections
-    std::vector<GeometryOut> dissolved;
-    BOOST_FOREACH(GeometryOut const& p, buffered_sections)
-    {
-        geometry::dissolve(p, dissolved);
-    }
-
-    /*BOOST_FOREACH(GeometryOut const& p, buffered_sections)
-    {
-        if (geometry::intersects(p))
-        {
-            //std::cout << ".";
-        }
-    }*/
-
-    // TEMP
-    //buffered.swap(dissolved);
-    //return;
-    // END TEMP
-
-
-    BOOST_FOREACH(GeometryOut const& p, dissolved)
-    {
-        if (buffered.empty())
-        {
-            buffered.push_back(p);
-            //geometry::union_inserter<GeometryOut>(geometry, p, std::back_inserter(buffered));
-        }
-        else if (boost::size(buffered) == 1)
-        {
-            std::vector<GeometryOut> unioned;
-            geometry::union_inserter<GeometryOut>(buffered.front(), p, std::back_inserter(unioned));
-            buffered.swap(unioned);
-        }
-        else
-        {
-            std::cerr << " D " << buffered.size();
-            /*std::vector<GeometryOut> dissolved;
-            dissolved.push_back(p);
-            geometry::dissolver(buffered, dissolved);
-            dissolved.swap(buffered);*/
-        }
-    }
-
-    // Output
-}
-
-
-}} // namespace detail::buffer
-#endif // DOXYGEN_NO_DETAIL
-
-
-}} // namespace boost::geometry
-
-#endif // BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_SECTIONALIZING_BUFFER_HPP
Deleted: trunk/boost/geometry/extensions/algorithms/buffer/segmenting_buffer.hpp
==============================================================================
--- trunk/boost/geometry/extensions/algorithms/buffer/segmenting_buffer.hpp	2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
+++ (empty file)
@@ -1,350 +0,0 @@
-// Boost.Geometry (aka GGL, Generic Geometry Library)
-
-// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
-
-// 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)
-
-#ifndef BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_SEGMENTING_BUFFER_HPP
-#define BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_SEGMENTING_BUFFER_HPP
-
-
-#include <cstddef>
-#include <vector>
-
-#include <boost/foreach.hpp>
-#include <boost/numeric/conversion/cast.hpp>
-
-#include <boost/range.hpp>
-
-#include <boost/geometry/core/point_type.hpp>
-#include <boost/geometry/core/ring_type.hpp>
-
-#include <boost/geometry/extensions/strategies/buffer_side.hpp>
-#include <boost/geometry/extensions/strategies/buffer_join_round.hpp>
-#include <boost/geometry/util/math.hpp>
-
-#include <boost/geometry/algorithms/detail/disjoint.hpp>
-
-
-#include <boost/geometry/extensions/algorithms/dissolve.hpp>
-
-
-// TEMPORARY do not use yet.
-
-
-namespace boost { namespace geometry
-{
-
-
-#ifndef DOXYGEN_NO_DETAIL
-namespace detail { namespace buffer
-{
-
-
-template <typename Point, typename PointOut, typename DistanceType>
-inline bool calculate_parallels(Point const& point1, Point const& point2,
-            PointOut& p1, PointOut& p2, DistanceType const& distance)
-{
-    typedef typename coordinate_type<Point>::type coordinate_type;
-
-    // Simulate a vector d (dx,dy)
-    coordinate_type dx = get<0>(point2) - get<0>(point1);
-    coordinate_type dy = get<1>(point2) - get<1>(point1);
-
-    // For normalization [0,1] (=dot product d.d, sqrt)
-    // TODO: promote to non-integer
-    coordinate_type length = sqrt(dx * dx + dy * dy);
-
-    // Because coordinates are not equal, should been checked before, length should not be zero
-    if(geometry::math::equals(length, 0))
-    {
-        return false;
-    }
-
-    // Generate the normalized perpendicular p, to the left (ccw)
-    coordinate_type px = -dy / length;
-    coordinate_type py = dx / length;
-
-    set<0>(p1, get<0>(point1) + px * distance);
-    set<1>(p1, get<1>(point1) + py * distance);
-
-    set<0>(p2, get<0>(point2) + px * distance);
-    set<1>(p2, get<1>(point2) + py * distance);
-    return true;
-}
-
-
-
-template
-<
-    typename GeometryOut, typename Range,
-    typename DistanceStrategy,
-    typename JoinStrategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-    , typename Mapper
-#endif
->
-struct per_segment_buffer
-{
-    typedef typename point_type<Range>::type input_point_type;
-    typedef typename point_type<GeometryOut>::type point_type;
-    typedef typename coordinate_type<point_type>::type coordinate_type;
-    typedef coordinate_type distance_type; // TODO promote to FP
-    typedef model::segment<point_type const> segment_type;
-    typedef typename geometry::ring_type<GeometryOut>::type ring_type;
-    typedef typename strategy::side::services::default_strategy<typename cs_tag<point_type>::type>::type side;
-
-    typedef typename boost::range_iterator<Range const>::type iterator_type;
-
-
-    static inline void calculate_tail(input_point_type const& tail, input_point_type const& head,
-            point_type& tail_left, point_type& tail_right,
-            distance_type& distance_left,
-            distance_type& distance_right,
-            distance_type& buffered_length)
-    {
-        coordinate_type ext_x = get<0>(head) - get<0>(tail);
-        coordinate_type ext_y = get<1>(head) - get<1>(tail);
-        distance_type segment_length = sqrt(ext_x * ext_x + ext_y * ext_y);
-
-        if (buffered_length < geometry::math::abs(distance_left))
-        {
-            distance_left = buffered_length * distance_left < 0 ? -1.0 : 1.0;
-        }
-        if (buffered_length < geometry::math::abs(distance_right))
-        {
-            distance_right = buffered_length * distance_right < 0 ? -1.0 : 1.0;
-        }
-
-        distance_type prop_left = geometry::math::abs(distance_left) / segment_length;
-        distance_type prop_right = geometry::math::abs(distance_right) / segment_length;
-
-        set<0>(tail_left, get<0>(tail) - ext_x * prop_left);
-        set<1>(tail_left, get<1>(tail) - ext_y * prop_left);
-        set<0>(tail_right, get<0>(tail) - ext_x * prop_right);
-        set<1>(tail_right, get<1>(tail) - ext_y * prop_right);
-
-        buffered_length += segment_length;
-    }
-
-
-    static inline void calculate_head(input_point_type const& tail, input_point_type const& head,
-            point_type& head_left, point_type& head_right,
-            distance_type& distance_left,
-            distance_type& distance_right,
-            distance_type const& rest_length)
-    {
-        coordinate_type ext_x = get<0>(head) - get<0>(tail);
-        coordinate_type ext_y = get<1>(head) - get<1>(tail);
-        distance_type segment_length = sqrt(ext_x * ext_x + ext_y * ext_y);
-
-        if (rest_length < distance_left)
-        {
-            distance_left = rest_length;
-        }
-        if (rest_length < distance_right)
-        {
-            distance_right = rest_length;
-        }
-
-        distance_type prop_left = distance_left / segment_length;
-        distance_type prop_right = distance_right / segment_length;
-
-        set<0>(head_left, get<0>(head) + ext_x * prop_left);
-        set<1>(head_left, get<1>(head) + ext_y * prop_left);
-        set<0>(head_right, get<0>(head) + ext_x * prop_right);
-        set<1>(head_right, get<1>(head) + ext_y * prop_right);
-    }
-
-    static inline void apply(Range const& range,
-        std::vector<GeometryOut>& buffered,
-        DistanceStrategy const& distance_strategy,
-        JoinStrategy const& join_strategy
-    #ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-        , Mapper& mapper
-    #endif
-        )
-    {
-        // Buffer all segments separately, and put them in a temporary vector
-        std::vector<GeometryOut> buffered_pieces;
-
-        bool first = true;
-
-        strategy::buffer::join_round2<point_type> new_join;
-        //strategy::buffer::join_none<point_type> new_join;
-
-        distance_type range_length = geometry::length(range);
-        distance_type buffered_length = coordinate_type();
-
-        iterator_type it = boost::begin(range);
-        //iterator_type it_c = boost::end(range);
-        for (iterator_type previous = it++;
-            it != boost::end(range);
-            ++it)
-        {
-            bool const last = it + 1 == boost::end(range);
-
-            distance_type distance_left = distance_strategy.apply(
-                            *previous, *it, buffer_side_left);
-            distance_type distance_right = distance_strategy.apply(
-                            *previous, *it, buffer_side_right);
-
-            point_type left_ab_p1, left_ab_p2, right_ab_p1, right_ab_p2;
-
-            if (detail::disjoint::disjoint_point_point(*previous, *it)
-                && calculate_parallels(*previous, *it, left_ab_p1, left_ab_p2,
-                        distance_left)
-                && calculate_parallels(*previous, *it, right_ab_p1, right_ab_p2,
-                        -distance_right)
-                )
-            {
-                {
-                    point_type tail_left, tail_right, head_left, head_right;
-
-                    // For flat buffers, generate corners only if outside range of buffer_distance
-                    distance_type distance_tail_left = distance_left;
-                    distance_type distance_tail_right = distance_right;
-                    distance_type distance_head_left = distance_left;
-                    distance_type distance_head_right = distance_right;
-
-                    calculate_tail(*previous, *it,
-                            tail_left, tail_right,
-                            distance_tail_left, distance_tail_right,
-                            buffered_length);
-
-                    distance_type const rest_length = range_length - buffered_length;
-
-                    calculate_head(*previous, *it,
-                            head_left, head_right,
-                            distance_head_left, distance_head_right,
-                            rest_length);
-
-                    // Add non-axis aligned rectangle
-                    buffered_pieces.resize(buffered_pieces.size() + 1);
-                    ring_type& ring = exterior_ring(buffered_pieces.back());
-                    ring.push_back(left_ab_p1);
-                    ring.push_back(left_ab_p2);
-
-                    if (! last)
-                    {
-                        new_join.apply(*it, left_ab_p2, left_ab_p2, head_left,
-                                    distance_left, distance_head_left,
-                                    std::back_inserter(ring));
-
-                        ring.push_back(head_left);
-                        ring.push_back(head_right);
-
-                        new_join.apply(*it, right_ab_p2, head_right, right_ab_p2,
-                                    distance_right, distance_head_right,
-                                    std::back_inserter(ring));
-                    }
-
-                    ring.push_back(right_ab_p2);
-                    ring.push_back(right_ab_p1);
-
-                    if (! first)
-                    {
-                        new_join.apply(*previous, right_ab_p1, right_ab_p1, tail_right,
-                                    distance_right, distance_tail_right,
-                                    std::back_inserter(ring));
-
-                        ring.push_back(tail_right);
-                        ring.push_back(tail_left);
-
-                        new_join.apply(*previous, left_ab_p1, tail_left, left_ab_p1,
-                                    distance_left, distance_tail_left,
-                                    std::back_inserter(ring));
-                    }
-
-                    ring.push_back(left_ab_p1);
-                }
-
-                previous = it;
-
-                first = false;
-            }
-        }
-
-        // TEMP, uncomment to see what was actually generated
-        //buffered.swap(buffered_pieces);
-        //return;
-        // END TEMP
-
-
-
-        BOOST_FOREACH(GeometryOut const& p, buffered_pieces)
-        {
-            if (buffered.empty())
-            {
-                buffered.push_back(p);
-            }
-            else if (boost::size(buffered) == 1)
-            {
-                std::vector<GeometryOut> unioned;
-                geometry::union_inserter<GeometryOut>(buffered.front(), p, std::back_inserter(unioned));
-                buffered.swap(unioned);
-            }
-            else
-            {
-                std::cerr << " D " << buffered.size();
-                /*std::vector<GeometryOut> dissolved;
-                dissolved.push_back(p);
-                geometry::dissolver(buffered, dissolved);
-                dissolved.swap(buffered);*/
-            }
-        }
-
-        /***
-        std::vector<GeometryOut> dissolved;
-        BOOST_FOREACH(GeometryOut const& p, buffered)
-        {
-            geometry::dissolve(p, dissolved);
-        }
-        dissolved.swap(buffered);
-        ***/
-
-        // Output
-    }
-};
-
-
-
-template
-<
-    typename GeometryOut, typename Geometry,
-    typename DistanceStrategy,
-    typename JoinStrategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-    , typename Mapper
-#endif
->
-inline void segmenting_buffer(Geometry const& geometry,
-        std::vector<GeometryOut>& buffered,
-        DistanceStrategy const& distance_strategy,
-        JoinStrategy const& join_strategy
-    #ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-        , Mapper& mapper
-    #endif
-        )
-{
-    per_segment_buffer
-        <
-            GeometryOut, Geometry,
-            DistanceStrategy, JoinStrategy
-        >::apply(geometry, buffered, distance_strategy, join_strategy);
-}
-
-
-
-}} // namespace detail::buffer
-#endif // DOXYGEN_NO_DETAIL
-
-
-
-
-
-}} // namespace boost::geometry
-
-#endif // BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_SEGMENTING_BUFFER_HPP
Deleted: trunk/boost/geometry/extensions/algorithms/buffer/splitting_buffer.hpp
==============================================================================
--- trunk/boost/geometry/extensions/algorithms/buffer/splitting_buffer.hpp	2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
+++ (empty file)
@@ -1,116 +0,0 @@
-// Boost.Geometry (aka GGL, Generic Geometry Library)
-
-// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
-
-// 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)
-
-#ifndef BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_SPLITTING_BUFFER_HPP
-#define BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_SPLITTING_BUFFER_HPP
-
-#include <cstddef>
-
-#include <boost/foreach.hpp>
-#include <boost/numeric/conversion/cast.hpp>
-
-#include <boost/range/functions.hpp>
-#include <boost/range/metafunctions.hpp>
-
-#include <boost/geometry/core/point_type.hpp>
-
-#include <boost/geometry/extensions/strategies/buffer_side.hpp>
-#include <boost/geometry/extensions/algorithms/detail/buffer/intersecting_inserter.hpp>
-#include <boost/geometry/extensions/algorithms/detail/buffer/linestring_buffer.hpp>
-#include <boost/geometry/extensions/algorithms/detail/buffer/line_line_intersection.hpp>
-
-
-#include <boost/geometry/extensions/algorithms/detail/overlay/dissolver.hpp>
-#include <boost/geometry/extensions/algorithms/detail/overlay/split_rings.hpp>
-
-
-
-namespace boost { namespace geometry
-{
-
-
-#ifndef DOXYGEN_NO_DETAIL
-namespace detail { namespace buffer
-{
-
-
-template
-<
-    typename GeometryOut, typename Geometry,
-    typename DistanceStrategy,
-    typename JoinStrategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-    , typename Mapper
-#endif
->
-inline void splitting_buffer(Geometry const& geometry,
-    std::vector<GeometryOut>& buffered,
-    DistanceStrategy const& distance_strategy,
-    JoinStrategy const& join_strategy
-
-    , int option
-    )
-{
-    typedef typename ring_type<GeometryOut>::type ring_type;
-    typedef detail::buffer::intersecting_inserter
-        <
-            std::vector<GeometryOut>
-        > inserter_type;
-
-
-    inserter_type inserter(buffered);
-
-    detail::buffer::linestring_buffer
-        <
-            Geometry, GeometryOut, DistanceStrategy, JoinStrategy
-        >::apply(geometry, inserter, distance_strategy, join_strategy);
-
-    if (option == 0)
-    {
-        return;
-    }
-
-    std::vector<ring_type> rings;
-    BOOST_FOREACH(GeometryOut const& polygon, buffered)
-    {
-//std::cout << geometry::wkt(polygon) << " ; POLYGON" << std::endl;
-        geometry::split_rings(polygon, rings);
-    }
-
-    if (option == 1)
-    {
-        buffered.resize(rings.size());
-        int i = 0;
-        BOOST_FOREACH(ring_type const& ring, rings)
-        {
-            exterior_ring(buffered[i++]) = ring;
-        }
-        return;
-    }
-
-    std::vector<GeometryOut> buffered_and_unioned;
-    geometry::dissolver(rings, buffered_and_unioned);
-
-    std::vector<GeometryOut> buffered_and_assembled;
-    detail::overlay::assemble<GeometryOut>(buffered_and_unioned,
-            std::map<ring_identifier, int>(),
-            buffered_and_unioned[0], buffered_and_unioned[0], 1, true, true,
-            std::back_inserter(buffered_and_assembled));
-
-    buffered = buffered_and_assembled;
-}
-
-
-
-}} // namespace detail::buffer
-#endif // DOXYGEN_NO_DETAIL
-
-
-}} // namespace boost::geometry
-
-#endif // BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_SPLITTING_BUFFER_HPP
Deleted: trunk/boost/geometry/extensions/algorithms/buffer/traversing_buffer.hpp
==============================================================================
--- trunk/boost/geometry/extensions/algorithms/buffer/traversing_buffer.hpp	2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
+++ (empty file)
@@ -1,89 +0,0 @@
-// Boost.Geometry (aka GGL, Generic Geometry Library)
-
-// Copyright (c) 2007-2012 Barend Gehrels, Amsterdam, the Netherlands.
-
-// 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)
-
-#ifndef BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_TRAVERSING_BUFFER_HPP
-#define BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_TRAVERSING_BUFFER_HPP
-
-#include <cstddef>
-
-#include <boost/foreach.hpp>
-#include <boost/numeric/conversion/cast.hpp>
-
-#include <boost/range/functions.hpp>
-#include <boost/range/metafunctions.hpp>
-
-#include <boost/geometry/core/point_type.hpp>
-
-#include <boost/geometry/extensions/strategies/buffer_side.hpp>
-#include <boost/geometry/extensions/algorithms/buffer/intersecting_inserter.hpp>
-#include <boost/geometry/extensions/algorithms/buffer/linestring_buffer.hpp>
-#include <boost/geometry/extensions/algorithms/buffer/line_line_intersection.hpp>
-
-
-#include <boost/geometry/extensions/algorithms/dissolve.hpp>
-
-
-
-namespace boost { namespace geometry
-{
-
-
-#ifndef DOXYGEN_NO_DETAIL
-namespace detail { namespace buffer
-{
-
-
-template
-<
-    typename GeometryOut, typename Geometry,
-    typename DistanceStrategy,
-    typename JoinStrategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-    , typename Mapper
-#endif
->
-inline void traversing_buffer(Geometry const& geometry,
-    std::vector<GeometryOut>& buffered,
-    DistanceStrategy const& distance_strategy,
-    JoinStrategy const& join_strategy
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-    , Mapper& mapper
-#endif
-    )
-{
-    typedef typename ring_type<GeometryOut>::type ring_type;
-    typedef detail::buffer::intersecting_inserter
-        <
-            std::vector<GeometryOut>
-        > inserter_type;
-
-
-    inserter_type inserter(buffered);
-
-    detail::buffer::linestring_buffer
-        <
-            Geometry, GeometryOut, DistanceStrategy, JoinStrategy
-        >::apply(geometry, inserter, distance_strategy, join_strategy);
-
-    std::vector<GeometryOut> buffered_and_assembled;
-    detail::overlay::assemble<GeometryOut>(buffered,
-            std::map<ring_identifier, int>(),
-            buffered[0], buffered[0], 1, true, true,
-            std::back_inserter(buffered_and_assembled));
-
-    buffered = buffered_and_assembled;
-}
-
-
-}} // namespace detail::buffer
-#endif // DOXYGEN_NO_DETAIL
-
-
-}} // namespace boost::geometry
-
-#endif // BOOST_GEOMETRY_ALGORITHMS_DETAIL_BUFFER_TRAVERSING_BUFFER_HPP
Modified: trunk/boost/geometry/extensions/strategies/buffer.hpp
==============================================================================
--- trunk/boost/geometry/extensions/strategies/buffer.hpp	(original)
+++ trunk/boost/geometry/extensions/strategies/buffer.hpp	2012-02-18 05:07:18 EST (Sat, 18 Feb 2012)
@@ -59,65 +59,25 @@
 */
 
 
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-template
-<
-    typename PointIn, typename Mapper
->
-struct join_mapper
-{
-    Mapper const& m_mapper;
-    join_mapper(Mapper const& mapper)
-        : m_mapper(mapper)
-    {}
-
-    template <typename BufferAppender>
-    inline void map(PointIn const& ip, PointIn const& vertex,
-                PointIn const& perp1, PointIn const& perp2) const
-    {
-        typename BufferAppender::range_type corner;
-        corner.push_back(vertex);
-        corner.push_back(perp1);
-        corner.push_back(ip);
-        corner.push_back(perp2);
-        corner.push_back(vertex);
-
-        const_cast<Mapper&>(m_mapper).map(corner,
-            "opacity:0.4;fill:rgb(255,0,0);stroke:rgb(0,0,0);stroke-width:1");
-    }
-};
-#endif
 
 // TODO: merge join_miter with join_round, lot of duplicate code
 
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-// Forget this, it will go
-template<typename PointIn, typename PointOut, bool AddHooklets, typename Mapper>
-struct join_miter : public join_mapper<PointIn, Mapper>
-{
-    join_miter(Mapper const& mapper) : join_mapper(mapper) {}
-#else
-
-
 template
 <
     typename PointIn,
-    typename PointOut,
-    bool AddHooklets = true
+    typename PointOut
 >
 struct join_miter
 {
-
-#endif
     typedef typename strategy::side::services::default_strategy<typename cs_tag<PointIn>::type>::type side;
     typedef typename coordinate_type<PointIn>::type coordinate_type;
 
 
-    template <typename BufferAppender>
+    template <typename RangeOut>
     inline void apply(PointIn const& ip, PointIn const& vertex,
                 PointIn const& perp1, PointIn const& perp2,
                 coordinate_type const& buffer_distance,
-                BufferAppender& appender) const
+                RangeOut& range_out) const
     {
         coordinate_type zero = 0;
         int signum = buffer_distance > zero ? 1
@@ -126,15 +86,6 @@
 
         if (side::apply(perp1, ip, perp2) == signum)
         {
-            if (AddHooklets)
-            {
-                appender.append_begin_hooklet(perp1);
-                appender.append_end_hooklet(perp2);
-            }
-            else
-            {
-                appender.append(ip);
-            }
         }
         else
         {
@@ -165,26 +116,15 @@
 #endif
             }
 
-            appender.append_begin_join(p);
-
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-            map<BufferAppender>(ip, vertex, perp1, perp2);
-#endif
+            range_out.push_back(perp1);
+            range_out.push_back(p);
+            range_out.push_back(perp2);
         }
 
     }
 };
 
 
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-// Forget this, it will go
-template<typename PointIn, typename PointOut, typename Mapper>
-struct join_bevel : public join_mapper<PointIn, Mapper>
-{
-    join_bevel(Mapper const& mapper) : join_mapper(mapper) {}
-#else
-
-
 template
 <
     typename PointIn,
@@ -192,62 +132,39 @@
 >
 struct join_bevel
 {
-#endif
-
-
     typedef typename coordinate_type<PointIn>::type coordinate_type;
 
-    template <typename BufferAppender>
+    template <typename RangeOut>
     inline void apply(PointIn const& ip, PointIn const& vertex,
                 PointIn const& perp1, PointIn const& perp2,
                 coordinate_type const& buffer_distance,
-                BufferAppender& appender) const
+                RangeOut& range_out) const
     {
-        appender.append(perp1);
-        appender.append(perp2);
-
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-            map<BufferAppender>(ip, vertex, perp1, perp2);
-#endif
     }
 };
 
 
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-// Forget this, it will go
-template<typename PointIn, typename PointOut, bool AddHooklets, typename Mapper>
-struct join_round : public join_mapper<PointIn, Mapper>
-{
-    join_round(Mapper const& mapper, int max_level = 4)
-        : join_mapper(mapper)
-        , m_max_level(max_level)
-    {}
-#else
-
-
 template
 <
     typename PointIn,
-    typename PointOut,
-    bool AddHooklets = true
+    typename PointOut
 >
 struct join_round
 {
-    inline join_round(int max_level = 4)
+    inline join_round(int max_level = 6)
         : m_max_level(max_level)
     {}
-#endif
 
     typedef typename strategy::side::services::default_strategy<typename cs_tag<PointIn>::type>::type side;
     typedef typename coordinate_type<PointOut>::type coordinate_type;
     int m_max_level;
 
 
-    template <typename BufferAppender>
+    template <typename RangeOut>
     inline void mid_points(PointIn const& vertex,
                 PointIn const& p1, PointIn const& p2,
                 coordinate_type const& buffer_distance,
-                BufferAppender& appender,
+                RangeOut& range_out,
                 int level = 1) const
     {
         // Generate 'vectors'
@@ -272,22 +189,22 @@
 
         if (level < m_max_level)
         {
-            mid_points(vertex, p1, mid_point, buffer_distance, appender, level + 1);
+            mid_points(vertex, p1, mid_point, buffer_distance, range_out, level + 1);
         }
-        appender.append(mid_point);
+        range_out.push_back(mid_point);
         if (level < m_max_level)
         {
-            mid_points(vertex, mid_point, p2, buffer_distance, appender, level + 1);
+            mid_points(vertex, mid_point, p2, buffer_distance, range_out, level + 1);
         }
 
     }
 
 
-    template <typename BufferAppender>
+    template <typename RangeOut>
     inline void apply(PointIn const& ip, PointIn const& vertex,
                 PointIn const& perp1, PointIn const& perp2,
                 coordinate_type const& buffer_distance,
-                BufferAppender& appender) const
+                RangeOut& range_out) const
     {
         coordinate_type zero = 0;
         int signum = buffer_distance > zero ? 1
@@ -296,16 +213,6 @@
 
         if (side::apply(perp1, ip, perp2) == signum)
         {
-            // If it is concave (corner to left), add helperline
-            if (AddHooklets)
-            {
-                appender.append_begin_hooklet(perp1);
-                appender.append_end_hooklet(perp2);
-            }
-            else
-            {
-                appender.append(ip);
-            }
         }
         else
         {
@@ -323,25 +230,21 @@
             set<0>(bp, get<0>(vertex) + vix * prop);
             set<1>(bp, get<1>(vertex) + viy * prop);
 
-            appender.append_begin_join(perp1);
+            range_out.push_back(perp1);
             if (m_max_level <= 1)
             {
                 if (m_max_level == 1)
                 {
-                    appender.append(bp);
+                    range_out.push_back(bp);
                 }
             }
             else
             {
-                mid_points(vertex, perp1, bp, bd, appender);
-                appender.append(bp);
-                mid_points(vertex, bp, perp2, bd, appender);
+                mid_points(vertex, perp1, bp, bd, range_out);
+                range_out.push_back(bp);
+                mid_points(vertex, bp, perp2, bd, range_out);
             }
-            appender.append_end_join(perp2);
-
-#ifdef BOOST_GEOMETRY_DEBUG_WITH_MAPPER
-            map<BufferAppender>(bp, vertex, perp1, perp2);
-#endif
+            range_out.push_back(perp2);
         }
     }
 };