Panda3D
 All Classes Functions Variables Enumerations
cMotionTrail.cxx
00001 // Filename: cMotionTrail.h
00002 // Created by:  aignacio (29Jan07)
00003 //
00004 ////////////////////////////////////////////////////////////////////
00005 //
00006 // PANDA 3D SOFTWARE
00007 // Copyright (c) Carnegie Mellon University.  All rights reserved.
00008 //
00009 // All use of this software is subject to the terms of the revised BSD
00010 // license.  You should have received a copy of this license along
00011 // with this source code in a file named "LICENSE."
00012 //
00013 ////////////////////////////////////////////////////////////////////
00014 
00015 #include "directbase.h"
00016 #include "cMotionTrail.h"
00017 #include "renderState.h"
00018 #include "colorAttrib.h"
00019 
00020 
00021 TypeHandle CMotionTrail::_type_handle;
00022 
00023 ////////////////////////////////////////////////////////////////////
00024 //     Function: CMotionTrail::Constructor
00025 //       Access: Published
00026 //  Description: Constructor
00027 ////////////////////////////////////////////////////////////////////
00028 CMotionTrail::
00029 CMotionTrail ( ) {
00030 
00031   _active = true;
00032   _enable = true;
00033   
00034   _pause = false;
00035   _pause_time = 0.0f;
00036 
00037   _fade = false;
00038   _fade_end = false;
00039   _fade_time = 0.0f;
00040   _fade_start_time = 0.0f;
00041   _fade_color_scale = 1.0f;
00042 
00043   _last_update_time = 0.0f;
00044 
00045   _vertex_list.clear ( );
00046   _frame_list.clear ( );
00047 
00048   // parameters
00049   _color_scale = 1.0;
00050   _sampling_time = 0.0;
00051   _time_window = 1.0;
00052   _square_t = true;
00053   _use_texture = false;
00054   _calculate_relative_matrix = false;
00055 
00056   // nurbs parameters
00057   _use_nurbs = false;
00058   _resolution_distance = 0.5f;
00059 
00060   // node path states
00061   _geom_node = 0;
00062 
00063   // real-time data
00064   _vertex_index = 0;
00065   _vertex_data = 0;
00066   _triangles = 0;  
00067 
00068   _vertex_array = 0;
00069 }
00070 
00071 ////////////////////////////////////////////////////////////////////
00072 //     Function: CMotionTrail::Destructor
00073 //       Access: Published
00074 //  Description: Destructor
00075 ////////////////////////////////////////////////////////////////////
00076 CMotionTrail::
00077 ~CMotionTrail ( ) {
00078 
00079 }
00080 
00081 ////////////////////////////////////////////////////////////////////
00082 //     Function: CMotionTrail::reset
00083 //       Access: Published
00084 //  Description: Reset the frame sample history.
00085 ////////////////////////////////////////////////////////////////////
00086 void CMotionTrail::
00087 reset ( ) {
00088   _frame_list.clear ( );
00089 }
00090 
00091 ////////////////////////////////////////////////////////////////////
00092 //     Function: CMotionTrail::reset_vertex_list
00093 //       Access: Published
00094 //  Description: Reset the vertex list.
00095 ////////////////////////////////////////////////////////////////////
00096 void CMotionTrail::
00097 reset_vertex_list ( ) {
00098   _vertex_list.clear ( );
00099 }
00100 
00101 ////////////////////////////////////////////////////////////////////
00102 //     Function: CMotionTrail::enable
00103 //       Access: Published
00104 //  Description: Enable/disable the motion trail.
00105 ////////////////////////////////////////////////////////////////////
00106 void CMotionTrail::
00107 enable (bool enable) {
00108   _enable = enable;
00109 }
00110 
00111 ////////////////////////////////////////////////////////////////////
00112 //     Function: CMotionTrail::set_geom_node
00113 //       Access: Published
00114 //  Description: Set the GeomNode.
00115 ////////////////////////////////////////////////////////////////////
00116 void CMotionTrail::
00117 set_geom_node (PT(GeomNode) geom_node) {
00118   _geom_node = geom_node;
00119 }
00120 
00121 ////////////////////////////////////////////////////////////////////
00122 //     Function: CMotionTrail::add_vertex
00123 //       Access: Published
00124 //  Description: Add a vertex.
00125 ////////////////////////////////////////////////////////////////////
00126 void CMotionTrail::
00127 add_vertex (LVector4 *vertex, LVector4 *start_color, LVector4 *end_color, PN_stdfloat v) {
00128 
00129   CMotionTrailVertex motion_trail_vertex;
00130 
00131   motion_trail_vertex._vertex = *vertex;
00132   motion_trail_vertex._start_color = *start_color;
00133   motion_trail_vertex._end_color = *end_color;
00134   motion_trail_vertex._v = v;
00135   
00136   motion_trail_vertex._nurbs_curve_evaluator = new NurbsCurveEvaluator ( );
00137 
00138   _vertex_list.push_back (motion_trail_vertex);
00139 }
00140 
00141 ////////////////////////////////////////////////////////////////////
00142 //     Function: CMotionTrail::set_parameters
00143 //       Access: Published
00144 //  Description: Set motion trail parameters.
00145 //
00146 //               sampling_time = Can be used to specify a lower 
00147 //               sampling rate than the frame rate. Use 0.0 with 
00148 //               nurbs. 
00149 //
00150 //               time_window = a component for the "length" of the 
00151 //               motion trail.  The motion trail length = 
00152 //               time_window * velocity of the object.
00153 //
00154 //               use_texture = texture option on/off.
00155 //
00156 //               calculate_relative_matrix = calculate relative 
00157 //               matrix on/off.
00158 //
00159 //               use_nurbs = nurbs option on/off
00160 //
00161 //               resolution_distance = the distance used to 
00162 //               determine the number of geometry samples. 
00163 //               samples = motion trail length / resolution_distance.
00164 //               Applicable only if nurbs is on.
00165 ////////////////////////////////////////////////////////////////////
00166 void CMotionTrail::
00167 set_parameters (PN_stdfloat sampling_time, PN_stdfloat time_window, bool use_texture, bool calculate_relative_matrix, bool use_nurbs, PN_stdfloat resolution_distance) {
00168 
00169   _sampling_time = sampling_time;
00170   _time_window = time_window;
00171   _use_texture = use_texture;
00172   _calculate_relative_matrix = calculate_relative_matrix;
00173   _use_nurbs = use_nurbs;
00174   _resolution_distance = resolution_distance;
00175 }
00176 
00177 ////////////////////////////////////////////////////////////////////
00178 //     Function: CMotionTrail::check_for_update
00179 //       Access: Published
00180 //  Description: Check if a sample can be submitted.
00181 ////////////////////////////////////////////////////////////////////
00182 int CMotionTrail::
00183 check_for_update (PN_stdfloat current_time) {
00184 
00185   int state;
00186   
00187   state = false;
00188   if ((current_time - _last_update_time) >= _sampling_time) {
00189       state = true;
00190   }
00191   if (_pause) {
00192       state = false;
00193   }
00194   state = state && _enable;
00195 
00196   return state;
00197 }
00198 
00199 PN_stdfloat one_minus_x (PN_stdfloat x) {
00200   x = 1.0 - x;
00201   if (x < 0.0) {
00202     x = 0.0;
00203   }
00204 
00205   return x;
00206 }
00207 
00208 ////////////////////////////////////////////////////////////////////
00209 //     Function: CMotionTrail::begin_geometry
00210 //       Access: Public
00211 //  Description: 
00212 ////////////////////////////////////////////////////////////////////
00213 void CMotionTrail::
00214 begin_geometry ( ) {
00215 
00216   const GeomVertexFormat *format;
00217 
00218   _vertex_index = 0;  
00219   if (_use_texture) {
00220     format = GeomVertexFormat::get_v3c4t2 ( );
00221   }
00222   else {
00223     format = GeomVertexFormat::get_v3c4 ( );
00224   }
00225 
00226   // Clear the previous writers before we create a new vertex data
00227   // object--this seems to work around an ordering problem in the
00228   // low-level vertex data destructors.
00229   _vertex_writer.clear();
00230   _color_writer.clear();
00231   _texture_writer.clear();
00232 
00233   _vertex_data = new GeomVertexData ("vertices", format, Geom::UH_static);
00234   _vertex_writer = GeomVertexWriter (_vertex_data, "vertex");
00235   _color_writer = GeomVertexWriter (_vertex_data, "color");
00236   if (_use_texture) {
00237     _texture_writer = GeomVertexWriter (_vertex_data, "texcoord");
00238   }
00239   
00240   _triangles = new GeomTriangles (Geom::UH_static);
00241 }
00242 
00243 ////////////////////////////////////////////////////////////////////
00244 //     Function: CMotionTrail::add_geometry_quad
00245 //       Access: Public
00246 //  Description: LVector3 vertex version.
00247 ////////////////////////////////////////////////////////////////////
00248 void CMotionTrail::
00249 add_geometry_quad (LVector3 &v0, LVector3 &v1, LVector3 &v2, LVector3 &v3, LVector4 &c0, LVector4 &c1, LVector4 &c2, LVector4 &c3, LVector2 &t0, LVector2 &t1, LVector2 &t2, LVector2 &t3) {
00250 
00251   _vertex_writer.add_data3 (v0);
00252   _vertex_writer.add_data3 (v1);
00253   _vertex_writer.add_data3 (v2);
00254   _vertex_writer.add_data3 (v3);
00255 
00256   _color_writer.add_data4 (c0);
00257   _color_writer.add_data4 (c1);
00258   _color_writer.add_data4 (c2);
00259   _color_writer.add_data4 (c3);
00260 
00261   if (_use_texture) {
00262     _texture_writer.add_data2 (t0);
00263     _texture_writer.add_data2 (t1);
00264     _texture_writer.add_data2 (t2);
00265     _texture_writer.add_data2 (t3);
00266   }
00267 
00268   int vertex_index;
00269   vertex_index = _vertex_index;
00270 
00271   _triangles -> add_vertex (vertex_index + 0);
00272   _triangles -> add_vertex (vertex_index + 1);
00273   _triangles -> add_vertex (vertex_index + 2);
00274   _triangles -> close_primitive ( );
00275 
00276   _triangles -> add_vertex (vertex_index + 1);
00277   _triangles -> add_vertex (vertex_index + 3);
00278   _triangles -> add_vertex (vertex_index + 2);
00279   _triangles -> close_primitive ( );
00280 
00281   _vertex_index += 4;
00282 }
00283 
00284 ////////////////////////////////////////////////////////////////////
00285 //     Function: CMotionTrail::add_geometry_quad
00286 //       Access: Public
00287 //  Description: LVector4 vertex version.
00288 ////////////////////////////////////////////////////////////////////
00289 void CMotionTrail::
00290 add_geometry_quad (LVector4 &v0, LVector4 &v1, LVector4 &v2, LVector4 &v3, LVector4 &c0, LVector4 &c1, LVector4 &c2, LVector4 &c3, LVector2 &t0, LVector2 &t1, LVector2 &t2, LVector2 &t3) {
00291 
00292   _vertex_writer.add_data3 (v0 [0], v0 [1], v0 [2]);
00293   _vertex_writer.add_data3 (v1 [0], v1 [1], v1 [2]);
00294   _vertex_writer.add_data3 (v2 [0], v2 [1], v2 [2]);
00295   _vertex_writer.add_data3 (v3 [0], v3 [1], v3 [2]);
00296 
00297   _color_writer.add_data4 (c0);
00298   _color_writer.add_data4 (c1);
00299   _color_writer.add_data4 (c2);
00300   _color_writer.add_data4 (c3);
00301 
00302   if (_use_texture) {
00303     _texture_writer.add_data2 (t0);
00304     _texture_writer.add_data2 (t1);
00305     _texture_writer.add_data2 (t2);
00306     _texture_writer.add_data2 (t3);
00307   }
00308 
00309   int vertex_index;
00310   vertex_index = _vertex_index;
00311 
00312   _triangles -> add_vertex (vertex_index + 0);
00313   _triangles -> add_vertex (vertex_index + 1);
00314   _triangles -> add_vertex (vertex_index + 2);
00315   _triangles -> close_primitive ( );
00316 
00317   _triangles -> add_vertex (vertex_index + 1);
00318   _triangles -> add_vertex (vertex_index + 3);
00319   _triangles -> add_vertex (vertex_index + 2);
00320   _triangles -> close_primitive ( );
00321 
00322   _vertex_index += 4;
00323 }
00324 
00325 ////////////////////////////////////////////////////////////////////
00326 //     Function: CMotionTrail::end_geometry
00327 //       Access: Public
00328 //  Description: 
00329 ////////////////////////////////////////////////////////////////////
00330 void CMotionTrail::end_geometry ( ) {    
00331   static CPT(RenderState) state;
00332   if (state == (RenderState *)NULL) {
00333     state = RenderState::make(ColorAttrib::make_vertex());
00334   }
00335 
00336   PT(Geom) geometry;
00337   
00338   geometry = new Geom (_vertex_data);
00339   geometry -> add_primitive (_triangles);
00340 
00341   if (_geom_node) {
00342     _geom_node -> remove_all_geoms ( );
00343     _geom_node -> add_geom (geometry, state);
00344   }
00345 }
00346 
00347 ////////////////////////////////////////////////////////////////////
00348 //     Function: CMotionTrail::update_motion_trail
00349 //       Access: Published
00350 //  Description: See class header comments.
00351 ////////////////////////////////////////////////////////////////////
00352 void CMotionTrail::
00353 update_motion_trail (PN_stdfloat current_time, LMatrix4 *transform) {
00354 
00355   int debug;
00356   int total_frames;
00357   
00358   debug = false;
00359 
00360   total_frames = _frame_list.size ( );
00361   if (total_frames >= 1) {
00362     FrameList::iterator frame_iterator;
00363     CMotionTrailFrame motion_trail_frame;
00364  
00365     frame_iterator = _frame_list.begin ( );
00366     motion_trail_frame = *frame_iterator;
00367     if (*transform == motion_trail_frame._transform) {
00368       // duplicate transform
00369       return;
00370     }
00371   }
00372 
00373   int total_vertices;
00374   PN_stdfloat color_scale;
00375   LMatrix4 start_transform;
00376   LMatrix4 end_transform;
00377   LMatrix4 inverse_matrix;
00378 
00379   total_vertices = _vertex_list.size ( );
00380   color_scale = _color_scale;
00381   if (_fade) {
00382     PN_stdfloat elapsed_time;
00383     
00384     elapsed_time = current_time - _fade_start_time;
00385     if (elapsed_time < 0.0) {
00386       elapsed_time = 0.0;
00387     }
00388     if (elapsed_time < _fade_time) {
00389       color_scale = (1.0f - (elapsed_time / _fade_time)) * color_scale;
00390     }
00391     else {
00392       color_scale = 0.0;
00393       _fade_end = true;
00394     }
00395   }
00396 
00397   _last_update_time = current_time;
00398 
00399   // remove expired frames
00400   PN_stdfloat minimum_time;
00401   
00402   minimum_time = current_time - _time_window;
00403   
00404   CMotionTrailFrame motion_trail_frame;
00405   
00406   while (!_frame_list.empty()) {
00407     motion_trail_frame = _frame_list.back();
00408     if (motion_trail_frame._time >= minimum_time) {
00409       break;
00410     }
00411     
00412     _frame_list.pop_back ( );
00413   }
00414   
00415   // add new frame to beginning of list
00416   {
00417     CMotionTrailFrame motion_trail_frame;
00418 
00419     motion_trail_frame._time = current_time;
00420     motion_trail_frame._transform = *transform;
00421 
00422     _frame_list.push_front(motion_trail_frame);
00423   }
00424 
00425   // convert frames and vertices to geometry
00426   total_frames = _frame_list.size ( );
00427 
00428   if (debug) {
00429     printf ("update_motion_trail, total_frames = %d, total_vertices = %d, nurbs = %d, _calculate_relative_matrix = %d \n", total_frames, total_vertices, _use_nurbs, _calculate_relative_matrix);
00430   }
00431 
00432   if ((total_frames >= 2) && (total_vertices >= 2)) {
00433     int total_segments;
00434     PN_stdfloat minimum_time;
00435     PN_stdfloat delta_time;
00436     CMotionTrailFrame last_motion_trail_frame;
00437 
00438     VertexList::iterator vertex_iterator;    
00439 
00440     // convert vertex list to vertex array
00441     int index = 0;
00442     _vertex_array = new CMotionTrailVertex [total_vertices];
00443     for (vertex_iterator = _vertex_list.begin ( ); vertex_iterator != _vertex_list.end ( ); vertex_iterator++) {   
00444       _vertex_array [index] = *vertex_iterator;        
00445       index++;
00446     }
00447     
00448     // begin geometry
00449     this -> begin_geometry ( );
00450 
00451     total_segments = total_frames - 1;
00452       
00453     last_motion_trail_frame = _frame_list.back();
00454     minimum_time = last_motion_trail_frame._time;
00455     delta_time = current_time - minimum_time;
00456 
00457     if (_calculate_relative_matrix) {
00458       inverse_matrix = *transform;
00459       inverse_matrix.invert_in_place ( );
00460     }
00461 
00462     if (_use_nurbs && (total_frames >= 5)) {
00463     
00464       // nurbs version
00465       int total_vertex_segments;
00466       PN_stdfloat total_distance;  
00467       LVector3 vector;
00468       LVector4 v;
00469       LVector4 v0;
00470       LVector4 v1;
00471       LVector4 v2;
00472       LVector4 v3;
00473 
00474       total_vertex_segments = total_vertices - 1;
00475       total_distance = 0.0f;
00476 
00477       // reset NurbsCurveEvaluators for each vertex (the starting point for the trail)
00478       {
00479         CMotionTrailVertex *motion_trail_vertex;
00480         PT(NurbsCurveEvaluator) nurbs_curve_evaluator;
00481 
00482         for (index = 0; index < total_vertices; index++) {   
00483           motion_trail_vertex = &_vertex_array [index];
00484           nurbs_curve_evaluator = motion_trail_vertex -> _nurbs_curve_evaluator;
00485           nurbs_curve_evaluator -> set_order (4);
00486           nurbs_curve_evaluator -> reset (total_segments);
00487         }
00488       }
00489       
00490       // add vertices to each NurbsCurveEvaluator
00491       int segment_index;
00492       CMotionTrailFrame motion_trail_frame_start;
00493       CMotionTrailFrame motion_trail_frame_end;
00494       
00495       segment_index = 0;
00496 
00497       FrameList::iterator frame_iterator;
00498       frame_iterator = _frame_list.begin ( );
00499       while (segment_index < total_segments) {
00500         int vertex_segement_index;
00501 
00502         motion_trail_frame_start = *frame_iterator;
00503         frame_iterator++;
00504         motion_trail_frame_end = *frame_iterator;
00505 
00506         if (_calculate_relative_matrix) {
00507           start_transform.multiply (motion_trail_frame_start._transform, inverse_matrix);
00508           end_transform.multiply (motion_trail_frame_end._transform, inverse_matrix);
00509         }
00510         else {
00511           start_transform = motion_trail_frame_start._transform;
00512           end_transform = motion_trail_frame_end._transform;
00513         }
00514 
00515         CMotionTrailVertex *motion_trail_vertex_start;
00516         CMotionTrailVertex *motion_trail_vertex_end;
00517         PT(NurbsCurveEvaluator) nurbs_curve_evaluator;
00518 
00519         motion_trail_vertex_start = &_vertex_array [0];
00520 
00521         v0 = start_transform.xform (motion_trail_vertex_start -> _vertex);
00522         v2 = end_transform.xform (motion_trail_vertex_start -> _vertex);
00523 
00524         nurbs_curve_evaluator = motion_trail_vertex_start -> _nurbs_curve_evaluator;
00525         nurbs_curve_evaluator -> set_vertex (segment_index, v0);
00526 
00527         vertex_segement_index = 0;
00528         while (vertex_segement_index < total_vertex_segments) {
00529           motion_trail_vertex_start = &_vertex_array [vertex_segement_index];
00530           motion_trail_vertex_end = &_vertex_array [vertex_segement_index + 1];
00531 
00532           v1 = start_transform.xform (motion_trail_vertex_end -> _vertex);
00533           v3 = end_transform.xform (motion_trail_vertex_end -> _vertex);
00534 
00535           nurbs_curve_evaluator = motion_trail_vertex_end -> _nurbs_curve_evaluator;
00536 
00537           nurbs_curve_evaluator -> set_vertex (segment_index, v1);
00538           if (vertex_segement_index == (total_vertex_segments - 1)) {
00539             PN_stdfloat distance;
00540 
00541             v = v1 - v3;
00542             vector.set (v[0], v[1], v[2]);
00543             distance = vector.length();
00544             total_distance += distance;
00545           }
00546 
00547           vertex_segement_index += 1;
00548         }
00549 
00550         segment_index += 1;
00551       }
00552       
00553       // evaluate NurbsCurveEvaluator for each vertex
00554       PT(NurbsCurveResult) *nurbs_curve_result_array;
00555       
00556       nurbs_curve_result_array = new PT(NurbsCurveResult) [total_vertices];
00557       for (index = 0; index < total_vertices; index++) {
00558       
00559         CMotionTrailVertex *motion_trail_vertex;
00560         PT(NurbsCurveEvaluator) nurbs_curve_evaluator;
00561         PT(NurbsCurveResult) nurbs_curve_result;
00562 
00563         motion_trail_vertex = &_vertex_array [index];
00564 
00565         nurbs_curve_evaluator = motion_trail_vertex -> _nurbs_curve_evaluator;
00566         nurbs_curve_result = nurbs_curve_evaluator -> evaluate ( );
00567         nurbs_curve_result_array [index] = nurbs_curve_result;
00568 
00569         if (debug) {
00570           PN_stdfloat nurbs_start_t;
00571           PN_stdfloat nurbs_end_t;
00572 
00573           nurbs_start_t = nurbs_curve_result -> get_start_t();
00574           nurbs_end_t = nurbs_curve_result -> get_end_t();
00575 
00576           printf ("nurbs_start_t %f, nurbs_end_t %f \n", nurbs_start_t, nurbs_end_t);
00577         }
00578       }
00579       
00580       // create quads from NurbsCurveResult                    
00581       PN_stdfloat total_curve_segments;
00582       
00583       total_curve_segments = (total_distance / _resolution_distance);
00584       if (total_curve_segments < total_segments) {
00585         total_curve_segments = total_segments;
00586       }
00587 
00588       {
00589         LVector3 v0;
00590         LVector3 v1;
00591         LVector3 v2;
00592         LVector3 v3;
00593 
00594         LVector4 c0;
00595         LVector4 c1;
00596         LVector4 c2;
00597         LVector4 c3;
00598 
00599         LVector2 t0;
00600         LVector2 t1;
00601         LVector2 t2;
00602         LVector2 t3;
00603 
00604         LVector4 vertex_start_color;
00605         LVector4 vertex_end_color;
00606 
00607         PN_stdfloat curve_segment_index;
00608 
00609         curve_segment_index = 0.0;
00610         while (curve_segment_index < total_curve_segments) {   
00611         
00612           PN_stdfloat st;
00613           PN_stdfloat et;
00614           PN_stdfloat start_t;
00615           PN_stdfloat end_t;
00616           PN_stdfloat color_start_t;
00617           PN_stdfloat color_end_t;
00618 
00619           int vertex_segement_index;
00620 
00621           CMotionTrailVertex *motion_trail_vertex_start;
00622           CMotionTrailVertex *motion_trail_vertex_end;
00623           PT(NurbsCurveResult) start_nurbs_curve_result;
00624           PT(NurbsCurveResult) end_nurbs_curve_result;
00625 
00626           vertex_segement_index = 0;
00627 
00628           st = curve_segment_index / total_curve_segments;
00629           et = (curve_segment_index + 1.0) / total_curve_segments;
00630 
00631           start_t = st;
00632           end_t = et;
00633 
00634           if (_square_t) {
00635             start_t *= start_t;
00636             end_t *= end_t;
00637           }
00638 
00639           motion_trail_vertex_start = &_vertex_array [0];
00640 
00641           vertex_start_color = motion_trail_vertex_start -> _end_color + (motion_trail_vertex_start -> _start_color - motion_trail_vertex_start  -> _end_color);
00642 
00643           color_start_t = color_scale * start_t;
00644           color_end_t = color_scale * end_t;
00645 
00646           c0 = vertex_start_color * one_minus_x (color_start_t);
00647           c2 = vertex_start_color * one_minus_x (color_end_t);
00648 
00649           t0.set (one_minus_x (st), motion_trail_vertex_start -> _v);
00650           t2.set (one_minus_x (et), motion_trail_vertex_start -> _v);
00651 
00652           while (vertex_segement_index < total_vertex_segments) {
00653 
00654             PN_stdfloat start_nurbs_start_t;
00655             PN_stdfloat start_nurbs_end_t;
00656             PN_stdfloat end_nurbs_start_t;
00657             PN_stdfloat end_nurbs_end_t;
00658 
00659             motion_trail_vertex_start = &_vertex_array [vertex_segement_index];
00660             motion_trail_vertex_end = &_vertex_array [vertex_segement_index + 1];
00661 
00662             start_nurbs_curve_result = nurbs_curve_result_array [vertex_segement_index];
00663             end_nurbs_curve_result = nurbs_curve_result_array [vertex_segement_index + 1];
00664 
00665             start_nurbs_start_t = start_nurbs_curve_result -> get_start_t();
00666             start_nurbs_end_t = start_nurbs_curve_result -> get_end_t();
00667             end_nurbs_start_t = end_nurbs_curve_result -> get_start_t();
00668             end_nurbs_end_t = end_nurbs_curve_result -> get_end_t();
00669 
00670             PN_stdfloat start_delta_t;
00671             PN_stdfloat end_delta_t;
00672 
00673             start_delta_t = (start_nurbs_end_t - start_nurbs_start_t);
00674             end_delta_t = (end_nurbs_end_t - end_nurbs_start_t);
00675 
00676             start_nurbs_curve_result -> eval_point (start_nurbs_start_t + (start_delta_t * st), v0);
00677             end_nurbs_curve_result -> eval_point (end_nurbs_start_t + (end_delta_t * st), v1);
00678 
00679             start_nurbs_curve_result -> eval_point (start_nurbs_start_t + (start_delta_t * et), v2);
00680             end_nurbs_curve_result -> eval_point (end_nurbs_start_t + (end_delta_t * et), v3);
00681 
00682             // color
00683             vertex_end_color = motion_trail_vertex_end -> _end_color + (motion_trail_vertex_end -> _start_color - motion_trail_vertex_end -> _end_color);
00684 
00685             c1 = vertex_end_color * one_minus_x (color_start_t);
00686             c3 = vertex_end_color * one_minus_x (color_end_t);
00687 
00688             // uv
00689             t1.set (one_minus_x (st), motion_trail_vertex_end -> _v);
00690             t3.set (one_minus_x (et), motion_trail_vertex_end -> _v);
00691 
00692             this -> add_geometry_quad (v0, v1, v2, v3, c0, c1, c2, c3, t0, t1, t2, t3);
00693 
00694             // reuse calculations
00695             c0 = c1;
00696             c2 = c3;
00697 
00698             t0 = t1;
00699             t2 = t3;
00700 
00701             vertex_segement_index += 1;
00702           }
00703 
00704           curve_segment_index += 1.0;
00705         }
00706       }
00707 
00708       for (index = 0; index < total_vertices; index++) {
00709         nurbs_curve_result_array [index] = 0;
00710       }
00711       
00712       delete[] nurbs_curve_result_array;
00713     }
00714     else {
00715 
00716       // non-nurbs version
00717       int segment_index;
00718       int vertex_segment_index;
00719       int total_vertex_segments;
00720       
00721       PN_stdfloat st;
00722       PN_stdfloat et;
00723       PN_stdfloat start_t;
00724       PN_stdfloat end_t;
00725       PN_stdfloat color_start_t;
00726       PN_stdfloat color_end_t;
00727 
00728       LVector4 v0;
00729       LVector4 v1;
00730       LVector4 v2;
00731       LVector4 v3;
00732 
00733       LVector4 c0;
00734       LVector4 c1;
00735       LVector4 c2;
00736       LVector4 c3;
00737 
00738       LVector2 t0;
00739       LVector2 t1;
00740       LVector2 t2;
00741       LVector2 t3;
00742 
00743       LVector4 vertex_start_color;
00744       LVector4 vertex_end_color;
00745 
00746       CMotionTrailFrame motion_trail_frame_start;
00747       CMotionTrailFrame motion_trail_frame_end;
00748                     
00749       segment_index = 0;
00750       FrameList::iterator frame_iterator;
00751       frame_iterator = _frame_list.begin ( );
00752       while (segment_index < total_segments) {
00753       
00754         CMotionTrailVertex *motion_trail_vertex_start;
00755         CMotionTrailVertex *motion_trail_vertex_end;
00756 
00757         motion_trail_frame_start = *frame_iterator;
00758         frame_iterator++;
00759         motion_trail_frame_end = *frame_iterator;
00760 
00761         start_t = (motion_trail_frame_start._time - minimum_time) / delta_time;
00762         end_t = (motion_trail_frame_end._time - minimum_time) / delta_time;
00763 
00764         st = start_t;
00765         et = end_t;
00766 
00767         if (_square_t) {
00768           start_t *= start_t;
00769           end_t *= end_t;
00770         }
00771 
00772         vertex_segment_index = 0;
00773         total_vertex_segments = total_vertices - 1;
00774 
00775         if (_calculate_relative_matrix) {
00776           start_transform.multiply (motion_trail_frame_start._transform, inverse_matrix);
00777           end_transform.multiply (motion_trail_frame_end._transform, inverse_matrix);
00778         }
00779         else {
00780           start_transform = motion_trail_frame_start._transform;
00781           end_transform = motion_trail_frame_end._transform;
00782         }
00783 
00784         motion_trail_vertex_start = &_vertex_array [0];
00785 
00786         v0 = start_transform.xform (motion_trail_vertex_start -> _vertex);
00787         v2 = end_transform.xform (motion_trail_vertex_start -> _vertex);
00788 
00789         vertex_start_color = motion_trail_vertex_start -> _end_color + (motion_trail_vertex_start -> _start_color - motion_trail_vertex_start -> _end_color);
00790         color_start_t = color_scale * start_t;
00791         color_end_t = color_scale * end_t;
00792         c0 = vertex_start_color * color_start_t;
00793         c2 = vertex_start_color * color_end_t;
00794 
00795         t0.set (st, motion_trail_vertex_start -> _v);
00796         t2.set (et, motion_trail_vertex_start -> _v);
00797 
00798         while (vertex_segment_index < total_vertex_segments) {
00799         
00800           motion_trail_vertex_start = &_vertex_array [vertex_segment_index];
00801           motion_trail_vertex_end = &_vertex_array [vertex_segment_index + 1];
00802 
00803           v1 = start_transform.xform (motion_trail_vertex_end -> _vertex);
00804           v3 = end_transform.xform (motion_trail_vertex_end -> _vertex);
00805 
00806           // color
00807           vertex_end_color = motion_trail_vertex_end -> _end_color + (motion_trail_vertex_end -> _start_color - motion_trail_vertex_end -> _end_color);
00808 
00809           c1 = vertex_end_color * color_start_t;
00810           c3 = vertex_end_color * color_end_t;
00811 
00812           // uv
00813           t1.set (st, motion_trail_vertex_end -> _v);
00814           t3.set (et, motion_trail_vertex_end -> _v);
00815 
00816           this -> add_geometry_quad (v0, v1, v2, v3, c0, c1, c2, c3, t0, t1, t2, t3);
00817 
00818           // reuse calculations
00819           v0 = v1;
00820           v2 = v3;
00821 
00822           c0 = c1;
00823           c2 = c3;
00824 
00825           t0 = t1;
00826           t2 = t3;
00827 
00828           vertex_segment_index += 1;
00829         }
00830 
00831         segment_index += 1;
00832       }  
00833     }
00834 
00835     // end geometry
00836     this -> end_geometry ( );   
00837 
00838     delete[] _vertex_array;
00839     _vertex_array = 0;
00840   }
00841 }
 All Classes Functions Variables Enumerations