Advertisement
Guest User

ShaderClass.cpp

a guest
May 1st, 2019
138
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 11.01 KB | None | 0 0
  1. #include "ShaderClass.h"
  2.  
  3.  
  4.  
  5. ShaderClass::ShaderClass() {
  6.     m_vertexShader = nullptr;
  7.     m_pixelShader = nullptr;
  8.     m_inputLayout = nullptr;
  9.     m_matrixBuffer = nullptr;
  10.     m_samplerState = nullptr;
  11. }
  12.  
  13. ShaderClass::~ShaderClass() {
  14.  
  15. }
  16.  
  17. bool ShaderClass::Initialize(ID3D11Device* device, string vertexShader, string pixelShader) {
  18.     bool result;
  19.     result = InitializeShader(device, vertexShader.c_str(), pixelShader.c_str());
  20.     if (!result) {
  21.         cout << "[ShaderClass]\tError: failed InitializeShader()." << endl;
  22.         return false;
  23.     }
  24.     return true;
  25. }
  26.  
  27. void ShaderClass::Shutdown() {
  28.     ShutdownShader();
  29. }
  30.  
  31. bool ShaderClass::Render(ID3D11DeviceContext* deviceContext, TexturesTable* texturesTable, size_t vertexCount, D3DXMATRIX& world, D3DXMATRIX& view, D3DXMATRIX& proj, Material* material) {
  32.     bool result;
  33.     result = SetShaderParameters(deviceContext, world, view, proj, material);
  34.     if (!result) {
  35.         cout << "[ShaderClass]\tError: failed SetShaderParameters()" << endl;
  36.         return false;
  37.     }
  38.     if (!material->map_Ka.empty()) {
  39.         ID3D11ShaderResourceView* resourceView = texturesTable->GetTextureByName(material->map_Ka)->GetTexture();
  40.         if (!resourceView) {
  41.             cout << "[ShaderClass]\tError: failed GetTextureByName() for map_Ka" << material->map_Ka << endl;
  42.             return false;
  43.         }
  44.         deviceContext->PSSetShaderResources(0, 1, &resourceView);
  45.     }
  46.     if (!material->map_Kd.empty()) {
  47.         ID3D11ShaderResourceView* resourceView = texturesTable->GetTextureByName(material->map_Kd)->GetTexture();
  48.         if (!resourceView) {
  49.             cout << "[ShaderClass]\tError: failed GetTextureByName() for map_Kd" << material->map_Kd << endl;
  50.             return false;
  51.         }
  52.         deviceContext->PSSetShaderResources(1, 1, &resourceView);
  53.     }
  54.     if (!material->map_Ks.empty()) {
  55.         ID3D11ShaderResourceView* resourceView = texturesTable->GetTextureByName(material->map_Ks)->GetTexture();
  56.         if (!resourceView) {
  57.             cout << "[ShaderClass]\tError: failed GetTextureByName() for map_Ks" << material->map_Ks << endl;
  58.             return false;
  59.         }
  60.         deviceContext->PSSetShaderResources(2, 1, &resourceView);
  61.     }
  62.     if (!material->map_Ns.empty()) {
  63.         ID3D11ShaderResourceView* resourceView = texturesTable->GetTextureByName(material->map_Ns)->GetTexture();
  64.         if (!resourceView) {
  65.             cout << "[ShaderClass]\tError: failed GetTextureByName() for map_Ns" << material->map_Ns << endl;
  66.             return false;
  67.         }
  68.         deviceContext->PSSetShaderResources(3, 1, &resourceView);
  69.     }
  70.     if (!material->map_d.empty()) {
  71.         ID3D11ShaderResourceView* resourceView = texturesTable->GetTextureByName(material->map_d)->GetTexture();
  72.         if (!resourceView) {
  73.             cout << "[ShaderClass]\tError: failed GetTextureByName() for map_d" << material->map_d << endl;
  74.             return false;
  75.         }
  76.         deviceContext->PSSetShaderResources(4, 1, &resourceView);
  77.     }
  78.     if (!material->map_bump.empty()) {
  79.         ID3D11ShaderResourceView* resourceView = texturesTable->GetTextureByName(material->map_bump)->GetTexture();
  80.         if (!resourceView) {
  81.             cout << "[ShaderClass]\tError: failed GetTextureByName() for map_bump" << material->map_bump << endl;
  82.             return false;
  83.         }
  84.         deviceContext->PSSetShaderResources(5, 1, &resourceView);
  85.     }
  86.    
  87.     RenderShader(deviceContext, vertexCount);
  88.     return true;
  89. }
  90.  
  91. bool ShaderClass::InitializeShader(ID3D11Device* device, string vsFileName, string psFileName) {
  92.     HRESULT result;
  93.     ID3D10Blob* errorMessage;
  94.     ID3D10Blob* vertexShaderBuffer;
  95.     ID3D10Blob* pixelShaderBuffer;
  96.     D3D11_INPUT_ELEMENT_DESC polygonLayout[3];
  97.     unsigned int numElements;
  98.     D3D11_BUFFER_DESC matrixBufferDesc;
  99.     D3D11_BUFFER_DESC shaderMaterialDesc;
  100.     D3D11_SAMPLER_DESC samplerDesc;
  101.  
  102.     errorMessage = nullptr;
  103.     vertexShaderBuffer = nullptr;
  104.     pixelShaderBuffer = nullptr;
  105.  
  106.     result = D3DX11CompileFromFile(vsFileName.c_str(), NULL, NULL, "vsEntryPoint", "vs_5_0", D3D10_SHADER_ENABLE_STRICTNESS, 0, NULL, &vertexShaderBuffer, &errorMessage, &result);
  107.     if (FAILED(result)) {
  108.         if (errorMessage) {
  109.             OutputShaderErrorMessage(errorMessage, vsFileName);
  110.         }
  111.         else {
  112.             cout << "[ShaderClass]\tError: missing shader file " << vsFileName.c_str() << endl;
  113.             return false;
  114.         }
  115.         return false;
  116.     }
  117.  
  118.     result = D3DX11CompileFromFile(psFileName.c_str(), NULL, NULL, "psEntryPoint", "ps_5_0", D3D10_SHADER_ENABLE_STRICTNESS, 0, NULL, &pixelShaderBuffer, &errorMessage, &result);
  119.     if (FAILED(result)) {
  120.         if (errorMessage) {
  121.             OutputShaderErrorMessage(errorMessage, psFileName);
  122.         }
  123.         else {
  124.             cout << "[ShaderClass]\tError: missing shader file " << psFileName.c_str() << endl;
  125.             return false;
  126.         }
  127.         return false;
  128.     }
  129.  
  130.     result = device->CreateVertexShader(vertexShaderBuffer->GetBufferPointer(), vertexShaderBuffer->GetBufferSize(), NULL, &m_vertexShader);
  131.     if (FAILED(result)) {
  132.         cout << "[ShaderClass]\tError: failed CreateVertexShader()" << endl;
  133.         return false;
  134.     }
  135.     result = device->CreatePixelShader(pixelShaderBuffer->GetBufferPointer(), pixelShaderBuffer->GetBufferSize(), NULL, &m_pixelShader);
  136.     if (FAILED(result)) {
  137.         cout << "[ShaderClass]\tError: failed CreatePixelShader()" << endl;
  138.         return false;
  139.     }
  140.  
  141.     polygonLayout[0].SemanticName = "POSITION";
  142.     polygonLayout[0].SemanticIndex = 0;
  143.     polygonLayout[0].Format = DXGI_FORMAT_R32G32B32A32_FLOAT;
  144.     polygonLayout[0].InputSlot = 0;
  145.     polygonLayout[0].InputSlotClass = D3D11_INPUT_PER_VERTEX_DATA;
  146.     polygonLayout[0].InstanceDataStepRate = 0;
  147.     polygonLayout[0].AlignedByteOffset = 0;
  148.  
  149.     polygonLayout[1].SemanticName = "NORMAL";
  150.     polygonLayout[1].SemanticIndex = 0;
  151.     polygonLayout[1].Format = DXGI_FORMAT_R32G32B32A32_FLOAT;
  152.     polygonLayout[1].InputSlot = 0;
  153.     polygonLayout[1].InputSlotClass = D3D11_INPUT_PER_VERTEX_DATA;
  154.     polygonLayout[1].InstanceDataStepRate = 0;
  155.     polygonLayout[1].AlignedByteOffset = D3D11_APPEND_ALIGNED_ELEMENT;
  156.  
  157.     polygonLayout[2].SemanticName = "TEXCOORD";
  158.     polygonLayout[2].SemanticIndex = 0;
  159.     polygonLayout[2].Format = DXGI_FORMAT_R32G32_FLOAT;
  160.     polygonLayout[2].InputSlot = 0;
  161.     polygonLayout[2].InputSlotClass = D3D11_INPUT_PER_VERTEX_DATA;
  162.     polygonLayout[2].InstanceDataStepRate = 0;
  163.     polygonLayout[2].AlignedByteOffset = D3D11_APPEND_ALIGNED_ELEMENT;
  164.  
  165.     numElements = 3;
  166.     result = device->CreateInputLayout(polygonLayout, numElements, vertexShaderBuffer->GetBufferPointer(), vertexShaderBuffer->GetBufferSize(), &m_inputLayout);
  167.     if (FAILED(result)) {
  168.         cout << "[ShaderClass]\tError: failed CreateInputLayout()." << endl;
  169.         return false;
  170.     }
  171.  
  172.     vertexShaderBuffer->Release();
  173.     vertexShaderBuffer = nullptr;
  174.  
  175.     pixelShaderBuffer->Release();
  176.     pixelShaderBuffer = nullptr;
  177.  
  178.     matrixBufferDesc.Usage = D3D11_USAGE_DYNAMIC;
  179.     matrixBufferDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
  180.     matrixBufferDesc.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
  181.     matrixBufferDesc.MiscFlags = 0;
  182.     matrixBufferDesc.StructureByteStride = 0;
  183.     matrixBufferDesc.ByteWidth = sizeof(MatrixBufferType);
  184.  
  185.     result = device->CreateBuffer(&matrixBufferDesc, NULL, &m_matrixBuffer);
  186.     if (FAILED(result)) {
  187.         cout << "[ShaderClass]\tError: failed to create constant buffer (m_matrixBuffer)." << endl;
  188.         return false;
  189.     }
  190.  
  191.     shaderMaterialDesc.Usage = D3D11_USAGE_DYNAMIC;
  192.     shaderMaterialDesc.ByteWidth = sizeof(cbShaderMaterial);
  193.     shaderMaterialDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE;
  194.     shaderMaterialDesc.MiscFlags = 0;
  195.     shaderMaterialDesc.StructureByteStride = 0;
  196.     shaderMaterialDesc.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
  197.  
  198.     result = device->CreateBuffer(&shaderMaterialDesc, NULL, &m_materialBuffer);
  199.     if (FAILED(result)) {
  200.         cout << "[ShaderClass]\tError: failed to create constant buffer (m_materialBuffer)." << endl;
  201.         return false;
  202.     }
  203.  
  204.     samplerDesc.Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR;
  205.     samplerDesc.AddressU = D3D11_TEXTURE_ADDRESS_WRAP;
  206.     samplerDesc.AddressV = D3D11_TEXTURE_ADDRESS_WRAP;
  207.     samplerDesc.AddressW = D3D11_TEXTURE_ADDRESS_WRAP;
  208.     samplerDesc.MipLODBias = 0.0f;
  209.     samplerDesc.MaxAnisotropy = 1;
  210.     samplerDesc.ComparisonFunc = D3D11_COMPARISON_ALWAYS;
  211.     samplerDesc.MinLOD = 0;
  212.     samplerDesc.MaxLOD = D3D11_FLOAT32_MAX;
  213.     samplerDesc.BorderColor[0] = 0;
  214.     samplerDesc.BorderColor[1] = 0;
  215.     samplerDesc.BorderColor[2] = 0;
  216.     samplerDesc.BorderColor[3] = 0;
  217.  
  218.     result = device->CreateSamplerState(&samplerDesc, &m_samplerState);
  219.     if (FAILED(result)) {
  220.         cout << "[ShaderClass]\tError: failed CreateSamplerState()." << endl;
  221.         return false;
  222.     }
  223.     return true;
  224. }
  225.  
  226. bool ShaderClass::SetShaderParameters(ID3D11DeviceContext* deviceContext, D3DXMATRIX& world, D3DXMATRIX& view, D3DXMATRIX& proj, Material* material) {
  227.     HRESULT result;
  228.     D3D11_MAPPED_SUBRESOURCE mappedResource;
  229.     MatrixBufferType* dataPtr;
  230.     cbShaderMaterial* materialDataPtr;
  231.  
  232.     // set matrix constant buffer
  233.     D3DXMatrixTranspose(&world, &world);
  234.     D3DXMatrixTranspose(&view, &view);
  235.     D3DXMatrixTranspose(&proj, &proj);
  236.  
  237.     result = deviceContext->Map(m_matrixBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
  238.     if (FAILED(result)) {
  239.         cout << "[ShaderClass]\tError: failed Map() for m_matrixBuffer." << endl;
  240.         return false;
  241.     }
  242.     dataPtr = (MatrixBufferType*)mappedResource.pData;
  243.     dataPtr->world = world;
  244.     dataPtr->view = view;
  245.     dataPtr->projection = proj;
  246.     deviceContext->Unmap(m_matrixBuffer, 0);
  247.     deviceContext->VSSetConstantBuffers(0, 1, &m_matrixBuffer);
  248.  
  249.     // set material constant buffer
  250.     result = deviceContext->Map(m_materialBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &mappedResource);
  251.     if (FAILED(result)) {
  252.         cout << "[ShaderClass]\tError: failed Map() for m_materialBuffer." << endl;
  253.         return false;
  254.     }
  255.     materialDataPtr = (cbShaderMaterial*)mappedResource.pData;
  256.     materialDataPtr->Ka = material->Ka;
  257.     materialDataPtr->Kd = material->Kd;
  258.     materialDataPtr->Ke = material->Ke;
  259.     materialDataPtr->Ks = material->Ks;
  260.     materialDataPtr->Ns = material->Ns;
  261.     materialDataPtr->Tr = material->Tr;
  262.     materialDataPtr->d = material->d;
  263.     materialDataPtr->bias = 0.0f;
  264.     deviceContext->Unmap(m_materialBuffer, 0);
  265.     deviceContext->PSSetConstantBuffers(0, 1, &m_materialBuffer);
  266.  
  267.     deviceContext->PSSetSamplers(0, 1, &m_samplerState);
  268.     return true;
  269. }
  270.  
  271. void ShaderClass::RenderShader(ID3D11DeviceContext* deviceContext, size_t vertexCount) {
  272.     deviceContext->IASetInputLayout(m_inputLayout);
  273.     deviceContext->VSSetShader(m_vertexShader, NULL, 0);
  274.     deviceContext->PSSetShader(m_pixelShader, NULL, 0);
  275.     deviceContext->Draw((UINT)vertexCount, 0);
  276. }
  277.  
  278. void ShaderClass::ShutdownShader() {
  279.     if (m_matrixBuffer) {
  280.         m_matrixBuffer->Release();
  281.         m_matrixBuffer = nullptr;
  282.     }
  283.  
  284.     if (m_inputLayout) {
  285.         m_inputLayout->Release();
  286.         m_inputLayout = nullptr;
  287.     }
  288.  
  289.     if (m_pixelShader) {
  290.         m_pixelShader->Release();
  291.         m_pixelShader = nullptr;
  292.     }
  293.  
  294.     if (m_vertexShader) {
  295.         m_vertexShader->Release();
  296.         m_vertexShader = nullptr;
  297.     }
  298.  
  299.     if (m_samplerState) {
  300.         m_samplerState->Release();
  301.         m_samplerState = nullptr;
  302.     }
  303. }
  304.  
  305. void ShaderClass::OutputShaderErrorMessage(ID3D10Blob* errorMessage, string shaderFileName) {
  306.     char* compileErrors;
  307.     size_t bufferSize;
  308.     ofstream fout;
  309.  
  310.     compileErrors = (char*)errorMessage->GetBufferPointer();
  311.     bufferSize = errorMessage->GetBufferSize();
  312.     fout.open("shader-error.txt");
  313.     for (int i = 0; i < (int)bufferSize; i++) {
  314.         fout << compileErrors[i];
  315.     }
  316.     fout.close();
  317.     errorMessage->Release();
  318.     errorMessage = nullptr;
  319. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement