feat(render): DoScreenGrabOnNextPresent now properly saves the file into the GameHDD folder

feat(storage): save files now filter out the file extension and all save to .ms files to avoid confusion
chore(render): make names more accurate
This commit is contained in:
Patoke
2026-03-09 01:15:33 -03:00
parent 3ead2bb093
commit 8716df6eee
5 changed files with 133 additions and 95 deletions
+27 -12
View File
@@ -35,11 +35,17 @@ SOFTWARE.
#define MATRIX_MODE_MODELVIEW_CBUFF 3 #define MATRIX_MODE_MODELVIEW_CBUFF 3
#define MATRIX_MODE_MODELVIEW_MAX 4 #define MATRIX_MODE_MODELVIEW_MAX 4
#define STACK_TYPES 4 #define STACK_TYPES 4
#define STACK_SIZE 16 #define STACK_SIZE 16
#define MAX_MIP_LEVELS 5
#define MAX_TEXTURES 512 #define MAX_TEXTURES 512
#define NUM_THUMBNAIL_DOWNSAMPLES 4 // the amount of downsamples we do to the thumbnail texture
#define THUMBNAIL_MAX_QUALITY 0 // 1920x1080
#define THUMBNAIL_DOWNSAMPLE_QUALITY_1 1 // 512x512
#define THUMBNAIL_DOWNSAMPLE_QUALITY_2 2 // 256x256
#define THUMBNAIL_DOWNSAMPLE_QUALITY_3 3 // 128x128
#define THUMBNAIL_DOWNSAMPLE_TARGET 4 // 64x64
#define NUM_COMMAND_HANDLES 0x800000 #define NUM_COMMAND_HANDLES 0x800000
#define MAX_COMMAND_BUFFERS 16000 #define MAX_COMMAND_BUFFERS 16000
@@ -164,6 +170,15 @@ private:
void DeleteInternalBuffer(int index); void DeleteInternalBuffer(int index);
Renderer::Context &getContext(); Renderer::Context &getContext();
public: public:
enum eTextureSamplerFlags
{
SAMPLER_PARAM_CLAMP_U = 1 << 0,
SAMPLER_PARAM_CLAMP_V = 1 << 1,
SAMPLER_PARAM_LINEAR_FILTER = 1 << 2,
SAMPLER_PARAM_LINEAR_MIPS = 1 << 3,
};
struct Texture struct Texture
{ {
bool allocated; bool allocated;
@@ -422,11 +437,11 @@ public:
ID3D11Device *m_pDevice; ID3D11Device *m_pDevice;
ID3D11DeviceContext *m_pDeviceContext; ID3D11DeviceContext *m_pDeviceContext;
IDXGISwapChain *m_pSwapChain; IDXGISwapChain *m_pSwapChain;
ID3D11RenderTargetView *renderTargetView; ID3D11RenderTargetView *mainRenderTargetView;
ID3D11RenderTargetView *renderTargetViews[4]; ID3D11RenderTargetView *downSampleRenderTargetViews[NUM_THUMBNAIL_DOWNSAMPLES];
ID3D11ShaderResourceView *renderTargetShaderResourceView; ID3D11ShaderResourceView *mainShaderResourceView;
ID3D11ShaderResourceView *renderTargetShaderResourceViews[4]; ID3D11ShaderResourceView *downSampleShaderResourceViews[NUM_THUMBNAIL_DOWNSAMPLES];
ID3D11Texture2D *renderTargetTextures[4]; ID3D11Texture2D *downSampleTextures[NUM_THUMBNAIL_DOWNSAMPLES];
ID3D11DepthStencilView *depthStencilView; ID3D11DepthStencilView *depthStencilView;
ID3D11VertexShader **vertexShaderTable; ID3D11VertexShader **vertexShaderTable;
ID3D11VertexShader *screenSpaceVertexShader; ID3D11VertexShader *screenSpaceVertexShader;
@@ -456,14 +471,14 @@ public:
BYTE reservedRendererByte1; BYTE reservedRendererByte1;
BYTE paddingAfterRendererByte1[3]; BYTE paddingAfterRendererByte1[3];
DWORD reservedRendererDword1; DWORD reservedRendererDword1;
int16_t *m_commandHandleToIndex; int16_t *m_vertexIdxToBufferIdx;
CommandBuffer **m_commandBuffers; CommandBuffer **m_commandBuffers;
DirectX::XMMATRIX *m_commandMatrices; DirectX::XMMATRIX *m_commandMatrices;
int *m_commandIndexToHandle; int *m_bufferIdxToVertexIdx;
uint8_t *m_commandPrimitiveTypes; uint8_t *m_commandPrimitiveTypes;
uint8_t *m_commandVertexTypes; uint8_t *m_commandVertexTypes;
DWORD reservedRendererDword2; DWORD m_currentCommandBuffer;
DWORD reservedRendererDword3; DWORD m_numBuffersToDeallocate;
std::unordered_map<int, ID3D11BlendState *> managedBlendStates; std::unordered_map<int, ID3D11BlendState *> managedBlendStates;
std::unordered_map<int, ID3D11DepthStencilState *> managedDepthStencilStates; std::unordered_map<int, ID3D11DepthStencilState *> managedDepthStencilStates;
std::unordered_map<int, ID3D11SamplerState *> managedSamplerStates; std::unordered_map<int, ID3D11SamplerState *> managedSamplerStates;
+41 -42
View File
@@ -114,7 +114,7 @@ bool Renderer::CBuffCall(int index, bool full)
EnterCriticalSection(&m_commandBufferCS); EnterCriticalSection(&m_commandBufferCS);
bool result = false; bool result = false;
const int commandIndex = m_commandHandleToIndex[index]; const int commandIndex = m_vertexIdxToBufferIdx[index];
if (commandIndex >= 0) if (commandIndex >= 0)
{ {
Renderer::Context &c = getContext(); Renderer::Context &c = getContext();
@@ -210,12 +210,11 @@ void Renderer::CBuffClear(int index)
{ {
EnterCriticalSection(&m_commandBufferCS); EnterCriticalSection(&m_commandBufferCS);
std::int16_t *externalToInternal = static_cast<std::int16_t*>(m_commandHandleToIndex); const int internalIndex = m_vertexIdxToBufferIdx[index];
const int internalIndex = externalToInternal[index];
if (internalIndex >= 0) if (internalIndex >= 0)
{ {
DeleteInternalBuffer(internalIndex); DeleteInternalBuffer(internalIndex);
externalToInternal[index] = static_cast<std::int16_t>(-2); m_vertexIdxToBufferIdx[index] = static_cast<std::int16_t>(-2);
} }
LeaveCriticalSection(&m_commandBufferCS); LeaveCriticalSection(&m_commandBufferCS);
@@ -235,7 +234,7 @@ int Renderer::CBuffCreate(int count)
assert(first < NUM_COMMAND_HANDLES); assert(first < NUM_COMMAND_HANDLES);
int cursor = probe; int cursor = probe;
while (cursor < end && cursor < NUM_COMMAND_HANDLES && m_commandHandleToIndex[cursor] == static_cast<std::int16_t>(-1)) while (cursor < end && cursor < NUM_COMMAND_HANDLES && m_vertexIdxToBufferIdx[cursor] == static_cast<std::int16_t>(-1))
{ {
++cursor; ++cursor;
} }
@@ -257,7 +256,7 @@ int Renderer::CBuffCreate(int count)
{ {
const int allocationEnd = first + count; const int allocationEnd = first + count;
for (int i = first; i < allocationEnd; ++i) for (int i = first; i < allocationEnd; ++i)
m_commandHandleToIndex[i] = static_cast<std::int16_t>(-2); m_vertexIdxToBufferIdx[i] = static_cast<std::int16_t>(-2);
if (reservedRendererByte1) if (reservedRendererByte1)
reservedRendererDword1 = allocationEnd; reservedRendererDword1 = allocationEnd;
@@ -284,18 +283,18 @@ void Renderer::CBuffDeferredModeEnd()
for (std::vector<Renderer::DeferredCBuff>::const_iterator it = c.deferredBuffers.begin(); it != c.deferredBuffers.end(); ++it) for (std::vector<Renderer::DeferredCBuff>::const_iterator it = c.deferredBuffers.begin(); it != c.deferredBuffers.end(); ++it)
{ {
const Renderer::DeferredCBuff &deferred = *it; const Renderer::DeferredCBuff &deferred = *it;
const int existingIndex = m_commandHandleToIndex[deferred.m_vertex_index]; const int existingIndex = m_vertexIdxToBufferIdx[deferred.m_vertex_index];
if (existingIndex >= 0) if (existingIndex >= 0)
DeleteInternalBuffer(existingIndex); DeleteInternalBuffer(existingIndex);
if (static_cast<int>(reservedRendererDword2 + reservedRendererDword3 + 10) > MAX_COMMAND_BUFFERS) if (static_cast<int>(m_currentCommandBuffer + m_numBuffersToDeallocate + 10) > MAX_COMMAND_BUFFERS)
DebugBreak(); DebugBreak();
const int internalSlot = reservedRendererDword2; const int internalSlot = m_currentCommandBuffer;
++reservedRendererDword2; ++m_currentCommandBuffer;
m_commandHandleToIndex[deferred.m_vertex_index] = static_cast<std::int16_t>(internalSlot); m_vertexIdxToBufferIdx[deferred.m_vertex_index] = static_cast<std::int16_t>(internalSlot);
m_commandIndexToHandle[internalSlot] = deferred.m_vertex_index; m_bufferIdxToVertexIdx[internalSlot] = deferred.m_vertex_index;
m_commandVertexTypes[internalSlot] = static_cast<std::uint8_t>(deferred.m_vertex_type); m_commandVertexTypes[internalSlot] = static_cast<std::uint8_t>(deferred.m_vertex_type);
m_commandPrimitiveTypes[internalSlot] = static_cast<std::uint8_t>(deferred.m_primitive_type); m_commandPrimitiveTypes[internalSlot] = static_cast<std::uint8_t>(deferred.m_primitive_type);
m_commandBuffers[internalSlot] = deferred.m_command_buf; m_commandBuffers[internalSlot] = deferred.m_command_buf;
@@ -318,11 +317,11 @@ void Renderer::CBuffDelete(int first, int count)
const int end = first + count; const int end = first + count;
for (int i = first; i < end; ++i) for (int i = first; i < end; ++i)
{ {
const int internalIndex = m_commandHandleToIndex[i]; const int internalIndex = m_vertexIdxToBufferIdx[i];
if (internalIndex >= 0) if (internalIndex >= 0)
DeleteInternalBuffer(internalIndex); DeleteInternalBuffer(internalIndex);
m_commandHandleToIndex[i] = static_cast<std::int16_t>(-1); m_vertexIdxToBufferIdx[i] = static_cast<std::int16_t>(-1);
} }
LeaveCriticalSection(&m_commandBufferCS); LeaveCriticalSection(&m_commandBufferCS);
@@ -349,18 +348,18 @@ void Renderer::CBuffEnd()
} }
else else
{ {
const int existingIndex = m_commandHandleToIndex[c.recordingBufferIndex]; const int existingIndex = m_vertexIdxToBufferIdx[c.recordingBufferIndex];
if (existingIndex >= 0) if (existingIndex >= 0)
DeleteInternalBuffer(existingIndex); DeleteInternalBuffer(existingIndex);
if (static_cast<int>(reservedRendererDword2 + reservedRendererDword3 + 10) > MAX_COMMAND_BUFFERS) if (static_cast<int>(m_currentCommandBuffer + m_numBuffersToDeallocate + 10) > MAX_COMMAND_BUFFERS)
DebugBreak(); DebugBreak();
const int internalSlot = reservedRendererDword2; const int internalSlot = m_currentCommandBuffer;
++reservedRendererDword2; ++m_currentCommandBuffer;
m_commandHandleToIndex[c.recordingBufferIndex] = static_cast<std::int16_t>(internalSlot); m_vertexIdxToBufferIdx[c.recordingBufferIndex] = static_cast<std::int16_t>(internalSlot);
m_commandIndexToHandle[internalSlot] = c.recordingBufferIndex; m_bufferIdxToVertexIdx[internalSlot] = c.recordingBufferIndex;
m_commandVertexTypes[internalSlot] = static_cast<std::uint8_t>(c.recordingVertexType); m_commandVertexTypes[internalSlot] = static_cast<std::uint8_t>(c.recordingVertexType);
m_commandPrimitiveTypes[internalSlot] = static_cast<std::uint8_t>(c.recordingPrimitiveType); m_commandPrimitiveTypes[internalSlot] = static_cast<std::uint8_t>(c.recordingPrimitiveType);
m_commandBuffers[internalSlot] = c.commandBuffer; m_commandBuffers[internalSlot] = c.commandBuffer;
@@ -386,7 +385,7 @@ int Renderer::CBuffSize(int index)
unsigned int size = 0; unsigned int size = 0;
EnterCriticalSection(&m_commandBufferCS); EnterCriticalSection(&m_commandBufferCS);
const int commandIndex = m_commandHandleToIndex[index]; const int commandIndex = m_vertexIdxToBufferIdx[index];
if (commandIndex >= 0) if (commandIndex >= 0)
size = static_cast<unsigned int>(m_commandBuffers[commandIndex]->GetAllocated()); size = static_cast<unsigned int>(m_commandBuffers[commandIndex]->GetAllocated());
LeaveCriticalSection(&m_commandBufferCS); LeaveCriticalSection(&m_commandBufferCS);
@@ -412,26 +411,26 @@ void Renderer::CBuffTick()
EnterCriticalSection(&m_commandBufferCS); EnterCriticalSection(&m_commandBufferCS);
int completedDeletes = 0; int completedDeletes = 0;
if (reservedRendererDword3 > 0) if (m_numBuffersToDeallocate > 0)
{ {
int tailSlot = MAX_COMMAND_BUFFERS - 1; int deleteIdx = MAX_COMMAND_BUFFERS - 1;
do do
{ {
Renderer::CommandBuffer *buffer = m_commandBuffers[tailSlot]; Renderer::CommandBuffer *buffer = m_commandBuffers[deleteIdx];
if (buffer) if (buffer)
delete buffer; delete buffer;
m_commandBuffers[tailSlot] = NULL; m_commandBuffers[deleteIdx] = NULL;
if (--reservedRendererDword3 == 0) if (--m_numBuffersToDeallocate == 0)
{ {
++completedDeletes; ++completedDeletes;
--tailSlot; --deleteIdx;
} }
else else
{ {
m_commandBuffers[tailSlot] = m_commandBuffers[(MAX_COMMAND_BUFFERS - 1) - static_cast<int>(reservedRendererDword3)]; m_commandBuffers[deleteIdx] = m_commandBuffers[(MAX_COMMAND_BUFFERS - 1) - static_cast<int>(m_numBuffersToDeallocate)];
} }
} while (completedDeletes < static_cast<int>(reservedRendererDword3)); } while (completedDeletes < static_cast<int>(m_numBuffersToDeallocate));
} }
LeaveCriticalSection(&m_commandBufferCS); LeaveCriticalSection(&m_commandBufferCS);
@@ -441,24 +440,24 @@ void Renderer::DeleteInternalBuffer(int index)
{ {
EnterCriticalSection(&m_commandBufferCS); EnterCriticalSection(&m_commandBufferCS);
++reservedRendererDword3; ++m_numBuffersToDeallocate;
const int recycledSlot = MAX_COMMAND_BUFFERS - static_cast<int>(reservedRendererDword3); const int index_delete = MAX_COMMAND_BUFFERS - static_cast<int>(m_numBuffersToDeallocate);
m_commandBuffers[recycledSlot] = m_commandBuffers[index]; m_commandBuffers[index_delete] = m_commandBuffers[index];
m_commandMatrices[recycledSlot] = m_commandMatrices[index]; m_commandMatrices[index_delete] = m_commandMatrices[index];
if (reservedRendererDword2-- != 1) if (m_currentCommandBuffer-- != 1)
{ {
const int lastActive = reservedRendererDword2; const int mappedFrom = m_currentCommandBuffer;
m_commandBuffers[index] = m_commandBuffers[lastActive]; m_commandBuffers[index] = m_commandBuffers[mappedFrom];
m_commandMatrices[index] = m_commandMatrices[lastActive]; m_commandMatrices[index] = m_commandMatrices[mappedFrom];
m_commandVertexTypes[index] = m_commandVertexTypes[lastActive]; m_commandVertexTypes[index] = m_commandVertexTypes[mappedFrom];
m_commandPrimitiveTypes[index] = m_commandPrimitiveTypes[lastActive]; m_commandPrimitiveTypes[index] = m_commandPrimitiveTypes[mappedFrom];
const int commandIndex = m_commandIndexToHandle[lastActive]; const int commandIndex = m_bufferIdxToVertexIdx[mappedFrom];
m_commandHandleToIndex[commandIndex] = static_cast<std::int16_t>(index); m_vertexIdxToBufferIdx[commandIndex] = static_cast<std::int16_t>(index);
m_commandIndexToHandle[index] = commandIndex; m_bufferIdxToVertexIdx[index] = commandIndex;
} }
LeaveCriticalSection(&m_commandBufferCS); LeaveCriticalSection(&m_commandBufferCS);
+38 -28
View File
@@ -31,7 +31,7 @@ Renderer InternalRenderManager;
DWORD Renderer::tlsIdx = TlsAlloc(); DWORD Renderer::tlsIdx = TlsAlloc();
_RTL_CRITICAL_SECTION Renderer::totalAllocCS = {}; _RTL_CRITICAL_SECTION Renderer::totalAllocCS = {};
DWORD Renderer::s_auiWidths[] = { 1920, 512, 256, 128, 64, 0 }; DWORD Renderer::s_auiWidths[] = { 1920, 512, 256, 128, 64 };
DWORD Renderer::s_auiHeights[] = { 1080, 512, 256, 128, 64 }; DWORD Renderer::s_auiHeights[] = { 1080, 512, 256, 128, 64 };
int Renderer::totalAlloc = 0; int Renderer::totalAlloc = 0;
const float Renderer::PI = 3.14159274f; const float Renderer::PI = 3.14159274f;
@@ -265,7 +265,7 @@ void Renderer::CaptureThumbnail(ImageFileBuffer *pngOut)
// @Patoke fix: bind render target to a proper backbuffer texture // @Patoke fix: bind render target to a proper backbuffer texture
ID3D11Resource *actualBackBuffer = NULL; ID3D11Resource *actualBackBuffer = NULL;
renderTargetView->GetResource(&actualBackBuffer); mainRenderTargetView->GetResource(&actualBackBuffer);
// copy the backbuffer contents // copy the backbuffer contents
c.m_pDeviceContext->CopyResource(m_backBufferTexture, actualBackBuffer); c.m_pDeviceContext->CopyResource(m_backBufferTexture, actualBackBuffer);
@@ -423,7 +423,7 @@ void Renderer::CaptureThumbnail(ImageFileBuffer *pngOut)
ID3D11ShaderResourceView *nullSRV[1] = {nullptr}; ID3D11ShaderResourceView *nullSRV[1] = {nullptr};
c.m_pDeviceContext->PSSetShaderResources(0, 1, nullSRV); c.m_pDeviceContext->PSSetShaderResources(0, 1, nullSRV);
for (UINT i = 0; i < MAX_MIP_LEVELS - 1; ++i) for (UINT i = 0; i < NUM_THUMBNAIL_DOWNSAMPLES; ++i)
{ {
D3D11_VIEWPORT viewport = {}; D3D11_VIEWPORT viewport = {};
viewport.TopLeftX = 0.0f; viewport.TopLeftX = 0.0f;
@@ -435,10 +435,10 @@ void Renderer::CaptureThumbnail(ImageFileBuffer *pngOut)
c.m_pDeviceContext->PSSetShaderResources(0, 1, nullSRV); c.m_pDeviceContext->PSSetShaderResources(0, 1, nullSRV);
c.m_pDeviceContext->OMSetRenderTargets(1, &renderTargetViews[i], NULL); c.m_pDeviceContext->OMSetRenderTargets(1, &downSampleRenderTargetViews[i], NULL);
c.m_pDeviceContext->RSSetViewports(1, &viewport); c.m_pDeviceContext->RSSetViewports(1, &viewport);
ID3D11ShaderResourceView *inputTexture = (i == 0) ? renderTargetShaderResourceView : renderTargetShaderResourceViews[i - 1]; ID3D11ShaderResourceView *inputTexture = (i == 0) ? mainShaderResourceView : downSampleShaderResourceViews[i - 1];
c.m_pDeviceContext->PSSetShaderResources(0, 1, &inputTexture); c.m_pDeviceContext->PSSetShaderResources(0, 1, &inputTexture);
c.m_pDeviceContext->PSSetSamplers(0, 1, &samplerState); c.m_pDeviceContext->PSSetSamplers(0, 1, &samplerState);
c.m_pDeviceContext->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP); c.m_pDeviceContext->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP);
@@ -475,7 +475,7 @@ void Renderer::CaptureThumbnail(ImageFileBuffer *pngOut)
} }
D3D11_TEXTURE2D_DESC texDesc = {}; D3D11_TEXTURE2D_DESC texDesc = {};
renderTargetTextures[MAX_MIP_LEVELS - 2]->GetDesc(&texDesc); downSampleTextures[THUMBNAIL_DOWNSAMPLE_QUALITY_3]->GetDesc(&texDesc);
texDesc.Usage = D3D11_USAGE_STAGING; texDesc.Usage = D3D11_USAGE_STAGING;
texDesc.BindFlags = 0; texDesc.BindFlags = 0;
texDesc.CPUAccessFlags = D3D11_CPU_ACCESS_READ | D3D11_CPU_ACCESS_WRITE; texDesc.CPUAccessFlags = D3D11_CPU_ACCESS_READ | D3D11_CPU_ACCESS_WRITE;
@@ -487,7 +487,7 @@ void Renderer::CaptureThumbnail(ImageFileBuffer *pngOut)
if (stagingTexture) if (stagingTexture)
{ {
c.m_pDeviceContext->CopyResource(stagingTexture, renderTargetTextures[MAX_MIP_LEVELS - 2]); c.m_pDeviceContext->CopyResource(stagingTexture, downSampleTextures[THUMBNAIL_DOWNSAMPLE_QUALITY_3]);
D3D11_MAPPED_SUBRESOURCE mapped = {}; D3D11_MAPPED_SUBRESOURCE mapped = {};
if (SUCCEEDED(c.m_pDeviceContext->Map(stagingTexture, 0, D3D11_MAP_READ, 0, &mapped))) if (SUCCEEDED(c.m_pDeviceContext->Map(stagingTexture, 0, D3D11_MAP_READ, 0, &mapped)))
@@ -538,7 +538,7 @@ void Renderer::CaptureThumbnail(ImageFileBuffer *pngOut)
viewport.MaxDepth = 1.0f; viewport.MaxDepth = 1.0f;
c.m_pDeviceContext->RSSetViewports(1, &viewport); c.m_pDeviceContext->RSSetViewports(1, &viewport);
c.m_pDeviceContext->OMSetRenderTargets(1, &renderTargetView, depthStencilView); c.m_pDeviceContext->OMSetRenderTargets(1, &mainRenderTargetView, depthStencilView);
activeVertexType = -1; activeVertexType = -1;
activePixelType = -1; activePixelType = -1;
@@ -680,27 +680,27 @@ void Renderer::Initialise(ID3D11Device *pDevice, IDXGISwapChain *pSwapChain)
PROFILER_INIT(); PROFILER_INIT();
m_commandHandleToIndex = new int16_t[NUM_COMMAND_HANDLES]; m_vertexIdxToBufferIdx = new int16_t[NUM_COMMAND_HANDLES];
m_commandBuffers = new CommandBuffer *[MAX_COMMAND_BUFFERS]; m_commandBuffers = new CommandBuffer *[MAX_COMMAND_BUFFERS];
m_commandMatrices = new DirectX::XMMATRIX[MAX_COMMAND_BUFFERS]; m_commandMatrices = new DirectX::XMMATRIX[MAX_COMMAND_BUFFERS];
m_commandIndexToHandle = new int[MAX_COMMAND_BUFFERS]; m_bufferIdxToVertexIdx = new int[MAX_COMMAND_BUFFERS];
m_commandPrimitiveTypes = new uint8_t[MAX_COMMAND_BUFFERS]; m_commandPrimitiveTypes = new uint8_t[MAX_COMMAND_BUFFERS];
m_commandVertexTypes = new uint8_t[MAX_COMMAND_BUFFERS]; m_commandVertexTypes = new uint8_t[MAX_COMMAND_BUFFERS];
std::memset(m_commandHandleToIndex, 0xFF, 0x1000000u); std::memset(m_vertexIdxToBufferIdx, 0xFF, NUM_COMMAND_HANDLES * sizeof(int16_t));
std::memset(m_commandBuffers, 0, 0xFA00u); std::memset(m_commandBuffers, 0, MAX_COMMAND_BUFFERS * sizeof(CommandBuffer *));
std::memset(m_commandIndexToHandle, 0, 0xFA00u); std::memset(m_bufferIdxToVertexIdx, 0, MAX_COMMAND_BUFFERS * sizeof(int));
std::memset(m_commandPrimitiveTypes, 0, 0x3E80u); std::memset(m_commandPrimitiveTypes, 0, MAX_COMMAND_BUFFERS * sizeof(uint8_t));
std::memset(m_commandVertexTypes, 0, 0x3E80u); std::memset(m_commandVertexTypes, 0, MAX_COMMAND_BUFFERS * sizeof(uint8_t));
reservedRendererDword3 = 0; m_numBuffersToDeallocate = 0;
m_bShouldScreenGrabNextFrame = false; m_bShouldScreenGrabNextFrame = false;
SetupShaders(); SetupShaders();
const float clearColour[4] = {0.0f, 0.0f, 0.0f, 0.0f}; const float clearColour[4] = {0.0f, 0.0f, 0.0f, 0.0f};
SetClearColour(clearColour); SetClearColour(clearColour);
m_pDeviceContext->OMGetRenderTargets(1, &renderTargetView, &depthStencilView); m_pDeviceContext->OMGetRenderTargets(1, &mainRenderTargetView, &depthStencilView);
D3D11_RENDER_TARGET_VIEW_DESC rtvDesc = {}; D3D11_RENDER_TARGET_VIEW_DESC rtvDesc = {};
std::memset(&rtvDesc, 0, sizeof(rtvDesc)); std::memset(&rtvDesc, 0, sizeof(rtvDesc));
@@ -717,7 +717,7 @@ void Renderer::Initialise(ID3D11Device *pDevice, IDXGISwapChain *pSwapChain)
ID3D11Resource *backBufferResource = NULL; ID3D11Resource *backBufferResource = NULL;
ID3D11Texture2D *backBufferTexture = NULL; ID3D11Texture2D *backBufferTexture = NULL;
renderTargetView->GetResource(&backBufferResource); mainRenderTargetView->GetResource(&backBufferResource);
backBufferResource->QueryInterface(IID_PPV_ARGS(&backBufferTexture)); backBufferResource->QueryInterface(IID_PPV_ARGS(&backBufferTexture));
D3D11_TEXTURE2D_DESC backDesc = {}; D3D11_TEXTURE2D_DESC backDesc = {};
@@ -735,9 +735,9 @@ void Renderer::Initialise(ID3D11Device *pDevice, IDXGISwapChain *pSwapChain)
m_pDevice->CreateTexture2D(&safeDesc, NULL, &m_backBufferTexture); m_pDevice->CreateTexture2D(&safeDesc, NULL, &m_backBufferTexture);
m_pDevice->CreateShaderResourceView(m_backBufferTexture, NULL, &renderTargetShaderResourceView); m_pDevice->CreateShaderResourceView(m_backBufferTexture, NULL, &mainShaderResourceView);
renderTargetTextures[0] = m_backBufferTexture; downSampleTextures[THUMBNAIL_MAX_QUALITY] = m_backBufferTexture;
//m_pDevice->CreateRenderTargetView(backBufferTexture, &rtvDesc, &renderTargetView); //m_pDevice->CreateRenderTargetView(backBufferTexture, &rtvDesc, &renderTargetView);
@@ -756,15 +756,15 @@ void Renderer::Initialise(ID3D11Device *pDevice, IDXGISwapChain *pSwapChain)
desc.BindFlags = D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE; desc.BindFlags = D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE;
desc.CPUAccessFlags = 0; desc.CPUAccessFlags = 0;
desc.MiscFlags = 0; desc.MiscFlags = 0;
for (UINT i = 0; i < MAX_MIP_LEVELS - 1; ++i) for (UINT i = 0; i < NUM_THUMBNAIL_DOWNSAMPLES; ++i)
{ {
desc.Width = s_auiWidths[i + 1]; desc.Width = s_auiWidths[i + 1];
desc.Height = s_auiHeights[i + 1]; desc.Height = s_auiHeights[i + 1];
// @Patoke fix: before these would fail and our views would be nullptrs // @Patoke fix: before these would fail and our views would be nullptrs
m_pDevice->CreateTexture2D(&desc, NULL, &renderTargetTextures[i]); m_pDevice->CreateTexture2D(&desc, NULL, &downSampleTextures[i]);
m_pDevice->CreateRenderTargetView(renderTargetTextures[i], NULL, &renderTargetViews[i]); m_pDevice->CreateRenderTargetView(downSampleTextures[i], NULL, &downSampleRenderTargetViews[i]);
m_pDevice->CreateShaderResourceView(renderTargetTextures[i], NULL, &renderTargetShaderResourceViews[i]); m_pDevice->CreateShaderResourceView(downSampleTextures[i], NULL, &downSampleShaderResourceViews[i]);
} }
std::memset(m_textures, 0, sizeof(m_textures)); std::memset(m_textures, 0, sizeof(m_textures));
@@ -878,7 +878,7 @@ void Renderer::Present()
ID3D11Texture2D *backBuffer = NULL; ID3D11Texture2D *backBuffer = NULL;
ID3D11Texture2D *stagingTexture = NULL; ID3D11Texture2D *stagingTexture = NULL;
renderTargetView->GetResource(&backBufferResource); mainRenderTargetView->GetResource(&backBufferResource);
backBufferResource->QueryInterface(IID_PPV_ARGS(&backBuffer)); backBufferResource->QueryInterface(IID_PPV_ARGS(&backBuffer));
D3D11_TEXTURE2D_DESC desc = {}; D3D11_TEXTURE2D_DESC desc = {};
backBuffer->GetDesc(&desc); backBuffer->GetDesc(&desc);
@@ -911,9 +911,19 @@ void Renderer::Present()
m_pDeviceContext->Unmap(stagingTexture, 0); m_pDeviceContext->Unmap(stagingTexture, 0);
} }
static int count = 0; // @Patoke add
char curDir[256];
GetCurrentDirectoryA(sizeof(curDir), curDir);
char ssPath[512];
sprintf(ssPath, "%s/Windows64/GameHDD/", curDir);
_SYSTEMTIME UTCSysTime;
GetSystemTime(&UTCSysTime);
char fileName[304]; char fileName[304];
sprintf(fileName, "d:\\screen%d.png", count++); sprintf(fileName, "%s/%4d-%02d-%02d-%02d-%02d-%02d.png", ssPath, UTCSysTime.wYear, UTCSysTime.wMonth, UTCSysTime.wDay, UTCSysTime.wHour, UTCSysTime.wMinute,
UTCSysTime.wSecond);
D3DXIMAGE_INFO info; D3DXIMAGE_INFO info;
info.Width = kScreenGrabWidth; info.Width = kScreenGrabWidth;
@@ -1015,7 +1025,7 @@ void Renderer::StartFrame()
viewport.MinDepth = 0.0f; viewport.MinDepth = 0.0f;
viewport.MaxDepth = 1.0f; viewport.MaxDepth = 1.0f;
c.m_pDeviceContext->RSSetViewports(1, &viewport); c.m_pDeviceContext->RSSetViewports(1, &viewport);
c.m_pDeviceContext->OMSetRenderTargets(1, &renderTargetView, depthStencilView); c.m_pDeviceContext->OMSetRenderTargets(1, &mainRenderTargetView, depthStencilView);
PROFILER_FLIP(); PROFILER_FLIP();
} }
+8 -7
View File
@@ -98,14 +98,15 @@ ID3D11SamplerState *Renderer::GetManagedSamplerState()
if (it != managedSamplerStates.end()) if (it != managedSamplerStates.end())
return it->second; return it->second;
const bool clampU = (key & 0x01) != 0; const bool clampU = (key & SAMPLER_PARAM_CLAMP_U) != 0;
const bool clampV = (key & 0x02) != 0; const bool clampV = (key & SAMPLER_PARAM_CLAMP_V) != 0;
const bool linearFilter = (key & 0x04) != 0; const bool linearFilter = (key & SAMPLER_PARAM_LINEAR_FILTER) != 0;
const bool mipLinear = (key & 0x08) != 0; const bool mipLinear = (key & SAMPLER_PARAM_LINEAR_MIPS) != 0;
const int filterBits = (mipLinear ? 0x08 : 0x00) | (linearFilter ? 0x22 : 0x02); const int filterBits = (mipLinear != 0 ? (linearFilter ? D3D11_FILTER_MIN_MAG_MIP_LINEAR : D3D11_FILTER_MIN_POINT_MAG_MIP_LINEAR)
: (linearFilter ? D3D11_FILTER_MIN_LINEAR_MAG_POINT_MIP_LINEAR : D3D11_FILTER_MIN_MAG_POINT_MIP_LINEAR));
D3D11_SAMPLER_DESC desc = {}; D3D11_SAMPLER_DESC desc = {};
desc.Filter = static_cast<D3D11_FILTER>(filterBits >> 1); desc.Filter = static_cast<D3D11_FILTER>(filterBits);
desc.AddressU = clampU ? D3D11_TEXTURE_ADDRESS_CLAMP : D3D11_TEXTURE_ADDRESS_WRAP; desc.AddressU = clampU ? D3D11_TEXTURE_ADDRESS_CLAMP : D3D11_TEXTURE_ADDRESS_WRAP;
desc.AddressV = clampV ? D3D11_TEXTURE_ADDRESS_CLAMP : D3D11_TEXTURE_ADDRESS_WRAP; desc.AddressV = clampV ? D3D11_TEXTURE_ADDRESS_CLAMP : D3D11_TEXTURE_ADDRESS_WRAP;
desc.AddressW = D3D11_TEXTURE_ADDRESS_CLAMP; desc.AddressW = D3D11_TEXTURE_ADDRESS_CLAMP;
@@ -577,7 +578,7 @@ void Renderer::StateSetViewport(C4JRender::eViewportType viewportType)
viewport.MaxDepth = 1.0f; viewport.MaxDepth = 1.0f;
m_pDeviceContext->RSSetViewports(1, &viewport); m_pDeviceContext->RSSetViewports(1, &viewport);
m_pDeviceContext->OMSetRenderTargets(1, &renderTargetView, depthStencilView); m_pDeviceContext->OMSetRenderTargets(1, &mainRenderTargetView, depthStencilView);
} }
+19 -6
View File
@@ -146,8 +146,21 @@ C4JStorage::ESaveGameState CSaveGame::GetSavesInfo(int iPad, int (*Func)(LPVOID
// too but this is good enough for now // too but this is good enough for now
if (!(saveFileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)) if (!(saveFileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY))
{ {
strcpy_s(szTitleName, sizeof(szTitleName), saveFileData.cFileName); // remove the file extension
strcpy_s(this->m_szSaveTitle, saveFileData.cFileName); // populate the save title std::string decoratedSaveTitle = saveFileData.cFileName;
uint64_t extensionDot = decoratedSaveTitle.rfind('.');
// populate the save title
if (extensionDot != std::string::npos)
{
strcpy_s(this->m_szSaveTitle, decoratedSaveTitle.substr(0, extensionDot).c_str());
}
else
{
strcpy_s(this->m_szSaveTitle, decoratedSaveTitle.c_str());
}
strcpy_s(szTitleName, sizeof(szTitleName), this->m_szSaveTitle);
break; break;
} }
} while (FindNextFileA(hSaveFile, &saveFileData)); } while (FindNextFileA(hSaveFile, &saveFileData));
@@ -159,7 +172,7 @@ C4JStorage::ESaveGameState CSaveGame::GetSavesInfo(int iPad, int (*Func)(LPVOID
strcpy_s(m_pSaveDetails->SaveInfoA[i].UTF8SaveTitle, szTitleName); strcpy_s(m_pSaveDetails->SaveInfoA[i].UTF8SaveTitle, szTitleName);
char fileName[280]; char fileName[280];
sprintf(fileName, "%s\\Windows64\\GameHDD\\%s\\%s", dirName, findFileData.cFileName, szTitleName); sprintf(fileName, "%s\\Windows64\\GameHDD\\%s\\%s.ms", dirName, findFileData.cFileName, szTitleName);
GetFileAttributesExA(fileName, GetFileExInfoStandard, &fileInfoBuffer); GetFileAttributesExA(fileName, GetFileExInfoStandard, &fileInfoBuffer);
m_pSaveDetails->SaveInfoA[i].metaData.dataSize = fileInfoBuffer.nFileSizeLow; m_pSaveDetails->SaveInfoA[i].metaData.dataSize = fileInfoBuffer.nFileSizeLow;
@@ -275,7 +288,7 @@ C4JStorage::ESaveGameState CSaveGame::LoadSaveData(PSAVE_INFO pSaveInfo, int (*F
GetCurrentDirectoryA(sizeof(curDir), curDir); GetCurrentDirectoryA(sizeof(curDir), curDir);
sprintf(dirName, "%s/Windows64/GameHDD/%s", curDir, m_szSaveUniqueName); sprintf(dirName, "%s/Windows64/GameHDD/%s", curDir, m_szSaveUniqueName);
CreateDirectoryA(dirName, 0); CreateDirectoryA(dirName, 0);
sprintf(fileName, "%s/%s", dirName, this->m_szSaveTitle); // @Patoke add sprintf(fileName, "%s/%s.ms", dirName, this->m_szSaveTitle); // @Patoke add
HANDLE h = CreateFileA(fileName, GENERIC_READ, 0, nullptr, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0); HANDLE h = CreateFileA(fileName, GENERIC_READ, 0, nullptr, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0);
@@ -490,7 +503,7 @@ C4JStorage::ESaveGameState CSaveGame::SaveSaveData(int (*Func)(LPVOID, const boo
GetCurrentDirectoryA(sizeof(curDir), curDir); GetCurrentDirectoryA(sizeof(curDir), curDir);
sprintf(dirName, "%s/Windows64/GameHDD/%s", curDir, m_szSaveUniqueName); sprintf(dirName, "%s/Windows64/GameHDD/%s", curDir, m_szSaveUniqueName);
CreateDirectoryA(dirName, 0); CreateDirectoryA(dirName, 0);
sprintf(fileName, "%s/%s", dirName, this->m_szSaveTitle); // @Patoke add sprintf(fileName, "%s/%s.ms", dirName, this->m_szSaveTitle); // @Patoke add
HANDLE h = CreateFileA(fileName, GENERIC_WRITE, 0, nullptr, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0); HANDLE h = CreateFileA(fileName, GENERIC_WRITE, 0, nullptr, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0);
@@ -534,7 +547,7 @@ C4JStorage::ESaveGameState CSaveGame::DeleteSaveData(PSAVE_INFO pSaveInfo, int (
GetCurrentDirectoryA(sizeof(curDir), curDir); GetCurrentDirectoryA(sizeof(curDir), curDir);
sprintf(dirName, "%s/Windows64/GameHDD/%s", curDir, pSaveInfo->UTF8SaveFilename); sprintf(dirName, "%s/Windows64/GameHDD/%s", curDir, pSaveInfo->UTF8SaveFilename);
sprintf(fileName, "%s/%s", dirName, pSaveInfo->UTF8SaveTitle); sprintf(fileName, "%s/%s.ms", dirName, pSaveInfo->UTF8SaveTitle);
sprintf(thumbName, "%s/thumbnails/thumbData.png", dirName); sprintf(thumbName, "%s/thumbnails/thumbData.png", dirName);
DeleteFileA(fileName); DeleteFileA(fileName);