使用具有ID3D11DeviceContext :: DrawIndexed?的PrimitiveBatch :: DrawIndexed?

问题描述 投票:0回答:1

我正在创建一个游戏引擎,当时我想绘制线框形状以进行调试(对撞机,触发器,光线投射等)。我以前使用的是线框光栅化器状态的网格,但现在我想将系统迁移到DirectXTK's example using their PrimitiveBatch class,以便绘制光线。

但是,当我调用批处理的DrawIndexed()方法时,我遇到了一个问题,在该方法中,我绘制该框架的所有东西,包括来自ID3D11DeviceContext的DrawIndexed()的对象,都变成了线框。

Here's what the scene is supposed to look like.

Here's what it looks like after activating the debug drawing.

我的调试绘图方法:

void Renderer::DrawDebugShapes(ID3D11DeviceContext* context, Camera* camera, float deltaTime)
{
    if (debugObjs[0].size() < 1 && debugObjs[1].size() < 1 && debugObjs[2].size() < 1
        && debugObjs[3].size() < 1)
        return;

    db_effect->SetView(XMLoadFloat4x4(&camera->GetViewMatrix()));
    db_effect->SetProjection(XMLoadFloat4x4(&camera->GetProjectionMatrix()));

    context->OMSetBlendState(db_states->Opaque(), nullptr, 0xFFFFFFFF);
    context->OMSetDepthStencilState(db_states->DepthNone(), 0);
    context->RSSetState(db_states->CullNone());

    db_effect->Apply(context);

    context->IASetInputLayout(db_inputLayout.Get());

    db_batch->Begin();

    //Loop through all debug objs
    //0 = cubes, 1 = spheres, 2 = cylinders, 3 = rays
    for (short i = 0; i < 4; i++)
    {
        if (debugObjs[i].size() > 0)
        {
            for (auto iter = debugObjs[i].end() - 1; iter > debugObjs[i].begin(); iter--)
            {
                switch (i)
                {
                    case 0:
                        DrawShape(db_batch.get(), iter->world);
                        break;
                    case 1: 
                        //Draw sphere
                        break;
                    case 2:
                        //Draw capsule
                        break;
                    case 3:
                        //Draw rays
                        break;
                    default: break;
                }
                if (iter->type == DebugDrawType::ForDuration)
                    iter->duration -= deltaTime;

                //Erase objs that need to be
                if (iter->type == DebugDrawType::SingleFrame ||
                    (iter->type == DebugDrawType::ForDuration && iter->duration <= 0))
                    iter = debugObjs[i].erase(iter);
            }
        }
    }

    db_batch->End();
    context->RSSetState(0);
    context->OMSetDepthStencilState(0, 0);
    context->OMSetBlendState(0, 0, 0xFFFFFFFF);
    context->IASetInputLayout(0);
}

如果情况为0,可以将DrawShape()调用注释掉,以消除问题。我的正常渲染是基本的网格正向渲染,在绘制完所有内容(包括调试形状)后,将为每个对象调用context-> DrawIndexed()并调用swapChain-> Present(0,0)。我试过将调试图移到交换链之后,但这并不能解决。

[DrawShape()只是将世界矩阵发送给使用原始批处理(from the DirectXTK wiki)绘制多维数据集的函数的函数:

inline void XM_CALLCONV DrawCube(PrimitiveBatch<VertexPositionColor>* batch,
    CXMMATRIX matWorld,
    FXMVECTOR color)
{
    static const XMVECTORF32 s_verts[8] =
    {
        { -1.f, -1.f, -1.f, 0.f },
        {  1.f, -1.f, -1.f, 0.f },
        {  1.f, -1.f,  1.f, 0.f },
        { -1.f, -1.f,  1.f, 0.f },
        { -1.f,  1.f, -1.f, 0.f },
        {  1.f,  1.f, -1.f, 0.f },
        {  1.f,  1.f,  1.f, 0.f },
        { -1.f,  1.f,  1.f, 0.f }
    };

    static const WORD s_indices[] =
    {
        0, 1,
        1, 2,
        2, 3,
        3, 0,
        4, 5,
        5, 6,
        6, 7,
        7, 4,
        0, 4,
        1, 5,
        2, 6,
        3, 7
    };

    VertexPositionColor verts[8];
    for (size_t i = 0; i < 8; ++i)
    {
        XMVECTOR v = XMVector3Transform(s_verts[i], matWorld);
        XMStoreFloat3(&verts[i].position, v);
        XMStoreFloat4(&verts[i].color, color);
    }

    batch->DrawIndexed(D3D_PRIMITIVE_TOPOLOGY_LINELIST, s_indices, _countof(s_indices), verts, 8);
}

我也尝试过在调试绘图完成后重置状态,但无济于事。有人有什么想法吗?

c++ graphics game-engine directx-11 directxtk
1个回答
0
投票

D3D_PRIMITIVE_TOPOLOGY_LINELIST画线,而不是三角形。如果需要三角形,请使用D3D_PRIMITIVE_TOPOLOGY_TRIANGLELIST

© www.soinside.com 2019 - 2024. All rights reserved.