コード例 #1
0
ファイル: gpu_shader.c プロジェクト: UPBGE/blender
// Used only for VSM shader with geometry instancing support.
void GPU_shader_bind_instancing_attrib(GPUShader *shader, void *matrixoffset, void *positionoffset, unsigned int stride)
{
	int posloc = GPU_shader_get_attribute(shader, GPU_builtin_name(GPU_INSTANCING_POSITION_ATTRIB));
	int matloc = GPU_shader_get_attribute(shader, GPU_builtin_name(GPU_INSTANCING_MATRIX_ATTRIB));

	// Matrix
	if (matloc != -1) {
		glEnableVertexAttribArrayARB(matloc);
		glEnableVertexAttribArrayARB(matloc + 1);
		glEnableVertexAttribArrayARB(matloc + 2);

		glVertexAttribPointerARB(matloc, 3, GL_FLOAT, GL_FALSE, stride, matrixoffset);
		glVertexAttribPointerARB(matloc + 1, 3, GL_FLOAT, GL_FALSE, stride, ((char *)matrixoffset) + 3 * sizeof(float));
		glVertexAttribPointerARB(matloc + 2, 3, GL_FLOAT, GL_FALSE, stride, ((char *)matrixoffset) + 6 * sizeof(float));

		glVertexAttribDivisorARB(matloc, 1);
		glVertexAttribDivisorARB(matloc + 1, 1);
		glVertexAttribDivisorARB(matloc + 2, 1);
	}

	// Position
	if (posloc != -1) {
		glEnableVertexAttribArrayARB(posloc);
		glVertexAttribPointerARB(posloc, 3, GL_FLOAT, GL_FALSE, stride, positionoffset);
		glVertexAttribDivisorARB(posloc, 1);
	}
}
コード例 #2
0
ファイル: instanced_arrays.c プロジェクト: nobled/piglit
static GLboolean
test_instancing(GLuint divisor)
{
   static const GLfloat verts[4][2] = {
      {-1, -1}, {1, -1}, {1, 1}, {-1, 1}
   };
   
   glVertexPointer(2, GL_FLOAT, 0, verts);
   glEnableClientState(GL_VERTEX_ARRAY);

   glVertexAttribPointer(PosAttrib, 2, GL_FLOAT, GL_FALSE, 0, Positions);
   glVertexAttribPointer(ColorAttrib, 4, GL_FLOAT, GL_FALSE, 0, Colors);
   glEnableVertexAttribArray(PosAttrib);
   glEnableVertexAttribArray(ColorAttrib);
   glVertexAttribDivisorARB(PosAttrib, 1);
   /* advance color once every 'n' instances */
   glVertexAttribDivisorARB(ColorAttrib, divisor);

   glClear(GL_COLOR_BUFFER_BIT);

   glUseProgram(Program);

   glDrawArraysInstancedARB(GL_POLYGON, 0, 4, PRIMS);

   glUseProgram(0);

   {
      GLint i;
      GLint pos[4];

      for (i = 0; i < PRIMS; i++) {
         GLuint elem = i / divisor;

         /* use glRasterPos to determine where to read a sample pixel */
         glRasterPos2fv(Positions[i]);
         glGetIntegerv(GL_CURRENT_RASTER_POSITION, pos);

         if (!piglit_probe_pixel_rgba(pos[0], pos[1], Colors[elem])) {
            fprintf(stderr, "%s: instance %d failed to draw correctly\n",
                    TestName, i);
            fprintf(stderr, "%s: color instance divisor = %u\n",
                    TestName, divisor);
            glutSwapBuffers();
            return GL_FALSE;
         }
      }
   }

   glDisableClientState(GL_VERTEX_ARRAY);
   glDisableVertexAttribArray(PosAttrib);
   glDisableVertexAttribArray(ColorAttrib);

   glutSwapBuffers();

   return GL_TRUE;
}
コード例 #3
0
void VAOInstanceUtil<InstanceDataDualTex>::SetVertexAttrib()
{
    SetVertexAttrib_impl();
    glEnableVertexAttribArray(10);
    glVertexAttribIPointer(10, 2, GL_UNSIGNED_INT, sizeof(InstanceDataDualTex), (GLvoid*)(9 * sizeof(float)));
    glVertexAttribDivisorARB(10, 1);
    glEnableVertexAttribArray(11);
    glVertexAttribIPointer(11, 2, GL_UNSIGNED_INT, sizeof(InstanceDataDualTex), (GLvoid*)(9 * sizeof(float) + 2 * sizeof(unsigned)));
    glVertexAttribDivisorARB(11, 1);
}
コード例 #4
0
ファイル: vao_manager.cpp プロジェクト: Benau/stk-code
 static void SetVertexAttrib_impl()
 {
     glEnableVertexAttribArray(7);
     glVertexAttribPointer(7, 3, GL_FLOAT, GL_FALSE, sizeof(T), 0);
     glVertexAttribDivisorARB(7, 1);
     glEnableVertexAttribArray(8);
     glVertexAttribPointer(8, 3, GL_FLOAT, GL_FALSE, sizeof(T), (GLvoid*)(3 * sizeof(float)));
     glVertexAttribDivisorARB(8, 1);
     glEnableVertexAttribArray(9);
     glVertexAttribPointer(9, 3, GL_FLOAT, GL_FALSE, sizeof(T), (GLvoid*)(6 * sizeof(float)));
     glVertexAttribDivisorARB(9, 1);
 }
コード例 #5
0
ファイル: vao_manager.cpp プロジェクト: Benau/stk-code
void VAOInstanceUtil<GlowInstanceData>::SetVertexAttrib()
{
    SetVertexAttrib_impl();
    glEnableVertexAttribArray(15);
    glVertexAttribPointer(15, 4, GL_UNSIGNED_BYTE, GL_TRUE, sizeof(GlowInstanceData), (GLvoid*)(9 * sizeof(float)));
    glVertexAttribDivisorARB(15, 1);
}
コード例 #6
0
ファイル: vao_manager.cpp プロジェクト: Benau/stk-code
void VAOInstanceUtil<InstanceDataThreeTex>::SetVertexAttrib()
{
    SetVertexAttrib_impl();
    glEnableVertexAttribArray(10);
    glVertexAttribPointer(10, 4, GL_FLOAT, GL_FALSE, sizeof(InstanceDataThreeTex), (GLvoid*)(9 * sizeof(float)));
    glVertexAttribDivisorARB(10, 1);
    glEnableVertexAttribArray(11);
    glVertexAttribIPointer(11, 2, GL_UNSIGNED_INT, sizeof(InstanceDataThreeTex), (GLvoid*)(13 * sizeof(float)));
    glVertexAttribDivisorARB(11, 1);
    glEnableVertexAttribArray(12);
    glVertexAttribIPointer(12, 2, GL_UNSIGNED_INT, sizeof(InstanceDataThreeTex), (GLvoid*)(13 * sizeof(float) + 2 * sizeof(unsigned)));
    glVertexAttribDivisorARB(12, 1);
    glEnableVertexAttribArray(13);
    glVertexAttribIPointer(13, 2, GL_UNSIGNED_INT, sizeof(InstanceDataThreeTex), (GLvoid*)(13 * sizeof(float) + 4 * sizeof(unsigned)));
    glVertexAttribDivisorARB(13, 1);
}
コード例 #7
0
EXTERN_C_ENTER

