4#include <d3d11shader.h>
5#include <d3dcompiler.h>
16 assert(m_device !=
nullptr);
17 m_device->GetImmediateContext(m_deviceContext.GetAddressOf());
26 if (!compileShader(shaderPath,
"VS_Main",
"vs_5_0", m_vertexShader,
27 m_vertexShaderBlob)) {
33 if (!compileShader(shaderPath,
"PS_Main",
"ps_5_0", m_pixelShader,
43 const std::string& fragPath) {
45 if (!compileShader(vertPath,
"Main",
"vs_5_0", m_vertexShader,
46 m_vertexShaderBlob)) {
52 if (!compileShader(fragPath,
"Main",
"ps_5_0", m_pixelShader,
62 if (!m_vertexShader || !m_pixelShader) {
63 throw std::runtime_error(
"Shaders are not compiled!");
66 m_deviceContext->VSSetShader(m_vertexShader.Get(),
nullptr, 0);
67 m_deviceContext->PSSetShader(m_pixelShader.Get(),
nullptr, 0);
69 m_deviceContext->IASetInputLayout(Layout.Get());
73 return m_vertexShaderBlob.Get();
78 bool isSkinned =
false;
79 Microsoft::WRL::ComPtr<ID3D11ShaderReflection> reflector;
80 HRESULT hr = D3DReflect(m_vertexShaderBlob->GetBufferPointer(),
81 m_vertexShaderBlob->GetBufferSize(),
82 IID_ID3D11ShaderReflection,
83 reinterpret_cast<void**
>(reflector.GetAddressOf()));
85 D3D11_SHADER_DESC shaderDesc;
86 reflector->GetDesc(&shaderDesc);
87 for (UINT p = 0; p < shaderDesc.InputParameters; ++p) {
88 D3D11_SIGNATURE_PARAMETER_DESC paramDesc;
89 reflector->GetInputParameterDesc(p, ¶mDesc);
90 if (strcmp(paramDesc.SemanticName,
"BLENDINDICES") == 0) {
97 D3D11_INPUT_ELEMENT_DESC* layoutDesc = isSkinned ? SkinnedLayout : DefaultLayout;
98 UINT layoutCount = isSkinned ? ARRAYSIZE(SkinnedLayout) : ARRAYSIZE(DefaultLayout);
100 ID3D11InputLayout* inputLayout =
nullptr;
101 hr = m_device->CreateInputLayout(
102 layoutDesc, layoutCount,
103 m_vertexShaderBlob->GetBufferPointer(),
104 m_vertexShaderBlob->GetBufferSize(), &inputLayout);
107 SLEAK_ERROR(
"Failed to create input layout: 0x{:08X}", hr);
112 Layout.Attach(inputLayout);
113 inputLayout->AddRef();
120bool DirectX11Shader::compileShader(
const std::string& filePath,
121 const std::string& entryPoint,
122 const std::string& profile,
123 Microsoft::WRL::ComPtr<T>& shader,
124 Microsoft::WRL::ComPtr<ID3DBlob>& blob) {
125 Microsoft::WRL::ComPtr<ID3DBlob> errorBlob;
126 HRESULT hr = D3DCompileFromFile(
127 std::wstring(filePath.begin(), filePath.end()).c_str(),
129 D3D_COMPILE_STANDARD_FILE_INCLUDE,
141 (
char*)errorBlob->GetBufferPointer());
147 if constexpr (std::is_same_v<T, ID3D11VertexShader>) {
148 hr = m_device->CreateVertexShader(
149 blob->GetBufferPointer(), blob->GetBufferSize(),
nullptr,
150 reinterpret_cast<ID3D11VertexShader**
>(shader.GetAddressOf()));
151 }
else if constexpr (std::is_same_v<T, ID3D11PixelShader>) {
152 hr = m_device->CreatePixelShader(
153 blob->GetBufferPointer(), blob->GetBufferSize(),
nullptr,
154 reinterpret_cast<ID3D11PixelShader**
>(shader.GetAddressOf()));
157 return SUCCEEDED(hr);
ID3D11InputLayout * createInputLayout()
Builds the input layout matching DefaultLayout or SkinnedLayout from the vertex shader bytecode.
bool compile(const std::string &shaderPath) override
Compiles the combined-path convention (vs_main/ps_main entry points) from a single HLSL file.
ID3DBlob * getVertexShaderBlob() const
~DirectX11Shader() override
void bind() override
Binds this program as the active shader for subsequent draws.
DirectX11Shader(ID3D11Device *device)
Backend-facing rendering layer shared by the four graphics backends.
Root namespace for everything the engine exposes.