2006-07-18 23:21:48 +08:00
/* -*-c++-*- OpenSceneGraph - Copyright (C) 1998-2006 Robert Osfield
2003-01-22 00:45:36 +08:00
*
* This library is open source and may be redistributed and / or modified under
* the terms of the OpenSceneGraph Public License ( OSGPL ) version 0.0 or
* ( at your option ) any later version . The full license is in LICENSE file
* included with this distribution , and on the openscenegraph . org website .
*
* This library is distributed in the hope that it will be useful ,
* but WITHOUT ANY WARRANTY ; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the
* OpenSceneGraph Public License for more details .
*/
2007-07-28 18:44:03 +08:00
# include <stdlib.h>
2002-06-21 03:54:08 +08:00
# include <osg/Geometry>
2002-07-18 08:53:03 +08:00
# include <osg/Notify>
2002-06-21 03:54:08 +08:00
using namespace osg ;
2003-09-10 06:18:35 +08:00
const Geometry : : ArrayData Geometry : : s_InvalidArrayData ;
2003-08-09 08:46:48 +08:00
class DrawVertex
{
public :
DrawVertex ( const Array * vertices , const IndexArray * indices ) :
_vertices ( vertices ) ,
_indices ( indices )
{
2003-08-12 18:15:59 +08:00
_verticesType = _vertices ? _vertices - > getType ( ) : Array : : ArrayType ;
_indicesType = _indices ? _indices - > getType ( ) : Array : : ArrayType ;
2003-08-09 08:46:48 +08:00
}
2003-08-12 18:15:59 +08:00
inline unsigned int index ( unsigned int pos )
{
2007-12-11 23:55:02 +08:00
if ( _indices )
2003-08-12 18:15:59 +08:00
{
2007-12-11 23:55:02 +08:00
return _indices - > index ( pos ) ;
}
else
{
return 0 ;
2003-08-12 18:15:59 +08:00
}
}
2003-08-09 08:46:48 +08:00
inline void operator ( ) ( unsigned int pos )
{
2003-08-12 18:15:59 +08:00
if ( _indices ) pos = index ( pos ) ;
2003-08-09 08:46:48 +08:00
switch ( _verticesType )
{
case ( Array : : Vec3ArrayType ) :
2007-12-11 23:55:02 +08:00
apply ( static_cast < const Vec3 * > ( _vertices - > getDataPointer ( ) ) [ pos ] ) ;
2003-08-09 08:46:48 +08:00
break ;
case ( Array : : Vec2ArrayType ) :
2007-12-11 23:55:02 +08:00
apply ( static_cast < const Vec2 * > ( _vertices - > getDataPointer ( ) ) [ pos ] ) ;
2003-08-09 08:46:48 +08:00
break ;
case ( Array : : Vec4ArrayType ) :
2007-12-11 23:55:02 +08:00
apply ( static_cast < const Vec4 * > ( _vertices - > getDataPointer ( ) ) [ pos ] ) ;
2003-08-09 08:46:48 +08:00
break ;
2007-12-04 22:46:46 +08:00
case ( Array : : Vec3dArrayType ) :
2007-12-11 23:55:02 +08:00
apply ( static_cast < const Vec3d * > ( _vertices - > getDataPointer ( ) ) [ pos ] ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec2dArrayType ) :
2007-12-11 23:55:02 +08:00
apply ( static_cast < const Vec2d * > ( _vertices - > getDataPointer ( ) ) [ pos ] ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec4dArrayType ) :
2007-12-11 23:55:02 +08:00
apply ( static_cast < const Vec4d * > ( _vertices - > getDataPointer ( ) ) [ pos ] ) ;
2007-12-04 22:46:46 +08:00
break ;
2003-08-12 18:15:59 +08:00
default :
break ;
2003-08-09 08:46:48 +08:00
}
}
inline void apply ( const Vec2 & v ) { glVertex2fv ( v . ptr ( ) ) ; }
inline void apply ( const Vec3 & v ) { glVertex3fv ( v . ptr ( ) ) ; }
inline void apply ( const Vec4 & v ) { glVertex4fv ( v . ptr ( ) ) ; }
2007-12-04 22:46:46 +08:00
inline void apply ( const Vec2d & v ) { glVertex2dv ( v . ptr ( ) ) ; }
inline void apply ( const Vec3d & v ) { glVertex3dv ( v . ptr ( ) ) ; }
inline void apply ( const Vec4d & v ) { glVertex4dv ( v . ptr ( ) ) ; }
2003-08-09 08:46:48 +08:00
const Array * _vertices ;
const IndexArray * _indices ;
Array : : Type _verticesType ;
2003-08-12 18:15:59 +08:00
Array : : Type _indicesType ;
2003-08-09 08:46:48 +08:00
} ;
2002-10-02 21:12:16 +08:00
class DrawNormal
{
public :
2005-07-05 23:57:53 +08:00
DrawNormal ( const Array * normals , const IndexArray * indices ) :
2002-10-02 21:12:16 +08:00
_normals ( normals ) ,
2005-07-05 23:57:53 +08:00
_indices ( indices )
{
_normalsType = normals ? normals - > getType ( ) : Array : : ArrayType ;
}
2002-10-02 21:12:16 +08:00
void operator ( ) ( unsigned int pos )
{
2005-07-05 23:57:53 +08:00
switch ( _normalsType )
{
case ( Array : : Vec3ArrayType ) :
{
2007-12-11 23:55:02 +08:00
const Vec3 * normals ( static_cast < const Vec3 * > ( _normals - > getDataPointer ( ) ) ) ;
2005-07-05 23:57:53 +08:00
if ( _indices ) glNormal3fv ( normals [ _indices - > index ( pos ) ] . ptr ( ) ) ;
else glNormal3fv ( normals [ pos ] . ptr ( ) ) ;
}
break ;
2005-07-15 22:41:19 +08:00
case ( Array : : Vec3sArrayType ) :
2005-07-05 23:57:53 +08:00
{
2007-12-11 23:55:02 +08:00
const Vec3s * normals ( static_cast < const Vec3s * > ( _normals - > getDataPointer ( ) ) ) ;
2005-07-05 23:57:53 +08:00
if ( _indices ) glNormal3sv ( normals [ _indices - > index ( pos ) ] . ptr ( ) ) ;
else glNormal3sv ( normals [ pos ] . ptr ( ) ) ;
}
break ;
2005-07-15 22:41:19 +08:00
case ( Array : : Vec4sArrayType ) :
2005-07-05 23:57:53 +08:00
{
2007-12-11 23:55:02 +08:00
const Vec4s * normals ( static_cast < const Vec4s * > ( _normals - > getDataPointer ( ) ) ) ;
2005-07-05 23:57:53 +08:00
if ( _indices ) glNormal3sv ( normals [ _indices - > index ( pos ) ] . ptr ( ) ) ;
else glNormal3sv ( normals [ pos ] . ptr ( ) ) ;
}
break ;
2005-07-15 22:41:19 +08:00
case ( Array : : Vec3bArrayType ) :
2005-07-05 23:57:53 +08:00
{
2007-12-11 23:55:02 +08:00
const Vec3b * normals ( static_cast < const Vec3b * > ( _normals - > getDataPointer ( ) ) ) ;
2005-07-05 23:57:53 +08:00
if ( _indices ) glNormal3bv ( ( const GLbyte * ) normals [ _indices - > index ( pos ) ] . ptr ( ) ) ;
else glNormal3bv ( ( const GLbyte * ) normals [ pos ] . ptr ( ) ) ;
}
break ;
2005-07-15 22:41:19 +08:00
case ( Array : : Vec4bArrayType ) :
2005-07-05 23:57:53 +08:00
{
2007-12-11 23:55:02 +08:00
const Vec4b * normals ( static_cast < const Vec4b * > ( _normals - > getDataPointer ( ) ) ) ;
2005-07-05 23:57:53 +08:00
if ( _indices ) glNormal3bv ( ( const GLbyte * ) normals [ _indices - > index ( pos ) ] . ptr ( ) ) ;
else glNormal3bv ( ( const GLbyte * ) normals [ pos ] . ptr ( ) ) ;
}
break ;
2007-12-11 23:55:02 +08:00
case ( Array : : Vec3dArrayType ) :
{
const Vec3d * normals ( static_cast < const Vec3d * > ( _normals - > getDataPointer ( ) ) ) ;
if ( _indices ) glNormal3dv ( normals [ _indices - > index ( pos ) ] . ptr ( ) ) ;
else glNormal3dv ( normals [ pos ] . ptr ( ) ) ;
}
break ;
case ( Array : : Vec4dArrayType ) :
{
const Vec4d * normals ( static_cast < const Vec4d * > ( _normals - > getDataPointer ( ) ) ) ;
if ( _indices ) glNormal3dv ( normals [ _indices - > index ( pos ) ] . ptr ( ) ) ;
else glNormal3dv ( normals [ pos ] . ptr ( ) ) ;
}
break ;
2005-07-05 23:57:53 +08:00
default :
break ;
}
2002-10-02 21:12:16 +08:00
}
2005-07-05 23:57:53 +08:00
const Array * _normals ;
2002-10-02 21:12:16 +08:00
const IndexArray * _indices ;
2005-07-05 23:57:53 +08:00
Array : : Type _normalsType ;
2002-10-02 21:12:16 +08:00
} ;
2003-08-09 08:46:48 +08:00
class DrawColor
{
public :
DrawColor ( const Array * colors , const IndexArray * indices ) :
_colors ( colors ) ,
_indices ( indices )
{
2003-08-12 18:15:59 +08:00
_colorsType = _colors ? _colors - > getType ( ) : Array : : ArrayType ;
_indicesType = _indices ? _indices - > getType ( ) : Array : : ArrayType ;
2003-08-09 08:46:48 +08:00
}
inline unsigned int index ( unsigned int pos )
{
2007-12-11 23:55:02 +08:00
if ( _indices ) {
return _indices - > index ( pos ) ;
}
else {
return 0 ;
2003-08-09 08:46:48 +08:00
}
}
inline void operator ( ) ( unsigned int pos )
{
if ( _indices ) pos = index ( pos ) ;
switch ( _colorsType )
{
case ( Array : : Vec4ArrayType ) :
2007-12-11 23:55:02 +08:00
apply ( static_cast < const Vec4 * > ( _colors - > getDataPointer ( ) ) [ pos ] ) ;
2003-08-09 08:46:48 +08:00
break ;
2005-07-15 22:41:19 +08:00
case ( Array : : Vec4ubArrayType ) :
2007-12-11 23:55:02 +08:00
apply ( static_cast < const Vec4ub * > ( _colors - > getDataPointer ( ) ) [ pos ] ) ;
2003-08-09 08:46:48 +08:00
break ;
case ( Array : : Vec3ArrayType ) :
2007-12-11 23:55:02 +08:00
apply ( static_cast < const Vec3 * > ( _colors - > getDataPointer ( ) ) [ pos ] ) ;
break ;
case ( Array : : Vec3dArrayType ) :
apply ( static_cast < const Vec3d * > ( _colors - > getDataPointer ( ) ) [ pos ] ) ;
break ;
case ( Array : : Vec4dArrayType ) :
apply ( static_cast < const Vec4d * > ( _colors - > getDataPointer ( ) ) [ pos ] ) ;
2003-08-09 08:46:48 +08:00
break ;
2003-08-12 18:15:59 +08:00
default :
break ;
2003-08-09 08:46:48 +08:00
}
}
2005-07-15 22:41:19 +08:00
inline void apply ( const Vec4ub & v ) { glColor4ubv ( v . ptr ( ) ) ; }
2003-08-09 08:46:48 +08:00
inline void apply ( const Vec3 & v ) { glColor3fv ( v . ptr ( ) ) ; }
inline void apply ( const Vec4 & v ) { glColor4fv ( v . ptr ( ) ) ; }
const Array * _colors ;
const IndexArray * _indices ;
Array : : Type _colorsType ;
Array : : Type _indicesType ;
} ;
2002-10-02 21:12:16 +08:00
2003-05-07 21:13:13 +08:00
class DrawVertexAttrib : public osg : : Referenced , public osg : : ConstValueVisitor
{
public :
2003-10-22 21:39:16 +08:00
DrawVertexAttrib ( const Drawable : : Extensions * extensions , unsigned int vertAttribIndex , GLboolean normalized , const Array * attribcoords , const IndexArray * indices ) :
_vertAttribIndex ( vertAttribIndex ) ,
2003-05-07 21:13:13 +08:00
_normalized ( normalized ) ,
_extensions ( extensions ) ,
_attribcoords ( attribcoords ) ,
2003-10-22 21:39:16 +08:00
_indices ( indices ) ,
_index ( 0 ) { ; }
inline void applyAndIncrement ( ) { operator ( ) ( _index + + ) ; }
2003-05-09 21:07:06 +08:00
2003-08-09 08:46:48 +08:00
inline void operator ( ) ( unsigned int pos )
2003-05-09 21:07:06 +08:00
{
if ( _indices ) _attribcoords - > accept ( _indices - > index ( pos ) , * this ) ;
else _attribcoords - > accept ( pos , * this ) ;
}
virtual void apply ( const GLshort & s )
{
2003-10-22 21:39:16 +08:00
_extensions - > glVertexAttrib1s ( _vertAttribIndex , s ) ;
2003-05-09 21:07:06 +08:00
}
virtual void apply ( const GLfloat & f )
{
2003-10-22 21:39:16 +08:00
_extensions - > glVertexAttrib1f ( _vertAttribIndex , f ) ;
2003-05-09 21:07:06 +08:00
}
2005-07-15 22:41:19 +08:00
virtual void apply ( const Vec4ub & v )
2003-05-09 21:07:06 +08:00
{
if ( _normalized )
{
2003-10-22 21:39:16 +08:00
_extensions - > glVertexAttrib4Nubv ( _vertAttribIndex , v . ptr ( ) ) ;
2003-05-09 21:07:06 +08:00
}
else
{
2003-10-22 21:39:16 +08:00
_extensions - > glVertexAttrib4ubv ( _vertAttribIndex , v . ptr ( ) ) ;
2003-05-09 21:07:06 +08:00
}
}
virtual void apply ( const Vec2 & v )
{
2003-10-22 21:39:16 +08:00
_extensions - > glVertexAttrib2fv ( _vertAttribIndex , v . ptr ( ) ) ;
2003-05-09 21:07:06 +08:00
}
virtual void apply ( const Vec3 & v )
{
2003-10-22 21:39:16 +08:00
_extensions - > glVertexAttrib3fv ( _vertAttribIndex , v . ptr ( ) ) ;
2003-05-09 21:07:06 +08:00
}
virtual void apply ( const Vec4 & v )
{
2003-10-22 21:39:16 +08:00
_extensions - > glVertexAttrib4fv ( _vertAttribIndex , v . ptr ( ) ) ;
2003-05-09 21:07:06 +08:00
}
2007-12-04 22:46:46 +08:00
virtual void apply ( const Vec2d & v )
{
_extensions - > glVertexAttrib2dv ( _vertAttribIndex , v . ptr ( ) ) ;
}
virtual void apply ( const Vec3d & v )
{
_extensions - > glVertexAttrib3dv ( _vertAttribIndex , v . ptr ( ) ) ;
}
virtual void apply ( const Vec4d & v )
{
_extensions - > glVertexAttrib4dv ( _vertAttribIndex , v . ptr ( ) ) ;
}
2003-05-07 21:13:13 +08:00
2003-10-22 21:39:16 +08:00
unsigned int _vertAttribIndex ;
2003-05-22 23:29:20 +08:00
GLboolean _normalized ;
2003-06-30 05:41:57 +08:00
const Drawable : : Extensions * _extensions ;
2003-05-22 23:29:20 +08:00
const Array * _attribcoords ;
const IndexArray * _indices ;
2003-10-22 21:39:16 +08:00
unsigned int _index ;
2003-05-07 21:13:13 +08:00
} ;
2002-10-02 21:12:16 +08:00
class DrawTexCoord : public osg : : Referenced , public osg : : ConstValueVisitor
{
public :
DrawTexCoord ( const Array * texcoords , const IndexArray * indices ) :
_texcoords ( texcoords ) ,
_indices ( indices ) { }
2003-08-09 08:46:48 +08:00
inline void operator ( ) ( unsigned int pos )
2002-10-02 21:12:16 +08:00
{
if ( _indices ) _texcoords - > accept ( _indices - > index ( pos ) , * this ) ;
else _texcoords - > accept ( pos , * this ) ;
}
virtual void apply ( const GLfloat & v ) { glTexCoord1f ( v ) ; }
virtual void apply ( const Vec2 & v ) { glTexCoord2fv ( v . ptr ( ) ) ; }
virtual void apply ( const Vec3 & v ) { glTexCoord3fv ( v . ptr ( ) ) ; }
virtual void apply ( const Vec4 & v ) { glTexCoord4fv ( v . ptr ( ) ) ; }
const Array * _texcoords ;
const IndexArray * _indices ;
} ;
class DrawMultiTexCoord : public osg : : Referenced , public osg : : ConstValueVisitor
{
public :
DrawMultiTexCoord ( GLenum target , const Array * texcoords , const IndexArray * indices ,
2003-06-30 05:41:57 +08:00
const Drawable : : Extensions * extensions ) :
2002-10-02 21:12:16 +08:00
_target ( target ) ,
_texcoords ( texcoords ) ,
_indices ( indices ) ,
2003-05-07 21:13:13 +08:00
_extensions ( extensions ) { }
2002-10-02 21:12:16 +08:00
2003-08-09 08:46:48 +08:00
inline void operator ( ) ( unsigned int pos )
2002-10-02 21:12:16 +08:00
{
if ( _indices ) _texcoords - > accept ( _indices - > index ( pos ) , * this ) ;
else _texcoords - > accept ( pos , * this ) ;
}
2003-05-07 21:13:13 +08:00
virtual void apply ( const GLfloat & v ) { _extensions - > glMultiTexCoord1f ( _target , v ) ; }
virtual void apply ( const Vec2 & v ) { _extensions - > glMultiTexCoord2fv ( _target , v . ptr ( ) ) ; }
virtual void apply ( const Vec3 & v ) { _extensions - > glMultiTexCoord3fv ( _target , v . ptr ( ) ) ; }
virtual void apply ( const Vec4 & v ) { _extensions - > glMultiTexCoord4fv ( _target , v . ptr ( ) ) ; }
2002-10-02 21:12:16 +08:00
GLenum _target ;
const Array * _texcoords ;
const IndexArray * _indices ;
2003-05-07 21:13:13 +08:00
2003-06-30 05:41:57 +08:00
const Drawable : : Extensions * _extensions ;
2002-10-02 21:12:16 +08:00
} ;
class DrawSecondaryColor : public osg : : ConstValueVisitor
{
public :
DrawSecondaryColor ( const Array * colors , const IndexArray * indices ,
2003-06-30 05:41:57 +08:00
const Drawable : : Extensions * extensions ) :
2002-10-02 21:12:16 +08:00
_colors ( colors ) ,
_indices ( indices ) ,
2003-05-07 21:13:13 +08:00
_extensions ( extensions )
{ }
2002-10-02 21:12:16 +08:00
2003-08-09 08:46:48 +08:00
inline void operator ( ) ( unsigned int pos )
2002-10-02 21:12:16 +08:00
{
if ( _indices ) _colors - > accept ( _indices - > index ( pos ) , * this ) ;
else _colors - > accept ( pos , * this ) ;
}
2005-07-15 22:41:19 +08:00
virtual void apply ( const Vec4ub & v ) { _extensions - > glSecondaryColor3ubv ( v . ptr ( ) ) ; }
2003-05-07 21:13:13 +08:00
virtual void apply ( const Vec3 & v ) { _extensions - > glSecondaryColor3fv ( v . ptr ( ) ) ; }
virtual void apply ( const Vec4 & v ) { _extensions - > glSecondaryColor3fv ( v . ptr ( ) ) ; }
2002-10-02 21:12:16 +08:00
const Array * _colors ;
const IndexArray * _indices ;
2003-06-30 05:41:57 +08:00
const Drawable : : Extensions * _extensions ;
2002-10-02 21:12:16 +08:00
} ;
class DrawFogCoord : public osg : : ConstValueVisitor
{
public :
2003-06-30 05:41:57 +08:00
DrawFogCoord ( const Array * fogcoords , const IndexArray * indices , const Drawable : : Extensions * extensions ) :
2002-10-02 21:12:16 +08:00
_fogcoords ( fogcoords ) ,
_indices ( indices ) ,
2003-05-07 21:13:13 +08:00
_extensions ( extensions ) { }
2002-10-02 21:12:16 +08:00
2003-08-09 08:46:48 +08:00
inline void operator ( ) ( unsigned int pos )
2002-10-02 21:12:16 +08:00
{
2003-01-05 04:45:53 +08:00
if ( _indices ) _fogcoords - > accept ( _indices - > index ( pos ) , * this ) ;
else _fogcoords - > accept ( pos , * this ) ;
2002-10-02 21:12:16 +08:00
}
2003-05-07 21:13:13 +08:00
virtual void apply ( const GLfloat & v ) { _extensions - > glFogCoordfv ( & v ) ; }
2003-01-05 04:45:53 +08:00
const Array * _fogcoords ;
2002-10-02 21:12:16 +08:00
const IndexArray * _indices ;
2003-06-30 05:41:57 +08:00
const Drawable : : Extensions * _extensions ;
2002-10-02 21:12:16 +08:00
} ;
2003-12-04 05:45:32 +08:00
Geometry : : ArrayData : : ArrayData ( const ArrayData & data , const CopyOp & copyop ) :
2003-12-18 20:20:38 +08:00
array ( copyop ( data . array . get ( ) ) ) ,
indices ( dynamic_cast < osg : : IndexArray * > ( copyop ( data . indices . get ( ) ) ) ) ,
2003-12-04 05:45:32 +08:00
binding ( data . binding ) ,
2007-05-02 02:03:32 +08:00
normalize ( data . normalize )
2003-12-04 05:45:32 +08:00
{
}
Geometry : : Vec3ArrayData : : Vec3ArrayData ( const Vec3ArrayData & data , const CopyOp & copyop ) :
2003-12-18 20:20:38 +08:00
array ( dynamic_cast < osg : : Vec3Array * > ( copyop ( data . array . get ( ) ) ) ) ,
indices ( dynamic_cast < osg : : IndexArray * > ( copyop ( data . indices . get ( ) ) ) ) ,
2003-12-04 05:45:32 +08:00
binding ( data . binding ) ,
2007-05-02 02:03:32 +08:00
normalize ( data . normalize )
2003-12-04 05:45:32 +08:00
{
}
2002-10-02 21:12:16 +08:00
2002-06-21 03:54:08 +08:00
Geometry : : Geometry ( )
{
2002-10-02 21:12:16 +08:00
_fastPath = false ;
2003-08-09 08:46:48 +08:00
_fastPathHint = true ;
2002-06-21 03:54:08 +08:00
}
Geometry : : Geometry ( const Geometry & geometry , const CopyOp & copyop ) :
Drawable ( geometry , copyop ) ,
2003-12-04 05:45:32 +08:00
_vertexData ( geometry . _vertexData , copyop ) ,
_normalData ( geometry . _normalData , copyop ) ,
_colorData ( geometry . _colorData , copyop ) ,
_secondaryColorData ( geometry . _secondaryColorData , copyop ) ,
_fogCoordData ( geometry . _fogCoordData , copyop ) ,
2003-08-08 08:21:30 +08:00
_fastPath ( geometry . _fastPath ) ,
2003-08-09 08:46:48 +08:00
_fastPathHint ( geometry . _fastPathHint )
2002-06-21 03:54:08 +08:00
{
2002-10-02 21:12:16 +08:00
for ( PrimitiveSetList : : const_iterator pitr = geometry . _primitives . begin ( ) ;
2002-07-26 05:50:08 +08:00
pitr ! = geometry . _primitives . end ( ) ;
+ + pitr )
{
2002-09-20 22:51:59 +08:00
PrimitiveSet * primitive = copyop ( pitr - > get ( ) ) ;
2002-07-26 05:50:08 +08:00
if ( primitive ) _primitives . push_back ( primitive ) ;
}
2007-04-27 22:52:30 +08:00
for ( ArrayDataList : : const_iterator titr = geometry . _texCoordList . begin ( ) ;
2002-07-26 05:50:08 +08:00
titr ! = geometry . _texCoordList . end ( ) ;
+ + titr )
{
2006-11-17 00:25:29 +08:00
_texCoordList . push_back ( ArrayData ( * titr , copyop ) ) ;
2002-07-26 05:50:08 +08:00
}
2003-05-07 21:13:13 +08:00
2007-04-27 22:52:30 +08:00
for ( ArrayDataList : : const_iterator vitr = geometry . _vertexAttribList . begin ( ) ;
2003-05-07 21:13:13 +08:00
vitr ! = geometry . _vertexAttribList . end ( ) ;
+ + vitr )
{
2006-11-17 00:25:29 +08:00
_vertexAttribList . push_back ( ArrayData ( * vitr , copyop ) ) ;
2003-05-07 21:13:13 +08:00
}
2002-06-21 03:54:08 +08:00
}
Geometry : : ~ Geometry ( )
{
2004-09-23 20:27:56 +08:00
// do dirty here to keep the getGLObjectSizeHint() estimate on the ball
dirtyDisplayList ( ) ;
2002-06-21 03:54:08 +08:00
// no need to delete, all automatically handled by ref_ptr :-)
}
2004-03-29 18:24:16 +08:00
bool Geometry : : empty ( ) const
{
if ( ! _primitives . empty ( ) ) return false ;
if ( ! _vertexData . empty ( ) ) return false ;
if ( ! _normalData . empty ( ) ) return false ;
if ( ! _colorData . empty ( ) ) return false ;
if ( ! _secondaryColorData . empty ( ) ) return false ;
if ( ! _fogCoordData . empty ( ) ) return false ;
if ( ! _texCoordList . empty ( ) ) return false ;
if ( ! _vertexAttribList . empty ( ) ) return false ;
return true ;
}
2007-04-27 22:52:30 +08:00
void Geometry : : setVertexArray ( Array * array )
{
_vertexData . array = array ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
dirtyBound ( ) ;
if ( _useVertexBufferObjects & & array ) addVertexBufferObjectIfRequired ( array ) ;
}
void Geometry : : setVertexIndices ( IndexArray * array )
{
_vertexData . indices = array ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
dirtyBound ( ) ;
}
void Geometry : : setVertexData ( const ArrayData & arrayData )
{
_vertexData = arrayData ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
dirtyBound ( ) ;
if ( _useVertexBufferObjects & & arrayData . array . valid ( ) ) addVertexBufferObjectIfRequired ( arrayData . array . get ( ) ) ;
}
void Geometry : : setNormalArray ( Array * array )
{
_normalData . array = array ;
if ( ! _normalData . array . valid ( ) ) _normalData . binding = BIND_OFF ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
if ( _useVertexBufferObjects & & array ) addVertexBufferObjectIfRequired ( array ) ;
}
void Geometry : : setNormalIndices ( IndexArray * array )
{
_normalData . indices = array ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
}
void Geometry : : setNormalData ( const ArrayData & arrayData )
{
_normalData = arrayData ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
if ( _useVertexBufferObjects & & arrayData . array . valid ( ) ) addVertexBufferObjectIfRequired ( arrayData . array . get ( ) ) ;
}
void Geometry : : setColorArray ( Array * array )
{
_colorData . array = array ;
if ( ! _colorData . array . valid ( ) ) _colorData . binding = BIND_OFF ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
if ( _useVertexBufferObjects & & array ) addVertexBufferObjectIfRequired ( array ) ;
}
void Geometry : : setColorIndices ( IndexArray * array )
{
_colorData . indices = array ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
}
void Geometry : : setColorData ( const ArrayData & arrayData )
{
_colorData = arrayData ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
if ( _useVertexBufferObjects & & arrayData . array . valid ( ) ) addVertexBufferObjectIfRequired ( arrayData . array . get ( ) ) ;
}
void Geometry : : setSecondaryColorArray ( Array * array )
{
_secondaryColorData . array = array ;
if ( ! _secondaryColorData . array . valid ( ) ) _secondaryColorData . binding = BIND_OFF ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
if ( _useVertexBufferObjects & & array ) addVertexBufferObjectIfRequired ( array ) ;
}
void Geometry : : setSecondaryColorIndices ( IndexArray * array )
{
_secondaryColorData . indices = array ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
}
void Geometry : : setSecondaryColorData ( const ArrayData & arrayData )
{
_secondaryColorData = arrayData ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
if ( _useVertexBufferObjects & & arrayData . array . valid ( ) ) addVertexBufferObjectIfRequired ( arrayData . array . get ( ) ) ;
}
void Geometry : : setFogCoordArray ( Array * array )
{
_fogCoordData . array = array ;
if ( ! _fogCoordData . array . valid ( ) ) _fogCoordData . binding = BIND_OFF ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
if ( _useVertexBufferObjects & & array ) addVertexBufferObjectIfRequired ( array ) ;
}
void Geometry : : setFogCoordIndices ( IndexArray * array )
{
_fogCoordData . indices = array ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
}
void Geometry : : setFogCoordData ( const ArrayData & arrayData )
{
_fogCoordData = arrayData ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
if ( _useVertexBufferObjects & & arrayData . array . valid ( ) ) addVertexBufferObjectIfRequired ( arrayData . array . get ( ) ) ;
}
2006-05-15 19:48:05 +08:00
void Geometry : : setNormalBinding ( AttributeBinding ab )
{
if ( _normalData . binding = = ab ) return ;
_normalData . binding = ab ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
}
void Geometry : : setColorBinding ( AttributeBinding ab )
{
if ( _colorData . binding = = ab ) return ;
_colorData . binding = ab ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
}
void Geometry : : setSecondaryColorBinding ( AttributeBinding ab )
{
if ( _secondaryColorData . binding = = ab ) return ;
_secondaryColorData . binding = ab ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
}
void Geometry : : setFogCoordBinding ( AttributeBinding ab )
{
if ( _fogCoordData . binding = = ab ) return ;
_fogCoordData . binding = ab ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
}
2003-10-01 17:18:24 +08:00
void Geometry : : setTexCoordData ( unsigned int unit , const ArrayData & arrayData )
{
2005-05-25 23:35:51 +08:00
if ( _texCoordList . size ( ) < = unit )
_texCoordList . resize ( unit + 1 ) ;
_texCoordList [ unit ] = arrayData ;
2007-04-27 22:52:30 +08:00
if ( _useVertexBufferObjects & & arrayData . array . valid ( ) ) addVertexBufferObjectIfRequired ( arrayData . array . get ( ) ) ;
2003-10-01 17:18:24 +08:00
}
2003-09-10 06:18:35 +08:00
Geometry : : ArrayData & Geometry : : getTexCoordData ( unsigned int unit )
2002-06-21 03:54:08 +08:00
{
2002-06-22 00:45:45 +08:00
if ( _texCoordList . size ( ) < = unit )
2002-10-02 21:12:16 +08:00
_texCoordList . resize ( unit + 1 ) ;
2002-06-21 03:54:08 +08:00
2003-09-10 06:18:35 +08:00
return _texCoordList [ unit ] ;
}
2002-06-26 04:27:51 +08:00
2003-09-10 06:18:35 +08:00
const Geometry : : ArrayData & Geometry : : getTexCoordData ( unsigned int unit ) const
{
if ( _texCoordList . size ( ) < = unit )
return s_InvalidArrayData ;
return _texCoordList [ unit ] ;
}
void Geometry : : setTexCoordArray ( unsigned int unit , Array * array )
{
2003-09-24 23:54:22 +08:00
getTexCoordData ( unit ) . binding = BIND_PER_VERTEX ;
2003-09-10 06:18:35 +08:00
getTexCoordData ( unit ) . array = array ;
computeFastPathsUsed ( ) ;
2002-06-26 04:27:51 +08:00
dirtyDisplayList ( ) ;
2007-04-27 22:52:30 +08:00
2007-04-29 16:12:29 +08:00
if ( _useVertexBufferObjects & & array )
{
addVertexBufferObjectIfRequired ( array ) ;
}
2002-06-21 03:54:08 +08:00
}
2002-06-27 21:15:34 +08:00
Array * Geometry : : getTexCoordArray ( unsigned int unit )
2002-06-21 03:54:08 +08:00
{
2003-09-10 06:18:35 +08:00
if ( unit < _texCoordList . size ( ) ) return _texCoordList [ unit ] . array . get ( ) ;
2002-06-21 03:54:08 +08:00
else return 0 ;
}
2002-07-18 08:53:03 +08:00
const Array * Geometry : : getTexCoordArray ( unsigned int unit ) const
{
2003-09-10 06:18:35 +08:00
if ( unit < _texCoordList . size ( ) ) return _texCoordList [ unit ] . array . get ( ) ;
2002-07-18 08:53:03 +08:00
else return 0 ;
}
2002-10-02 21:12:16 +08:00
void Geometry : : setTexCoordIndices ( unsigned int unit , IndexArray * array )
2002-06-21 03:54:08 +08:00
{
2003-09-10 06:18:35 +08:00
getTexCoordData ( unit ) . indices = array ;
2002-10-02 21:12:16 +08:00
2003-09-10 06:18:35 +08:00
computeFastPathsUsed ( ) ;
2002-10-02 21:12:16 +08:00
dirtyDisplayList ( ) ;
}
IndexArray * Geometry : : getTexCoordIndices ( unsigned int unit )
{
2003-09-10 06:18:35 +08:00
if ( unit < _texCoordList . size ( ) ) return _texCoordList [ unit ] . indices . get ( ) ;
2002-10-02 21:12:16 +08:00
else return 0 ;
}
const IndexArray * Geometry : : getTexCoordIndices ( unsigned int unit ) const
{
2003-09-10 06:18:35 +08:00
if ( unit < _texCoordList . size ( ) ) return _texCoordList [ unit ] . indices . get ( ) ;
2002-10-02 21:12:16 +08:00
else return 0 ;
}
2003-05-09 21:07:06 +08:00
2003-09-10 06:18:35 +08:00
void Geometry : : setVertexAttribData ( unsigned int index , const Geometry : : ArrayData & attrData )
2003-05-09 21:07:06 +08:00
{
2003-09-10 06:18:35 +08:00
if ( _vertexAttribList . size ( ) < = index )
_vertexAttribList . resize ( index + 1 ) ;
2003-05-09 21:07:06 +08:00
2003-09-10 06:18:35 +08:00
_vertexAttribList [ index ] = attrData ;
2007-04-27 22:52:30 +08:00
2005-11-22 21:56:50 +08:00
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
2007-04-27 22:52:30 +08:00
if ( _useVertexBufferObjects & & attrData . array . valid ( ) ) addVertexBufferObjectIfRequired ( attrData . array . get ( ) ) ;
2003-05-09 21:07:06 +08:00
}
2003-09-10 06:18:35 +08:00
Geometry : : ArrayData & Geometry : : getVertexAttribData ( unsigned int index )
2003-05-09 21:07:06 +08:00
{
2003-09-10 06:18:35 +08:00
if ( _vertexAttribList . size ( ) < = index )
_vertexAttribList . resize ( index + 1 ) ;
return _vertexAttribList [ index ] ;
2003-05-09 21:07:06 +08:00
}
2003-09-10 06:18:35 +08:00
const Geometry : : ArrayData & Geometry : : getVertexAttribData ( unsigned int index ) const
2003-05-09 21:07:06 +08:00
{
2003-09-10 06:18:35 +08:00
if ( _vertexAttribList . size ( ) < = _vertexAttribList . size ( ) )
return s_InvalidArrayData ;
return _vertexAttribList [ index ] ;
2003-05-09 21:07:06 +08:00
}
2003-09-10 06:18:35 +08:00
void Geometry : : setVertexAttribArray ( unsigned int index , Array * array )
2003-05-09 21:07:06 +08:00
{
2003-09-10 06:18:35 +08:00
getVertexAttribData ( index ) . array = array ;
2003-05-09 21:07:06 +08:00
2003-09-10 06:18:35 +08:00
computeFastPathsUsed ( ) ;
2003-05-09 21:07:06 +08:00
dirtyDisplayList ( ) ;
2007-04-27 22:52:30 +08:00
if ( _useVertexBufferObjects & & array ) addVertexBufferObjectIfRequired ( array ) ;
2003-05-09 21:07:06 +08:00
}
2003-09-10 06:18:35 +08:00
Array * Geometry : : getVertexAttribArray ( unsigned int index )
2003-05-09 21:07:06 +08:00
{
2003-09-10 06:18:35 +08:00
if ( index < _vertexAttribList . size ( ) ) return _vertexAttribList [ index ] . array . get ( ) ;
2003-05-09 21:07:06 +08:00
else return 0 ;
}
2003-09-10 06:18:35 +08:00
const Array * Geometry : : getVertexAttribArray ( unsigned int index ) const
2003-05-09 21:07:06 +08:00
{
2003-09-10 06:18:35 +08:00
if ( index < _vertexAttribList . size ( ) ) return _vertexAttribList [ index ] . array . get ( ) ;
2003-05-09 21:07:06 +08:00
else return 0 ;
}
2003-09-10 06:18:35 +08:00
void Geometry : : setVertexAttribIndices ( unsigned int index , IndexArray * array )
2003-05-07 21:13:13 +08:00
{
2003-09-10 06:18:35 +08:00
getVertexAttribData ( index ) . indices = array ;
2003-05-07 21:13:13 +08:00
2003-06-30 05:41:57 +08:00
computeFastPathsUsed ( ) ;
2003-05-07 21:13:13 +08:00
dirtyDisplayList ( ) ;
}
2003-09-10 06:18:35 +08:00
IndexArray * Geometry : : getVertexAttribIndices ( unsigned int index )
2003-05-07 21:13:13 +08:00
{
2003-09-10 06:18:35 +08:00
if ( index < _vertexAttribList . size ( ) ) return _vertexAttribList [ index ] . indices . get ( ) ;
2003-05-07 21:13:13 +08:00
else return 0 ;
}
2003-09-10 06:18:35 +08:00
const IndexArray * Geometry : : getVertexAttribIndices ( unsigned int index ) const
2003-05-07 21:13:13 +08:00
{
2003-09-10 06:18:35 +08:00
if ( index < _vertexAttribList . size ( ) ) return _vertexAttribList [ index ] . indices . get ( ) ;
2003-05-07 21:13:13 +08:00
else return 0 ;
}
2003-09-10 06:18:35 +08:00
void Geometry : : setVertexAttribBinding ( unsigned int index , AttributeBinding ab )
2003-05-07 21:13:13 +08:00
{
2006-05-15 19:48:05 +08:00
if ( getVertexAttribData ( index ) . binding = = ab )
return ;
2003-09-10 06:18:35 +08:00
getVertexAttribData ( index ) . binding = ab ;
computeFastPathsUsed ( ) ;
dirtyDisplayList ( ) ;
2003-05-07 21:13:13 +08:00
}
2003-09-10 06:18:35 +08:00
Geometry : : AttributeBinding Geometry : : getVertexAttribBinding ( unsigned int index ) const
2003-05-07 21:13:13 +08:00
{
2003-09-10 06:18:35 +08:00
if ( index < _vertexAttribList . size ( ) ) return _vertexAttribList [ index ] . binding ;
else return BIND_OFF ;
2003-05-07 21:13:13 +08:00
}
2003-09-10 06:18:35 +08:00
void Geometry : : setVertexAttribNormalize ( unsigned int index , GLboolean norm )
2003-05-07 21:13:13 +08:00
{
2003-09-10 06:18:35 +08:00
getVertexAttribData ( index ) . normalize = norm ;
2003-05-07 21:13:13 +08:00
dirtyDisplayList ( ) ;
}
2003-09-10 06:18:35 +08:00
GLboolean Geometry : : getVertexAttribNormalize ( unsigned int index ) const
2003-05-07 21:13:13 +08:00
{
2003-09-10 06:18:35 +08:00
if ( index < _vertexAttribList . size ( ) ) return _vertexAttribList [ index ] . normalize ;
else return GL_FALSE ;
2003-05-07 21:13:13 +08:00
}
2002-11-21 17:07:11 +08:00
bool Geometry : : addPrimitiveSet ( PrimitiveSet * primitiveset )
{
if ( primitiveset )
{
2007-05-01 14:28:20 +08:00
if ( _useVertexBufferObjects ) addElementBufferObjectIfRequired ( primitiveset ) ;
2007-04-27 22:52:30 +08:00
2002-11-21 17:07:11 +08:00
_primitives . push_back ( primitiveset ) ;
dirtyDisplayList ( ) ;
dirtyBound ( ) ;
return true ;
}
notify ( WARN ) < < " Warning: invalid index i or primitiveset passed to osg::Geometry::addPrimitiveSet(i,primitiveset), ignoring call. " < < std : : endl ;
return false ;
}
bool Geometry : : setPrimitiveSet ( unsigned int i , PrimitiveSet * primitiveset )
{
if ( i < _primitives . size ( ) & & primitiveset )
{
2007-05-01 14:28:20 +08:00
if ( _useVertexBufferObjects ) addElementBufferObjectIfRequired ( primitiveset ) ;
2007-04-27 22:52:30 +08:00
2002-11-21 17:07:11 +08:00
_primitives [ i ] = primitiveset ;
dirtyDisplayList ( ) ;
dirtyBound ( ) ;
return true ;
}
notify ( WARN ) < < " Warning: invalid index i or primitiveset passed to osg::Geometry::setPrimitiveSet(i,primitiveset), ignoring call. " < < std : : endl ;
return false ;
}
bool Geometry : : insertPrimitiveSet ( unsigned int i , PrimitiveSet * primitiveset )
{
2007-04-27 22:52:30 +08:00
2002-11-21 17:07:11 +08:00
if ( primitiveset )
{
2007-05-01 14:28:20 +08:00
if ( _useVertexBufferObjects ) addElementBufferObjectIfRequired ( primitiveset ) ;
2007-04-27 22:52:30 +08:00
2002-11-21 17:07:11 +08:00
if ( i < _primitives . size ( ) )
{
_primitives . insert ( _primitives . begin ( ) + i , primitiveset ) ;
dirtyDisplayList ( ) ;
dirtyBound ( ) ;
return true ;
}
else if ( i = = _primitives . size ( ) )
{
return addPrimitiveSet ( primitiveset ) ;
}
2007-04-27 22:52:30 +08:00
2002-11-21 17:07:11 +08:00
}
notify ( WARN ) < < " Warning: invalid index i or primitiveset passed to osg::Geometry::insertPrimitiveSet(i,primitiveset), ignoring call. " < < std : : endl ;
return false ;
}
bool Geometry : : removePrimitiveSet ( unsigned int i , unsigned int numElementsToRemove )
{
2008-01-21 20:00:10 +08:00
if ( numElementsToRemove = = 0 ) return false ;
if ( i < _primitives . size ( ) )
2002-11-21 17:07:11 +08:00
{
2003-04-01 23:08:30 +08:00
if ( i + numElementsToRemove < = _primitives . size ( ) )
2002-11-21 17:07:11 +08:00
{
_primitives . erase ( _primitives . begin ( ) + i , _primitives . begin ( ) + i + numElementsToRemove ) ;
}
else
{
// asking to delete too many elements, report a warning, and delete to
// the end of the primitive list.
notify ( WARN ) < < " Warning: osg::Geometry::removePrimitiveSet(i,numElementsToRemove) has been asked to remove more elements than are available, " < < std : : endl ;
2002-11-22 04:28:28 +08:00
notify ( WARN ) < < " removing on from i to the end of the list of primitive sets. " < < std : : endl ;
2002-11-21 17:07:11 +08:00
_primitives . erase ( _primitives . begin ( ) + i , _primitives . end ( ) ) ;
}
dirtyDisplayList ( ) ;
dirtyBound ( ) ;
return true ;
}
notify ( WARN ) < < " Warning: invalid index i passed to osg::Geometry::removePrimitiveSet(i,numElementsToRemove), ignoring call. " < < std : : endl ;
return false ;
}
unsigned int Geometry : : getPrimitiveSetIndex ( const PrimitiveSet * primitiveset ) const
{
for ( unsigned int primitiveSetIndex = 0 ; primitiveSetIndex < _primitives . size ( ) ; + + primitiveSetIndex )
{
if ( _primitives [ primitiveSetIndex ] = = primitiveset ) return primitiveSetIndex ;
}
return _primitives . size ( ) ; // node not found.
}
2003-06-30 05:41:57 +08:00
bool Geometry : : computeFastPathsUsed ( )
2002-10-02 21:12:16 +08:00
{
2004-02-24 20:04:48 +08:00
static bool s_DisableFastPathInDisplayLists = getenv ( " OSG_DISABLE_FAST_PATH_IN_DISPLAY_LISTS " ) ! = 0 ;
2004-02-17 17:46:16 +08:00
if ( _useDisplayList & & s_DisableFastPathInDisplayLists )
{
osg : : notify ( osg : : DEBUG_INFO ) < < " Geometry::computeFastPathsUsed() - Disabling fast paths in display lists " < < std : : endl ;
2007-12-09 01:00:38 +08:00
_supportsVertexBufferObjects = _fastPath = false ;
2004-02-17 17:46:16 +08:00
return _fastPath ;
}
2002-10-02 21:12:16 +08:00
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//
// check to see if fast path can be used.
//
_fastPath = true ;
2003-09-10 06:18:35 +08:00
if ( _vertexData . indices . valid ( ) ) _fastPath = false ;
else if ( _normalData . binding = = BIND_PER_PRIMITIVE | | ( _normalData . binding = = BIND_PER_VERTEX & & _normalData . indices . valid ( ) ) ) _fastPath = false ;
else if ( _colorData . binding = = BIND_PER_PRIMITIVE | | ( _colorData . binding = = BIND_PER_VERTEX & & _colorData . indices . valid ( ) ) ) _fastPath = false ;
else if ( _secondaryColorData . binding = = BIND_PER_PRIMITIVE | | ( _secondaryColorData . binding = = BIND_PER_VERTEX & & _secondaryColorData . indices . valid ( ) ) ) _fastPath = false ;
else if ( _fogCoordData . binding = = BIND_PER_PRIMITIVE | | ( _fogCoordData . binding = = BIND_PER_VERTEX & & _fogCoordData . indices . valid ( ) ) ) _fastPath = false ;
2003-05-07 21:13:13 +08:00
else
{
2003-09-10 06:18:35 +08:00
for ( unsigned int va = 0 ; va < _vertexAttribList . size ( ) ; + + va )
2003-05-07 21:13:13 +08:00
{
2003-09-10 06:18:35 +08:00
if ( _vertexAttribList [ va ] . binding = = BIND_PER_PRIMITIVE )
2003-05-07 21:13:13 +08:00
{
_fastPath = false ;
break ;
}
else
{
2003-09-10 06:18:35 +08:00
const Array * array = _vertexAttribList [ va ] . array . get ( ) ;
const IndexArray * idxArray = _vertexAttribList [ va ] . indices . get ( ) ;
2003-05-07 21:13:13 +08:00
2003-09-10 06:18:35 +08:00
if ( _vertexAttribList [ va ] . binding = = BIND_PER_VERTEX & &
2003-05-07 21:13:13 +08:00
array & & array - > getNumElements ( ) > 0 & &
idxArray & & idxArray - > getNumElements ( ) > 0 )
{
_fastPath = false ;
break ;
}
}
}
}
2002-06-21 03:54:08 +08:00
2002-08-16 04:27:33 +08:00
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//
2002-10-02 21:12:16 +08:00
// Set up tex coords if required.
2002-08-16 04:27:33 +08:00
//
2003-12-18 20:20:38 +08:00
for ( unsigned int unit = 0 ; unit < _texCoordList . size ( ) ; + + unit )
2002-08-16 04:27:33 +08:00
{
2003-09-10 06:18:35 +08:00
const ArrayData & texcoordData = _texCoordList [ unit ] ;
if ( texcoordData . array . valid ( ) & & texcoordData . array - > getNumElements ( ) > 0 )
2002-08-16 04:27:33 +08:00
{
2003-09-10 06:18:35 +08:00
if ( texcoordData . indices . valid ( ) )
2002-08-16 04:27:33 +08:00
{
2003-09-10 06:18:35 +08:00
if ( texcoordData . indices - > getNumElements ( ) > 0 )
2002-10-02 21:12:16 +08:00
{
2003-05-07 21:13:13 +08:00
_fastPath = false ;
break ;
2002-10-02 21:12:16 +08:00
}
2002-08-16 04:27:33 +08:00
}
}
}
2003-06-30 05:41:57 +08:00
_supportsVertexBufferObjects = _fastPath ;
//_supportsVertexBufferObjects = false;
//_useVertexBufferObjects = false;
2002-10-02 21:12:16 +08:00
return _fastPath ;
}
2004-09-22 01:26:08 +08:00
unsigned int Geometry : : getGLObjectSizeHint ( ) const
{
2004-09-23 20:27:56 +08:00
unsigned int totalSize = 0 ;
if ( _vertexData . array . valid ( ) ) totalSize + = _vertexData . array - > getTotalDataSize ( ) ;
if ( _normalData . array . valid ( ) ) totalSize + = _normalData . array - > getTotalDataSize ( ) ;
if ( _colorData . array . valid ( ) ) totalSize + = _colorData . array - > getTotalDataSize ( ) ;
if ( _secondaryColorData . array . valid ( ) ) totalSize + = _secondaryColorData . array - > getTotalDataSize ( ) ;
if ( _fogCoordData . array . valid ( ) ) totalSize + = _fogCoordData . array - > getTotalDataSize ( ) ;
unsigned int unit ;
for ( unit = 0 ; unit < _texCoordList . size ( ) ; + + unit )
{
const Array * array = _texCoordList [ unit ] . array . get ( ) ;
if ( array ) totalSize + = array - > getTotalDataSize ( ) ;
}
bool handleVertexAttributes = true ;
if ( handleVertexAttributes )
{
unsigned int index ;
for ( index = 0 ; index < _vertexAttribList . size ( ) ; + + index )
{
const Array * array = _vertexAttribList [ index ] . array . get ( ) ;
if ( array ) totalSize + = array - > getTotalDataSize ( ) ;
}
}
2007-04-29 16:12:29 +08:00
for ( PrimitiveSetList : : const_iterator itr = _primitives . begin ( ) ;
itr ! = _primitives . end ( ) ;
+ + itr )
{
2004-09-23 20:27:56 +08:00
2007-04-29 16:12:29 +08:00
totalSize + = 4 * ( * itr ) - > getNumIndices ( ) ;
2004-09-23 20:27:56 +08:00
2007-04-29 16:12:29 +08:00
}
2004-09-23 20:27:56 +08:00
2004-09-22 01:26:08 +08:00
// do a very simply mapping of display list size proportional to vertex datasize.
2004-09-23 20:27:56 +08:00
return totalSize ;
2004-09-22 01:26:08 +08:00
}
2007-05-02 02:03:32 +08:00
bool Geometry : : getArrayList ( ArrayList & arrayList ) const
2007-04-27 22:52:30 +08:00
{
unsigned int startSize = arrayList . size ( ) ;
if ( _vertexData . array . valid ( ) ) arrayList . push_back ( _vertexData . array . get ( ) ) ;
if ( _normalData . array . valid ( ) ) arrayList . push_back ( _normalData . array . get ( ) ) ;
if ( _colorData . array . valid ( ) ) arrayList . push_back ( _colorData . array . get ( ) ) ;
if ( _secondaryColorData . array . valid ( ) ) arrayList . push_back ( _secondaryColorData . array . get ( ) ) ;
if ( _fogCoordData . array . valid ( ) ) arrayList . push_back ( _fogCoordData . array . get ( ) ) ;
2007-04-29 16:12:29 +08:00
for ( unsigned int unit = 0 ; unit < _texCoordList . size ( ) ; + + unit )
{
Array * array = _texCoordList [ unit ] . array . get ( ) ;
if ( array ) arrayList . push_back ( array ) ;
}
for ( unsigned int index = 0 ; index < _vertexAttribList . size ( ) ; + + index )
{
Array * array = _vertexAttribList [ index ] . array . get ( ) ;
if ( array ) arrayList . push_back ( array ) ;
}
2007-04-27 22:52:30 +08:00
return arrayList . size ( ) ! = startSize ;
}
2007-05-02 02:03:32 +08:00
bool Geometry : : getDrawElementsList ( DrawElementsList & drawElementsList ) const
2007-04-27 22:52:30 +08:00
{
unsigned int startSize = drawElementsList . size ( ) ;
2007-05-02 02:03:32 +08:00
for ( PrimitiveSetList : : const_iterator itr = _primitives . begin ( ) ;
2007-04-27 22:52:30 +08:00
itr ! = _primitives . end ( ) ;
+ + itr )
{
osg : : DrawElements * de = ( * itr ) - > getDrawElements ( ) ;
if ( de ) drawElementsList . push_back ( de ) ;
}
return drawElementsList . size ( ) ! = startSize ;
}
void Geometry : : addVertexBufferObjectIfRequired ( osg : : Array * array )
{
if ( _useVertexBufferObjects )
{
if ( ! array - > getVertexBufferObject ( ) )
{
array - > setVertexBufferObject ( getOrCreateVertexBufferObject ( ) ) ;
}
}
}
2007-05-01 14:28:20 +08:00
void Geometry : : addElementBufferObjectIfRequired ( osg : : PrimitiveSet * primitiveSet )
2007-04-27 22:52:30 +08:00
{
if ( _useVertexBufferObjects )
{
osg : : DrawElements * drawElements = primitiveSet - > getDrawElements ( ) ;
2007-05-01 14:28:20 +08:00
if ( drawElements & & ! drawElements - > getElementBufferObject ( ) )
2007-04-27 22:52:30 +08:00
{
2007-05-01 14:28:20 +08:00
drawElements - > setElementBufferObject ( getOrCreateElementBufferObject ( ) ) ;
2007-04-27 22:52:30 +08:00
}
}
}
osg : : VertexBufferObject * Geometry : : getOrCreateVertexBufferObject ( )
{
ArrayList arrayList ;
getArrayList ( arrayList ) ;
ArrayList : : iterator vitr ;
for ( vitr = arrayList . begin ( ) ;
2009-10-06 17:28:41 +08:00
vitr ! = arrayList . end ( ) ;
2007-04-27 22:52:30 +08:00
+ + vitr )
{
osg : : Array * array = * vitr ;
2009-10-06 17:28:41 +08:00
if ( array - > getVertexBufferObject ( ) ) return array - > getVertexBufferObject ( ) ;
2007-04-27 22:52:30 +08:00
}
2009-10-06 17:28:41 +08:00
return new osg : : VertexBufferObject ;
2007-04-27 22:52:30 +08:00
}
2007-05-01 14:28:20 +08:00
osg : : ElementBufferObject * Geometry : : getOrCreateElementBufferObject ( )
2007-04-27 22:52:30 +08:00
{
DrawElementsList drawElementsList ;
getDrawElementsList ( drawElementsList ) ;
DrawElementsList : : iterator deitr ;
for ( deitr = drawElementsList . begin ( ) ;
deitr ! = drawElementsList . end ( ) ;
+ + deitr )
{
osg : : DrawElements * elements = * deitr ;
2009-10-06 17:28:41 +08:00
if ( elements - > getElementBufferObject ( ) ) return elements - > getElementBufferObject ( ) ;
2007-04-27 22:52:30 +08:00
}
2009-10-06 17:28:41 +08:00
return new osg : : ElementBufferObject ;
2007-04-27 22:52:30 +08:00
}
void Geometry : : setUseVertexBufferObjects ( bool flag )
{
2007-05-02 02:03:32 +08:00
// flag = true;
2007-04-30 04:13:53 +08:00
2007-04-29 16:12:29 +08:00
// osg::notify(osg::NOTICE)<<"Geometry::setUseVertexBufferObjects("<<flag<<")"<<std::endl;
2007-04-27 22:52:30 +08:00
if ( _useVertexBufferObjects = = flag ) return ;
Drawable : : setUseVertexBufferObjects ( flag ) ;
ArrayList arrayList ;
getArrayList ( arrayList ) ;
DrawElementsList drawElementsList ;
getDrawElementsList ( drawElementsList ) ;
typedef std : : vector < osg : : VertexBufferObject * > VertexBufferObjectList ;
2007-05-01 14:28:20 +08:00
typedef std : : vector < osg : : ElementBufferObject * > ElementBufferObjectList ;
2007-04-27 22:52:30 +08:00
if ( _useVertexBufferObjects )
{
if ( ! arrayList . empty ( ) )
{
VertexBufferObjectList vboList ;
osg : : VertexBufferObject * vbo = 0 ;
ArrayList : : iterator vitr ;
for ( vitr = arrayList . begin ( ) ;
vitr ! = arrayList . end ( ) & & ! vbo ;
+ + vitr )
{
osg : : Array * array = * vitr ;
2007-10-19 17:58:11 +08:00
if ( array - > getVertexBufferObject ( ) ) vbo = array - > getVertexBufferObject ( ) ;
2007-04-27 22:52:30 +08:00
}
if ( ! vbo ) vbo = new osg : : VertexBufferObject ;
for ( vitr = arrayList . begin ( ) ;
vitr ! = arrayList . end ( ) ;
+ + vitr )
{
osg : : Array * array = * vitr ;
if ( ! array - > getVertexBufferObject ( ) ) array - > setVertexBufferObject ( vbo ) ;
}
}
if ( ! drawElementsList . empty ( ) )
{
2007-05-01 14:28:20 +08:00
ElementBufferObjectList eboList ;
2007-04-27 22:52:30 +08:00
2007-05-01 14:28:20 +08:00
osg : : ElementBufferObject * ebo = 0 ;
2007-04-27 22:52:30 +08:00
DrawElementsList : : iterator deitr ;
for ( deitr = drawElementsList . begin ( ) ;
deitr ! = drawElementsList . end ( ) ;
+ + deitr )
{
osg : : DrawElements * elements = * deitr ;
2007-10-19 17:58:11 +08:00
if ( elements - > getElementBufferObject ( ) ) ebo = elements - > getElementBufferObject ( ) ;
2007-04-27 22:52:30 +08:00
}
2007-05-01 14:28:20 +08:00
if ( ! ebo ) ebo = new osg : : ElementBufferObject ;
2007-04-27 22:52:30 +08:00
for ( deitr = drawElementsList . begin ( ) ;
deitr ! = drawElementsList . end ( ) ;
+ + deitr )
{
osg : : DrawElements * elements = * deitr ;
2007-05-01 14:28:20 +08:00
if ( ! elements - > getElementBufferObject ( ) ) elements - > setElementBufferObject ( ebo ) ;
2007-04-27 22:52:30 +08:00
}
}
}
else
{
for ( ArrayList : : iterator vitr = arrayList . begin ( ) ;
vitr ! = arrayList . end ( ) ;
+ + vitr )
{
osg : : Array * array = * vitr ;
2007-10-19 17:58:11 +08:00
if ( array - > getVertexBufferObject ( ) ) array - > setVertexBufferObject ( 0 ) ;
2007-04-27 22:52:30 +08:00
}
for ( DrawElementsList : : iterator deitr = drawElementsList . begin ( ) ;
deitr ! = drawElementsList . end ( ) ;
+ + deitr )
{
osg : : DrawElements * elements = * deitr ;
2007-10-19 17:58:11 +08:00
if ( elements - > getElementBufferObject ( ) ) elements - > setElementBufferObject ( 0 ) ;
2007-04-27 22:52:30 +08:00
}
}
}
void Geometry : : dirtyDisplayList ( )
{
Drawable : : dirtyDisplayList ( ) ;
}
2007-05-02 02:03:32 +08:00
void Geometry : : resizeGLObjectBuffers ( unsigned int maxSize )
{
Drawable : : resizeGLObjectBuffers ( maxSize ) ;
ArrayList arrays ;
if ( getArrayList ( arrays ) )
{
for ( ArrayList : : iterator itr = arrays . begin ( ) ;
itr ! = arrays . end ( ) ;
+ + itr )
{
( * itr ) - > resizeGLObjectBuffers ( maxSize ) ;
}
}
DrawElementsList drawElements ;
if ( getDrawElementsList ( drawElements ) )
{
for ( DrawElementsList : : iterator itr = drawElements . begin ( ) ;
itr ! = drawElements . end ( ) ;
+ + itr )
{
( * itr ) - > resizeGLObjectBuffers ( maxSize ) ;
}
}
}
2007-04-29 16:12:29 +08:00
2007-05-02 02:03:32 +08:00
void Geometry : : releaseGLObjects ( State * state ) const
{
Drawable : : releaseGLObjects ( state ) ;
ArrayList arrays ;
if ( getArrayList ( arrays ) )
{
for ( ArrayList : : iterator itr = arrays . begin ( ) ;
itr ! = arrays . end ( ) ;
+ + itr )
{
( * itr ) - > releaseGLObjects ( state ) ;
}
}
2007-04-29 16:12:29 +08:00
2007-05-02 02:03:32 +08:00
DrawElementsList drawElements ;
if ( getDrawElementsList ( drawElements ) )
{
for ( DrawElementsList : : iterator itr = drawElements . begin ( ) ;
itr ! = drawElements . end ( ) ;
+ + itr )
{
( * itr ) - > releaseGLObjects ( state ) ;
}
}
}
2007-04-29 16:12:29 +08:00
2007-03-28 19:30:38 +08:00
void Geometry : : drawImplementation ( RenderInfo & renderInfo ) const
2002-10-02 21:12:16 +08:00
{
2007-03-28 19:30:38 +08:00
State & state = * renderInfo . getState ( ) ;
2007-09-07 23:03:56 +08:00
// unsigned int contextID = state.getContextID();
2007-04-29 16:12:29 +08:00
2005-08-31 06:28:30 +08:00
// osg::notify(osg::NOTICE)<<"Geometry::drawImplementation"<<std::endl;
2003-08-08 08:21:30 +08:00
if ( _internalOptimizedGeometry . valid ( ) )
{
2007-03-28 19:30:38 +08:00
_internalOptimizedGeometry - > drawImplementation ( renderInfo ) ;
2003-08-08 08:21:30 +08:00
return ;
}
2003-05-07 21:13:13 +08:00
const Extensions * extensions = getExtensions ( state . getContextID ( ) , true ) ;
2003-09-10 06:18:35 +08:00
if ( ! ( ( _vertexData . array . valid ( ) & & _vertexData . array - > getNumElements ( ) ! = 0 ) | |
2003-05-07 21:13:13 +08:00
( _vertexAttribList . size ( ) > 0 & &
2003-09-10 06:18:35 +08:00
_vertexAttribList [ 0 ] . array . valid ( ) & &
_vertexAttribList [ 0 ] . array - > getNumElements ( ) ! = 0 ) ) )
2003-05-07 21:13:13 +08:00
{
return ;
}
2002-08-18 19:16:31 +08:00
2003-09-10 06:18:35 +08:00
if ( ( _vertexData . indices . valid ( ) & & _vertexData . indices - > getNumElements ( ) = = 0 ) | |
2003-05-07 21:13:13 +08:00
( _vertexAttribList . size ( ) > 0 & &
2003-09-10 06:18:35 +08:00
_vertexAttribList [ 0 ] . indices . valid ( ) & &
_vertexAttribList [ 0 ] . indices - > getNumElements ( ) = = 0 ) )
2003-05-07 21:13:13 +08:00
{
return ;
}
2002-10-02 21:12:16 +08:00
2003-09-10 06:18:35 +08:00
DrawNormal drawNormal ( _normalData . array . get ( ) , _normalData . indices . get ( ) ) ;
DrawColor drawColor ( _colorData . array . get ( ) , _colorData . indices . get ( ) ) ;
DrawSecondaryColor drawSecondaryColor ( _secondaryColorData . array . get ( ) , _secondaryColorData . indices . get ( ) , extensions ) ;
2002-10-02 21:12:16 +08:00
2003-09-10 06:18:35 +08:00
DrawFogCoord drawFogCoord ( _fogCoordData . array . get ( ) , _fogCoordData . indices . get ( ) , extensions ) ;
2002-10-02 21:12:16 +08:00
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//
// Set up secondary color if required.
//
2003-09-10 06:18:35 +08:00
AttributeBinding secondaryColorBinding = _secondaryColorData . binding ;
2003-05-07 21:13:13 +08:00
if ( secondaryColorBinding ! = BIND_OFF & & ! extensions - > isSecondaryColorSupported ( ) )
2002-08-16 04:27:33 +08:00
{
// switch off if not supported or have a valid data.
secondaryColorBinding = BIND_OFF ;
}
2002-10-02 21:12:16 +08:00
2002-08-16 04:27:33 +08:00
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//
// Set up fog coord if required.
//
2003-09-10 06:18:35 +08:00
AttributeBinding fogCoordBinding = _fogCoordData . binding ;
2003-05-07 21:13:13 +08:00
if ( fogCoordBinding ! = BIND_OFF & & ! extensions - > isFogCoordSupported ( ) )
2002-08-16 04:27:33 +08:00
{
2002-10-02 21:12:16 +08:00
// switch off if not supported or have a valid data.
2002-08-16 04:27:33 +08:00
fogCoordBinding = BIND_OFF ;
}
2002-10-02 21:12:16 +08:00
unsigned int normalIndex = 0 ;
unsigned int colorIndex = 0 ;
unsigned int secondaryColorIndex = 0 ;
unsigned int fogCoordIndex = 0 ;
2003-01-20 19:02:27 +08:00
# if USE_DEFAULT_NORMAL
2002-10-18 20:26:23 +08:00
// if no values are defined for normal and color provide some defaults...
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_OFF ) glNormal3f ( 0.0f , 0.0f , 1.0f ) ;
2003-01-20 19:02:27 +08:00
# endif
2003-02-10 21:58:39 +08:00
# if USE_DEFAULT_COLOUR
2003-09-10 06:18:35 +08:00
if ( _colorData . binding = = BIND_OFF ) glColor4f ( 1.0f , 1.0f , 1.0f , 1.0f ) ;
2003-01-20 19:02:27 +08:00
# endif
2002-10-18 20:26:23 +08:00
2003-05-07 21:13:13 +08:00
typedef std : : vector < ref_ptr < DrawVertexAttrib > > DrawVertexAttribList ;
typedef std : : map < Geometry : : AttributeBinding , DrawVertexAttribList > DrawVertexAttribMap ;
DrawVertexAttribMap drawVertexAttribMap ;
2003-09-01 19:23:29 +08:00
bool vertexVertexAttributesSupported = extensions - > isVertexProgramSupported ( ) ;
bool handleVertexAttributes = ( ! _vertexAttribList . empty ( ) & & vertexVertexAttributesSupported ) ;
2003-07-07 16:01:09 +08:00
bool usingVertexBufferObjects = _useVertexBufferObjects & & state . isVertexBufferObjectSupported ( ) ;
2003-06-30 05:41:57 +08:00
2002-10-02 21:12:16 +08:00
if ( areFastPathsUsed ( ) )
2002-08-16 04:27:33 +08:00
{
2007-04-27 22:52:30 +08:00
2002-10-02 21:12:16 +08:00
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//
// fast path.
//
2003-07-07 16:01:09 +08:00
if ( usingVertexBufferObjects )
2003-06-30 05:41:57 +08:00
{
2009-10-02 04:19:42 +08:00
// osg::notify(osg::NOTICE)<<"Geometry::drawImplementation() Using VertexBufferObjects"<<std::endl;
2007-04-27 22:52:30 +08:00
2007-04-29 16:12:29 +08:00
//
// Vertex Buffer Object path for defining vertex arrays.
//
2007-05-01 14:28:20 +08:00
state . setNormalPointer ( _normalData . binding = = BIND_PER_VERTEX ? _normalData . array . get ( ) : 0 ) ;
state . setColorPointer ( _colorData . binding = = BIND_PER_VERTEX ? _colorData . array . get ( ) : 0 ) ;
state . setSecondaryColorPointer ( _secondaryColorData . binding = = BIND_PER_VERTEX ? _secondaryColorData . array . get ( ) : 0 ) ;
state . setFogCoordPointer ( _fogCoordData . binding = = BIND_PER_VERTEX ? _fogCoordData . array . get ( ) : 0 ) ;
unsigned int unit ;
for ( unit = 0 ; unit < _texCoordList . size ( ) ; + + unit )
{
state . setTexCoordPointer ( unit , _texCoordList [ unit ] . array . get ( ) ) ;
}
state . disableTexCoordPointersAboveAndIncluding ( unit ) ;
if ( handleVertexAttributes )
{
unsigned int index ;
for ( index = 0 ; index < _vertexAttribList . size ( ) ; + + index )
{
const Array * array = _vertexAttribList [ index ] . array . get ( ) ;
const AttributeBinding ab = _vertexAttribList [ index ] . binding ;
state . setVertexAttribPointer ( index , ( ab = = BIND_PER_VERTEX ? array : 0 ) , _vertexAttribList [ index ] . normalize ) ;
if ( array & & ab ! = BIND_PER_VERTEX )
{
const IndexArray * indexArray = _vertexAttribList [ index ] . indices . get ( ) ;
if ( indexArray & & indexArray - > getNumElements ( ) > 0 )
{
drawVertexAttribMap [ ab ] . push_back (
new DrawVertexAttrib ( extensions , index , _vertexAttribList [ index ] . normalize , array , indexArray ) ) ;
}
else
{
drawVertexAttribMap [ ab ] . push_back (
new DrawVertexAttrib ( extensions , index , _vertexAttribList [ index ] . normalize , array , 0 ) ) ;
}
}
}
state . disableVertexAttribPointersAboveAndIncluding ( index ) ;
}
else if ( vertexVertexAttributesSupported )
{
state . disableVertexAttribPointersAboveAndIncluding ( 0 ) ;
}
state . setVertexPointer ( _vertexData . array . get ( ) ) ;
2003-06-30 05:41:57 +08:00
2003-05-07 21:13:13 +08:00
}
2003-06-30 05:41:57 +08:00
else
{
2009-10-02 04:19:42 +08:00
// osg::notify(osg::NOTICE)<<"none VertexBuffer path"<<std::endl;
2003-06-30 05:41:57 +08:00
//
2007-04-23 04:19:43 +08:00
// Non Vertex Buffer Object path for defining vertex arrays.
2003-06-30 05:41:57 +08:00
//
2003-09-10 06:18:35 +08:00
if ( _vertexData . array . valid ( ) )
state . setVertexPointer ( _vertexData . array - > getDataSize ( ) , _vertexData . array - > getDataType ( ) , 0 , _vertexData . array - > getDataPointer ( ) ) ;
2003-06-30 05:41:57 +08:00
else
state . disableVertexPointer ( ) ;
2005-12-06 19:24:24 +08:00
if ( _normalData . binding = = BIND_PER_VERTEX & & _normalData . array . valid ( ) )
2005-07-05 23:57:53 +08:00
state . setNormalPointer ( _normalData . array - > getDataType ( ) , 0 , _normalData . array - > getDataPointer ( ) ) ;
2003-06-30 05:41:57 +08:00
else
state . disableNormalPointer ( ) ;
2005-12-06 19:24:24 +08:00
if ( _colorData . binding = = BIND_PER_VERTEX & & _colorData . array . valid ( ) )
2003-09-10 06:18:35 +08:00
state . setColorPointer ( _colorData . array - > getDataSize ( ) , _colorData . array - > getDataType ( ) , 0 , _colorData . array - > getDataPointer ( ) ) ;
2003-06-30 05:41:57 +08:00
else
state . disableColorPointer ( ) ;
2005-12-06 19:24:24 +08:00
if ( secondaryColorBinding = = BIND_PER_VERTEX & & _secondaryColorData . array . valid ( ) )
2003-09-10 06:18:35 +08:00
state . setSecondaryColorPointer ( _secondaryColorData . array - > getDataSize ( ) , _secondaryColorData . array - > getDataType ( ) , 0 , _secondaryColorData . array - > getDataPointer ( ) ) ;
2003-06-30 05:41:57 +08:00
else
state . disableSecondaryColorPointer ( ) ;
2005-12-06 19:24:24 +08:00
if ( fogCoordBinding = = BIND_PER_VERTEX & & _fogCoordData . array . valid ( ) )
2003-09-10 06:18:35 +08:00
state . setFogCoordPointer ( GL_FLOAT , 0 , _fogCoordData . array - > getDataPointer ( ) ) ;
2003-06-30 05:41:57 +08:00
else
state . disableFogCoordPointer ( ) ;
unsigned int unit ;
for ( unit = 0 ; unit < _texCoordList . size ( ) ; + + unit )
{
2003-09-10 06:18:35 +08:00
const Array * array = _texCoordList [ unit ] . array . get ( ) ;
2003-06-30 05:41:57 +08:00
if ( array )
state . setTexCoordPointer ( unit , array - > getDataSize ( ) , array - > getDataType ( ) , 0 , array - > getDataPointer ( ) ) ;
else
state . disableTexCoordPointer ( unit ) ;
}
state . disableTexCoordPointersAboveAndIncluding ( unit ) ;
if ( handleVertexAttributes )
{
unsigned int index ;
for ( index = 0 ; index < _vertexAttribList . size ( ) ; + + index )
{
2003-09-10 06:18:35 +08:00
const Array * array = _vertexAttribList [ index ] . array . get ( ) ;
const AttributeBinding ab = _vertexAttribList [ index ] . binding ;
2003-06-30 05:41:57 +08:00
if ( ab = = BIND_PER_VERTEX & & array )
{
state . setVertexAttribPointer ( index , array - > getDataSize ( ) , array - > getDataType ( ) ,
2003-09-10 06:18:35 +08:00
_vertexAttribList [ index ] . normalize , 0 , array - > getDataPointer ( ) ) ;
2003-06-30 05:41:57 +08:00
}
else
{
if ( array )
{
2003-09-10 06:18:35 +08:00
const IndexArray * indexArray = _vertexAttribList [ index ] . indices . get ( ) ;
2003-06-30 05:41:57 +08:00
if ( indexArray & & indexArray - > getNumElements ( ) > 0 )
{
drawVertexAttribMap [ ab ] . push_back (
2003-09-10 06:18:35 +08:00
new DrawVertexAttrib ( extensions , index , _vertexAttribList [ index ] . normalize , array , indexArray ) ) ;
2003-06-30 05:41:57 +08:00
}
else
{
drawVertexAttribMap [ ab ] . push_back (
2003-09-10 06:18:35 +08:00
new DrawVertexAttrib ( extensions , index , _vertexAttribList [ index ] . normalize , array , 0 ) ) ;
2003-06-30 05:41:57 +08:00
}
}
2002-10-02 21:12:16 +08:00
2003-06-30 05:41:57 +08:00
state . disableVertexAttribPointer ( index ) ;
}
}
state . disableVertexAttribPointersAboveAndIncluding ( index ) ;
2003-09-01 19:23:29 +08:00
}
else if ( vertexVertexAttributesSupported )
{
state . disableVertexAttribPointersAboveAndIncluding ( 0 ) ;
2003-06-30 05:41:57 +08:00
}
}
2002-10-02 21:12:16 +08:00
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//
// pass the overall binding values onto OpenGL.
//
2005-12-06 19:24:24 +08:00
if ( _normalData . binding = = BIND_OVERALL ) drawNormal ( normalIndex + + ) ;
if ( _colorData . binding = = BIND_OVERALL ) drawColor ( colorIndex + + ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_OVERALL ) drawSecondaryColor ( secondaryColorIndex + + ) ;
if ( fogCoordBinding = = BIND_OVERALL ) drawFogCoord ( fogCoordIndex + + ) ;
2003-06-30 05:41:57 +08:00
if ( handleVertexAttributes )
2003-05-07 21:13:13 +08:00
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_OVERALL ] ;
2002-10-02 21:12:16 +08:00
2003-05-07 21:13:13 +08:00
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//
// draw the primitives themselves.
//
2002-11-06 23:43:11 +08:00
for ( PrimitiveSetList : : const_iterator itr = _primitives . begin ( ) ;
2002-10-02 21:12:16 +08:00
itr ! = _primitives . end ( ) ;
+ + itr )
2002-06-22 00:45:45 +08:00
{
2002-10-02 21:12:16 +08:00
2005-12-06 19:24:24 +08:00
if ( _normalData . binding = = BIND_PER_PRIMITIVE_SET ) drawNormal ( normalIndex + + ) ;
if ( _colorData . binding = = BIND_PER_PRIMITIVE_SET ) drawColor ( colorIndex + + ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_PER_PRIMITIVE_SET ) drawSecondaryColor ( secondaryColorIndex + + ) ;
if ( fogCoordBinding = = BIND_PER_PRIMITIVE_SET ) drawFogCoord ( fogCoordIndex + + ) ;
2003-06-30 05:41:57 +08:00
if ( handleVertexAttributes )
2003-05-07 21:13:13 +08:00
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_PER_PRIMITIVE_SET ] ;
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
2004-06-29 23:04:38 +08:00
( * itr ) - > draw ( state , usingVertexBufferObjects ) ;
2002-10-02 21:12:16 +08:00
}
2003-07-07 16:01:09 +08:00
if ( usingVertexBufferObjects )
2003-06-30 05:41:57 +08:00
{
2007-05-01 17:29:30 +08:00
# if 1
2007-05-01 14:28:20 +08:00
state . unbindVertexBufferObject ( ) ;
state . unbindElementBufferObject ( ) ;
2007-05-01 17:29:30 +08:00
# endif
2003-06-30 05:41:57 +08:00
}
2002-10-02 21:12:16 +08:00
}
else
{
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//
// slow path.
//
typedef std : : vector < ref_ptr < DrawMultiTexCoord > > DrawTexCoordList ;
DrawTexCoordList drawTexCoordList ;
drawTexCoordList . reserve ( _texCoordList . size ( ) ) ;
// fallback if multitexturing not supported.
ref_ptr < DrawTexCoord > drawTextCoord ;
2003-09-10 06:18:35 +08:00
if ( extensions - > isMultiTexSupported ( ) & & _texCoordList . size ( ) > 1 )
2002-10-02 21:12:16 +08:00
{
// multitexture supported..
for ( unsigned int unit = 0 ; unit ! = _texCoordList . size ( ) ; + + unit )
2002-06-22 00:45:45 +08:00
{
2003-09-10 06:18:35 +08:00
const ArrayData & texcoordData = _texCoordList [ unit ] ;
if ( texcoordData . array . valid ( ) & & texcoordData . array - > getNumElements ( ) > 0 )
2002-10-02 21:12:16 +08:00
{
2003-09-10 06:18:35 +08:00
if ( texcoordData . indices . valid ( ) & & texcoordData . indices - > getNumElements ( ) > 0 )
2002-10-02 21:12:16 +08:00
{
2003-09-10 06:18:35 +08:00
drawTexCoordList . push_back ( new DrawMultiTexCoord ( GL_TEXTURE0 + unit , texcoordData . array . get ( ) , texcoordData . indices . get ( ) ,
extensions ) ) ;
2002-10-02 21:12:16 +08:00
}
else
{
2003-09-10 06:18:35 +08:00
drawTexCoordList . push_back ( new DrawMultiTexCoord ( GL_TEXTURE0 + unit , texcoordData . array . get ( ) , 0 ,
2003-05-07 21:13:13 +08:00
extensions ) ) ;
2002-10-02 21:12:16 +08:00
}
}
}
}
else
{
if ( ! _texCoordList . empty ( ) )
{
2003-09-10 06:18:35 +08:00
const ArrayData & texcoordData = _texCoordList [ 0 ] ;
if ( texcoordData . array . valid ( ) & & texcoordData . array - > getNumElements ( ) > 0 )
2002-10-02 21:12:16 +08:00
{
2003-09-10 06:18:35 +08:00
if ( texcoordData . indices . valid ( ) )
2002-10-02 21:12:16 +08:00
{
2003-09-10 06:18:35 +08:00
if ( texcoordData . indices - > getNumElements ( ) > 0 )
2002-10-02 21:12:16 +08:00
{
2003-09-10 06:18:35 +08:00
drawTextCoord = new DrawTexCoord ( texcoordData . array . get ( ) , texcoordData . indices . get ( ) ) ;
2002-10-02 21:12:16 +08:00
}
}
else
{
2003-09-10 06:18:35 +08:00
drawTextCoord = new DrawTexCoord ( texcoordData . array . get ( ) , 0 ) ;
2002-10-02 21:12:16 +08:00
}
}
2002-06-22 00:45:45 +08:00
}
2002-06-21 03:54:08 +08:00
}
2003-06-30 05:41:57 +08:00
if ( handleVertexAttributes )
2003-05-07 21:13:13 +08:00
{
unsigned int index ;
2003-05-09 21:07:06 +08:00
for ( index = 1 ; index < _vertexAttribList . size ( ) ; + + index )
2003-05-07 21:13:13 +08:00
{
2003-09-10 06:18:35 +08:00
const ArrayData & vertAttribData = _vertexAttribList [ index ] ;
if ( vertAttribData . array . valid ( ) & & vertAttribData . array - > getNumElements ( ) > 0 )
2003-05-07 21:13:13 +08:00
{
2003-09-10 06:18:35 +08:00
if ( vertAttribData . indices . valid ( ) & & vertAttribData . indices - > getNumElements ( ) > 0 )
2003-05-07 21:13:13 +08:00
{
2003-09-10 06:18:35 +08:00
drawVertexAttribMap [ vertAttribData . binding ] . push_back (
new DrawVertexAttrib ( extensions , index , vertAttribData . normalize , vertAttribData . array . get ( ) , vertAttribData . indices . get ( ) ) ) ;
2003-05-07 21:13:13 +08:00
}
2003-05-09 21:07:06 +08:00
else
{
2003-09-10 06:18:35 +08:00
drawVertexAttribMap [ vertAttribData . binding ] . push_back (
new DrawVertexAttrib ( extensions , index , vertAttribData . normalize , vertAttribData . array . get ( ) , 0 ) ) ;
2003-05-09 21:07:06 +08:00
}
2003-05-07 21:13:13 +08:00
}
}
}
2002-10-02 21:12:16 +08:00
// disable all the vertex arrays in the slow path as we are
// sending everything using glVertex etc.
state . disableAllVertexArrays ( ) ;
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//
// pass the overall binding values onto OpenGL.
//
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_OVERALL ) drawNormal ( normalIndex + + ) ;
if ( _colorData . binding = = BIND_OVERALL ) drawColor ( colorIndex + + ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_OVERALL ) drawSecondaryColor ( secondaryColorIndex + + ) ;
if ( fogCoordBinding = = BIND_OVERALL ) drawFogCoord ( fogCoordIndex + + ) ;
2003-06-30 05:41:57 +08:00
if ( handleVertexAttributes )
2003-05-07 21:13:13 +08:00
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_OVERALL ] ;
2002-10-02 21:12:16 +08:00
2003-05-07 21:13:13 +08:00
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
// set up vertex functor.
2003-09-10 06:18:35 +08:00
DrawVertex drawVertex ( _vertexData . array . get ( ) , _vertexData . indices . get ( ) ) ;
2002-10-02 21:12:16 +08:00
2003-05-09 21:07:06 +08:00
bool useVertexAttrib = _vertexAttribList . size ( ) > 0 & &
2003-09-10 06:18:35 +08:00
_vertexAttribList [ 0 ] . array . valid ( ) & &
2009-10-08 21:33:41 +08:00
_vertexAttribList [ 0 ] . array - > getNumElements ( ) ! = 0 ;
2003-05-09 21:07:06 +08:00
ref_ptr < DrawVertexAttrib > drawVertexAttribZero ;
if ( useVertexAttrib )
{
drawVertexAttribZero = new DrawVertexAttrib ( extensions , 0 ,
2003-09-10 06:18:35 +08:00
_vertexAttribList [ 0 ] . normalize , _vertexAttribList [ 0 ] . array . get ( ) ,
_vertexAttribList [ 0 ] . indices . get ( ) ) ;
2003-05-09 21:07:06 +08:00
}
2002-10-02 21:12:16 +08:00
///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
//
// draw the primitives themselves.
//
2002-11-06 23:43:11 +08:00
for ( PrimitiveSetList : : const_iterator itr = _primitives . begin ( ) ;
2002-10-02 21:12:16 +08:00
itr ! = _primitives . end ( ) ;
+ + itr )
2002-08-16 04:27:33 +08:00
{
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_PER_PRIMITIVE_SET ) drawNormal ( normalIndex + + ) ;
if ( _colorData . binding = = BIND_PER_PRIMITIVE_SET ) drawColor ( colorIndex + + ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_PER_PRIMITIVE_SET ) drawSecondaryColor ( secondaryColorIndex + + ) ;
if ( fogCoordBinding = = BIND_PER_PRIMITIVE_SET ) drawFogCoord ( fogCoordIndex + + ) ;
2003-06-30 05:41:57 +08:00
if ( handleVertexAttributes )
2003-05-07 21:13:13 +08:00
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_PER_PRIMITIVE_SET ] ;
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-11-06 23:43:11 +08:00
const PrimitiveSet * primitiveset = itr - > get ( ) ;
2002-10-02 21:12:16 +08:00
GLenum mode = primitiveset - > getMode ( ) ;
unsigned int primLength ;
switch ( mode )
{
case ( GL_POINTS ) : primLength = 1 ; break ;
case ( GL_LINES ) : primLength = 2 ; break ;
case ( GL_TRIANGLES ) : primLength = 3 ; break ;
case ( GL_QUADS ) : primLength = 4 ; break ;
default : primLength = 0 ; break ; // compute later when =0.
}
2007-12-11 01:30:18 +08:00
// draw primitives by the more flexible "slow" path,
2002-10-02 21:12:16 +08:00
// sending OpenGL glBegin/glVertex.../glEnd().
switch ( primitiveset - > getType ( ) )
2002-08-16 04:27:33 +08:00
{
2002-10-02 21:12:16 +08:00
case ( PrimitiveSet : : DrawArraysPrimitiveType ) :
{
if ( primLength = = 0 ) primLength = primitiveset - > getNumIndices ( ) ;
const DrawArrays * drawArray = static_cast < const DrawArrays * > ( primitiveset ) ;
glBegin ( mode ) ;
unsigned int primCount = 0 ;
unsigned int indexEnd = drawArray - > getFirst ( ) + drawArray - > getCount ( ) ;
for ( unsigned int vindex = drawArray - > getFirst ( ) ;
vindex < indexEnd ;
+ + vindex , + + primCount )
{
if ( ( primCount % primLength ) = = 0 )
{
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_PER_PRIMITIVE ) drawNormal ( normalIndex + + ) ;
if ( _colorData . binding = = BIND_PER_PRIMITIVE ) drawColor ( colorIndex + + ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_PER_PRIMITIVE ) drawSecondaryColor ( secondaryColorIndex + + ) ;
if ( fogCoordBinding = = BIND_PER_PRIMITIVE ) drawFogCoord ( fogCoordIndex + + ) ;
2003-06-30 05:41:57 +08:00
if ( handleVertexAttributes )
2003-05-07 21:13:13 +08:00
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_PER_PRIMITIVE ] ;
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
}
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_PER_VERTEX ) drawNormal ( vindex ) ;
if ( _colorData . binding = = BIND_PER_VERTEX ) drawColor ( vindex ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_PER_VERTEX ) drawSecondaryColor ( vindex ) ;
if ( fogCoordBinding = = BIND_PER_VERTEX ) drawFogCoord ( vindex ) ;
2003-06-30 05:41:57 +08:00
if ( handleVertexAttributes )
2003-05-07 21:13:13 +08:00
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_PER_VERTEX ] ;
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
for ( DrawTexCoordList : : iterator texItr = drawTexCoordList . begin ( ) ;
texItr ! = drawTexCoordList . end ( ) ;
+ + texItr )
{
( * ( * texItr ) ) ( vindex ) ;
}
if ( drawTextCoord . valid ( ) ) ( * drawTextCoord ) ( vindex ) ;
2003-05-09 21:07:06 +08:00
if ( useVertexAttrib )
{
( * drawVertexAttribZero ) ( vindex ) ;
}
else
{
drawVertex ( vindex ) ;
}
2002-10-02 21:12:16 +08:00
}
glEnd ( ) ;
2002-08-16 04:27:33 +08:00
break ;
2002-10-02 21:12:16 +08:00
}
case ( PrimitiveSet : : DrawArrayLengthsPrimitiveType ) :
{
const DrawArrayLengths * drawArrayLengths = static_cast < const DrawArrayLengths * > ( primitiveset ) ;
unsigned int vindex = drawArrayLengths - > getFirst ( ) ;
for ( DrawArrayLengths : : const_iterator primItr = drawArrayLengths - > begin ( ) ;
primItr ! = drawArrayLengths - > end ( ) ;
+ + primItr )
{
unsigned int localPrimLength ;
if ( primLength = = 0 ) localPrimLength = * primItr ;
else localPrimLength = primLength ;
glBegin ( mode ) ;
for ( GLsizei primCount = 0 ; primCount < * primItr ; + + primCount )
{
if ( ( primCount % localPrimLength ) = = 0 )
{
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_PER_PRIMITIVE ) drawNormal ( normalIndex + + ) ;
if ( _colorData . binding = = BIND_PER_PRIMITIVE ) drawColor ( colorIndex + + ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_PER_PRIMITIVE ) drawSecondaryColor ( secondaryColorIndex + + ) ;
if ( fogCoordBinding = = BIND_PER_PRIMITIVE ) drawFogCoord ( fogCoordIndex + + ) ;
2003-06-30 05:41:57 +08:00
if ( handleVertexAttributes )
2003-05-07 21:13:13 +08:00
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_PER_PRIMITIVE ] ;
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
}
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_PER_VERTEX ) drawNormal ( vindex ) ;
if ( _colorData . binding = = BIND_PER_VERTEX ) drawColor ( vindex ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_PER_VERTEX ) drawSecondaryColor ( vindex ) ;
if ( fogCoordBinding = = BIND_PER_VERTEX ) drawFogCoord ( vindex ) ;
2003-06-30 05:41:57 +08:00
if ( handleVertexAttributes )
2003-05-07 21:13:13 +08:00
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_PER_VERTEX ] ;
2002-10-02 21:12:16 +08:00
2003-05-07 21:13:13 +08:00
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
for ( DrawTexCoordList : : iterator texItr = drawTexCoordList . begin ( ) ;
texItr ! = drawTexCoordList . end ( ) ;
+ + texItr )
{
( * ( * texItr ) ) ( vindex ) ;
}
if ( drawTextCoord . valid ( ) ) ( * drawTextCoord ) ( vindex ) ;
2003-05-09 21:07:06 +08:00
if ( useVertexAttrib )
{
( * drawVertexAttribZero ) ( vindex ) ;
}
else
{
drawVertex ( vindex ) ;
}
2002-10-02 21:12:16 +08:00
+ + vindex ;
}
glEnd ( ) ;
}
2002-08-16 04:27:33 +08:00
break ;
2002-10-02 21:12:16 +08:00
}
case ( PrimitiveSet : : DrawElementsUBytePrimitiveType ) :
{
if ( primLength = = 0 ) primLength = primitiveset - > getNumIndices ( ) ;
const DrawElementsUByte * drawElements = static_cast < const DrawElementsUByte * > ( primitiveset ) ;
glBegin ( mode ) ;
unsigned int primCount = 0 ;
for ( DrawElementsUByte : : const_iterator primItr = drawElements - > begin ( ) ;
primItr ! = drawElements - > end ( ) ;
+ + primCount , + + primItr )
{
if ( ( primCount % primLength ) = = 0 )
{
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_PER_PRIMITIVE ) drawNormal ( normalIndex + + ) ;
if ( _colorData . binding = = BIND_PER_PRIMITIVE ) drawColor ( colorIndex + + ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_PER_PRIMITIVE ) drawSecondaryColor ( secondaryColorIndex + + ) ;
if ( fogCoordBinding = = BIND_PER_PRIMITIVE ) drawFogCoord ( fogCoordIndex + + ) ;
2003-06-30 05:41:57 +08:00
if ( handleVertexAttributes )
2003-05-07 21:13:13 +08:00
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_PER_PRIMITIVE ] ;
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
}
unsigned int vindex = * primItr ;
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_PER_VERTEX ) drawNormal ( vindex ) ;
if ( _colorData . binding = = BIND_PER_VERTEX ) drawColor ( vindex ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_PER_VERTEX ) drawSecondaryColor ( vindex ) ;
if ( fogCoordBinding = = BIND_PER_VERTEX ) drawFogCoord ( vindex ) ;
2003-05-07 21:13:13 +08:00
if ( extensions - > isVertexProgramSupported ( ) )
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_PER_VERTEX ] ;
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
for ( DrawTexCoordList : : iterator texItr = drawTexCoordList . begin ( ) ;
texItr ! = drawTexCoordList . end ( ) ;
+ + texItr )
{
( * ( * texItr ) ) ( vindex ) ;
}
if ( drawTextCoord . valid ( ) ) ( * drawTextCoord ) ( vindex ) ;
2003-05-09 21:07:06 +08:00
if ( useVertexAttrib )
{
( * drawVertexAttribZero ) ( vindex ) ;
}
else
{
drawVertex ( vindex ) ;
}
2002-10-02 21:12:16 +08:00
}
glEnd ( ) ;
break ;
}
case ( PrimitiveSet : : DrawElementsUShortPrimitiveType ) :
{
if ( primLength = = 0 ) primLength = primitiveset - > getNumIndices ( ) ;
const DrawElementsUShort * drawElements = static_cast < const DrawElementsUShort * > ( primitiveset ) ;
glBegin ( mode ) ;
unsigned int primCount = 0 ;
for ( DrawElementsUShort : : const_iterator primItr = drawElements - > begin ( ) ;
primItr ! = drawElements - > end ( ) ;
+ + primCount , + + primItr )
{
if ( ( primCount % primLength ) = = 0 )
{
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_PER_PRIMITIVE ) drawNormal ( normalIndex + + ) ;
if ( _colorData . binding = = BIND_PER_PRIMITIVE ) drawColor ( colorIndex + + ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_PER_PRIMITIVE ) drawSecondaryColor ( secondaryColorIndex + + ) ;
if ( fogCoordBinding = = BIND_PER_PRIMITIVE ) drawFogCoord ( fogCoordIndex + + ) ;
2003-06-30 05:41:57 +08:00
if ( handleVertexAttributes )
2003-05-07 21:13:13 +08:00
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_PER_PRIMITIVE ] ;
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
}
unsigned int vindex = * primItr ;
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_PER_VERTEX ) drawNormal ( vindex ) ;
if ( _colorData . binding = = BIND_PER_VERTEX ) drawColor ( vindex ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_PER_VERTEX ) drawSecondaryColor ( vindex ) ;
if ( fogCoordBinding = = BIND_PER_VERTEX ) drawFogCoord ( vindex ) ;
2003-06-30 05:41:57 +08:00
if ( handleVertexAttributes )
2003-05-07 21:13:13 +08:00
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_PER_VERTEX ] ;
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
for ( DrawTexCoordList : : iterator texItr = drawTexCoordList . begin ( ) ;
texItr ! = drawTexCoordList . end ( ) ;
+ + texItr )
{
( * ( * texItr ) ) ( vindex ) ;
}
if ( drawTextCoord . valid ( ) ) ( * drawTextCoord ) ( vindex ) ;
2003-05-09 21:07:06 +08:00
if ( useVertexAttrib )
{
( * drawVertexAttribZero ) ( vindex ) ;
}
else
{
drawVertex ( vindex ) ;
}
2002-10-02 21:12:16 +08:00
}
glEnd ( ) ;
break ;
}
case ( PrimitiveSet : : DrawElementsUIntPrimitiveType ) :
{
if ( primLength = = 0 ) primLength = primitiveset - > getNumIndices ( ) ;
const DrawElementsUInt * drawElements = static_cast < const DrawElementsUInt * > ( primitiveset ) ;
glBegin ( mode ) ;
unsigned int primCount = 0 ;
for ( DrawElementsUInt : : const_iterator primItr = drawElements - > begin ( ) ;
primItr ! = drawElements - > end ( ) ;
+ + primCount , + + primItr )
{
if ( ( primCount % primLength ) = = 0 )
{
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_PER_PRIMITIVE ) drawNormal ( normalIndex + + ) ;
if ( _colorData . binding = = BIND_PER_PRIMITIVE ) drawColor ( colorIndex + + ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_PER_PRIMITIVE ) drawSecondaryColor ( secondaryColorIndex + + ) ;
if ( fogCoordBinding = = BIND_PER_PRIMITIVE ) drawFogCoord ( fogCoordIndex + + ) ;
2003-05-07 21:13:13 +08:00
if ( extensions - > isVertexProgramSupported ( ) )
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_PER_PRIMITIVE ] ;
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
}
unsigned int vindex = * primItr ;
2003-09-10 06:18:35 +08:00
if ( _normalData . binding = = BIND_PER_VERTEX ) drawNormal ( vindex ) ;
if ( _colorData . binding = = BIND_PER_VERTEX ) drawColor ( vindex ) ;
2002-10-02 21:12:16 +08:00
if ( secondaryColorBinding = = BIND_PER_VERTEX ) drawSecondaryColor ( vindex ) ;
if ( fogCoordBinding = = BIND_PER_VERTEX ) drawFogCoord ( vindex ) ;
2003-05-07 21:13:13 +08:00
if ( extensions - > isVertexProgramSupported ( ) )
{
DrawVertexAttribList & list = drawVertexAttribMap [ BIND_PER_VERTEX ] ;
for ( unsigned int i = 0 ; i < list . size ( ) ; + + i )
{
2003-10-22 21:39:16 +08:00
list [ i ] - > applyAndIncrement ( ) ;
2003-05-07 21:13:13 +08:00
}
}
2002-10-02 21:12:16 +08:00
for ( DrawTexCoordList : : iterator texItr = drawTexCoordList . begin ( ) ;
texItr ! = drawTexCoordList . end ( ) ;
+ + texItr )
{
( * ( * texItr ) ) ( vindex ) ;
}
if ( drawTextCoord . valid ( ) ) ( * drawTextCoord ) ( vindex ) ;
2003-05-09 21:07:06 +08:00
if ( useVertexAttrib )
{
( * drawVertexAttribZero ) ( vindex ) ;
}
else
{
drawVertex ( vindex ) ;
}
2002-10-02 21:12:16 +08:00
}
glEnd ( ) ;
break ;
}
2002-08-16 04:27:33 +08:00
default :
2002-10-02 21:12:16 +08:00
{
2002-08-16 04:27:33 +08:00
break ;
2002-10-02 21:12:16 +08:00
}
2002-08-16 04:27:33 +08:00
}
}
2002-06-22 00:45:45 +08:00
}
2002-06-21 03:54:08 +08:00
}
2004-12-07 08:42:21 +08:00
class AttributeFunctorArrayVisitor : public ArrayVisitor
2002-11-06 18:24:33 +08:00
{
public :
2004-12-07 08:42:21 +08:00
AttributeFunctorArrayVisitor ( Drawable : : AttributeFunctor & af ) :
2002-11-06 18:24:33 +08:00
_af ( af ) { }
2004-12-07 08:42:21 +08:00
virtual ~ AttributeFunctorArrayVisitor ( ) { }
2002-11-06 18:24:33 +08:00
virtual void apply ( ByteArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( ShortArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( IntArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( UByteArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( UShortArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( UIntArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
2005-07-15 22:41:19 +08:00
virtual void apply ( Vec4ubArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
2002-11-06 18:24:33 +08:00
virtual void apply ( FloatArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( Vec2Array & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( Vec3Array & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( Vec4Array & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
2007-12-04 22:46:46 +08:00
virtual void apply ( DoubleArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( Vec2dArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( Vec3dArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( Vec4dArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
2002-11-06 18:24:33 +08:00
2002-11-22 17:46:25 +08:00
inline void applyArray ( Drawable : : AttributeType type , Array * array )
2002-11-06 18:24:33 +08:00
{
if ( array )
{
_type = type ;
array - > accept ( * this ) ;
}
}
2009-01-07 20:27:45 +08:00
protected :
AttributeFunctorArrayVisitor & operator = ( const AttributeFunctorArrayVisitor & ) { return * this ; }
2002-11-06 18:24:33 +08:00
Drawable : : AttributeFunctor & _af ;
Drawable : : AttributeType _type ;
} ;
2002-06-21 03:54:08 +08:00
2002-07-18 23:36:14 +08:00
void Geometry : : accept ( AttributeFunctor & af )
2002-06-21 03:54:08 +08:00
{
2004-12-07 08:42:21 +08:00
AttributeFunctorArrayVisitor afav ( af ) ;
2006-03-01 03:46:02 +08:00
2009-10-09 21:39:11 +08:00
if ( _vertexData . array . valid ( ) )
{
afav . applyArray ( VERTICES , _vertexData . array . get ( ) ) ;
}
else if ( _vertexAttribList . size ( ) > 0 )
{
osg : : notify ( osg : : INFO ) < < " Geometry::accept(AttributeFunctor& af): Using vertex attribute instead " < < std : : endl ;
afav . applyArray ( VERTICES , _vertexAttribList [ 0 ] . array . get ( ) ) ;
}
2003-09-10 06:18:35 +08:00
afav . applyArray ( NORMALS , _normalData . array . get ( ) ) ;
afav . applyArray ( COLORS , _colorData . array . get ( ) ) ;
2006-03-01 03:46:02 +08:00
afav . applyArray ( SECONDARY_COLORS , _secondaryColorData . array . get ( ) ) ;
afav . applyArray ( FOG_COORDS , _fogCoordData . array . get ( ) ) ;
2002-11-06 18:24:33 +08:00
for ( unsigned unit = 0 ; unit < _texCoordList . size ( ) ; + + unit )
2002-06-28 04:29:32 +08:00
{
2003-09-10 06:18:35 +08:00
afav . applyArray ( ( AttributeType ) ( TEXTURE_COORDS_0 + unit ) , _texCoordList [ unit ] . array . get ( ) ) ;
2002-06-28 04:29:32 +08:00
}
2006-03-01 03:46:02 +08:00
for ( unsigned int index = 0 ; index < _vertexAttribList . size ( ) ; + + index )
{
afav . applyArray ( index , _vertexAttribList [ index ] . array . get ( ) ) ;
}
2002-11-06 18:24:33 +08:00
}
2004-12-07 08:42:21 +08:00
class ConstAttributeFunctorArrayVisitor : public ConstArrayVisitor
2002-11-06 18:24:33 +08:00
{
public :
2002-06-28 04:29:32 +08:00
2004-12-07 08:42:21 +08:00
ConstAttributeFunctorArrayVisitor ( Drawable : : ConstAttributeFunctor & af ) :
2002-11-06 18:24:33 +08:00
_af ( af ) { }
2004-12-07 08:42:21 +08:00
virtual ~ ConstAttributeFunctorArrayVisitor ( ) { }
2002-11-06 18:24:33 +08:00
virtual void apply ( const ByteArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( const ShortArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( const IntArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( const UByteArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( const UShortArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( const UIntArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
2005-07-15 22:41:19 +08:00
virtual void apply ( const Vec4ubArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
2002-11-06 18:24:33 +08:00
virtual void apply ( const FloatArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( const Vec2Array & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( const Vec3Array & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( const Vec4Array & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
2007-12-04 22:46:46 +08:00
virtual void apply ( const DoubleArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( const Vec2dArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( const Vec3dArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
virtual void apply ( const Vec4dArray & array ) { if ( ! array . empty ( ) ) _af . apply ( _type , array . size ( ) , & ( array . front ( ) ) ) ; }
2002-11-06 18:24:33 +08:00
2002-11-22 17:46:25 +08:00
inline void applyArray ( Drawable : : AttributeType type , const Array * array )
2002-11-06 18:24:33 +08:00
{
if ( array )
{
_type = type ;
array - > accept ( * this ) ;
}
}
2009-01-07 20:27:45 +08:00
protected :
ConstAttributeFunctorArrayVisitor & operator = ( const ConstAttributeFunctorArrayVisitor & ) { return * this ; }
2002-11-06 18:24:33 +08:00
Drawable : : ConstAttributeFunctor & _af ;
Drawable : : AttributeType _type ;
} ;
void Geometry : : accept ( ConstAttributeFunctor & af ) const
{
2004-12-07 08:42:21 +08:00
ConstAttributeFunctorArrayVisitor afav ( af ) ;
2002-11-06 18:24:33 +08:00
2009-10-09 21:39:11 +08:00
if ( _vertexData . array . valid ( ) )
{
afav . applyArray ( VERTICES , _vertexData . array . get ( ) ) ;
}
else if ( _vertexAttribList . size ( ) > 0 )
{
osg : : notify ( osg : : INFO ) < < " Geometry::accept(ConstAttributeFunctor& af): Using vertex attribute instead " < < std : : endl ;
afav . applyArray ( VERTICES , _vertexAttribList [ 0 ] . array . get ( ) ) ;
}
2003-09-10 06:18:35 +08:00
afav . applyArray ( NORMALS , _normalData . array . get ( ) ) ;
afav . applyArray ( COLORS , _colorData . array . get ( ) ) ;
2006-03-01 03:46:02 +08:00
afav . applyArray ( SECONDARY_COLORS , _secondaryColorData . array . get ( ) ) ;
afav . applyArray ( FOG_COORDS , _fogCoordData . array . get ( ) ) ;
2002-11-06 18:24:33 +08:00
for ( unsigned unit = 0 ; unit < _texCoordList . size ( ) ; + + unit )
2002-06-28 04:29:32 +08:00
{
2003-09-10 06:18:35 +08:00
afav . applyArray ( ( AttributeType ) ( TEXTURE_COORDS_0 + unit ) , _texCoordList [ unit ] . array . get ( ) ) ;
2002-06-28 04:29:32 +08:00
}
2006-03-01 03:46:02 +08:00
for ( unsigned int index = 0 ; index < _vertexAttribList . size ( ) ; + + index )
{
afav . applyArray ( index , _vertexAttribList [ index ] . array . get ( ) ) ;
}
2002-06-21 03:54:08 +08:00
}
2002-11-06 18:24:33 +08:00
void Geometry : : accept ( PrimitiveFunctor & functor ) const
2002-06-26 04:27:51 +08:00
{
2009-10-09 21:39:11 +08:00
const osg : : Array * vertices = _vertexData . array . get ( ) ;
const osg : : IndexArray * indices = _vertexData . indices . get ( ) ;
2003-06-24 23:40:09 +08:00
2009-10-09 21:39:11 +08:00
if ( ! vertices & & _vertexAttribList . size ( ) > 0 )
{
osg : : notify ( osg : : INFO ) < < " Using vertex attribute instead " < < std : : endl ;
vertices = _vertexAttribList [ 0 ] . array . get ( ) ;
indices = _vertexAttribList [ 0 ] . indices . get ( ) ;
}
if ( ! vertices | | vertices - > getNumElements ( ) = = 0 ) return ;
if ( ! indices )
2002-06-26 04:27:51 +08:00
{
2009-10-09 21:39:11 +08:00
switch ( vertices - > getType ( ) )
2003-06-24 23:40:09 +08:00
{
case ( Array : : Vec2ArrayType ) :
2009-10-09 21:39:11 +08:00
functor . setVertexArray ( vertices - > getNumElements ( ) , static_cast < const Vec2 * > ( vertices - > getDataPointer ( ) ) ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec3ArrayType ) :
2009-10-09 21:39:11 +08:00
functor . setVertexArray ( vertices - > getNumElements ( ) , static_cast < const Vec3 * > ( vertices - > getDataPointer ( ) ) ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec4ArrayType ) :
2009-10-09 21:39:11 +08:00
functor . setVertexArray ( vertices - > getNumElements ( ) , static_cast < const Vec4 * > ( vertices - > getDataPointer ( ) ) ) ;
2003-06-24 23:40:09 +08:00
break ;
2007-12-04 22:46:46 +08:00
case ( Array : : Vec2dArrayType ) :
2009-10-09 21:39:11 +08:00
functor . setVertexArray ( vertices - > getNumElements ( ) , static_cast < const Vec2d * > ( vertices - > getDataPointer ( ) ) ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec3dArrayType ) :
2009-10-09 21:39:11 +08:00
functor . setVertexArray ( vertices - > getNumElements ( ) , static_cast < const Vec3d * > ( vertices - > getDataPointer ( ) ) ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec4dArrayType ) :
2009-10-09 21:39:11 +08:00
functor . setVertexArray ( vertices - > getNumElements ( ) , static_cast < const Vec4d * > ( vertices - > getDataPointer ( ) ) ) ;
2007-12-04 22:46:46 +08:00
break ;
2003-06-24 23:40:09 +08:00
default :
2009-10-09 21:39:11 +08:00
notify ( WARN ) < < " Warning: Geometry::accept(PrimitiveFunctor&) cannot handle Vertex Array type " < < vertices - > getType ( ) < < std : : endl ;
2003-06-24 23:40:09 +08:00
return ;
}
2002-11-06 18:24:33 +08:00
for ( PrimitiveSetList : : const_iterator itr = _primitives . begin ( ) ;
2002-10-08 22:10:55 +08:00
itr ! = _primitives . end ( ) ;
+ + itr )
{
( * itr ) - > accept ( functor ) ;
}
2002-06-26 04:27:51 +08:00
}
2002-10-08 22:10:55 +08:00
else
{
2007-12-11 23:55:02 +08:00
const Vec2 * vec2Array = 0 ;
const Vec3 * vec3Array = 0 ;
const Vec4 * vec4Array = 0 ;
const Vec2d * vec2dArray = 0 ;
const Vec3d * vec3dArray = 0 ;
const Vec4d * vec4dArray = 0 ;
2009-10-09 21:39:11 +08:00
Array : : Type type = vertices - > getType ( ) ;
2003-06-24 23:40:09 +08:00
switch ( type )
{
case ( Array : : Vec2ArrayType ) :
2009-10-09 21:39:11 +08:00
vec2Array = static_cast < const Vec2 * > ( vertices - > getDataPointer ( ) ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec3ArrayType ) :
2009-10-09 21:39:11 +08:00
vec3Array = static_cast < const Vec3 * > ( vertices - > getDataPointer ( ) ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec4ArrayType ) :
2009-10-09 21:39:11 +08:00
vec4Array = static_cast < const Vec4 * > ( vertices - > getDataPointer ( ) ) ;
2003-06-24 23:40:09 +08:00
break ;
2007-12-04 22:46:46 +08:00
case ( Array : : Vec2dArrayType ) :
2009-10-09 21:39:11 +08:00
vec2dArray = static_cast < const Vec2d * > ( vertices - > getDataPointer ( ) ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec3dArrayType ) :
2009-10-09 21:39:11 +08:00
vec3dArray = static_cast < const Vec3d * > ( vertices - > getDataPointer ( ) ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec4dArrayType ) :
2009-10-09 21:39:11 +08:00
vec4dArray = static_cast < const Vec4d * > ( vertices - > getDataPointer ( ) ) ;
2007-12-04 22:46:46 +08:00
break ;
2003-06-24 23:40:09 +08:00
default :
2009-10-09 21:39:11 +08:00
notify ( WARN ) < < " Warning: Geometry::accept(PrimitiveFunctor&) cannot handle Vertex Array type " < < vertices - > getType ( ) < < std : : endl ;
2003-06-24 23:40:09 +08:00
return ;
}
2002-11-06 18:24:33 +08:00
for ( PrimitiveSetList : : const_iterator itr = _primitives . begin ( ) ;
2002-10-08 22:10:55 +08:00
itr ! = _primitives . end ( ) ;
+ + itr )
{
2002-11-06 18:24:33 +08:00
const PrimitiveSet * primitiveset = itr - > get ( ) ;
2002-10-08 22:10:55 +08:00
GLenum mode = primitiveset - > getMode ( ) ;
switch ( primitiveset - > getType ( ) )
{
case ( PrimitiveSet : : DrawArraysPrimitiveType ) :
{
const DrawArrays * drawArray = static_cast < const DrawArrays * > ( primitiveset ) ;
functor . begin ( mode ) ;
unsigned int indexEnd = drawArray - > getFirst ( ) + drawArray - > getCount ( ) ;
for ( unsigned int vindex = drawArray - > getFirst ( ) ;
vindex < indexEnd ;
+ + vindex )
{
2003-06-24 23:40:09 +08:00
switch ( type )
{
case ( Array : : Vec2ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec2Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec3ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec3Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec4ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec4Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
2007-12-04 22:46:46 +08:00
case ( Array : : Vec2dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec2dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec3dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec3dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec4dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec4dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
2003-06-24 23:40:09 +08:00
default :
break ;
}
2002-10-08 22:10:55 +08:00
}
2009-10-09 21:39:11 +08:00
2002-10-08 22:10:55 +08:00
functor . end ( ) ;
break ;
}
case ( PrimitiveSet : : DrawArrayLengthsPrimitiveType ) :
{
const DrawArrayLengths * drawArrayLengths = static_cast < const DrawArrayLengths * > ( primitiveset ) ;
unsigned int vindex = drawArrayLengths - > getFirst ( ) ;
for ( DrawArrayLengths : : const_iterator primItr = drawArrayLengths - > begin ( ) ;
primItr ! = drawArrayLengths - > end ( ) ;
+ + primItr )
{
functor . begin ( mode ) ;
for ( GLsizei primCount = 0 ; primCount < * primItr ; + + primCount )
{
2003-06-24 23:40:09 +08:00
switch ( type )
{
case ( Array : : Vec2ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec2Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec3ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec3Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec4ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec4Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
2007-12-04 22:46:46 +08:00
case ( Array : : Vec2dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec2dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec3dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec3dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec4dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec4dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
2003-06-24 23:40:09 +08:00
default :
break ;
}
2002-10-08 22:10:55 +08:00
+ + vindex ;
}
2009-10-09 21:39:11 +08:00
2002-10-08 22:10:55 +08:00
functor . end ( ) ;
}
break ;
}
case ( PrimitiveSet : : DrawElementsUBytePrimitiveType ) :
{
const DrawElementsUByte * drawElements = static_cast < const DrawElementsUByte * > ( primitiveset ) ;
functor . begin ( mode ) ;
unsigned int primCount = 0 ;
for ( DrawElementsUByte : : const_iterator primItr = drawElements - > begin ( ) ;
primItr ! = drawElements - > end ( ) ;
+ + primCount , + + primItr )
{
unsigned int vindex = * primItr ;
2003-06-24 23:40:09 +08:00
switch ( type )
{
case ( Array : : Vec2ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec2Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec3ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec3Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec4ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec4Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
2007-12-04 22:46:46 +08:00
case ( Array : : Vec2dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec2dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec3dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec3dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec4dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec4dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
2003-06-24 23:40:09 +08:00
default :
break ;
}
2002-10-08 22:10:55 +08:00
}
functor . end ( ) ;
break ;
}
case ( PrimitiveSet : : DrawElementsUShortPrimitiveType ) :
{
const DrawElementsUShort * drawElements = static_cast < const DrawElementsUShort * > ( primitiveset ) ;
functor . begin ( mode ) ;
for ( DrawElementsUShort : : const_iterator primItr = drawElements - > begin ( ) ;
primItr ! = drawElements - > end ( ) ;
+ + primItr )
{
unsigned int vindex = * primItr ;
2003-06-24 23:40:09 +08:00
switch ( type )
{
case ( Array : : Vec2ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec2Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec3ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec3Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec4ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec4Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
2007-12-04 22:46:46 +08:00
case ( Array : : Vec2dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec2dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec3dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec3dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec4dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec4dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
2003-06-24 23:40:09 +08:00
default :
break ;
}
2002-10-08 22:10:55 +08:00
}
functor . end ( ) ;
break ;
}
case ( PrimitiveSet : : DrawElementsUIntPrimitiveType ) :
{
const DrawElementsUInt * drawElements = static_cast < const DrawElementsUInt * > ( primitiveset ) ;
functor . begin ( mode ) ;
for ( DrawElementsUInt : : const_iterator primItr = drawElements - > begin ( ) ;
primItr ! = drawElements - > end ( ) ;
+ + primItr )
{
unsigned int vindex = * primItr ;
2003-06-24 23:40:09 +08:00
switch ( type )
{
case ( Array : : Vec2ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec2Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec3ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec3Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
case ( Array : : Vec4ArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec4Array [ _vertexData . indices - > index ( vindex ) ] ) ;
2003-06-24 23:40:09 +08:00
break ;
2007-12-04 22:46:46 +08:00
case ( Array : : Vec2dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec2dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec3dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec3dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec4dArrayType ) :
2007-12-11 23:55:02 +08:00
functor . vertex ( vec4dArray [ _vertexData . indices - > index ( vindex ) ] ) ;
2007-12-04 22:46:46 +08:00
break ;
2003-06-24 23:40:09 +08:00
default :
break ;
}
2002-10-08 22:10:55 +08:00
}
functor . end ( ) ;
break ;
}
default :
{
break ;
}
}
}
2002-11-06 18:24:33 +08:00
}
return ;
2002-06-26 04:27:51 +08:00
}
2004-03-15 05:54:17 +08:00
void Geometry : : accept ( PrimitiveIndexFunctor & functor ) const
{
2009-10-09 21:39:11 +08:00
const osg : : Array * vertices = _vertexData . array . get ( ) ;
const osg : : IndexArray * indices = _vertexData . indices . get ( ) ;
if ( ! vertices & & _vertexAttribList . size ( ) > 0 )
{
osg : : notify ( osg : : INFO ) < < " Geometry::accept(PrimitiveIndexFunctor& functor): Using vertex attribute instead " < < std : : endl ;
vertices = _vertexAttribList [ 0 ] . array . get ( ) ;
indices = _vertexAttribList [ 0 ] . indices . get ( ) ;
}
if ( ! vertices | | vertices - > getNumElements ( ) = = 0 ) return ;
2004-03-15 05:54:17 +08:00
2009-10-09 21:39:11 +08:00
switch ( vertices - > getType ( ) )
2004-03-15 05:54:17 +08:00
{
case ( Array : : Vec2ArrayType ) :
2009-10-09 21:39:11 +08:00
functor . setVertexArray ( vertices - > getNumElements ( ) , static_cast < const Vec2 * > ( vertices - > getDataPointer ( ) ) ) ;
2004-03-15 05:54:17 +08:00
break ;
case ( Array : : Vec3ArrayType ) :
2009-10-09 21:39:11 +08:00
functor . setVertexArray ( vertices - > getNumElements ( ) , static_cast < const Vec3 * > ( vertices - > getDataPointer ( ) ) ) ;
2004-03-15 05:54:17 +08:00
break ;
case ( Array : : Vec4ArrayType ) :
2009-10-09 21:39:11 +08:00
functor . setVertexArray ( vertices - > getNumElements ( ) , static_cast < const Vec4 * > ( vertices - > getDataPointer ( ) ) ) ;
2004-03-15 05:54:17 +08:00
break ;
2007-12-04 22:46:46 +08:00
case ( Array : : Vec2dArrayType ) :
2009-10-09 21:39:11 +08:00
functor . setVertexArray ( vertices - > getNumElements ( ) , static_cast < const Vec2d * > ( vertices - > getDataPointer ( ) ) ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec3dArrayType ) :
2009-10-09 21:39:11 +08:00
functor . setVertexArray ( vertices - > getNumElements ( ) , static_cast < const Vec3d * > ( vertices - > getDataPointer ( ) ) ) ;
2007-12-04 22:46:46 +08:00
break ;
case ( Array : : Vec4dArrayType ) :
2009-10-09 21:39:11 +08:00
functor . setVertexArray ( vertices - > getNumElements ( ) , static_cast < const Vec4d * > ( vertices - > getDataPointer ( ) ) ) ;
2007-12-04 22:46:46 +08:00
break ;
2004-03-15 05:54:17 +08:00
default :
2009-10-09 21:39:11 +08:00
notify ( WARN ) < < " Warning: Geometry::accept(PrimitiveIndexFunctor&) cannot handle Vertex Array type " < < vertices - > getType ( ) < < std : : endl ;
2004-03-15 05:54:17 +08:00
return ;
}
if ( ! _vertexData . indices . valid ( ) )
{
for ( PrimitiveSetList : : const_iterator itr = _primitives . begin ( ) ;
itr ! = _primitives . end ( ) ;
+ + itr )
{
( * itr ) - > accept ( functor ) ;
}
}
else
{
for ( PrimitiveSetList : : const_iterator itr = _primitives . begin ( ) ;
itr ! = _primitives . end ( ) ;
+ + itr )
{
const PrimitiveSet * primitiveset = itr - > get ( ) ;
GLenum mode = primitiveset - > getMode ( ) ;
switch ( primitiveset - > getType ( ) )
{
case ( PrimitiveSet : : DrawArraysPrimitiveType ) :
{
const DrawArrays * drawArray = static_cast < const DrawArrays * > ( primitiveset ) ;
functor . begin ( mode ) ;
unsigned int indexEnd = drawArray - > getFirst ( ) + drawArray - > getCount ( ) ;
for ( unsigned int vindex = drawArray - > getFirst ( ) ;
vindex < indexEnd ;
+ + vindex )
{
functor . vertex ( _vertexData . indices - > index ( vindex ) ) ;
}
functor . end ( ) ;
break ;
}
case ( PrimitiveSet : : DrawArrayLengthsPrimitiveType ) :
{
const DrawArrayLengths * drawArrayLengths = static_cast < const DrawArrayLengths * > ( primitiveset ) ;
unsigned int vindex = drawArrayLengths - > getFirst ( ) ;
for ( DrawArrayLengths : : const_iterator primItr = drawArrayLengths - > begin ( ) ;
primItr ! = drawArrayLengths - > end ( ) ;
+ + primItr )
{
functor . begin ( mode ) ;
for ( GLsizei primCount = 0 ; primCount < * primItr ; + + primCount )
{
functor . vertex ( _vertexData . indices - > index ( vindex ) ) ;
+ + vindex ;
}
functor . end ( ) ;
}
break ;
}
case ( PrimitiveSet : : DrawElementsUBytePrimitiveType ) :
{
const DrawElementsUByte * drawElements = static_cast < const DrawElementsUByte * > ( primitiveset ) ;
functor . begin ( mode ) ;
unsigned int primCount = 0 ;
for ( DrawElementsUByte : : const_iterator primItr = drawElements - > begin ( ) ;
primItr ! = drawElements - > end ( ) ;
+ + primCount , + + primItr )
{
unsigned int vindex = * primItr ;
functor . vertex ( _vertexData . indices - > index ( vindex ) ) ;
}
functor . end ( ) ;
break ;
}
case ( PrimitiveSet : : DrawElementsUShortPrimitiveType ) :
{
const DrawElementsUShort * drawElements = static_cast < const DrawElementsUShort * > ( primitiveset ) ;
functor . begin ( mode ) ;
for ( DrawElementsUShort : : const_iterator primItr = drawElements - > begin ( ) ;
primItr ! = drawElements - > end ( ) ;
+ + primItr )
{
unsigned int vindex = * primItr ;
functor . vertex ( _vertexData . indices - > index ( vindex ) ) ;
}
functor . end ( ) ;
break ;
}
case ( PrimitiveSet : : DrawElementsUIntPrimitiveType ) :
{
const DrawElementsUInt * drawElements = static_cast < const DrawElementsUInt * > ( primitiveset ) ;
functor . begin ( mode ) ;
for ( DrawElementsUInt : : const_iterator primItr = drawElements - > begin ( ) ;
primItr ! = drawElements - > end ( ) ;
+ + primItr )
{
unsigned int vindex = * primItr ;
functor . vertex ( _vertexData . indices - > index ( vindex ) ) ;
}
functor . end ( ) ;
break ;
}
default :
{
break ;
}
}
}
}
return ;
}
2003-09-24 23:54:22 +08:00
2008-03-11 21:23:49 +08:00
unsigned int _computeNumberOfPrimitives ( const osg : : Geometry & geom )
2002-07-18 08:53:03 +08:00
{
2003-09-24 23:54:22 +08:00
unsigned int totalNumberOfPrimitives = 0 ;
for ( Geometry : : PrimitiveSetList : : const_iterator itr = geom . getPrimitiveSetList ( ) . begin ( ) ;
itr ! = geom . getPrimitiveSetList ( ) . end ( ) ;
+ + itr )
2002-07-18 08:53:03 +08:00
{
2003-09-24 23:54:22 +08:00
const PrimitiveSet * primitiveset = itr - > get ( ) ;
GLenum mode = primitiveset - > getMode ( ) ;
unsigned int primLength ;
switch ( mode )
{
2004-06-12 05:05:50 +08:00
case ( GL_POINTS ) : primLength = 1 ; osg : : notify ( osg : : INFO ) < < " prim=GL_POINTS " < < std : : endl ; break ;
case ( GL_LINES ) : primLength = 2 ; osg : : notify ( osg : : INFO ) < < " prim=GL_LINES " < < std : : endl ; break ;
case ( GL_TRIANGLES ) : primLength = 3 ; osg : : notify ( osg : : INFO ) < < " prim=GL_TRIANGLES " < < std : : endl ; break ;
case ( GL_QUADS ) : primLength = 4 ; osg : : notify ( osg : : INFO ) < < " prim=GL_QUADS " < < std : : endl ; break ;
default : primLength = 0 ; osg : : notify ( osg : : INFO ) < < " prim= " < < std : : hex < < mode < < std : : dec < < std : : endl ; break ; // compute later when =0.
2003-09-24 23:54:22 +08:00
}
2007-12-11 01:30:18 +08:00
// draw primitives by the more flexible "slow" path,
2003-09-24 23:54:22 +08:00
// sending OpenGL glBegin/glVertex.../glEnd().
switch ( primitiveset - > getType ( ) )
{
case ( PrimitiveSet : : DrawArrayLengthsPrimitiveType ) :
2002-07-18 08:53:03 +08:00
{
2003-09-24 23:54:22 +08:00
const DrawArrayLengths * drawArrayLengths = static_cast < const DrawArrayLengths * > ( primitiveset ) ;
for ( DrawArrayLengths : : const_iterator primItr = drawArrayLengths - > begin ( ) ;
primItr ! = drawArrayLengths - > end ( ) ;
+ + primItr )
{
if ( primLength = = 0 ) totalNumberOfPrimitives + = 1 ;
2004-06-04 16:13:36 +08:00
else totalNumberOfPrimitives + = * primItr / primLength ;
2003-09-24 23:54:22 +08:00
}
break ;
2002-07-18 08:53:03 +08:00
}
2003-09-24 23:54:22 +08:00
default :
{
2004-06-12 05:05:50 +08:00
if ( primLength = = 0 ) { totalNumberOfPrimitives + = 1 ; osg : : notify ( osg : : INFO ) < < " totalNumberOfPrimitives= " < < totalNumberOfPrimitives < < std : : endl ; }
else { totalNumberOfPrimitives + = primitiveset - > getNumIndices ( ) / primLength ; osg : : notify ( osg : : INFO ) < < " primitiveset->getNumIndices()= " < < primitiveset - > getNumIndices ( ) < < " totalNumberOfPrimitives= " < < totalNumberOfPrimitives < < std : : endl ; }
2003-09-24 23:54:22 +08:00
}
}
}
return totalNumberOfPrimitives ;
}
template < class A >
bool _verifyBindings ( const osg : : Geometry & geom , const A & arrayData )
{
2003-09-29 22:07:46 +08:00
unsigned int numElements = arrayData . indices . valid ( ) ? arrayData . indices - > getNumElements ( ) :
arrayData . array . valid ( ) ? arrayData . array - > getNumElements ( ) : 0 ;
2003-09-24 23:54:22 +08:00
switch ( arrayData . binding )
2002-07-18 08:53:03 +08:00
{
2003-09-24 23:54:22 +08:00
case ( osg : : Geometry : : BIND_OFF ) :
2003-09-29 22:07:46 +08:00
if ( numElements > 0 ) return false ;
2002-07-18 08:53:03 +08:00
break ;
2003-09-24 23:54:22 +08:00
case ( osg : : Geometry : : BIND_OVERALL ) :
2003-09-29 22:07:46 +08:00
if ( numElements ! = 1 ) return false ;
2002-07-18 08:53:03 +08:00
break ;
2003-09-24 23:54:22 +08:00
case ( osg : : Geometry : : BIND_PER_PRIMITIVE_SET ) :
2003-09-29 22:07:46 +08:00
if ( numElements ! = geom . getPrimitiveSetList ( ) . size ( ) ) return false ;
2002-07-18 08:53:03 +08:00
break ;
2003-09-24 23:54:22 +08:00
case ( osg : : Geometry : : BIND_PER_PRIMITIVE ) :
2007-12-11 01:30:18 +08:00
if ( numElements ! = _computeNumberOfPrimitives ( geom ) ) return false ;
2003-05-22 23:29:20 +08:00
break ;
2003-09-24 23:54:22 +08:00
case ( osg : : Geometry : : BIND_PER_VERTEX ) :
2003-09-29 22:07:46 +08:00
{
unsigned int numVertices = geom . getVertexIndices ( ) ? geom . getVertexIndices ( ) - > getNumElements ( ) :
geom . getVertexArray ( ) ? geom . getVertexArray ( ) - > getNumElements ( ) : 0 ;
if ( numElements ! = numVertices ) return false ;
2002-07-18 08:53:03 +08:00
break ;
2003-09-29 22:07:46 +08:00
}
2002-07-18 08:53:03 +08:00
}
return true ;
}
2003-09-24 23:54:22 +08:00
template < class A >
2004-08-08 03:08:12 +08:00
void _computeCorrectBindingsAndArraySizes ( std : : ostream & out , const osg : : Geometry & geom , A & arrayData , const char * arrayName )
2002-07-18 08:53:03 +08:00
{
2004-10-07 04:32:09 +08:00
unsigned int numElements = arrayData . indices . valid ( ) ? arrayData . indices - > getNumElements ( ) :
arrayData . array . valid ( ) ? arrayData . array - > getNumElements ( ) : 0 ;
// check to see if binding matches 0 elements required.
if ( numElements = = 0 )
{
// correct binding if not correct.
if ( arrayData . binding ! = osg : : Geometry : : BIND_OFF )
{
out < < " Warning: in osg::Geometry::computeCorrectBindingsAndArraySizes() " < < std : : endl
< < " " < < arrayName < < " binding has been reset to BIND_OFF " < < std : : endl ;
arrayData . binding = osg : : Geometry : : BIND_OFF ;
}
return ;
}
// check to see if binding matches 1 elements required.
if ( numElements = = 1 )
{
// correct binding if not correct.
if ( arrayData . binding ! = osg : : Geometry : : BIND_OVERALL )
{
out < < " Warning: in osg::Geometry::computeCorrectBindingsAndArraySizes() " < < std : : endl
< < " " < < arrayName < < " binding has been reset to BIND_OVERALL " < < std : : endl ;
arrayData . binding = osg : : Geometry : : BIND_OVERALL ;
}
return ;
}
2003-09-29 22:07:46 +08:00
unsigned int numVertices = geom . getVertexIndices ( ) ? geom . getVertexIndices ( ) - > getNumElements ( ) :
geom . getVertexArray ( ) ? geom . getVertexArray ( ) - > getNumElements ( ) : 0 ;
if ( numVertices = = 0 )
2002-07-18 08:53:03 +08:00
{
2003-09-29 22:07:46 +08:00
if ( arrayData . binding ! = osg : : Geometry : : BIND_OFF )
2003-09-24 23:54:22 +08:00
{
arrayData . array = 0 ;
arrayData . indices = 0 ;
arrayData . binding = osg : : Geometry : : BIND_OFF ;
2004-08-08 03:08:12 +08:00
out < < " Warning: in osg::Geometry::computeCorrectBindingsAndArraySizes() vertex array is empty but " < < std : : endl
< < " vertex array is empty but " < < arrayName < < " is set " < < std : : endl
< < " reseting " < < arrayName < < " binding to BIND_OFF and array & indices to 0. " < < std : : endl ;
2003-09-24 23:54:22 +08:00
}
2002-07-18 08:53:03 +08:00
}
2004-10-07 04:32:09 +08:00
if ( numElements = = numVertices )
{
// correct the binding to per vertex.
if ( arrayData . binding ! = osg : : Geometry : : BIND_PER_VERTEX )
{
out < < " Warning: in osg::Geometry::computeCorrectBindingsAndArraySizes() " < < std : : endl
< < " " < < arrayName < < " binding has been reset to BIND_PER_VERTEX " < < std : : endl ;
arrayData . binding = osg : : Geometry : : BIND_PER_VERTEX ;
}
return ;
}
2003-09-24 23:54:22 +08:00
2003-09-29 22:07:46 +08:00
2004-10-07 04:32:09 +08:00
// check to see if binding might be per primitive set
unsigned int numPrimitiveSets = geom . getPrimitiveSetList ( ) . size ( ) ;
if ( numElements = = numPrimitiveSets )
2002-07-18 08:53:03 +08:00
{
2004-10-07 04:32:09 +08:00
if ( arrayData . binding ! = osg : : Geometry : : BIND_PER_PRIMITIVE_SET )
2003-09-24 23:54:22 +08:00
{
2004-10-07 04:32:09 +08:00
out < < " Warning: in osg::Geometry::computeCorrectBindingsAndArraySizes() " < < std : : endl
< < " " < < arrayName < < " binding has been reset to BIND_PER_PRIMITIVE_SET " < < std : : endl ;
arrayData . binding = osg : : Geometry : : BIND_PER_PRIMITIVE_SET ;
2003-09-24 23:54:22 +08:00
}
2004-10-07 04:32:09 +08:00
return ;
}
// check to see if binding might be per primitive
2007-12-11 01:30:18 +08:00
unsigned int numPrimitives = _computeNumberOfPrimitives ( geom ) ;
2004-10-07 04:32:09 +08:00
if ( numElements = = numPrimitives )
{
if ( arrayData . binding ! = osg : : Geometry : : BIND_PER_PRIMITIVE )
{
out < < " Warning: in osg::Geometry::computeCorrectBindingsAndArraySizes() " < < std : : endl
< < " " < < arrayName < < " binding has been reset to BIND_PER_PRIMITIVE " < < std : : endl ;
arrayData . binding = osg : : Geometry : : BIND_PER_PRIMITIVE ;
}
return ;
}
if ( numElements > numVertices )
{
arrayData . binding = osg : : Geometry : : BIND_PER_VERTEX ;
return ;
}
if ( numElements > numPrimitives )
{
arrayData . binding = osg : : Geometry : : BIND_PER_PRIMITIVE ;
return ;
}
if ( numElements > numPrimitiveSets )
{
arrayData . binding = osg : : Geometry : : BIND_PER_PRIMITIVE_SET ;
return ;
}
if ( numElements > = 1 )
{
arrayData . binding = osg : : Geometry : : BIND_OVERALL ;
return ;
}
arrayData . binding = osg : : Geometry : : BIND_OFF ;
2003-09-24 23:54:22 +08:00
}
bool Geometry : : verifyBindings ( const ArrayData & arrayData ) const
{
return _verifyBindings ( * this , arrayData ) ;
}
bool Geometry : : verifyBindings ( const Vec3ArrayData & arrayData ) const
{
return _verifyBindings ( * this , arrayData ) ;
}
void Geometry : : computeCorrectBindingsAndArraySizes ( ArrayData & arrayData , const char * arrayName )
{
2004-08-08 03:08:12 +08:00
_computeCorrectBindingsAndArraySizes ( osg : : notify ( osg : : INFO ) , * this , arrayData , arrayName ) ;
2003-09-24 23:54:22 +08:00
}
void Geometry : : computeCorrectBindingsAndArraySizes ( Vec3ArrayData & arrayData , const char * arrayName )
{
2004-08-08 03:08:12 +08:00
_computeCorrectBindingsAndArraySizes ( osg : : notify ( osg : : INFO ) , * this , arrayData , arrayName ) ;
2003-09-24 23:54:22 +08:00
}
bool Geometry : : verifyBindings ( ) const
{
if ( ! verifyBindings ( _normalData ) ) return false ;
if ( ! verifyBindings ( _colorData ) ) return false ;
if ( ! verifyBindings ( _secondaryColorData ) ) return false ;
if ( ! verifyBindings ( _fogCoordData ) ) return false ;
2007-04-27 22:52:30 +08:00
for ( ArrayDataList : : const_iterator titr = _texCoordList . begin ( ) ;
2003-09-24 23:54:22 +08:00
titr ! = _texCoordList . end ( ) ;
+ + titr )
{
if ( ! verifyBindings ( * titr ) ) return false ;
}
2007-04-27 22:52:30 +08:00
for ( ArrayDataList : : const_iterator vitr = _vertexAttribList . begin ( ) ;
2003-09-24 23:54:22 +08:00
vitr ! = _vertexAttribList . end ( ) ;
+ + vitr )
{
if ( ! verifyBindings ( * vitr ) ) return false ;
}
return true ;
}
void Geometry : : computeCorrectBindingsAndArraySizes ( )
{
2004-10-07 04:32:09 +08:00
// if (verifyBindings()) return;
2002-07-18 08:53:03 +08:00
2003-09-24 23:54:22 +08:00
computeCorrectBindingsAndArraySizes ( _normalData , " _normalData " ) ;
computeCorrectBindingsAndArraySizes ( _colorData , " _colorData " ) ;
computeCorrectBindingsAndArraySizes ( _secondaryColorData , " _secondaryColorData " ) ;
computeCorrectBindingsAndArraySizes ( _fogCoordData , " _fogCoordData " ) ;
2007-04-27 22:52:30 +08:00
for ( ArrayDataList : : iterator titr = _texCoordList . begin ( ) ;
2003-09-24 23:54:22 +08:00
titr ! = _texCoordList . end ( ) ;
+ + titr )
{
computeCorrectBindingsAndArraySizes ( * titr , " _texCoordList[] " ) ;
}
2007-04-27 22:52:30 +08:00
for ( ArrayDataList : : iterator vitr = _vertexAttribList . begin ( ) ;
2003-09-24 23:54:22 +08:00
vitr ! = _vertexAttribList . end ( ) ;
+ + vitr )
{
computeCorrectBindingsAndArraySizes ( * vitr , " _vertAttribList[] " ) ;
}
2002-07-18 08:53:03 +08:00
}
2003-05-07 21:13:13 +08:00
2003-08-08 08:21:30 +08:00
class ExpandIndexedArray : public osg : : ConstArrayVisitor
{
public :
ExpandIndexedArray ( const osg : : IndexArray & indices , Array * targetArray ) :
_indices ( indices ) ,
_targetArray ( targetArray ) { }
2003-12-05 01:14:06 +08:00
virtual ~ ExpandIndexedArray ( ) { }
2007-12-11 23:55:02 +08:00
// Create when both of the arrays are predefined templated classes. We
// can do some optimizations in this case that aren't possible in the general
// case.
2003-08-08 08:21:30 +08:00
template < class T , class I >
2007-12-11 23:55:02 +08:00
T * create_inline ( const T & array , const I & indices )
2003-08-08 08:21:30 +08:00
{
T * newArray = 0 ;
2003-12-05 01:14:06 +08:00
// if source array type and target array type are equal but arrays arn't equal
2003-12-05 17:22:03 +08:00
if ( _targetArray & & _targetArray - > getType ( ) = = array . getType ( ) & & _targetArray ! = ( osg : : Array * ) ( & array ) )
2003-08-08 08:21:30 +08:00
{
// reuse exisiting target array
newArray = static_cast < T * > ( _targetArray ) ;
if ( newArray - > size ( ) ! = indices . size ( ) )
{
// make sure its the right size
newArray - > resize ( indices . size ( ) ) ;
}
}
else
{
// else create a new array.
newArray = new T ( indices . size ( ) ) ;
}
for ( unsigned int i = 0 ; i < indices . size ( ) ; + + i )
{
( * newArray ) [ i ] = array [ indices [ i ] ] ;
}
return newArray ;
}
2007-12-11 23:55:02 +08:00
// Create when one of the arrays isn't one of the predefined templated classes. The
// template parameter is the type of the array that will get created. This is always
// one of the predefined classes. We could call clone to get one of the same type as
// the input array, but the interface of the osg::Array class doesn't include a way
// to set an element.
2003-08-08 08:21:30 +08:00
template < class T >
2009-01-07 20:27:45 +08:00
osg : : Array * create_noinline ( const osg : : Array & array , const osg : : IndexArray & indices )
{
2007-12-11 23:55:02 +08:00
T * newArray = 0 ;
typedef typename T : : ElementDataType EDT ;
unsigned int num_indices = indices . getNumElements ( ) ;
newArray = new T ( num_indices ) ;
const EDT * src = static_cast < const EDT * > ( array . getDataPointer ( ) ) ;
for ( unsigned int i = 0 ; i < num_indices ; + + i )
{
( * newArray ) [ i ] = src [ indices . index ( i ) ] ;
}
return newArray ;
}
2009-01-07 20:27:45 +08:00
osg : : Array * create_noinline ( const osg : : Array & array , const osg : : IndexArray & indices )
{
switch ( array . getType ( ) )
2007-12-11 23:55:02 +08:00
{
2009-01-07 20:27:45 +08:00
case ( osg : : Array : : ByteArrayType ) : return create_noinline < osg : : ByteArray > ( array , indices ) ;
case ( osg : : Array : : ShortArrayType ) : return create_noinline < osg : : ShortArray > ( array , indices ) ;
case ( osg : : Array : : IntArrayType ) : return create_noinline < osg : : IntArray > ( array , indices ) ;
case ( osg : : Array : : UByteArrayType ) : return create_noinline < osg : : UByteArray > ( array , indices ) ;
case ( osg : : Array : : UShortArrayType ) : return create_noinline < osg : : UShortArray > ( array , indices ) ;
case ( osg : : Array : : UIntArrayType ) : return create_noinline < osg : : UIntArray > ( array , indices ) ;
case ( osg : : Array : : Vec4ubArrayType ) : return create_noinline < osg : : Vec4ubArray > ( array , indices ) ;
case ( osg : : Array : : FloatArrayType ) : return create_noinline < osg : : FloatArray > ( array , indices ) ;
case ( osg : : Array : : Vec2ArrayType ) : return create_noinline < osg : : Vec2Array > ( array , indices ) ;
case ( osg : : Array : : Vec3ArrayType ) : return create_noinline < osg : : Vec3Array > ( array , indices ) ;
case ( osg : : Array : : Vec4ArrayType ) : return create_noinline < osg : : Vec4Array > ( array , indices ) ;
case ( osg : : Array : : Vec2dArrayType ) : return create_noinline < osg : : Vec2dArray > ( array , indices ) ;
case ( osg : : Array : : Vec3dArrayType ) : return create_noinline < osg : : Vec3dArray > ( array , indices ) ;
case ( osg : : Array : : Vec4dArrayType ) : return create_noinline < osg : : Vec4dArray > ( array , indices ) ;
default :
return NULL ;
}
2007-12-11 23:55:02 +08:00
}
template < class TA , class TI >
2009-01-07 20:27:45 +08:00
osg : : Array * create ( const TA & array , const osg : : IndexArray & indices )
{
// We know that indices.getType returned the same thing as TI, but
// we need to determine whether it is really an instance of TI, or
// perhaps another subclass of osg::Array that contains the same
// type of data.
const TI * ba ( dynamic_cast < const TI * > ( & indices ) ) ;
if ( ba ! = NULL ) {
return create_inline ( array , * ba ) ;
}
else {
return create_noinline ( array , _indices ) ;
}
2007-12-11 23:55:02 +08:00
}
template < class T >
osg : : Array * create ( const T & array )
2003-08-08 08:21:30 +08:00
{
switch ( _indices . getType ( ) )
{
2007-12-11 23:55:02 +08:00
case ( osg : : Array : : ByteArrayType ) : return create < T , osg : : ByteArray > ( array , _indices ) ;
case ( osg : : Array : : ShortArrayType ) : return create < T , osg : : ShortArray > ( array , _indices ) ;
case ( osg : : Array : : IntArrayType ) : return create < T , osg : : IntArray > ( array , _indices ) ;
case ( osg : : Array : : UByteArrayType ) : return create < T , osg : : UByteArray > ( array , _indices ) ;
case ( osg : : Array : : UShortArrayType ) : return create < T , osg : : UShortArray > ( array , _indices ) ;
case ( osg : : Array : : UIntArrayType ) : return create < T , osg : : UIntArray > ( array , _indices ) ;
2009-01-07 20:27:45 +08:00
default : return create_noinline ( array , _indices ) ;
2003-08-08 08:21:30 +08:00
}
}
2007-12-11 23:55:02 +08:00
// applys for the predefined classes go through 1-arg create to do indexing
2003-08-08 08:21:30 +08:00
virtual void apply ( const osg : : ByteArray & array ) { _targetArray = create ( array ) ; }
virtual void apply ( const osg : : ShortArray & array ) { _targetArray = create ( array ) ; }
virtual void apply ( const osg : : IntArray & array ) { _targetArray = create ( array ) ; }
virtual void apply ( const osg : : UByteArray & array ) { _targetArray = create ( array ) ; }
virtual void apply ( const osg : : UShortArray & array ) { _targetArray = create ( array ) ; }
virtual void apply ( const osg : : UIntArray & array ) { _targetArray = create ( array ) ; }
2005-07-15 22:41:19 +08:00
virtual void apply ( const osg : : Vec4ubArray & array ) { _targetArray = create ( array ) ; }
2003-08-08 08:21:30 +08:00
virtual void apply ( const osg : : FloatArray & array ) { _targetArray = create ( array ) ; }
virtual void apply ( const osg : : Vec2Array & array ) { _targetArray = create ( array ) ; }
virtual void apply ( const osg : : Vec3Array & array ) { _targetArray = create ( array ) ; }
virtual void apply ( const osg : : Vec4Array & array ) { _targetArray = create ( array ) ; }
2007-12-11 23:55:02 +08:00
// other subclasses of osg::Array end up here
virtual void apply ( const osg : : Array & array ) { _targetArray = create_noinline ( array , _indices ) ; }
2003-08-08 08:21:30 +08:00
const osg : : IndexArray & _indices ;
osg : : Array * _targetArray ;
2009-01-07 20:27:45 +08:00
protected :
ExpandIndexedArray & operator = ( const ExpandIndexedArray & ) { return * this ; }
2003-08-08 08:21:30 +08:00
} ;
bool Geometry : : suitableForOptimization ( ) const
{
bool hasIndices = false ;
if ( getVertexIndices ( ) ) hasIndices = true ;
if ( getNormalIndices ( ) ) hasIndices = true ;
if ( getColorIndices ( ) ) hasIndices = true ;
if ( getSecondaryColorIndices ( ) ) hasIndices = true ;
if ( getFogCoordIndices ( ) ) hasIndices = true ;
for ( unsigned int ti = 0 ; ti < getNumTexCoordArrays ( ) ; + + ti )
{
if ( getTexCoordIndices ( ti ) ) hasIndices = true ;
}
for ( unsigned int vi = 0 ; vi < getNumVertexAttribArrays ( ) ; + + vi )
{
if ( getVertexAttribIndices ( vi ) ) hasIndices = true ;
}
return hasIndices ;
}
void Geometry : : copyToAndOptimize ( Geometry & target )
{
2003-12-05 01:14:06 +08:00
bool copyToSelf = ( this = = & target ) ;
2003-08-08 08:21:30 +08:00
// copy over primitive sets.
2003-12-05 01:14:06 +08:00
if ( ! copyToSelf ) target . getPrimitiveSetList ( ) = getPrimitiveSetList ( ) ;
2003-08-08 08:21:30 +08:00
// copy over attribute arrays.
2009-03-11 19:58:31 +08:00
if ( getVertexIndices ( ) & & getVertexArray ( ) )
2003-08-08 08:21:30 +08:00
{
ExpandIndexedArray eia ( * ( getVertexIndices ( ) ) , target . getVertexArray ( ) ) ;
getVertexArray ( ) - > accept ( eia ) ;
target . setVertexArray ( eia . _targetArray ) ;
target . setVertexIndices ( 0 ) ;
}
else if ( getVertexArray ( ) )
{
2003-12-05 01:14:06 +08:00
if ( ! copyToSelf ) target . setVertexArray ( getVertexArray ( ) ) ;
2003-08-08 08:21:30 +08:00
}
target . setNormalBinding ( getNormalBinding ( ) ) ;
2009-03-11 19:58:31 +08:00
if ( getNormalIndices ( ) & & getNormalArray ( ) )
2003-08-08 08:21:30 +08:00
{
ExpandIndexedArray eia ( * ( getNormalIndices ( ) ) , target . getNormalArray ( ) ) ;
getNormalArray ( ) - > accept ( eia ) ;
target . setNormalArray ( dynamic_cast < osg : : Vec3Array * > ( eia . _targetArray ) ) ;
target . setNormalIndices ( 0 ) ;
}
else if ( getNormalArray ( ) )
{
2003-12-05 01:14:06 +08:00
if ( ! copyToSelf ) target . setNormalArray ( getNormalArray ( ) ) ;
2003-08-08 08:21:30 +08:00
}
target . setColorBinding ( getColorBinding ( ) ) ;
2009-03-11 19:58:31 +08:00
if ( getColorIndices ( ) & & getColorArray ( ) )
2003-08-08 08:21:30 +08:00
{
ExpandIndexedArray eia ( * ( getColorIndices ( ) ) , target . getColorArray ( ) ) ;
getColorArray ( ) - > accept ( eia ) ;
target . setColorArray ( eia . _targetArray ) ;
target . setColorIndices ( 0 ) ;
}
else if ( getColorArray ( ) )
{
2003-12-05 01:14:06 +08:00
if ( ! copyToSelf ) target . setColorArray ( getColorArray ( ) ) ;
2003-08-08 08:21:30 +08:00
}
target . setSecondaryColorBinding ( getSecondaryColorBinding ( ) ) ;
2009-03-11 19:58:31 +08:00
if ( getSecondaryColorIndices ( ) & & getSecondaryColorArray ( ) )
2003-08-08 08:21:30 +08:00
{
ExpandIndexedArray eia ( * ( getSecondaryColorIndices ( ) ) , target . getSecondaryColorArray ( ) ) ;
getSecondaryColorArray ( ) - > accept ( eia ) ;
target . setSecondaryColorArray ( eia . _targetArray ) ;
target . setSecondaryColorIndices ( 0 ) ;
}
else if ( getSecondaryColorArray ( ) )
{
2003-12-05 01:14:06 +08:00
if ( ! copyToSelf ) target . setSecondaryColorArray ( getSecondaryColorArray ( ) ) ;
2003-08-08 08:21:30 +08:00
}
target . setFogCoordBinding ( getFogCoordBinding ( ) ) ;
2009-03-11 19:58:31 +08:00
if ( getFogCoordIndices ( ) & & getFogCoordArray ( ) )
2003-08-08 08:21:30 +08:00
{
ExpandIndexedArray eia ( * ( getFogCoordIndices ( ) ) , target . getFogCoordArray ( ) ) ;
getFogCoordArray ( ) - > accept ( eia ) ;
target . setFogCoordArray ( eia . _targetArray ) ;
target . setFogCoordIndices ( 0 ) ;
}
else if ( getFogCoordArray ( ) )
{
2003-12-05 01:14:06 +08:00
if ( ! copyToSelf ) target . setFogCoordArray ( getFogCoordArray ( ) ) ;
2003-08-08 08:21:30 +08:00
}
for ( unsigned int ti = 0 ; ti < getNumTexCoordArrays ( ) ; + + ti )
{
2009-03-11 19:58:31 +08:00
if ( getTexCoordIndices ( ti ) & & getTexCoordArray ( ti ) )
2003-08-08 08:21:30 +08:00
{
ExpandIndexedArray eia ( * ( getTexCoordIndices ( ti ) ) , target . getTexCoordArray ( ti ) ) ;
2009-03-11 19:58:31 +08:00
2003-08-08 08:21:30 +08:00
getTexCoordArray ( ti ) - > accept ( eia ) ;
target . setTexCoordArray ( ti , eia . _targetArray ) ;
target . setTexCoordIndices ( ti , 0 ) ;
}
else if ( getTexCoordArray ( ti ) )
{
2003-12-05 01:14:06 +08:00
if ( ! copyToSelf ) target . setTexCoordArray ( ti , getTexCoordArray ( ti ) ) ;
2003-08-08 08:21:30 +08:00
}
}
2003-09-10 06:18:35 +08:00
for ( unsigned int vi = 0 ; vi < _vertexAttribList . size ( ) ; + + vi )
2003-08-08 08:21:30 +08:00
{
2003-09-10 06:18:35 +08:00
ArrayData & arrayData = _vertexAttribList [ vi ] ;
if ( arrayData . indices . valid ( ) )
2003-08-08 08:21:30 +08:00
{
2003-09-10 06:18:35 +08:00
ExpandIndexedArray eia ( * arrayData . indices , target . getVertexAttribArray ( vi ) ) ;
arrayData . array - > accept ( eia ) ;
target . setVertexAttribData ( vi , ArrayData ( eia . _targetArray , 0 , arrayData . binding , arrayData . normalize ) ) ;
2003-08-08 08:21:30 +08:00
}
2003-09-10 06:18:35 +08:00
else if ( arrayData . array . valid ( ) )
2003-08-08 08:21:30 +08:00
{
2003-12-05 01:14:06 +08:00
if ( ! copyToSelf ) target . setVertexAttribData ( vi , arrayData ) ;
2003-08-08 08:21:30 +08:00
}
}
}
2008-09-14 18:31:27 +08:00
bool Geometry : : containsSharedArrays ( ) const
{
unsigned int numSharedArrays = 0 ;
if ( getVertexArray ( ) & & getVertexArray ( ) - > referenceCount ( ) > 1 ) + + numSharedArrays ;
if ( getNormalArray ( ) & & getNormalArray ( ) - > referenceCount ( ) > 1 ) + + numSharedArrays ;
if ( getColorArray ( ) & & getColorArray ( ) - > referenceCount ( ) > 1 ) + + numSharedArrays ;
if ( getSecondaryColorArray ( ) & & getSecondaryColorArray ( ) - > referenceCount ( ) > 1 ) + + numSharedArrays ;
if ( getFogCoordArray ( ) & & getFogCoordArray ( ) - > referenceCount ( ) > 1 ) + + numSharedArrays ;
for ( unsigned int ti = 0 ; ti < getNumTexCoordArrays ( ) ; + + ti )
{
if ( getTexCoordArray ( ti ) & & getTexCoordArray ( ti ) - > referenceCount ( ) > 1 ) + + numSharedArrays ;
}
for ( unsigned int vi = 0 ; vi < _vertexAttribList . size ( ) ; + + vi )
{
const ArrayData & arrayData = _vertexAttribList [ vi ] ;
if ( arrayData . array . valid ( ) & & arrayData . array - > referenceCount ( ) > 1 ) + + numSharedArrays ;
}
return numSharedArrays ! = 0 ;
}
void Geometry : : duplicateSharedArrays ( )
{
# define DUPLICATE_IF_REQUIRED(A) \
if ( get # # A ( ) & & get # # A ( ) - > referenceCount ( ) > 1 ) \
{ \
set # # A ( dynamic_cast < osg : : Array * > ( get # # A ( ) - > clone ( osg : : CopyOp : : DEEP_COPY_ARRAYS ) ) ) ; \
}
DUPLICATE_IF_REQUIRED ( VertexArray )
DUPLICATE_IF_REQUIRED ( NormalArray )
DUPLICATE_IF_REQUIRED ( ColorArray )
DUPLICATE_IF_REQUIRED ( SecondaryColorArray )
DUPLICATE_IF_REQUIRED ( FogCoordArray )
for ( unsigned int ti = 0 ; ti < getNumTexCoordArrays ( ) ; + + ti )
{
if ( getTexCoordArray ( ti ) & & getTexCoordArray ( ti ) - > referenceCount ( ) > 1 )
{
setTexCoordArray ( ti , dynamic_cast < osg : : Array * > ( getTexCoordArray ( ti ) - > clone ( osg : : CopyOp : : DEEP_COPY_ARRAYS ) ) ) ;
}
}
for ( unsigned int vi = 0 ; vi < _vertexAttribList . size ( ) ; + + vi )
{
ArrayData & arrayData = _vertexAttribList [ vi ] ;
if ( arrayData . array . valid ( ) & & arrayData . array - > referenceCount ( ) > 1 )
{
arrayData . array = dynamic_cast < osg : : Array * > ( arrayData . array - > clone ( osg : : CopyOp : : DEEP_COPY_ARRAYS ) ) ;
}
}
}
2003-08-08 08:21:30 +08:00
void Geometry : : computeInternalOptimizedGeometry ( )
{
if ( suitableForOptimization ( ) )
{
if ( ! _internalOptimizedGeometry ) _internalOptimizedGeometry = new Geometry ;
copyToAndOptimize ( * _internalOptimizedGeometry ) ;
}
}
2003-06-25 05:57:13 +08:00
2004-07-12 09:01:00 +08:00
Geometry * osg : : createTexturedQuadGeometry ( const Vec3 & corner , const Vec3 & widthVec , const Vec3 & heightVec , float l , float b , float r , float t )
2003-06-25 05:57:13 +08:00
{
Geometry * geom = new Geometry ;
Vec3Array * coords = new Vec3Array ( 4 ) ;
( * coords ) [ 0 ] = corner + heightVec ;
( * coords ) [ 1 ] = corner ;
( * coords ) [ 2 ] = corner + widthVec ;
( * coords ) [ 3 ] = corner + widthVec + heightVec ;
geom - > setVertexArray ( coords ) ;
Vec2Array * tcoords = new Vec2Array ( 4 ) ;
2004-07-12 09:01:00 +08:00
( * tcoords ) [ 0 ] . set ( l , t ) ;
( * tcoords ) [ 1 ] . set ( l , b ) ;
( * tcoords ) [ 2 ] . set ( r , b ) ;
( * tcoords ) [ 3 ] . set ( r , t ) ;
2003-06-25 05:57:13 +08:00
geom - > setTexCoordArray ( 0 , tcoords ) ;
osg : : Vec4Array * colours = new osg : : Vec4Array ( 1 ) ;
( * colours ) [ 0 ] . set ( 1.0f , 1.0f , 1.0 , 1.0f ) ;
geom - > setColorArray ( colours ) ;
geom - > setColorBinding ( Geometry : : BIND_OVERALL ) ;
osg : : Vec3Array * normals = new osg : : Vec3Array ( 1 ) ;
( * normals ) [ 0 ] = widthVec ^ heightVec ;
( * normals ) [ 0 ] . normalize ( ) ;
geom - > setNormalArray ( normals ) ;
geom - > setNormalBinding ( Geometry : : BIND_OVERALL ) ;
geom - > addPrimitiveSet ( new DrawArrays ( PrimitiveSet : : QUADS , 0 , 4 ) ) ;
return geom ;
}
2003-09-01 06:08:22 +08:00
///////////////////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////////////////////
// experimental templated rendering code, please ignore...
// will move to osg::Geometry once complete.
// Robert Osfield, August 2003.
#if 0
2003-09-24 23:54:22 +08:00
struct DrawAttributeArrays
{
virtual bool valid ( ) const = 0 ;
virtual void set ( osg : : Geometry * geometry ) = 0 ;
virtual unsigned int draw ( unsigned int index , unsigned int count ) const = 0 ;
} ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
struct V3
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
V3 ( ) : _array ( 0 ) { }
bool valid ( ) const { return _array ! = 0 ; }
void set ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
_array = 0 ;
osg : : Array * array = geometry - > getVertexArray ( ) ;
if ( array & & array - > getType ( ) = = osg : : Array : : Vec3ArrayType )
{
osg : : Vec3Array * vec3array = static_cast < osg : : Vec3Array * > ( array ) ;
if ( ! vec3array - > empty ( ) ) _array = & ( vec3array - > front ( ) ) ;
}
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
inline void draw ( unsigned int index ) const
{
glVertex3fv ( _array [ index ] . ptr ( ) ) ;
}
osg : : Vec3 * _array ;
} ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
struct V3USI
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
V3USI ( ) : _array ( 0 ) , _indices ( 0 ) { }
bool valid ( ) const { return _array ! = 0 & & _indices ! = 0 ; }
void set ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
_array = 0 ;
osg : : Array * array = geometry - > getVertexArray ( ) ;
if ( array & & array - > getType ( ) = = osg : : Array : : Vec3ArrayType )
{
osg : : Vec3Array * vec3array = static_cast < osg : : Vec3Array * > ( array ) ;
if ( ! vec3array - > empty ( ) ) _array = & ( vec3array - > front ( ) ) ;
}
_indices = 0 ;
osg : : IndexArray * indices = geometry - > getVertexIndices ( ) ;
if ( indices & & indices - > getType ( ) = = osg : : Array : : UShortArrayType )
{
osg : : UShortArray * ushort3array = static_cast < osg : : UShortArray * > ( array ) ;
if ( ! ushort3array - > empty ( ) ) _indices = & ( ushort3array - > front ( ) ) ;
}
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
inline void draw ( unsigned int index ) const
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
glVertex3fv ( _array [ _indices [ index ] ] . ptr ( ) ) ;
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
osg : : Vec3 * _array ;
unsigned short * _indices ;
} ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
//////////////////////////////
struct N3
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
N3 ( ) : _array ( 0 ) { }
bool valid ( ) const { return _array ! = 0 ; }
void set ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
_array = 0 ;
osg : : Array * array = geometry - > getVertexArray ( ) ;
if ( array & & array - > getType ( ) = = osg : : Array : : Vec3ArrayType )
{
osg : : Vec3Array * vec3array = static_cast < osg : : Vec3Array * > ( array ) ;
if ( ! vec3array - > empty ( ) ) _array = & ( vec3array - > front ( ) ) ;
}
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
inline void draw ( unsigned int index ) const
{
glNormal3fv ( _array [ index ] . ptr ( ) ) ;
}
osg : : Vec3 * _array ;
} ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
struct N3USI
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
N3USI ( ) : _array ( 0 ) , _indices ( 0 ) { }
bool valid ( ) const { return _array ! = 0 & & _indices ! = 0 ; }
void set ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
_array = 0 ;
osg : : Array * array = geometry - > getVertexArray ( ) ;
if ( array & & array - > getType ( ) = = osg : : Array : : Vec3ArrayType )
{
osg : : Vec3Array * vec3array = static_cast < osg : : Vec3Array * > ( array ) ;
if ( ! vec3array - > empty ( ) ) _array = & ( vec3array - > front ( ) ) ;
}
_indices = 0 ;
osg : : IndexArray * indices = geometry - > getVertexIndices ( ) ;
if ( indices & & indices - > getType ( ) = = osg : : Array : : UShortArrayType )
{
osg : : UShortArray * ushortarray = static_cast < osg : : UShortArray * > ( array ) ;
if ( ! ushortarray - > empty ( ) ) _indices = & ( ushortarray - > front ( ) ) ;
}
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
inline void draw ( unsigned int index ) const
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
glNormal3fv ( _array [ _indices [ index ] ] . ptr ( ) ) ;
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
osg : : Vec3 * _array ;
unsigned short * _indices ;
} ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
//////////////////////////////
struct C4
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
C4 ( ) : _array ( 0 ) { }
bool valid ( ) const { return _array ! = 0 ; }
void set ( osg : : Geometry * geometry )
{
_array = 0 ;
osg : : Array * array = geometry - > getColorArray ( ) ;
if ( array & & array - > getType ( ) = = osg : : Array : : Vec4ArrayType )
{
osg : : Vec4Array * vec4array = static_cast < osg : : Vec4Array * > ( array ) ;
if ( ! vec4array - > empty ( ) ) _array = & ( vec4array - > front ( ) ) ;
}
}
inline void draw ( unsigned int index ) const
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
glVertex3fv ( _array [ index ] . ptr ( ) ) ;
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
osg : : Vec4 * _array ;
} ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
struct C4USI
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
C4USI ( ) : _array ( 0 ) , _indices ( 0 ) { }
bool valid ( ) const { return _array ! = 0 & & _indices ! = 0 ; }
void set ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
_array = 0 ;
osg : : Array * array = geometry - > getColorArray ( ) ;
if ( array & & array - > getType ( ) = = osg : : Array : : Vec4ArrayType )
{
osg : : Vec4Array * vec4array = static_cast < osg : : Vec4Array * > ( array ) ;
if ( ! vec4array - > empty ( ) ) _array = & ( vec4array - > front ( ) ) ;
}
_indices = 0 ;
osg : : IndexArray * indices = geometry - > getColorIndices ( ) ;
if ( indices & & indices - > getType ( ) = = osg : : Array : : UShortArrayType )
{
osg : : UShortArray * ushortarray = static_cast < osg : : UShortArray * > ( array ) ;
if ( ! ushortarray - > empty ( ) ) _indices = & ( ushortarray - > front ( ) ) ;
}
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
inline void draw ( unsigned int index ) const
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
glColor4fv ( _array [ _indices [ index ] ] . ptr ( ) ) ;
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
osg : : Vec4 * _array ;
unsigned short * _indices ;
} ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
//////////////////////////////
struct T2
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
T2 ( ) : _array ( 0 ) { }
bool valid ( ) const { return _array ! = 0 ; }
void set ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
_array = 0 ;
osg : : Array * array = geometry - > getTexCoordArray ( 0 ) ;
if ( array & & array - > getType ( ) = = osg : : Array : : Vec2ArrayType )
{
osg : : Vec2Array * vec2array = static_cast < osg : : Vec2Array * > ( array ) ;
if ( ! vec2array - > empty ( ) ) _array = & ( vec2array - > front ( ) ) ;
}
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
inline void draw ( unsigned int index ) const
{
glTexCoord2fv ( _array [ index ] . ptr ( ) ) ;
}
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
osg : : Vec2 * _array ;
} ;
struct T2USI
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
T2USI ( ) : _array ( 0 ) , _indices ( 0 ) { }
bool valid ( ) const { return _array ! = 0 & & _indices ! = 0 ; }
void set ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
_array = 0 ;
osg : : Array * array = geometry - > getTexCoordArray ( 0 ) ;
if ( array & & array - > getType ( ) = = osg : : Array : : Vec2ArrayType )
{
osg : : Vec2Array * vec2array = static_cast < osg : : Vec2Array * > ( array ) ;
if ( ! vec2array - > empty ( ) ) _array = & ( vec2array - > front ( ) ) ;
}
_indices = 0 ;
osg : : IndexArray * indices = geometry - > getTexCoordIndices ( 0 ) ;
if ( indices & & indices - > getType ( ) = = osg : : Array : : UShortArrayType )
{
osg : : UShortArray * ushortarray = static_cast < osg : : UShortArray * > ( array ) ;
if ( ! ushortarray - > empty ( ) ) _indices = & ( ushortarray - > front ( ) ) ;
}
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
inline void draw ( unsigned int index ) const
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
glTexCoord2fv ( _array [ _indices [ index ] ] . ptr ( ) ) ;
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
osg : : Vec2 * _array ;
unsigned short * _indices ;
} ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
template < class T1 >
struct DrawAttributeArrays_T : public DrawAttributeArrays
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
DrawAttributeArrays_T ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
virtual bool valid ( ) const { return _t1 . valid ( ) ; }
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
virtual void set ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
_t1 . set ( geometry ) ;
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
virtual unsigned int draw ( unsigned int index , unsigned int count ) const
{
for ( unsigned int i = 0 ; i < count ; + + i , + + index )
{
_t1 . draw ( index ) ;
}
return index ;
}
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
T1 _t1 ;
} ;
template < class T1 , class T2 >
struct DrawAttributeArrays_TT : public DrawAttributeArrays
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
DrawAttributeArrays_TT ( )
2003-09-01 06:08:22 +08:00
{
}
2003-09-24 23:54:22 +08:00
virtual bool valid ( ) const { return _t1 . valid ( ) & & _t2 . valid ( ) ; }
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
virtual void set ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
_t1 . set ( geometry ) ;
_t2 . set ( geometry ) ;
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
virtual unsigned int draw ( unsigned int index , unsigned int count ) const
{
for ( unsigned int i = 0 ; i < count ; + + i , + + index )
{
_t1 . draw ( index ) ;
_t2 . draw ( index ) ;
}
return index ;
}
T1 _t1 ;
T1 _t2 ;
} ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
template < class T1 , class T2 , class T3 >
struct DrawAttributeArrays_TTT : public DrawAttributeArrays
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
DrawAttributeArrays_TTT ( )
{
}
virtual bool valid ( ) const { return _t1 . valid ( ) & & _t2 . valid ( ) & & _t3 . valid ( ) ; }
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
virtual void set ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
_t1 . set ( geometry ) ;
_t2 . set ( geometry ) ;
_t3 . set ( geometry ) ;
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
virtual unsigned int draw ( unsigned int index , unsigned int count ) const
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
for ( unsigned int i = 0 ; i < count ; + + i , + + index )
{
_t1 . draw ( index ) ;
_t2 . draw ( index ) ;
_t3 . draw ( index ) ;
}
return index ;
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
T1 _t1 ;
T2 _t2 ;
T3 _t3 ;
} ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
template < class T1 , class T2 , class T3 , class T4 >
struct DrawAttributeArrays_TTTT : public DrawAttributeArrays
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
DrawAttributeArrays_TTTT ( )
{
}
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
virtual bool valid ( ) const { return _t1 . valid ( ) & & _t2 . valid ( ) & & _t3 . valid ( ) & & _t4 . valid ( ) ; }
virtual void set ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
_t1 . set ( geometry ) ;
_t2 . set ( geometry ) ;
_t3 . set ( geometry ) ;
_t4 . set ( geometry ) ;
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
virtual unsigned int draw ( unsigned int index , unsigned int count ) const
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
for ( unsigned int i = 0 ; i < count ; + + i , + + index )
{
_t1 . draw ( index ) ;
_t2 . draw ( index ) ;
_t3 . draw ( index ) ;
_t4 . draw ( index ) ;
}
return index ;
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
T1 _t1 ;
T2 _t2 ;
T3 _t3 ;
T4 _t4 ;
} ;
template < class T1 , class T2 >
struct DrawAttributeArrays_TT_USI : public DrawAttributeArrays
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
DrawAttributeArrays_TT_USI ( )
{
}
virtual bool valid ( ) const { return _t1 . valid ( ) & & _t2 . valid ( ) & & _indices ! = 0 ; }
virtual void set ( osg : : Geometry * geometry )
{
_t1 . set ( geometry ) ;
_t2 . set ( geometry ) ;
_indices = 0 ;
osg : : IndexArray * indices = geometry - > getVertexIndices ( ) ;
if ( indices & & indices - > getType ( ) = = osg : : Array : : UShortArrayType )
{
osg : : UShortArray * ushort3array = static_cast < osg : : UShortArray * > ( array ) ;
if ( ! ushort3array - > empty ( ) ) _indices = & ( ushort3array - > front ( ) ) ;
}
}
virtual unsigned int draw ( unsigned int index , unsigned int count ) const
{
for ( unsigned int i = 0 ; i < count ; + + i , + + index )
{
unsigned int ivalue = _indices [ index ] ;
_t1 . draw ( ivalue ) ;
_t2 . draw ( ivalue ) ;
}
return index ;
}
T1 _t1 ;
T2 _t2 ;
} ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
template < class T1 , class T2 , class T3 >
struct DrawAttributeArrays_TTT_USI : public DrawAttributeArrays
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
DrawAttributeArrays_TTT_USI ( )
{
}
virtual bool valid ( ) const { return _t1 . valid ( ) & & _t2 . valid ( ) & & _t3 . valid ( ) & & _indices ! = 0 ; }
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
virtual void set ( osg : : Geometry * geometry )
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
_t1 . set ( geometry ) ;
_t2 . set ( geometry ) ;
_t3 . set ( geometry ) ;
_indices = 0 ;
osg : : IndexArray * indices = geometry - > getVertexIndices ( ) ;
if ( indices & & indices - > getType ( ) = = osg : : Array : : UShortArrayType )
{
osg : : UShortArray * ushort3array = static_cast < osg : : UShortArray * > ( array ) ;
if ( ! ushort3array - > empty ( ) ) _indices = & ( ushort3array - > front ( ) ) ;
}
2003-09-01 06:08:22 +08:00
}
2003-09-24 23:54:22 +08:00
virtual unsigned int draw ( unsigned int index , unsigned int count ) const
{
for ( unsigned int i = 0 ; i < count ; + + i , + + index )
{
unsigned int ivalue = _indices [ index ] ;
_t1 . draw ( ivalue ) ;
_t2 . draw ( ivalue ) ;
_t3 . draw ( ivalue ) ;
}
return index ;
}
T1 _t1 ;
T2 _t2 ;
T3 _t3 ;
} ;
template < class T1 , class T2 , class T3 , class T4 >
struct DrawAttributeArrays_TTTT_USI : public DrawAttributeArrays
2003-09-01 06:08:22 +08:00
{
2003-09-24 23:54:22 +08:00
DrawAttributeArrays_TTTT_USI ( )
2003-09-01 06:08:22 +08:00
{
}
2003-09-24 23:54:22 +08:00
virtual bool valid ( ) const { return _t1 . valid ( ) & & _t2 . valid ( ) & & _t3 . valid ( ) & & _t4 . valid ( ) & & _indices ! = 0 ; }
virtual void set ( osg : : Geometry * geometry )
{
_t1 . set ( geometry ) ;
_t2 . set ( geometry ) ;
_t3 . set ( geometry ) ;
_t4 . set ( geometry ) ;
_indices = 0 ;
osg : : IndexArray * indices = geometry - > getVertexIndices ( ) ;
if ( indices & & indices - > getType ( ) = = osg : : Array : : UShortArrayType )
{
osg : : UShortArray * ushort3array = static_cast < osg : : UShortArray * > ( array ) ;
if ( ! ushort3array - > empty ( ) ) _indices = & ( ushort3array - > front ( ) ) ;
}
}
virtual unsigned int draw ( unsigned int index , unsigned int count ) const
{
for ( unsigned int i = 0 ; i < count ; + + i , + + index )
{
unsigned int ivalue = _indices [ index ] ;
_t1 . draw ( ivalue ) ;
_t2 . draw ( ivalue ) ;
_t3 . draw ( ivalue ) ;
_t4 . draw ( ivalue ) ;
}
return index ;
}
T1 _t1 ;
T2 _t2 ;
T3 _t3 ;
T4 _t4 ;
} ;
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
// One attribute x 2
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_T < V3 > DrawAttributeArrays_V3 ;
typedef DrawAttributeArrays_T < V3USI > DrawAttributeArrays_V3i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
// Two attributes x 15
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TT < N3 , V3 > DrawAttributeArrays_N3V3 ;
typedef DrawAttributeArrays_TT < N3USI , V3 > DrawAttributeArrays_N3iV3 ;
typedef DrawAttributeArrays_TT < N3 , V3USI > DrawAttributeArrays_N3V3i ;
typedef DrawAttributeArrays_TT < N3USI , V3USI > DrawAttributeArrays_N3iV3i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TT_USI < N3 , V3 > DrawAttributeArrays_N3V3_i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TT < C4 , V3 > DrawAttributeArrays_C4V3 ;
typedef DrawAttributeArrays_TT < C4USI , V3 > DrawAttributeArrays_C4iV3 ;
typedef DrawAttributeArrays_TT < C4 , V3USI > DrawAttributeArrays_C4V3i ;
typedef DrawAttributeArrays_TT < C4USI , V3USI > DrawAttributeArrays_C4iV3i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TT_USI < C4 , V3 > DrawAttributeArrays_C4V3_i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TT < T2 , V3 > DrawAttributeArrays_T2V3 ;
typedef DrawAttributeArrays_TT < T2USI , V3 > DrawAttributeArrays_T2iV3 ;
typedef DrawAttributeArrays_TT < T2 , V3USI > DrawAttributeArrays_T2V3i ;
typedef DrawAttributeArrays_TT < T2USI , V3USI > DrawAttributeArrays_T2iV3i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TT_USI < T2 , V3 > DrawAttributeArrays_T2V3_i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
// Three attributes x 27
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTT < C4 , N3 , V3 > DrawAttributeArrays_C4N3V3 ;
typedef DrawAttributeArrays_TTT < C4USI , N3 , V3 > DrawAttributeArrays_C4iN3V3 ;
typedef DrawAttributeArrays_TTT < C4 , N3USI , V3 > DrawAttributeArrays_C4N3iV3 ;
typedef DrawAttributeArrays_TTT < C4USI , N3USI , V3 > DrawAttributeArrays_C4iN3iV3 ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTT < C4 , N3 , V3USI > DrawAttributeArrays_C4N3V3i ;
typedef DrawAttributeArrays_TTT < C4USI , N3 , V3USI > DrawAttributeArrays_C4iN3V3i ;
typedef DrawAttributeArrays_TTT < C4 , N3USI , V3USI > DrawAttributeArrays_C4N3iV3i ;
typedef DrawAttributeArrays_TTT < C4USI , N3USI , V3USI > DrawAttributeArrays_C4iN3iV3i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTT_USI < C4 , N3 , V3 > DrawAttributeArrays_C4N3V3_i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTT < T2 , N3 , V3 > DrawAttributeArrays_T2N3V3 ;
typedef DrawAttributeArrays_TTT < T2USI , N3 , V3 > DrawAttributeArrays_T2iN3V3 ;
typedef DrawAttributeArrays_TTT < T2 , N3USI , V3 > DrawAttributeArrays_T2iN3iV3 ;
typedef DrawAttributeArrays_TTT < T2USI , N3USI , V3 > DrawAttributeArrays_T2N3iV3 ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTT < T2 , N3 , V3USI > DrawAttributeArrays_T2N3V3i ;
typedef DrawAttributeArrays_TTT < T2USI , N3 , V3USI > DrawAttributeArrays_T2iN3V3i ;
typedef DrawAttributeArrays_TTT < T2 , N3USI , V3USI > DrawAttributeArrays_T2iN3iV3i ;
typedef DrawAttributeArrays_TTT < T2USI , N3USI , V3USI > DrawAttributeArrays_T2N3iV3i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTT_USI < T2 , N3 , V3 > DrawAttributeArrays_T2N3V3_i ;
2003-09-01 06:08:22 +08:00
2008-03-11 21:23:49 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTT < T2 , C4 , V3 > DrawAttributeArrays_T2C4V3 ;
typedef DrawAttributeArrays_TTT < T2USI , C4 , V3 > DrawAttributeArrays_T2iC4V3 ;
typedef DrawAttributeArrays_TTT < T2 , C4USI , V3 > DrawAttributeArrays_T2C4iV3 ;
typedef DrawAttributeArrays_TTT < T2USI , C4USI , V3 > DrawAttributeArrays_T2iC4iV3 ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTT < T2 , C4 , V3USI > DrawAttributeArrays_T2C4V3i ;
typedef DrawAttributeArrays_TTT < T2USI , C4 , V3USI > DrawAttributeArrays_T2iC4V3i ;
typedef DrawAttributeArrays_TTT < T2 , C4USI , V3USI > DrawAttributeArrays_T2C4iV3i ;
typedef DrawAttributeArrays_TTT < T2USI , C4USI , V3USI > DrawAttributeArrays_T2iC4iV3i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTT_USI < T2 , C4 , V3 > DrawAttributeArrays_T2C4V3_t ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
// Four attributes x 17
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTTT < T2 , C4 , N3 , V3 > DrawAttributeArrays_T2C4N3V3 ;
typedef DrawAttributeArrays_TTTT < T2USI , C4 , N3 , V3 > DrawAttributeArrays_T2iC4N3V3 ;
typedef DrawAttributeArrays_TTTT < T2 , C4USI , N3 , V3 > DrawAttributeArrays_T2C4iN3V3 ;
typedef DrawAttributeArrays_TTTT < T2USI , C4USI , N3 , V3 > DrawAttributeArrays_T2iC4iN3V3 ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTTT < T2 , C4 , N3USI , V3 > DrawAttributeArrays_T2C4N3iV3 ;
typedef DrawAttributeArrays_TTTT < T2USI , C4 , N3USI , V3 > DrawAttributeArrays_T2iC4N3iV3 ;
typedef DrawAttributeArrays_TTTT < T2 , C4USI , N3USI , V3 > DrawAttributeArrays_T2C4iN3iV3 ;
typedef DrawAttributeArrays_TTTT < T2USI , C4USI , N3USI , V3 > DrawAttributeArrays_T2iC4iN3iV3 ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTTT < T2 , C4 , N3 , V3USI > DrawAttributeArrays_T2C4N3V3i ;
typedef DrawAttributeArrays_TTTT < T2USI , C4 , N3 , V3USI > DrawAttributeArrays_T2iC4N3V3i ;
typedef DrawAttributeArrays_TTTT < T2 , C4USI , N3 , V3USI > DrawAttributeArrays_T2C4iN3V3i ;
typedef DrawAttributeArrays_TTTT < T2USI , C4USI , N3 , V3USI > DrawAttributeArrays_T2iC4iN3V3i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTTT < T2 , C4 , N3USI , V3USI > DrawAttributeArrays_T2C4N3iV3i ;
typedef DrawAttributeArrays_TTTT < T2USI , C4 , N3USI , V3USI > DrawAttributeArrays_T2iC4N3iV3i ;
typedef DrawAttributeArrays_TTTT < T2 , C4USI , N3USI , V3USI > DrawAttributeArrays_T2C4iN3iV3i ;
typedef DrawAttributeArrays_TTTT < T2USI , C4USI , N3USI , V3USI > DrawAttributeArrays_T2iC4iN3iV3i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
typedef DrawAttributeArrays_TTTT_USI < T2 , C4 , N3 , V3 > DrawAttributeArrays_T2C4N3V3_i ;
2003-09-01 06:08:22 +08:00
2003-09-24 23:54:22 +08:00
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
2003-09-01 06:08:22 +08:00
# endif