mirror of
https://github.com/hrydgard/ppsspp.git
synced 2025-04-02 11:01:50 -04:00
Unify BlitFramebufferDepth.
This commit is contained in:
parent
d0f7b1e30f
commit
d6d72db0a9
10 changed files with 21 additions and 63 deletions
|
@ -469,6 +469,26 @@ void FramebufferManagerCommon::DestroyFramebuf(VirtualFramebuffer *v) {
|
||||||
delete v;
|
delete v;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void FramebufferManagerCommon::BlitFramebufferDepth(VirtualFramebuffer *src, VirtualFramebuffer *dst) {
|
||||||
|
bool matchingDepthBuffer = src->z_address == dst->z_address && src->z_stride != 0 && dst->z_stride != 0;
|
||||||
|
bool matchingSize = src->width == dst->width && src->height == dst->height;
|
||||||
|
|
||||||
|
// Note: we don't use CopyFramebufferImage here, because it would copy depth AND stencil. See #9740.
|
||||||
|
if (matchingDepthBuffer && matchingSize) {
|
||||||
|
int w = std::min(src->renderWidth, dst->renderWidth);
|
||||||
|
int h = std::min(src->renderHeight, dst->renderHeight);
|
||||||
|
// Let's only do this if not clearing depth.
|
||||||
|
if (gstate_c.Supports(GPU_SUPPORTS_FRAMEBUFFER_BLIT)) {
|
||||||
|
draw_->BlitFramebuffer(src->fbo, 0, 0, w, h, dst->fbo, 0, 0, w, h, Draw::FB_DEPTH_BIT, Draw::FB_BLIT_NEAREST, "BlitFramebufferDepth");
|
||||||
|
RebindFramebuffer("BlitFramebufferDepth");
|
||||||
|
} else if (gstate_c.Supports(GPU_SUPPORTS_COPY_IMAGE)) {
|
||||||
|
draw_->CopyFramebufferImage(src->fbo, 0, 0, 0, 0, dst->fbo, 0, 0, 0, 0, w, h, 1, Draw::FB_DEPTH_BIT, "BlitFramebufferDepth");
|
||||||
|
RebindFramebuffer("BlitFramebufferDepth");
|
||||||
|
}
|
||||||
|
dst->last_frame_depth_updated = gpuStats.numFlips;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void FramebufferManagerCommon::NotifyRenderFramebufferCreated(VirtualFramebuffer *vfb) {
|
void FramebufferManagerCommon::NotifyRenderFramebufferCreated(VirtualFramebuffer *vfb) {
|
||||||
if (!useBufferedRendering_) {
|
if (!useBufferedRendering_) {
|
||||||
// Let's ignore rendering to targets that have not (yet) been displayed.
|
// Let's ignore rendering to targets that have not (yet) been displayed.
|
||||||
|
|
|
@ -339,7 +339,7 @@ protected:
|
||||||
void NotifyRenderFramebufferSwitched(VirtualFramebuffer *prevVfb, VirtualFramebuffer *vfb, bool isClearingDepth);
|
void NotifyRenderFramebufferSwitched(VirtualFramebuffer *prevVfb, VirtualFramebuffer *vfb, bool isClearingDepth);
|
||||||
|
|
||||||
virtual void ReformatFramebufferFrom(VirtualFramebuffer *vfb, GEBufferFormat old) = 0;
|
virtual void ReformatFramebufferFrom(VirtualFramebuffer *vfb, GEBufferFormat old) = 0;
|
||||||
virtual void BlitFramebufferDepth(VirtualFramebuffer *src, VirtualFramebuffer *dst) = 0;
|
void BlitFramebufferDepth(VirtualFramebuffer *src, VirtualFramebuffer *dst);
|
||||||
|
|
||||||
void ResizeFramebufFBO(VirtualFramebuffer *vfb, int w, int h, bool force = false, bool skipCopy = false);
|
void ResizeFramebufFBO(VirtualFramebuffer *vfb, int w, int h, bool force = false, bool skipCopy = false);
|
||||||
void ShowScreenResolution();
|
void ShowScreenResolution();
|
||||||
|
|
|
@ -315,19 +315,6 @@ static void CopyPixelDepthOnly(u32 *dstp, const u32 *srcp, size_t c) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void FramebufferManagerD3D11::BlitFramebufferDepth(VirtualFramebuffer *src, VirtualFramebuffer *dst) {
|
|
||||||
bool matchingDepthBuffer = src->z_address == dst->z_address && src->z_stride != 0 && dst->z_stride != 0;
|
|
||||||
bool matchingSize = src->width == dst->width && src->height == dst->height;
|
|
||||||
if (matchingDepthBuffer && matchingSize) {
|
|
||||||
int w = std::min(src->renderWidth, dst->renderWidth);
|
|
||||||
int h = std::min(src->renderHeight, dst->renderHeight);
|
|
||||||
// TODO: Currently, this copies depth AND stencil, which is a problem. See #9740.
|
|
||||||
draw_->CopyFramebufferImage(src->fbo, 0, 0, 0, 0, dst->fbo, 0, 0, 0, 0, w, h, 1, Draw::FB_DEPTH_BIT, "BlitFramebufferDepth");
|
|
||||||
RebindFramebuffer("RebindFramebuffer - BlitFramebufferDepth");
|
|
||||||
dst->last_frame_depth_updated = gpuStats.numFlips;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void FramebufferManagerD3D11::BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags) {
|
void FramebufferManagerD3D11::BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags) {
|
||||||
if (!framebuffer->fbo || !useBufferedRendering_) {
|
if (!framebuffer->fbo || !useBufferedRendering_) {
|
||||||
ID3D11ShaderResourceView *view = nullptr;
|
ID3D11ShaderResourceView *view = nullptr;
|
||||||
|
|
|
@ -45,8 +45,6 @@ public:
|
||||||
void DeviceLost();
|
void DeviceLost();
|
||||||
void ReformatFramebufferFrom(VirtualFramebuffer *vfb, GEBufferFormat old) override;
|
void ReformatFramebufferFrom(VirtualFramebuffer *vfb, GEBufferFormat old) override;
|
||||||
|
|
||||||
void BlitFramebufferDepth(VirtualFramebuffer *src, VirtualFramebuffer *dst) override;
|
|
||||||
|
|
||||||
void BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags);
|
void BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags);
|
||||||
|
|
||||||
virtual bool NotifyStencilUpload(u32 addr, int size, StencilUpload flags = StencilUpload::NEEDS_CLEAR) override;
|
virtual bool NotifyStencilUpload(u32 addr, int size, StencilUpload flags = StencilUpload::NEEDS_CLEAR) override;
|
||||||
|
|
|
@ -305,19 +305,6 @@ static const D3DVERTEXELEMENT9 g_FramebufferVertexElements[] = {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void FramebufferManagerDX9::BlitFramebufferDepth(VirtualFramebuffer *src, VirtualFramebuffer *dst) {
|
|
||||||
bool matchingDepthBuffer = src->z_address == dst->z_address && src->z_stride != 0 && dst->z_stride != 0;
|
|
||||||
bool matchingSize = src->width == dst->width && src->height == dst->height;
|
|
||||||
if (matchingDepthBuffer && matchingSize) {
|
|
||||||
// Should use StretchRect here? Note: should only copy depth and ideally NOT copy stencil. See #9740.
|
|
||||||
int w = std::min(src->renderWidth, dst->renderWidth);
|
|
||||||
int h = std::min(src->renderHeight, dst->renderHeight);
|
|
||||||
draw_->CopyFramebufferImage(src->fbo, 0, 0, 0, 0, dst->fbo, 0, 0, 0, 0, w, h, 1, Draw::FB_DEPTH_BIT, "BlitFramebufferDepth");
|
|
||||||
RebindFramebuffer("RebindFramebuffer - BlitFramebufferDepth");
|
|
||||||
dst->last_frame_depth_updated = gpuStats.numFlips;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
LPDIRECT3DSURFACE9 FramebufferManagerDX9::GetOffscreenSurface(LPDIRECT3DSURFACE9 similarSurface, VirtualFramebuffer *vfb) {
|
LPDIRECT3DSURFACE9 FramebufferManagerDX9::GetOffscreenSurface(LPDIRECT3DSURFACE9 similarSurface, VirtualFramebuffer *vfb) {
|
||||||
D3DSURFACE_DESC desc = {};
|
D3DSURFACE_DESC desc = {};
|
||||||
HRESULT hr = similarSurface->GetDesc(&desc);
|
HRESULT hr = similarSurface->GetDesc(&desc);
|
||||||
|
|
|
@ -50,8 +50,6 @@ public:
|
||||||
void DeviceLost();
|
void DeviceLost();
|
||||||
void ReformatFramebufferFrom(VirtualFramebuffer *vfb, GEBufferFormat old) override;
|
void ReformatFramebufferFrom(VirtualFramebuffer *vfb, GEBufferFormat old) override;
|
||||||
|
|
||||||
void BlitFramebufferDepth(VirtualFramebuffer *src, VirtualFramebuffer *dst) override;
|
|
||||||
|
|
||||||
void BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags);
|
void BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags);
|
||||||
|
|
||||||
virtual bool NotifyStencilUpload(u32 addr, int size, StencilUpload flags = StencilUpload::NEEDS_CLEAR) override;
|
virtual bool NotifyStencilUpload(u32 addr, int size, StencilUpload flags = StencilUpload::NEEDS_CLEAR) override;
|
||||||
|
|
|
@ -263,21 +263,6 @@ void FramebufferManagerGLES::ReformatFramebufferFrom(VirtualFramebuffer *vfb, GE
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void FramebufferManagerGLES::BlitFramebufferDepth(VirtualFramebuffer *src, VirtualFramebuffer *dst) {
|
|
||||||
bool matchingDepthBuffer = src->z_address == dst->z_address && src->z_stride != 0 && dst->z_stride != 0;
|
|
||||||
bool matchingSize = src->width == dst->width && src->height == dst->height;
|
|
||||||
|
|
||||||
// Note: we don't use CopyFramebufferImage here, because it would copy depth AND stencil. See #9740.
|
|
||||||
if (matchingDepthBuffer && matchingSize && gstate_c.Supports(GPU_SUPPORTS_FRAMEBUFFER_BLIT)) {
|
|
||||||
int w = std::min(src->renderWidth, dst->renderWidth);
|
|
||||||
int h = std::min(src->renderHeight, dst->renderHeight);
|
|
||||||
// Let's only do this if not clearing depth.
|
|
||||||
draw_->BlitFramebuffer(src->fbo, 0, 0, w, h, dst->fbo, 0, 0, w, h, Draw::FB_DEPTH_BIT, Draw::FB_BLIT_NEAREST, "BlitFramebufferDepth");
|
|
||||||
RebindFramebuffer("BlitFramebufferDepth");
|
|
||||||
dst->last_frame_depth_updated = gpuStats.numFlips;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void FramebufferManagerGLES::BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags) {
|
void FramebufferManagerGLES::BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags) {
|
||||||
if (!framebuffer->fbo || !useBufferedRendering_) {
|
if (!framebuffer->fbo || !useBufferedRendering_) {
|
||||||
render_->BindTexture(stage, nullptr);
|
render_->BindTexture(stage, nullptr);
|
||||||
|
|
|
@ -49,8 +49,6 @@ public:
|
||||||
void DeviceLost();
|
void DeviceLost();
|
||||||
void ReformatFramebufferFrom(VirtualFramebuffer *vfb, GEBufferFormat old) override;
|
void ReformatFramebufferFrom(VirtualFramebuffer *vfb, GEBufferFormat old) override;
|
||||||
|
|
||||||
void BlitFramebufferDepth(VirtualFramebuffer *src, VirtualFramebuffer *dst) override;
|
|
||||||
|
|
||||||
// For use when texturing from a framebuffer. May create a duplicate if target.
|
// For use when texturing from a framebuffer. May create a duplicate if target.
|
||||||
void BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags);
|
void BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags);
|
||||||
|
|
||||||
|
|
|
@ -269,19 +269,6 @@ void FramebufferManagerVulkan::ReformatFramebufferFrom(VirtualFramebuffer *vfb,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Except for a missing rebind and silly scissor enables, identical copy of the same function in GPU_GLES - tricky parts are in thin3d.
|
|
||||||
void FramebufferManagerVulkan::BlitFramebufferDepth(VirtualFramebuffer *src, VirtualFramebuffer *dst) {
|
|
||||||
bool matchingDepthBuffer = src->z_address == dst->z_address && src->z_stride != 0 && dst->z_stride != 0;
|
|
||||||
bool matchingSize = src->width == dst->width && src->height == dst->height;
|
|
||||||
if (matchingDepthBuffer && matchingSize) {
|
|
||||||
int w = std::min(src->renderWidth, dst->renderWidth);
|
|
||||||
int h = std::min(src->renderHeight, dst->renderHeight);
|
|
||||||
// TODO: Currently, this copies depth AND stencil, which is a problem. See #9740.
|
|
||||||
draw_->CopyFramebufferImage(src->fbo, 0, 0, 0, 0, dst->fbo, 0, 0, 0, 0, w, h, 1, Draw::FB_DEPTH_BIT, "BlitFramebufferDepth");
|
|
||||||
dst->last_frame_depth_updated = gpuStats.numFlips;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
VkImageView FramebufferManagerVulkan::BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags) {
|
VkImageView FramebufferManagerVulkan::BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags) {
|
||||||
if (!framebuffer->fbo || !useBufferedRendering_) {
|
if (!framebuffer->fbo || !useBufferedRendering_) {
|
||||||
gstate_c.skipDrawReason |= SKIPDRAW_BAD_FB_TEXTURE;
|
gstate_c.skipDrawReason |= SKIPDRAW_BAD_FB_TEXTURE;
|
||||||
|
|
|
@ -54,8 +54,6 @@ public:
|
||||||
int GetLineWidth();
|
int GetLineWidth();
|
||||||
void ReformatFramebufferFrom(VirtualFramebuffer *vfb, GEBufferFormat old) override;
|
void ReformatFramebufferFrom(VirtualFramebuffer *vfb, GEBufferFormat old) override;
|
||||||
|
|
||||||
void BlitFramebufferDepth(VirtualFramebuffer *src, VirtualFramebuffer *dst) override;
|
|
||||||
|
|
||||||
bool NotifyStencilUpload(u32 addr, int size, StencilUpload flags = StencilUpload::NEEDS_CLEAR) override;
|
bool NotifyStencilUpload(u32 addr, int size, StencilUpload flags = StencilUpload::NEEDS_CLEAR) override;
|
||||||
|
|
||||||
VkImageView BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags);
|
VkImageView BindFramebufferAsColorTexture(int stage, VirtualFramebuffer *framebuffer, int flags);
|
||||||
|
|
Loading…
Add table
Reference in a new issue