From 76bf3390eb119a7dfd879bbbc31b4d5e687aac8f Mon Sep 17 00:00:00 2001 From: Cosmic Linden Date: Fri, 13 Oct 2023 09:56:55 -0700 Subject: DRTVWR-592: (WIP) Detect when terrain materials are loaded, use as fallback when terrain textures do not load --- indra/newview/lldrawpoolterrain.cpp | 32 +++++++- indra/newview/llfetchedgltfmaterial.h | 1 + indra/newview/llfloaterregioninfo.cpp | 6 +- indra/newview/llviewerregion.cpp | 16 ++-- indra/newview/llvlcomposition.cpp | 135 +++++++++++++++++++++++----------- indra/newview/llvlcomposition.h | 21 ++++-- 6 files changed, 150 insertions(+), 61 deletions(-) (limited to 'indra/newview') diff --git a/indra/newview/lldrawpoolterrain.cpp b/indra/newview/lldrawpoolterrain.cpp index 77189dceae..687ff5f462 100644 --- a/indra/newview/lldrawpoolterrain.cpp +++ b/indra/newview/lldrawpoolterrain.cpp @@ -121,8 +121,36 @@ void LLDrawPoolTerrain::boostTerrainDetailTextures() LLVLComposition *compp = regionp->getComposition(); for (S32 i = 0; i < 4; i++) { - compp->mDetailTextures[i]->setBoostLevel(LLGLTexture::BOOST_TERRAIN); - compp->mDetailTextures[i]->addTextureStats(1024.f * 1024.f); + constexpr LLGLTexture::EBoostLevel level = LLGLTexture::BOOST_TERRAIN; + constexpr float stats = 1024.f * 1024.f; + + LLPointer& tex = compp->mDetailTextures[i]; + llassert(tex.notNull()); + tex->setBoostLevel(level); + tex->addTextureStats(stats); + + LLPointer& mat = compp->mDetailMaterials[i]; + llassert(mat.notNull()); + if (mat->mBaseColorTexture) + { + mat->mBaseColorTexture->setBoostLevel(level); + mat->mBaseColorTexture->addTextureStats(stats); + } + if (mat->mNormalTexture) + { + mat->mNormalTexture->setBoostLevel(level); + mat->mNormalTexture->addTextureStats(stats); + } + if (mat->mMetallicRoughnessTexture) + { + mat->mMetallicRoughnessTexture->setBoostLevel(level); + mat->mMetallicRoughnessTexture->addTextureStats(stats); + } + if (mat->mEmissiveTexture) + { + mat->mEmissiveTexture->setBoostLevel(level); + mat->mEmissiveTexture->addTextureStats(stats); + } } } diff --git a/indra/newview/llfetchedgltfmaterial.h b/indra/newview/llfetchedgltfmaterial.h index 1668657281..ce4d33a213 100644 --- a/indra/newview/llfetchedgltfmaterial.h +++ b/indra/newview/llfetchedgltfmaterial.h @@ -49,6 +49,7 @@ public: void bind(LLViewerTexture* media_tex = nullptr); bool isFetching() const { return mFetching; } + bool isLoaded() const { return !mFetching; } // Textures used for fetching/rendering LLPointer mBaseColorTexture; diff --git a/indra/newview/llfloaterregioninfo.cpp b/indra/newview/llfloaterregioninfo.cpp index ff7012efb5..b5698c1d65 100644 --- a/indra/newview/llfloaterregioninfo.cpp +++ b/indra/newview/llfloaterregioninfo.cpp @@ -1541,8 +1541,8 @@ bool LLPanelRegionTerrainInfo::refreshFromRegion(LLViewerRegion* region) if(asset_ctrl) { LL_DEBUGS() << "Detail Texture " << i << ": " - << compp->getDetailTextureID(i) << LL_ENDL; - LLUUID tmp_id(compp->getDetailTextureID(i)); + << compp->getDetailAssetID(i) << LL_ENDL; + LLUUID tmp_id(compp->getDetailAssetID(i)); asset_ctrl->setImageAssetID(tmp_id); } } @@ -1552,7 +1552,7 @@ bool LLPanelRegionTerrainInfo::refreshFromRegion(LLViewerRegion* region) asset_ctrl = getChild(buffer); if(asset_ctrl) { - LLUUID tmp_id(compp->getDetailTextureID(i)); + LLUUID tmp_id(compp->getDetailAssetID(i)); asset_ctrl->setImageAssetID(tmp_id); } } diff --git a/indra/newview/llviewerregion.cpp b/indra/newview/llviewerregion.cpp index 6b92b16ef4..9d3e63333e 100755 --- a/indra/newview/llviewerregion.cpp +++ b/indra/newview/llviewerregion.cpp @@ -2962,20 +2962,20 @@ void LLViewerRegion::unpackRegionHandshake() // Get the 4 textures for land msg->getUUID("RegionInfo", "TerrainDetail0", tmp_id); - changed |= (tmp_id != compp->getDetailTextureID(0)); - compp->setDetailTextureID(0, tmp_id); + changed |= (tmp_id != compp->getDetailAssetID(0)); + compp->setDetailAssetID(0, tmp_id); msg->getUUID("RegionInfo", "TerrainDetail1", tmp_id); - changed |= (tmp_id != compp->getDetailTextureID(1)); - compp->setDetailTextureID(1, tmp_id); + changed |= (tmp_id != compp->getDetailAssetID(1)); + compp->setDetailAssetID(1, tmp_id); msg->getUUID("RegionInfo", "TerrainDetail2", tmp_id); - changed |= (tmp_id != compp->getDetailTextureID(2)); - compp->setDetailTextureID(2, tmp_id); + changed |= (tmp_id != compp->getDetailAssetID(2)); + compp->setDetailAssetID(2, tmp_id); msg->getUUID("RegionInfo", "TerrainDetail3", tmp_id); - changed |= (tmp_id != compp->getDetailTextureID(3)); - compp->setDetailTextureID(3, tmp_id); + changed |= (tmp_id != compp->getDetailAssetID(3)); + compp->setDetailAssetID(3, tmp_id); // Get the start altitude and range values for land textures F32 tmp_f32; diff --git a/indra/newview/llvlcomposition.cpp b/indra/newview/llvlcomposition.cpp index 001fab7755..8480c9ce3d 100644 --- a/indra/newview/llvlcomposition.cpp +++ b/indra/newview/llvlcomposition.cpp @@ -65,10 +65,10 @@ LLVLComposition::LLVLComposition(LLSurface *surfacep, const U32 width, const F32 mSurfacep = surfacep; // Load Terrain Textures - Original ones - setDetailTextureID(0, TERRAIN_DIRT_DETAIL); - setDetailTextureID(1, TERRAIN_GRASS_DETAIL); - setDetailTextureID(2, TERRAIN_MOUNTAIN_DETAIL); - setDetailTextureID(3, TERRAIN_ROCK_DETAIL); + setDetailAssetID(0, TERRAIN_DIRT_DETAIL); + setDetailAssetID(1, TERRAIN_GRASS_DETAIL); + setDetailAssetID(2, TERRAIN_MOUNTAIN_DETAIL); + setDetailAssetID(3, TERRAIN_ROCK_DETAIL); // Initialize the texture matrix to defaults. for (S32 i = 0; i < CORNER_COUNT; ++i) @@ -93,7 +93,7 @@ void LLVLComposition::setSurface(LLSurface *surfacep) } -void LLVLComposition::setDetailTextureID(S32 corner, const LLUUID& id) +void LLVLComposition::setDetailAssetID(S32 corner, const LLUUID& id) { if(id.isNull()) { @@ -104,6 +104,25 @@ void LLVLComposition::setDetailTextureID(S32 corner, const LLUUID& id) mDetailTextures[corner] = LLViewerTextureManager::getFetchedTexture(id); mDetailTextures[corner]->setNoDelete() ; mRawImages[corner] = NULL; + // *TODO: Decide if we have textures or materials. Whichever loads first determines the terrain type. + // *TODO: As the material textures are loaded, prevent deletion + mDetailMaterials[corner] = LLGLTFMaterialList::getMaterial(id); +} + +void LLVLComposition::setDetailMaterialID(S32 corner, const LLUUID& id) +{ + if(id.isNull()) + { + mDetailMaterials[corner] = nullptr; + } + else + { + // This is terrain material, but we are not setting it as BOOST_TERRAIN + // since we will be manipulating it later as needed. + mDetailTextures[corner] = LLViewerTextureManager::getFetchedTexture(id); + mDetailTextures[corner]->setNoDelete() ; + mRawImages[corner] = NULL; + } } BOOL LLVLComposition::generateHeights(const F32 x, const F32 y, @@ -149,10 +168,6 @@ BOOL LLVLComposition::generateHeights(const F32 x, const F32 y, const F32 noise_magnitude = 2.f; // Degree to which noise modulates composition layer (versus // simple height) - // Heights map into textures as 0-1 = first, 1-2 = second, etc. - // So we need to compress heights into this range. - const S32 NUM_TEXTURES = 4; - const F32 xyScaleInv = (1.f / xyScale); const F32 zScaleInv = (1.f / zScale); @@ -199,7 +214,7 @@ BOOL LLVLComposition::generateHeights(const F32 x, const F32 y, twiddle += turbulence2(vec, 2)*slope_squared; // High frequency component twiddle *= noise_magnitude; - F32 scaled_noisy_height = (height + twiddle - start_height) * F32(NUM_TEXTURES) / height_range; + F32 scaled_noisy_height = (height + twiddle - start_height) * F32(ASSET_COUNT) / height_range; scaled_noisy_height = llmax(0.f, scaled_noisy_height); scaled_noisy_height = llmin(3.f, scaled_noisy_height); @@ -211,6 +226,37 @@ BOOL LLVLComposition::generateHeights(const F32 x, const F32 y, static const U32 BASE_SIZE = 128; +// Boost the texture loading priority +// Return true when ready to use (i.e. texture is sufficiently loaded) +bool boost_texture_until_ready(LLPointer& tex) +{ + if (tex->getDiscardLevel() < 0) + { + tex->setBoostLevel(LLGLTexture::BOOST_TERRAIN); // in case we are at low detail + tex->addTextureStats(BASE_SIZE*BASE_SIZE); + return false; + } + if ((tex->getDiscardLevel() != 0 && + (tex->getWidth() < BASE_SIZE || + tex->getHeight() < BASE_SIZE))) + { + S32 width = tex->getFullWidth(); + S32 height = tex->getFullHeight(); + S32 min_dim = llmin(width, height); + S32 ddiscard = 0; + while (min_dim > BASE_SIZE && ddiscard < MAX_DISCARD_LEVEL) + { + ddiscard++; + min_dim /= 2; + } + tex->setBoostLevel(LLGLTexture::BOOST_TERRAIN); // in case we are at low detail + tex->setMinDiscardLevel(ddiscard); + tex->addTextureStats(BASE_SIZE*BASE_SIZE); // priority + return false; + } + return true; +} + BOOL LLVLComposition::generateComposition() { @@ -220,35 +266,44 @@ BOOL LLVLComposition::generateComposition() return FALSE; } - for (S32 i = 0; i < 4; i++) + bool textures_ready = true; + for (S32 i = 0; i < ASSET_COUNT; i++) { - if (mDetailTextures[i]->getDiscardLevel() < 0) - { - mDetailTextures[i]->setBoostLevel(LLGLTexture::BOOST_TERRAIN); // in case we are at low detail - mDetailTextures[i]->addTextureStats(BASE_SIZE*BASE_SIZE); - return FALSE; - } - if ((mDetailTextures[i]->getDiscardLevel() != 0 && - (mDetailTextures[i]->getWidth() < BASE_SIZE || - mDetailTextures[i]->getHeight() < BASE_SIZE))) - { - S32 width = mDetailTextures[i]->getFullWidth(); - S32 height = mDetailTextures[i]->getFullHeight(); - S32 min_dim = llmin(width, height); - S32 ddiscard = 0; - while (min_dim > BASE_SIZE && ddiscard < MAX_DISCARD_LEVEL) - { - ddiscard++; - min_dim /= 2; - } - mDetailTextures[i]->setBoostLevel(LLGLTexture::BOOST_TERRAIN); // in case we are at low detail - mDetailTextures[i]->setMinDiscardLevel(ddiscard); - mDetailTextures[i]->addTextureStats(BASE_SIZE*BASE_SIZE); // priority - return FALSE; - } + if (!boost_texture_until_ready(mDetailTextures[i])) + { + textures_ready = false; + break; + } } + + if (textures_ready) + { + return TRUE; + } - return TRUE; + bool materials_ready = true; + for (S32 i = 0; i < ASSET_COUNT; i++) + { + const LLPointer& mat = mDetailMaterials[i]; + if (!mat.isLoaded() || + (mat->mBaseColorTexture && !boost_texture_until_ready(mat->mBaseColorTexture)) || + (mat->mNormalTexture && !boost_texture_until_ready(mat->mNormalTexture)) || + (mat->mMetallicRoughnessTexture && !boost_texture_until_ready(mat->mMetallicRoughnessTexture)) || + (mat->mEmissiveTexture && !boost_texture_until_ready(mat->mEmissiveTexture))) + { + materials_ready = false; + break; + } + } + + if (materials_ready) + { + return TRUE; + } + else + { + return FALSE; + } } BOOL LLVLComposition::generateTexture(const F32 x, const F32 y, @@ -469,16 +524,12 @@ BOOL LLVLComposition::generateTexture(const F32 x, const F32 y, return TRUE; } -LLUUID LLVLComposition::getDetailTextureID(S32 corner) +LLUUID LLVLComposition::getDetailAssetID(S32 corner) { + llassert(mDetailTextures[corner] && mDetailMaterials[corner] && mDetailTextures[corner]->getID() == mDetailMaterials[corner].getID()); return mDetailTextures[corner]->getID(); } -LLViewerFetchedTexture* LLVLComposition::getDetailTexture(S32 corner) -{ - return mDetailTextures[corner]; -} - F32 LLVLComposition::getStartHeight(S32 corner) { return mStartHeight[corner]; diff --git a/indra/newview/llvlcomposition.h b/indra/newview/llvlcomposition.h index 2dd04ac5a5..3e465efc95 100644 --- a/indra/newview/llvlcomposition.h +++ b/indra/newview/llvlcomposition.h @@ -28,10 +28,13 @@ #define LL_LLVLCOMPOSITION_H #include "llviewerlayer.h" -#include "llviewertexture.h" +#include "llpointer.h" class LLSurface; +class LLViewerFetchedTexture; +class LLFetchedGLTFMaterial; + class LLVLComposition : public LLViewerLayer { public: @@ -46,6 +49,10 @@ public: // Generate texture from composition values. BOOL generateTexture(const F32 x, const F32 y, const F32 width, const F32 height); + // Heights map into textures (or materials) as 0-1 = first, 1-2 = second, etc. + // So we need to compress heights into this range. + static const S32 ASSET_COUNT = 4; + // Use these as indeces ito the get/setters below that use 'corner' enum ECorner { @@ -55,12 +62,12 @@ public: NORTHEAST = 3, CORNER_COUNT = 4 }; - LLUUID getDetailTextureID(S32 corner); - LLViewerFetchedTexture* getDetailTexture(S32 corner); + + LLUUID getDetailAssetID(S32 asset); F32 getStartHeight(S32 corner); F32 getHeightRange(S32 corner); - void setDetailTextureID(S32 corner, const LLUUID& id); + void setDetailAssetID(S32 asset, const LLUUID& id); void setStartHeight(S32 corner, F32 start_height); void setHeightRange(S32 corner, F32 range); @@ -73,8 +80,10 @@ protected: LLSurface *mSurfacep; BOOL mTexturesLoaded; - LLPointer mDetailTextures[CORNER_COUNT]; - LLPointer mRawImages[CORNER_COUNT]; + // TODO: Set flag to indicate whether the textures or materials loaded first + LLPointer mDetailTextures[ASSET_COUNT]; + LLPointer mRawImages[ASSET_COUNT]; + LLPointer mDetailMaterials[ASSET_COUNT]; F32 mStartHeight[CORNER_COUNT]; F32 mHeightRange[CORNER_COUNT]; -- cgit v1.2.3