Пример #1
0
/*
* RB_DrawElementsInstanced
*
* Draws <numInstances> instances of elements
*/
void RB_DrawElementsInstanced( int firstVert, int numVerts, int firstElem, int numElems,
                               int firstShadowVert, int numShadowVerts, int firstShadowElem, int numShadowElems,
                               int numInstances, instancePoint_t *instances )
{
    if( !numInstances ) {
        return;
    }

    // currently not supporting dynamic instances
    // they will need a separate stream so they can be used with both static and dynamic geometry
    // (dynamic geometry will need changes to rbDynamicDraw_t)
    assert( rb.currentVBOId > RB_VBO_NONE );
    if( rb.currentVBOId <= RB_VBO_NONE ) {
        return;
    }

    rb.drawElements.numVerts = numVerts;
    rb.drawElements.numElems = numElems;
    rb.drawElements.firstVert = firstVert;
    rb.drawElements.firstElem = firstElem;
    rb.drawElements.numInstances = 0;

    rb.drawShadowElements.numVerts = numShadowVerts;
    rb.drawShadowElements.numElems = numShadowElems;
    rb.drawShadowElements.firstVert = firstShadowVert;
    rb.drawShadowElements.firstElem = firstShadowElem;
    rb.drawShadowElements.numInstances = 0;

    // check for vertex-attrib-divisor style instancing
    if( glConfig.ext.instanced_arrays ) {
        if( rb.currentVBO->instancesOffset ) {
            // static VBO's must come with their own set of instance data
            rb.currentVAttribs |= VATTRIB_INSTANCES_BITS;
        }
    }

    if( !( rb.currentVAttribs & VATTRIB_INSTANCES_BITS ) ) {
        // can't use instanced arrays so we'll have to manually update
        // the uniform state in between draw calls
        if( rb.maxDrawInstances < numInstances ) {
            if( rb.drawInstances ) {
                RB_Free( rb.drawInstances );
            }
            rb.drawInstances = RB_Alloc( numInstances * sizeof( *rb.drawInstances ) );
            rb.maxDrawInstances = numInstances;
        }
        memcpy( rb.drawInstances, instances, numInstances * sizeof( *instances ) );
    }

    rb.drawElements.numInstances = numInstances;
    rb.drawShadowElements.numInstances = numInstances;
    RB_DrawElements_();
}
Пример #2
0
/*
* RB_DrawElementsInstanced
*
* Draws <numInstances> instances of elements
*/
void RB_DrawElementsInstanced( int firstVert, int numVerts, int firstElem, int numElems, 
	int numInstances, instancePoint_t *instances )
{
	if( !numInstances ) {
		return;
	}

	// check for vertex-attrib-divisor style instancing
	if( glConfig.ext.instanced_arrays ) {
		// upload instances
		if( rb.currentVBOId < RB_VBO_NONE ) {
			rb.currentVAttribs |= VATTRIB_INSTANCES_BIT;

			// FIXME: this is nasty!
			while( numInstances > MAX_STREAM_VBO_INSTANCES ) {
				R_UploadVBOInstancesData( rb.currentVBO, 0, MAX_STREAM_VBO_INSTANCES, instances );

				rb.drawElements.numInstances = MAX_STREAM_VBO_INSTANCES;
				RB_DrawElements_( firstVert, numVerts, firstElem, numElems );

				instances += MAX_STREAM_VBO_INSTANCES;
				numInstances -= MAX_STREAM_VBO_INSTANCES;
			}

			if( !numInstances ) {
				return;
			}

			R_UploadVBOInstancesData( rb.currentVBO, 0, numInstances, instances );
		} else if( rb.currentVBO->instancesOffset ) {
			// static VBO's must come with their own set of instance data
			rb.currentVAttribs |= VATTRIB_INSTANCES_BIT;
		}
	}

	if( !( rb.currentVAttribs & VATTRIB_INSTANCES_BIT ) ) {
		// can't use instanced arrays so we'll have to manually update
		// the uniform state in between draw calls
		if( rb.maxDrawInstances < numInstances ) {
			if( rb.drawInstances ) {
				RB_Free( rb.drawInstances );
			}
			rb.drawInstances = RB_Alloc( numInstances * sizeof( *rb.drawInstances ) );
			rb.maxDrawInstances = numInstances;
		}
		memcpy( rb.drawInstances, instances, numInstances * sizeof( *instances ) );
	}

	rb.drawElements.numInstances = numInstances;
	RB_DrawElements_( firstVert, numVerts, firstElem, numElems );
}