Commit 20f8828c by Cody Northrop Committed by Commit Bot

Capture/Replay: Fixes for compressed texture cache

Some compressed block sizes don't align properly to surface dimensions. For instance, ASTC_6x6_UNORM populating a 64x64 surface. Our FrameCapture code was assuming block alignment and was losing data. To handle this, round the dimensions up to natural block alignment before doing any scaling math. This also fixes the problem we've had of losing small mip levels due to scaling. Test: Aztec Ruins MEC Bug: b/160808198 Bug: angleproject:5552 Change-Id: I194cdac87f7361f85539e78f85069b336ffb1f36 Reviewed-on: https://chromium-review.googlesource.com/c/angle/angle/+/2634205Reviewed-by: 's avatarTim Van Patten <timvp@google.com> Reviewed-by: 's avatarJamie Madill <jmadill@chromium.org> Commit-Queue: Cody Northrop <cnorthrop@google.com>
parent 31f64e44
...@@ -3848,20 +3848,30 @@ void FrameCapture::captureCompressedTextureData(const gl::Context *context, cons ...@@ -3848,20 +3848,30 @@ void FrameCapture::captureCompressedTextureData(const gl::Context *context, cons
const gl::Extents &levelExtents = texture->getExtents(targetPacked, level); const gl::Extents &levelExtents = texture->getExtents(targetPacked, level);
// Scale down the width/height pixel offsets to reflect block size // Scale down the width/height pixel offsets to reflect block size
int widthScale = static_cast<int>(format.compressedBlockWidth); int blockWidth = static_cast<int>(format.compressedBlockWidth);
int heightScale = static_cast<int>(format.compressedBlockHeight); int blockHeight = static_cast<int>(format.compressedBlockHeight);
ASSERT(format.compressedBlockDepth == 1); ASSERT(format.compressedBlockDepth == 1);
pixelWidth /= widthScale;
pixelHeight /= heightScale; // Round the incoming width and height up to align with block size
xoffset /= widthScale; pixelWidth = rx::roundUp(pixelWidth, blockWidth);
yoffset /= heightScale; pixelHeight = rx::roundUp(pixelHeight, blockHeight);
// Scale the width, height, and offsets
pixelWidth /= blockWidth;
pixelHeight /= blockHeight;
xoffset /= blockWidth;
yoffset /= blockHeight;
GLint pixelBytes = static_cast<GLint>(format.pixelBytes); GLint pixelBytes = static_cast<GLint>(format.pixelBytes);
// Also round the texture's width and height up to reflect block size
int levelWidth = rx::roundUp(levelExtents.width, blockWidth);
int levelHeight = rx::roundUp(levelExtents.height, blockHeight);
GLint pixelRowPitch = pixelWidth * pixelBytes; GLint pixelRowPitch = pixelWidth * pixelBytes;
GLint pixelDepthPitch = pixelRowPitch * pixelHeight; GLint pixelDepthPitch = pixelRowPitch * pixelHeight;
GLint levelRowPitch = (levelExtents.width / widthScale) * pixelBytes; GLint levelRowPitch = (levelWidth / blockWidth) * pixelBytes;
GLint levelDepthPitch = levelRowPitch * (levelExtents.height / heightScale); GLint levelDepthPitch = (levelHeight / blockHeight) * levelRowPitch;
for (GLint zindex = 0; zindex < pixelDepth; ++zindex) for (GLint zindex = 0; zindex < pixelDepth; ++zindex)
{ {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment