Dynamic Probe Allocation (#3787)
* #3788 Support dynamic probe allocation. * #3738 Mitigate probe flashing * #3735 Mitigate realtime probes flashingmaster
parent
3c96bd2c69
commit
32c7d3064f
|
|
@ -154,6 +154,7 @@ void calcAtmosphericVarsLinear(vec3 inPositionEye, vec3 norm, vec3 light_dir, ou
|
|||
if (classic_mode < 1)
|
||||
{
|
||||
amblit = srgb_to_linear(amblit);
|
||||
amblit = vec3(dot(amblit, vec3(0.2126, 0.7152, 0.0722)));
|
||||
sunlit = srgb_to_linear(sunlit);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -86,7 +86,6 @@ RenderTonemapType 1 1
|
|||
RenderTonemapMix 1 1
|
||||
RenderDisableVintageMode 1 1
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 1 256
|
||||
|
||||
//
|
||||
// Low Graphics Settings
|
||||
|
|
@ -129,7 +128,6 @@ RenderTonemapType 1 1
|
|||
RenderTonemapMix 1 0.7
|
||||
RenderDisableVintageMode 1 0
|
||||
RenderMaxTextureResolution 1 512
|
||||
RenderReflectionProbeCount 1 1
|
||||
|
||||
//
|
||||
// Medium Low Graphics Settings
|
||||
|
|
@ -172,7 +170,6 @@ RenderTonemapType 1 1
|
|||
RenderTonemapMix 1 0.7
|
||||
RenderDisableVintageMode 1 0
|
||||
RenderMaxTextureResolution 1 1024
|
||||
RenderReflectionProbeCount 1 16
|
||||
|
||||
//
|
||||
// Medium Graphics Settings (standard)
|
||||
|
|
@ -214,7 +211,6 @@ RenderExposure 1 1
|
|||
RenderTonemapType 1 1
|
||||
RenderTonemapMix 1 0.7
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 1 32
|
||||
|
||||
//
|
||||
// Medium High Graphics Settings
|
||||
|
|
@ -245,7 +241,7 @@ RenderFSAASamples 1 1
|
|||
RenderReflectionsEnabled 1 1
|
||||
RenderReflectionProbeDetail 1 1
|
||||
RenderScreenSpaceReflections 1 0
|
||||
RenderReflectionProbeLevel 1 2
|
||||
RenderReflectionProbeLevel 1 1
|
||||
RenderMirrors 1 0
|
||||
RenderHeroProbeResolution 1 512
|
||||
RenderHeroProbeDistance 1 6
|
||||
|
|
@ -256,7 +252,6 @@ RenderExposure 1 1
|
|||
RenderTonemapType 1 1
|
||||
RenderTonemapMix 1 0.7
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 1 64
|
||||
|
||||
//
|
||||
// High Graphics Settings (SSAO + sun shadows)
|
||||
|
|
@ -287,7 +282,7 @@ RenderFSAASamples 1 2
|
|||
RenderReflectionsEnabled 1 1
|
||||
RenderReflectionProbeDetail 1 1
|
||||
RenderScreenSpaceReflections 1 0
|
||||
RenderReflectionProbeLevel 1 3
|
||||
RenderReflectionProbeLevel 1 2
|
||||
RenderMirrors 1 0
|
||||
RenderHeroProbeResolution 1 512
|
||||
RenderHeroProbeDistance 1 8
|
||||
|
|
@ -298,7 +293,6 @@ RenderExposure 1 1
|
|||
RenderTonemapType 1 1
|
||||
RenderTonemapMix 1 0.7
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 1 128
|
||||
|
||||
//
|
||||
// High Ultra Graphics Settings (deferred + SSAO + all shadows)
|
||||
|
|
@ -340,7 +334,6 @@ RenderExposure 1 1
|
|||
RenderTonemapType 1 1
|
||||
RenderTonemapMix 1 0.7
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 1 256
|
||||
|
||||
//
|
||||
// Ultra graphics (REALLY PURTY!)
|
||||
|
|
@ -382,7 +375,6 @@ RenderExposure 1 1
|
|||
RenderTonemapType 1 1
|
||||
RenderTonemapMix 1 0.7
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 1 256
|
||||
|
||||
//
|
||||
// Class Unknown Hardware (unknown)
|
||||
|
|
@ -416,7 +408,6 @@ RenderReflectionProbeDetail 0 -1
|
|||
RenderMirrors 0 0
|
||||
RenderDisableVintageMode 1 0
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 0 0
|
||||
|
||||
list Intel
|
||||
RenderAnisotropic 1 0
|
||||
|
|
@ -438,7 +429,6 @@ RenderMirrors 0 0
|
|||
RenderGLMultiThreadedTextures 0 0
|
||||
RenderGLMultiThreadedMedia 0 0
|
||||
RenderDisableVintageMode 1 0
|
||||
RenderReflectionProbeCount 0 0
|
||||
|
||||
list TexUnit16orLess
|
||||
RenderTerrainPBRDetail 1 -1
|
||||
|
|
|
|||
|
|
@ -86,7 +86,6 @@ RenderTonemapMix 1 1
|
|||
RenderDisableVintageMode 1 1
|
||||
RenderDownScaleMethod 1 0
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 1 256
|
||||
|
||||
//
|
||||
// Low Graphics Settings
|
||||
|
|
@ -129,7 +128,6 @@ RenderTonemapType 1 1
|
|||
RenderTonemapMix 1 0.7
|
||||
RenderDisableVintageMode 1 0
|
||||
RenderMaxTextureResolution 1 512
|
||||
RenderReflectionProbeCount 1 1
|
||||
|
||||
//
|
||||
// Medium Low Graphics Settings
|
||||
|
|
@ -172,7 +170,6 @@ RenderTonemapType 1 1
|
|||
RenderTonemapMix 1 0.7
|
||||
RenderDisableVintageMode 1 0
|
||||
RenderMaxTextureResolution 1 1024
|
||||
RenderReflectionProbeCount 1 16
|
||||
|
||||
//
|
||||
// Medium Graphics Settings (standard)
|
||||
|
|
@ -214,7 +211,6 @@ RenderExposure 1 1
|
|||
RenderTonemapType 1 1
|
||||
RenderTonemapMix 1 0.7
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 1 32
|
||||
|
||||
//
|
||||
// Medium High Graphics Settings
|
||||
|
|
@ -256,7 +252,6 @@ RenderExposure 1 1
|
|||
RenderTonemapType 1 1
|
||||
RenderTonemapMix 1 0.7
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 1 64
|
||||
|
||||
//
|
||||
// High Graphics Settings (SSAO + sun shadows)
|
||||
|
|
@ -298,7 +293,6 @@ RenderExposure 1 1
|
|||
RenderTonemapType 1 1
|
||||
RenderTonemapMix 1 0.7
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 1 128
|
||||
|
||||
//
|
||||
// High Ultra Graphics Settings (SSAO + all shadows)
|
||||
|
|
@ -340,7 +334,6 @@ RenderExposure 1 1
|
|||
RenderTonemapType 1 1
|
||||
RenderTonemapMix 1 0.7
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 1 256
|
||||
|
||||
//
|
||||
// Ultra graphics (REALLY PURTY!)
|
||||
|
|
@ -382,7 +375,6 @@ RenderExposure 1 1
|
|||
RenderTonemapType 1 1
|
||||
RenderTonemapMix 1 0.7
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 1 256
|
||||
|
||||
//
|
||||
// Class Unknown Hardware (unknown)
|
||||
|
|
@ -415,7 +407,6 @@ RenderShadowDetail 0 0
|
|||
RenderMirrors 0 0
|
||||
RenderDisableVintageMode 1 0
|
||||
RenderMaxTextureResolution 1 2048
|
||||
RenderReflectionProbeCount 0 0
|
||||
|
||||
list TexUnit8orLess
|
||||
RenderDeferredSSAO 0 0
|
||||
|
|
@ -456,7 +447,6 @@ RenderReflectionProbeDetail 0 0
|
|||
RenderReflectionsEnabled 0 0
|
||||
RenderMirrors 0 0
|
||||
RenderDisableVintageMode 1 0
|
||||
RenderReflectionProbeCount 0 0
|
||||
|
||||
list VaryingVectors16orLess
|
||||
RenderTerrainPBRPlanarSampleCount 1 1
|
||||
|
|
|
|||
|
|
@ -52,6 +52,9 @@ LLReflectionMap::~LLReflectionMap()
|
|||
void LLReflectionMap::update(U32 resolution, U32 face, bool force_dynamic, F32 near_clip, bool useClipPlane, LLPlane clipPlane)
|
||||
{
|
||||
LL_PROFILE_ZONE_SCOPED_CATEGORY_DISPLAY;
|
||||
if (!mCubeArray.notNull())
|
||||
return;
|
||||
|
||||
mLastUpdateTime = gFrameTimeSeconds;
|
||||
llassert(mCubeArray.notNull());
|
||||
llassert(mCubeIndex != -1);
|
||||
|
|
|
|||
|
|
@ -144,13 +144,14 @@ static void touch_default_probe(LLReflectionMap* probe)
|
|||
|
||||
LLReflectionMapManager::LLReflectionMapManager()
|
||||
{
|
||||
mDynamicProbeCount = LL_MAX_REFLECTION_PROBE_COUNT;
|
||||
initCubeFree();
|
||||
}
|
||||
|
||||
void LLReflectionMapManager::initCubeFree()
|
||||
{
|
||||
// start at 1 because index 0 is reserved for mDefaultProbe
|
||||
for (int i = 1; i < LL_MAX_REFLECTION_PROBE_COUNT; ++i)
|
||||
for (U32 i = 1; i < mDynamicProbeCount; ++i)
|
||||
{
|
||||
mCubeFree.push_back(i);
|
||||
}
|
||||
|
|
@ -221,15 +222,50 @@ void LLReflectionMapManager::update()
|
|||
resume();
|
||||
}
|
||||
|
||||
static LLCachedControl<U32> probe_count(gSavedSettings, "RenderReflectionProbeCount", 256U);
|
||||
bool countReset = mReflectionProbeCount != probe_count;
|
||||
static LLCachedControl<S32> sDetail(gSavedSettings, "RenderReflectionProbeDetail", -1);
|
||||
static LLCachedControl<S32> sLevel(gSavedSettings, "RenderReflectionProbeLevel", 3);
|
||||
|
||||
if (countReset)
|
||||
// Once every 20 frames, update the dynamic probe count.
|
||||
if (gFrameCount % 20)
|
||||
{
|
||||
mResetFade = -0.5f;
|
||||
U32 probe_count_temp = mDynamicProbeCount;
|
||||
if (sLevel == 0)
|
||||
{
|
||||
mDynamicProbeCount = 1;
|
||||
}
|
||||
else if (sLevel == 1)
|
||||
{
|
||||
mDynamicProbeCount = (U32)mProbes.size();
|
||||
|
||||
}
|
||||
else if (sLevel == 2)
|
||||
{
|
||||
mDynamicProbeCount = llmax((U32)mProbes.size(), 128);
|
||||
}
|
||||
else
|
||||
{
|
||||
mDynamicProbeCount = 256;
|
||||
}
|
||||
|
||||
// Round mDynamicProbeCount to the nearest increment of 32
|
||||
mDynamicProbeCount = ((mDynamicProbeCount + 16) / 32) * 32;
|
||||
mDynamicProbeCount = llclamp(mDynamicProbeCount, 1, LL_MAX_REFLECTION_PROBE_COUNT);
|
||||
|
||||
if (mDynamicProbeCount < probe_count_temp * 1.1 && mDynamicProbeCount > probe_count_temp * 0.9)
|
||||
mDynamicProbeCount = probe_count_temp;
|
||||
else
|
||||
mGlobalFadeTarget = 0.f;
|
||||
}
|
||||
|
||||
initReflectionMaps();
|
||||
if (mGlobalFadeTarget < mResetFade)
|
||||
mResetFade = llmax(mGlobalFadeTarget, mResetFade - (F32)gFrameIntervalSeconds * 2);
|
||||
else
|
||||
mResetFade = llmin(mGlobalFadeTarget, mResetFade + (F32)gFrameIntervalSeconds * 2);
|
||||
|
||||
if (mResetFade == mGlobalFadeTarget)
|
||||
{
|
||||
initReflectionMaps();
|
||||
}
|
||||
|
||||
static LLCachedControl<bool> render_hdr(gSavedSettings, "RenderHDREnabled", true);
|
||||
|
||||
|
|
@ -286,9 +322,6 @@ void LLReflectionMapManager::update()
|
|||
|
||||
bool did_update = false;
|
||||
|
||||
static LLCachedControl<S32> sDetail(gSavedSettings, "RenderReflectionProbeDetail", -1);
|
||||
static LLCachedControl<S32> sLevel(gSavedSettings, "RenderReflectionProbeLevel", 3);
|
||||
|
||||
bool realtime = sDetail >= (S32)LLReflectionMapManager::DetailLevel::REALTIME;
|
||||
|
||||
LLReflectionMap* closestDynamic = nullptr;
|
||||
|
|
@ -343,12 +376,7 @@ void LLReflectionMapManager::update()
|
|||
}
|
||||
}
|
||||
|
||||
if (countReset)
|
||||
{
|
||||
mResetFade = -0.5f;
|
||||
}
|
||||
|
||||
mResetFade = llmin((F32)(mResetFade + gFrameIntervalSeconds), 1.f);
|
||||
mResetFade = llmin((F32)(mResetFade + gFrameIntervalSeconds * 2.f), 1.f);
|
||||
|
||||
for (unsigned int i = 0; i < mProbes.size(); ++i)
|
||||
{
|
||||
|
|
@ -520,6 +548,16 @@ LLReflectionMap* LLReflectionMapManager::addProbe(LLSpatialGroup* group)
|
|||
return probe;
|
||||
}
|
||||
|
||||
U32 LLReflectionMapManager::probeCount()
|
||||
{
|
||||
return mDynamicProbeCount;
|
||||
}
|
||||
|
||||
U32 LLReflectionMapManager::probeMemory()
|
||||
{
|
||||
return (mDynamicProbeCount * 6 * (mProbeResolution * mProbeResolution) * 4) / 1024 / 1024 + (mDynamicProbeCount * 6 * (LL_IRRADIANCE_MAP_RESOLUTION * LL_IRRADIANCE_MAP_RESOLUTION) * 4) / 1024 / 1024;
|
||||
}
|
||||
|
||||
struct CompareProbeDepth
|
||||
{
|
||||
bool operator()(const LLReflectionMap* lhs, const LLReflectionMap* rhs)
|
||||
|
|
@ -1058,7 +1096,11 @@ void LLReflectionMapManager::updateUniforms()
|
|||
|
||||
bool is_ambiance_pass = gCubeSnapshot && !isRadiancePass();
|
||||
F32 ambscale = is_ambiance_pass ? 0.f : 1.f;
|
||||
ambscale *= mResetFade;
|
||||
ambscale = llmax(0, ambscale);
|
||||
F32 radscale = is_ambiance_pass ? 0.5f : 1.f;
|
||||
radscale *= mResetFade;
|
||||
radscale = llmax(0, radscale);
|
||||
|
||||
for (auto* refmap : mReflectionMaps)
|
||||
{
|
||||
|
|
@ -1129,8 +1171,8 @@ void LLReflectionMapManager::updateUniforms()
|
|||
}
|
||||
|
||||
mProbeData.refParams[count].set(
|
||||
llmax(minimum_ambiance, refmap->getAmbiance())*ambscale * llmax(mResetFade, 0.f), // ambiance scale
|
||||
radscale * llmax(mResetFade, 0.f), // radiance scale
|
||||
llmax(minimum_ambiance, refmap->getAmbiance())*ambscale, // ambiance scale
|
||||
radscale, // radiance scale
|
||||
refmap->mFadeIn, // fade in weight
|
||||
oa.getF32ptr()[2] - refmap->mRadius); // z near
|
||||
|
||||
|
|
@ -1365,12 +1407,9 @@ void LLReflectionMapManager::renderDebug()
|
|||
|
||||
void LLReflectionMapManager::initReflectionMaps()
|
||||
{
|
||||
static LLCachedControl<U32> probe_count(gSavedSettings, "RenderReflectionProbeCount", 256U);
|
||||
U32 count = probe_count();
|
||||
|
||||
static LLCachedControl<U32> ref_probe_res(gSavedSettings, "RenderReflectionProbeResolution", 128U);
|
||||
U32 probe_resolution = nhpo2(llclamp(ref_probe_res(), (U32)64, (U32)512));
|
||||
if (mTexture.isNull() || mReflectionProbeCount != count || mProbeResolution != probe_resolution || mReset)
|
||||
if (mTexture.isNull() || mReflectionProbeCount != mDynamicProbeCount || mProbeResolution != probe_resolution || mReset)
|
||||
{
|
||||
if(mProbeResolution != probe_resolution)
|
||||
{
|
||||
|
|
@ -1379,9 +1418,10 @@ void LLReflectionMapManager::initReflectionMaps()
|
|||
}
|
||||
|
||||
gEXRImage = nullptr;
|
||||
|
||||
mGlobalFadeTarget = 1.f;
|
||||
mResetFade = -0.125f;
|
||||
mReset = false;
|
||||
mReflectionProbeCount = count;
|
||||
mReflectionProbeCount = mDynamicProbeCount;
|
||||
mProbeResolution = probe_resolution;
|
||||
mMaxProbeLOD = log2f((F32)mProbeResolution) - 1.f; // number of mips - 1
|
||||
|
||||
|
|
|
|||
|
|
@ -38,7 +38,7 @@ class LLViewerObject;
|
|||
#define LL_MAX_REFLECTION_PROBE_COUNT 256
|
||||
|
||||
// reflection probe resolution
|
||||
#define LL_IRRADIANCE_MAP_RESOLUTION 64
|
||||
#define LL_IRRADIANCE_MAP_RESOLUTION 16
|
||||
|
||||
// reflection probe mininum scale
|
||||
#define LL_REFLECTION_PROBE_MINIMUM_SCALE 1.f;
|
||||
|
|
@ -159,6 +159,9 @@ public:
|
|||
// with false when done.
|
||||
void forceDefaultProbeAndUpdateUniforms(bool force = true);
|
||||
|
||||
U32 probeCount();
|
||||
U32 probeMemory();
|
||||
|
||||
private:
|
||||
friend class LLPipeline;
|
||||
friend class LLHeroProbeManager;
|
||||
|
|
@ -166,6 +169,9 @@ private:
|
|||
// initialize mCubeFree array to default values
|
||||
void initCubeFree();
|
||||
|
||||
// Just does a bulk clear of all of the cubemaps.
|
||||
void clearCubeMaps();
|
||||
|
||||
// delete the probe with the given index in mProbes
|
||||
void deleteProbe(U32 i);
|
||||
|
||||
|
|
@ -240,6 +246,8 @@ private:
|
|||
// number of reflection probes to use for rendering
|
||||
U32 mReflectionProbeCount;
|
||||
|
||||
U32 mDynamicProbeCount;
|
||||
|
||||
// resolution of reflection probes
|
||||
U32 mProbeResolution = 128;
|
||||
|
||||
|
|
@ -253,6 +261,7 @@ private:
|
|||
bool mReset = false;
|
||||
|
||||
float mResetFade = 1.f;
|
||||
float mGlobalFadeTarget = 1.f;
|
||||
|
||||
// if true, only update the default probe
|
||||
bool mPaused = false;
|
||||
|
|
|
|||
|
|
@ -559,10 +559,12 @@ void LLGLTexMemBar::draw()
|
|||
gGL.color4f(0.f, 0.f, 0.f, 0.25f);
|
||||
gl_rect_2d(-10, getRect().getHeight() + line_height*2 + 1, getRect().getWidth()+2, getRect().getHeight()+2);
|
||||
|
||||
text = llformat("Est. Free: %d MB Sys Free: %d MB FBO: %d MB Bias: %.2f Cache: %.1f/%.1f MB",
|
||||
text = llformat("Est. Free: %d MB Sys Free: %d MB FBO: %d MB Probe#: %d Probe Mem: %d MB Bias: %.2f Cache: %.1f/%.1f MB",
|
||||
(S32)LLViewerTexture::sFreeVRAMMegabytes,
|
||||
LLMemory::getAvailableMemKB()/1024,
|
||||
LLRenderTarget::sBytesAllocated/(1024*1024),
|
||||
gPipeline.mReflectionMapManager.probeCount(),
|
||||
gPipeline.mReflectionMapManager.probeMemory(),
|
||||
discard_bias,
|
||||
cache_usage,
|
||||
cache_max_usage);
|
||||
|
|
|
|||
|
|
@ -504,8 +504,11 @@ void LLViewerTexture::updateClass()
|
|||
// NOTE: our metrics miss about half the vram we use, so this biases high but turns out to typically be within 5% of the real number
|
||||
F32 used = (F32)ll_round(texture_bytes_alloc + vertex_bytes_alloc);
|
||||
|
||||
F32 budget = max_vram_budget == 0 ? (F32)gGLManager.mVRAM : (F32)max_vram_budget;
|
||||
budget /= tex_vram_divisor;
|
||||
// For debugging purposes, it's useful to be able to set the VRAM budget manually.
|
||||
// But when manual control is not enabled, use the VRAM divisor.
|
||||
// While we're at it, assume we have 1024 to play with at minimum when the divisor is in use. Works more elegantly with the logic below this.
|
||||
// -Geenz 2025-03-21
|
||||
F32 budget = max_vram_budget == 0 ? llmax(1024, (F32)gGLManager.mVRAM / tex_vram_divisor) : (F32)max_vram_budget;
|
||||
|
||||
// Try to leave at least half a GB for everyone else and for bias,
|
||||
// but keep at least 768MB for ourselves
|
||||
|
|
|
|||
|
|
@ -858,23 +858,6 @@
|
|||
value="3"/>
|
||||
</combo_box>
|
||||
|
||||
<slider
|
||||
control_name="RenderReflectionProbeCount"
|
||||
decimal_digits="0"
|
||||
follows="left|top"
|
||||
height="16"
|
||||
increment="1"
|
||||
initial_value="256"
|
||||
label="Max. Reflection Probes:"
|
||||
label_width="145"
|
||||
layout="topleft"
|
||||
left="420"
|
||||
min_val="1"
|
||||
max_val="256"
|
||||
name="MaxProbes"
|
||||
top_delta="24"
|
||||
width="260" />
|
||||
|
||||
<slider
|
||||
control_name="RenderExposure"
|
||||
decimal_digits="1"
|
||||
|
|
|
|||
Loading…
Reference in New Issue