2015-04-30 10 views
0

Я работаю над проектом, в котором я использую DirectX Toolkit для загрузки моделей FBX. Как я понял, DXTK не поддерживает шейдеры HLSL для своих моделей, поэтому мне нужно получить информацию о модели (буфер вершин, индексный буфер и т. Д.) Из объекта модели и реализовать стандартный чертеж Direct3D, если я хочу использовать шейдеры HLSL для рендеринга.Загруженная модель DirectX Toolkit с пользовательским шейдером HLSL-шейдера Vertex shader input signature

Моя проблема заключается в том, что я не могу достичь координат текстуры из вершинного шейдера. Для тестирования я поставил вершинный шейдер, чтобы пройти через координаты в пиксельный шейдер, где я окрасить весь объект с текстурных координат, как это:

float4(input.texCoord, 0.0f, 1.0f); 

В результате весь объект черного цвета, поэтому texcoords (0.0, 0.0) везде. Я проверил модель с помощью функции DXTK Model :: Draw (...), и она текстурирована правильно, поэтому моя модель и код загрузки моей модели кажутся правильными.

я узнал, что DXTK модель загрузки использует следующую буфера вершин объявление:

const D3D11_INPUT_ELEMENT_DESC VertexPositionNormalTangentColorTexture::InputElements[] = 
{ 
    { "SV_Position", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, D3D11_APPEND_ALIGNED_ELEMENT, D3D11_INPUT_PER_VERTEX_DATA, 0 }, 
    { "NORMAL",  0, DXGI_FORMAT_R32G32B32_FLOAT, 0, D3D11_APPEND_ALIGNED_ELEMENT, D3D11_INPUT_PER_VERTEX_DATA, 0 }, 
    { "TANGENT",  0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, D3D11_APPEND_ALIGNED_ELEMENT, D3D11_INPUT_PER_VERTEX_DATA, 0 }, 
    { "COLOR",  0, DXGI_FORMAT_R8G8B8A8_UNORM,  0, D3D11_APPEND_ALIGNED_ELEMENT, D3D11_INPUT_PER_VERTEX_DATA, 0 }, 
    { "TEXCOORD", 0, DXGI_FORMAT_R32G32_FLOAT,  0, D3D11_APPEND_ALIGNED_ELEMENT, D3D11_INPUT_PER_VERTEX_DATA, 0 }, 
}; 

Так что я пытался соответствовать моей вершины входной структуры шейдера следующим образом:

struct VertexShaderInput 
{ 
    float3 pos : SV_Position; 
    float3 normal : NORMAL; 
    float4 tangent : TANGENT; 
    float4 color : COLOR; 
    float2 texCoord : TEXCOORD; 
}; 

Вот как я загружаю модель:

void SceneObject::LoadMesh(
    std::shared_ptr<DX::DeviceResources> deviceResources, 
    const wchar_t* modelFile) 
{ 
    auto device = deviceResources->GetD3DDevice(); 
    EffectFactory fx(device); 
    this->model = Model::CreateFromCMO(device, modelFile, fx, true); 
} 

А вот моя функция ничья:

