DumpDVD/DumpDVD/Gui/DvdSpin/D3DSpin.cpp

295 lines
10 KiB
C++

#include "ceedee.h"
#include "vec.hpp"
#include "SpinShaderVarients.h"
#include "CdTex.hpp"
#include <imgui.h>
#include <d3d11.h>
#include <directxmath.h>
#include <d3dcompiler.h>
#include "D3DSpin.hpp"
namespace Li::Gui::DvdSpin {
// dvd spin
void D3DSpin::setupSpinningDVD() {
this->createCdVertexShader();
this->createCdVertexLayout();
this->setCdVertexLayout();
this->createCdPixelShader();
this->createCdVertexBuffer();
this->setCdVertexBuffer();
this->createCdIndexBuffer();
this->setCdIndexBuffer();
this->createCamBuffer();
this->updateCamBuffer();
this->createCdTexture();
this->createCdResourceView();
this->createCdSampler();
}
HRESULT D3DSpin::createCdPixelShader() {
ID3DBlob* pixelShaderBlob;
d3d->CompileShader(std::string(spinShaderSrc), "pixelShaderMain", "ps_4_0", (void**)&pixelShaderBlob);
HRESULT hres = d3d->D3dDevice()->CreatePixelShader(pixelShaderBlob->GetBufferPointer(), pixelShaderBlob->GetBufferSize(), nullptr, &this->cdPixelShader);
pixelShaderBlob->Release();
return hres;
}
HRESULT D3DSpin::createCdVertexShader() {
d3d->CompileShader(std::string(spinShaderSrc), "vertexShaderMain", "vs_4_0", (void**)&this->cdVertexShaderBlob);
return d3d->D3dDevice()->CreateVertexShader(this->cdVertexShaderBlob->GetBufferPointer(), this->cdVertexShaderBlob->GetBufferSize(), nullptr, &this->cdVertexShader);
}
HRESULT D3DSpin::createCdVertexLayout() {
// define the layout
D3D11_INPUT_ELEMENT_DESC layout[] =
{
{ "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 },
{ "UV", 0, DXGI_FORMAT_R32G32_FLOAT, 0, D3D11_APPEND_ALIGNED_ELEMENT, D3D11_INPUT_PER_VERTEX_DATA, 0 },
};
// actually create it
return d3d->D3dDevice()->CreateInputLayout(layout, ARRAYSIZE(layout), this->cdVertexShaderBlob->GetBufferPointer(), this->cdVertexShaderBlob->GetBufferSize(), &this->cdVertexLayout);
}
void D3DSpin::setCdVertexLayout() {
this->cdVertexShaderBlob->Release();
d3d->D3dDeviceContext()->IASetInputLayout(this->cdVertexLayout);
}
void D3DSpin::updateCamBuffer() {
this->camWorld = DirectX::XMMatrixIdentity();
this->camView = DirectX::XMMatrixLookAtLH(this->eye, this->at, this->up);
this->camProjection = DirectX::XMMatrixPerspectiveFovLH(DirectX::XM_PIDIV2, this->d3d->WindowWidth() / (FLOAT)d3d->WindowHeight(), 0.01f, 100.0f);
}
HRESULT D3DSpin::createCamBuffer() {
D3D11_BUFFER_DESC camBufferDesc;
memset(&camBufferDesc, 0, sizeof(D3D11_BUFFER_DESC));
camBufferDesc.Usage = D3D11_USAGE_DEFAULT;
camBufferDesc.ByteWidth = (sizeof(DirectX::XMMATRIX) * 3);
camBufferDesc.BindFlags = D3D11_BIND_CONSTANT_BUFFER;
camBufferDesc.CPUAccessFlags = 0;
return d3d->D3dDevice()->CreateBuffer(&camBufferDesc, nullptr, &this->camBuffer);
}
HRESULT D3DSpin::createCdIndexBuffer() {
D3D11_BUFFER_DESC indexBufferDesc;
memset(&indexBufferDesc, 0, sizeof(D3D11_BUFFER_DESC));
indexBufferDesc.Usage = D3D11_USAGE_DEFAULT;
indexBufferDesc.ByteWidth = (sizeof(uint16_t) * ceedeeModelTotalIndices);
indexBufferDesc.BindFlags = D3D11_BIND_INDEX_BUFFER;
indexBufferDesc.CPUAccessFlags = 0;
D3D11_SUBRESOURCE_DATA indexBufferInitData;
memset(&indexBufferInitData, 0, sizeof(D3D11_SUBRESOURCE_DATA));
indexBufferInitData.pSysMem = ceedeeModelIndexBuffer;
return d3d->D3dDevice()->CreateBuffer(&indexBufferDesc, &indexBufferInitData, &this->cdIndexBuffer);
}
void D3DSpin::setCdIndexBuffer() {
d3d->D3dDeviceContext()->IASetIndexBuffer(this->cdIndexBuffer, DXGI_FORMAT_R16_UINT, 0);
}
void D3DSpin::setCdVertexBuffer() {
uint32_t stride = sizeof(ModelVertex);
uint32_t offset = 0;
return d3d->D3dDeviceContext()->IASetVertexBuffers(0, 1, &this->cdVertexBuffer, &stride, &offset);
}
HRESULT D3DSpin::createCdVertexBuffer() {
D3D11_BUFFER_DESC vertexBufferDesc;
memset(&vertexBufferDesc, 0, sizeof(D3D11_BUFFER_DESC));
vertexBufferDesc.Usage = D3D11_USAGE_DEFAULT;
vertexBufferDesc.ByteWidth = sizeof(ModelVertex) * ceedeeModelTotalVertices;
vertexBufferDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
vertexBufferDesc.CPUAccessFlags = 0;
D3D11_SUBRESOURCE_DATA vertexBufferInitData;
memset(&vertexBufferInitData, 0, sizeof(D3D11_SUBRESOURCE_DATA));
vertexBufferInitData.pSysMem = ceedeeModelVertexBuffer;
return d3d->D3dDevice()->CreateBuffer(&vertexBufferDesc, &vertexBufferInitData, &this->cdVertexBuffer);
}
void D3DSpin::updateCdTexture() {
this->d3d->D3dDeviceContext()->UpdateSubresource(this->cdTexture,
NULL,
nullptr,
this->cdTextureProvider->CurrentTexture(),
this->cdTextureProvider->Pitch(),
NULL);
}
HRESULT D3DSpin::createCdTexture() {
D3D11_TEXTURE2D_DESC tdesc;
tdesc.Width = this->cdTextureProvider->Width();
tdesc.Height = this->cdTextureProvider->Height();
tdesc.MipLevels = 1;
tdesc.ArraySize = 1;
tdesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB;
tdesc.SampleDesc.Count = 1;
tdesc.SampleDesc.Quality = 0;
tdesc.Usage = D3D11_USAGE_DEFAULT;
tdesc.BindFlags = D3D11_BIND_SHADER_RESOURCE;
tdesc.CPUAccessFlags = 0;
tdesc.MiscFlags = 0;
D3D11_SUBRESOURCE_DATA tres = {};
tres.pSysMem = this->cdTextureProvider->CurrentTexture();
tres.SysMemPitch = this->cdTextureProvider->Pitch();
tres.SysMemSlicePitch = 0;
return d3d->D3dDevice()->CreateTexture2D(&tdesc, &tres, &this->cdTexture);
}
HRESULT D3DSpin::createCdResourceView() {
return d3d->D3dDevice()->CreateShaderResourceView(this->cdTexture, NULL, &this->cdResourceView);
}
HRESULT D3DSpin::createCdSampler() {
D3D11_SAMPLER_DESC sdesc;
sdesc.Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR;
sdesc.AddressU = D3D11_TEXTURE_ADDRESS_CLAMP;
sdesc.AddressV = D3D11_TEXTURE_ADDRESS_CLAMP;
sdesc.AddressW = D3D11_TEXTURE_ADDRESS_CLAMP;
sdesc.MipLODBias = 1.0f;
sdesc.MaxAnisotropy = 1;
sdesc.ComparisonFunc = D3D11_COMPARISON_NEVER;
sdesc.BorderColor[0] = 1.0f;
sdesc.BorderColor[1] = 1.0f;
sdesc.BorderColor[2] = 1.0f;
sdesc.BorderColor[3] = 1.0f;
sdesc.MinLOD = -FLT_MAX;
sdesc.MaxLOD = FLT_MAX;
return d3d->D3dDevice()->CreateSamplerState(&sdesc, &this->cdSampler);
}
void D3DSpin::RenderDVD() {
this->counter++;
this->camWorld = DirectX::XMMatrixRotationY((float)((float)this->counter / 10.0f));
DirectX::XMMATRIX camBufData[3];
camBufData[0] = XMMatrixTranspose(this->camWorld);
camBufData[1] = XMMatrixTranspose(this->camView);
camBufData[2] = XMMatrixTranspose(this->camProjection);
d3d->D3dDeviceContext()->UpdateSubresource(this->camBuffer, 0, nullptr, &camBufData, 0, 0);
d3d->D3dDeviceContext()->VSSetShader(this->cdVertexShader, nullptr, 0);
d3d->D3dDeviceContext()->VSSetConstantBuffers(0, 1, &this->camBuffer);
d3d->D3dDeviceContext()->PSSetShader(this->cdPixelShader, nullptr, 0);
d3d->D3dDeviceContext()->PSSetShaderResources(0, 1, &this->cdResourceView);
d3d->D3dDeviceContext()->PSSetSamplers(0, 1, &this->cdSampler);
d3d->D3dDeviceContext()->DrawIndexed(ceedeeModelTotalIndices, 0, 0);
this->updateCamBuffer();
#ifdef _DEBUG
ImGui::Begin("Debug Position");
ImGui::DragFloat4("Eye", (float*)this->eye.m128_f32);
ImGui::DragFloat4("At", (float*)this->at.m128_f32);
ImGui::DragFloat4("Up", (float*)this->up.m128_f32);
ImGui::End();
ImGui::Begin("Change Tex");
if (ImGui::Button("Unknown Disc")) {
this->UpdateTexture(CdType::UNKNOWN_DISC);
}
if(ImGui::Button("Blu-Ray")){
this->UpdateTexture(CdType::BLU_RAY);
}
if (ImGui::Button("Hd Dvd")) {
this->UpdateTexture(CdType::HIGH_DEFINITION_DIGITAL_VERSITLE_DISC);
}
if (ImGui::Button("Dvd")) {
this->UpdateTexture(CdType::DIGITAL_VERSITLE_DISC);
}
if (ImGui::Button("Cd")) {
this->UpdateTexture(CdType::COMPACT_DISC);
}
ImGui::End();
#endif
}
void D3DSpin::UpdateTexture(CdType type) {
if (this->cdTextureProvider->CurrentCdType() == type) return;
switch (type) {
case CdType::COMPACT_DISC:
this->cdTextureProvider->SetCdTexture();
break;
case CdType::DIGITAL_VERSITLE_DISC:
this->cdTextureProvider->SetDvdTexture();
break;
case CdType::HIGH_DEFINITION_DIGITAL_VERSITLE_DISC:
this->cdTextureProvider->SetHdDvdTexture();
break;
case CdType::BLU_RAY:
this->cdTextureProvider->SetBdTexture();
break;
case CdType::UNKNOWN_DISC:
default:
this->cdTextureProvider->SetUnknownTexture();
break;
}
this->updateCdTexture();
}
D3DSpin::D3DSpin(D3D* d3d) {
this->eye = DirectX::XMVectorSet(0.0f, 2.0f, 3.0f, 0.0f);
this->at = DirectX::XMVectorSet(0.0f, 2.0f, 0.0f, 0.0f);
this->up = DirectX::XMVectorSet(0.0f, 1.0f, 0.0f, 0.0f);
this->d3d = d3d;
this->cdVertexShader = nullptr;
this->cdPixelShader = nullptr;
this->cdVertexLayout = nullptr;
this->cdVertexBuffer = nullptr;
this->cdIndexBuffer = nullptr;
this->camBuffer = nullptr;
this->cdTexture = nullptr;
this->cdSampler = nullptr;
this->cdResourceView = nullptr;
this->cdTextureProvider = new CdTex();
this->setupSpinningDVD();
}
D3DSpin::~D3DSpin() {
this->cdVertexShader->Release();
this->cdPixelShader->Release();
this->cdVertexLayout->Release();
this->cdVertexBuffer->Release();
this->cdIndexBuffer->Release();
this->camBuffer->Release();
this->cdTexture->Release();
this->cdSampler->Release();
this->cdResourceView->Release();
delete this->cdTextureProvider;
}
}