Branch data Line data Source code
1 : : //-------------------------------------------------------------------------
2 : : // Filename : CylinderEvaluator.cpp
3 : : //
4 : : // Purpose :
5 : : //
6 : : // Special Notes :
7 : : //
8 : : // Creator : Matt Staten
9 : : //
10 : : // Creation Date : 09/15/04
11 : : //
12 : : // Owner : Matt Staten
13 : : //-------------------------------------------------------------------------
14 : :
15 : : #include "CylinderEvaluator.hpp"
16 : : #include "CubitMessage.hpp"
17 : : #include "CubitBox.hpp"
18 : : #include "CubitVector.hpp"
19 : :
20 : : // ********** END CUBIT INCLUDES **********
21 : :
22 : : // ********** BEGIN STATIC DECLARATIONS **********
23 : : // ********** END STATIC DECLARATIONS **********
24 : :
25 : : // ********** BEGIN PUBLIC FUNCTIONS **********
26 : :
27 : : //-------------------------------------------------------------------------
28 : : // Purpose : Construct a CylinderEvaluator object given a structure
29 : : // containing the radius, center, etc. for the desired
30 : : // Cylinder.
31 : : //
32 : : // Special Notes :
33 : : //
34 : : //-------------------------------------------------------------------------
35 : 0 : CylinderEvaluator::CylinderEvaluator( const CylinderEvaluatorData *data )
36 : : {
37 : 0 : mEvalData = *data;
38 : :
39 [ # # ]: 0 : mTmatrix.scale_about_origin( 1.0, mEvalData.base_radius_y/mEvalData.base_radius_x, 1.0 );
40 : 0 : }
41 : :
42 : : //-------------------------------------------------------------------------
43 : : // Purpose : Compute and return the bounding box for this cylinder.
44 : : //
45 : : // Special Notes :
46 : : //
47 : : //-------------------------------------------------------------------------
48 : 0 : CubitBox CylinderEvaluator::bounding_box( void ) const
49 : : {
50 : 0 : int ipt = 0;
51 [ # # ][ # # ]: 0 : CubitVector pts[8];
52 [ # # ]: 0 : CubitVector axis( 0.0, 0.0, 1.0 );
53 [ # # ]: 0 : CubitVector base_pt = base();
54 [ # # ][ # # ]: 0 : CubitVector top_pt = base() + mEvalData.height * axis;
[ # # ]
55 [ # # ]: 0 : CubitVector x_dir( 1.0, 0.0, 0.0 );
56 [ # # ]: 0 : CubitVector y_dir( 0.0, 1.0, 0.0 );
57 : 0 : double scale = mEvalData.base_radius_y * mEvalData.base_radius_x;
58 : :
59 [ # # ][ # # ]: 0 : pts[0] = base_pt + ( x_dir * mEvalData.base_radius_x );
[ # # ]
60 [ # # ][ # # ]: 0 : pts[1] = base_pt - ( x_dir * mEvalData.base_radius_x );
[ # # ]
61 [ # # ][ # # ]: 0 : pts[2] = base_pt + ( y_dir * mEvalData.base_radius_y );
[ # # ]
62 [ # # ][ # # ]: 0 : pts[3] = base_pt - ( y_dir * mEvalData.base_radius_y );
[ # # ]
63 [ # # ][ # # ]: 0 : pts[4] = top_pt + ( x_dir * mEvalData.top_radius );
[ # # ]
64 [ # # ][ # # ]: 0 : pts[5] = top_pt - ( x_dir * mEvalData.top_radius );
[ # # ]
65 [ # # ][ # # ]: 0 : pts[6] = top_pt + ( y_dir * mEvalData.top_radius * scale );
[ # # ][ # # ]
66 [ # # ][ # # ]: 0 : pts[7] = top_pt - ( y_dir * mEvalData.top_radius * scale );
[ # # ][ # # ]
67 : :
68 [ # # ]: 0 : for ( ipt = 0; ipt < 8; ipt++ )
69 : : {
70 [ # # ][ # # ]: 0 : pts[ipt] = mTmatrix * pts[ipt];
71 : : }
72 : :
73 [ # # ]: 0 : CubitVector min( pts[0] ),
74 [ # # ]: 0 : max( pts[0] );
75 [ # # ]: 0 : for ( ipt = 1; ipt < 8; ipt++ )
76 : : {
77 : 0 : CubitVector *pt = &(pts[ipt]);
78 [ # # ][ # # ]: 0 : if ( min.x() > pt->x() ) min.x( pt->x() );
[ # # ][ # # ]
[ # # ]
79 [ # # ][ # # ]: 0 : if ( min.y() > pt->y() ) min.y( pt->y() );
[ # # ][ # # ]
[ # # ]
80 [ # # ][ # # ]: 0 : if ( min.z() > pt->z() ) min.z( pt->z() );
[ # # ][ # # ]
[ # # ]
81 [ # # ][ # # ]: 0 : if ( max.x() < pt->x() ) max.x( pt->x() );
[ # # ][ # # ]
[ # # ]
82 [ # # ][ # # ]: 0 : if ( max.y() < pt->y() ) max.y( pt->y() );
[ # # ][ # # ]
[ # # ]
83 [ # # ][ # # ]: 0 : if ( max.z() < pt->z() ) max.z( pt->z() );
[ # # ][ # # ]
[ # # ]
84 : : }
85 : :
86 [ # # ]: 0 : CubitBox thebbox( min, max );
87 : :
88 : 0 : return thebbox;
89 : : }
90 : :
91 : : //-------------------------------------------------------------------------
92 : : // Purpose : This functions computes the point on the surface that is
93 : : // closest to the input location and then calculates the
94 : : // magnitudes of the principal curvatures at this (possibly,
95 : : // new) point on the surface.
96 : : //
97 : : // Special Notes :
98 : : //
99 : : //-------------------------------------------------------------------------
100 : 0 : CubitStatus CylinderEvaluator::principal_curvatures(
101 : : CubitVector const& location,
102 : : double& curvature_1,
103 : : double& curvature_2,
104 : : CubitVector* closest_location )
105 : : {
106 [ # # ][ # # ]: 0 : PRINT_ERROR("principles_curvatures not implemented for cylinders yet.\n");
107 : 0 : return CUBIT_FAILURE;
108 : :
109 : : // if ( closest_location )
110 : : // {
111 : : // return closest_point( location, closest_location );
112 : : // }
113 : : // return CUBIT_SUCCESS;
114 : : }
115 : :
116 : : //-------------------------------------------------------------------------
117 : : // Purpose : Computes the closest_point on the surface to the input
118 : : // location. Optionally, it also computes and returns
119 : : // the normal to the surface and the principal curvatures
120 : : // at closest_location.
121 : : //
122 : : //-------------------------------------------------------------------------
123 : 0 : CubitStatus CylinderEvaluator::closest_point( CubitVector const& location,
124 : : CubitVector* closest_location,
125 : : CubitVector* unit_normal_ptr,
126 : : CubitVector* curvature1_ptr,
127 : : CubitVector* curvature2_ptr) const
128 : : {
129 [ # # ]: 0 : CubitTransformMatrix inverse_Tmatrix = mTmatrix;
130 [ # # ]: 0 : inverse_Tmatrix.inverse();
131 [ # # ]: 0 : CubitVector new_pt = inverse_Tmatrix * location;
132 [ # # ]: 0 : CubitVector normal;
133 [ # # ][ # # ]: 0 : double dist = sqrt( ( new_pt.x() * new_pt.x() ) + ( new_pt.y() * new_pt.y() ) );
[ # # ][ # # ]
134 [ # # ]: 0 : if ( dist < GEOMETRY_RESABS )
135 : : {
136 [ # # ]: 0 : normal.set( 1.0, 0.0, 0.0 );
137 : : }
138 : : else
139 : : {
140 [ # # ][ # # ]: 0 : normal.set( new_pt.x(), new_pt.y(), 0.0 );
[ # # ]
141 : : }
142 [ # # ]: 0 : normal.normalize();
143 [ # # ]: 0 : if ( unit_normal_ptr )
144 : : {
145 [ # # ]: 0 : CubitVector origin( 0.0, 0.0, 0.0 );
146 [ # # ]: 0 : CubitVector endpt( normal );
147 : :
148 [ # # ][ # # ]: 0 : origin = mTmatrix * origin;;
149 [ # # ][ # # ]: 0 : endpt = mTmatrix * endpt;
150 : :
151 [ # # ][ # # ]: 0 : *unit_normal_ptr = endpt - origin;
152 [ # # ]: 0 : unit_normal_ptr->normalize();
153 : : }
154 [ # # ]: 0 : if ( closest_location != NULL )
155 : : {
156 [ # # ][ # # ]: 0 : CubitVector axis_pt( 0.0, 0.0, new_pt.z() );
157 [ # # ][ # # ]: 0 : double v = axis_pt.z() - base().z();
[ # # ]
158 : 0 : double radius = v * ( ( mEvalData.top_radius - mEvalData.base_radius_x ) / mEvalData.height ) + mEvalData.base_radius_x;
159 : :
160 [ # # ][ # # ]: 0 : *closest_location = axis_pt + ( radius * normal );
[ # # ]
161 [ # # ][ # # ]: 0 : *closest_location = mTmatrix * (*closest_location);
162 : : }
163 [ # # ]: 0 : return CUBIT_SUCCESS;
164 : : }
165 : :
166 : : //-------------------------------------------------------------------------
167 : : // Purpose : Given a UV parametric location, return the cooresponding
168 : : // XYZ location.
169 : : //-------------------------------------------------------------------------
170 : 0 : CubitVector CylinderEvaluator::position_from_u_v( double u, double v ) const
171 : : {
172 : 0 : double radius = v * ( ( mEvalData.top_radius - mEvalData.base_radius_x ) / mEvalData.height ) + mEvalData.base_radius_x;
173 [ # # ]: 0 : CubitVector base_pt = base();
174 : 0 : double two_pi = 2.0 * CUBIT_PI;
175 : :
176 [ # # ]: 0 : while ( u > two_pi ) u -= two_pi;
177 [ # # ]: 0 : while ( u < 0.0 ) u += two_pi;
178 : :
179 : 0 : double x = radius * sin( u );
180 : 0 : double y = radius * cos( u );
181 [ # # ]: 0 : double z = base_pt.z() + v;
182 : :
183 [ # # ]: 0 : CubitVector position( x, y, z );
184 [ # # ][ # # ]: 0 : position = mTmatrix * position;
185 : :
186 : 0 : return position;
187 : : }
188 : :
189 : : //-------------------------------------------------------------------------
190 : : // Purpose : Project a given XYZ position to a surface and return
191 : : // the UV and XYZ locations on the surface.
192 : : //-------------------------------------------------------------------------
193 : 0 : CubitStatus CylinderEvaluator::u_v_from_position
194 : : (
195 : : CubitVector const& location,
196 : : double& u,
197 : : double& v,
198 : : CubitVector* closest_location
199 : : ) const
200 : : {
201 [ # # ]: 0 : CubitTransformMatrix inverse_Tmatrix = mTmatrix;
202 [ # # ]: 0 : inverse_Tmatrix.inverse();
203 [ # # ]: 0 : CubitVector transformed_pt = inverse_Tmatrix * location;
204 [ # # ]: 0 : CubitVector base_pt = base();
205 [ # # ][ # # ]: 0 : CubitVector dir( transformed_pt.x(), transformed_pt.y(), 0.0 );
[ # # ]
206 [ # # ]: 0 : dir.normalize();
207 : :
208 [ # # ][ # # ]: 0 : v = transformed_pt.z() - base_pt.z();
209 [ # # ]: 0 : u = acos( dir.y() );
210 [ # # ][ # # ]: 0 : if ( dir.x() < 0.0 )
211 : 0 : u = 2*CUBIT_PI - u;
212 : :
213 [ # # ]: 0 : while ( u < 0.0 ) u += 2*CUBIT_PI;
214 [ # # ]: 0 : while ( u >= 2*CUBIT_PI ) u -= 2*CUBIT_PI;
215 : :
216 [ # # ]: 0 : if ( closest_location )
217 [ # # ]: 0 : closest_point( location, closest_location );
218 [ # # ]: 0 : return CUBIT_SUCCESS;
219 : : }
220 : :
221 : : //-------------------------------------------------------------------------
222 : : // Purpose : return the dimension parameters of this cylinder.
223 : : //
224 : : //-------------------------------------------------------------------------
225 : 0 : const CubitEvaluatorData* CylinderEvaluator::evaluator_data( void ) const
226 : : {
227 : 0 : return &mEvalData;
228 : : }
229 : :
230 : : //-------------------------------------------------------------------------
231 : : // Purpose : return parametric extremes in the U direction
232 : : //
233 : : //-------------------------------------------------------------------------
234 : 0 : CubitBoolean CylinderEvaluator::get_param_range_U
235 : : (
236 : : double& lower_bound,
237 : : double& upper_bound
238 : : ) const
239 : : {
240 : 0 : lower_bound = 0.0;
241 : 0 : upper_bound = 2*CUBIT_PI;
242 : 0 : return CUBIT_TRUE;
243 : : }
244 : :
245 : : //-------------------------------------------------------------------------
246 : : // Purpose : return parametric extremes in the V direction
247 : : //
248 : : //-------------------------------------------------------------------------
249 : 0 : CubitBoolean CylinderEvaluator::get_param_range_V
250 : : (
251 : : double& lower_bound,
252 : : double& upper_bound
253 : : ) const
254 : : {
255 : 0 : lower_bound = 0.0;
256 : 0 : upper_bound = mEvalData.height;
257 : 0 : return CUBIT_TRUE;
258 : : }
259 : :
260 : : // ********** END PUBLIC FUNCTIONS **********
261 : :
262 : 0 : CubitVector CylinderEvaluator::base() const
263 : : {
264 : 0 : return CubitVector( 0.0, 0.0, -0.5*mEvalData.height );
265 : : }
266 : :
267 : : // ********** END PROTECTED FUNCTIONS **********
268 : :
269 : : // ********** BEGIN PRIVATE FUNCTIONS **********
270 : : // ********** END PRIVATE FUNCTIONS **********
271 : :
272 : : // ********** BEGIN HELPER CLASSES **********
273 : : // ********** END HELPER CLASSES **********
274 : :
275 : : // ********** BEGIN EXTERN FUNCTIONS **********
276 : : // ********** END EXTERN FUNCTIONS **********
277 : :
278 : : // ********** BEGIN STATIC FUNCTIONS **********
279 : : // ********** END STATIC FUNCTIONS **********
|