mirror of
https://github.com/hrydgard/ppsspp.git
synced 2025-04-02 11:01:50 -04:00
D3D11: Lumines is now playable in non-buffered, with reverse colors.
This commit is contained in:
parent
a8dc9360f0
commit
3f4e14f504
13 changed files with 83 additions and 38 deletions
|
@ -7,13 +7,19 @@
|
|||
#include "GPU/Math3D.h"
|
||||
#include "Core/Reporting.h"
|
||||
|
||||
static void ConvertProjMatrixToVulkan(Matrix4x4 &in, bool invertedX, bool invertedY) {
|
||||
static void ConvertProjMatrixToVulkan(Matrix4x4 &in) {
|
||||
const Vec3 trans(0, 0, gstate_c.vpZOffset * 0.5f + 0.5f);
|
||||
const Vec3 scale(gstate_c.vpWidthScale, gstate_c.vpHeightScale, gstate_c.vpDepthScale * 0.5f);
|
||||
in.translateAndScale(trans, scale);
|
||||
}
|
||||
|
||||
void BaseUpdateUniforms(UB_VS_FS_Base *ub, uint64_t dirtyUniforms) {
|
||||
static void ConvertProjMatrixToD3D11(Matrix4x4 &in) {
|
||||
const Vec3 trans(0, 0, gstate_c.vpZOffset * 0.5f + 0.5f);
|
||||
const Vec3 scale(gstate_c.vpWidthScale, gstate_c.vpHeightScale, gstate_c.vpDepthScale * 0.5f);
|
||||
in.translateAndScale(trans, scale);
|
||||
}
|
||||
|
||||
void BaseUpdateUniforms(UB_VS_FS_Base *ub, uint64_t dirtyUniforms, bool flipViewport) {
|
||||
if (dirtyUniforms & DIRTY_TEXENV) {
|
||||
Uint8x3ToFloat4(ub->texEnvColor, gstate.texenvcolor);
|
||||
}
|
||||
|
@ -65,13 +71,21 @@ void BaseUpdateUniforms(UB_VS_FS_Base *ub, uint64_t dirtyUniforms) {
|
|||
flippedMatrix[8] = -flippedMatrix[8];
|
||||
flippedMatrix[12] = -flippedMatrix[12];
|
||||
}
|
||||
ConvertProjMatrixToVulkan(flippedMatrix, invertedX, invertedY);
|
||||
if (flipViewport) {
|
||||
ConvertProjMatrixToD3D11(flippedMatrix);
|
||||
} else {
|
||||
ConvertProjMatrixToVulkan(flippedMatrix);
|
||||
}
|
||||
CopyMatrix4x4(ub->proj, flippedMatrix.getReadPtr());
|
||||
}
|
||||
|
||||
if (dirtyUniforms & DIRTY_PROJTHROUGHMATRIX) {
|
||||
Matrix4x4 proj_through;
|
||||
proj_through.setOrthoVulkan(0.0f, gstate_c.curRTWidth, 0, gstate_c.curRTHeight, 0, 1);
|
||||
if (flipViewport) {
|
||||
proj_through.setOrthoD3D(0.0f, gstate_c.curRTWidth, gstate_c.curRTHeight, 0, 0, 1);
|
||||
} else {
|
||||
proj_through.setOrthoVulkan(0.0f, gstate_c.curRTWidth, 0, gstate_c.curRTHeight, 0, 1);
|
||||
}
|
||||
CopyMatrix4x4(ub->proj_through, proj_through.getReadPtr());
|
||||
}
|
||||
|
||||
|
|
|
@ -69,7 +69,7 @@ R"( float4x4 u_proj;
|
|||
float4x4 u_tex;
|
||||
float4 u_uvscaleoffset;
|
||||
float4 u_depthRange;
|
||||
float3 u_fogcoef_stencilreplace;
|
||||
float3 u_fogcoef;
|
||||
float4 u_matambientalpha;
|
||||
float3 u_fogcolor;
|
||||
float3 u_texenv;
|
||||
|
@ -98,7 +98,7 @@ struct UB_VS_Lights {
|
|||
};
|
||||
|
||||
static const char *ub_vs_lightsStr =
|
||||
R"( vec4 globalAmbient;
|
||||
R"( vec4 u_ambient;
|
||||
vec3 matdiffuse;
|
||||
vec4 matspecular;
|
||||
vec3 matemissive;
|
||||
|
@ -114,18 +114,36 @@ R"( vec4 globalAmbient;
|
|||
|
||||
// HLSL code is shared so these names are changed to match those in DX9.
|
||||
static const char *cb_vs_lightsStr =
|
||||
R"( float4 globalAmbient;
|
||||
R"( float4 u_ambient;
|
||||
float3 u_matdiffuse;
|
||||
float4 u_matspecular;
|
||||
float3 u_matemissive;
|
||||
float3 u_lightpos[4];
|
||||
float3 u_lightdir[4];
|
||||
float3 u_lightatt[4];
|
||||
float3 u_lightpos0;
|
||||
float3 u_lightpos1;
|
||||
float3 u_lightpos2;
|
||||
float3 u_lightpos3;
|
||||
float3 u_lightdir0;
|
||||
float3 u_lightdir1;
|
||||
float3 u_lightdir2;
|
||||
float3 u_lightdir3;
|
||||
float3 u_lightatt0;
|
||||
float3 u_lightatt1;
|
||||
float3 u_lightatt2;
|
||||
float3 u_lightatt3;
|
||||
float u_lightangle[4];
|
||||
float u_lightspotCoef[4];
|
||||
float3 u_ambient[4];
|
||||
float3 u_diffuse[4];
|
||||
float3 u_specular[4];
|
||||
float3 u_lightambient0;
|
||||
float3 u_lightambient1;
|
||||
float3 u_lightambient2;
|
||||
float3 u_lightambient3;
|
||||
float3 u_lightdiffuse0;
|
||||
float3 u_lightdiffuse1;
|
||||
float3 u_lightdiffuse2;
|
||||
float3 u_lightdiffuse3;
|
||||
float3 u_lightspecular0;
|
||||
float3 u_lightspecular1;
|
||||
float3 u_lightspecular2;
|
||||
float3 u_lightspecular3;
|
||||
)";
|
||||
|
||||
// With some cleverness, we could get away with uploading just half this when only the four first
|
||||
|
@ -144,7 +162,7 @@ static const char *cb_vs_bonesStr =
|
|||
R"( float4x4 m[8];
|
||||
)";
|
||||
|
||||
void BaseUpdateUniforms(UB_VS_FS_Base *ub, uint64_t dirtyUniforms);
|
||||
void BaseUpdateUniforms(UB_VS_FS_Base *ub, uint64_t dirtyUniforms, bool flipViewport);
|
||||
void LightUpdateUniforms(UB_VS_Lights *ub, uint64_t dirtyUniforms);
|
||||
void BoneUpdateUniforms(UB_VS_Bones *ub, uint64_t dirtyUniforms);
|
||||
|
||||
|
|
|
@ -44,8 +44,9 @@ public:
|
|||
nextMapDiscard_ = true;
|
||||
}
|
||||
|
||||
uint8_t *BeginPush(ID3D11DeviceContext *context, UINT *offset, size_t size) {
|
||||
uint8_t *BeginPush(ID3D11DeviceContext *context, UINT *offset, size_t size, int align = 16) {
|
||||
D3D11_MAPPED_SUBRESOURCE map;
|
||||
pos_ = (pos_ + align - 1) & ~(align - 1);
|
||||
context->Map(buffer_, 0, nextMapDiscard_ ? D3D11_MAP_WRITE_DISCARD : D3D11_MAP_WRITE_NO_OVERWRITE, 0, &map);
|
||||
nextMapDiscard_ = false;
|
||||
*offset = (UINT)pos_;
|
||||
|
|
|
@ -587,6 +587,8 @@ void DrawEngineD3D11::DoFlush() {
|
|||
if (useHWTransform) {
|
||||
ID3D11Buffer *vb_ = nullptr;
|
||||
ID3D11Buffer *ib_ = nullptr;
|
||||
if (prim == GE_PRIM_TRIANGLE_FAN)
|
||||
Crash();
|
||||
|
||||
int vertexCount = 0;
|
||||
int maxIndex = 0;
|
||||
|
@ -785,15 +787,13 @@ rotateVBO:
|
|||
context_->IASetVertexBuffers(0, 1, &buf, &stride, &vOffset);
|
||||
if (useElements) {
|
||||
UINT iOffset;
|
||||
int iSize = 2 * vertexCount;
|
||||
int iSize = 2 * indexGen.VertexCount();
|
||||
uint8_t *iptr = pushInds_->BeginPush(context_, &iOffset, iSize);
|
||||
memcpy(iptr, decIndex, iSize);
|
||||
pushInds_->EndPush(context_);
|
||||
context_->IASetIndexBuffer(pushInds_->Buf(), DXGI_FORMAT_R16_UINT, iOffset);
|
||||
context_->DrawIndexed(vertexCount, 0, 0);
|
||||
// context_->DrawIndexedPrimitiveUP(glprim[prim], 0, maxIndex + 1, D3DPrimCount(glprim[prim], vertexCount), decIndex, D3DFMT_INDEX16, decoded, dec_->GetDecVtxFmt().stride);
|
||||
} else {
|
||||
// context_->DrawPrimitiveUP(glprim[prim], D3DPrimCount(glprim[prim], vertexCount), decoded, dec_->GetDecVtxFmt().stride);
|
||||
context_->Draw(vertexCount, 0);
|
||||
}
|
||||
} else {
|
||||
|
@ -873,7 +873,7 @@ rotateVBO:
|
|||
|
||||
UINT stride = sizeof(TransformedVertex);
|
||||
UINT vOffset = 0;
|
||||
int vSize = numTrans * dec_->GetDecVtxFmt().stride;
|
||||
int vSize = maxIndex * stride;
|
||||
uint8_t *vptr = pushVerts_->BeginPush(context_, &vOffset, vSize);
|
||||
memcpy(vptr, drawBuffer, vSize);
|
||||
pushVerts_->EndPush(context_);
|
||||
|
@ -881,13 +881,12 @@ rotateVBO:
|
|||
context_->IASetVertexBuffers(0, 1, &buf, &stride, &vOffset);
|
||||
if (drawIndexed) {
|
||||
UINT iOffset;
|
||||
int iSize = 2 * (maxIndex + 1);
|
||||
int iSize = sizeof(int16_t) * numTrans;
|
||||
uint8_t *iptr = pushInds_->BeginPush(context_, &iOffset, iSize);
|
||||
memcpy(iptr, inds, iSize);
|
||||
pushInds_->EndPush(context_);
|
||||
context_->IASetIndexBuffer(pushInds_->Buf(), DXGI_FORMAT_R16_UINT, iOffset);
|
||||
context_->DrawIndexed(maxIndex + 1, 0, 0);
|
||||
// context_->DrawIndexedPrimitiveUP(glprim[prim], 0, maxIndex, numTrans, inds, DXGI_FORMAT_R16_UINT, drawBuffer, sizeof(TransformedVertex));
|
||||
context_->DrawIndexed(numTrans, 0, 0);
|
||||
} else {
|
||||
context_->Draw(numTrans, 0);
|
||||
}
|
||||
|
|
|
@ -453,7 +453,8 @@ void FramebufferManagerD3D11::BindFramebufferColor(int stage, VirtualFramebuffer
|
|||
}
|
||||
|
||||
if (!framebuffer->fbo || !useBufferedRendering_) {
|
||||
context_->PSSetShaderResources(stage, 1, nullptr);
|
||||
ID3D11ShaderResourceView *view = nullptr;
|
||||
context_->PSSetShaderResources(stage, 1, &view);
|
||||
gstate_c.skipDrawReason |= SKIPDRAW_BAD_FB_TEXTURE;
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -557,6 +557,7 @@ void GPU_D3D11::DumpNextFrame() {
|
|||
|
||||
void GPU_D3D11::BeginFrame() {
|
||||
ScheduleEvent(GPU_EVENT_BEGIN_FRAME);
|
||||
gstate_c.Dirty(DIRTY_PROJTHROUGHMATRIX);
|
||||
}
|
||||
|
||||
void GPU_D3D11::ReapplyGfxStateInternal() {
|
||||
|
|
|
@ -148,7 +148,7 @@ uint64_t ShaderManagerD3D11::UpdateUniforms() {
|
|||
if (dirty != 0) {
|
||||
D3D11_MAPPED_SUBRESOURCE map;
|
||||
if (dirty & DIRTY_BASE_UNIFORMS) {
|
||||
BaseUpdateUniforms(&ub_base, dirty);
|
||||
BaseUpdateUniforms(&ub_base, dirty, true);
|
||||
context_->Map(push_base, 0, D3D11_MAP_WRITE_DISCARD, 0, &map);
|
||||
memcpy(map.pData, &ub_base, sizeof(ub_base));
|
||||
context_->Unmap(push_base, 0);
|
||||
|
|
|
@ -132,7 +132,8 @@ void TextureCacheD3D11::SetFramebufferManager(FramebufferManagerD3D11 *fbManager
|
|||
}
|
||||
|
||||
void TextureCacheD3D11::Clear(bool delete_them) {
|
||||
// context_->PSSetShaderResources(0, 1, nullptr);
|
||||
// ID3D11ShaderResourceView *srv = nullptr;
|
||||
// context_->PSSetShaderResources(0, 1, &srv);
|
||||
lastBoundTexture = INVALID_TEX;
|
||||
if (delete_them) {
|
||||
for (TexCache::iterator iter = cache.begin(); iter != cache.end(); ++iter) {
|
||||
|
@ -182,7 +183,8 @@ void TextureCacheD3D11::Decimate() {
|
|||
if (cacheSizeEstimate_ >= TEXCACHE_MIN_PRESSURE) {
|
||||
const u32 had = cacheSizeEstimate_;
|
||||
|
||||
context_->PSSetShaderResources(0, 1, nullptr);
|
||||
ID3D11ShaderResourceView *srv = nullptr;
|
||||
context_->PSSetShaderResources(0, 1, &srv);
|
||||
lastBoundTexture = INVALID_TEX;
|
||||
int killAge = lowMemoryMode_ ? TEXTURE_KILL_AGE_LOWMEM : TEXTURE_KILL_AGE;
|
||||
for (TexCache::iterator iter = cache.begin(); iter != cache.end(); ) {
|
||||
|
@ -603,7 +605,8 @@ void TextureCacheD3D11::SetTexture(bool force) {
|
|||
u32 texaddr = gstate.getTextureAddress(0);
|
||||
if (!Memory::IsValidAddress(texaddr)) {
|
||||
// Bind a null texture and return.
|
||||
context_->PSSetShaderResources(0, 1, nullptr);
|
||||
ID3D11ShaderResourceView *srv = nullptr;
|
||||
context_->PSSetShaderResources(0, 1, &srv);
|
||||
lastBoundTexture = INVALID_TEX;
|
||||
return;
|
||||
}
|
||||
|
@ -1000,7 +1003,8 @@ void TextureCacheD3D11::BuildTexture(TexCacheEntry *const entry, bool replaceIma
|
|||
|
||||
if (replaceImages) {
|
||||
// Make sure it's not currently set.
|
||||
context_->PSSetShaderResources(0, 1, nullptr);
|
||||
ID3D11ShaderResourceView *srv = nullptr;
|
||||
context_->PSSetShaderResources(0, 1, &srv);
|
||||
}
|
||||
|
||||
// Seems to cause problems in Tactics Ogre.
|
||||
|
|
|
@ -254,7 +254,7 @@ void GenerateVertexShaderHLSL(const ShaderID &id, char *buffer, ShaderLanguage l
|
|||
}
|
||||
|
||||
WRITE(p, "VS_OUT main(VS_IN In) {\n");
|
||||
WRITE(p, " VS_OUT Out = (VS_OUT)0; \n");
|
||||
WRITE(p, " VS_OUT Out;\n");
|
||||
if (!useHWTransform) {
|
||||
// Simple pass-through of vertex data to fragment shader
|
||||
if (doTexture) {
|
||||
|
@ -304,13 +304,13 @@ void GenerateVertexShaderHLSL(const ShaderID &id, char *buffer, ShaderLanguage l
|
|||
if (lang == HLSL_D3D11) {
|
||||
WRITE(p, " float3 worldpos = mul(u_world, float4(In.position.xyz, 1.0)).xyz;\n");
|
||||
if (hasNormal)
|
||||
WRITE(p, " float3 worldnormal = normalize( mul(u_world, float4(%sIn.normal, 0.0)));\n", flipNormal ? "-" : "");
|
||||
WRITE(p, " float3 worldnormal = normalize(mul(u_world, float4(%sIn.normal, 0.0))).xyz;\n", flipNormal ? "-" : "");
|
||||
else
|
||||
WRITE(p, " float3 worldnormal = float3(0.0, 0.0, 1.0);\n");
|
||||
} else {
|
||||
WRITE(p, " float3 worldpos = mul(float4(In.position.xyz, 1.0), u_world);\n");
|
||||
if (hasNormal)
|
||||
WRITE(p, " float3 worldnormal = normalize( mul(float4(%sIn.normal, 0.0), u_world));\n", flipNormal ? "-" : "");
|
||||
WRITE(p, " float3 worldnormal = normalize(mul(float4(%sIn.normal, 0.0), u_world));\n", flipNormal ? "-" : "");
|
||||
else
|
||||
WRITE(p, " float3 worldnormal = float3(0.0, 0.0, 1.0);\n");
|
||||
}
|
||||
|
|
|
@ -222,7 +222,7 @@ uint64_t ShaderManagerVulkan::UpdateUniforms() {
|
|||
uint64_t dirty = gstate_c.GetDirtyUniforms();
|
||||
if (dirty != 0) {
|
||||
if (dirty & DIRTY_BASE_UNIFORMS)
|
||||
BaseUpdateUniforms(&ub_base, dirty);
|
||||
BaseUpdateUniforms(&ub_base, dirty, false);
|
||||
if (dirty & DIRTY_LIGHT_UNIFORMS)
|
||||
LightUpdateUniforms(&ub_lights, dirty);
|
||||
if (dirty & DIRTY_BONE_UNIFORMS)
|
||||
|
|
|
@ -304,7 +304,7 @@ bool GenerateVulkanGLSLVertexShader(const ShaderID &id, char *buffer, bool *uses
|
|||
bool distanceNeeded = false;
|
||||
|
||||
if (enableLighting) {
|
||||
WRITE(p, " vec4 lightSum0 = light.globalAmbient * %s + vec4(light.matemissive, 0.0);\n", ambientStr);
|
||||
WRITE(p, " vec4 lightSum0 = light.u_ambient * %s + vec4(light.matemissive, 0.0);\n", ambientStr);
|
||||
|
||||
for (int i = 0; i < 4; i++) {
|
||||
GELightType type = static_cast<GELightType>(id.Bits(VS_BIT_LIGHT0_TYPE + 4 * i, 2));
|
||||
|
|
|
@ -75,11 +75,10 @@ bool D3D11Context::Init(HINSTANCE hInst, HWND wnd, std::string *error_message) {
|
|||
|
||||
#ifdef _DEBUG
|
||||
if (SUCCEEDED(device_->QueryInterface(__uuidof(ID3D11Debug), (void**)&d3dDebug_))) {
|
||||
ID3D11InfoQueue *d3dInfoQueue = nullptr;
|
||||
if (SUCCEEDED(d3dDebug_->QueryInterface(__uuidof(ID3D11InfoQueue), (void**)&d3dInfoQueue))) {
|
||||
d3dInfoQueue->SetBreakOnSeverity(D3D11_MESSAGE_SEVERITY_CORRUPTION, true);
|
||||
d3dInfoQueue->SetBreakOnSeverity(D3D11_MESSAGE_SEVERITY_ERROR, true);
|
||||
d3dInfoQueue->SetBreakOnSeverity(D3D11_MESSAGE_SEVERITY_WARNING, true);
|
||||
if (SUCCEEDED(d3dDebug_->QueryInterface(__uuidof(ID3D11InfoQueue), (void**)&d3dInfoQueue_))) {
|
||||
d3dInfoQueue_->SetBreakOnSeverity(D3D11_MESSAGE_SEVERITY_CORRUPTION, true);
|
||||
d3dInfoQueue_->SetBreakOnSeverity(D3D11_MESSAGE_SEVERITY_ERROR, true);
|
||||
d3dInfoQueue_->SetBreakOnSeverity(D3D11_MESSAGE_SEVERITY_WARNING, true);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
@ -112,9 +111,16 @@ void D3D11Context::Resize() {
|
|||
}
|
||||
|
||||
void D3D11Context::Shutdown() {
|
||||
#ifdef _DEBUG
|
||||
d3dInfoQueue_->SetBreakOnSeverity(D3D11_MESSAGE_SEVERITY_CORRUPTION, false);
|
||||
d3dInfoQueue_->SetBreakOnSeverity(D3D11_MESSAGE_SEVERITY_ERROR, false);
|
||||
d3dInfoQueue_->SetBreakOnSeverity(D3D11_MESSAGE_SEVERITY_WARNING, false);
|
||||
#endif
|
||||
#ifdef _DEBUG
|
||||
d3dDebug_->ReportLiveDeviceObjects(D3D11_RLDO_SUMMARY | D3D11_RLDO_DETAIL);
|
||||
#endif
|
||||
d3dDebug_->Release();
|
||||
d3dInfoQueue_->Release();
|
||||
context_->ClearState();
|
||||
context_->Flush();
|
||||
|
||||
|
|
|
@ -45,6 +45,7 @@ private:
|
|||
|
||||
#ifdef _DEBUG
|
||||
ID3D11Debug *d3dDebug_ = nullptr;
|
||||
ID3D11InfoQueue *d3dInfoQueue_ = nullptr;
|
||||
#endif
|
||||
|
||||
D3D_DRIVER_TYPE driverType_;
|
||||
|
|
Loading…
Add table
Reference in a new issue