feat(biome): abyssal bioluminescent + glow blocks + abyssal jellyfish + particles

- BlockDatabase: GLOW_CORAL_CYAN(10), GLOW_CORAL_VIOLET(11), LAVA_VENT(12) with emission data
- WorldGenerator: abyssal blocks at y<-40 (cyan 4%, violet 1%, vent 0.5% via 3D noise)
- Chunk.gd: multi-surface mesh (solid + 3 emissive surfaces with StandardMaterial3D emission)
- MobSpawner: abyssal jellyfish spawn when player y<-30, max 8
- AbyssalJellyfish: cyan fluo, slower, double damage (10), bioluminescent flash on attack
- BioluminescentParticles: 200 cyan-green particles follow player, only emit in abyss

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
Floppyrj45
2026-04-19 18:12:37 +02:00
parent e1fda4d393
commit d8e19932cc
6 changed files with 324 additions and 28 deletions

View File

@@ -0,0 +1,81 @@
extends Jellyfish
# Abyssal variant: slower, packs double damage, bioluminescent cyan flash on contact
func _build_visuals() -> void:
# Cyan emissive dome material
var mat := StandardMaterial3D.new()
mat.transparency = BaseMaterial3D.TRANSPARENCY_ALPHA
mat.albedo_color = Color(0.1, 0.9, 1.0, 0.6)
mat.emission_enabled = true
mat.emission = Color(0.2, 0.8, 1.0)
mat.emission_energy_multiplier = 2.5
mat.cull_mode = BaseMaterial3D.CULL_DISABLED
_dome = MeshInstance3D.new()
var sphere := SphereMesh.new()
sphere.radius = 0.55
sphere.height = 0.75
_dome.mesh = sphere
_dome.material_override = mat
_dome.scale = Vector3(1.0, 0.7, 1.0)
add_child(_dome)
# Thin luminous tentacles
var tent_mat := StandardMaterial3D.new()
tent_mat.transparency = BaseMaterial3D.TRANSPARENCY_ALPHA
tent_mat.albedo_color = Color(0.1, 0.9, 1.0, 0.4)
tent_mat.emission_enabled = true
tent_mat.emission = Color(0.2, 0.8, 1.0)
tent_mat.emission_energy_multiplier = 2.0
tent_mat.cull_mode = BaseMaterial3D.CULL_DISABLED
var offsets: Array[Vector2] = [
Vector2(0.25, 0.0), Vector2(-0.25, 0.0),
Vector2(0.0, 0.25), Vector2(0.0, -0.25),
Vector2(0.18, 0.18), Vector2(-0.18, -0.18)
]
for off: Vector2 in offsets:
var tent := MeshInstance3D.new()
var cap := CapsuleMesh.new()
cap.radius = 0.02
cap.height = 0.9
tent.mesh = cap
tent.material_override = tent_mat
tent.position = Vector3(off.x, -0.65, off.y)
add_child(tent)
_tentacles.append(tent)
# Collision
var col := CollisionShape3D.new()
var cshape := SphereShape3D.new()
cshape.radius = 0.6
col.shape = cshape
add_child(col)
func _ready() -> void:
# Override stats before parent _ready to ensure double damage and slower speed
damage = 10.0 # double base jellyfish damage
move_speed = 0.6 # slower
detection_radius = 8.0 # wider detection in dark abyss
super._ready()
func _on_attack() -> void:
# Bioluminescent flash: briefly boost emission on dome
if _dome != null and _dome.material_override != null:
var mat := _dome.material_override as StandardMaterial3D
if mat != null:
mat.emission_energy_multiplier = 8.0
await get_tree().create_timer(0.15).timeout
if is_instance_valid(self) and _dome != null and _dome.material_override != null:
mat.emission_energy_multiplier = 2.5
func _physics_process(delta: float) -> void:
var was_attacking: bool = (_state == State.ATTACK)
super._physics_process(delta)
# Trigger flash when we just entered attack
if not was_attacking and _state == State.ATTACK:
_on_attack()