mirror of
https://github.com/cemu-project/Cemu.git
synced 2024-11-22 00:59:18 +01:00
Latte: Small refactor and clean up for texture size code
This commit is contained in:
parent
0993658c82
commit
dd7cb74cd2
1
.gitignore
vendored
1
.gitignore
vendored
@ -39,6 +39,7 @@ bin/sdcard/*
|
|||||||
bin/screenshots/*
|
bin/screenshots/*
|
||||||
bin/dump/*
|
bin/dump/*
|
||||||
bin/cafeLibs/*
|
bin/cafeLibs/*
|
||||||
|
bin/keys.txt
|
||||||
|
|
||||||
!bin/shaderCache/info.txt
|
!bin/shaderCache/info.txt
|
||||||
bin/shaderCache/*
|
bin/shaderCache/*
|
||||||
|
@ -309,7 +309,7 @@ public:
|
|||||||
{
|
{
|
||||||
if ((rangeBegin & 0xF))
|
if ((rangeBegin & 0xF))
|
||||||
{
|
{
|
||||||
cemuLog_logDebug(LogType::Force, "writeStreamout(): RangeBegin not aligned to 16. Begin {:08x} End {:08x}", rangeBegin, rangeEnd);
|
cemuLog_logDebugOnce(LogType::Force, "writeStreamout(): RangeBegin not aligned to 16. Begin {:08x} End {:08x}", rangeBegin, rangeEnd);
|
||||||
rangeBegin = (rangeBegin + 0xF) & ~0xF;
|
rangeBegin = (rangeBegin + 0xF) & ~0xF;
|
||||||
rangeEnd = std::max(rangeBegin, rangeEnd);
|
rangeEnd = std::max(rangeBegin, rangeEnd);
|
||||||
}
|
}
|
||||||
|
@ -42,7 +42,7 @@ private:
|
|||||||
if(colorBuffer[i].texture == nullptr)
|
if(colorBuffer[i].texture == nullptr)
|
||||||
continue;
|
continue;
|
||||||
sint32 effectiveWidth, effectiveHeight;
|
sint32 effectiveWidth, effectiveHeight;
|
||||||
LatteTexture_getEffectiveSize(colorBuffer[i].texture->baseTexture, &effectiveWidth, &effectiveHeight, nullptr, colorBuffer[i].texture->firstMip);
|
colorBuffer[i].texture->baseTexture->GetEffectiveSize(effectiveWidth, effectiveHeight, colorBuffer[i].texture->firstMip);
|
||||||
if (rtEffectiveSize.x == 0 && rtEffectiveSize.y == 0)
|
if (rtEffectiveSize.x == 0 && rtEffectiveSize.y == 0)
|
||||||
{
|
{
|
||||||
rtEffectiveSize.x = effectiveWidth;
|
rtEffectiveSize.x = effectiveWidth;
|
||||||
@ -64,7 +64,7 @@ private:
|
|||||||
if (depthBuffer.texture)
|
if (depthBuffer.texture)
|
||||||
{
|
{
|
||||||
sint32 effectiveWidth, effectiveHeight;
|
sint32 effectiveWidth, effectiveHeight;
|
||||||
LatteTexture_getEffectiveSize(depthBuffer.texture->baseTexture, &effectiveWidth, &effectiveHeight, nullptr, depthBuffer.texture->firstMip);
|
depthBuffer.texture->baseTexture->GetEffectiveSize(effectiveWidth, effectiveHeight, depthBuffer.texture->firstMip);
|
||||||
if (rtEffectiveSize.x == 0 && rtEffectiveSize.y == 0)
|
if (rtEffectiveSize.x == 0 && rtEffectiveSize.y == 0)
|
||||||
{
|
{
|
||||||
rtEffectiveSize.x = effectiveWidth;
|
rtEffectiveSize.x = effectiveWidth;
|
||||||
|
@ -516,14 +516,12 @@ bool LatteMRT::UpdateCurrentFBO()
|
|||||||
sLatteRenderTargetState.rtUpdateList[sLatteRenderTargetState.rtUpdateListCount] = colorAttachmentView;
|
sLatteRenderTargetState.rtUpdateList[sLatteRenderTargetState.rtUpdateListCount] = colorAttachmentView;
|
||||||
sLatteRenderTargetState.rtUpdateListCount++;
|
sLatteRenderTargetState.rtUpdateListCount++;
|
||||||
|
|
||||||
sint32 colorAttachmentWidth;
|
sint32 colorAttachmentWidth, colorAttachmentHeight;
|
||||||
sint32 colorAttachmentHeight;
|
colorAttachmentView->baseTexture->GetSize(colorAttachmentWidth, colorAttachmentHeight, colorAttachmentView->firstMip);
|
||||||
|
|
||||||
LatteTexture_getSize(colorAttachmentView->baseTexture, &colorAttachmentWidth, &colorAttachmentHeight, nullptr, colorAttachmentView->firstMip);
|
|
||||||
|
|
||||||
// set effective size
|
// set effective size
|
||||||
sint32 effectiveWidth, effectiveHeight;
|
sint32 effectiveWidth, effectiveHeight;
|
||||||
LatteTexture_getEffectiveSize(colorAttachmentView->baseTexture, &effectiveWidth, &effectiveHeight, nullptr, colorAttachmentView->firstMip);
|
colorAttachmentView->baseTexture->GetEffectiveSize(effectiveWidth, effectiveHeight, colorAttachmentView->firstMip);
|
||||||
if (rtEffectiveSize->width == 0 && rtEffectiveSize->height == 0)
|
if (rtEffectiveSize->width == 0 && rtEffectiveSize->height == 0)
|
||||||
{
|
{
|
||||||
rtEffectiveSize->width = effectiveWidth;
|
rtEffectiveSize->width = effectiveWidth;
|
||||||
@ -531,9 +529,7 @@ bool LatteMRT::UpdateCurrentFBO()
|
|||||||
}
|
}
|
||||||
else if (rtEffectiveSize->width != effectiveWidth && rtEffectiveSize->height != effectiveHeight)
|
else if (rtEffectiveSize->width != effectiveWidth && rtEffectiveSize->height != effectiveHeight)
|
||||||
{
|
{
|
||||||
#ifdef CEMU_DEBUG_ASSERT
|
cemuLog_logDebug(LogType::Force, "Color buffer size mismatch ({}x{}). Effective size: {}x{} Real size: {}x{} Mismatching texture: {:08x} {}x{} fmt {:04x}", rtEffectiveSize->width, rtEffectiveSize->height, effectiveWidth, effectiveHeight, colorAttachmentView->baseTexture->width, colorAttachmentView->baseTexture->height, colorAttachmentView->baseTexture->physAddress, colorAttachmentView->baseTexture->width, colorAttachmentView->baseTexture->height, (uint32)colorAttachmentView->baseTexture->format);
|
||||||
cemuLog_log(LogType::Force, "Color buffer size mismatch ({}x{}). Effective size: {}x{} Real size: {}x{} Mismatching texture: {:08x} {}x{} fmt {:04x}", rtEffectiveSize->width, rtEffectiveSize->height, effectiveWidth, effectiveHeight, colorAttachmentView->baseTexture->width, colorAttachmentView->baseTexture->height, colorAttachmentView->baseTexture->physAddress, colorAttachmentView->baseTexture->width, colorAttachmentView->baseTexture->height, (uint32)colorAttachmentView->baseTexture->format);
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
// currently the first color attachment defines the size of the current render target
|
// currently the first color attachment defines the size of the current render target
|
||||||
if (rtRealSize->width == 0 && rtRealSize->height == 0)
|
if (rtRealSize->width == 0 && rtRealSize->height == 0)
|
||||||
@ -608,15 +604,11 @@ bool LatteMRT::UpdateCurrentFBO()
|
|||||||
|
|
||||||
if (depthBufferPhysMem != MPTR_NULL)
|
if (depthBufferPhysMem != MPTR_NULL)
|
||||||
{
|
{
|
||||||
bool depthBufferWasFound = false;
|
|
||||||
LatteTextureView* depthBufferView = LatteTextureViewLookupCache::lookupSliceEx(depthBufferPhysMem, depthBufferWidth, depthBufferHeight, depthBufferPitch, 0, depthBufferViewFirstSlice, depthBufferFormat, true);
|
LatteTextureView* depthBufferView = LatteTextureViewLookupCache::lookupSliceEx(depthBufferPhysMem, depthBufferWidth, depthBufferHeight, depthBufferPitch, 0, depthBufferViewFirstSlice, depthBufferFormat, true);
|
||||||
if (depthBufferView == nullptr)
|
if (depthBufferView == nullptr)
|
||||||
{
|
{
|
||||||
// create depth buffer view
|
// create new depth buffer view and if it doesn't exist then also create the texture
|
||||||
if(depthBufferViewFirstSlice == 0)
|
depthBufferView = LatteTexture_CreateMapping(depthBufferPhysMem, 0, depthBufferWidth, depthBufferHeight, depthBufferViewFirstSlice+1, depthBufferPitch, depthBufferTileMode, depthBufferSwizzle, 0, 1, depthBufferViewFirstSlice, 1, depthBufferFormat, depthBufferViewFirstSlice > 0 ? Latte::E_DIM::DIM_2D_ARRAY : Latte::E_DIM::DIM_2D, Latte::E_DIM::DIM_2D, true);
|
||||||
depthBufferView = LatteTexture_CreateMapping(depthBufferPhysMem, 0, depthBufferWidth, depthBufferHeight, 1, depthBufferPitch, depthBufferTileMode, depthBufferSwizzle, 0, 1, 0, 1, depthBufferFormat, Latte::E_DIM::DIM_2D, Latte::E_DIM::DIM_2D, true);
|
|
||||||
else
|
|
||||||
depthBufferView = LatteTexture_CreateMapping(depthBufferPhysMem, 0, depthBufferWidth, depthBufferHeight, depthBufferViewFirstSlice+1, depthBufferPitch, depthBufferTileMode, depthBufferSwizzle, 0, 1, depthBufferViewFirstSlice, 1, depthBufferFormat, Latte::E_DIM::DIM_2D_ARRAY, Latte::E_DIM::DIM_2D, true);
|
|
||||||
LatteGPUState.repeatTextureInitialization = true;
|
LatteGPUState.repeatTextureInitialization = true;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -626,7 +618,7 @@ bool LatteMRT::UpdateCurrentFBO()
|
|||||||
}
|
}
|
||||||
// set effective size
|
// set effective size
|
||||||
sint32 effectiveWidth, effectiveHeight;
|
sint32 effectiveWidth, effectiveHeight;
|
||||||
LatteTexture_getEffectiveSize(depthBufferView->baseTexture, &effectiveWidth, &effectiveHeight, NULL);
|
depthBufferView->baseTexture->GetEffectiveSize(effectiveWidth, effectiveHeight, depthBufferViewFirstSlice);
|
||||||
if (rtEffectiveSize->width == 0 && rtEffectiveSize->height == 0)
|
if (rtEffectiveSize->width == 0 && rtEffectiveSize->height == 0)
|
||||||
{
|
{
|
||||||
rtEffectiveSize->width = effectiveWidth;
|
rtEffectiveSize->width = effectiveWidth;
|
||||||
@ -917,10 +909,8 @@ void LatteRenderTarget_copyToBackbuffer(LatteTextureView* textureView, bool isPa
|
|||||||
// mark source texture as still in use
|
// mark source texture as still in use
|
||||||
LatteTC_MarkTextureStillInUse(textureView->baseTexture);
|
LatteTC_MarkTextureStillInUse(textureView->baseTexture);
|
||||||
|
|
||||||
sint32 effectiveWidth;
|
sint32 effectiveWidth, effectiveHeight;
|
||||||
sint32 effectiveHeight;
|
textureView->baseTexture->GetEffectiveSize(effectiveWidth, effectiveHeight, 0);
|
||||||
sint32 effectiveDepth;
|
|
||||||
LatteTexture_getEffectiveSize(textureView->baseTexture, &effectiveWidth, &effectiveHeight, &effectiveDepth, 0);
|
|
||||||
_currentOutputImageWidth = effectiveWidth;
|
_currentOutputImageWidth = effectiveWidth;
|
||||||
_currentOutputImageHeight = effectiveHeight;
|
_currentOutputImageHeight = effectiveHeight;
|
||||||
|
|
||||||
|
@ -297,9 +297,9 @@ void LatteTexture_copyData(LatteTexture* srcTexture, LatteTexture* dstTexture, s
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
sint32 effectiveWidth_dst, effectiveHeight_dst;
|
sint32 effectiveWidth_dst, effectiveHeight_dst;
|
||||||
LatteTexture_getEffectiveSize(srcTexture, &effectiveWidth_dst, &effectiveHeight_dst, NULL, 0);
|
srcTexture->GetEffectiveSize(effectiveWidth_dst, effectiveHeight_dst, 0);
|
||||||
sint32 effectiveWidth_src, effectiveHeight_src;
|
sint32 effectiveWidth_src, effectiveHeight_src;
|
||||||
LatteTexture_getEffectiveSize(dstTexture, &effectiveWidth_src, &effectiveHeight_src, NULL, 0);
|
dstTexture->GetEffectiveSize(effectiveWidth_src, effectiveHeight_src, 0);
|
||||||
|
|
||||||
debug_printf("texture_copyData(): Effective size mismatch\n");
|
debug_printf("texture_copyData(): Effective size mismatch\n");
|
||||||
cemuLog_logDebug(LogType::Force, "texture_copyData(): Effective size mismatch (due to texture rule)");
|
cemuLog_logDebug(LogType::Force, "texture_copyData(): Effective size mismatch (due to texture rule)");
|
||||||
@ -307,8 +307,6 @@ void LatteTexture_copyData(LatteTexture* srcTexture, LatteTexture* dstTexture, s
|
|||||||
cemuLog_logDebug(LogType::Force, "Source: origResolution {:04}x{:04} effectiveResolution {:04}x{:04} fmt {:04x} mipIndex {}", srcTexture->width, srcTexture->height, effectiveWidth_src, effectiveHeight_src, (uint32)srcTexture->format, 0);
|
cemuLog_logDebug(LogType::Force, "Source: origResolution {:04}x{:04} effectiveResolution {:04}x{:04} fmt {:04x} mipIndex {}", srcTexture->width, srcTexture->height, effectiveWidth_src, effectiveHeight_src, (uint32)srcTexture->format, 0);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
catchOpenGLError();
|
|
||||||
|
|
||||||
for (sint32 mipIndex = 0; mipIndex < mipCount; mipIndex++)
|
for (sint32 mipIndex = 0; mipIndex < mipCount; mipIndex++)
|
||||||
{
|
{
|
||||||
sint32 sliceCopyWidth = std::max(effectiveCopyWidth >> mipIndex, 1);
|
sint32 sliceCopyWidth = std::max(effectiveCopyWidth >> mipIndex, 1);
|
||||||
@ -323,9 +321,7 @@ void LatteTexture_copyData(LatteTexture* srcTexture, LatteTexture* dstTexture, s
|
|||||||
LatteTextureSliceMipInfo* dstTexSliceInfo = dstTexture->sliceMipInfo + dstTexture->GetSliceMipArrayIndex(sliceIndex, mipIndex);
|
LatteTextureSliceMipInfo* dstTexSliceInfo = dstTexture->sliceMipInfo + dstTexture->GetSliceMipArrayIndex(sliceIndex, mipIndex);
|
||||||
dstTexSliceInfo->lastDynamicUpdate = srcTexSliceInfo->lastDynamicUpdate;
|
dstTexSliceInfo->lastDynamicUpdate = srcTexSliceInfo->lastDynamicUpdate;
|
||||||
}
|
}
|
||||||
catchOpenGLError();
|
|
||||||
}
|
}
|
||||||
catchOpenGLError();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
template<bool bothMustMatch>
|
template<bool bothMustMatch>
|
||||||
|
@ -55,6 +55,29 @@ public:
|
|||||||
|
|
||||||
bool Is3DTexture() const { return dim == Latte::E_DIM::DIM_3D; };
|
bool Is3DTexture() const { return dim == Latte::E_DIM::DIM_3D; };
|
||||||
|
|
||||||
|
void GetSize(sint32& width, sint32& height, sint32 mipLevel) const
|
||||||
|
{
|
||||||
|
width = std::max(1, this->width >> mipLevel);
|
||||||
|
height = std::max(1, this->height >> mipLevel);
|
||||||
|
}
|
||||||
|
|
||||||
|
// similar to GetSize, but returns the real size of the texture taking into account any resolution overwrite by gfx pack rules
|
||||||
|
void GetEffectiveSize(sint32& effectiveWidth, sint32& effectiveHeight, sint32 mipLevel) const
|
||||||
|
{
|
||||||
|
if( overwriteInfo.hasResolutionOverwrite )
|
||||||
|
{
|
||||||
|
effectiveWidth = overwriteInfo.width;
|
||||||
|
effectiveHeight = overwriteInfo.height;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
effectiveWidth = this->width;
|
||||||
|
effectiveHeight = this->height;
|
||||||
|
}
|
||||||
|
effectiveWidth = std::max(1, effectiveWidth >> mipLevel);
|
||||||
|
effectiveHeight = std::max(1, effectiveHeight >> mipLevel);
|
||||||
|
}
|
||||||
|
|
||||||
sint32 GetMipDepth(sint32 mipIndex)
|
sint32 GetMipDepth(sint32 mipIndex)
|
||||||
{
|
{
|
||||||
cemu_assert_debug(mipIndex >= 0 && mipIndex < this->mipLevels);
|
cemu_assert_debug(mipIndex >= 0 && mipIndex < this->mipLevels);
|
||||||
@ -310,8 +333,6 @@ void LatteTexture_Delete(LatteTexture* texture);
|
|||||||
|
|
||||||
void LatteTextureLoader_writeReadbackTextureToMemory(LatteTextureDefinition* textureData, uint32 sliceIndex, uint32 mipIndex, uint8* linearPixelData);
|
void LatteTextureLoader_writeReadbackTextureToMemory(LatteTextureDefinition* textureData, uint32 sliceIndex, uint32 mipIndex, uint8* linearPixelData);
|
||||||
|
|
||||||
void LatteTexture_getSize(LatteTexture* texture, sint32* width, sint32* height, sint32* depth, sint32 mipLevel);
|
|
||||||
void LatteTexture_getEffectiveSize(LatteTexture* texture, sint32* effectiveWidth, sint32* effectiveHeight, sint32* effectiveDepth, sint32 mipLevel = 0);
|
|
||||||
sint32 LatteTexture_getEffectiveWidth(LatteTexture* texture);
|
sint32 LatteTexture_getEffectiveWidth(LatteTexture* texture);
|
||||||
bool LatteTexture_doesEffectiveRescaleRatioMatch(LatteTexture* texture1, sint32 mipLevel1, LatteTexture* texture2, sint32 mipLevel2);
|
bool LatteTexture_doesEffectiveRescaleRatioMatch(LatteTexture* texture1, sint32 mipLevel1, LatteTexture* texture2, sint32 mipLevel2);
|
||||||
void LatteTexture_scaleToEffectiveSize(LatteTexture* texture, sint32* x, sint32* y, sint32 mipLevel);
|
void LatteTexture_scaleToEffectiveSize(LatteTexture* texture, sint32* x, sint32* y, sint32 mipLevel);
|
||||||
|
@ -206,14 +206,10 @@ void LatteTexture_updateTexturesForStage(LatteDecompilerShader* shaderContext, u
|
|||||||
|
|
||||||
bool isDepthSampler = shaderContext->textureUsesDepthCompare[textureIndex];
|
bool isDepthSampler = shaderContext->textureUsesDepthCompare[textureIndex];
|
||||||
// look for already existing texture
|
// look for already existing texture
|
||||||
LatteTextureView* textureView;
|
LatteTextureView* textureView = LatteTextureViewLookupCache::lookup(physAddr, width, height, depth, pitch, viewFirstMip, viewNumMips, viewFirstSlice, viewNumSlices, format, dim, isDepthSampler);
|
||||||
if (isDepthSampler == false)
|
if (!textureView)
|
||||||
textureView = LatteTextureViewLookupCache::lookup(physAddr, width, height, depth, pitch, viewFirstMip, viewNumMips, viewFirstSlice, viewNumSlices, format, dim);
|
|
||||||
else
|
|
||||||
textureView = LatteTextureViewLookupCache::lookup(physAddr, width, height, depth, pitch, viewFirstMip, viewNumMips, viewFirstSlice, viewNumSlices, format, dim, true);
|
|
||||||
if (textureView == nullptr)
|
|
||||||
{
|
{
|
||||||
// create new mapping
|
// view not found, create a new mapping which will also create a new texture if necessary
|
||||||
textureView = LatteTexture_CreateMapping(physAddr, physMipAddr, width, height, depth, pitch, tileMode, swizzle, viewFirstMip, viewNumMips, viewFirstSlice, viewNumSlices, format, dim, dim, isDepthSampler);
|
textureView = LatteTexture_CreateMapping(physAddr, physMipAddr, width, height, depth, pitch, tileMode, swizzle, viewFirstMip, viewNumMips, viewFirstSlice, viewNumSlices, format, dim, dim, isDepthSampler);
|
||||||
if (textureView == nullptr)
|
if (textureView == nullptr)
|
||||||
continue;
|
continue;
|
||||||
@ -273,9 +269,7 @@ void LatteTexture_updateTexturesForStage(LatteDecompilerShader* shaderContext, u
|
|||||||
// check for changes
|
// check for changes
|
||||||
if (LatteTC_HasTextureChanged(textureView->baseTexture) || swizzleChanged)
|
if (LatteTC_HasTextureChanged(textureView->baseTexture) || swizzleChanged)
|
||||||
{
|
{
|
||||||
#ifdef CEMU_DEBUG_ASSERT
|
|
||||||
debug_printf("Reload texture 0x%08x res %dx%d memRange %08x-%08x SwizzleChange: %s\n", textureView->baseTexture->physAddress, textureView->baseTexture->width, textureView->baseTexture->height, textureView->baseTexture->texDataPtrLow, textureView->baseTexture->texDataPtrHigh, swizzleChanged ? "yes" : "no");
|
debug_printf("Reload texture 0x%08x res %dx%d memRange %08x-%08x SwizzleChange: %s\n", textureView->baseTexture->physAddress, textureView->baseTexture->width, textureView->baseTexture->height, textureView->baseTexture->texDataPtrLow, textureView->baseTexture->texDataPtrHigh, swizzleChanged ? "yes" : "no");
|
||||||
#endif
|
|
||||||
// update swizzle / changed mip address
|
// update swizzle / changed mip address
|
||||||
if (swizzleChanged)
|
if (swizzleChanged)
|
||||||
{
|
{
|
||||||
@ -338,44 +332,6 @@ void LatteTexture_updateTextures()
|
|||||||
LatteTexture_updateTexturesForStage(geometryShader, LATTE_CEMU_GS_TEX_UNIT_BASE, LatteGPUState.contextNew.SQ_TEX_START_GS);
|
LatteTexture_updateTexturesForStage(geometryShader, LATTE_CEMU_GS_TEX_UNIT_BASE, LatteGPUState.contextNew.SQ_TEX_START_GS);
|
||||||
}
|
}
|
||||||
|
|
||||||
// returns the width, height, depth of the texture
|
|
||||||
void LatteTexture_getSize(LatteTexture* texture, sint32* width, sint32* height, sint32* depth, sint32 mipLevel)
|
|
||||||
{
|
|
||||||
*width = texture->width;
|
|
||||||
*height = texture->height;
|
|
||||||
if (depth != NULL)
|
|
||||||
*depth = texture->depth;
|
|
||||||
// handle mip level
|
|
||||||
*width = std::max(1, *width >> mipLevel);
|
|
||||||
*height = std::max(1, *height >> mipLevel);
|
|
||||||
if(texture->Is3DTexture() && depth)
|
|
||||||
*depth = std::max(1, *depth >> mipLevel);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Returns the internally used width/height/depth of the texture
|
|
||||||
* Usually this is the width/height/depth specified by the game,
|
|
||||||
* unless the texture resolution was redefined via graphic pack texture rules
|
|
||||||
*/
|
|
||||||
void LatteTexture_getEffectiveSize(LatteTexture* texture, sint32* effectiveWidth, sint32* effectiveHeight, sint32* effectiveDepth, sint32 mipLevel)
|
|
||||||
{
|
|
||||||
*effectiveWidth = texture->width;
|
|
||||||
*effectiveHeight = texture->height;
|
|
||||||
if( effectiveDepth != NULL )
|
|
||||||
*effectiveDepth = texture->depth;
|
|
||||||
if( texture->overwriteInfo.hasResolutionOverwrite )
|
|
||||||
{
|
|
||||||
*effectiveWidth = texture->overwriteInfo.width;
|
|
||||||
*effectiveHeight = texture->overwriteInfo.height;
|
|
||||||
if( effectiveDepth != NULL )
|
|
||||||
*effectiveDepth = texture->overwriteInfo.depth;
|
|
||||||
}
|
|
||||||
// handle mipLevel
|
|
||||||
// todo: Mip-mapped 3D textures decrease in depth also?
|
|
||||||
*effectiveWidth = std::max(1, *effectiveWidth >> mipLevel);
|
|
||||||
*effectiveHeight = std::max(1, *effectiveHeight >> mipLevel);
|
|
||||||
}
|
|
||||||
|
|
||||||
sint32 LatteTexture_getEffectiveWidth(LatteTexture* texture)
|
sint32 LatteTexture_getEffectiveWidth(LatteTexture* texture)
|
||||||
{
|
{
|
||||||
if (texture->overwriteInfo.hasResolutionOverwrite)
|
if (texture->overwriteInfo.hasResolutionOverwrite)
|
||||||
|
@ -569,10 +569,8 @@ void OpenGLRenderer::DrawBackbufferQuad(LatteTextureView* texView, RendererOutpu
|
|||||||
g_renderer->ClearColorbuffer(padView);
|
g_renderer->ClearColorbuffer(padView);
|
||||||
}
|
}
|
||||||
|
|
||||||
// calculate effective size
|
sint32 effectiveWidth, effectiveHeight;
|
||||||
sint32 effectiveWidth;
|
texView->baseTexture->GetEffectiveSize(effectiveWidth, effectiveHeight, 0);
|
||||||
sint32 effectiveHeight;
|
|
||||||
LatteTexture_getEffectiveSize(texView->baseTexture, &effectiveWidth, &effectiveHeight, nullptr, 0);
|
|
||||||
|
|
||||||
shader_unbind(RendererShader::ShaderType::kGeometry);
|
shader_unbind(RendererShader::ShaderType::kGeometry);
|
||||||
shader_bind(shader->GetVertexShader());
|
shader_bind(shader->GetVertexShader());
|
||||||
@ -1127,8 +1125,8 @@ void OpenGLRenderer::texture_clearColorSlice(LatteTexture* hostTexture, sint32 s
|
|||||||
LatteTextureGL* texGL = (LatteTextureGL*)hostTexture;
|
LatteTextureGL* texGL = (LatteTextureGL*)hostTexture;
|
||||||
cemu_assert_debug(!texGL->isDepth);
|
cemu_assert_debug(!texGL->isDepth);
|
||||||
|
|
||||||
sint32 eWidth, eHeight, eDepth;
|
sint32 eWidth, eHeight;
|
||||||
LatteTexture_getEffectiveSize(hostTexture, &eWidth, &eHeight, &eDepth, mipIndex);
|
hostTexture->GetEffectiveSize(eWidth, eHeight, mipIndex);
|
||||||
renderstate_resetColorControl();
|
renderstate_resetColorControl();
|
||||||
renderTarget_setViewport(0, 0, eWidth, eHeight, 0.0f, 1.0f);
|
renderTarget_setViewport(0, 0, eWidth, eHeight, 0.0f, 1.0f);
|
||||||
LatteMRT::BindColorBufferOnly(hostTexture->GetOrCreateView(mipIndex, 1, sliceIndex, 1));
|
LatteMRT::BindColorBufferOnly(hostTexture->GetOrCreateView(mipIndex, 1, sliceIndex, 1));
|
||||||
@ -1141,8 +1139,8 @@ void OpenGLRenderer::texture_clearDepthSlice(LatteTexture* hostTexture, uint32 s
|
|||||||
LatteTextureGL* texGL = (LatteTextureGL*)hostTexture;
|
LatteTextureGL* texGL = (LatteTextureGL*)hostTexture;
|
||||||
cemu_assert_debug(texGL->isDepth);
|
cemu_assert_debug(texGL->isDepth);
|
||||||
|
|
||||||
sint32 eWidth, eHeight, eDepth;
|
sint32 eWidth, eHeight;
|
||||||
LatteTexture_getEffectiveSize(hostTexture, &eWidth, &eHeight, &eDepth, mipIndex);
|
hostTexture->GetEffectiveSize(eWidth, eHeight, mipIndex);
|
||||||
renderstate_resetColorControl();
|
renderstate_resetColorControl();
|
||||||
renderstate_resetDepthControl();
|
renderstate_resetDepthControl();
|
||||||
renderTarget_setViewport(0, 0, eWidth, eHeight, 0.0f, 1.0f);
|
renderTarget_setViewport(0, 0, eWidth, eHeight, 0.0f, 1.0f);
|
||||||
@ -1170,13 +1168,12 @@ void OpenGLRenderer::texture_clearSlice(LatteTexture* hostTextureGeneric, sint32
|
|||||||
LatteTextureGL::FormatInfoGL formatInfoGL;
|
LatteTextureGL::FormatInfoGL formatInfoGL;
|
||||||
LatteTextureGL::GetOpenGLFormatInfo(hostTexture->isDepth, hostTexture->format, hostTexture->dim, &formatInfoGL);
|
LatteTextureGL::GetOpenGLFormatInfo(hostTexture->isDepth, hostTexture->format, hostTexture->dim, &formatInfoGL);
|
||||||
// get effective size of mip
|
// get effective size of mip
|
||||||
sint32 effectiveWidth;
|
sint32 effectiveWidth, effectiveHeight;
|
||||||
sint32 effectiveHeight;
|
hostTexture->GetEffectiveSize(effectiveWidth, effectiveHeight, mipIndex);
|
||||||
LatteTexture_getEffectiveSize(hostTexture, &effectiveWidth, &effectiveHeight, nullptr, mipIndex);
|
|
||||||
|
|
||||||
// on Nvidia glClearTexImage and glClearTexSubImage has bad performance (clearing a 4K texture takes up to 50ms)
|
// on Nvidia glClearTexImage and glClearTexSubImage has bad performance (clearing a 4K texture takes up to 50ms)
|
||||||
// clearing with glTextureSubImage2D from a CPU RAM buffer is only slightly slower
|
// clearing with glTextureSubImage2D from a CPU RAM buffer is only slightly slower
|
||||||
// clearing with glTextureSubImage2D from a OpenGL buffer is 10-20% faster than glClearTexImage)
|
// clearing with glTextureSubImage2D from a OpenGL buffer is 10-20% faster than glClearTexImage
|
||||||
// clearing with FBO and glClear is orders of magnitude faster than the other methods
|
// clearing with FBO and glClear is orders of magnitude faster than the other methods
|
||||||
// (these are results from 2018, may be different now)
|
// (these are results from 2018, may be different now)
|
||||||
|
|
||||||
@ -1207,7 +1204,6 @@ void OpenGLRenderer::texture_clearSlice(LatteTexture* hostTextureGeneric, sint32
|
|||||||
}
|
}
|
||||||
if (glClearTexSubImage == nullptr)
|
if (glClearTexSubImage == nullptr)
|
||||||
return;
|
return;
|
||||||
// clear
|
|
||||||
glClearTexSubImage(hostTexture->glId_texture, mipIndex, 0, 0, sliceIndex, effectiveWidth, effectiveHeight, 1, formatInfoGL.glSuppliedFormat, formatInfoGL.glSuppliedFormatType, NULL);
|
glClearTexSubImage(hostTexture->glId_texture, mipIndex, 0, 0, sliceIndex, effectiveWidth, effectiveHeight, 1, formatInfoGL.glSuppliedFormat, formatInfoGL.glSuppliedFormatType, NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1215,7 +1211,6 @@ LatteTexture* OpenGLRenderer::texture_createTextureEx(Latte::E_DIM dim, MPTR phy
|
|||||||
uint32 swizzle, Latte::E_HWTILEMODE tileMode, bool isDepth)
|
uint32 swizzle, Latte::E_HWTILEMODE tileMode, bool isDepth)
|
||||||
{
|
{
|
||||||
return new LatteTextureGL(dim, physAddress, physMipAddress, format, width, height, depth, pitch, mipLevels, swizzle, tileMode, isDepth);
|
return new LatteTextureGL(dim, physAddress, physMipAddress, format, width, height, depth, pitch, mipLevels, swizzle, tileMode, isDepth);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void OpenGLRenderer::texture_setActiveTextureUnit(sint32 index)
|
void OpenGLRenderer::texture_setActiveTextureUnit(sint32 index)
|
||||||
|
@ -30,9 +30,8 @@ void OpenGLRenderer::surfaceCopy_copySurfaceWithFormatConversion(LatteTexture* s
|
|||||||
sint32 effectiveCopyWidth = width;
|
sint32 effectiveCopyWidth = width;
|
||||||
sint32 effectiveCopyHeight = height;
|
sint32 effectiveCopyHeight = height;
|
||||||
LatteTexture_scaleToEffectiveSize(sourceTexture, &effectiveCopyWidth, &effectiveCopyHeight, 0);
|
LatteTexture_scaleToEffectiveSize(sourceTexture, &effectiveCopyWidth, &effectiveCopyHeight, 0);
|
||||||
sint32 sourceEffectiveWidth;
|
sint32 sourceEffectiveWidth, sourceEffectiveHeight;
|
||||||
sint32 sourceEffectiveHeight;
|
sourceTexture->GetEffectiveSize(sourceEffectiveWidth, sourceEffectiveHeight, srcMip);
|
||||||
LatteTexture_getEffectiveSize(sourceTexture, &sourceEffectiveWidth, &sourceEffectiveHeight, nullptr, srcMip);
|
|
||||||
// reset everything
|
// reset everything
|
||||||
renderstate_resetColorControl();
|
renderstate_resetColorControl();
|
||||||
renderstate_resetDepthControl();
|
renderstate_resetDepthControl();
|
||||||
|
@ -764,7 +764,7 @@ void VulkanRenderer::HandleScreenshotRequest(LatteTextureView* texView, bool pad
|
|||||||
//dumpImage->flagForCurrentCommandBuffer();
|
//dumpImage->flagForCurrentCommandBuffer();
|
||||||
|
|
||||||
int width, height;
|
int width, height;
|
||||||
LatteTexture_getEffectiveSize(baseImageTex, &width, &height, nullptr, 0);
|
baseImageTex->GetEffectiveSize(width, height, 0);
|
||||||
|
|
||||||
VkImage image = nullptr;
|
VkImage image = nullptr;
|
||||||
VkDeviceMemory imageMemory = nullptr;;
|
VkDeviceMemory imageMemory = nullptr;;
|
||||||
|
@ -464,9 +464,8 @@ VKRObjectFramebuffer* VulkanRenderer::surfaceCopy_getOrCreateFramebuffer(VkCopyS
|
|||||||
VKRObjectTextureView* vkObjTextureView = surfaceCopy_createImageView(state.destinationTexture, state.dstSlice, state.dstMip);
|
VKRObjectTextureView* vkObjTextureView = surfaceCopy_createImageView(state.destinationTexture, state.dstSlice, state.dstMip);
|
||||||
|
|
||||||
// create new framebuffer
|
// create new framebuffer
|
||||||
sint32 effectiveWidth = 0;
|
sint32 effectiveWidth, effectiveHeight;
|
||||||
sint32 effectiveHeight = 0;
|
state.destinationTexture->GetEffectiveSize(effectiveWidth, effectiveHeight, state.dstMip);
|
||||||
LatteTexture_getEffectiveSize(state.destinationTexture, &effectiveWidth, &effectiveHeight, nullptr, state.dstMip);
|
|
||||||
|
|
||||||
std::array<VKRObjectTextureView*, 1> fbAttachments;
|
std::array<VKRObjectTextureView*, 1> fbAttachments;
|
||||||
fbAttachments[0] = vkObjTextureView;
|
fbAttachments[0] = vkObjTextureView;
|
||||||
@ -595,15 +594,11 @@ void VulkanRenderer::surfaceCopy_viaDrawcall(LatteTextureVk* srcTextureVk, sint3
|
|||||||
// get descriptor set
|
// get descriptor set
|
||||||
VKRObjectDescriptorSet* vkObjDescriptorSet = surfaceCopy_getOrCreateDescriptorSet(copySurfaceState, copySurfacePipelineInfo);
|
VKRObjectDescriptorSet* vkObjDescriptorSet = surfaceCopy_getOrCreateDescriptorSet(copySurfaceState, copySurfacePipelineInfo);
|
||||||
|
|
||||||
// get extend
|
sint32 dstEffectiveWidth, dstEffectiveHeight;
|
||||||
sint32 effectiveWidth = 0;
|
dstTextureVk->GetEffectiveSize(dstEffectiveWidth, dstEffectiveHeight, texDstMip);
|
||||||
sint32 effectiveHeight = 0;
|
|
||||||
LatteTexture_getEffectiveSize(dstTextureVk, &effectiveWidth, &effectiveHeight, nullptr, texDstMip);
|
|
||||||
|
|
||||||
// get extend
|
sint32 srcEffectiveWidth, srcEffectiveHeight;
|
||||||
sint32 srcEffectiveWidth = 0;
|
srcTextureVk->GetEffectiveSize(srcEffectiveWidth, srcEffectiveHeight, texSrcMip);
|
||||||
sint32 srcEffectiveHeight = 0;
|
|
||||||
LatteTexture_getEffectiveSize(srcTextureVk, &srcEffectiveWidth, &srcEffectiveHeight, nullptr, texSrcMip);
|
|
||||||
|
|
||||||
CopyShaderPushConstantData_t pushConstantData;
|
CopyShaderPushConstantData_t pushConstantData;
|
||||||
|
|
||||||
@ -878,9 +873,8 @@ void VulkanRenderer::surfaceCopy_copySurfaceWithFormatConversion(LatteTexture* s
|
|||||||
sint32 effectiveCopyWidth = width;
|
sint32 effectiveCopyWidth = width;
|
||||||
sint32 effectiveCopyHeight = height;
|
sint32 effectiveCopyHeight = height;
|
||||||
LatteTexture_scaleToEffectiveSize(sourceTexture, &effectiveCopyWidth, &effectiveCopyHeight, 0);
|
LatteTexture_scaleToEffectiveSize(sourceTexture, &effectiveCopyWidth, &effectiveCopyHeight, 0);
|
||||||
sint32 sourceEffectiveWidth;
|
sint32 sourceEffectiveWidth, sourceEffectiveHeight;
|
||||||
sint32 sourceEffectiveHeight;
|
sourceTexture->GetEffectiveSize(sourceEffectiveWidth, sourceEffectiveHeight, srcMip);
|
||||||
LatteTexture_getEffectiveSize(sourceTexture, &sourceEffectiveWidth, &sourceEffectiveHeight, nullptr, srcMip);
|
|
||||||
|
|
||||||
sint32 texSrcMip = srcMip;
|
sint32 texSrcMip = srcMip;
|
||||||
sint32 texSrcSlice = srcSlice;
|
sint32 texSrcSlice = srcSlice;
|
||||||
|
@ -114,7 +114,7 @@ namespace GX2
|
|||||||
|
|
||||||
void GX2RSetStreamOutBuffer(uint32 bufferIndex, GX2StreamOutBuffer* soBuffer)
|
void GX2RSetStreamOutBuffer(uint32 bufferIndex, GX2StreamOutBuffer* soBuffer)
|
||||||
{
|
{
|
||||||
// seen in CoD: Ghosts
|
// seen in CoD: Ghosts and CoD: Black Ops 2
|
||||||
GX2SetStreamOutBuffer(bufferIndex, soBuffer);
|
GX2SetStreamOutBuffer(bufferIndex, soBuffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -112,6 +112,8 @@ bool cemuLog_logDebug(LogType type, TFmt format, TArgs&&... args)
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#define cemuLog_logDebugOnce(...) { static bool _not_first_call = false; if (!_not_first_call) { _not_first_call = true; cemuLog_logDebug(__VA_ARGS__); } }
|
||||||
|
|
||||||
// cafe lib calls
|
// cafe lib calls
|
||||||
bool cemuLog_advancedPPCLoggingEnabled();
|
bool cemuLog_advancedPPCLoggingEnabled();
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user