JNIEXPORT void JNICALL Java_org_lwjgl_opengl_ARBInstancedArrays_glVertexAttribDivisorARB(JNIEnv *__env, jclass clazz, jint index, jint divisor) {
    glVertexAttribDivisorARBPROC glVertexAttribDivisorARB = (glVertexAttribDivisorARBPROC)tlsGetFunction(1203);
    UNUSED_PARAM(clazz)
    glVertexAttribDivisorARB(index, divisor);
}
コード例 #8
0
ファイル: VaoImplCore.cpp プロジェクト: Ahbee/Cinder
void VaoImplCore::vertexAttribDivisorImpl( GLuint index, GLuint divisor )
{
	mLayout.vertexAttribDivisor( index, divisor );

#if defined( CINDER_GL_ES )
  #if defined( CINDER_GL_ANGLE )
	glVertexAttribDivisorANGLE( index, divisor );
  #else
	if( gl::env()->supportsInstancedArrays() ) {
		glVertexAttribDivisor( index, divisor );
	}
  #endif	
#else
	if( glVertexAttribDivisor ) {
		// not always available
		glVertexAttribDivisor( index, divisor );
	}
	else if( glVertexAttribDivisorARB ) {
		glVertexAttribDivisorARB( index, divisor );
	}
#endif

/*
#if defined( CINDER_GL_ANGLE )
	glVertexAttribDivisorANGLE( index, divisor );
#elif defined( CINDER_GL_ES_3 )
	glVertexAttribDivisor( index, divisor );
#else
	if( glVertexAttribDivisor ) // not always available
		glVertexAttribDivisor( index, divisor );
	else if( glVertexAttribDivisorARB )
		glVertexAttribDivisorARB( index, divisor );
#endif
*/
}
コード例 #9
0
ファイル: context.hpp プロジェクト: BigMacchia/DynamO
      /*! \brief Sets the divisor of a vertex attribute.
       
        The divisor is used in instancing to set the rate at which
        vertex attributes are incremented.
       */
      inline void setAttributeDivisor(GLuint idx, GLuint divisor)
      {
	if (idx >= _vertexAttributeState.size())
	  M_throw() << "Attribute index out of range";

	if (divisor == _vertexAttributeState[idx].divisor) return;
	_vertexAttributeState[idx].divisor = divisor;
	glVertexAttribDivisorARB(idx, divisor);
	detail::errorCheck();
      }
