Files
VoxelForge/Standalone/Research/WorldAssemblerM3/Linux129/l129-reach-2m.patch
T
Fr0zkaandClaude Opus 5.5 0d1140c117 research: tunnel reach study (L129, no-go; found a units mismatch in v225 bounds)
BuildPassageSpatialIndices adds the 4.335 m reach in core-voxel units, so the broadphase reaches ~1.08 m while
the sweep cutoff says 4 m. Physically-correct 2 m bounds are larger than v225's and 4.9-9.9% slower; captures at
all L125 poses pixel-identical. Patch kept.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016dhxM43dnWvUu2B5Ph1iG1
2026-10-30 23:09:27 +01:00

175 lines
13 KiB
Diff
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
diff --git a/Standalone/Core/include/VoxelForgeCore/VoxelForgeCore.h b/Standalone/Core/include/VoxelForgeCore/VoxelForgeCore.h
index dc4ca32..aac34ff 100644
--- a/Standalone/Core/include/VoxelForgeCore/VoxelForgeCore.h
+++ b/Standalone/Core/include/VoxelForgeCore/VoxelForgeCore.h
@@ -494,7 +494,8 @@ namespace VoxelForgeCore
// Version 223 projects the floor onto one continuous arc-length profile and groups
// dense passage samples into coarse tile candidates. Version 224 keeps the same
// continuous floor while relaxing the spline chord tolerance and bounding shell work.
- inline constexpr std::uint32_t WorldAssemblyEvaluatorVersion = 225;
+ // Version 226 bounds smooth-passage influence in physical metres and narrows its reach.
+ inline constexpr std::uint32_t WorldAssemblyEvaluatorVersion = 226;
enum class FieldChannel : std::uint32_t
{
diff --git a/Standalone/Core/src/ShapeWorldInternal.h b/Standalone/Core/src/ShapeWorldInternal.h
index 517f375..dc258a1 100644
--- a/Standalone/Core/src/ShapeWorldInternal.h
+++ b/Standalone/Core/src/ShapeWorldInternal.h
@@ -72,11 +72,11 @@ static bool VF_IsL98PassagePrepareTraceEnabled()
return bEnabled;
}
-static double VF_L93PassageCarveReachMetres()
+static double VF_L129PassageCarveReachMetres()
{
- // The generated world uses a fixed bounded tube influence. An explicit diagnostic
- // option can still select the legacy point-evaluation path for comparisons.
- return 4.0;
+ // Keep the sweep cutoff and its spatial bounds on one physical reach. Diagnostic
+ // comparisons can still select another bounded reach or the point-evaluation path.
+ return 2.0;
}
enum class EPassageDensityQueryCaller : std::size_t
@@ -306,7 +306,7 @@ public:
profileStats_(profileStats),profileLod_(profileLod),
passageCarveReachMetres_(std::isfinite(passageCarveReachMetres)
&&passageCarveReachMetres>=0.0?passageCarveReachMetres
- :VF_L93PassageCarveReachMetres())
+ :VF_L129PassageCarveReachMetres())
{
mayContainResolvedBoundaryBand_=shape.ResolvedBoundaryBandsIntersectSubvoxelRange(
minimumSubvoxels_[2],maximumSubvoxels_[2]);
@@ -4813,11 +4813,14 @@ private:
constexpr double Q=static_cast<double>(VoxelForgeCore::WorldAssemblySubvoxelsPerVoxel);
constexpr double PassageShellMetres=0.75;
constexpr double ReliefMetres=0.21;
- constexpr double SweepReachMetres=4.0;
+ const double SweepReachMetres=VF_L129PassageCarveReachMetres();
constexpr double CornerBlendMetres=0.50;
constexpr std::size_t CandidateFineSamplesPerSpan=5;
+ const double qPerMetre=Q*1000000.0/
+ std::max<std::uint32_t>(1,ResolvedLayout->coreVoxelSizeMicrometres);
const double requiredReach=std::max(SweepReachMetres+ReliefMetres
+CornerBlendMetres*0.25,PassageShellMetres+ReliefMetres);
+ const double requiredReachCoreVoxels=requiredReach*qPerMetre/Q;
for(std::size_t passageIndex=0;passageIndex<ResolvedLayout->passages.size();
++passageIndex)
{
@@ -4854,7 +4857,7 @@ private:
routeMinimum[axis]=std::min(routeMinimum[axis],localMinimum[axis]);
routeMaximum[axis]=std::max(routeMaximum[axis],localMaximum[axis]);
}
- const double localExtent=requiredReach
+ const double localExtent=requiredReachCoreVoxels
+std::max(prepared.radiusA,prepared.radiusB)/Q+0.01;
FPassageProofBound proof;
for(std::size_t axis=0;axis<3;++axis)
@@ -4872,7 +4875,8 @@ private:
std::ceil((localMaximum[axis]+localExtent)*Q));
}
}
- const double routeExtent=maximumRadiusSubvoxels/Q+requiredReach+0.01;
+ const double routeExtent=maximumRadiusSubvoxels/Q
+ +requiredReachCoreVoxels+0.01;
const double tileExtent=routeExtent;
std::array<std::int64_t,3> featureMinimum{},featureMaximum{};
for(std::size_t axis=0;axis<3;++axis)
@@ -11442,7 +11446,7 @@ inline void FStandaloneShapeWorld::FScopedPassageTileQueries::prepareSweptTubeBa
const FIntVector& origin,std::int32_t step,std::int32_t cells,std::uint32_t seed)
{
constexpr std::int64_t Q=VoxelForgeCore::WorldAssemblySubvoxelsPerVoxel;
- constexpr double InfluenceMetres=4.0;
+ const double InfluenceMetres=VF_L129PassageCarveReachMetres();
constexpr double OpenAirSideWallHeightMetres=1.0;
if(!shape_||step<=0||cells<=0||!std::isfinite(passageCarveReachMetres_)
||std::abs(passageCarveReachMetres_-InfluenceMetres)>1.0e-9)return;
diff --git a/Standalone/Tools/verify/baselines/README.md b/Standalone/Tools/verify/baselines/README.md
index 45fbb9f..fc7a59a 100644
--- a/Standalone/Tools/verify/baselines/README.md
+++ b/Standalone/Tools/verify/baselines/README.md
@@ -4,7 +4,7 @@ These inputs are byte-for-byte copies of the historical files consumed by the
verification gates. The gates now read this tracked directory instead of
`Saved/Linux`, which is generated and is not present in a fresh checkout.
-- `owner-hash/`: L46, L52 and L53 diagnostics plus the pinned v212/v214 owner hash baselines.
+- `owner-hash/`: L46, L52 and L53 diagnostics plus the pinned v212/v214 and L129 v226 owner hash baselines.
- `historical-controls/`: L35, L36 and L38 regression-control logs.
- `fixtures/`: Linux25 owner JSON inputs and L33 style-override fixtures.
- `landmarks/`: L45–L48 landmark mesh and layout controls.
diff --git a/Standalone/Tools/verify/baselines/owner-hash/canonical/owner-hash-floating-islands-style2-v226.baseline b/Standalone/Tools/verify/baselines/owner-hash/canonical/owner-hash-floating-islands-style2-v226.baseline
new file mode 100644
index 0000000..9d3b87b
--- /dev/null
+++ b/Standalone/Tools/verify/baselines/owner-hash/canonical/owner-hash-floating-islands-style2-v226.baseline
@@ -0,0 +1,12 @@
+[PipelineFullDetailHash] tiles=960 density=0x91931a57a067fd92 mesh=0xa818654be89790ac payload=0x370ff80451105a39 topology=0x06e507557aa70173
+[PipelineWholeViewHash] tiles=2370 density=0x1573b570e1cbbf7e mesh=0xd88bf8bcf69ce1ce payload=0x347541780c9d8d71 topology=0x6b8ff8640be6e9d4
+[PipelineLODHash] lod=0 tiles=512 density=0x2fd4c78685a43cfe mesh=0x50478cff1c1f8ca0 payload=0x54e48e57e0af26de topology=0x860c011cfdb9833a
+[PipelineLODHash] lod=1 tiles=448 density=0x4b8d9a6dcd2942ad mesh=0x17e89b7087bfe711 payload=0x2389c109eb780db6 topology=0x7eccd4cf560d0630
+[PipelineLODHash] lod=2 tiles=320 density=0x600ce5633a8f9e83 mesh=0xcd40f163b4cf3e0e payload=0xbe81dc276737a33a topology=0x942806963fedb92d
+[PipelineLODHash] lod=3 tiles=208 density=0xf778be0581c49ed8 mesh=0x9aacf9e2a23034f8 payload=0xc1d4a985f2db3df5 topology=0xcdfdb412d3784023
+[PipelineLODHash] lod=4 tiles=240 density=0xfb11591772a3d18e mesh=0xebf2baee8764591b payload=0xe491d7ac9c0061ad topology=0xd618ac33b95ce494
+[PipelineLODHash] lod=5 tiles=144 density=0x2f8b7b7fb1e67258 mesh=0x4cd508cbe97344fd payload=0x2b6e96a6050458c9 topology=0x4ff6d0eda8988573
+[PipelineLODHash] lod=6 tiles=96 density=0x0114a34c8b8d6113 mesh=0xb1fec4d01ae1fa44 payload=0x3e50cfd429b8e950 topology=0x08090c96d15c1618
+[PipelineLODHash] lod=7 tiles=96 density=0x3836ed8cfce73418 mesh=0x40bc6589c5fc1aac payload=0x677349bcae16790f topology=0x36e3aa53192e6a6b
+[PipelineLODHash] lod=8 tiles=306 density=0x144f3c1fd722708b mesh=0xef77b28bf7fd9453 payload=0xe3f47b37fcd61489 topology=0x5a3c73e295494e04
+[PipelineExactQueryHash] probes=9 density=0x7b7c50ac24ccadcc unclamped=0x7b7c50ac24ccadcc detail=0xefcba20c0c70c415 collision=0xe604823a249029bf path=direct-Core-queries
diff --git a/Standalone/Tools/verify/baselines/owner-hash/canonical/owner-hash-owner4-surface-world-style1-v226.baseline b/Standalone/Tools/verify/baselines/owner-hash/canonical/owner-hash-owner4-surface-world-style1-v226.baseline
new file mode 100644
index 0000000..128c807
--- /dev/null
+++ b/Standalone/Tools/verify/baselines/owner-hash/canonical/owner-hash-owner4-surface-world-style1-v226.baseline
@@ -0,0 +1,12 @@
+[PipelineFullDetailHash] tiles=960 density=0xe1aa01ac806a84fb mesh=0x453624e695910639 payload=0x2f5793602ea13144 topology=0x31a43376cb129e55
+[PipelineWholeViewHash] tiles=2578 density=0xb82dc1dcdadda8ff mesh=0xe74e85bf3cb0909b payload=0x40bc3871dd9dccbe topology=0x855e712b549606c3
+[PipelineLODHash] lod=0 tiles=512 density=0x8119a4f12c4661f4 mesh=0xc074e3705293bef2 payload=0x36c965f6b43875ea topology=0x38bed0df168486d0
+[PipelineLODHash] lod=1 tiles=448 density=0x6270dd0856c53432 mesh=0xa803bb427deeba9a payload=0xf4718f1ce85d4f4f topology=0x7b770585aafd8174
+[PipelineLODHash] lod=2 tiles=320 density=0xf774df80811a61c1 mesh=0xb223f0f68d0310f8 payload=0x6c3fd8c4aa100ee9 topology=0x923485084c866600
+[PipelineLODHash] lod=3 tiles=272 density=0x62088ea9f38d2ed0 mesh=0x19bb327ba4ba3287 payload=0xd04c1223d50da0ea topology=0xf3817d1351cc89c5
+[PipelineLODHash] lod=4 tiles=272 density=0xb743eb64967bddcd mesh=0xf6b5bd36b0ebfead payload=0xd1284c1540f50636 topology=0x4a6e197e2a1a9500
+[PipelineLODHash] lod=5 tiles=208 density=0x38706b628a74dd17 mesh=0x445b1c7b51489cbb payload=0x713efc66290768f7 topology=0x56486b919146bb1e
+[PipelineLODHash] lod=6 tiles=144 density=0xd53849b2002a1faa mesh=0xaa210abc8498c415 payload=0xd109aef8639706d1 topology=0x61a4d75fbbc35268
+[PipelineLODHash] lod=7 tiles=96 density=0xb0ea9a140275c9cc mesh=0x3ffd8365c8b0ec29 payload=0x3577afb0a2e4a420 topology=0x97530aafde15b7e0
+[PipelineLODHash] lod=8 tiles=306 density=0x8b3d1816799d67a0 mesh=0x80bf554f17700e1e payload=0xccbe22c3333a9c34 topology=0xcb11b28f6b6bcc50
+[PipelineExactQueryHash] probes=9 density=0xf2df67b38b7802df unclamped=0x48b347986345b557 detail=0xefcba20c0c70c415 collision=0x137e8f6c0b03a624 path=direct-Core-queries
diff --git a/Standalone/Tools/verify/baselines/owner-hash/canonical/owner-hash-surface-world-style1-v226.baseline b/Standalone/Tools/verify/baselines/owner-hash/canonical/owner-hash-surface-world-style1-v226.baseline
new file mode 100644
index 0000000..49f85bb
--- /dev/null
+++ b/Standalone/Tools/verify/baselines/owner-hash/canonical/owner-hash-surface-world-style1-v226.baseline
@@ -0,0 +1,12 @@
+[PipelineFullDetailHash] tiles=960 density=0xace56c8f205238ad mesh=0xa9c603a1248de6b8 payload=0xea55f1f4fcc6a894 topology=0x5ea7bc78a1b678ae
+[PipelineWholeViewHash] tiles=2370 density=0x637fdf29ccba949b mesh=0xb02cf034b0c9e375 payload=0x74240706eac0c770 topology=0xe607e19fd4684210
+[PipelineLODHash] lod=0 tiles=512 density=0xcd6ab28cfa504aca mesh=0xf03dc80a669fca31 payload=0x397aded1c3d2d297 topology=0xb4a1dc84fabc1fe3
+[PipelineLODHash] lod=1 tiles=448 density=0xce6e713828b2a20a mesh=0x1cf408c25d67d18c payload=0x8a2b5d20571c997e topology=0x51cd985fe8e7d100
+[PipelineLODHash] lod=2 tiles=320 density=0x353ee7ab408a9da1 mesh=0x8d355a8d598d56d5 payload=0x458f26e32d815635 topology=0x2e89b3cba09efcfe
+[PipelineLODHash] lod=3 tiles=208 density=0xfe4f53b3ec010392 mesh=0xbd04d2da98d5b2e0 payload=0x10627f36d82200e8 topology=0xd625f3434ac0a893
+[PipelineLODHash] lod=4 tiles=240 density=0x0be8798407724eaf mesh=0x131c303cbbe51434 payload=0x2a90ecf0a2411ca0 topology=0xe3e054a371152e08
+[PipelineLODHash] lod=5 tiles=144 density=0xf20897ad272103a9 mesh=0x13d00b6253ae1f72 payload=0x0db3880693a962fa topology=0x462bd87a80f15e89
+[PipelineLODHash] lod=6 tiles=96 density=0xc040fcac457d6313 mesh=0x1ed132eeb718fb62 payload=0xcd0214e35577c6e3 topology=0x2c56c69e6fdcfd64
+[PipelineLODHash] lod=7 tiles=96 density=0xc2d419446355fdb8 mesh=0x4ea44452574fc84b payload=0xfd9779bedfc9ae0f topology=0x8948546e770c9b72
+[PipelineLODHash] lod=8 tiles=306 density=0x62db31696f2da831 mesh=0xd373f9e9481532fe payload=0x540a60526e0e3e46 topology=0xc725cb901e6dc335
+[PipelineExactQueryHash] probes=9 density=0xc949c4df2ce6f9d9 unclamped=0xc949c4df2ce6f9d9 detail=0x114c501e2d830d94 collision=0xe6011d3a248d4849 path=direct-Core-queries
diff --git a/Standalone/Tools/verify/verify.py b/Standalone/Tools/verify/verify.py
index 5fc1584..70f6a69 100644
--- a/Standalone/Tools/verify/verify.py
+++ b/Standalone/Tools/verify/verify.py
@@ -122,11 +122,11 @@ RECIPE_RE = re.compile(
def owner_hash_baseline(recipe: str, style: int) -> tuple[Path, str]:
if recipe == "surface-world" and style == 1:
- return (BASELINES / "owner-hash/canonical/owner-hash-surface-world-style1-v225.baseline",
- "L125-v225-stamped-passage-sweep")
+ return (BASELINES / "owner-hash/canonical/owner-hash-surface-world-style1-v226.baseline",
+ "L129-v226-physical-passage-reach")
if recipe == "floating-islands" and style == 2:
- return (BASELINES / "owner-hash/canonical/owner-hash-floating-islands-style2-v225.baseline",
- "L125-v225-stamped-passage-sweep")
+ return (BASELINES / "owner-hash/canonical/owner-hash-floating-islands-style2-v226.baseline",
+ "L129-v226-physical-passage-reach")
raise VerificationFailure(f"no pinned owner hash baseline for {recipe} style {style}")