/* -*-c++-*- OpenSceneGraph - Copyright (C) 1998-2006 Robert Osfield * Copyright (C) 2010 Tim Moore * Copyright (C) 2012 David Callu * * 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. */ #ifndef OSG_BUFFERINDEXBINDING #define OSG_BUFFERINDEXBINDING 1 #include #include #include #include #ifndef GL_TRANSFORM_FEEDBACK_BUFFER #define GL_TRANSFORM_FEEDBACK_BUFFER 0x8C8E #endif namespace osg { class State; /** Encapsulate binding buffer objects to index targets. This * specifically supports the uniform buffer and transform feedback * targets. */ // Common implementation superclass class OSG_EXPORT BufferIndexBinding : public StateAttribute { protected: BufferIndexBinding(GLenum target, GLuint index); BufferIndexBinding(GLenum target, GLuint index, BufferObject* bo, GLintptr offset, GLsizeiptr size); BufferIndexBinding(const BufferIndexBinding& rhs, const CopyOp& copyop=CopyOp::SHALLOW_COPY); public: // The member value is part of the key to this state attribute in // the State class. Using the index target, we can separately // track the bindings for many different index targets. virtual unsigned getMember() const { return static_cast(_index); } GLenum getTarget() const { return _target; } /** Set the renderbuffer index of the BlendEquationi. */ void setIndex(unsigned int index); /** Get the index target. */ unsigned int getIndex() const { return _index; } /** Set the buffer object that will be bound to the index target. */ void setBufferObject(BufferObject *bo) { _bufferObject = bo; } /** Get the buffer object to be bound. */ const BufferObject* getBufferObject() const { return _bufferObject.get(); } BufferObject* getBufferObject(){ return _bufferObject.get(); } /** Set the starting offset into the buffer object for data for the indexed target. Note: the required alignment on the offset may be quite large (e.g., 256 bytes on NVidia 8600M). This should be checked with glGetIntegerv(GL_UNIFORM_BUFFER_OFFSET_ALIGNMENT...). */ void setOffset(GLintptr offset) { _offset = offset; } GLintptr getOffset() const { return _offset; } /** Set the size of data for the indexed target. */ void setSize(GLsizeiptr size) { _size = size; } GLsizeiptr getSize() const { return _size; } virtual void apply(State& state) const; protected: virtual ~BufferIndexBinding(); const GLenum _target; GLuint _index; ref_ptr _bufferObject; GLintptr _offset; GLsizeiptr _size; }; /** StateAttribute for binding a uniform buffer index target. */ class OSG_EXPORT UniformBufferBinding : public BufferIndexBinding { public: UniformBufferBinding(); UniformBufferBinding(GLuint index); /** Create a binding for a uniform buffer index target. * @param index the index target * @param bo associated buffer object * @param offset offset into buffer object * @param size size of data in buffer object */ UniformBufferBinding(GLuint index, BufferObject* bo, GLintptr offset, GLsizeiptr size); UniformBufferBinding(const UniformBufferBinding& rhs, const CopyOp& copyop=CopyOp::SHALLOW_COPY); META_StateAttribute(osg, UniformBufferBinding, UNIFORMBUFFERBINDING); virtual int compare(const StateAttribute& bb) const { COMPARE_StateAttribute_Types(UniformBufferBinding, bb) COMPARE_StateAttribute_Parameter(_target) COMPARE_StateAttribute_Parameter(_index) COMPARE_StateAttribute_Parameter(_bufferObject) COMPARE_StateAttribute_Parameter(_offset) COMPARE_StateAttribute_Parameter(_size) return 0; } }; /** StateAttribute for binding a transform feedback index target. */ class OSG_EXPORT TransformFeedbackBufferBinding : public BufferIndexBinding { public: TransformFeedbackBufferBinding(GLuint index = 0); TransformFeedbackBufferBinding(GLuint index, BufferObject* bo, GLintptr offset, GLsizeiptr size); TransformFeedbackBufferBinding(const TransformFeedbackBufferBinding& rhs, const CopyOp& copyop=CopyOp::SHALLOW_COPY); META_StateAttribute(osg, TransformFeedbackBufferBinding, TRANSFORMFEEDBACKBUFFERBINDING); virtual int compare(const StateAttribute& bb) const { COMPARE_StateAttribute_Types(TransformFeedbackBufferBinding, bb) COMPARE_StateAttribute_Parameter(_target) COMPARE_StateAttribute_Parameter(_index) COMPARE_StateAttribute_Parameter(_bufferObject) COMPARE_StateAttribute_Parameter(_offset) COMPARE_StateAttribute_Parameter(_size) return 0; } }; /** StateAttribute for binding a atomic counter buffer index target. */ class OSG_EXPORT AtomicCounterBufferBinding : public BufferIndexBinding { public: AtomicCounterBufferBinding(GLuint index=0); /** Create a binding for a atomic counter buffer index target. * @param index the index target * @param bo associated buffer object * @param offset offset into buffer object * @param size size of data in buffer object */ AtomicCounterBufferBinding(GLuint index, BufferObject* bo, GLintptr offset, GLsizeiptr size); AtomicCounterBufferBinding(const AtomicCounterBufferBinding& rhs, const CopyOp& copyop=CopyOp::SHALLOW_COPY); META_StateAttribute(osg, AtomicCounterBufferBinding, ATOMICCOUNTERBUFFERBINDING); void readData(osg::State & state, osg::UIntArray & uintArray) const; virtual int compare(const StateAttribute& bb) const { COMPARE_StateAttribute_Types(AtomicCounterBufferBinding, bb) COMPARE_StateAttribute_Parameter(_target) COMPARE_StateAttribute_Parameter(_index) COMPARE_StateAttribute_Parameter(_bufferObject) COMPARE_StateAttribute_Parameter(_offset) COMPARE_StateAttribute_Parameter(_size) return 0; } }; class OSG_EXPORT ShaderStorageBufferBinding : public BufferIndexBinding { public: ShaderStorageBufferBinding(GLuint index=0); /** Create a binding for a shader storage buffer index target. * @param index the index target * @param bo associated buffer object * @param offset offset into buffer object * @param size size of data in buffer object */ ShaderStorageBufferBinding(GLuint index, BufferObject* bo, GLintptr offset, GLsizeiptr size); ShaderStorageBufferBinding(const ShaderStorageBufferBinding& rhs, const CopyOp& copyop=CopyOp::SHALLOW_COPY); META_StateAttribute(osg, ShaderStorageBufferBinding, SHADERSTORAGEBUFFERBINDING); virtual int compare(const StateAttribute& bb) const { COMPARE_StateAttribute_Types(ShaderStorageBufferBinding, bb) COMPARE_StateAttribute_Parameter(_target) COMPARE_StateAttribute_Parameter(_index) COMPARE_StateAttribute_Parameter(_bufferObject) COMPARE_StateAttribute_Parameter(_offset) COMPARE_StateAttribute_Parameter(_size) return 0; } }; class OSG_EXPORT DrawIndirectBufferBinding : public BufferIndexBinding { public: DrawIndirectBufferBinding(); /** Create a binding for a uniform buffer index target. * @param bo associated buffer object */ DrawIndirectBufferBinding( BufferObject* bo); void apply(State& state) const; DrawIndirectBufferBinding(const DrawIndirectBufferBinding& rhs, const CopyOp& copyop=CopyOp::SHALLOW_COPY); META_StateAttribute(osg, DrawIndirectBufferBinding, INDIRECTDRAWBUFFERBINDING); virtual int compare(const StateAttribute& bb) const { COMPARE_StateAttribute_Types(DrawIndirectBufferBinding, bb) COMPARE_StateAttribute_Parameter(_target) COMPARE_StateAttribute_Parameter(_bufferObject) return 0; } }; } // namespace osg #endif