feat(world): seabed flora and encrusting growth on rock
Quality Gate / Quality Gate (pull_request) Failing after 2m58s

SeabedFloraActor scatters seagrass tufts on flat sand in the lit band and
sea fans on rock between 15 and 60 m, deterministically from the site id,
one MultiMesh per tile and kind, with procedural alpha-cut meshes and
textures (SeabedFloraAssets), vertex sway and wrapped lighting, no
collision and no sonar presence. Placement reads the field arrays
directly and runs on the worker thread pool. The seabed shader grows
turf algae on sunlit rock, coralline crusts in patches and encrusting
sponges in the shade, fading out between 40 and 75 m. The water-column
optics move to a shared shader include.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
This commit is contained in:
OlivierandClaude Fable 5.1 committed 2026-10-07 00:44:10 +02:00
1 parent 122f3f5800
commit 0f9918224a
16 files changed
+585 -14

No files matched your search

+11
View File
@@ -7,11 +7,13 @@ const SitePlacement = preload("res://game/domain/sites/site_placement.gd")
const BathymetricTerrainActor = preload(
"res://game/world/sites/bathymetric_terrain_actor.gd"
)
const SeabedFloraActor = preload("res://game/world/sites/seabed_flora_actor.gd")
const METAL_REFLECTIVITY := 1.0
const BEACON_COLOR := Color(0.2, 0.78, 0.9)
@onready var _terrain: BathymetricTerrainActor = %Terrain
@onready var _flora: SeabedFloraActor = %Flora
@onready var _placements_root: Node3D = %Placements
var _definition: DiveSiteDefinition
@@ -29,6 +31,11 @@ func configure(definition: DiveSiteDefinition) -> String:
var terrain_error := _terrain.configure(field)
if not terrain_error.is_empty():
return terrain_error
if _flora != null:
# The flora is seeded by the site id, so a site always grows the same meadows.
var flora_error := _flora.configure(field, hash(String(definition.site_id)))
if not flora_error.is_empty():
return flora_error
_definition = definition
for child in _placements_root.get_children():
_placements_root.remove_child(child)
@@ -47,6 +54,10 @@ func terrain() -> BathymetricTerrainActor:
return _terrain
func flora() -> SeabedFloraActor:
return _flora
func spawn_transform() -> Transform3D:
return _definition.spawn_transform() if _definition != null else Transform3D.IDENTITY