void SceneObject::Draw(std::shared_ptr<DX::DeviceResources> deviceResources) 
{ 
    auto device = deviceResources->GetD3DDevice(); 
    auto context = deviceResources->GetD3DDeviceContext(); 
    CommonStates states(device); 

    context->UpdateSubresource(
     this->vsConstantBuffer.Get(), 
     0, 
     NULL, 
     &this->vsConstantBufferData, 
     0, 
     0); 

    context->UpdateSubresource(
     this->psConstantBuffer.Get(), 
     0, 
     NULL, 
     &this->psConstantBufferData, 
     0, 
     0); 

    //model->Draw(context, states, local, view, proj); 
    XMVECTOR qid = XMQuaternionIdentity(); 
    const XMVECTORF32 scale = { 1.f, 1.f, 1.f }; 
    const XMVECTORF32 translate = { 0.f, 0.f, 0.f }; 
    //XMVECTOR rotate = XMQuaternionRotationRollPitchYaw(0, XM_PI/2.f, -XM_PI/2.f); 
    XMVECTOR rotate = XMQuaternionRotationRollPitchYaw(0, 0, 0); 
    XMMATRIX worldMatrix = XMLoadFloat4x4(&this->vsConstantBufferData.model); 
    XMMATRIX local = XMMatrixMultiply(worldMatrix, XMMatrixTransformation(g_XMZero, qid, scale, g_XMZero, rotate, translate)); 
    //this->model->Draw(context, states, local, XMLoadFloat4x4(&vsConstantBufferData.view), XMLoadFloat4x4(&vsConstantBufferData.projection), false); 

    XMStoreFloat4x4(&this->vsConstantBufferData.model, local); 

    for each(auto& mesh in model->meshes) 
    { 
     for each (auto& part in mesh->meshParts) 
     { 
      context->IASetVertexBuffers(
       0, 
       1, 
       part->vertexBuffer.GetAddressOf(), 
       &part->vertexStride, 
       &part->vertexOffset 
       ); 

      context->IASetIndexBuffer(
       part->indexBuffer.Get(), 
       part->indexFormat, 
       0 
       ); 

      context->IASetPrimitiveTopology(part->primitiveType); 

      //context->IASetInputLayout(inputLayout.Get()); 
      context->IASetInputLayout(part->inputLayout.Get()); 

      // Attach our vertex shader. 
      context->VSSetShader(
       vertexShader.Get(), 
       nullptr, 
       0 
       ); 

      // Send the constant buffer to the graphics device. 
      context->VSSetConstantBuffers(
       0, 
       1, 
       vsConstantBuffer.GetAddressOf() 
       ); 

      // Attach our pixel shader. 
      context->PSSetShader(
       pixelShader.Get(), 
       nullptr, 
       0 
       ); 

      // Send the constant buffer to the graphics device. 
      context->PSSetConstantBuffers(
       1, 
       1, 
       psConstantBuffer.GetAddressOf() 
       ); 

      context->PSSetShaderResources(0, 1, diffuseTexture.GetAddressOf()); 
      context->PSSetSamplers(0, 1, linearSampler.GetAddressOf()); 

      // Draw the objects. 
      context->DrawIndexed(
       part->indexCount, 
       part->startIndex, 
       0 
       ); 
     } 
    } 
} 

Если вам нужно больше кода, вы можете проверить весь мой проект здесь: https://github.com/GiGu92/WaterRenderingDemo

Что я Мессинг?

+0

Мне удалось решить проблему временно, поскольку я реализовал обработанную процедурой плоскость сетки, но вы все равно можете просмотреть мой проект по ссылке github выше. См. «Мелкие изменения» фиксации (texcoords все еще не работают) », вот где я все еще пытаюсь нарисовать загруженную модель с моим шейдером. –

ответ

1

Ваш код не указывает, где вы создаете вершинный шейдер.

Для CMOs взгляните на Src\Shaders\DGSLEffect.fx на то, как они используются с пользовательскими шейдерами.

EffectFactory или DGSLEffectFactory является создание стандартной вершинных & пиксельных шейдеров для рендеринга Model как BasicEffect, SkinnedEffect или DGSLEffect по умолчанию. Подробные сведения о выполнении пользовательского рендеринга рассматриваются в wiki, но я предлагаю вам сначала получить рендеринг с использованием эффектов по умолчанию, как вы ожидаете. См. tutorial.

Вы можете изменить весь трубопровод при необходимости в ряде способов:

  • Реализовать собственные IEffect * интерфейсы и IEffectFactory использовать с Типовым погрузчиком
  • Переопределить шейдеры при визуализации непосредственно ModelMesh/ModelMeshParts

для CMO файлов, формат вершин действительно либо VertexPositionNormalTangentColorTexture или VertexPositionNormalTangentColorTextureSkinning, хотя для SDKMESH файлов это немного больше ва riable.

Как всегда, убедитесь, что у вас включен debug device и проверьте HRESULT любой функции Direct3D, которая возвращает ее, чтобы убедиться, что вы не заметили проблемы с настройкой или использованием API.

 Смежные вопросы

  • Нет связанных вопросов^_^