Skip to content

Commit d90630c

Browse files
Merge pull request #13262 from hrydgard/depth-texturing
Implement texturing from depth buffers (Vulkan only so far)
2 parents dd79d33 + 0aa2ceb commit d90630c

13 files changed

+175
-80
lines changed

GPU/Common/DepalettizeShaderCommon.cpp

+30-2
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121

2222
#include "GPU/Common/ShaderId.h"
2323
#include "GPU/Common/ShaderCommon.h"
24+
#include "Common/StringUtils.h"
2425
#include "Common/Log.h"
2526
#include "Core/Reporting.h"
2627
#include "GPU/GPUState.h"
@@ -45,6 +46,14 @@ void GenerateDepalShader300(char *buffer, GEBufferFormat pixelFormat, ShaderLang
4546
WRITE(p, "layout(set = 0, binding = 1) uniform sampler2D pal;\n");
4647
WRITE(p, "layout(location = 0) in vec2 v_texcoord0;\n");
4748
WRITE(p, "layout(location = 0) out vec4 fragColor0;\n");
49+
50+
// Support for depth.
51+
if (pixelFormat == GE_FORMAT_DEPTH16) {
52+
WRITE(p, "layout (push_constant) uniform params {\n");
53+
WRITE(p, " float z_scale; float z_offset;\n");
54+
WRITE(p, "};\n");
55+
}
56+
4857
} else {
4958
if (gl_extensions.IsGLES) {
5059
WRITE(p, "#version 300 es\n");
@@ -63,9 +72,12 @@ void GenerateDepalShader300(char *buffer, GEBufferFormat pixelFormat, ShaderLang
6372
WRITE(p, "float4 main(in float2 v_texcoord0 : TEXCOORD0) : SV_Target {\n");
6473
WRITE(p, " float4 color = tex.Sample(texSamp, v_texcoord0);\n");
6574
} else {
66-
// TODO: Add support for integer textures. Though it hardly matters.
6775
WRITE(p, "void main() {\n");
68-
WRITE(p, " vec4 color = texture(tex, v_texcoord0);\n");
76+
if (pixelFormat == GE_FORMAT_DEPTH16) {
77+
WRITE(p, " float color = texture(tex, v_texcoord0).r;\n");
78+
} else {
79+
WRITE(p, " vec4 color = texture(tex, v_texcoord0);\n");
80+
}
6981
}
7082

7183
int mask = gstate.getClutIndexMask();
@@ -105,6 +117,11 @@ void GenerateDepalShader300(char *buffer, GEBufferFormat pixelFormat, ShaderLang
105117
if (shiftedMask & 0x8000) WRITE(p, " int a = int(color.a);\n"); else WRITE(p, " int a = 0;\n");
106118
WRITE(p, " int index = (a << 15) | (b << 10) | (g << 5) | (r);\n");
107119
break;
120+
case GE_FORMAT_DEPTH16:
121+
// Remap depth buffer.
122+
WRITE(p, " float depth = (color - z_offset) * z_scale;\n");
123+
WRITE(p, " int index = int(clamp(depth, 0.0, 65535.0));\n");
124+
break;
108125
default:
109126
break;
110127
}
@@ -225,6 +242,17 @@ void GenerateDepalShaderFloat(char *buffer, GEBufferFormat pixelFormat, ShaderLa
225242
formatOK = false;
226243
}
227244
break;
245+
case GE_FORMAT_DEPTH16:
246+
{
247+
// TODO: I think we can handle most scenarios here, but texturing from depth buffers requires an extension on ES 2.0 anyway.
248+
if ((mask & (mask + 1)) == 0 && shift < 16) {
249+
index_multiplier = 1.0f / (float)(1 << shift);
250+
truncate_cpy(lookupMethod, "index.r");
251+
} else {
252+
formatOK = false;
253+
}
254+
break;
255+
}
228256
default:
229257
break;
230258
}

GPU/Common/FramebufferManagerCommon.cpp

+17-11
Original file line numberDiff line numberDiff line change
@@ -374,7 +374,7 @@ VirtualFramebuffer *FramebufferManagerCommon::DoSetRenderFrameBuffer(const Frame
374374
ResizeFramebufFBO(vfb, drawing_width, drawing_height, true);
375375
NotifyRenderFramebufferCreated(vfb);
376376

377-
INFO_LOG(FRAMEBUF, "Creating FBO for %08x : %i x %i x %i", vfb->fb_address, vfb->width, vfb->height, vfb->format);
377+
INFO_LOG(FRAMEBUF, "Creating FBO for %08x (z: %08x) : %i x %i x %i", vfb->fb_address, vfb->z_address, vfb->width, vfb->height, vfb->format);
378378

379379
vfb->last_frame_render = gpuStats.numFlips;
380380
frameLastFramebufUsed_ = gpuStats.numFlips;
@@ -445,7 +445,9 @@ VirtualFramebuffer *FramebufferManagerCommon::DoSetRenderFrameBuffer(const Frame
445445
}
446446

447447
void FramebufferManagerCommon::DestroyFramebuf(VirtualFramebuffer *v) {
448-
textureCache_->NotifyFramebuffer(v->fb_address, v, NOTIFY_FB_DESTROYED);
448+
// Notify the texture cache of both the color and depth buffers.
449+
textureCache_->NotifyFramebuffer(v->fb_address, v, NOTIFY_FB_DESTROYED, NOTIFY_FB_COLOR);
450+
textureCache_->NotifyFramebuffer(v->z_address, v, NOTIFY_FB_DESTROYED, NOTIFY_FB_DEPTH);
449451
if (v->fbo) {
450452
v->fbo->Release();
451453
v->fbo = nullptr;
@@ -472,7 +474,8 @@ void FramebufferManagerCommon::NotifyRenderFramebufferCreated(VirtualFramebuffer
472474
DownloadFramebufferOnSwitch(currentRenderVfb_);
473475
}
474476

475-
textureCache_->NotifyFramebuffer(vfb->fb_address, vfb, NOTIFY_FB_CREATED);
477+
textureCache_->NotifyFramebuffer(vfb->fb_address, vfb, NOTIFY_FB_CREATED, NOTIFY_FB_COLOR);
478+
textureCache_->NotifyFramebuffer(vfb->z_address, vfb, NOTIFY_FB_CREATED, NOTIFY_FB_DEPTH);
476479

477480
// Ugly...
478481
if (gstate_c.curRTWidth != vfb->width || gstate_c.curRTHeight != vfb->height) {
@@ -486,7 +489,8 @@ void FramebufferManagerCommon::NotifyRenderFramebufferCreated(VirtualFramebuffer
486489

487490
void FramebufferManagerCommon::NotifyRenderFramebufferUpdated(VirtualFramebuffer *vfb, bool vfbFormatChanged) {
488491
if (vfbFormatChanged) {
489-
textureCache_->NotifyFramebuffer(vfb->fb_address, vfb, NOTIFY_FB_UPDATED);
492+
textureCache_->NotifyFramebuffer(vfb->fb_address, vfb, NOTIFY_FB_UPDATED, NOTIFY_FB_COLOR);
493+
textureCache_->NotifyFramebuffer(vfb->fb_address, vfb, NOTIFY_FB_UPDATED, NOTIFY_FB_DEPTH);
490494
if (vfb->drawnFormat != vfb->format) {
491495
ReformatFramebufferFrom(vfb, vfb->drawnFormat);
492496
}
@@ -552,7 +556,8 @@ void FramebufferManagerCommon::NotifyRenderFramebufferSwitched(VirtualFramebuffe
552556
} else {
553557
if (vfb->fbo) {
554558
// This should only happen very briefly when toggling useBufferedRendering_.
555-
textureCache_->NotifyFramebuffer(vfb->fb_address, vfb, NOTIFY_FB_DESTROYED);
559+
textureCache_->NotifyFramebuffer(vfb->fb_address, vfb, NOTIFY_FB_DESTROYED, NOTIFY_FB_COLOR);
560+
textureCache_->NotifyFramebuffer(vfb->z_address, vfb, NOTIFY_FB_DESTROYED, NOTIFY_FB_DEPTH);
556561
vfb->fbo->Release();
557562
vfb->fbo = nullptr;
558563
}
@@ -564,7 +569,8 @@ void FramebufferManagerCommon::NotifyRenderFramebufferSwitched(VirtualFramebuffe
564569
gstate_c.skipDrawReason |= SKIPDRAW_NON_DISPLAYED_FB;
565570
}
566571
}
567-
textureCache_->NotifyFramebuffer(vfb->fb_address, vfb, NOTIFY_FB_UPDATED);
572+
textureCache_->NotifyFramebuffer(vfb->fb_address, vfb, NOTIFY_FB_UPDATED, NOTIFY_FB_COLOR);
573+
textureCache_->NotifyFramebuffer(vfb->z_address, vfb, NOTIFY_FB_UPDATED, NOTIFY_FB_DEPTH);
568574

569575
// ugly... is all this needed?
570576
if (gstate_c.curRTWidth != vfb->width || gstate_c.curRTHeight != vfb->height) {
@@ -1164,9 +1170,9 @@ bool FramebufferManagerCommon::NotifyFramebufferCopy(u32 src, u32 dst, int size,
11641170

11651171
if (dstBuffer && srcBuffer && !isMemset) {
11661172
if (srcBuffer == dstBuffer) {
1167-
WARN_LOG_REPORT_ONCE(dstsrccpy, G3D, "Intra-buffer memcpy (not supported) %08x -> %08x", src, dst);
1173+
WARN_LOG_ONCE(dstsrccpy, G3D, "Intra-buffer memcpy (not supported) %08x -> %08x (size: %x)", src, dst, size);
11681174
} else {
1169-
WARN_LOG_REPORT_ONCE(dstnotsrccpy, G3D, "Inter-buffer memcpy %08x -> %08x", src, dst);
1175+
WARN_LOG_ONCE(dstnotsrccpy, G3D, "Inter-buffer memcpy %08x -> %08x (size: %x)", src, dst, size);
11701176
// Just do the blit!
11711177
BlitFramebuffer(dstBuffer, 0, dstY, srcBuffer, 0, srcY, srcBuffer->width, srcH, 0);
11721178
SetColorUpdated(dstBuffer, skipDrawReason);
@@ -1177,7 +1183,7 @@ bool FramebufferManagerCommon::NotifyFramebufferCopy(u32 src, u32 dst, int size,
11771183
if (isMemset) {
11781184
gpuStats.numClears++;
11791185
}
1180-
WARN_LOG_ONCE(btucpy, G3D, "Memcpy fbo upload %08x -> %08x", src, dst);
1186+
WARN_LOG_ONCE(btucpy, G3D, "Memcpy fbo upload %08x -> %08x (size: %x)", src, dst, size);
11811187
FlushBeforeCopy();
11821188
const u8 *srcBase = Memory::GetPointerUnchecked(src);
11831189
DrawPixels(dstBuffer, 0, dstY, srcBase, dstBuffer->format, dstBuffer->fb_stride, dstBuffer->width, dstH);
@@ -1189,7 +1195,7 @@ bool FramebufferManagerCommon::NotifyFramebufferCopy(u32 src, u32 dst, int size,
11891195
WARN_LOG_ONCE(btdcpy, G3D, "Memcpy fbo download %08x -> %08x", src, dst);
11901196
FlushBeforeCopy();
11911197
if (srcH == 0 || srcY + srcH > srcBuffer->bufferHeight) {
1192-
WARN_LOG_REPORT_ONCE(btdcpyheight, G3D, "Memcpy fbo download %08x -> %08x skipped, %d+%d is taller than %d", src, dst, srcY, srcH, srcBuffer->bufferHeight);
1198+
WARN_LOG_ONCE(btdcpyheight, G3D, "Memcpy fbo download %08x -> %08x skipped, %d+%d is taller than %d", src, dst, srcY, srcH, srcBuffer->bufferHeight);
11931199
} else if (g_Config.bBlockTransferGPU && !srcBuffer->memoryUpdated && !PSP_CoreParameter().compat.flags().DisableReadbacks) {
11941200
ReadFramebufferToMemory(srcBuffer, 0, srcY, srcBuffer->width, srcH);
11951201
srcBuffer->usageFlags = (srcBuffer->usageFlags | FB_USAGE_DOWNLOAD) & ~FB_USAGE_DOWNLOAD_CLEAR;
@@ -1330,9 +1336,9 @@ VirtualFramebuffer *FramebufferManagerCommon::CreateRAMFramebuffer(uint32_t fbAd
13301336
vfb->drawnFormat = GE_FORMAT_8888;
13311337
vfb->usageFlags = FB_USAGE_RENDERTARGET;
13321338
SetColorUpdated(vfb, 0);
1333-
textureCache_->NotifyFramebuffer(vfb->fb_address, vfb, NOTIFY_FB_CREATED);
13341339
char name[64];
13351340
snprintf(name, sizeof(name), "%08x_color_RAM", vfb->fb_address);
1341+
textureCache_->NotifyFramebuffer(vfb->fb_address, vfb, NOTIFY_FB_CREATED, NOTIFY_FB_COLOR);
13361342
vfb->fbo = draw_->CreateFramebuffer({ vfb->renderWidth, vfb->renderHeight, 1, 1, true, (Draw::FBColorDepth)vfb->colorDepth, name });
13371343
vfbs_.push_back(vfb);
13381344

GPU/Common/GPUStateUtils.cpp

-3
Original file line numberDiff line numberDiff line change
@@ -633,9 +633,6 @@ void ConvertViewportAndScissor(bool useBufferedRendering, float renderWidth, flo
633633
float vpWidth = fabsf(gstate_c.vpWidth);
634634
float vpHeight = fabsf(gstate_c.vpHeight);
635635

636-
// We used to apply the viewport here via glstate, but there are limits which vary by driver.
637-
// This may mean some games won't work, or at least won't work at higher render resolutions.
638-
// So we apply it in the shader instead.
639636
float left = renderX + vpX0;
640637
float top = renderY + vpY0;
641638
float right = left + vpWidth;

0 commit comments

Comments
 (0)