コード例 #10
0
ファイル: gpu_shader.c プロジェクト: UPBGE/blender
void GPU_shader_unbind_instancing_attrib(GPUShader *shader)
{
	int posloc = GPU_shader_get_attribute(shader, GPU_builtin_name(GPU_INSTANCING_POSITION_ATTRIB));
	int matloc = GPU_shader_get_attribute(shader, GPU_builtin_name(GPU_INSTANCING_MATRIX_ATTRIB));

	// Matrix
	if (matloc != -1) {
		glDisableVertexAttribArrayARB(matloc);
		glDisableVertexAttribArrayARB(matloc + 1);
		glDisableVertexAttribArrayARB(matloc + 2);

		glVertexAttribDivisorARB(matloc, 0);
		glVertexAttribDivisorARB(matloc + 1, 0);
		glVertexAttribDivisorARB(matloc + 2, 0);
	}

	// Position
	if (posloc != -1) {
		glDisableVertexAttribArrayARB(posloc);
		glVertexAttribDivisorARB(posloc, 0);
	}
}
コード例 #11
0
void VertexArrayNoVao::enableOpenGLVertexAttribArrays()
{
#ifndef OPENGLRENDERER_NO_STATE_CLEANUP
    // Backup the currently bound OpenGL array buffer
    // -> Using "GL_EXT_direct_state_access" this would not help in here because "glVertexAttribPointerARB" is not specified there :/
    GLint openGLArrayBufferBackup = 0;
    glGetIntegerv(GL_ARRAY_BUFFER_BINDING_ARB, &openGLArrayBufferBackup);
#endif

    // Loop through all attributes
    // -> We're using "glBindAttribLocationARB()" when linking the program so we have known attribute locations (the vertex array can't know about the program)
    GLuint attributeLocation = 0;
    const Renderer::VertexAttribute *attributeEnd = mAttributes + mNumberOfAttributes;
    for (const Renderer::VertexAttribute *attribute = mAttributes; attribute < attributeEnd; ++attribute, ++attributeLocation)
    {
        // Set the OpenGL vertex attribute pointer
        // TODO(co) Add security check: Is the given resource one of the currently used renderer?
        const Renderer::VertexArrayVertexBuffer& vertexArrayVertexBuffer = mVertexBuffers[attribute->inputSlot];
        glBindBufferARB(GL_ARRAY_BUFFER_ARB, static_cast<VertexBuffer*>(vertexArrayVertexBuffer.vertexBuffer)->getOpenGLArrayBuffer());
        glVertexAttribPointerARB(attributeLocation,
                                 Mapping::getOpenGLSize(attribute->vertexAttributeFormat),
                                 Mapping::getOpenGLType(attribute->vertexAttributeFormat),
                                 static_cast<GLboolean>(Mapping::isOpenGLVertexAttributeFormatNormalized(attribute->vertexAttributeFormat)),
                                 static_cast<GLsizei>(vertexArrayVertexBuffer.strideInBytes),
                                 reinterpret_cast<GLvoid*>(attribute->alignedByteOffset));

        // Per-instance instead of per-vertex requires "GL_ARB_instanced_arrays"
        if (attribute->instancesPerElement > 0 && mIsGL_ARB_instanced_arrays)
        {
            glVertexAttribDivisorARB(attributeLocation, attribute->instancesPerElement);
        }

        // Enable OpenGL vertex attribute array
        glEnableVertexAttribArrayARB(attributeLocation);
    }

#ifndef OPENGLRENDERER_NO_STATE_CLEANUP
    // Be polite and restore the previous bound OpenGL array buffer
    glBindBufferARB(GL_ARRAY_BUFFER_ARB, static_cast<GLuint>(openGLArrayBufferBackup));
#endif

    // Get the used index buffer
    // -> In case of no index buffer we don't bind buffer 0, there's not really a point in it
    const IndexBuffer *indexBuffer = getIndexBuffer();
    if (nullptr != indexBuffer)
    {
        // Bind OpenGL element array buffer
        glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, indexBuffer->getOpenGLElementArrayBuffer());
    }
}
コード例 #12
0
void VertexArrayNoVao::disableOpenGLVertexAttribArrays()
{
    // No previous bound OpenGL element array buffer restore, there's not really a point in it

    // Loop through all attributes
    // -> We're using "glBindAttribLocationARB()" when linking the program so we have known attribute locations (the vertex array can't know about the program)
    GLuint attributeLocation = 0;
    const Renderer::VertexAttribute *attributeEnd = mAttributes + mNumberOfAttributes;
    for (const Renderer::VertexAttribute *attribute = mAttributes; attribute < attributeEnd; ++attribute, ++attributeLocation)
    {
        // Disable OpenGL vertex attribute array
        glDisableVertexAttribArrayARB(attributeLocation);

        // Per-instance instead of per-vertex requires "GL_ARB_instanced_arrays"
        if (attribute->instancesPerElement > 0 && mIsGL_ARB_instanced_arrays)
        {
            glVertexAttribDivisorARB(attributeLocation, 0);
        }
    }
}
コード例 #13
0
void GLInstancingRenderer::RenderScene(void)
{
	 B3_PROFILE("GLInstancingRenderer::RenderScene");

	 {
		B3_PROFILE("init");
		init();
	 }

    GLint err = glGetError();
    assert(err==GL_NO_ERROR);
    
	{
		B3_PROFILE("updateCamera");
		updateCamera();
	}
    err = glGetError();
    assert(err==GL_NO_ERROR);
    
    
	//render coordinate system
#if 0
    glBegin(GL_LINES);
	err = glGetError();
    assert(err==GL_NO_ERROR);
    
    glColor3f(1,0,0);
	glVertex3f(0,0,0);
	glVertex3f(1,0,0);
	glColor3f(0,1,0);
	glVertex3f(0,0,0);
	glVertex3f(0,1,0);
	glColor3f(0,0,1);
	glVertex3f(0,0,0);
	glVertex3f(0,0,1);
	glEnd();
#endif
    
    
	//do a finish, to make sure timings are clean
	//	glFinish();



	//	glBindBuffer(GL_ARRAY_BUFFER, 0);
	{
		B3_PROFILE("glFlush2");

		glBindBuffer(GL_ARRAY_BUFFER, m_data->m_vbo);
		glFlush();
	}
    err = glGetError();
    assert(err==GL_NO_ERROR);
    
	//updatePos();

//	simulationLoop();

	//useCPU = true;

	int totalNumInstances = 0;

	for (int i=0;i<m_graphicsInstances.size();i++)
	{
		totalNumInstances+=m_graphicsInstances[i]->m_numGraphicsInstances;
	}

	int curOffset = 0;
	GLuint lastBindTexture = 0;


	for (int i=0;i<m_graphicsInstances.size();i++)
	{
		
		b3GraphicsInstance* gfxObj = m_graphicsInstances[i];
		if (gfxObj->m_numGraphicsInstances)
		{

			GLuint curBindTexture = 0;
			if (gfxObj->m_texturehandle)
				curBindTexture = gfxObj->m_texturehandle;
			else
				curBindTexture = m_data->m_defaultTexturehandle;

			if (lastBindTexture != curBindTexture)
			{
				glBindTexture(GL_TEXTURE_2D,curBindTexture);
			}
			lastBindTexture = curBindTexture;

			err = glGetError();
			assert(err==GL_NO_ERROR);
	//	int myOffset = gfxObj->m_instanceOffset*4*sizeof(float);

		int POSITION_BUFFER_SIZE = (totalNumInstances*sizeof(float)*4);
		int ORIENTATION_BUFFER_SIZE = (totalNumInstances*sizeof(float)*4);
		int COLOR_BUFFER_SIZE = (totalNumInstances*sizeof(float)*4);
//		int SCALE_BUFFER_SIZE = (totalNumInstances*sizeof(float)*3);

		glBindVertexArray(gfxObj->m_cube_vao);

		
		int vertexStride = 9*sizeof(float);
		int vertexBase = gfxObj->m_vertexArrayOffset*vertexStride;

		glVertexAttribPointer(0, 4, GL_FLOAT, GL_FALSE, 9*sizeof(float), (GLvoid*)vertexBase);
		glVertexAttribPointer(1, 4, GL_FLOAT, GL_FALSE, 0, (GLvoid *)(curOffset*4*sizeof(float)+m_maxShapeCapacityInBytes));
		glVertexAttribPointer(2, 4, GL_FLOAT, GL_FALSE, 0, (GLvoid *)(curOffset*4*sizeof(float)+m_maxShapeCapacityInBytes+POSITION_BUFFER_SIZE));
		int uvoffset = 7*sizeof(float)+vertexBase;
		int normaloffset = 4*sizeof(float)+vertexBase;

		glVertexAttribPointer(3, 2, GL_FLOAT, GL_FALSE, 9*sizeof(float), (GLvoid *)uvoffset);
		glVertexAttribPointer(4, 3, GL_FLOAT, GL_FALSE, 9*sizeof(float), (GLvoid *)normaloffset);
		glVertexAttribPointer(5, 4, GL_FLOAT, GL_FALSE, 0, (GLvoid *)(curOffset*4*sizeof(float)+m_maxShapeCapacityInBytes+POSITION_BUFFER_SIZE+ORIENTATION_BUFFER_SIZE));
		glVertexAttribPointer(6, 3, GL_FLOAT, GL_FALSE, 0, (GLvoid *)(curOffset*3*sizeof(float)+m_maxShapeCapacityInBytes+POSITION_BUFFER_SIZE+ORIENTATION_BUFFER_SIZE+COLOR_BUFFER_SIZE));

		glEnableVertexAttribArray(0);
		glEnableVertexAttribArray(1);
		glEnableVertexAttribArray(2);
		glEnableVertexAttribArray(3);
		glEnableVertexAttribArray(4);
		glEnableVertexAttribArray(5);
		glEnableVertexAttribArray(6);
		glVertexAttribDivisorARB(0, 0);
		glVertexAttribDivisorARB(1, 1);
		glVertexAttribDivisorARB(2, 1);
		glVertexAttribDivisorARB(3, 0);
		glVertexAttribDivisorARB(4, 0);
		glVertexAttribDivisorARB(5, 1);
		glVertexAttribDivisorARB(6, 1);
        
		
		

		{
			B3_PROFILE("glFlush");
			glFlush();
		}
		
			int indexCount = gfxObj->m_numIndices;
			int indexOffset = 0;

			glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, gfxObj->m_index_vbo);
			{
				B3_PROFILE("glDrawElementsInstanced");
				
				if (gfxObj->m_primitiveType==B3_GL_POINTS)
				{
					glUseProgram(instancingShaderPointSprite);
					glUniformMatrix4fv(ProjectionMatrixPointSprite, 1, false, &projectionMatrix[0]);
					glUniformMatrix4fv(ModelViewMatrixPointSprite, 1, false, &modelviewMatrix[0]);
					glUniform1f(screenWidthPointSprite,m_screenWidth);
					
					//glUniform1i(uniform_texture_diffusePointSprite, 0);
					  err = glGetError();
    assert(err==GL_NO_ERROR);
					glPointSize(20);

#ifndef __APPLE__
					glEnable(GL_POINT_SPRITE_ARB);
					glTexEnvi(GL_POINT_SPRITE_ARB, GL_COORD_REPLACE_ARB, GL_TRUE);
#endif

					glEnable(GL_VERTEX_PROGRAM_POINT_SIZE);
					glDrawElementsInstanced(GL_POINTS, indexCount, GL_UNSIGNED_INT, (void*)indexOffset, gfxObj->m_numGraphicsInstances);
				} else
				{
					glUseProgram(instancingShader);
					glUniform1f(angle_loc, 0);
					glUniformMatrix4fv(ProjectionMatrix, 1, false, &projectionMatrix[0]);
					glUniformMatrix4fv(ModelViewMatrix, 1, false, &modelviewMatrix[0]);
					glUniform1i(uniform_texture_diffuse, 0);
					glDrawElementsInstanced(GL_TRIANGLES, indexCount, GL_UNSIGNED_INT, (void*)indexOffset, gfxObj->m_numGraphicsInstances);
				}

				
				//glDrawElementsInstanced(GL_LINE_LOOP, indexCount, GL_UNSIGNED_INT, (void*)indexOffset, gfxObj->m_numGraphicsInstances);
			}
		}
		curOffset+= gfxObj->m_numGraphicsInstances;
	}
    err = glGetError();
    assert(err==GL_NO_ERROR);
	{
		B3_PROFILE("glUseProgram(0);");
		glUseProgram(0);
		glBindBuffer(GL_ARRAY_BUFFER,0);
		glBindVertexArray(0);
	}
	
	err = glGetError();
	assert(err==GL_NO_ERROR);
	
}
コード例 #14
0
	//[-------------------------------------------------------]
	//[ Public methods                                        ]
	//[-------------------------------------------------------]
	VertexArrayVaoDsa::VertexArrayVaoDsa(OpenGLRenderer &openGLRenderer, const Renderer::VertexAttributes& vertexAttributes, uint32_t numberOfVertexBuffers, const Renderer::VertexArrayVertexBuffer *vertexBuffers, IndexBuffer *indexBuffer) :
		VertexArrayVao(openGLRenderer, numberOfVertexBuffers, vertexBuffers, indexBuffer)
	{
		// Vertex buffer reference handling is done within the base class "VertexArrayVao"
		const bool isARB_DSA = openGLRenderer.getExtensions().isGL_ARB_direct_state_access();
		if (isARB_DSA)
		{
			// Create the OpenGL vertex array
			glCreateVertexArrays(1, &mOpenGLVertexArray);
		}
		else
		{
			// Create the OpenGL vertex array
			glGenVertexArrays(1, &mOpenGLVertexArray);
		}

		// Loop through all attributes
		// -> We're using "glBindAttribLocationARB()" when linking the program so we have known attribute locations (the vertex array can't know about the program)
		GLuint attributeLocation = 0;
		const Renderer::VertexAttribute *attributeEnd = vertexAttributes.attributes + vertexAttributes.numberOfAttributes;
		for (const Renderer::VertexAttribute *attribute = vertexAttributes.attributes; attribute < attributeEnd; ++attribute, ++attributeLocation)
		{
			// Set the OpenGL vertex attribute pointer
			// TODO(co) Add security check: Is the given resource one of the currently used renderer?
			const Renderer::VertexArrayVertexBuffer& vertexArrayVertexBuffer = vertexBuffers[attribute->inputSlot];

			if (isARB_DSA)
			{
				// Enable attribute
				glEnableVertexArrayAttrib(mOpenGLVertexArray, attributeLocation);

				// Set up the format for my attribute
				glVertexArrayAttribFormat(mOpenGLVertexArray, attributeLocation, Mapping::getOpenGLSize(attribute->vertexAttributeFormat), Mapping::getOpenGLType(attribute->vertexAttributeFormat), static_cast<GLboolean>(Mapping::isOpenGLVertexAttributeFormatNormalized(attribute->vertexAttributeFormat)), static_cast<GLuint>(attribute->alignedByteOffset));

				// Bind vertex buffer to buffer point
				glVertexArrayVertexBuffer(mOpenGLVertexArray,
										  attributeLocation,
										  static_cast<VertexBuffer*>(vertexArrayVertexBuffer.vertexBuffer)->getOpenGLArrayBuffer(),
										  0,	// No offset to the first element of the buffer
										  static_cast<GLsizei>(vertexArrayVertexBuffer.strideInBytes));

				// Per-instance instead of per-vertex requires "GL_ARB_instanced_arrays"
				if (attribute->instancesPerElement > 0 && openGLRenderer.getExtensions().isGL_ARB_instanced_arrays())
				{
					glVertexArrayBindingDivisor(mOpenGLVertexArray, attributeLocation, attribute->instancesPerElement);
				}
			}
			else
			{
				glVertexArrayVertexAttribOffsetEXT(mOpenGLVertexArray,
												  static_cast<VertexBuffer*>(vertexArrayVertexBuffer.vertexBuffer)->getOpenGLArrayBuffer(),
												  attributeLocation, Mapping::getOpenGLSize(attribute->vertexAttributeFormat),
												  Mapping::getOpenGLType(attribute->vertexAttributeFormat),
												  static_cast<GLboolean>(Mapping::isOpenGLVertexAttributeFormatNormalized(attribute->vertexAttributeFormat)),
												  static_cast<GLsizei>(vertexArrayVertexBuffer.strideInBytes),
												  static_cast<GLintptr>(attribute->alignedByteOffset));

				// Per-instance instead of per-vertex requires "GL_ARB_instanced_arrays"
				if (attribute->instancesPerElement > 0 && openGLRenderer.getExtensions().isGL_ARB_instanced_arrays())
				{
					// Sadly, DSA has no support for "GL_ARB_instanced_arrays", so, we have to use the bind way
					// -> Keep the bind-horror as local as possible

					#ifndef OPENGLRENDERER_NO_STATE_CLEANUP
						// Backup the currently bound OpenGL vertex array
						GLint openGLVertexArrayBackup = 0;
						glGetIntegerv(GL_VERTEX_ARRAY_BINDING, &openGLVertexArrayBackup);
					#endif

					// Bind this OpenGL vertex array
					glBindVertexArray(mOpenGLVertexArray);

					// Set divisor
					glVertexAttribDivisorARB(attributeLocation, attribute->instancesPerElement);

					#ifndef OPENGLRENDERER_NO_STATE_CLEANUP
						// Be polite and restore the previous bound OpenGL vertex array
						glBindVertexArray(static_cast<GLuint>(openGLVertexArrayBackup));
					#endif
				}

				// Enable OpenGL vertex attribute array
				glEnableVertexArrayAttribEXT(mOpenGLVertexArray, attributeLocation);
			}
		}

		// Check the used index buffer
		// -> In case of no index buffer we don't bind buffer 0, there's not really a point in it
		if (nullptr != indexBuffer)
		{
			if (isARB_DSA)
			{
				// Bind the index buffer
				glVertexArrayElementBuffer(mOpenGLVertexArray, indexBuffer->getOpenGLElementArrayBuffer());
			}
			else
			{
				// Sadly, EXT DSA has no support for element array buffer, so, we have to use the bind way
				// -> Keep the bind-horror as local as possible

				#ifndef OPENGLRENDERER_NO_STATE_CLEANUP
					// Backup the currently bound OpenGL vertex array
					GLint openGLVertexArrayBackup = 0;
					glGetIntegerv(GL_VERTEX_ARRAY_BINDING, &openGLVertexArrayBackup);

					// Backup the currently bound OpenGL element array buffer
					GLint openGLElementArrayBufferBackup = 0;
					glGetIntegerv(GL_ELEMENT_ARRAY_BUFFER_BINDING_ARB, &openGLElementArrayBufferBackup);
				#endif

				// Bind this OpenGL vertex array
				glBindVertexArray(mOpenGLVertexArray);

				// Bind OpenGL element array buffer
				glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, indexBuffer->getOpenGLElementArrayBuffer());

				#ifndef OPENGLRENDERER_NO_STATE_CLEANUP
					// Be polite and restore the previous bound OpenGL vertex array
					glBindVertexArray(static_cast<GLuint>(openGLVertexArrayBackup));

					// Be polite and restore the previous bound OpenGL element array buffer
					glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, static_cast<GLuint>(openGLElementArrayBufferBackup));
				#endif
			}
		}
	}
