Added a dampening (lowpass) spatial audio effect for obstacles between the player and the audio source
This commit is contained in:
parent
e147517ad2
commit
47c8576f66
3 changed files with 58 additions and 12 deletions
|
@ -1,7 +1,13 @@
|
|||
class_name SpatialAudioStreamPlayer2D
|
||||
extends AudioStreamPlayer2D
|
||||
|
||||
# DETERMINE REVERB AMOUNT
|
||||
# EXPORTED VARS
|
||||
|
||||
@export var lowpass_cutoff_mult: float = 1000
|
||||
@export var lowpass_cutoff_min: float = 100
|
||||
@export var dampening_distance_divisor_mult: float = 500
|
||||
|
||||
# DETERMINE REVERB EFFECT PARAMETERS
|
||||
|
||||
const RAYCAST_VECS: Array[Vector2] = [
|
||||
Vector2(-1, 0), # 0 - left
|
||||
|
@ -43,10 +49,10 @@ const REVERB_PAIRS = [
|
|||
[5, 7, REVERB_MULT_90DEG]
|
||||
]
|
||||
const REVERB_PAIRS_SUM_DIVISOR = 2500.0 # i dunno
|
||||
|
||||
var raycasts: Array[RayCast2D] = []
|
||||
|
||||
func create_raycasts():
|
||||
# raycasts used for reverb
|
||||
for v in RAYCAST_VECS:
|
||||
var r = RayCast2D.new()
|
||||
r.target_position = v.normalized() * max_distance
|
||||
|
@ -78,18 +84,53 @@ func determine_reverb_params() -> Array[float]:
|
|||
var wetness = n_coll / 8.0
|
||||
return [room_size, wetness]
|
||||
|
||||
# DETERMINE DAMPENING (LOWPASS) EFFECT PARAMETERS
|
||||
|
||||
const N_POINTCASTS_TO_PLAYER: int = 25
|
||||
const POINTCAST_TO_PLAYER_COLL_MASK: int = 0b00000000_00000000_00000000_00000001
|
||||
const LOWPASS_CUTOFF_MAX: float = 20000
|
||||
|
||||
func determine_distance_amount_blocked() -> float:
|
||||
# returns how many points (in relation to the amount of points)
|
||||
# between this and the player are intersecting
|
||||
# and therefore an obstacle for the sound
|
||||
var position_player = NodeRegistry.player.global_position
|
||||
var distance_to_player = self.global_position.distance_to(position_player)
|
||||
# get n collisions
|
||||
var n_coll: int = 0
|
||||
# cast points towards player
|
||||
var space_state = get_world_2d().direct_space_state
|
||||
for i in range(N_POINTCASTS_TO_PLAYER):
|
||||
# linear interpolate between own position and player position
|
||||
var point_pos = lerp(self.global_position, position_player, i/float(N_POINTCASTS_TO_PLAYER))
|
||||
var query_params = PhysicsPointQueryParameters2D.new()
|
||||
query_params.collision_mask = POINTCAST_TO_PLAYER_COLL_MASK
|
||||
query_params.position = point_pos
|
||||
var result = space_state.intersect_point(query_params)
|
||||
if len(result) > 0:
|
||||
n_coll += 1
|
||||
return (n_coll*distance_to_player) / (float(N_POINTCASTS_TO_PLAYER)*dampening_distance_divisor_mult)
|
||||
|
||||
# AUDIO EFFECTS
|
||||
|
||||
var audio_effect_reverb = AudioEffectReverb.new()
|
||||
var audio_effect_dampen = AudioEffectLowPassFilter.new()
|
||||
|
||||
func update_reverb(room_size: float, wetness: float):
|
||||
audio_effect_reverb.room_size = room_size
|
||||
audio_effect_reverb.wet = wetness
|
||||
|
||||
func update_dampening(distance_blocked: float):
|
||||
audio_effect_dampen.cutoff_hz = clamp(
|
||||
lowpass_cutoff_mult / max(0.001, distance_blocked),
|
||||
lowpass_cutoff_min, LOWPASS_CUTOFF_MAX
|
||||
)
|
||||
|
||||
# AUDIO BUS
|
||||
|
||||
const BUS_NAME_PREFIX = "Spatial2DBus#"
|
||||
const BUS_EFFECT_POS_REVERB = 0
|
||||
const BUS_EFFECT_POS_LOWPASS = 1
|
||||
var bus_idx: int = -1
|
||||
var bus_name: String = ""
|
||||
|
||||
|
@ -107,6 +148,8 @@ func create_audio_bus_effects():
|
|||
return
|
||||
# reverb
|
||||
AudioServer.add_bus_effect(bus_idx, audio_effect_reverb, BUS_EFFECT_POS_REVERB)
|
||||
# dampeing (lowpass)
|
||||
AudioServer.add_bus_effect(bus_idx, audio_effect_dampen, BUS_EFFECT_POS_LOWPASS)
|
||||
|
||||
#
|
||||
|
||||
|
@ -117,4 +160,6 @@ func _ready() -> void:
|
|||
|
||||
func _physics_process(_delta: float) -> void:
|
||||
var reverb_params = determine_reverb_params()
|
||||
var blocked_amount = determine_distance_amount_blocked()
|
||||
update_reverb(reverb_params[0], reverb_params[1])
|
||||
update_dampening(blocked_amount)
|
||||
|
|
Reference in a new issue