Not sure how to adapt this code to AudioStreamPlayer3D

Godot Version

4.4

Question

I have code I’ve borrowed from this guide and i fixed the error that comes with using it in Godot 4.x. But i’ve been trying to use it for 3d audiostreamplayers but the play function requires a float and i cant just play it? It’s easy enough to figure out if i used an audiostreamplayer3D for every single different audio since i can drag and drop but I have no idea how to do it through code. I can’t find any guides on making dynamic audio for 3d so any help would be appreciated including just linking videos that discuss it.

extends Node3D

var num_players = 8
var bus = "master"

var available = []  # The available players.
var queue = []  # The queue of sounds to play.


func _ready():
	# Create the pool of AudioStreamPlayer nodes.
	for i in num_players:
		var p = AudioStreamPlayer3D.new()
		add_child(p)
		available.append(p)
		p.finished.connect(func(): _on_stream_finished(p))
		p.bus = bus

func _on_stream_finished(stream):
	# When finished playing a stream, make the player available again.
	available.append(stream)


func play(sound_path):
	queue.append(sound_path)


func _process(delta):
	# Play a queued sound if any players are available.
	if not queue.empty() and not available.empty():
		available[0].stream = load(queue.pop_front())
		available[0].play()
		available.pop_front()

This is my adapted code and I have 3d nodes that move positions in animation so i can play the animation and have the sound move accordingly, but even before i cross that bridge I was stopped by this one.

I changed some things, most of them in the process function.
Not sure why the code coloring does not work.

extends Node3D

var num_players = 8
var bus = "master"

var available = []  # The available players.
var queue = []  # The queue of sounds to play.

# added some filepaths to streams in the inspector for testing
@export var streams : Array[String]


func _ready():
	# Create the pool of AudioStreamPlayer nodes.
	for i in num_players:
		var p = AudioStreamPlayer3D.new()
		add_child(p)
		available.append(p)
		p.finished.connect(func(): _on_stream_finished(p))
		# alternative way:
		# p.finished.connect(_on_stream_finished.bind(p))
		p.bus = bus

func _on_stream_finished(stream):
	# When finished playing a stream, make the player available again.
	available.append(stream)


func play(sound_path):
	queue.append(sound_path)

# for testing press space or enter
func _input(event: InputEvent) -> void:
	if event.is_action_pressed("ui_accept"):
		play(load(streams.pick_random()))


func _process(delta):
	# Play a queued sound if any players are available.
	# Should be ".is_empty()"
	if not queue.is_empty() and not available.is_empty():
		var audio_player = available.pop_front()
		audio_player.stream = queue.pop_front()
		audio_player.play()
1 Like