From 1b431bf63372220fab856d0ef8dbb01b25edd03f Mon Sep 17 00:00:00 2001 From: Dave Corley Date: Mon, 19 Feb 2024 05:25:20 -0600 Subject: [PATCH 1/8] Fix(editor): Don't save dirty water height values --- components/esm3/loadcell.cpp | 22 ++++++---------------- 1 file changed, 6 insertions(+), 16 deletions(-) diff --git a/components/esm3/loadcell.cpp b/components/esm3/loadcell.cpp index 829cf9e916..5b8521f9a1 100644 --- a/components/esm3/loadcell.cpp +++ b/components/esm3/loadcell.cpp @@ -190,25 +190,15 @@ namespace ESM if (mData.mFlags & Interior) { - if (mWaterInt) - { - int32_t water = (mWater >= 0) ? static_cast(mWater + 0.5) : static_cast(mWater - 0.5); - esm.writeHNT("INTV", water); - } - else - { + // Try to avoid saving ambient information when it's unnecessary. + // This is to fix black lighting and flooded water + // in resaved cell records that lack this information. + if (mWaterInt && mWater != 0) esm.writeHNT("WHGT", mWater); - } - if (mData.mFlags & QuasiEx) esm.writeHNOCRefId("RGNN", mRegion); - else - { - // Try to avoid saving ambient lighting information when it's unnecessary. - // This is to fix black lighting in resaved cell records that lack this information. - if (mHasAmbi) - esm.writeHNT("AMBI", mAmbi, 16); - } + else if (mHasAmbi) + esm.writeHNT("AMBI", mAmbi, 16); } else { From bb35f0366a12c1eea5e68d7aeabe4e19aac66758 Mon Sep 17 00:00:00 2001 From: Dave Corley Date: Tue, 20 Feb 2024 07:12:42 -0600 Subject: [PATCH 2/8] Fix(loadcell): Save water height regardless of value, if the user actually adjusted it --- apps/opencs/model/world/nestedcoladapterimp.cpp | 3 +++ components/esm3/loadcell.cpp | 5 ++++- components/esm3/loadcell.hpp | 4 ++++ 3 files changed, 11 insertions(+), 1 deletion(-) diff --git a/apps/opencs/model/world/nestedcoladapterimp.cpp b/apps/opencs/model/world/nestedcoladapterimp.cpp index 13ae821a77..ea3a3bde26 100644 --- a/apps/opencs/model/world/nestedcoladapterimp.cpp +++ b/apps/opencs/model/world/nestedcoladapterimp.cpp @@ -996,7 +996,10 @@ namespace CSMWorld case 5: { if (isInterior && interiorWater) + { cell.mWater = value.toFloat(); + cell.setHasWater(true); + } else return; // return without saving break; diff --git a/components/esm3/loadcell.cpp b/components/esm3/loadcell.cpp index 5b8521f9a1..f550c190cb 100644 --- a/components/esm3/loadcell.cpp +++ b/components/esm3/loadcell.cpp @@ -118,6 +118,7 @@ namespace ESM bool overriding = !mName.empty(); bool isLoaded = false; mHasAmbi = false; + mHasWater = false; while (!isLoaded && esm.hasMoreSubs()) { esm.getSubName(); @@ -133,6 +134,7 @@ namespace ESM float waterLevel; esm.getHT(waterLevel); mWaterInt = false; + mHasWater = true; if (!std::isfinite(waterLevel)) { if (!overriding) @@ -193,7 +195,7 @@ namespace ESM // Try to avoid saving ambient information when it's unnecessary. // This is to fix black lighting and flooded water // in resaved cell records that lack this information. - if (mWaterInt && mWater != 0) + if (mHasWater) esm.writeHNT("WHGT", mWater); if (mData.mFlags & QuasiEx) esm.writeHNOCRefId("RGNN", mRegion); @@ -323,6 +325,7 @@ namespace ESM mData.mY = 0; mHasAmbi = true; + mHasWater = true; mAmbi.mAmbient = 0; mAmbi.mSunlight = 0; mAmbi.mFog = 0; diff --git a/components/esm3/loadcell.hpp b/components/esm3/loadcell.hpp index bfabdd58f9..d54ba9573a 100644 --- a/components/esm3/loadcell.hpp +++ b/components/esm3/loadcell.hpp @@ -112,6 +112,7 @@ namespace ESM , mHasAmbi(true) , mWater(0) , mWaterInt(false) + , mHasWater(false) , mMapColor(0) , mRefNumCounter(0) { @@ -132,6 +133,7 @@ namespace ESM float mWater; // Water level bool mWaterInt; + bool mHasWater; int32_t mMapColor; // Counter for RefNums. This is only used during content file editing and has no impact on gameplay. // It prevents overwriting previous refNums, even if they were deleted. @@ -163,6 +165,8 @@ namespace ESM bool hasWater() const { return ((mData.mFlags & HasWater) != 0) || isExterior(); } + void setHasWater(bool hasWater) { mHasWater = hasWater; } + bool hasAmbient() const { return mHasAmbi; } void setHasAmbient(bool hasAmbi) { mHasAmbi = hasAmbi; } From f95cad07f2a5fc7087d10a1a3ca13c28b1bccf62 Mon Sep 17 00:00:00 2001 From: Dave Corley Date: Tue, 20 Feb 2024 08:01:08 -0600 Subject: [PATCH 3/8] Cleanup(loadcell): Remove unused integer water flag --- components/esm3/loadcell.cpp | 3 --- components/esm3/loadcell.hpp | 2 -- 2 files changed, 5 deletions(-) diff --git a/components/esm3/loadcell.cpp b/components/esm3/loadcell.cpp index f550c190cb..1d54cd84bf 100644 --- a/components/esm3/loadcell.cpp +++ b/components/esm3/loadcell.cpp @@ -128,12 +128,10 @@ namespace ESM int32_t waterl; esm.getHT(waterl); mWater = static_cast(waterl); - mWaterInt = true; break; case fourCC("WHGT"): float waterLevel; esm.getHT(waterLevel); - mWaterInt = false; mHasWater = true; if (!std::isfinite(waterLevel)) { @@ -316,7 +314,6 @@ namespace ESM mName.clear(); mRegion = ESM::RefId(); mWater = 0; - mWaterInt = false; mMapColor = 0; mRefNumCounter = 0; diff --git a/components/esm3/loadcell.hpp b/components/esm3/loadcell.hpp index d54ba9573a..1397479154 100644 --- a/components/esm3/loadcell.hpp +++ b/components/esm3/loadcell.hpp @@ -111,7 +111,6 @@ namespace ESM , mRegion(ESM::RefId()) , mHasAmbi(true) , mWater(0) - , mWaterInt(false) , mHasWater(false) , mMapColor(0) , mRefNumCounter(0) @@ -132,7 +131,6 @@ namespace ESM bool mHasAmbi; float mWater; // Water level - bool mWaterInt; bool mHasWater; int32_t mMapColor; // Counter for RefNums. This is only used during content file editing and has no impact on gameplay. From d04572ac847180c569aa793c6c80557762ce181d Mon Sep 17 00:00:00 2001 From: Dave Corley Date: Tue, 20 Feb 2024 08:39:43 -0600 Subject: [PATCH 4/8] Cleanup(loadcell): Rename mHasWater to mHasWaterHeightSub for clarity. --- components/esm3/loadcell.cpp | 8 ++++---- components/esm3/loadcell.hpp | 6 +++--- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/components/esm3/loadcell.cpp b/components/esm3/loadcell.cpp index 1d54cd84bf..473c4c7d72 100644 --- a/components/esm3/loadcell.cpp +++ b/components/esm3/loadcell.cpp @@ -118,7 +118,7 @@ namespace ESM bool overriding = !mName.empty(); bool isLoaded = false; mHasAmbi = false; - mHasWater = false; + mHasWaterHeightSub = false; while (!isLoaded && esm.hasMoreSubs()) { esm.getSubName(); @@ -132,7 +132,7 @@ namespace ESM case fourCC("WHGT"): float waterLevel; esm.getHT(waterLevel); - mHasWater = true; + mHasWaterHeightSub = true; if (!std::isfinite(waterLevel)) { if (!overriding) @@ -193,7 +193,7 @@ namespace ESM // Try to avoid saving ambient information when it's unnecessary. // This is to fix black lighting and flooded water // in resaved cell records that lack this information. - if (mHasWater) + if (mHasWaterHeightSub) esm.writeHNT("WHGT", mWater); if (mData.mFlags & QuasiEx) esm.writeHNOCRefId("RGNN", mRegion); @@ -322,7 +322,7 @@ namespace ESM mData.mY = 0; mHasAmbi = true; - mHasWater = true; + mHasWaterHeightSub = true; mAmbi.mAmbient = 0; mAmbi.mSunlight = 0; mAmbi.mFog = 0; diff --git a/components/esm3/loadcell.hpp b/components/esm3/loadcell.hpp index 1397479154..a22110be32 100644 --- a/components/esm3/loadcell.hpp +++ b/components/esm3/loadcell.hpp @@ -111,7 +111,7 @@ namespace ESM , mRegion(ESM::RefId()) , mHasAmbi(true) , mWater(0) - , mHasWater(false) + , mHasWaterHeightSub(false) , mMapColor(0) , mRefNumCounter(0) { @@ -131,7 +131,7 @@ namespace ESM bool mHasAmbi; float mWater; // Water level - bool mHasWater; + bool mHasWaterHeightSub; int32_t mMapColor; // Counter for RefNums. This is only used during content file editing and has no impact on gameplay. // It prevents overwriting previous refNums, even if they were deleted. @@ -163,7 +163,7 @@ namespace ESM bool hasWater() const { return ((mData.mFlags & HasWater) != 0) || isExterior(); } - void setHasWater(bool hasWater) { mHasWater = hasWater; } + void setHasWater(bool hasWater) { mHasWaterHeightSub = hasWater; } bool hasAmbient() const { return mHasAmbi; } From b2b1c98396edb05888b0c59e3ebb5bfa1188e140 Mon Sep 17 00:00:00 2001 From: Dave Corley Date: Tue, 20 Feb 2024 22:23:53 -0600 Subject: [PATCH 5/8] fix(esmtool): Don't try to log a variable that doesn't exist --- apps/esmtool/record.cpp | 1 - 1 file changed, 1 deletion(-) diff --git a/apps/esmtool/record.cpp b/apps/esmtool/record.cpp index 245012ce13..b1185a4d33 100644 --- a/apps/esmtool/record.cpp +++ b/apps/esmtool/record.cpp @@ -612,7 +612,6 @@ namespace EsmTool } else std::cout << " Map Color: " << Misc::StringUtils::format("0x%08X", mData.mMapColor) << std::endl; - std::cout << " Water Level Int: " << mData.mWaterInt << std::endl; std::cout << " RefId counter: " << mData.mRefNumCounter << std::endl; std::cout << " Deleted: " << mIsDeleted << std::endl; } From 7f67d2e805bfba82c84163f429d266a9c4d84826 Mon Sep 17 00:00:00 2001 From: Dave Corley Date: Thu, 22 Feb 2024 03:02:10 -0600 Subject: [PATCH 6/8] Add changelog entry for #7841 --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 96e6de5648..c4fbaf3166 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -150,6 +150,7 @@ Bug #7796: Absorbed enchantments don't restore magicka Bug #7832: Ingredient tooltips show magnitude for Fortify Maximum Magicka effect Bug #7840: First run of the launcher doesn't save viewing distance as the default value + Bug #7841: Editor: "Dirty" water heights are saved in modified CELLs Feature #2566: Handle NAM9 records for manual cell references Feature #3537: Shader-based water ripples Feature #5173: Support for NiFogProperty From ce2787e15e7581c2aae5cd5a0b40203a5b3fe017 Mon Sep 17 00:00:00 2001 From: Dave Corley Date: Thu, 22 Feb 2024 03:23:23 -0600 Subject: [PATCH 7/8] Cleanup(loadcell): Rename setHasWater to setHasWaterHeightSub --- apps/opencs/model/world/nestedcoladapterimp.cpp | 2 +- components/esm3/loadcell.hpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/apps/opencs/model/world/nestedcoladapterimp.cpp b/apps/opencs/model/world/nestedcoladapterimp.cpp index ea3a3bde26..8b8c7b17be 100644 --- a/apps/opencs/model/world/nestedcoladapterimp.cpp +++ b/apps/opencs/model/world/nestedcoladapterimp.cpp @@ -998,7 +998,7 @@ namespace CSMWorld if (isInterior && interiorWater) { cell.mWater = value.toFloat(); - cell.setHasWater(true); + cell.setHasWaterHeightSub(true); } else return; // return without saving diff --git a/components/esm3/loadcell.hpp b/components/esm3/loadcell.hpp index a22110be32..3f16bcca31 100644 --- a/components/esm3/loadcell.hpp +++ b/components/esm3/loadcell.hpp @@ -163,7 +163,7 @@ namespace ESM bool hasWater() const { return ((mData.mFlags & HasWater) != 0) || isExterior(); } - void setHasWater(bool hasWater) { mHasWaterHeightSub = hasWater; } + void setHasWaterHeightSub(bool hasWater) { mHasWaterHeightSub = hasWater; } bool hasAmbient() const { return mHasAmbi; } From 059191c84069e8edca3b9ac1d48d032b0969508a Mon Sep 17 00:00:00 2001 From: Dave Corley Date: Sun, 25 Feb 2024 07:30:23 -0600 Subject: [PATCH 8/8] Also apply hasWaterHeightSub for INTV --- components/esm3/loadcell.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/components/esm3/loadcell.cpp b/components/esm3/loadcell.cpp index 473c4c7d72..0c37e64f1e 100644 --- a/components/esm3/loadcell.cpp +++ b/components/esm3/loadcell.cpp @@ -127,6 +127,7 @@ namespace ESM case fourCC("INTV"): int32_t waterl; esm.getHT(waterl); + mHasWaterHeightSub = true; mWater = static_cast(waterl); break; case fourCC("WHGT"):