Moved the ArrayDispatchers management so that osg::State now has a ArrayDispatchers object that any osg::Geometry can reuse,
and optimized the implementation to reduce the CPU overhead.
This commit is contained in:
@@ -17,12 +17,12 @@
|
||||
#include <osg/ref_ptr>
|
||||
#include <osg/Array>
|
||||
#include <osg/Matrixd>
|
||||
#include <osg/GLBeginEndAdapter>
|
||||
|
||||
namespace osg {
|
||||
|
||||
// forward declare
|
||||
class State;
|
||||
class GLBeginEndAdapter;
|
||||
class AttributeDispatchMap;
|
||||
|
||||
struct AttributeDispatch : public osg::Referenced
|
||||
@@ -36,11 +36,10 @@ class OSG_EXPORT ArrayDispatchers : public osg::Referenced
|
||||
{
|
||||
public:
|
||||
|
||||
ArrayDispatchers(osg::State& state);
|
||||
ArrayDispatchers();
|
||||
~ArrayDispatchers();
|
||||
|
||||
void assignTexCoordDispatchers(unsigned int unit);
|
||||
void assignVertexAttribDispatchers(unsigned int unit);
|
||||
void setState(osg::State* state);
|
||||
|
||||
AttributeDispatch* vertexDispatcher(Array* array, IndexArray* indices);
|
||||
AttributeDispatch* normalDispatcher(Array* array, IndexArray* indices);
|
||||
@@ -55,24 +54,52 @@ class OSG_EXPORT ArrayDispatchers : public osg::Referenced
|
||||
void setUseGLBeginEndAdapter(bool flag) { _useGLBeginEndAdapter = flag; }
|
||||
bool getUseGLBeginEndAdapter() const { return _useGLBeginEndAdapter; }
|
||||
|
||||
void activate(unsigned int binding, AttributeDispatch* at);
|
||||
void activate(unsigned int binding, AttributeDispatch* at)
|
||||
{
|
||||
if (at) _activeDispatchList[binding].push_back(at);
|
||||
}
|
||||
|
||||
void activateVertexArray(unsigned int binding, osg::Array* array, osg::IndexArray* indices) { activate(binding, vertexDispatcher(array, indices)); }
|
||||
void activateColorArray(unsigned int binding, osg::Array* array, osg::IndexArray* indices) { activate(binding, colorDispatcher(array, indices)); }
|
||||
void activateNormalArray(unsigned int binding, osg::Array* array, osg::IndexArray* indices) { activate(binding, normalDispatcher(array, indices)); }
|
||||
void activateSecondaryColorArray(unsigned int binding, osg::Array* array, osg::IndexArray* indices) { activate(binding, secondaryColorDispatcher(array, indices)); }
|
||||
void activateFogCoordArray(unsigned int binding, osg::Array* array, osg::IndexArray* indices) { activate(binding, fogCoordDispatcher(array, indices)); }
|
||||
void activateTexCoordArray(unsigned int binding, unsigned int unit, osg::Array* array, osg::IndexArray* indices) { activate(binding, texCoordDispatcher(unit, array, indices)); }
|
||||
void activateVertexAttribArray(unsigned int binding, unsigned int unit, osg::Array* array, osg::IndexArray* indices) { activate(binding, vertexAttribDispatcher(unit, array, indices)); }
|
||||
void activateVertexArray(unsigned int binding, osg::Array* array, osg::IndexArray* indices) { if (binding && array) activate(binding, vertexDispatcher(array, indices)); }
|
||||
void activateColorArray(unsigned int binding, osg::Array* array, osg::IndexArray* indices) { if (binding && array) activate(binding, colorDispatcher(array, indices)); }
|
||||
void activateNormalArray(unsigned int binding, osg::Array* array, osg::IndexArray* indices) { if (binding && array) activate(binding, normalDispatcher(array, indices)); }
|
||||
void activateSecondaryColorArray(unsigned int binding, osg::Array* array, osg::IndexArray* indices) { if (binding && array) activate(binding, secondaryColorDispatcher(array, indices)); }
|
||||
void activateFogCoordArray(unsigned int binding, osg::Array* array, osg::IndexArray* indices) { if (binding && array) activate(binding, fogCoordDispatcher(array, indices)); }
|
||||
void activateTexCoordArray(unsigned int binding, unsigned int unit, osg::Array* array, osg::IndexArray* indices) { if (binding && array) activate(binding, texCoordDispatcher(unit, array, indices)); }
|
||||
void activateVertexAttribArray(unsigned int binding, unsigned int unit, osg::Array* array, osg::IndexArray* indices) { if (binding && array) activate(binding, vertexAttribDispatcher(unit, array, indices)); }
|
||||
|
||||
void dispatch(unsigned int binding);
|
||||
void dispatch(unsigned int binding, unsigned int index);
|
||||
void dispatch(unsigned int binding, unsigned int index)
|
||||
{
|
||||
AttributeDispatchList& ad = _activeDispatchList[binding];
|
||||
for(AttributeDispatchList::iterator itr = ad.begin();
|
||||
itr != ad.end();
|
||||
++itr)
|
||||
{
|
||||
(*(*itr))(index);
|
||||
}
|
||||
}
|
||||
|
||||
void Begin(GLenum mode);
|
||||
void End();
|
||||
bool active(unsigned int binding) const { return !_activeDispatchList[binding].empty(); }
|
||||
|
||||
void Begin(GLenum mode)
|
||||
{
|
||||
if (_useGLBeginEndAdapter) _glBeginEndAdapter->Begin(mode);
|
||||
else ::glBegin(mode);
|
||||
}
|
||||
|
||||
void End()
|
||||
{
|
||||
if (_useGLBeginEndAdapter) _glBeginEndAdapter->End();
|
||||
else ::glEnd();
|
||||
}
|
||||
|
||||
protected:
|
||||
|
||||
void init();
|
||||
|
||||
void assignTexCoordDispatchers(unsigned int unit);
|
||||
void assignVertexAttribDispatchers(unsigned int unit);
|
||||
|
||||
bool _initialized;
|
||||
State* _state;
|
||||
GLBeginEndAdapter* _glBeginEndAdapter;
|
||||
|
||||
@@ -88,19 +115,12 @@ class OSG_EXPORT ArrayDispatchers : public osg::Referenced
|
||||
|
||||
typedef std::vector<AttributeDispatch*> AttributeDispatchList;
|
||||
|
||||
struct BindingGroup
|
||||
{
|
||||
unsigned int _index;
|
||||
AttributeDispatchList _attributeDispatchList;
|
||||
};
|
||||
|
||||
typedef std::vector<BindingGroup> BindingGroupList;
|
||||
BindingGroupList _bindingGroupList;
|
||||
typedef std::vector<AttributeDispatchList> ActiveDispatchList;
|
||||
ActiveDispatchList _activeDispatchList;
|
||||
|
||||
bool _useGLBeginEndAdapter;
|
||||
};
|
||||
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
@@ -73,6 +73,7 @@ class Vec4f;
|
||||
class Vec4ub;
|
||||
class Geometry;
|
||||
class NodeVisitor;
|
||||
class ArrayDispatchers;
|
||||
|
||||
// this is defined to alter the way display lists are compiled inside the
|
||||
// the draw method, it has been found that the NVidia drivers fail completely
|
||||
@@ -666,7 +667,9 @@ class OSG_EXPORT Drawable : public Object
|
||||
void glGetQueryObjectuiv(GLuint id, GLenum pname, GLuint *params) const;
|
||||
void glGetQueryObjectui64v(GLuint id, GLenum pname, GLuint64EXT *params) const;
|
||||
|
||||
public:
|
||||
protected:
|
||||
|
||||
friend class ArrayDispatchers;
|
||||
|
||||
typedef void (APIENTRY * FogCoordProc) (const GLfloat* coord);
|
||||
|
||||
|
||||
@@ -26,6 +26,7 @@
|
||||
#include <osg/Polytope>
|
||||
#include <osg/Viewport>
|
||||
#include <osg/GLBeginEndAdapter>
|
||||
#include <osg/ArrayDispatchers>
|
||||
|
||||
#include <vector>
|
||||
#include <map>
|
||||
@@ -1246,6 +1247,8 @@ class OSG_EXPORT State : public Referenced, public Observer
|
||||
/** get the GL adapter object used to map OpenGL 1.0 glBegin/glEnd usage to vertex arrays.*/
|
||||
inline GLBeginEndAdapter& getGLBeginEndAdapter() { return _glBeginEndAdapter; }
|
||||
|
||||
/** get the helper class for dispatching osg::Arrays as OpenGL attribute data.*/
|
||||
inline ArrayDispatchers& getArrayDispatchers() { return _arrayDispatchers; }
|
||||
|
||||
protected:
|
||||
|
||||
@@ -1558,6 +1561,7 @@ class OSG_EXPORT State : public Referenced, public Observer
|
||||
osg::ref_ptr<DynamicObjectRenderingCompletedCallback> _completeDynamicObjectRenderingCallback;
|
||||
|
||||
GLBeginEndAdapter _glBeginEndAdapter;
|
||||
ArrayDispatchers _arrayDispatchers;
|
||||
|
||||
};
|
||||
|
||||
|
||||
Reference in New Issue
Block a user