00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #include "Teddy/Models/Cone.h"
00026 #include "Teddy/Models/QuadStrip.h"
00027 #include "Teddy/Models/TriangleFan.h"
00028 #include "Teddy/Models/Vertex.h"
00029 #include "Teddy/Models/Model.h"
00030 #include "Teddy/Models/Face.h"
00031 #include "Teddy/SysSupport/StdMaths.h"
00032
00033
00034 namespace Teddy {
00035 namespace Models {
00036
00037
00047 Cone::Cone(
00048 const std::string &name,
00049 const double base_radius,
00050 const double top_radius,
00051 const double height,
00052 int slices,
00053 int stacks,
00054 bool use_bottom,
00055 bool use_top
00056 )
00057 :Model( name )
00058 {
00059 if( slices < 3 ) slices = 4;
00060 if( stacks < 1 ) stacks = 1;
00061 if( base_radius == 0 ) use_bottom = false;
00062 if( top_radius == 0 ) use_top = false;
00063
00064 double da = M_2_PI / slices;
00065 double dr = (top_radius - base_radius) / stacks;
00066 double dz = height / stacks;
00067 double nz = (base_radius - top_radius) / height;
00068 double ds = 1 / slices;
00069 double dt = 1 / stacks;
00070 double t = 0;
00071 double z = 0;
00072 double r = base_radius;
00073 Face *top = NULL;
00074 Face *bottom = NULL;
00075 Vertex *v1;
00076 Vertex *v2;
00077 Vector n1;
00078 Vector n2;
00079 int i;
00080 int j;
00081
00082 if( use_bottom ) bottom = new Face();
00083 if( use_top ) top = new Face();
00084
00085 for( j=0; j<=stacks-1; j++ ){
00086 double s = 0;
00087 QuadStrip *qs = new QuadStrip();
00088
00089 for( i=slices; i>=0; i-- ){
00090 double x;
00091 double y;
00092
00093 if( i==slices ){
00094 x = ::sin( 0 );
00095 y = ::cos( 0 );
00096 }else{
00097 x = ::sin( i * da );
00098 y = ::cos( i * da );
00099 }
00100
00101 v1 = new Vertex( r*x, r*y, z );
00102 n1 = Vector( x, y, nz );
00103 n1. normalize();
00104 v1 ->setNormal( n1 );
00105 qs->add( v1 );
00106
00107 v2 = new Vertex( (r+dr)*x, (r+dr)*y, dz+z );
00108 n2 = Vector( x, y, nz );
00109 n2. normalize();
00110 v2 ->setNormal( n2 );
00111 qs->add( v2 );
00112
00113 if( i!=slices ){
00114
00115 if( use_bottom ){
00116 if( (j==0) && (r!=0) ){
00117 Vertex *v_bot = new Vertex( v1 );
00118 v_bot->disable( Element::VX_USE_PARENT_NORMAL|Element::VX_USE_THIS_VERTEX );
00119 bottom->add( v_bot );
00120 }
00121 }
00122
00123
00124 if( use_top ){
00125 if( (j==stacks-1) && ((r+dr)!=0) ){
00126 Vertex *v_top = new Vertex( v2 );
00127 v_top->disable( Element::VX_USE_PARENT_NORMAL|Element::VX_USE_THIS_VERTEX );
00128 top->add( v_top );
00129 }
00130 }
00131 }
00132
00133 s += ds;
00134 }
00135 add( qs );
00136 r += dr;
00137 t += dt;
00138 z += dz;
00139 }
00140 if( use_bottom ){
00141 bottom->reverse();
00142 bottom->makeNormal();
00143 add( bottom );
00144 }
00145 if( use_top ){
00146 top ->makeNormal();
00147 add( top );
00148 }
00149
00150 setupClipRadius();
00151 }
00152
00153
00154 };
00155 };
00156