diff --git a/.gitattributes b/.gitattributes index 10faaf263c3..97c2f5a89bf 100644 --- a/.gitattributes +++ b/.gitattributes @@ -3126,6 +3126,11 @@ Straight_skeleton_2/doc_tex/Straight_skeleton_2/validly_touching.eps -text svneo Straight_skeleton_2/doc_tex/Straight_skeleton_2/validly_touching.pdf -text svneol=unset#application/pdf Straight_skeleton_2/doc_tex/Straight_skeleton_2/validly_touching.png -text svneol=unset#image/png Straight_skeleton_2/examples/Straight_skeleton_2/Straight_skeleton_2.kdevelop.pcs -text +Straight_skeleton_2/include/CGAL/IO/Dxf_stream.h -text +Straight_skeleton_2/include/CGAL/IO/Dxf_writer.h -text +Straight_skeleton_2/include/CGAL/Straight_skeleton_2/assertions.h -text +Straight_skeleton_2/include/CGAL/Straight_skeleton_2/debug.h -text +Straight_skeleton_2/include/CGAL/Straight_skeleton_2/test.h -text Straight_skeleton_2/test/Straight_skeleton_2/data/1_Example.poly -text Straight_skeleton_2/test/Straight_skeleton_2/data/1_Example_Working.poly -text Straight_skeleton_2/test/Straight_skeleton_2/data/2_Example.poly -text diff --git a/Straight_skeleton_2/include/CGAL/IO/Dxf_stream.h b/Straight_skeleton_2/include/CGAL/IO/Dxf_stream.h new file mode 100644 index 00000000000..209094fcf49 --- /dev/null +++ b/Straight_skeleton_2/include/CGAL/IO/Dxf_stream.h @@ -0,0 +1,322 @@ +// Copyright (c) 2007 GeometryFactory (France). All rights reserved. +// +// This file is part of CGAL (www.cgal.org); you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public License as +// published by the Free Software Foundation; version 2.1 of the License. +// See the file LICENSE.LGPL distributed with CGAL. +// +// Licensees holding a valid commercial license may use this file in +// accordance with the commercial license agreement provided with the software. +// +// This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE +// WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. +// +// $URL: $ +// $Id: $ +// +// +// Author(s) : Fernando Cacciola +// +// Descriptions of the file format can be found at +// http://www.autodesk.com/techpubs/autocad/acad2000/dxf/ + +#ifndef CGAL_DXF_STREAM_H +#define CGAL_DXF_STREAM_H + +#include +#include + +#include + +#include +#include +#include + +CGAL_BEGIN_NAMESPACE + +class Dxf_layer +{ +public: + + Dxf_layer( string aStr ) : mStr(aStr) {} + + std::string str() const { return mStr ; } + +private: + + std::string mStr ; +} ; + +template +class Dxf_stream +{ +public: + + typedef Kernel_ Kernel; + + // Define the kernel objects. + typedef typename Kernel::FT NT; + typedef typename Kernel::Point_2 Point_2; + typedef typename Kernel::Segment_2 Segment_2; + typedef typename Kernel::Ray_2 Ray_2; + typedef typename Kernel::Line_2 Line_2; + typedef typename Kernel::Triangle_2 Triangle_2; + typedef typename Kernel::Iso_rectangle_2 Iso_rectangle_2; + typedef Polygon_2 Polygon_2; + typedef typename Kernel::Circle_2 Circle_2; + +protected: + + // Data members: + Dxf_writer mWriter ; + int mDefaultDxfColor; + int mDxfColor; + Color mCgalColor ; + std::string mLayer ; + + struct Color_less + { + bool operator() ( Color const& a, Color const& b ) const + { + return Color_value(a) < Color_value(b); + } + + static int Color_value ( Color const& c ) + { + return ( int(c.r()) << 16 ) + ( int(c.g()) << 8 ) + ( int(c.b()) ) ; + } + } ; + + typedef std::map Color_table ; + typedef typename Color_table::const_iterator Color_table_iterator ; + Color_table mColorTable ; + +private: + + // Copy constructor and assignment operator - not supported. + Dxf_stream (const Dxf_stream& ); + const Dxf_stream& operator= (const Dxf_stream& ); + +public: + + /// \name Constructors and destructor. + //@{ + + /*! + * Constructor. + * \param filename The name of the output FIG file. + */ + Dxf_stream ( ostream& out ) + : + mWriter (out) + ,mDefaultDxfColor (255) + ,mDxfColor (255) + ,mCgalColor (WHITE) + ,mLayer ("0") + { + setup_initial_color_table(); + } + + /*! + * Destructor. + */ + virtual ~Dxf_stream () {} + //@} + + /// \name Accessing drawing properties. + //@{ + + /*! + * Get the current layer. + */ + std::string layer() const { return mLayer ; } + + /*! + * Get the current CGAL color. + */ + Color color () const { return mCgalColor ; } + + /*! + * Get the current DXF color. + */ + int dxf_color () const { return mDxfColor ; } + + /*! + * Get the current DXF color. + */ + int default_dxf_color () const { return mDefaultDxfColor ; } + + /// \name Set the drawing properties. + //@{ + + /*! + * Set the current layer. + */ + void set_layer ( string aLayer ) { mLayer = aLayer ; } + + /*! + * Set the current color. + * \pre The color must be defined. + */ + void set_color ( Color aColor ) + { + mCgalColor = aColor ; + + Color_table_iterator f = mColorTable.find(aColor); + if ( f != mColorTable.end() ) + mDxfColor = f->second ; + else mDxfColor = mDefaultDxfColor ; + } + + + /*! + * Sets the default DXF color in case a CGAL color is unmapped. + * \param aDxfColor The default DXF color. + */ + void define_default_dxf_color ( int aDxfColor ) + { + mDefaultDxfColor = aDxfColor ; + } + + /*! + * Adds a mapping between a CGAL Color and a DXF color. + * \param aCgalColor The CGAL color. + * \param aDxfColor The DXF color. + */ + void define_color ( Color const& aCgalColor, int aDxfColor ) + { + mColorTable.insert( std::make_pair(aCgalColor,aDxfColor) ) ; + } + + //@} + + /// \name Writing objects. + //@{ + + /*! + * Write a 2D segment. + */ + void write_segment_2 (const Segment_2& seg) + { + mWriter.add_segment_2( seg.source(), seg.target(), mLayer, mDxfColor ) ; + } + + + /*! + * Write a 2D polyline. + * \param begin An iterator of the control points (of type Point_2). + * \param end A past-the-end iterator for the control points. + */ + template + void write_polyline_2 (const Input_iterator& begin, const Input_iterator& end) + { + mWriter.add_polyline_2( begin, end, false, mLayer, mDxfColor ) ; + } + + /*! + * Write a 2D polygon (there is an added segment between the last vertex and the first) + * \param begin An iterator of the control points (of type Point_2). + * \param end A past-the-end iterator for the control points. + */ + template + void write_polygon_2 (const Input_iterator& begin, const Input_iterator& end) + { + mWriter.add_polyline_2( begin, end, true, mLayer, mDxfColor ) ; + } + + /*! + * Write a 2D polyline but as a sequence of line segments + * \param begin An iterator of the control points (of type Point_2). + * \param end A past-the-end iterator for the control points. + */ + template + void write_open_segment_chain_2 (const Input_iterator& begin, const Input_iterator& end) + { + mWriter.add_segments_2( begin, end, false, mLayer, mDxfColor ) ; + } + + /*! + * Write a 2D closed polyline but as a sequence of line segments + * \param begin An iterator of the control points (of type Point_2). + * \param end A past-the-end iterator for the control points. + */ + template + void write_closed_segment_chain_2 (const Input_iterator& begin, const Input_iterator& end) + { + mWriter.add_segments_2( begin, end, true, mLayer, mDxfColor ) ; + } + + /*! + * Write a 2D (closed) polygon. + */ + void write_polygon (const Polygon_2& pgn) + { + mWriter.add_polyline_2( pgn.begin(), pgn.end(), true, mLayer, mDxfColor ) ; + } + + + /// \name Setting the draw properties via the << operator. + //@{ + + /*! + * Set the current layer. + */ + Dxf_stream& operator<< ( Dxf_layer const& aLayer ) + { + set_layer ( aLayer.str() ); + return (*this); + } + + /*! + * Set the current color. + */ + Dxf_stream& operator<< ( Color const& aColor ) + { + set_color (aColor); + return (*this); + } + + + /// \name Drawing objects via the << operator. + //@{ + + /*! + * Write a line segment. + */ + Dxf_stream& operator<< (const Segment_2& seg) + { + write_segment_2 (seg); + return (*this); + } + + /*! + * Write a polygon. + */ + Dxf_stream& operator<< (const Polygon_2& pgn) + { + write_polygon_2 (pgn); + return (*this); + } + + //@} + +protected: + + void setup_initial_color_table() + { + define_color(BLACK,0); + define_color(RED,1); + define_color(YELLOW,2); + define_color(GREEN,3); + define_color(PURPLE,4); + define_color(BLUE,5); + define_color(VIOLET,6); + define_color(WHITE,7); + define_color(GRAY,8); + } + +}; + +CGAL_END_NAMESPACE + +#endif diff --git a/Straight_skeleton_2/include/CGAL/IO/Dxf_writer.h b/Straight_skeleton_2/include/CGAL/IO/Dxf_writer.h new file mode 100644 index 00000000000..d48d0ed4578 --- /dev/null +++ b/Straight_skeleton_2/include/CGAL/IO/Dxf_writer.h @@ -0,0 +1,282 @@ +// Copyright (c) 2007 GeometryFactory (France). All rights reserved. +// +// This file is part of CGAL (www.cgal.org); you can redistribute it and/or +// modify it under the terms of the GNU Lesser General Public License as +// published by the Free Software Foundation; version 2.1 of the License. +// See the file LICENSE.LGPL distributed with CGAL. +// +// Licensees holding a valid commercial license may use this file in +// accordance with the commercial license agreement provided with the software. +// +// This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE +// WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. +// +// $URL: $ +// $Id: $ +// +// +// Author(s) : Fernando Cacciola +// +// Descriptions of the file format can be found at +// http://www.autodesk.com/techpubs/autocad/acad2000/dxf/ + + +#ifndef CGAL_IO_DXF_WRITER_H +#define CGAL_IO_DXF_WRITER_H + +#include +#include +#include +#include + +CGAL_BEGIN_NAMESPACE + +class Dxf_writer +{ + typedef std::list Lines ; + typedef Lines::iterator Line_iterator ; + + typedef std::set Layers ; + typedef Layers::iterator Layer_iterator ; + +public: + + Dxf_writer ( std::ostream& out ) : mOut(out), mHandle(32) + { + mPos = mLines.end(); + add_header(); + } + + ~Dxf_writer() + { + add_footer(); + dump(); + } + + template + void add_segment_2 ( XY const& aSrc + , XY const& aTgt + , std::string aLayer = "" + , int aColor = 255 + ) + { + add_entity ( "LINE" , aLayer ) ; + add_code ( 62 , to_str ( aColor ) ) ; + add_code ( 10 , to_str ( to_double(aSrc.x()) ) ) ; + add_code ( 20 , to_str ( to_double(aSrc.y()) ) ) ; + add_code ( 30 , to_str ( to_double(0.0 ) ) ) ; + add_code ( 11 , to_str ( to_double(aTgt.x()) ) ) ; + add_code ( 21 , to_str ( to_double(aTgt.y()) ) ) ; + add_code ( 31 , to_str ( to_double(0.0 ) ) ) ; + } + + + template + void add_polyline_2 ( XY_Iterator aVerticesBegin + , XY_Iterator aVerticesEnd + , bool aIsClosed + , std::string aLayer = "" + , int aColor = 255 + ) + { + if ( aVerticesBegin < aVerticesEnd ) + { + add_entity ( "POLYLINE" , aLayer) ; + add_code ( 62 , to_str ( aColor ) ) ; + add_code ( 66 , to_str ( 1 ) ) ; + add_code ( 10 , to_str ( 0.0 ) ) ; + add_code ( 20 , to_str ( 0.0 ) ) ; + add_code ( 30 , to_str ( 0.0 ) ) ; + add_code ( 70 , to_str ( aIsClosed ? 1 : 0 ) ) ; + + while ( aVerticesBegin != aVerticesEnd ) + { + add_entity ( "VERTEX" , aLayer) ; + add_code ( 10 , to_str ( to_double( aVerticesBegin->x() ) ) ) ; + add_code ( 20 , to_str ( to_double( aVerticesBegin->y() ) ) ) ; + add_code ( 30 , to_str ( to_double( 0.0 ) ) ) ; + ++ aVerticesBegin ; + } + + add_entity ( "SEQEND" , aLayer) ; + } + } + + template + void add_segments_2 ( XY_Iterator aVerticesBegin + , XY_Iterator aVerticesEnd + , bool aIsClosed + , std::string aLayer = "" + , int aColor = 255 + ) + { + if ( aVerticesBegin < aVerticesEnd ) + { + XY_Iterator lFirstVertex = aVerticesBegin ; + XY_Iterator lLastVertex = aVerticesEnd ; -- lLastVertex ; + + if ( lFirstVertex != lLastVertex ) + { + XY_Iterator lCurrVertex = aVerticesBegin ; + + while ( lCurrVertex != aVerticesEnd ) + { + XY_Iterator lNextVertex = ( lCurrVertex == lLastVertex ? lFirstVertex : successor(lCurrVertex) ) ; + + add_segment_2 ( *lCurrVertex, *lNextVertex, aLayer, aColor ) ; + + ++ lCurrVertex ; + } + + if ( aIsClosed ) + add_segment_2 ( *lLastVertex, *lFirstVertex, aLayer, aColor ) ; + } + } + + } + +private: + + std::string get_entity_handle() + { + char lBuff[64]; + sprintf(lBuff,"%5x",mHandle++); + return std::string(lBuff); + } + + std::string to_str ( int aN ) + { + char lBuff[64]; + sprintf(lBuff,"%6d",aN); + return std::string(lBuff); + } + + + std::string to_str ( double aN ) + { + char lBuff[64]; + sprintf(lBuff,"%6.6f",aN); + return std::string(lBuff); + } + + void insert_line ( Line_iterator aPos, std::string aLine ) + { + mLines.insert(aPos,aLine); + } + + void add_line ( std::string aLine ) + { + insert_line(mPos,aLine); + } + + void add_code ( int aCode, std::string aValue ) + { + add_line( to_str(aCode) ) ; + add_line( aValue ) ; + } + + void add_group_begin ( std::string aGroup, std::string aName ) + { + add_code ( 0 , aGroup ) ; + add_code ( 2 , aName ) ; + } + + void add_group_end ( std::string aGroup ) + { + add_code ( 0 , aGroup ) ; + } + + void add_entity ( std::string aName, std::string aLayer ) + { + add_code ( 0 , aName ) ; + add_code ( 5 , get_entity_handle() ) ; + + if ( !aLayer.empty() && aLayer != "0" ) + { + mLayers.insert(aLayer); + add_code ( 8 , aLayer ) ; + } + } + + void add_header() + { + add_group_begin ( "SECTION" , "HEADER" ) ; + add_group_end ( "ENDSEC" ) ; + + add_group_begin ( "SECTION" , "TABLES" ) ; + add_group_begin ( "TABLE" , "LTYPE" ) ; + add_code ( 70 , to_str ( 1 ) ) ; + add_code ( 0 , "LTYPE" ) ; + add_code ( 2 , "CONTINUOUS" ) ; + add_code ( 70 , to_str ( 0 ) ) ; + add_code ( 3 , "Solid line" ) ; + add_code ( 72 , to_str ( 65 ) ) ; + add_code ( 73 , to_str ( 0 ) ) ; + add_code ( 40 , to_str ( 0.0 ) ) ; + add_group_end ( "ENDTAB" ) ; + add_group_begin ( "TABLE" , "APPID" ) ; + add_code ( 70 , to_str ( 1 ) ) ; + add_code ( 0 , "APPID" ) ; + add_code ( 2 , "ACAD" ) ; + add_code ( 70 , to_str ( 0 ) ) ; + add_group_end ( "ENDTAB" ) ; + + mLayersTablePos = mPos ; -- mLayersTablePos ; + + add_group_end ( "ENDSEC" ) ; + + add_group_begin ( "SECTION" , "ENTITIES" ) ; + } + + void add_footer() + { + add_group_end( "ENDSEC" ) ; + add_group_end( "EOF" ) ; + + insert_layers(); + } + + void insert_layers() + { + if ( mLayers.size() > 0 ) + { + mPos = mLayersTablePos ; ++ mPos ; + + add_group_begin ( "TABLE" , "LAYER" ) ; + add_code ( 70 , to_str ( int(mLayers.size() + 1) ) ) ; + add_code ( 0 , "LAYER" ) ; + add_code ( 2 , "0" ) ; + add_code ( 70 , to_str ( 0 ) ) ; + add_code ( 62 , to_str ( 7 ) ) ; + add_code ( 6 , "CONTINUOUS" ) ; + + for ( Layer_iterator lit = mLayers.begin() ; lit != mLayers.end() ; ++ lit ) + { + add_code ( 0 , "LAYER" ) ; + add_code ( 2 , *lit ) ; + add_code ( 70 , to_str ( 0 ) ) ; + add_code ( 62 , to_str ( 0 ) ) ; + add_code ( 6 , "CONTINUOUS" ) ; + } + add_group_end ( "ENDTAB" ) ; + } + } + + void dump() + { + std::copy(mLines.begin(),mLines.end(), std::ostream_iterator(mOut,"\n")); + } + + + std::ostream& mOut ; + Lines mLines ; + Line_iterator mPos ; + Line_iterator mLayersTablePos ; + Layers mLayers ; + int mHandle ; + +} ; + +CGAL_END_NAMESPACE + +#endif // CGAL_IO_DXF_WRITER_H diff --git a/Straight_skeleton_2/include/CGAL/Straight_skeleton_2/assertions.h b/Straight_skeleton_2/include/CGAL/Straight_skeleton_2/assertions.h new file mode 100644 index 00000000000..d47ec2a0333 --- /dev/null +++ b/Straight_skeleton_2/include/CGAL/Straight_skeleton_2/assertions.h @@ -0,0 +1,51 @@ +// Copyright (c) 2007 Fernando Luis Cacciola Carballal. All rights reserved. +// +// This file is part of CGAL (www.cgal.org); you may redistribute it under +// the terms of the Q Public License version 1.0. +// See the file LICENSE.QPL distributed with CGAL. +// +// Licensees holding a valid commercial license may use this file in +// accordance with the commercial license agreement provided with the software. +// +// This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE +// WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. +// +// $URL: svn+ssh://fcacciola@scm.gforge.inria.fr/svn/cgal/trunk/Straight_skeleton_2/include/CGAL/Straight_skeleton_2.h $ +// $Id: Straight_skeleton_2.h 32540 2006-07-14 14:13:45Z fcacciola $ +// +// Author(s) : Fernando Cacciola + +#ifndef CGAL_STRAIGHT_SKELETON_ASSERTIONS_H +#define CGAL_STRAIGHT_SKELETON_ASSERTIONS_H + +#if defined(CGAL_STRAIGHT_SKELETON_NO_POSTCONDITIONS) \ + || defined(CGAL_NO_POSTCONDITIONS) \ + || (!defined(CGAL_STRAIGHT_SKELETON_CHECK_EXPENSIVE) && !defined(CGAL_CHECK_EXPENSIVE)) \ + || defined(NDEBUG) +# define CGAL_stskel_expensive_postcondition(EX) (static_cast(0)) +# define CGAL_stskel_expensive_postcondition_msg(EX,MSG) (static_cast(0)) +# define CGAL_stskel_expensive_postcondition_code(CODE) +#else +# define CGAL_stskel_expensive_postcondition(EX) ((EX)?(static_cast(0)): ::CGAL::postcondition_fail( # EX , __FILE__, __LINE__, 0)) +# define CGAL_stskel_expensive_postcondition_msg(EX,MSG) ((EX)?(static_cast(0)): ::CGAL::postcondition_fail( # EX , __FILE__, __LINE__, MSG)) +# define CGAL_stskel_expensive_postcondition_code(CODE) CODE +#endif + + +CGAL_BEGIN_NAMESPACE + +namespace { + +template inline bool handle_assigned ( Handle const& aH ) +{ + Handle null ; + return aH != null ; +} + +} + +CGAL_END_NAMESPACE + +#endif // CGAL_STRAIGHT_SKELETON_ASSERTIONS_H // +// EOF // + diff --git a/Straight_skeleton_2/include/CGAL/Straight_skeleton_2/debug.h b/Straight_skeleton_2/include/CGAL/Straight_skeleton_2/debug.h new file mode 100644 index 00000000000..48cd3b35ba6 --- /dev/null +++ b/Straight_skeleton_2/include/CGAL/Straight_skeleton_2/debug.h @@ -0,0 +1,311 @@ +// Copyright (c) 2007 Fernando Luis Cacciola Carballal. All rights reserved. +// +// This file is part of CGAL (www.cgal.org); you may redistribute it under +// the terms of the Q Public License version 1.0. +// See the file LICENSE.QPL distributed with CGAL. +// +// Licensees holding a valid commercial license may use this file in +// accordance with the commercial license agreement provided with the software. +// +// This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE +// WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. +// +// $URL: svn+ssh://fcacciola@scm.gforge.inria.fr/svn/cgal/trunk/Straight_skeleton_2/include/CGAL/Straight_skeleton_2.h $ +// $Id: Straight_skeleton_2.h 32540 2006-07-14 14:13:45Z fcacciola $ +// +// Author(s) : Fernando Cacciola + +#ifndef CGAL_STRAIGHT_SKELETON_DEBUG_H +#define CGAL_STRAIGHT_SKELETON_DEBUG_H 1 + +#ifdef CGAL_USE_CORE +# include +#endif + +#if defined(CGAL_STRAIGHT_SKELETON_ENABLE_TRACE) \ + || defined(CGAL_POLYGON_OFFSET_ENABLE_TRACE) \ + || defined(CGAL_STRAIGHT_SKELETON_TRAITS_ENABLE_TRACE) \ + || defined(CGAL_STRAIGHT_SKELETON_ENABLE_VALIDITY_TRACE) \ + || defined(CGAL_STRAIGHT_SKELETON_ENABLE_INTRINSIC_TESTING) +# +# define CGAL_STSKEL_TRACE_ON +# +# include +# include +# include +# include +# define CGAL_STSKEL_TRACE(m) \ + { \ + std::ostringstream ss ; \ + ss << m ; \ + std::string s = ss.str(); \ + Straight_skeleton_external_trace(s); \ + } + +template +inline std::string o2str( boost::optional const& o ) +{ + std::ostringstream ss ; + if ( o ) + ss << *o ; + else ss << "·NONE·" ; + return ss.str(); +} + +template +inline std::string ptr2str( boost::intrusive_ptr const& ptr ) +{ + std::ostringstream ss ; + if ( ptr ) + ss << *ptr ; + else ss << "·NULL·" ; + return ss.str(); +} + +template +inline std::string n2str( N const& n ) +{ + std::ostringstream ss ; + + ss << CGAL_NTS to_double(n) ; + + return ss.str(); +} + + +#if 0 //CGAL_USE_CORE + +inline CORE::BigFloat to_big_float( CGAL::MP_Float const& n ) +{ + return n.to_rational() ; +} + +inline CORE::BigFloat to_big_float( CGAL::Quotient const& q ) +{ + CORE::BigFloat n = to_big_float(q.numerator ()) ; + CORE::BigFloat d = to_big_float(q.denominator()) ; + if ( !d.isZeroIn()) + return n / d ; + else return CORE::BigFloat(std::numeric_limits::infinity()); +} + +template +inline CORE::BigFloat to_big_float( NT const& n ) +{ + return CORE::BigFloat( CGAL_NTS to_double(n) ) ; +} + + +inline std::string n2str( CGAL::MP_Float const& n ) +{ + std::ostringstream ss ; + ss << to_big_float(n) ; + return ss.str(); +} + +inline std::string n2str( CGAL::Quotient< CGAL::MP_Float > const& n ) +{ + std::ostringstream ss ; + ss << to_big_float(n) ; + return ss.str(); +} +#else +inline std::string n2str( CGAL::MP_Float const& n ) +{ + std::ostringstream ss ; + ss << CGAL_NTS to_double(n) ; + return ss.str(); +} + +inline std::string n2str( CGAL::Quotient< CGAL::MP_Float > const& n ) +{ + std::ostringstream ss ; + ss << CGAL_NTS to_double(n) ; + return ss.str(); +} +#endif + +template +inline std::string xy2str( XY const& xy ) +{ + std::ostringstream ss ; + ss << "(" << n2str(xy.x()) << "," << n2str(xy.y()) << ")" ; + return ss.str(); +} +template +inline std::string dir2str( D const& d ) +{ + std::ostringstream ss ; + ss << "(" << n2str(d.dx()) << "," << n2str(d.dy()) << ")" ; + return ss.str(); +} +template +inline std::string p2str( P const& p ) +{ + std::ostringstream ss ; + ss << "(" << n2str(p.x()) << "," << n2str(p.y()) << ")" ; + return ss.str(); +} +template +inline std::string op2str( OP const& op ) +{ + return op ? p2str(*op) : std::string("·NONE·"); +} +template +inline std::string v2str( V const& v ) +{ + std::ostringstream ss ; + ss << "V" << v.id() << " " << p2str(v.point()) << " [" << v.time() << "]" ; + return ss.str(); +} +template +inline std::string vh2str( VH const& vh ) +{ + VH null ; + return vh != null ? v2str(*vh) : "NULL_VERTEX_HANDLE" ; +} + +template +inline std::string s2str( P const& s, P const& t ) +{ + std::ostringstream ss ; + ss << "{" << p2str(s) << "-" << p2str(t) << "}" ; + return ss.str(); +} +template +inline std::string s2str( S const& seg ) { return s2str(seg.source(),seg.target()); } + +template +inline std::string e2str( E const& e ) +{ + std::ostringstream ss ; + if ( e.is_bisector() ) + { + ss << "B" << e.id() + << "[E" << e.defining_contour_edge()->id() + << ",E" << e.opposite()->defining_contour_edge()->id() << "]" + << " (/" << ( e.slope() == CGAL::ZERO ? "·" : ( e.slope() == CGAL::NEGATIVE ? "-" : "+" ) ) + << " " << e.opposite()->vertex()->time() << "->" << e.vertex()->time() << ")" ; + } + else + { + ss << "E" << e.id() ; + } + ss << " " << s2str(e.opposite()->vertex()->point(),e.vertex()->point()) ; + return ss.str(); +} +template +inline std::string eh2str( EH const& eh ) +{ + EH null ; + return eh != null ? e2str(*eh) : "NULL_HALFEDGE_HANDLE" ; +} +#endif + +#ifdef CGAL_STRAIGHT_SKELETON_ENABLE_TRACE +# define CGAL_STSKEL_DEBUG_CODE(code) code +# define CGAL_STSKEL_BUILDER_TRACE(l,m) if ( l <= CGAL_STRAIGHT_SKELETON_ENABLE_TRACE ) CGAL_STSKEL_TRACE(m) +# define CGAL_STSKEL_BUILDER_TRACE_IF(c,l,m) if ( (c) && l <= CGAL_STRAIGHT_SKELETON_ENABLE_TRACE ) CGAL_STSKEL_TRACE(m) +#else +# define CGAL_STSKEL_DEBUG_CODE(code) +# define CGAL_STSKEL_BUILDER_TRACE(l,m) +# define CGAL_STSKEL_BUILDER_TRACE_IF(c,l,m) +#endif + +#ifdef CGAL_POLYGON_OFFSET_ENABLE_TRACE +# define CGAL_POLYOFFSET_DEBUG_CODE(code) code +# define CGAL_POLYOFFSET_TRACE(l,m) if ( l <= CGAL_POLYGON_OFFSET_ENABLE_TRACE ) CGAL_STSKEL_TRACE(m) +#else +# define CGAL_POLYOFFSET_DEBUG_CODE(code) +# define CGAL_POLYOFFSET_TRACE(l,m) +#endif + +#ifdef CGAL_STRAIGHT_SKELETON_TRAITS_ENABLE_TRACE +bool sEnableTraitsTrace = false ; +# define CGAL_STSKEL_TRAITS_ENABLE_TRACE sEnableTraitsTrace = true ; +# define CGAL_STSKEL_TRAITS_ENABLE_TRACE_IF(cond) if ((cond)) sEnableTraitsTrace = true ; +# define CGAL_STSKEL_TRAITS_DISABLE_TRACE sEnableTraitsTrace = false; +# define CGAL_STSKEL_TRAITS_TRACE(m) \ + if ( sEnableTraitsTrace ) \ + { \ + std::ostringstream ss ; \ + ss << m ; \ + std::string s = ss.str(); \ + Straight_skeleton_traits_external_trace(s); \ + } +#else +# define CGAL_STSKEL_TRAITS_ENABLE_TRACE +# define CGAL_STSKEL_TRAITS_ENABLE_TRACE_IF(cond) +# define CGAL_STSKEL_TRAITS_DISABLE_TRACE +# define CGAL_STSKEL_TRAITS_TRACE(m) +#endif + + +#ifdef CGAL_STRAIGHT_SKELETON_ENABLE_VALIDITY_TRACE +# define CGAL_STSKEL_VALIDITY_TRACE(m) CGAL_STSKEL_TRACE(m) +# define CGAL_STSKEL_VALIDITY_TRACE_IF(cond,m) if ( cond ) CGAL_STSKEL_VALIDITY_TRACE(m) +#else +# define CGAL_STSKEL_VALIDITY_TRACE(m) +# define CGAL_STSKEL_VALIDITY_TRACE_IF(cond,m) +#endif + + +#ifdef CGAL_STRAIGHT_SKELETON_PROFILING_ENABLED // Reserved use. DO NOT define this macro switch +# include +# include +# include + +CGAL_BEGIN_NAMESPACE + +namespace CGAL_STRAIGHT_SKELETON_i_profiling +{ + +template char const* kernel_type() { return typeid(NT).name() ; } + +template<> char const* kernel_type () { return "double" ; } +template<> char const* kernel_type() { return "Interval" ; } +template<> char const* kernel_type< Quotient >() { return "MP_Float" ; } +template<> char const* kernel_type () { return "Expr" ; } + +} // CGAL_STRAIGHT_SKELETON_i_profiling + +CGAL_END_NAMESPACE + +#define CGAL_STSKEL_ASSERT_PREDICATE_RESULT(expr,K,pred,error) \ + { \ + std::ostringstream predss ; \ + predss << CGAL_STRAIGHT_SKELETON_i_profiling::kernel_type< typename K::FT >() << " . " << pred ; \ + std::string preds = predss.str(); \ + if ( is_indeterminate((expr)) ) \ + { \ + std::ostringstream errss ; errss << error ; std::string errs = errss.str(); \ + register_predicate_failure(preds,errs); \ + } \ + else register_predicate_success(preds); \ + } + +#define CGAL_STSKEL_ASSERT_CONSTRUCTION_RESULT(expr,K,cons,error) \ + { \ + std::ostringstream consss ; \ + consss << CGAL_STRAIGHT_SKELETON_i_profiling::kernel_type< typename K::FT >() << " . " << cons ; \ + std::string conss = consss.str(); \ + if ( !(expr) ) \ + { \ + std::ostringstream errss ; errss << error ; std::string errs = errss.str(); \ + register_construction_failure(conss,errs); \ + } \ + else register_construction_success(conss); \ + } +#else + +#define CGAL_STSKEL_ASSERT_PREDICATE_RESULT(expr,K,pred,error) +#define CGAL_STSKEL_ASSERT_CONSTRUCTION_RESULT(expr,K,cons,error) + +#endif + +#undef CGAL_STSKEL_ENABLE_TRACE + +#endif // CGAL_STRAIGHT_SKELETON_DEBUG_H // +// EOF // + + diff --git a/Straight_skeleton_2/include/CGAL/Straight_skeleton_2/test.h b/Straight_skeleton_2/include/CGAL/Straight_skeleton_2/test.h new file mode 100644 index 00000000000..8fb6842ce36 --- /dev/null +++ b/Straight_skeleton_2/include/CGAL/Straight_skeleton_2/test.h @@ -0,0 +1,177 @@ +// Copyright (c) 2007 Fernando Luis Cacciola Carballal. All rights reserved. +// +// This file is part of CGAL (www.cgal.org); you may redistribute it under +// the terms of the Q Public License version 1.0. +// See the file LICENSE.QPL distributed with CGAL. +// +// Licensees holding a valid commercial license may use this file in +// accordance with the commercial license agreement provided with the software. +// +// This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE +// WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. +// +// $URL: svn+ssh://fcacciola@scm.gforge.inria.fr/svn/cgal/trunk/Straight_skeleton_2/include/CGAL/Straight_skeleton_2.h $ +// $Id: Straight_skeleton_2.h 32540 2006-07-14 14:13:45Z fcacciola $ +// +// Author(s) : Fernando Cacciola + +#ifndef CGAL_STRAIGHT_SKELETON_TEST_H +#define CGAL_STRAIGHT_SKELETON_TEST_H 1 + +// +// INTRINSIC UNIT TESTING macros. +// +// These are OFF by default and should only be turn on by the testsuite. +// + +// +// These are assertions that may not be true unless certain external conditions are met, such as the kernel +// beigng exact or the input being specifically designed to be non-degenerate, avoid significant round-off, etc. +// +#ifdef CGAL_STRAIGHT_SKELETON_ENABLE_INTRINSIC_TESTING +# define CGAL_stskel_intrinsic_test_assertion(EX) ((EX)?(static_cast(0)): ::CGAL::assertion_fail( # EX , __FILE__, __LINE__, 0)) +# define CGAL_stskel_intrinsic_test_assertion_msg(EX,MSG) ((EX)?(static_cast(0)): ::CGAL::assertion_fail( # EX , __FILE__, __LINE__, MSG)) +# define CGAL_stskel_intrinsic_test_assertion_code(CODE) CODE +# define CGAL_stskel_intrinsic_test_trace(m) std::cerr << m << std::endl +# define CGAL_stskel_intrinsic_test_trace_if(EX,m) if ( (EX) ) { std::cerr << m << std::endl ; } +#else +# define CGAL_stskel_intrinsic_test_assertion(EX) (static_cast(0)) +# define CGAL_stskel_intrinsic_test_assertion_msg(EX,MSG) (static_cast(0)) +# define CGAL_stskel_intrinsic_test_assertion_code(CODE) +# define CGAL_stskel_intrinsic_test_trace(m) +# define CGAL_stskel_intrinsic_test_trace_if(EX,m) +#endif + +#ifdef CGAL_STRAIGHT_SKELETON_ENABLE_INTRINSIC_TESTING + +CGAL_BEGIN_NAMESPACE + +namespace CGAL_SS_i { + +// +// The following tests are used by the testsuite only. +// +// Their purpose is to detect clearly wrong results without resorting to exact constructions. +// +// These are negative tests only. For instance, they don't test whether a number is zero (since it can be +// near zero but not exactly due to roundoff); rather, they test whether a number is clearly not zero, +// which is a test that can be done robustelly if a pesimistic upper bound on the error is know. +// +// The test are overloaded on number types so if exact constructions are used, the tests are exact. + +inline bool is_possibly_inexact_distance_clearly_not_zero ( double n, double eps ) +{ + return std::abs( CGAL_NTS to_double(n) ) > eps ; +} + +#ifdef CGAL_CORE_EXPR_H +inline bool is_possibly_inexact_distance_clearly_not_zero ( CORE::Expr const& n ) +{ + return ! CGAL_NTS is_zero(n); +} +#endif + +#ifdef CGAL_LEDA_REAL_H +inline bool is_possibly_inexact_distance_clearly_not_zero ( leda_real const& n ) +{ + return ! CGAL_NTS is_zero(n); +} +#endif + +#ifdef CGAL_GMPQ_H +inline bool is_possibly_inexact_distance_clearly_not_zero ( Gmpq const& n ) +{ + return is_possibly_inexact_distance_clearly_not_zero( to_double(n), 1e-8 ) ; +} +#endif + +#ifdef CGAL_MP_FLOAT_H +inline bool is_possibly_inexact_distance_clearly_not_zero ( MP_Float const& n ) +{ + return is_possibly_inexact_distance_clearly_not_zero( to_double(n), 1e-8 ) ; +} + +inline bool is_possibly_inexact_distance_clearly_not_zero ( Quotient const& n ) +{ + return is_possibly_inexact_distance_clearly_not_zero( to_double(n), 1e-8 ) ; +} +#endif + +#if defined(CGAL_LAZY_EXACT_NT_H) +template +inline bool is_possibly_inexact_distance_clearly_not_zero ( Lazy_exact_nt const& n ) +{ + return is_possibly_inexact_distance_clearly_not_zero( to_double(n), 1e-8 ) ; +} +#endif + + +inline bool is_possibly_inexact_distance_clearly_not_zero ( double n ) +{ + return std::abs( CGAL_NTS to_double(n) ) > 1e-5 ; +} + +inline bool is_possibly_inexact_distance_clearly_not_zero ( Interval_nt_advanced const& n ) +{ + return is_possibly_inexact_distance_clearly_not_zero(to_double(n)); +} + + + + + +template +inline bool is_possibly_inexact_distance_clearly_not_equal_to( NT const& n, NT const& m ) +{ + return is_possibly_inexact_distance_clearly_not_zero(n-m); +} + +template +inline bool is_possibly_inexact_time_clearly_not_zero( NT const& n ) +{ + return is_possibly_inexact_distance_clearly_not_zero(n); +} + +template +inline bool is_possibly_inexact_time_clearly_not_equal_to( NT const& n, NT const& m ) +{ + return is_possibly_inexact_distance_clearly_not_zero(n-m); +} + +template +inline bool is_time_clearly_not_within_possibly_inexact_bisector_time_interval( FT const& aT , Bisector const& aBisector ) +{ + FT lSrcT = aBisector->opposite()->vertex()->time() ; + FT lTgtT = aBisector->vertex()->time() ; + FT lLoT = std::min(lSrcT,lTgtT); + FT lHiT = std::max(lSrcT,lTgtT); + + return ( aT < lLoT || aT > lHiT ) + && is_possibly_inexact_time_clearly_not_equal_to(aT,lLoT) + && is_possibly_inexact_time_clearly_not_equal_to(aT,lHiT) ; +} + +template +inline bool is_time_clearly_within_possibly_inexact_bisector_time_interval( FT const& aT , Bisector const& aBisector ) +{ + FT lSrcT = aBisector->opposite()->vertex()->time() ; + FT lTgtT = aBisector->vertex()->time() ; + FT lLoT = std::min(lSrcT,lTgtT); + FT lHiT = std::max(lSrcT,lTgtT); + + return ( lLoT < aT && aT < lHiT ) + && is_possibly_inexact_time_clearly_not_equal_to(aT,lLoT) + && is_possibly_inexact_time_clearly_not_equal_to(aT,lHiT) ; +} + + +} // namespace CGAL_SS_i + +CGAL_END_NAMESPACE + +#endif + +#endif // CGAL_STRAIGHT_SKELETON_TEST_H // +// EOF // + +