Main Page   Class Hierarchy   Alphabetical List   Compound List   File List   Compound Members   File Members  

panda/src/gobj/geomTristrip.cxx

Go to the documentation of this file.
00001 // Filename: geomTristrip.cxx
00002 // Created by:  charles (13Jul00)
00003 //
00004 ////////////////////////////////////////////////////////////////////
00005 //
00006 // PANDA 3D SOFTWARE
00007 // Copyright (c) 2001, Disney Enterprises, Inc.  All rights reserved
00008 //
00009 // All use of this software is subject to the terms of the Panda 3d
00010 // Software license.  You should have received a copy of this license
00011 // along with this source code; you will also find a current copy of
00012 // the license at http://www.panda3d.org/license.txt .
00013 //
00014 // To contact the maintainers of this program write to
00015 // panda3d@yahoogroups.com .
00016 //
00017 ////////////////////////////////////////////////////////////////////
00018 
00019 #include <datagram.h>
00020 #include <datagramIterator.h>
00021 #include <bamReader.h>
00022 #include <bamWriter.h>
00023 #include <ioPtaDatagramShort.h>
00024 #include <ioPtaDatagramInt.h>
00025 #include <ioPtaDatagramLinMath.h>
00026 #include <graphicsStateGuardianBase.h>
00027 
00028 #include "geomTri.h"
00029 #include "geomTristrip.h"
00030 
00031 TypeHandle GeomTristrip::_type_handle;
00032 
00033 
00034 ////////////////////////////////////////////////////////////////////
00035 //     Function: GeomTristrip::make_copy
00036 //       Access: Public, Virtual
00037 //  Description: Returns a newly-allocated Geom that is a shallow copy
00038 //               of this one.  It will be a different Geom pointer,
00039 //               but its internal data may or may not be shared with
00040 //               that of the original Geom.
00041 ////////////////////////////////////////////////////////////////////
00042 Geom *GeomTristrip::
00043 make_copy() const {
00044   return new GeomTristrip(*this);
00045 }
00046 
00047 ////////////////////////////////////////////////////////////////////
00048 //     Function: GeomTristrip::print_draw_immediate
00049 //       Access:
00050 //  Description:
00051 ////////////////////////////////////////////////////////////////////
00052 void GeomTristrip::print_draw_immediate( void ) const
00053 {
00054   /*
00055     int i;
00056     int j;
00057     int k;
00058     int nprims = _numprims;
00059     int* plen = _primlengths;
00060     Vertexf* tcoords = _coords;
00061     Normalf* tnorms = _norms;
00062     Colorf* tcolors = _colors;
00063     TexCoordf* ttexcoords = _texcoords;
00064     ushort* tvindex = _vindex;
00065     ushort* tnindex = _nindex;
00066     ushort* tcindex = _cindex;
00067     ushort* ttindex = _tindex;
00068 
00069     // Draw overall
00070     if ( _color_command[G_OVERALL] != _issue_color_noop )
00071     {
00072         nout << "Color (Overall): ";
00073         if ( tcindex )
00074         {
00075             nout << "idx: " << *tcindex << " ";
00076             nout << tcolors[*(tcindex++)];
00077         }
00078         else
00079             nout << *(tcolors++);
00080         nout << endl;
00081     }
00082     if ( _normal_command[G_OVERALL] != _issue_normal_noop )
00083     {
00084         nout << "Normal (Overall): ";
00085         if ( tnindex )
00086         {
00087             nout << "idx: " << *tnindex << " ";
00088             nout << tnorms[*(tnindex++)];
00089         }
00090         else
00091             nout << *(tnorms++);
00092         nout << endl;
00093     }
00094 
00095     for ( i = nprims; i > 0; i-- )
00096     {
00097         // Draw per primitive
00098         if ( _color_command[G_PER_PRIM] != _issue_color_noop )
00099         {
00100             nout << "Color (Per Prim): ";
00101             if ( tcindex )
00102             {
00103                 nout << "idx: " << *tcindex << " ";
00104                 nout << tcolors[*(tcindex++)];
00105             }
00106             else
00107                 nout << *(tcolors++);
00108             nout << endl;
00109         }
00110         if ( _normal_command[G_PER_PRIM] != _issue_normal_noop )
00111         {
00112             nout << "Normal (Per Prim): ";
00113             if ( tnindex )
00114             {
00115                 nout << "idx: " << *tnindex << " ";
00116                 nout << tnorms[*(tnindex++)];
00117             }
00118             else
00119                 nout << *(tnorms++);
00120             nout << endl;
00121         }
00122 
00123         nout << "BeginGfx()" << endl;
00124 
00125         for ( j = *(plen++); j > 1; j -= 2 )
00126         {
00127             // Draw per component
00128             if ( _color_command[G_PER_COMPONENT] != _issue_color_noop )
00129             {
00130                 nout << "Color (Per Component): ";
00131                 if ( tcindex )
00132                 {
00133                     nout << "idx: " << *tcindex << " ";
00134                     nout << tcolors[*(tcindex++)];
00135                 }
00136                 else
00137                     nout << *(tcolors++);
00138                 nout << endl;
00139             }
00140             if ( _normal_command[G_PER_COMPONENT] != _issue_normal_noop )
00141             {
00142                 nout << "Normal (Per Component): ";
00143                 if ( tnindex )
00144                 {
00145                     nout << "idx: " << *tnindex << " ";
00146                     nout << tnorms[*(tnindex++)];
00147                 }
00148                 else
00149                     nout << *(tnorms++);
00150                 nout << endl;
00151             }
00152 
00153             for ( k = 0; k < 2; k++ )
00154             {
00155                 // Draw per vertex
00156             if ( _color_command[G_PER_VERTEX] != _issue_color_noop )
00157             {
00158                 nout << "Color (Per Vertex): ";
00159                 if ( tcindex )
00160                 {
00161                     nout << "idx: " << *tcindex << " ";
00162                     nout << tcolors[*(tcindex++)];
00163                 }
00164                 else
00165                     nout << *(tcolors++);
00166                 nout << endl;
00167             }
00168             if ( _normal_command[G_PER_VERTEX] != _issue_normal_noop )
00169             {
00170                 nout << "Normal (Per Vertex): ";
00171                 if ( tnindex )
00172                 {
00173                     nout << "idx: " << *tnindex << " ";
00174                     nout << tnorms[*(tnindex++)];
00175                 }
00176                 else
00177                     nout << *(tnorms++);
00178                 nout << endl;
00179             }
00180             if ( _texcoord_command[G_PER_VERTEX] != _issue_texcoord_noop )
00181             {
00182                 nout << "TexCoord (Per Vertex): ";
00183                 if ( ttindex )
00184                 {
00185                     nout << "idx: " << *ttindex << " ";
00186                     nout << ttexcoords[*(ttindex++)];
00187                 }
00188                 else
00189                     nout << *(ttexcoords++);
00190                 nout << endl;
00191             }
00192             if ( _vertex_command[G_PER_VERTEX] != _issue_vertex_noop )
00193             {
00194                 nout << "Vertex (Per Vertex): ";
00195                 if ( tvindex )
00196                 {
00197                     nout << "idx: " << *tvindex << " ";
00198                     nout << tcoords[*(tvindex++)];
00199                 }
00200                 else
00201                     nout << *(tcoords++);
00202                 nout << endl;
00203             }
00204             }
00205         }
00206         if ( !j )
00207         {
00208             nout << "EndGfx()" << endl;
00209             continue;
00210         }
00211         else
00212         {
00213             // Draw per vertex
00214             if ( _color_command[G_PER_VERTEX] != _issue_color_noop )
00215             {
00216                 nout << "Color (Per Vertex): ";
00217                 if ( tcindex )
00218                 {
00219                     nout << "idx: " << *tcindex << " ";
00220                     nout << tcolors[*(tcindex++)];
00221                 }
00222                 else
00223                     nout << *(tcolors++);
00224                 nout << endl;
00225             }
00226             if ( _normal_command[G_PER_VERTEX] != _issue_normal_noop )
00227             {
00228                 nout << "Normal (Per Vertex): ";
00229                 if ( tnindex )
00230                 {
00231                     nout << "idx: " << *tnindex << " ";
00232                     nout << tnorms[*(tnindex++)];
00233                 }
00234                 else
00235                     nout << *(tnorms++);
00236                 nout << endl;
00237             }
00238             if ( _texcoord_command[G_PER_VERTEX] != _issue_texcoord_noop )
00239             {
00240                 nout << "TexCoord (Per Vertex): ";
00241                 if ( ttindex )
00242                 {
00243                     nout << "idx: " << *ttindex << " ";
00244                     nout << ttexcoords[*(ttindex++)];
00245                 }
00246                 else
00247                     nout << *(ttexcoords++);
00248                 nout << endl;
00249             }
00250             if ( _vertex_command[G_PER_VERTEX] != _issue_vertex_noop )
00251             {
00252                 nout << "Vertex (Per Vertex): ";
00253                 if ( tvindex )
00254                 {
00255                     nout << "idx: " << *tvindex << " ";
00256                     nout << tcoords[*(tvindex++)];
00257                 }
00258                 else
00259                     nout << *(tcoords++);
00260                 nout << endl;
00261             }
00262 
00263             nout << "EndGfx()" << endl;
00264             continue;
00265         }
00266     }
00267     */
00268 }
00269 
00270 ////////////////////////////////////////////////////////////////////
00271 //     Function: GeomTristrip::draw_immediate
00272 //       Access:
00273 //  Description:
00274 ////////////////////////////////////////////////////////////////////
00275 void GeomTristrip::draw_immediate(GraphicsStateGuardianBase *gsg, GeomContext *gc) {
00276   gsg->draw_tristrip(this, gc);
00277 }
00278 
00279 ////////////////////////////////////////////////////////////////////
00280 //     Function: GeomTristrip::get_num_tris
00281 //       Access:
00282 //  Description:
00283 ////////////////////////////////////////////////////////////////////
00284 int
00285 GeomTristrip::get_num_tris() const {
00286   int numtris = 0;
00287   for (int i = 0; i < _numprims; i++) {
00288     numtris += _primlengths[i] - 2;
00289   }
00290   return numtris;
00291 }
00292 
00293 ////////////////////////////////////////////////////////////////////
00294 //     Function: GeomTristrip::explode
00295 //       Access: Public, Virtual
00296 //  Description: Allocate and return a new Geom which represents the
00297 //               individual triangles that make up the tristrip.
00298 ////////////////////////////////////////////////////////////////////
00299 Geom *GeomTristrip::
00300 explode() const {
00301   PTA_Vertexf coords=PTA_Vertexf::empty_array(0);
00302   PTA_Normalf normals=PTA_Normalf::empty_array(0);
00303   PTA_TexCoordf texcoords=PTA_TexCoordf::empty_array(0);
00304   PTA_Colorf colors=PTA_Colorf::empty_array(0);
00305 
00306   VertexIterator vi = make_vertex_iterator();
00307   NormalIterator ni = make_normal_iterator();
00308   TexCoordIterator ti = make_texcoord_iterator();
00309   ColorIterator ci = make_color_iterator();
00310 
00311   // Get overall values
00312   if (get_binding(G_COLOR) == G_OVERALL) {
00313     colors.push_back(get_next_color(ci));
00314   }
00315   if (get_binding(G_NORMAL) == G_OVERALL) {
00316     normals.push_back(get_next_normal(ni));
00317   }
00318 
00319   int num_tris = 0;
00320   int num_prims = get_num_prims();
00321 
00322   for (int i = 0; i < num_prims; i++) {
00323     // Get per-primitive values
00324     Colorf per_tristrip_color;
00325     Normalf per_tristrip_normal;
00326     if (get_binding(G_COLOR) == G_PER_PRIM) {
00327       per_tristrip_color = get_next_color(ci);
00328     }
00329     if (get_binding(G_NORMAL) == G_PER_PRIM) {
00330       per_tristrip_normal = get_next_normal(ni);
00331     }
00332 
00333     int num_verts = get_length(i);
00334     assert(num_verts >= 3);
00335 
00336     // A few temporary arrays to hold the three most recent per-vertex
00337     // values.
00338     Vertexf f3vertex[3];
00339     Normalf f3normal[3];
00340     Colorf f3color[3];
00341     TexCoordf f3texcoord[3];
00342 
00343     // Get the first two vertices.  We get these into positions [0]
00344     // and [2], to prepare for the back-and-forth switchback logic in
00345     // the following loop.
00346 
00347     int v;
00348     for (v = 0; v <= 2; v += 2) {
00349       if (get_binding(G_COORD) == G_PER_VERTEX) {
00350         f3vertex[v] = get_next_vertex(vi);
00351       }
00352       if (get_binding(G_NORMAL) == G_PER_VERTEX) {
00353         f3normal[v] = get_next_normal(ni);
00354       }
00355       if (get_binding(G_TEXCOORD) == G_PER_VERTEX) {
00356         f3texcoord[v] = get_next_texcoord(ti);
00357       }
00358       if (get_binding(G_COLOR) == G_PER_VERTEX) {
00359         f3color[v] = get_next_color(ci);
00360       }
00361     }
00362 
00363     // Now fill each triangle.  Each vertex from this point on defines
00364     // a new triangle.
00365     for (v = 2; v < num_verts; v++) {
00366       num_tris++;
00367 
00368       if (get_binding(G_COLOR) == G_PER_PRIM) {
00369         colors.push_back(per_tristrip_color);
00370       } else if (get_binding(G_COLOR) == G_PER_COMPONENT) {
00371         colors.push_back(get_next_color(ci));
00372       }
00373 
00374       if (get_binding(G_NORMAL) == G_PER_PRIM) {
00375         normals.push_back(per_tristrip_normal);
00376       } else if (get_binding(G_NORMAL) == G_PER_COMPONENT) {
00377         normals.push_back(get_next_normal(ni));
00378       }
00379 
00380       if ((v & 1) == 0) {
00381         // Even.  The triangle is counter-clockwise.
00382         f3vertex[1] = f3vertex[2];
00383         f3normal[1] = f3normal[2];
00384         f3texcoord[1] = f3texcoord[2];
00385         f3color[1] = f3color[2];
00386       } else {
00387         // Odd.  The triangle is clockwise.
00388         f3vertex[0] = f3vertex[2];
00389         f3normal[0] = f3normal[2];
00390         f3texcoord[0] = f3texcoord[2];
00391         f3color[0] = f3color[2];
00392       }
00393 
00394       // Per-vertex attributes.
00395       if (get_binding(G_COORD) == G_PER_VERTEX) {
00396         f3vertex[2] = get_next_vertex(vi);
00397         coords.push_back(f3vertex[0]);
00398         coords.push_back(f3vertex[1]);
00399         coords.push_back(f3vertex[2]);
00400       }
00401       if (get_binding(G_NORMAL) == G_PER_VERTEX) {
00402         f3normal[2] = get_next_normal(ni);
00403         normals.push_back(f3normal[0]);
00404         normals.push_back(f3normal[1]);
00405         normals.push_back(f3normal[2]);
00406       }
00407       if (get_binding(G_TEXCOORD) == G_PER_VERTEX) {
00408         f3texcoord[2] = get_next_texcoord(ti);
00409         texcoords.push_back(f3texcoord[0]);
00410         texcoords.push_back(f3texcoord[1]);
00411         texcoords.push_back(f3texcoord[2]);
00412       }
00413       if (get_binding(G_COLOR) == G_PER_VERTEX) {
00414         f3color[2] = get_next_color(ci);
00415         colors.push_back(f3color[0]);
00416         colors.push_back(f3color[1]);
00417         colors.push_back(f3color[2]);
00418       }
00419     }
00420   }
00421 
00422   Geom *tris = new GeomTri;
00423   tris->set_coords(coords);
00424   tris->set_normals(normals,
00425                     get_binding(G_NORMAL) == G_PER_COMPONENT ?
00426                     G_PER_PRIM : get_binding(G_NORMAL));
00427   tris->set_texcoords(texcoords, get_binding(G_TEXCOORD));
00428   tris->set_colors(colors,
00429                    get_binding(G_COLOR) == G_PER_COMPONENT ?
00430                    G_PER_PRIM : get_binding(G_COLOR));
00431   tris->set_num_prims(num_tris);
00432 
00433   return tris;
00434 }
00435 
00436 ////////////////////////////////////////////////////////////////////
00437 //     Function: GeomTristrip::get_tris
00438 //       Access: Public, Virtual
00439 //  Description: This is similar in principle to explode(), except it
00440 //               returns only a list of triangle vertex indices, with
00441 //               no information about color or whatever.  The array
00442 //               returned is a set of indices into the geom's _coords
00443 //               array, as retrieve by get_coords(); there will be 3*n
00444 //               elements in the array, where n is the number of
00445 //               triangles described by the geometry.  This is useful
00446 //               when it's important to determine the physical
00447 //               structure of the geometry, without necessarily
00448 //               worrying about its rendering properties, and when
00449 //               performance considerations are not overwhelming.
00450 ////////////////////////////////////////////////////////////////////
00451 PTA_ushort GeomTristrip::
00452 get_tris() const {
00453   int num_tris = get_num_tris();
00454   PTA_ushort tris;
00455   tris.reserve(num_tris * 3);
00456 
00457   int k = 0;
00458 
00459   for (int i = 0; i < _numprims; i++) {
00460     ushort v0, v1, v2;
00461     if (_vindex.empty()) {
00462       v0 = k++;
00463       v1 = k++;
00464     } else {
00465       v0 = _vindex[k++];
00466       v1 = _vindex[k++];
00467     }
00468 
00469     bool even = true;
00470     int len = _primlengths[i];
00471 
00472     for (int j = 2; j < len; j++) {
00473       if (_vindex.empty()) {
00474         v2 = k++;
00475       } else {
00476         v2 = _vindex[k++];
00477       }
00478 
00479       even = !even;
00480 
00481       if (even) {
00482         ushort vtmp = v1;
00483         v1 = v2;
00484         v2 = vtmp;
00485       }
00486 
00487       tris.push_back(v0);
00488       tris.push_back(v1);
00489       tris.push_back(v2);
00490 
00491       if (even) {
00492         v0 = v2;
00493       } else {
00494         v0 = v1;
00495         v1 = v2;
00496       }
00497     }
00498   }
00499 
00500   nassertr((int)tris.size() == num_tris * 3, PTA_ushort());
00501   return tris;
00502 }
00503 
00504 ////////////////////////////////////////////////////////////////////
00505 //     Function: GeomTristrip::make_GeomTristrip
00506 //       Access: Protected
00507 //  Description: Factory method to generate a GeomTristrip object
00508 ////////////////////////////////////////////////////////////////////
00509 TypedWritable* GeomTristrip::
00510 make_GeomTristrip(const FactoryParams &params) {
00511   GeomTristrip *me = new GeomTristrip;
00512   DatagramIterator scan;
00513   BamReader *manager;
00514 
00515   parse_params(params, scan, manager);
00516   me->fillin(scan, manager);
00517   me->make_dirty();
00518   me->config();
00519   return me;
00520 }
00521 
00522 ////////////////////////////////////////////////////////////////////
00523 //     Function: GeomTristrip::register_with_factory
00524 //       Access: Public, Static
00525 //  Description: Factory method to generate a GeomTristrip object
00526 ////////////////////////////////////////////////////////////////////
00527 void GeomTristrip::
00528 register_with_read_factory(void) {
00529   BamReader::get_factory()->register_factory(get_class_type(), make_GeomTristrip);
00530 }

Generated on Fri May 2 00:39:30 2003 for Panda by doxygen1.3