コード例 #15
0
void
piglit_init(int argc, char **argv)
{
	GLuint vertices_bo;
	GLuint instance_bo;
	GLuint indices_bo;
	GLuint indirect_bo;

	piglit_require_extension("GL_ARB_draw_indirect");
	piglit_require_extension("GL_ARB_base_instance");
	piglit_require_extension("GL_ARB_instanced_arrays");

	glGenVertexArrays(1, &vao);
	glBindVertexArray(vao);

	glGenBuffers(1, &vertices_bo);
	glBindBuffer(GL_ARRAY_BUFFER, vertices_bo);
	glBufferData(GL_ARRAY_BUFFER, sizeof(vertices_data), vertices_data, GL_STATIC_DRAW);
	glEnableVertexAttribArray(0);
	glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, 0, 0);

	glGenBuffers(1, &instance_bo);
	glBindBuffer(GL_ARRAY_BUFFER, instance_bo);
	glBufferData(GL_ARRAY_BUFFER, sizeof(instance_data), instance_data, GL_STATIC_DRAW);
	glEnableVertexAttribArray(1);
	glVertexAttribIPointer(1, 1, GL_INT, 0, 0);
	glVertexAttribDivisorARB(1, 1);

	glGenBuffers(1, &indices_bo);
	glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, indices_bo);
	glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indices_data), indices_data, GL_STATIC_DRAW);

	glGenBuffers(1, &indirect_bo);
	glBindBuffer(GL_DRAW_INDIRECT_BUFFER, indirect_bo);
	glBufferData(GL_DRAW_INDIRECT_BUFFER, sizeof(indirect_data), indirect_data, GL_STATIC_DRAW);

	prog = piglit_build_simple_program(
			"#version 130\n"
			"#extension GL_ARB_explicit_attrib_location: require\n"
			"#extension GL_ARB_draw_instanced: require\n"
			"\n"
			"layout(location=0) in vec2 pos;\n"
			"layout(location=1) in int instance_in;\n"
			"\n"
			"flat out int instance;\n"
			"\n"
			"void main() {\n"
			"	gl_Position = vec4(pos, 0, 1);\n"
			"	instance = instance_in;\n"
			"}\n",

			"#version 130\n"
			"\n"
			"flat in int instance;\n"
			"\n"
			"void main() {\n"
			"	if (instance == 42) {\n"
			"		gl_FragColor = vec4(0,1,0,1);\n"
			"	} else {\n"
			"		gl_FragColor = vec4(1,0,0,1);\n"
			"	}\n"
			"}\n");

	glBindVertexArray(0);
}
コード例 #16
0
void GLInstancingRenderer::renderSceneInternal(int renderMode)
{
	
//	glEnable(GL_DEPTH_TEST);

	GLint dims[4];
        glGetIntegerv(GL_VIEWPORT, dims);
	//we need to get the viewport dims, because on Apple Retina the viewport dimension is different from screenWidth
	//printf("dims=%d,%d,%d,%d\n",dims[0],dims[1],dims[2],dims[3]);
	// Accept fragment if it closer to the camera than the former one
	//glDepthFunc(GL_LESS); 

	// Cull triangles which normal is not towards the camera
	//glEnable(GL_CULL_FACE);



	 B3_PROFILE("GLInstancingRenderer::RenderScene");

	 {
		B3_PROFILE("init");
		init();
	 }

    GLint err = glGetError();
    b3Assert(err==GL_NO_ERROR);


	float depthProjectionMatrix[4][4];
	GLfloat depthModelViewMatrix[4][4];
	//GLfloat depthModelViewMatrix2[4][4];

	// Compute the MVP matrix from the light's point of view
	if (renderMode==B3_CREATE_SHADOWMAP_RENDERMODE)
	{
		if (!m_data->m_shadowMap)
		{
			glActiveTexture(GL_TEXTURE0);

			glGenTextures(1,&m_data->m_shadowTexture);
			glBindTexture(GL_TEXTURE_2D,m_data->m_shadowTexture);
			//glTexImage2D(GL_TEXTURE_2D,0,GL_DEPTH_COMPONENT16,m_screenWidth,m_screenHeight,0,GL_DEPTH_COMPONENT,GL_FLOAT,0);
			//glTexImage2D(GL_TEXTURE_2D,0,GL_DEPTH_COMPONENT32,m_screenWidth,m_screenHeight,0,GL_DEPTH_COMPONENT,GL_FLOAT,0);
			glTexImage2D(GL_TEXTURE_2D, 0,GL_DEPTH_COMPONENT16, shadowMapWidth, shadowMapHeight, 0,GL_DEPTH_COMPONENT, GL_FLOAT, 0);
			
			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);

			float l_ClampColor[] = {1.0, 1.0, 1.0, 1.0};
			glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR, l_ClampColor);
			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER);
			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_BORDER);
