00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #pragma once
00024
00025 #include "cinder/Vector.h"
00026 #include "cinder/Rect.h"
00027 #include "cinder/Path2d.h"
00028
00029 #include <vector>
00030
00031 namespace cinder {
00032
00033 class Shape2d {
00034 public:
00035 void moveTo( const Vec2f &p );
00036 void moveTo( float x, float y ) { moveTo( Vec2f( x, y ) ); }
00037 void lineTo( const Vec2f &p );
00038 void lineTo( float x, float y ) { lineTo( Vec2f( x, y ) ); }
00039 void quadTo( const Vec2f &p1, const Vec2f &p2 );
00040 void quadTo( float x1, float y1, float x2, float y2 ) { quadTo( Vec2f( x1, y1 ), Vec2f( x2, y2 ) ); }
00041 void curveTo( const Vec2f &p1, const Vec2f &p2, const Vec2f &p3 );
00042 void curveTo( float x1, float y1, float x2, float y2, float x3, float y3 ) { curveTo( Vec2f( x1, y1 ), Vec2f( x2, y2 ), Vec2f( x3, y3 ) ); }
00043 void close();
00044
00045 bool empty() const { return mContours.empty(); }
00046 void clear() { mContours.clear(); }
00047 size_t getNumContours() const { return mContours.size(); }
00048
00049 const Path2d& getContour( size_t i ) const { return mContours[i]; }
00050 Path2d& getContour( size_t i ) { return mContours[i]; }
00051
00052 const Vec2f& getCurrentPoint() const { return mContours.back().getCurrentPoint(); }
00053
00054 void removeContour( size_t i ) { mContours.erase( mContours.begin() + i ); }
00055
00057 Rectf calcBoundingBox() const;
00058
00060
00064 template<typename IT>
00065 void iterate( IT &it )
00066 {
00067 bool stop = false;
00068 for( std::vector<Path2d>::const_iterator contourIt = mContours.begin(); contourIt != mContours.end(); ++contourIt ) {
00069 size_t pt = 0;
00070 for( std::vector<Path2d::SegmentType>::const_iterator segIt = contourIt->mSegments.begin(); segIt != contourIt->mSegments.end(); ++segIt ) {
00071 if( ! it( *segIt, &contourIt->mPoints[pt], ( pt > 0 ) ? &contourIt->mPoints[pt-1] : 0 ) ) {
00072 stop = true;
00073 break;
00074 }
00075 pt += Path2d::sSegmentTypePointCounts[*segIt];
00076 }
00077 if( stop ) break;
00078 else if( contourIt->isClosed() ) {
00079 if( ! it( Path2d::CLOSE, contourIt->empty() ? NULL : &contourIt->mPoints[0], ( pt > 0 ) ? &contourIt->mPoints[pt-1] : 0 ) )
00080 break;
00081 }
00082 }
00083 }
00084
00085 private:
00086 std::vector<Path2d> mContours;
00087 };
00088
00089 }