Files
Cinderwild/tests/test_terrain_edges.gd
Paul Bailey 12f7fd677d M0.5: detailed scenery, mountain/sea-cliff boundary, Godot 4.7
Scenery (all procedural, seeded, no imported assets):
- Terrain shader: grass/dry grass/dirt/sand/rock strata/snow + detail normals
- 5 tree types, faceted mossy rocks, cliff outcrops, sea stacks, bushes,
  logs and stumps, batched as MultiMesh per 48 m cell
- Wind-animated grass and flowers streamed in tiles around the player
- Lake (depth-shaded water with shore foam), ocean to the horizon,
  cloud sky shader, volumetric fog, glow, softer shadows
- Swimming: float at the surface, swim-jump to climb out

World bounds:
- Steep mountain rim with an invisible wall partway up; one side opens to
  a sheer sea cliff with the wall 1 m inside the edge; whole chunk is an
  island so the mesh edge is never visible
- Respawn safety net if the player leaves the walkable area or the map
- Fix: the cliff edge now tracks the wall in the headlands (it used to
  drop away inside the wall, leaving a pit with lake water hanging over it)

Tests: tests/test_boundary.gd (24-direction escape attempt) and
tests/test_terrain_edges.gd (no ground below waterline near the wall).

Upgrades the project to Godot 4.7 (project.godot rewritten by the 4.7
importer, .uid files added) and documents it in the setup guide.
2026-11-03 23:49:39 +00:00

40 lines
1.4 KiB
GDScript

extends SceneTree
## Terrain edge check: there must be no ground below the inland waterline in the
## band just inside the boundary wall. Ground like that shows up as inland water
## hanging over a drop (the lake water surface stops at the wall) and makes pits
## the player can fall into and not climb out of.
##
## Run: godot --headless --path . --script res://tests/test_terrain_edges.gd
const BAND := 10.0 # metres inside the wall to check
func _initialize() -> void:
var terrain: Node3D = load("res://scripts/world/terrain.gd").new()
root.add_child(terrain) # builds in _ready
_run.call_deferred(terrain)
func _run(terrain: Node3D) -> void:
var bad := 0
var worst := INF
var worst_at := Vector2.ZERO
var half: float = terrain.size * 0.5
var x := -half
while x < half:
var z := -half
while z < half:
if terrain.inside_boundary(x, z, 0.0) and not terrain.inside_boundary(x, z, BAND):
var h: float = terrain.sample_height(x, z)
if h < terrain.water_level + 0.2:
bad += 1
if h < worst:
worst = h
worst_at = Vector2(x, z)
z += 1.0
x += 1.0
if bad > 0:
print("FAIL: %d samples near the wall are below the waterline; lowest %.1f m at (%.0f, %.0f), sea weight %.2f" % [
bad, worst, worst_at.x, worst_at.y, terrain.sea_weight(worst_at.x, worst_at.y)])
else:
print("PASS: ground near the wall stays above the waterline")
quit(1 if bad > 0 else 0)