//			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
//			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_COMPARE_FUNC, GL_LEQUAL);
			glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_COMPARE_MODE, GL_COMPARE_R_TO_TEXTURE);

			m_data->m_shadowMap=new GLRenderToTexture();
			m_data->m_shadowMap->init(shadowMapWidth, shadowMapHeight,m_data->m_shadowTexture,RENDERTEXTURE_DEPTH);
		}
		m_data->m_shadowMap->enable();
		glViewport(0,0,shadowMapWidth,shadowMapHeight);
		//glClearColor(1,1,1,1);
		glClear(GL_DEPTH_BUFFER_BIT);
		//glClearColor(0.3,0.3,0.3,1);

//		m_data->m_shadowMap->disable();
	//	return;
	//	glEnable(GL_CULL_FACE);
//		glCullFace(GL_BACK); // Cull back-facing triangles -> draw only front-facing triangles

		GLint err = glGetError();
		b3Assert(err==GL_NO_ERROR);
	} 
	static b3Vector3 lightPos = b3MakeVector3(-5.f,200,-40);//20,15,10);//-13,6,2);// = b3Vector3(0.5f,2,2);
//	lightPos.y+=0.1f;
	b3CreateOrtho(-shadowMapWorldSize,shadowMapWorldSize,-shadowMapWorldSize,shadowMapWorldSize,1,300,depthProjectionMatrix);//-14,14,-14,14,1,200, depthProjectionMatrix);
	float depthViewMatrix[4][4];
	b3Vector3 center = b3MakeVector3(0,0,0);
	b3Vector3 up =b3MakeVector3(0,1,0);
	b3CreateLookAt(lightPos,center,up,&depthViewMatrix[0][0]);
	//b3CreateLookAt(lightPos,m_data->m_cameraTargetPosition,b3Vector3(0,1,0),(float*)depthModelViewMatrix2);

	GLfloat depthModelMatrix[4][4];
	b3CreateDiagonalMatrix(1.f,depthModelMatrix);

	b3Matrix4x4Mul(depthViewMatrix, depthModelMatrix, depthModelViewMatrix);
		
	GLfloat depthMVP[4][4];
	b3Matrix4x4Mul(depthProjectionMatrix,depthModelViewMatrix,depthMVP);
	
	GLfloat biasMatrix[4][4]={
			0.5, 0.0, 0.0, 0.0, 
			0.0, 0.5, 0.0, 0.0,
			0.0, 0.0, 0.5, 0.0,
			0.5, 0.5, 0.5, 1.0
	};

	GLfloat depthBiasMVP[4][4];
	b3Matrix4x4Mul(biasMatrix,depthMVP,depthBiasMVP);

	
	//float m_frustumZNear=0.1;
    //float m_frustumZFar=100.f;

	

	//b3CreateFrustum(-m_frustumZNear, m_frustumZNear, -m_frustumZNear, m_frustumZNear, m_frustumZNear, m_frustumZFar,(float*)depthProjectionMatrix);
    

    //b3CreateLookAt(lightPos,m_data->m_cameraTargetPosition,b3Vector3(0,0,1),(float*)depthModelViewMatrix);

	{
		B3_PROFILE("updateCamera");
		updateCamera();
	}

    err = glGetError();
    b3Assert(err==GL_NO_ERROR);
    


	//	glBindBuffer(GL_ARRAY_BUFFER, 0);
	{
		B3_PROFILE("glFlush2");

		glBindBuffer(GL_ARRAY_BUFFER, m_data->m_vbo);
		glFlush();
	}
    err = glGetError();
    b3Assert(err==GL_NO_ERROR);
    

	int totalNumInstances = 0;

	for (int i=0;i<m_graphicsInstances.size();i++)
	{
		totalNumInstances+=m_graphicsInstances[i]->m_numGraphicsInstances;
	}

	int curOffset = 0;
	GLuint lastBindTexture = 0;


	for (int i=0;i<m_graphicsInstances.size();i++)
	{
		
		b3GraphicsInstance* gfxObj = m_graphicsInstances[i];
		if (gfxObj->m_numGraphicsInstances)
		{
			glActiveTexture(GL_TEXTURE0);
			GLuint curBindTexture = 0;
			if (gfxObj->m_texturehandle)
				curBindTexture = gfxObj->m_texturehandle;
			else
				curBindTexture = m_data->m_defaultTexturehandle;

			//if (lastBindTexture != curBindTexture)
			{
				glBindTexture(GL_TEXTURE_2D,curBindTexture);
			}
			lastBindTexture = curBindTexture;

			err = glGetError();
			b3Assert(err==GL_NO_ERROR);
	//	int myOffset = gfxObj->m_instanceOffset*4*sizeof(float);

		int POSITION_BUFFER_SIZE = (totalNumInstances*sizeof(float)*4);
		int ORIENTATION_BUFFER_SIZE = (totalNumInstances*sizeof(float)*4);
		int COLOR_BUFFER_SIZE = (totalNumInstances*sizeof(float)*4);
//		int SCALE_BUFFER_SIZE = (totalNumInstances*sizeof(float)*3);

		glBindVertexArray(gfxObj->m_cube_vao);

		
		int vertexStride = 9*sizeof(float);
		int vertexBase = gfxObj->m_vertexArrayOffset*vertexStride;

		glVertexAttribPointer(0, 4, GL_FLOAT, GL_FALSE, 9*sizeof(float), (GLvoid*)vertexBase);
		glVertexAttribPointer(1, 4, GL_FLOAT, GL_FALSE, 0, (GLvoid *)(curOffset*4*sizeof(float)+m_maxShapeCapacityInBytes));
		glVertexAttribPointer(2, 4, GL_FLOAT, GL_FALSE, 0, (GLvoid *)(curOffset*4*sizeof(float)+m_maxShapeCapacityInBytes+POSITION_BUFFER_SIZE));
		int uvoffset = 7*sizeof(float)+vertexBase;
		int normaloffset = 4*sizeof(float)+vertexBase;

		glVertexAttribPointer(3, 2, GL_FLOAT, GL_FALSE, 9*sizeof(float), (GLvoid *)uvoffset);
		glVertexAttribPointer(4, 3, GL_FLOAT, GL_FALSE, 9*sizeof(float), (GLvoid *)normaloffset);
		glVertexAttribPointer(5, 4, GL_FLOAT, GL_FALSE, 0, (GLvoid *)(curOffset*4*sizeof(float)+m_maxShapeCapacityInBytes+POSITION_BUFFER_SIZE+ORIENTATION_BUFFER_SIZE));
		glVertexAttribPointer(6, 3, GL_FLOAT, GL_FALSE, 0, (GLvoid *)(curOffset*3*sizeof(float)+m_maxShapeCapacityInBytes+POSITION_BUFFER_SIZE+ORIENTATION_BUFFER_SIZE+COLOR_BUFFER_SIZE));

		glEnableVertexAttribArray(0);
		glEnableVertexAttribArray(1);
		glEnableVertexAttribArray(2);
		glEnableVertexAttribArray(3);
		glEnableVertexAttribArray(4);
		glEnableVertexAttribArray(5);
		glEnableVertexAttribArray(6);
		glVertexAttribDivisorARB(0, 0);
		glVertexAttribDivisorARB(1, 1);
		glVertexAttribDivisorARB(2, 1);
		glVertexAttribDivisorARB(3, 0);
		glVertexAttribDivisorARB(4, 0);
		glVertexAttribDivisorARB(5, 1);
		glVertexAttribDivisorARB(6, 1);
        
		
		

		
		
			int indexCount = gfxObj->m_numIndices;
			int indexOffset = 0;

			glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, gfxObj->m_index_vbo);
			{
				B3_PROFILE("glDrawElementsInstanced");
				
				if (gfxObj->m_primitiveType==B3_GL_POINTS)
				{
					glUseProgram(instancingShaderPointSprite);
					glUniformMatrix4fv(ProjectionMatrixPointSprite, 1, false, &projectionMatrix[0]);
					glUniformMatrix4fv(ModelViewMatrixPointSprite, 1, false, &modelviewMatrix[0]);
					glUniform1f(screenWidthPointSprite,m_screenWidth);
					
					//glUniform1i(uniform_texture_diffusePointSprite, 0);
					  err = glGetError();
    b3Assert(err==GL_NO_ERROR);
					glPointSize(20);

#ifndef __APPLE__
					glEnable(GL_POINT_SPRITE_ARB);
//					glTexEnvi(GL_POINT_SPRITE_ARB, GL_COORD_REPLACE_ARB, GL_TRUE);
#endif

					glEnable(GL_VERTEX_PROGRAM_POINT_SIZE);
					glDrawElementsInstanced(GL_POINTS, indexCount, GL_UNSIGNED_INT, (void*)indexOffset, gfxObj->m_numGraphicsInstances);
				} else
				{
					switch (renderMode)
					{

					case B3_DEFAULT_RENDERMODE:
						{
							glUseProgram(instancingShader);
							glUniformMatrix4fv(ProjectionMatrix, 1, false, &projectionMatrix[0]);
							glUniformMatrix4fv(ModelViewMatrix, 1, false, &modelviewMatrix[0]);
							glUniform1i(uniform_texture_diffuse, 0);
							glDrawElementsInstanced(GL_TRIANGLES, indexCount, GL_UNSIGNED_INT, (void*)indexOffset, gfxObj->m_numGraphicsInstances);
							break;
						}
						case B3_CREATE_SHADOWMAP_RENDERMODE:
						{
							glUseProgram(createShadowMapInstancingShader);
							glUniformMatrix4fv(createShadow_depthMVP, 1, false, &depthMVP[0][0]);
							glDrawElementsInstanced(GL_TRIANGLES, indexCount, GL_UNSIGNED_INT, (void*)indexOffset, gfxObj->m_numGraphicsInstances);
							break;
						}

					case B3_USE_SHADOWMAP_RENDERMODE:
						{
							glUseProgram(useShadowMapInstancingShader);
							glUniformMatrix4fv(useShadow_ProjectionMatrix, 1, false, &projectionMatrix[0]);
							glUniformMatrix4fv(useShadow_ModelViewMatrix, 1, false, &modelviewMatrix[0]);
							float MVP[16];
							b3Matrix4x4Mul16(projectionMatrix,modelviewMatrix,MVP);
							glUniformMatrix4fv(useShadow_MVP, 1, false, &MVP[0]);
							glUniformMatrix4fv(useShadow_DepthBiasModelViewMatrix, 1, false, &depthBiasMVP[0][0]);
							glActiveTexture(GL_TEXTURE1);
							glBindTexture(GL_TEXTURE_2D, m_data->m_shadowTexture);
							glUniform1i(useShadow_shadowMap,1);
							glDrawElementsInstanced(GL_TRIANGLES, indexCount, GL_UNSIGNED_INT, (void*)indexOffset, gfxObj->m_numGraphicsInstances);
							break;
						}
					default:
						{
						//	b3Assert(0);
						}
					};
				}

				
				//glDrawElementsInstanced(GL_LINE_LOOP, indexCount, GL_UNSIGNED_INT, (void*)indexOffset, gfxObj->m_numGraphicsInstances);
			}
		}
		curOffset+= gfxObj->m_numGraphicsInstances;
	}

	{
			B3_PROFILE("glFlush");
			glFlush();
		}
	if (renderMode==B3_CREATE_SHADOWMAP_RENDERMODE)
	{
	//	writeTextureToPng(shadowMapWidth,shadowMapHeight,"shadowmap.png",4);
		m_data->m_shadowMap->disable();
		glViewport(dims[0],dims[1],dims[2],dims[3]);

	}

    err = glGetError();
    b3Assert(err==GL_NO_ERROR);
	{
		B3_PROFILE("glUseProgram(0);");
		glUseProgram(0);
		glBindBuffer(GL_ARRAY_BUFFER,0);
		glBindVertexArray(0);
	}
	

	

	err = glGetError();
	b3Assert(err==GL_NO_ERROR);
	
}
JNIEXPORT void JNICALL Java_org_lwjgl_opengl_ARBInstancedArrays_nglVertexAttribDivisorARB(JNIEnv *env, jclass clazz, jint index, jint divisor, jlong function_pointer) {
	glVertexAttribDivisorARBPROC glVertexAttribDivisorARB = (glVertexAttribDivisorARBPROC)((intptr_t)function_pointer);
	glVertexAttribDivisorARB(index, divisor);
}
コード例 #18
0
/* 
 * bindShaders - bind buffer data and pass shader variables.
 * code based on example in http://www.opengl-tutorial.org/intermediate-tutorials/billboards-particles/particles-instancing/ 
 */
