Initial commit.
This commit is contained in:
161
engine/sound.odin
Normal file
161
engine/sound.odin
Normal file
@@ -0,0 +1,161 @@
|
||||
package engine
|
||||
|
||||
import os "core:os/os2"
|
||||
import "core:container/queue"
|
||||
import "core:log"
|
||||
|
||||
import "ljud"
|
||||
|
||||
Sound :: struct {
|
||||
path: string, // Where I was loaded from.
|
||||
data: []u8,
|
||||
backend: ^Sound_Backend, // Backend-representation.
|
||||
}
|
||||
|
||||
Sound_Instance :: struct {
|
||||
parent: ^Sound, // What I'm an instance of.
|
||||
backend: Sound_Instance_Backend, // Backend-representation.
|
||||
|
||||
spatialized: bool,
|
||||
volume: f32, // 0..1
|
||||
position: [3]f32,
|
||||
min_distance, max_distance: f32,
|
||||
// ..
|
||||
}
|
||||
|
||||
Sound_Instance_ID :: distinct u32
|
||||
|
||||
load_sound_from_path :: proc(engine: ^Engine, path: string) -> (Sound, bool) {
|
||||
assert(engine != nil)
|
||||
|
||||
if len(path) == 0 {
|
||||
return {}, false
|
||||
}
|
||||
|
||||
base, ext := os.split_filename(path)
|
||||
log.info("Loading sound '%v' with extension '%v'.", base, ext)
|
||||
|
||||
// TODO: SS - Check extension.
|
||||
|
||||
data, err := os.read_entire_file(path, context.allocator)
|
||||
if err != nil {
|
||||
log.errorf("Failed to load sound! Could not read entire file. Error: %v", err)
|
||||
return {}, false
|
||||
}
|
||||
|
||||
if len(data) == 0 {
|
||||
log.errorf("Failed to load sound! No data.")
|
||||
return {}, false
|
||||
}
|
||||
|
||||
when AUDIO_ENGINE_LJUD {
|
||||
backend, ok := ljud.load_sound_from_data(&engine.backend, data, ext)
|
||||
if !ok {
|
||||
return {}, false
|
||||
}
|
||||
assert(backend != nil)
|
||||
|
||||
log.info("Loaded sound, returning")
|
||||
|
||||
return Sound {
|
||||
path = path,
|
||||
data = data,
|
||||
backend = backend,
|
||||
}, true
|
||||
}
|
||||
else when AUDIO_ENGINE_FMOD {
|
||||
|
||||
}
|
||||
else when AUDIO_ENGINE_WWISE {
|
||||
|
||||
}
|
||||
|
||||
log.info("No engine defined")
|
||||
|
||||
return {}, false
|
||||
}
|
||||
|
||||
unload_sound :: proc(engine: ^Engine, sound: ^Sound) {
|
||||
assert(engine != nil)
|
||||
assert(sound != nil)
|
||||
assert(sound.data != nil)
|
||||
|
||||
when AUDIO_ENGINE_LJUD {
|
||||
ljud.unload_sound(&engine.backend, sound.backend)
|
||||
}
|
||||
else when AUDIO_ENGINE_FMOD {
|
||||
|
||||
}
|
||||
else when AUDIO_ENGINE_WWISE {
|
||||
|
||||
}
|
||||
|
||||
delete(sound.data)
|
||||
sound.data = nil
|
||||
|
||||
free(sound.backend)
|
||||
sound.backend = nil
|
||||
}
|
||||
|
||||
create_sound_instance :: proc(engine: ^Engine, sound: ^Sound, bus: ^Bus) -> (^Sound_Instance, bool) {
|
||||
assert(engine != nil)
|
||||
assert(sound != nil)
|
||||
|
||||
// TODO: SS - Get an available instance from a pre-allocated buffer.
|
||||
|
||||
sound_instance_id, pop_ok := queue.pop_front_safe(&engine.sound_instance_ids)
|
||||
if !pop_ok {
|
||||
log.warnf("No free sound-instance available.")
|
||||
return {}, false
|
||||
}
|
||||
|
||||
sound_instance := &engine.sound_instances[sound_instance_id]
|
||||
assert(sound_instance != nil)
|
||||
|
||||
sound_instance.parent = sound
|
||||
sound_instance.backend = {}
|
||||
|
||||
instance_ok: bool
|
||||
when AUDIO_ENGINE_LJUD {
|
||||
instance_ok = ljud.init_sound_instance(&engine.backend, bus != nil ? bus.backend : nil, sound.backend, &sound_instance.backend)
|
||||
}
|
||||
else when AUDIO_ENGINE_FMOD {
|
||||
|
||||
}
|
||||
else when AUDIO_ENGINE_WWISE {
|
||||
|
||||
}
|
||||
|
||||
if !instance_ok {
|
||||
log.errorf("Failed to create a Sound-Instance for sound '%v'.", sound.path)
|
||||
return nil, false
|
||||
}
|
||||
|
||||
return sound_instance, true
|
||||
}
|
||||
|
||||
play_sound_instance :: proc(engine: ^Engine, sound_instance: ^Sound_Instance) -> bool {
|
||||
assert(engine != nil)
|
||||
assert(sound_instance != nil)
|
||||
|
||||
when AUDIO_ENGINE_LJUD {
|
||||
spec := ljud.Play_Sound_Instance_Spec {
|
||||
spatialized = sound_instance.spatialized,
|
||||
volume = sound_instance.volume,
|
||||
|
||||
position = sound_instance.position,
|
||||
distance = {
|
||||
min = sound_instance.min_distance,
|
||||
max = sound_instance.max_distance,
|
||||
},
|
||||
}
|
||||
return ljud.play_sound_instance(&engine.backend, &sound_instance.backend, spec)
|
||||
}
|
||||
else when AUDIO_ENGINE_FMOD {
|
||||
}
|
||||
else when AUDIO_ENGINE_WWISE {
|
||||
|
||||
}
|
||||
|
||||
return false
|
||||
}
|
||||
Reference in New Issue
Block a user