diff --git a/src/bgfx.cpp b/src/bgfx.cpp index 2a93d7d13..404f5227a 100644 --- a/src/bgfx.cpp +++ b/src/bgfx.cpp @@ -3495,7 +3495,7 @@ error: void setVertexBuffer(VertexBufferHandle _handle, uint32_t _startVertex, uint32_t _numVertices) { BGFX_CHECK_MAIN_THREAD(); - s_ctx->setVertexBuffer(_handle, _startVertex, _numVertices); + s_ctx->setVertexBuffer(0, _handle, _startVertex, _numVertices); } void setVertexBuffer(DynamicVertexBufferHandle _handle) @@ -3506,7 +3506,7 @@ error: void setVertexBuffer(DynamicVertexBufferHandle _handle, uint32_t _startVertex, uint32_t _numVertices) { BGFX_CHECK_MAIN_THREAD(); - s_ctx->setVertexBuffer(_handle, _startVertex, _numVertices); + s_ctx->setVertexBuffer(0, _handle, _startVertex, _numVertices); } void setVertexBuffer(const TransientVertexBuffer* _tvb) @@ -3518,7 +3518,7 @@ error: { BGFX_CHECK_MAIN_THREAD(); BX_CHECK(NULL != _tvb, "_tvb can't be NULL"); - s_ctx->setVertexBuffer(_tvb, _startVertex, _numVertices); + s_ctx->setVertexBuffer(0, _tvb, _startVertex, _numVertices); } void setInstanceDataBuffer(const InstanceDataBuffer* _idb, uint32_t _num) @@ -3543,12 +3543,15 @@ error: void setTexture(uint8_t _stage, UniformHandle _sampler, TextureHandle _handle, uint32_t _flags) { BGFX_CHECK_MAIN_THREAD(); + BX_CHECK(_stage < BGFX_CONFIG_MAX_TEXTURE_SAMPLERS, "Invalid stage %d (max %d).", _stage, BGFX_CONFIG_MAX_TEXTURE_SAMPLERS); s_ctx->setTexture(_stage, _sampler, _handle, _flags); } void setTexture(uint8_t _stage, UniformHandle _sampler, FrameBufferHandle _handle, uint8_t _attachment, uint32_t _flags) { BGFX_CHECK_MAIN_THREAD(); + BX_CHECK(_stage < BGFX_CONFIG_MAX_TEXTURE_SAMPLERS, "Invalid stage %d (max %d).", _stage, BGFX_CONFIG_MAX_TEXTURE_SAMPLERS); + BX_CHECK(_attachment < g_caps.maxFBAttachments, "Frame buffer attachment index %d is invalid.", _attachment); s_ctx->setTexture(_stage, _sampler, _handle, _attachment, _flags); } @@ -3584,42 +3587,50 @@ error: void setBuffer(uint8_t _stage, IndexBufferHandle _handle, Access::Enum _access) { BGFX_CHECK_MAIN_THREAD(); + BX_CHECK(_stage < BGFX_CONFIG_MAX_TEXTURE_SAMPLERS, "Invalid stage %d (max %d).", _stage, BGFX_CONFIG_MAX_TEXTURE_SAMPLERS); s_ctx->setBuffer(_stage, _handle, _access); } void setBuffer(uint8_t _stage, VertexBufferHandle _handle, Access::Enum _access) { BGFX_CHECK_MAIN_THREAD(); + BX_CHECK(_stage < BGFX_CONFIG_MAX_TEXTURE_SAMPLERS, "Invalid stage %d (max %d).", _stage, BGFX_CONFIG_MAX_TEXTURE_SAMPLERS); s_ctx->setBuffer(_stage, _handle, _access); } void setBuffer(uint8_t _stage, DynamicIndexBufferHandle _handle, Access::Enum _access) { BGFX_CHECK_MAIN_THREAD(); + BX_CHECK(_stage < BGFX_CONFIG_MAX_TEXTURE_SAMPLERS, "Invalid stage %d (max %d).", _stage, BGFX_CONFIG_MAX_TEXTURE_SAMPLERS); s_ctx->setBuffer(_stage, _handle, _access); } void setBuffer(uint8_t _stage, DynamicVertexBufferHandle _handle, Access::Enum _access) { BGFX_CHECK_MAIN_THREAD(); + BX_CHECK(_stage < BGFX_CONFIG_MAX_TEXTURE_SAMPLERS, "Invalid stage %d (max %d).", _stage, BGFX_CONFIG_MAX_TEXTURE_SAMPLERS); s_ctx->setBuffer(_stage, _handle, _access); } void setBuffer(uint8_t _stage, IndirectBufferHandle _handle, Access::Enum _access) { BGFX_CHECK_MAIN_THREAD(); + BX_CHECK(_stage < BGFX_CONFIG_MAX_TEXTURE_SAMPLERS, "Invalid stage %d (max %d).", _stage, BGFX_CONFIG_MAX_TEXTURE_SAMPLERS); s_ctx->setBuffer(_stage, _handle, _access); } void setImage(uint8_t _stage, UniformHandle _sampler, TextureHandle _handle, uint8_t _mip, Access::Enum _access, TextureFormat::Enum _format) { BGFX_CHECK_MAIN_THREAD(); + BX_CHECK(_stage < BGFX_CONFIG_MAX_TEXTURE_SAMPLERS, "Invalid stage %d (max %d).", _stage, BGFX_CONFIG_MAX_TEXTURE_SAMPLERS); s_ctx->setImage(_stage, _sampler, _handle, _mip, _access, _format); } void setImage(uint8_t _stage, UniformHandle _sampler, FrameBufferHandle _handle, uint8_t _attachment, Access::Enum _access, TextureFormat::Enum _format) { BGFX_CHECK_MAIN_THREAD(); + BX_CHECK(_stage < BGFX_CONFIG_MAX_TEXTURE_SAMPLERS, "Invalid stage %d (max %d).", _stage, BGFX_CONFIG_MAX_TEXTURE_SAMPLERS); + BX_CHECK(_attachment < g_caps.maxFBAttachments, "Frame buffer attachment index %d is invalid.", _attachment); s_ctx->setImage(_stage, _sampler, _handle, _attachment, _access, _format); } @@ -3662,6 +3673,7 @@ error: { BGFX_CHECK_MAIN_THREAD(); BGFX_CHECK_CAPS(BGFX_CAPS_TEXTURE_BLIT, "Texture blit is not supported!"); + BX_CHECK(_attachment < g_caps.maxFBAttachments, "Frame buffer attachment index %d is invalid.", _attachment); s_ctx->blit(_id, _dst, _dstMip, _dstX, _dstY, _dstZ, _src, _attachment, _srcMip, _srcX, _srcY, _srcZ, _width, _height, _depth); } diff --git a/src/bgfx_p.h b/src/bgfx_p.h index a15d8d382..c0d673bd2 100644 --- a/src/bgfx_p.h +++ b/src/bgfx_p.h @@ -1216,6 +1216,20 @@ namespace bgfx } m_un; }; + struct Stream + { + void clear() + { + m_startVertex = 0; + m_handle.idx = invalidHandle; + m_decl.idx = invalidHandle; + } + + uint32_t m_startVertex; + VertexBufferHandle m_handle; + VertexDeclHandle m_decl; + }; + struct RenderDraw { void clear() @@ -1228,7 +1242,6 @@ namespace bgfx m_matrix = 0; m_startIndex = 0; m_numIndices = UINT32_MAX; - m_startVertex = 0; m_numVertices = UINT32_MAX; m_instanceDataOffset = 0; m_instanceDataStride = 0; @@ -1238,8 +1251,8 @@ namespace bgfx m_num = 1; m_submitFlags = BGFX_SUBMIT_EYE_FIRST; m_scissor = UINT16_MAX; - m_vertexBuffer.idx = invalidHandle; - m_vertexDecl.idx = invalidHandle; + m_streamMask = 0; + m_stream[0].clear(); m_indexBuffer.idx = invalidHandle; m_instanceDataBuffer.idx = invalidHandle; m_indirectBuffer.idx = invalidHandle; @@ -1255,6 +1268,7 @@ namespace bgfx } Binding m_bind[BGFX_CONFIG_MAX_TEXTURE_SAMPLERS]; + Stream m_stream[BGFX_CONFIG_MAX_VERTEX_STREAMS]; uint64_t m_stateFlags; uint64_t m_stencil; uint32_t m_rgba; @@ -1263,7 +1277,6 @@ namespace bgfx uint32_t m_matrix; uint32_t m_startIndex; uint32_t m_numIndices; - uint32_t m_startVertex; uint32_t m_numVertices; uint32_t m_instanceDataOffset; uint32_t m_numInstances; @@ -1273,9 +1286,8 @@ namespace bgfx uint16_t m_num; uint16_t m_scissor; uint8_t m_submitFlags; + uint8_t m_streamMask; - VertexBufferHandle m_vertexBuffer; - VertexDeclHandle m_vertexDecl; IndexBufferHandle m_indexBuffer; VertexBufferHandle m_instanceDataBuffer; IndirectBufferHandle m_indirectBuffer; @@ -1555,27 +1567,49 @@ namespace bgfx m_discard = 0 == _numIndices; } - void setVertexBuffer(VertexBufferHandle _handle, uint32_t _startVertex, uint32_t _numVertices) + void setVertexBuffer(uint8_t _stream, VertexBufferHandle _handle, uint32_t _startVertex, uint32_t _numVertices) { - m_draw.m_startVertex = _startVertex; - m_draw.m_numVertices = _numVertices; - m_draw.m_vertexBuffer = _handle; + const uint8_t bit = 1<<_stream; + BX_CHECK(0 == (m_draw.m_streamMask & bit), "Vertex stream %d is already set.", _stream); + m_draw.m_streamMask |= bit; + + Stream& stream = m_draw.m_stream[_stream]; + stream.m_startVertex = _startVertex; + stream.m_handle = _handle; + stream.m_decl.idx = invalidHandle; + m_draw.m_numVertices = bx::uint32_min(m_draw.m_numVertices, _numVertices); } - void setVertexBuffer(const DynamicVertexBuffer& _dvb, uint32_t _startVertex, uint32_t _numVertices) + void setVertexBuffer(uint8_t _stream, const DynamicVertexBuffer& _dvb, uint32_t _startVertex, uint32_t _numVertices) { - m_draw.m_startVertex = _dvb.m_startVertex + _startVertex; - m_draw.m_numVertices = bx::uint32_min(bx::uint32_imax(0, _dvb.m_numVertices - _startVertex), _numVertices); - m_draw.m_vertexBuffer = _dvb.m_handle; - m_draw.m_vertexDecl = _dvb.m_decl; + const uint8_t bit = 1<<_stream; + BX_CHECK(0 == (m_draw.m_streamMask & bit), "Vertex stream %d is already set.", _stream); + m_draw.m_streamMask |= bit; + + Stream& stream = m_draw.m_stream[_stream]; + stream.m_startVertex = _dvb.m_startVertex + _startVertex; + stream.m_handle = _dvb.m_handle; + stream.m_decl = _dvb.m_decl; + m_draw.m_numVertices = + bx::uint32_min(m_draw.m_numVertices + , bx::uint32_min(bx::uint32_imax(0, _dvb.m_numVertices - _startVertex), _numVertices) + ); } - void setVertexBuffer(const TransientVertexBuffer* _tvb, uint32_t _startVertex, uint32_t _numVertices) + void setVertexBuffer(uint8_t _stream, const TransientVertexBuffer* _tvb, uint32_t _startVertex, uint32_t _numVertices) { - m_draw.m_startVertex = _tvb->startVertex + _startVertex; - m_draw.m_numVertices = bx::uint32_min(bx::uint32_imax(0, _tvb->size/_tvb->stride - _startVertex), _numVertices); - m_draw.m_vertexBuffer = _tvb->handle; - m_draw.m_vertexDecl = _tvb->decl; + const uint8_t bit = 1<<_stream; + BX_CHECK(0 == (m_draw.m_streamMask & bit), "Vertex stream %d is already set.", _stream); + m_draw.m_streamMask |= bit; + + Stream& stream = m_draw.m_stream[_stream]; + stream.m_startVertex = _tvb->startVertex + _startVertex; + stream.m_handle = _tvb->handle; + stream.m_decl = _tvb->decl; + m_draw.m_numVertices = + bx::uint32_min(m_draw.m_numVertices + , bx::uint32_min(bx::uint32_imax(0, _tvb->size/_tvb->stride - _startVertex), _numVertices) + ); } void setInstanceDataBuffer(const InstanceDataBuffer* _idb, uint32_t _num) @@ -3702,22 +3736,25 @@ namespace bgfx m_submit->setIndexBuffer(_tib, _firstIndex, _numIndices); } - BGFX_API_FUNC(void setVertexBuffer(VertexBufferHandle _handle, uint32_t _startVertex, uint32_t _numVertices) ) + BGFX_API_FUNC(void setVertexBuffer(uint8_t _stream, VertexBufferHandle _handle, uint32_t _startVertex, uint32_t _numVertices) ) { BGFX_CHECK_HANDLE("setVertexBuffer", m_vertexBufferHandle, _handle); - m_submit->setVertexBuffer(_handle, _startVertex, _numVertices); + BX_CHECK(_stream < BGFX_CONFIG_MAX_VERTEX_STREAMS, "Invalid stream %d (max %d).", _stream, BGFX_CONFIG_MAX_VERTEX_STREAMS); + m_submit->setVertexBuffer(_stream, _handle, _startVertex, _numVertices); } - BGFX_API_FUNC(void setVertexBuffer(DynamicVertexBufferHandle _handle, uint32_t _startVertex, uint32_t _numVertices) ) + BGFX_API_FUNC(void setVertexBuffer(uint8_t _stream, DynamicVertexBufferHandle _handle, uint32_t _startVertex, uint32_t _numVertices) ) { BGFX_CHECK_HANDLE("setVertexBuffer", m_dynamicVertexBufferHandle, _handle); - m_submit->setVertexBuffer(m_dynamicVertexBuffers[_handle.idx], _startVertex, _numVertices); + BX_CHECK(_stream < BGFX_CONFIG_MAX_VERTEX_STREAMS, "Invalid stream %d (max %d).", _stream, BGFX_CONFIG_MAX_VERTEX_STREAMS); + m_submit->setVertexBuffer(_stream, m_dynamicVertexBuffers[_handle.idx], _startVertex, _numVertices); } - BGFX_API_FUNC(void setVertexBuffer(const TransientVertexBuffer* _tvb, uint32_t _startVertex, uint32_t _numVertices) ) + BGFX_API_FUNC(void setVertexBuffer(uint8_t _stream, const TransientVertexBuffer* _tvb, uint32_t _startVertex, uint32_t _numVertices) ) { BGFX_CHECK_HANDLE("setVertexBuffer", m_vertexBufferHandle, _tvb->handle); - m_submit->setVertexBuffer(_tvb, _startVertex, _numVertices); + BX_CHECK(_stream < BGFX_CONFIG_MAX_VERTEX_STREAMS, "Invalid stream %d (max %d).", _stream, BGFX_CONFIG_MAX_VERTEX_STREAMS); + m_submit->setVertexBuffer(_stream, _tvb, _startVertex, _numVertices); } BGFX_API_FUNC(void setInstanceDataBuffer(const InstanceDataBuffer* _idb, uint32_t _num) ) @@ -3754,7 +3791,6 @@ namespace bgfx BGFX_API_FUNC(void setTexture(uint8_t _stage, UniformHandle _sampler, FrameBufferHandle _handle, uint8_t _attachment, uint32_t _flags) ) { BGFX_CHECK_HANDLE_INVALID_OK("setTexture/FrameBufferHandle", m_frameBufferHandle, _handle); - BX_CHECK(_attachment < g_caps.maxFBAttachments, "Frame buffer attachment index %d is invalid.", _attachment); TextureHandle textureHandle = BGFX_INVALID_HANDLE; if (isValid(_handle) ) { @@ -3846,7 +3882,6 @@ namespace bgfx BGFX_API_FUNC(void setImage(uint8_t _stage, UniformHandle _sampler, FrameBufferHandle _handle, uint8_t _attachment, Access::Enum _access, TextureFormat::Enum _format) ) { - BX_CHECK(_attachment < g_caps.maxFBAttachments, "Frame buffer attachment index %d is invalid.", _attachment); TextureHandle textureHandle = BGFX_INVALID_HANDLE; if (isValid(_handle) ) { diff --git a/src/config.h b/src/config.h index f9e4ddd24..dd80f94e4 100644 --- a/src/config.h +++ b/src/config.h @@ -237,6 +237,10 @@ # define BGFX_CONFIG_MAX_VERTEX_BUFFERS (4<<10) #endif // BGFX_CONFIG_MAX_VERTEX_BUFFERS +#ifndef BGFX_CONFIG_MAX_VERTEX_STREAMS +# define BGFX_CONFIG_MAX_VERTEX_STREAMS 1 +#endif // BGFX_CONFIG_MAX_VERTEX_STREAMS + #ifndef BGFX_CONFIG_MAX_DYNAMIC_INDEX_BUFFERS # define BGFX_CONFIG_MAX_DYNAMIC_INDEX_BUFFERS (4<<10) #endif // BGFX_CONFIG_MAX_DYNAMIC_INDEX_BUFFERS diff --git a/src/renderer_d3d11.cpp b/src/renderer_d3d11.cpp index 605fc83ed..f58487b4b 100644 --- a/src/renderer_d3d11.cpp +++ b/src/renderer_d3d11.cpp @@ -5816,24 +5816,24 @@ BX_PRAGMA_DIAGNOSTIC_POP(); } if (programChanged - || currentState.m_vertexDecl.idx != draw.m_vertexDecl.idx - || currentState.m_vertexBuffer.idx != draw.m_vertexBuffer.idx + || currentState.m_stream[0].m_decl.idx != draw.m_stream[0].m_decl.idx + || currentState.m_stream[0].m_handle.idx != draw.m_stream[0].m_handle.idx || currentState.m_instanceDataBuffer.idx != draw.m_instanceDataBuffer.idx || currentState.m_instanceDataOffset != draw.m_instanceDataOffset || currentState.m_instanceDataStride != draw.m_instanceDataStride) { - currentState.m_vertexDecl = draw.m_vertexDecl; - currentState.m_vertexBuffer = draw.m_vertexBuffer; + currentState.m_stream[0].m_decl = draw.m_stream[0].m_decl; + currentState.m_stream[0].m_handle = draw.m_stream[0].m_handle; currentState.m_instanceDataBuffer.idx = draw.m_instanceDataBuffer.idx; currentState.m_instanceDataOffset = draw.m_instanceDataOffset; currentState.m_instanceDataStride = draw.m_instanceDataStride; - uint16_t handle = draw.m_vertexBuffer.idx; + uint16_t handle = draw.m_stream[0].m_handle.idx; if (invalidHandle != handle) { const VertexBufferD3D11& vb = m_vertexBuffers[handle]; - uint16_t decl = !isValid(vb.m_decl) ? draw.m_vertexDecl.idx : vb.m_decl.idx; + uint16_t decl = !isValid(vb.m_decl) ? draw.m_stream[0].m_decl.idx : vb.m_decl.idx; const VertexDecl& vertexDecl = m_vertexDecls[decl]; uint32_t stride = vertexDecl.m_stride; uint32_t offset = 0; @@ -5877,13 +5877,13 @@ BX_PRAGMA_DIAGNOSTIC_POP(); } } - if (isValid(currentState.m_vertexBuffer) ) + if (isValid(currentState.m_stream[0].m_handle) ) { uint32_t numVertices = draw.m_numVertices; if (UINT32_MAX == numVertices) { - const VertexBufferD3D11& vb = m_vertexBuffers[currentState.m_vertexBuffer.idx]; - uint16_t decl = !isValid(vb.m_decl) ? draw.m_vertexDecl.idx : vb.m_decl.idx; + const VertexBufferD3D11& vb = m_vertexBuffers[currentState.m_stream[0].m_handle.idx]; + uint16_t decl = !isValid(vb.m_decl) ? draw.m_stream[0].m_decl.idx : vb.m_decl.idx; const VertexDecl& vertexDecl = m_vertexDecls[decl]; numVertices = vb.m_size/vertexDecl.m_stride; } @@ -5949,7 +5949,7 @@ BX_PRAGMA_DIAGNOSTIC_POP(); deviceCtx->DrawIndexedInstanced(numIndices , draw.m_numInstances , 0 - , draw.m_startVertex + , draw.m_stream[0].m_startVertex , 0 ); } @@ -5957,7 +5957,7 @@ BX_PRAGMA_DIAGNOSTIC_POP(); { deviceCtx->DrawIndexed(numIndices , 0 - , draw.m_startVertex + , draw.m_stream[0].m_startVertex ); } } @@ -5973,7 +5973,7 @@ BX_PRAGMA_DIAGNOSTIC_POP(); deviceCtx->DrawIndexedInstanced(numIndices , draw.m_numInstances , draw.m_startIndex - , draw.m_startVertex + , draw.m_stream[0].m_startVertex , 0 ); } @@ -5981,7 +5981,7 @@ BX_PRAGMA_DIAGNOSTIC_POP(); { deviceCtx->DrawIndexed(numIndices , draw.m_startIndex - , draw.m_startVertex + , draw.m_stream[0].m_startVertex ); } } @@ -5996,14 +5996,14 @@ BX_PRAGMA_DIAGNOSTIC_POP(); { deviceCtx->DrawInstanced(numVertices , draw.m_numInstances - , draw.m_startVertex + , draw.m_stream[0].m_startVertex , 0 ); } else { deviceCtx->Draw(numVertices - , draw.m_startVertex + , draw.m_stream[0].m_startVertex ); } } diff --git a/src/renderer_d3d12.cpp b/src/renderer_d3d12.cpp index d60a5039d..2cd96fa2d 100644 --- a/src/renderer_d3d12.cpp +++ b/src/renderer_d3d12.cpp @@ -3431,10 +3431,10 @@ data.NumQualityLevels = 0; { Enum type = Enum(!!isValid(_draw.m_indexBuffer) ); - VertexBufferD3D12& vb = s_renderD3D12->m_vertexBuffers[_draw.m_vertexBuffer.idx]; + VertexBufferD3D12& vb = s_renderD3D12->m_vertexBuffers[_draw.m_stream[0].m_handle.idx]; vb.setState(_commandList, D3D12_RESOURCE_STATE_GENERIC_READ); - uint16_t declIdx = !isValid(vb.m_decl) ? _draw.m_vertexDecl.idx : vb.m_decl.idx; + uint16_t declIdx = !isValid(vb.m_decl) ? _draw.m_stream[0].m_decl.idx : vb.m_decl.idx; const VertexDecl& vertexDecl = s_renderD3D12->m_vertexDecls[declIdx]; uint32_t numIndices = 0; @@ -3464,7 +3464,7 @@ data.NumQualityLevels = 0; } cmd.draw.InstanceCount = _draw.m_numInstances; cmd.draw.VertexCountPerInstance = numVertices; - cmd.draw.StartVertexLocation = _draw.m_startVertex; + cmd.draw.StartVertexLocation = _draw.m_stream[0].m_startVertex; cmd.draw.StartInstanceLocation = 0; } else @@ -3506,7 +3506,7 @@ data.NumQualityLevels = 0; cmd.drawIndexed.IndexCountPerInstance = numIndices; cmd.drawIndexed.InstanceCount = _draw.m_numInstances; cmd.drawIndexed.StartIndexLocation = _draw.m_startIndex; - cmd.drawIndexed.BaseVertexLocation = _draw.m_startVertex; + cmd.drawIndexed.BaseVertexLocation = _draw.m_stream[0].m_startVertex; cmd.drawIndexed.StartInstanceLocation = 0; } @@ -5200,7 +5200,7 @@ data.NumQualityLevels = 0; rendererUpdateUniforms(this, _render->m_uniformBuffer, draw.m_constBegin, draw.m_constEnd); - if (isValid(draw.m_vertexBuffer) ) + if (isValid(draw.m_stream[0].m_handle) ) { const uint64_t state = draw.m_stateFlags; bool hasFactor = 0 @@ -5210,8 +5210,8 @@ data.NumQualityLevels = 0; || f3 == (state & f3) ; - const VertexBufferD3D12& vb = m_vertexBuffers[draw.m_vertexBuffer.idx]; - uint16_t declIdx = !isValid(vb.m_decl) ? draw.m_vertexDecl.idx : vb.m_decl.idx; + const VertexBufferD3D12& vb = m_vertexBuffers[draw.m_stream[0].m_handle.idx]; + uint16_t declIdx = !isValid(vb.m_decl) ? draw.m_stream[0].m_decl.idx : vb.m_decl.idx; ID3D12PipelineState* pso = getPipelineState(state diff --git a/src/renderer_d3d9.cpp b/src/renderer_d3d9.cpp index cc3555c4b..ebd8a5b9b 100644 --- a/src/renderer_d3d9.cpp +++ b/src/renderer_d3d9.cpp @@ -4021,22 +4021,22 @@ namespace bgfx { namespace d3d9 } if (programChanged - || currentState.m_vertexBuffer.idx != draw.m_vertexBuffer.idx + || currentState.m_stream[0].m_handle.idx != draw.m_stream[0].m_handle.idx || currentState.m_instanceDataBuffer.idx != draw.m_instanceDataBuffer.idx - || currentState.m_instanceDataOffset != draw.m_instanceDataOffset - || currentState.m_instanceDataStride != draw.m_instanceDataStride) + || currentState.m_instanceDataOffset != draw.m_instanceDataOffset + || currentState.m_instanceDataStride != draw.m_instanceDataStride) { - currentState.m_vertexBuffer = draw.m_vertexBuffer; + currentState.m_stream[0].m_handle = draw.m_stream[0].m_handle; currentState.m_instanceDataBuffer.idx = draw.m_instanceDataBuffer.idx; - currentState.m_instanceDataOffset = draw.m_instanceDataOffset; - currentState.m_instanceDataStride = draw.m_instanceDataStride; + currentState.m_instanceDataOffset = draw.m_instanceDataOffset; + currentState.m_instanceDataStride = draw.m_instanceDataStride; - uint16_t handle = draw.m_vertexBuffer.idx; + uint16_t handle = draw.m_stream[0].m_handle.idx; if (invalidHandle != handle) { const VertexBufferD3D9& vb = m_vertexBuffers[handle]; - uint16_t decl = !isValid(vb.m_decl) ? draw.m_vertexDecl.idx : vb.m_decl.idx; + uint16_t decl = !isValid(vb.m_decl) ? draw.m_stream[0].m_decl.idx : vb.m_decl.idx; const VertexDeclD3D9& vertexDecl = m_vertexDecls[decl]; DX_CHECK(device->SetStreamSource(0, vb.m_ptr, 0, vertexDecl.m_decl.m_stride) ); @@ -4082,13 +4082,13 @@ namespace bgfx { namespace d3d9 } } - if (isValid(currentState.m_vertexBuffer) ) + if (isValid(currentState.m_stream[0].m_handle) ) { uint32_t numVertices = draw.m_numVertices; if (UINT32_MAX == numVertices) { - const VertexBufferD3D9& vb = m_vertexBuffers[currentState.m_vertexBuffer.idx]; - uint16_t decl = !isValid(vb.m_decl) ? draw.m_vertexDecl.idx : vb.m_decl.idx; + const VertexBufferD3D9& vb = m_vertexBuffers[currentState.m_stream[0].m_handle.idx]; + uint16_t decl = !isValid(vb.m_decl) ? draw.m_stream[0].m_decl.idx : vb.m_decl.idx; const VertexDeclD3D9& vertexDecl = m_vertexDecls[decl]; numVertices = vb.m_size/vertexDecl.m_decl.m_stride; } @@ -4115,7 +4115,7 @@ namespace bgfx { namespace d3d9 numPrimsRendered = numPrimsSubmitted*draw.m_numInstances; DX_CHECK(device->DrawIndexedPrimitive(prim.m_type - , draw.m_startVertex + , draw.m_stream[0].m_startVertex , 0 , numVertices , 0 @@ -4130,7 +4130,7 @@ namespace bgfx { namespace d3d9 numPrimsRendered = numPrimsSubmitted*draw.m_numInstances; DX_CHECK(device->DrawIndexedPrimitive(prim.m_type - , draw.m_startVertex + , draw.m_stream[0].m_startVertex , 0 , numVertices , draw.m_startIndex @@ -4145,7 +4145,7 @@ namespace bgfx { namespace d3d9 numPrimsRendered = numPrimsSubmitted*draw.m_numInstances; DX_CHECK(device->DrawPrimitive(prim.m_type - , draw.m_startVertex + , draw.m_stream[0].m_startVertex , numPrimsSubmitted ) ); } diff --git a/src/renderer_gl.cpp b/src/renderer_gl.cpp index b97ee35c9..ad5fd6d78 100644 --- a/src/renderer_gl.cpp +++ b/src/renderer_gl.cpp @@ -6779,25 +6779,27 @@ namespace bgfx { namespace gl } if (0 != defaultVao - && 0 == draw.m_startVertex + && 0 == draw.m_stream[0].m_startVertex && 0 == draw.m_instanceDataOffset) { if (programChanged - || baseVertex != draw.m_startVertex - || currentState.m_vertexBuffer.idx != draw.m_vertexBuffer.idx - || currentState.m_indexBuffer.idx != draw.m_indexBuffer.idx - || currentState.m_instanceDataOffset != draw.m_instanceDataOffset - || currentState.m_instanceDataStride != draw.m_instanceDataStride + || baseVertex != draw.m_stream[0].m_startVertex + || currentState.m_stream[0].m_handle.idx != draw.m_stream[0].m_handle.idx + || currentState.m_indexBuffer.idx != draw.m_indexBuffer.idx + || currentState.m_instanceDataOffset != draw.m_instanceDataOffset + || currentState.m_instanceDataStride != draw.m_instanceDataStride || currentState.m_instanceDataBuffer.idx != draw.m_instanceDataBuffer.idx) { bx::HashMurmur2A murmur; murmur.begin(); - murmur.add(draw.m_vertexBuffer.idx); - if (isValid(draw.m_vertexBuffer) ) + const Stream& stream = draw.m_stream[0]; + murmur.add(stream.m_handle.idx); + + if (isValid(stream.m_handle) ) { - const VertexBufferGL& vb = m_vertexBuffers[draw.m_vertexBuffer.idx]; - uint16_t decl = !isValid(vb.m_decl) ? draw.m_vertexDecl.idx : vb.m_decl.idx; + const VertexBufferGL& vb = m_vertexBuffers[stream.m_handle.idx]; + uint16_t decl = !isValid(vb.m_decl) ? stream.m_decl.idx : vb.m_decl.idx; murmur.add(decl); } @@ -6808,11 +6810,12 @@ namespace bgfx { namespace gl murmur.add(programIdx); uint32_t hash = murmur.end(); - currentState.m_vertexBuffer = draw.m_vertexBuffer; + currentState.m_stream[0].m_handle = stream.m_handle; + baseVertex = stream.m_startVertex; + currentState.m_indexBuffer = draw.m_indexBuffer; currentState.m_instanceDataOffset = draw.m_instanceDataOffset; currentState.m_instanceDataStride = draw.m_instanceDataStride; - baseVertex = draw.m_startVertex; GLuint id = m_vaoStateCache.find(hash); if (UINT32_MAX != id) @@ -6828,14 +6831,14 @@ namespace bgfx { namespace gl program.add(hash); - if (isValid(draw.m_vertexBuffer) ) + if (isValid(stream.m_handle) ) { - VertexBufferGL& vb = m_vertexBuffers[draw.m_vertexBuffer.idx]; + VertexBufferGL& vb = m_vertexBuffers[stream.m_handle.idx]; vb.add(hash); GL_CHECK(glBindBuffer(GL_ARRAY_BUFFER, vb.m_id) ); - uint16_t decl = !isValid(vb.m_decl) ? draw.m_vertexDecl.idx : vb.m_decl.idx; - program.bindAttributes(m_vertexDecls[decl], draw.m_startVertex); + uint16_t decl = !isValid(vb.m_decl) ? stream.m_decl.idx : vb.m_decl.idx; + program.bindAttributes(m_vertexDecls[decl], stream.m_startVertex); if (isValid(draw.m_instanceDataBuffer) ) { @@ -6869,24 +6872,24 @@ namespace bgfx { namespace gl && 0 != currentVao) { GL_CHECK(glBindVertexArray(defaultVao) ); - currentState.m_vertexBuffer.idx = invalidHandle; - currentState.m_indexBuffer.idx = invalidHandle; + currentState.m_stream[0].m_handle.idx = invalidHandle; + currentState.m_indexBuffer.idx = invalidHandle; bindAttribs = true; currentVao = 0; } if (programChanged - || currentState.m_vertexBuffer.idx != draw.m_vertexBuffer.idx + || currentState.m_stream[0].m_handle.idx != draw.m_stream[0].m_handle.idx || currentState.m_instanceDataBuffer.idx != draw.m_instanceDataBuffer.idx - || currentState.m_instanceDataOffset != draw.m_instanceDataOffset - || currentState.m_instanceDataStride != draw.m_instanceDataStride) + || currentState.m_instanceDataOffset != draw.m_instanceDataOffset + || currentState.m_instanceDataStride != draw.m_instanceDataStride) { - currentState.m_vertexBuffer = draw.m_vertexBuffer; + currentState.m_stream[0].m_handle = draw.m_stream[0].m_handle; currentState.m_instanceDataBuffer.idx = draw.m_instanceDataBuffer.idx; - currentState.m_instanceDataOffset = draw.m_instanceDataOffset; - currentState.m_instanceDataStride = draw.m_instanceDataStride; + currentState.m_instanceDataOffset = draw.m_instanceDataOffset; + currentState.m_instanceDataStride = draw.m_instanceDataStride; - uint16_t handle = draw.m_vertexBuffer.idx; + uint16_t handle = draw.m_stream[0].m_handle.idx; if (invalidHandle != handle) { VertexBufferGL& vb = m_vertexBuffers[handle]; @@ -6915,15 +6918,15 @@ namespace bgfx { namespace gl } } - if (isValid(currentState.m_vertexBuffer) ) + if (isValid(currentState.m_stream[0].m_handle) ) { - if (baseVertex != draw.m_startVertex + if (baseVertex != draw.m_stream[0].m_startVertex || bindAttribs) { - baseVertex = draw.m_startVertex; - const VertexBufferGL& vb = m_vertexBuffers[draw.m_vertexBuffer.idx]; - uint16_t decl = !isValid(vb.m_decl) ? draw.m_vertexDecl.idx : vb.m_decl.idx; - program.bindAttributes(m_vertexDecls[decl], draw.m_startVertex); + baseVertex = draw.m_stream[0].m_startVertex; + const VertexBufferGL& vb = m_vertexBuffers[draw.m_stream[0].m_handle.idx]; + uint16_t decl = !isValid(vb.m_decl) ? draw.m_stream[0].m_decl.idx : vb.m_decl.idx; + program.bindAttributes(m_vertexDecls[decl], draw.m_stream[0].m_startVertex); if (isValid(draw.m_instanceDataBuffer) ) { @@ -6934,13 +6937,13 @@ namespace bgfx { namespace gl } } - if (isValid(currentState.m_vertexBuffer) ) + if (isValid(currentState.m_stream[0].m_handle) ) { uint32_t numVertices = draw.m_numVertices; if (UINT32_MAX == numVertices) { - const VertexBufferGL& vb = m_vertexBuffers[currentState.m_vertexBuffer.idx]; - uint16_t decl = !isValid(vb.m_decl) ? draw.m_vertexDecl.idx : vb.m_decl.idx; + const VertexBufferGL& vb = m_vertexBuffers[currentState.m_stream[0].m_handle.idx]; + uint16_t decl = !isValid(vb.m_decl) ? draw.m_stream[0].m_decl.idx : vb.m_decl.idx; const VertexDecl& vertexDecl = m_vertexDecls[decl]; numVertices = vb.m_size/vertexDecl.m_stride; } diff --git a/src/renderer_mtl.mm b/src/renderer_mtl.mm index d04ff0b0f..3c44dd832 100644 --- a/src/renderer_mtl.mm +++ b/src/renderer_mtl.mm @@ -3382,13 +3382,13 @@ namespace bgfx { namespace mtl if (key.m_program != programIdx || (BGFX_STATE_BLEND_MASK|BGFX_STATE_BLEND_EQUATION_MASK|BGFX_STATE_ALPHA_WRITE|BGFX_STATE_RGB_WRITE|BGFX_STATE_BLEND_INDEPENDENT|BGFX_STATE_MSAA|BGFX_STATE_BLEND_ALPHA_TO_COVERAGE) & changedFlags - || currentState.m_vertexBuffer.idx != draw.m_vertexBuffer.idx - || currentState.m_vertexDecl.idx != draw.m_vertexDecl.idx - || currentState.m_instanceDataStride != draw.m_instanceDataStride + || currentState.m_stream[0].m_handle.idx != draw.m_stream[0].m_handle.idx + || currentState.m_stream[0].m_decl.idx != draw.m_stream[0].m_decl.idx + || currentState.m_instanceDataStride != draw.m_instanceDataStride || ( (blendFactor != draw.m_rgba) && !!(newFlags & BGFX_STATE_BLEND_INDEPENDENT) ) ) { programIdx = key.m_program; - currentState.m_vertexDecl = draw.m_vertexDecl; + currentState.m_stream[0].m_decl = draw.m_stream[0].m_decl; currentState.m_instanceDataStride = draw.m_instanceDataStride; if (invalidHandle == programIdx) @@ -3403,18 +3403,18 @@ namespace bgfx { namespace mtl RenderPipelineState pipelineState = NULL; - if ( isValid(draw.m_vertexBuffer) ) + if (isValid(draw.m_stream[0].m_handle) ) { - uint16_t handle = draw.m_vertexBuffer.idx; + uint16_t handle = draw.m_stream[0].m_handle.idx; const VertexBufferMtl& vb = m_vertexBuffers[handle]; VertexDeclHandle decl; - decl.idx = !isValid(vb.m_decl) ? draw.m_vertexDecl.idx : vb.m_decl.idx; + decl.idx = !isValid(vb.m_decl) ? draw.m_stream[0].m_decl.idx : vb.m_decl.idx; pipelineState = program.getRenderPipelineState(newFlags, draw.m_rgba, fbh, decl, draw.m_instanceDataStride/16); } - if (NULL == pipelineState ) - { //call with invalid program + if (NULL == pipelineState) + { currentProgram = NULL; programIdx = invalidHandle; continue; @@ -3500,24 +3500,24 @@ namespace bgfx { namespace mtl } } - if (currentState.m_vertexBuffer.idx != draw.m_vertexBuffer.idx - || currentState.m_startVertex != draw.m_startVertex - || currentState.m_instanceDataBuffer.idx != draw.m_instanceDataBuffer.idx - || currentState.m_instanceDataOffset != draw.m_instanceDataOffset) + if (currentState.m_stream[0].m_handle.idx != draw.m_stream[0].m_handle.idx + || currentState.m_stream[0].m_startVertex != draw.m_stream[0].m_startVertex + || currentState.m_instanceDataBuffer.idx != draw.m_instanceDataBuffer.idx + || currentState.m_instanceDataOffset != draw.m_instanceDataOffset) { - currentState.m_vertexBuffer = draw.m_vertexBuffer; - currentState.m_startVertex = draw.m_startVertex; - currentState.m_instanceDataBuffer.idx = draw.m_instanceDataBuffer.idx; - currentState.m_instanceDataOffset = draw.m_instanceDataOffset; + currentState.m_stream[0].m_handle = draw.m_stream[0].m_handle; + currentState.m_stream[0].m_startVertex = draw.m_stream[0].m_startVertex; + currentState.m_instanceDataBuffer.idx = draw.m_instanceDataBuffer.idx; + currentState.m_instanceDataOffset = draw.m_instanceDataOffset; - uint16_t handle = draw.m_vertexBuffer.idx; + uint16_t handle = draw.m_stream[0].m_handle.idx; if (invalidHandle != handle) { const VertexBufferMtl& vb = m_vertexBuffers[handle]; - uint16_t decl = !isValid(vb.m_decl) ? draw.m_vertexDecl.idx : vb.m_decl.idx; + uint16_t decl = !isValid(vb.m_decl) ? draw.m_stream[0].m_decl.idx : vb.m_decl.idx; const VertexDecl& vertexDecl = m_vertexDecls[decl]; - uint32_t offset = draw.m_startVertex * vertexDecl.getStride(); + uint32_t offset = draw.m_stream[0].m_startVertex * vertexDecl.getStride(); rce.setVertexBuffer(vb.getBuffer(), offset, 1); @@ -3529,13 +3529,13 @@ namespace bgfx { namespace mtl } } - if (isValid(currentState.m_vertexBuffer) ) + if (isValid(currentState.m_stream[0].m_handle) ) { uint32_t numVertices = draw.m_numVertices; if (UINT32_MAX == numVertices) { - const VertexBufferMtl& vb = m_vertexBuffers[currentState.m_vertexBuffer.idx]; - uint16_t decl = !isValid(vb.m_decl) ? draw.m_vertexDecl.idx : vb.m_decl.idx; + const VertexBufferMtl& vb = m_vertexBuffers[currentState.m_stream[0].m_handle.idx]; + uint16_t decl = !isValid(vb.m_decl) ? draw.m_stream[0].m_decl.idx : vb.m_decl.idx; const VertexDecl& vertexDecl = m_vertexDecls[decl]; numVertices = vb.m_size/vertexDecl.m_stride; }