【问题标题】:Why sprites render over objects?为什么精灵渲染对象?
【发布时间】:2019-03-27 21:12:33
【问题描述】:

我想在tutorial 这样的图片上渲染一个立方体。问题是它只渲染图片而立方体不渲染。你能帮助我吗 ?谢谢你

m_spriteBatch->Begin();
m_spriteBatch->Draw(m_background.Get(), m_fullscreenRect);

//
// Clear the back buffer
//
g_pImmediateContext->ClearRenderTargetView( g_pRenderTargetView, Colors::MidnightBlue );

g_pImmediateContext->ClearDepthStencilView(g_pDepthStencilView, D3D11_CLEAR_DEPTH, 1.0f, 0);

g_pImmediateContext->OMSetRenderTargets(1, &g_pRenderTargetView, g_pDepthStencilView);


//
// Update variables
//
ConstantBuffer cb;
cb.mWorld = XMMatrixTranspose( g_World );
cb.mView = XMMatrixTranspose( g_View );
cb.mProjection = XMMatrixTranspose( g_Projection );
g_pImmediateContext->UpdateSubresource( g_pConstantBuffer, 0, nullptr, &cb, 0, 0 );

//
// Renders a triangle
//
g_pImmediateContext->VSSetShader( g_pVertexShader, nullptr, 0 );
g_pImmediateContext->VSSetConstantBuffers( 0, 1, &g_pConstantBuffer );
g_pImmediateContext->PSSetShader( g_pPixelShader, nullptr, 0 );
g_pImmediateContext->DrawIndexed( 36, 0, 0 );        // 36 vertices needed for 12 triangles in a triangle list

//
// Present our back buffer to our front buffer
//
m_spriteBatch->End();
g_pSwapChain->Present( 0, 0 );

【问题讨论】:

    标签: directx spritebatch directxtk


    【解决方案1】:

    SpriteBatch 批量绘制以提高性能,因此它很可能在立方体绘制之后进行绘制。如果要确保先绘制精灵背景,则需要在提交立方体之前调用End。您还需要在设置渲染目标之后调用Begin

    // Clear
    g_pImmediateContext->ClearDepthStencilView(g_pDepthStencilView, D3D11_CLEAR_DEPTH, 1.0f, 0);
    g_pImmediateContext->OMSetRenderTargets(1, &g_pRenderTargetView, g_pDepthStencilView);
    
    // Draw background image
    m_spriteBatch->Begin();
    m_spriteBatch->Draw(m_background.Get(), m_fullscreenRect);
    m_spriteBatch->End();
    
    // Draw objects
    context->OMSetBlendState(…);
    context->OMSetDepthStencilState(…);
    context->IASetInputLayout(…);
    context->IASetVertexBuffers(…);
    context->IASetIndexBuffer(…);
    context->IASetPrimitiveTopology(…);
    

    如果m_background 纹理覆盖整个屏幕,您可以省略ClearRenderTargetView

    有关SpriteBatch 绘制顺序和批处理如何工作的更多信息,请参阅wiki

    【讨论】:

    【解决方案2】:

    基于@ChuckWalbourn 的answer,我解决了这个问题。

     g_pImmediateContext->ClearRenderTargetView( g_pRenderTargetView, Colors::MidnightBlue );
    
    
    g_pImmediateContext->ClearDepthStencilView(g_pDepthStencilView, D3D11_CLEAR_DEPTH | 
    
    D3D11_CLEAR_STENCIL, 1.0f, 0);
    
    
    m_spriteBatch->Begin();
    m_spriteBatch->Draw(m_background.Get(), m_fullscreenRect);
    m_spriteBatch->End();
    
    states = std::make_unique<CommonStates>(g_pd3dDevice);
    g_pImmediateContext->OMSetBlendState(states->Opaque(), Colors::Black, 0xFFFFFFFF);
    g_pImmediateContext->OMSetDepthStencilState(states->DepthDefault(), 0);
    // Set the input layout
    g_pImmediateContext->IASetInputLayout(g_pVertexLayout);
    UINT stride = sizeof(SimpleVertex);
    UINT offset = 0;
    g_pImmediateContext->IASetVertexBuffers(0, 1, &g_pVertexBuffer, &stride, &offset);
    // Set index buffer
    g_pImmediateContext->IASetIndexBuffer(g_pIndexBuffer, DXGI_FORMAT_R16_UINT, 0);
    
    // Set primitive topology
    g_pImmediateContext->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST);
    
    // Draw objects
    

    【讨论】:

    • 我建议不要每帧都创建一个新的CommonStates 对象。创建 Direct3D 资源对象的成本可能很高,因此如果不需要,您不希望每秒执行 60 次以上。使其成为成员变量,就像您拥有 SpriteBatch 等一样。
    • 好的,谢谢您的帮助。顺便说一句,您认为我可以使用 firect composition 获得相同的效果吗?
    猜你喜欢
    • 2021-12-07
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-30
    • 2023-03-08
    • 2019-06-29
    相关资源
    最近更新 更多