void ParticleSystem::bindShaders()
{
    /* Update the buffers that OpenGL uses for rendering */
    glBindBuffer(GL_ARRAY_BUFFER, particles_position_buffer);
    glBufferData(GL_ARRAY_BUFFER, max_particles * 4 * sizeof(GLfloat), NULL, GL_STREAM_DRAW); // Buffer orphaning, a common way to improve streaming perf. See above link for details.
    glBufferSubData(GL_ARRAY_BUFFER, 0, active_particles * sizeof(GLfloat) * 4, position_size_data);

    glBindBuffer(GL_ARRAY_BUFFER, particles_color_buffer);
    glBufferData(GL_ARRAY_BUFFER, max_particles * 4 * sizeof(GLubyte), NULL, GL_STREAM_DRAW); // Buffer orphaning, a common way to improve streaming perf. See above link for details.
    glBufferSubData(GL_ARRAY_BUFFER, 0, active_particles * sizeof(GLubyte) * 4, color_data);

    glBindBuffer(GL_ARRAY_BUFFER, particles_age_buffer);
    glBufferData(GL_ARRAY_BUFFER, max_particles * sizeof(GLfloat), NULL, GL_STREAM_DRAW); // Buffer orphaning, a common way to improve streaming perf. See above link for details.
    glBufferSubData(GL_ARRAY_BUFFER, 0, active_particles * sizeof(GLfloat), age_data);

    glEnable(GL_BLEND);
    glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);

    // Use our shader
    glUseProgram(programID);

    // Bind our texture in Texture Unit 0
    glActiveTexture(GL_TEXTURE0);
    glBindTexture(GL_TEXTURE_2D, texture);
    glUniform1i(texture_ID, 0);

    glUniform3f(CameraRight_worldspace_ID, model_view[0][0], model_view[1][0], model_view[2][0]);
    glUniform3f(CameraUp_worldspace_ID, model_view[0][1], model_view[1][1], model_view[2][1]);
    glUniformMatrix4fv(ViewProjMatrixID, 1, GL_FALSE, &model_projection[0][0]);

    /* billboard vertices */
    glEnableVertexAttribArray(squareVerticesID);
    glBindBuffer(GL_ARRAY_BUFFER, billboard_vertex_buffer);
    glVertexAttribPointer(squareVerticesID, 3, GL_FLOAT, GL_FALSE, 0, (void *)0);

    /* bind particle attributes */

    /* positions of particles' centers */
    glEnableVertexAttribArray(xyzsID);
    glBindBuffer(GL_ARRAY_BUFFER, particles_position_buffer);
    glVertexAttribPointer(xyzsID, 4, GL_FLOAT, GL_FALSE, 0, (void *)0);

    /* particles' colors */
    glEnableVertexAttribArray(colorID);
    glBindBuffer(GL_ARRAY_BUFFER, particles_color_buffer);
    glVertexAttribPointer(colorID, 4, GL_UNSIGNED_BYTE, GL_TRUE, 0, (void *)0);

    /* particles' age */
    glEnableVertexAttribArray(ageID);
    glBindBuffer(GL_ARRAY_BUFFER, particles_age_buffer);
    glVertexAttribPointer(ageID, 1, GL_FLOAT, GL_TRUE, 0, (void *)0);

    glVertexAttribDivisorARB(squareVerticesID, 0); // particles vertices : always reuse the same 4 vertices -> 0
    glVertexAttribDivisorARB(xyzsID, 1); // positions: one per quad (its center)                 -> 1
    glVertexAttribDivisorARB(colorID, 1); // color: one per quad                                  -> 1
    glVertexAttribDivisorARB(ageID, 1); /* age: one per quad */
                             
    /* draw each instance */
    glDrawArraysInstancedARB(GL_TRIANGLE_STRIP, 0, 4, active_particles);

    glDisableVertexAttribArray(squareVerticesID);
    glDisableVertexAttribArray(xyzsID);
    glDisableVertexAttribArray(colorID);
    glDisableVertexAttribArray(ageID);
}
コード例 #19
0
ファイル: instancing.cpp プロジェクト: hanwj/myStudy
void InstancingApp::Initialize(void)
{
    GLenum err = glewInit();
    if (GLEW_OK != err)
    {
        /* Problem: glewInit failed, something is seriously wrong. */
        fprintf(stderr, "Error: %s\n", glewGetErrorString(err));
    }

    instancingProg = gltLoadShaderPair("instancing.vs", "instancing.fs");
    glBindAttribLocation(instancingProg, 0, "position");
    glBindAttribLocation(instancingProg, 1, "instance_color");
    glBindAttribLocation(instancingProg, 2, "instance_position");
    glLinkProgram(instancingProg);
    glUseProgram(instancingProg);

    static const GLfloat square_vertices[] =
    {
        -1.0f, -1.0f, 0.0f, 1.0f,
         1.0f, -1.0f, 0.0f, 1.0f,
         1.0f,  1.0f, 0.0f, 1.0f,
        -1.0f,  1.0f, 0.0f, 1.0f
    };

    static const GLfloat instance_colors[] =
    {
        1.0f, 0.0f, 0.0f, 1.0f,
        0.0f, 1.0f, 0.0f, 1.0f,
        0.0f, 0.0f, 1.0f, 1.0f,
        1.0f, 1.0f, 0.0f, 1.0f
    };

    static const GLfloat instance_positions[] =
    {
        -2.0f, -2.0f, 0.0f, 0.0f,
         2.0f, -2.0f, 0.0f, 0.0f,
         2.0f,  2.0f, 0.0f, 0.0f,
        -2.0f,  2.0f, 0.0f, 0.0f
    };

    GLuint offset = 0;

    glGenVertexArrays(1, &square_vao);
    glGenBuffers(1, &square_vbo);
    glBindVertexArray(square_vao);
    glBindBuffer(GL_ARRAY_BUFFER, square_vbo);
    glBufferData(GL_ARRAY_BUFFER, sizeof(square_vertices) + sizeof(instance_colors) + sizeof(instance_positions), NULL, GL_STATIC_DRAW);
    glBufferSubData(GL_ARRAY_BUFFER, offset, sizeof(square_vertices), square_vertices);
    offset += sizeof(square_vertices);
    glBufferSubData(GL_ARRAY_BUFFER, offset, sizeof(instance_colors), instance_colors);
    offset += sizeof(instance_colors);
    glBufferSubData(GL_ARRAY_BUFFER, offset, sizeof(instance_positions), instance_positions);
    offset += sizeof(instance_positions);

    glVertexAttribPointer(0, 4, GL_FLOAT, GL_FALSE, 0, 0);
    glVertexAttribPointer(1, 4, GL_FLOAT, GL_FALSE, 0, (GLvoid *)sizeof(square_vertices));
    glVertexAttribPointer(2, 4, GL_FLOAT, GL_FALSE, 0, (GLvoid *)(sizeof(square_vertices) + sizeof(instance_colors)));

    glEnableVertexAttribArray(0);
    glEnableVertexAttribArray(1);
    glEnableVertexAttribArray(2);

    glVertexAttribDivisorARB(1, 1);
    glVertexAttribDivisorARB(2, 1);
}
コード例 #20
0
ファイル: instanced_arrays.c プロジェクト: kphillisjr/piglit
static GLboolean
test_instancing(GLuint divisor)
{
    static const GLfloat verts[4][2] = {
        {-1, -1}, {1, -1}, {1, 1}, {-1, 1}
    };
    GLuint vbo;
    uintptr_t offset = 0;

    if (use_vbo) {
        glGenBuffers(1, &vbo);
        glBindBuffer(GL_ARRAY_BUFFER, vbo);
        glBufferData(GL_ARRAY_BUFFER,
                     sizeof(verts) + sizeof(Positions) + sizeof(Colors),
                     NULL,
                     GL_STATIC_DRAW);
        glBufferSubData(GL_ARRAY_BUFFER, offset, sizeof(verts), verts);
        glVertexPointer(2, GL_FLOAT, 0, (void*) offset);
        offset += sizeof(verts);

        glBufferSubData(GL_ARRAY_BUFFER, offset, sizeof(Positions), Positions);
        glVertexAttribPointer(PosAttrib, 2, GL_FLOAT, GL_FALSE, 0, (void*) offset);
        offset += sizeof(Positions);

        glBufferSubData(GL_ARRAY_BUFFER, offset, sizeof(Colors), Colors);
        glVertexAttribPointer(ColorAttrib, 4, GL_FLOAT, GL_FALSE, 0, (void*) offset);
        offset += sizeof(Colors);

        glBindBuffer(GL_ARRAY_BUFFER, 0);
    } else {
        glVertexPointer(2, GL_FLOAT, 0, verts);
        glVertexAttribPointer(PosAttrib, 2, GL_FLOAT, GL_FALSE, 0, Positions);
        glVertexAttribPointer(ColorAttrib, 4, GL_FLOAT, GL_FALSE, 0, Colors);
    }

    glEnableClientState(GL_VERTEX_ARRAY);
    glEnableVertexAttribArray(PosAttrib);
    glEnableVertexAttribArray(ColorAttrib);

    glVertexAttribDivisorARB(PosAttrib, 1);
    /* advance color once every 'n' instances */
    glVertexAttribDivisorARB(ColorAttrib, divisor);

    glClear(GL_COLOR_BUFFER_BIT);

    glUseProgram(Program);

    glDrawArraysInstancedARB(GL_POLYGON, 0, 4, PRIMS);

    glUseProgram(0);

    if (use_vbo) {
        glDeleteBuffers(1, &vbo);
    }

    {
        GLint i;
        GLint pos[4];

        for (i = 0; i < PRIMS; i++) {
            GLuint elem = i / divisor;

            /* use glRasterPos to determine where to read a sample pixel */
            glRasterPos2fv(Positions[i]);
            glGetIntegerv(GL_CURRENT_RASTER_POSITION, pos);

            if (!piglit_probe_pixel_rgba(pos[0], pos[1], Colors[elem])) {
                fprintf(stderr, "%s: instance %d failed to draw correctly\n",
                        TestName, i);
                fprintf(stderr, "%s: color instance divisor = %u\n",
                        TestName, divisor);
                piglit_present_results();
                return GL_FALSE;
            }
        }
    }

    glDisableClientState(GL_VERTEX_ARRAY);
    glDisableVertexAttribArray(PosAttrib);
    glDisableVertexAttribArray(ColorAttrib);

    piglit_present_results();

    return GL_TRUE;
}