From 743e178f0a6164bc7bd56efbb6874c140ff73daf Mon Sep 17 00:00:00 2001 From: MihailRis Date: Wed, 19 Feb 2025 22:22:00 +0300 Subject: [PATCH] add effects control (WIP) --- src/audio/AL/ALAudio.cpp | 59 +++++++++++++++++++++++----------------- src/audio/AL/ALAudio.hpp | 6 ++-- src/audio/effects.hpp | 29 ++++++++++++++++++++ 3 files changed, 67 insertions(+), 27 deletions(-) create mode 100644 src/audio/effects.hpp diff --git a/src/audio/AL/ALAudio.cpp b/src/audio/AL/ALAudio.cpp index 3255195f1..4ac4785d8 100644 --- a/src/audio/AL/ALAudio.cpp +++ b/src/audio/AL/ALAudio.cpp @@ -535,16 +535,42 @@ ALAudio::~ALAudio() { context = nullptr; } +template +static bool get_proc_address(const char* name, T& ptr) { + ptr = (T) alGetProcAddress(name); + return ptr != nullptr; +} + void ALAudio::initEffects() { - for (uint i = 0; i < effectSlots.size(); i++) { + bool ok = get_proc_address("alAuxiliaryEffectSloti", alAuxiliaryEffectSloti) + && get_proc_address("alGenAuxiliaryEffectSlots", alGenAuxiliaryEffectSlots) + && get_proc_address("alGenEffects", alGenEffects) + && get_proc_address("alDeleteEffects", alDeleteEffects) + && get_proc_address("alIsEffect", alIsEffect) + && get_proc_address("alEffecti", alEffecti) + && get_proc_address("alEffectf", alEffectf) + && get_proc_address("alGenFilters", alGenFilters) + && get_proc_address("alDeleteFilters", alDeleteFilters) + && get_proc_address("alIsFilter", alIsFilter) + && get_proc_address("alFilteri", alFilteri) + && get_proc_address("alFilterf", alFilterf) + ; + if (!ok) { + logger.error() << "could not get effects extension function pointers"; + useEffects = false; + return; + } + for (uint i = 0; i < maxEffectSlots; i++) { + effectSlots.emplace_back(); alGenAuxiliaryEffectSlots(1, &effectSlots[i]); if (alGetError() != AL_NO_ERROR) { - logger.error() << "could not to create aux effect slot #" << i; - useEffects = false; - return; + break; } } - for (uint i = 0; i < effects.size(); i++) { + logger.info() << "created " << effectSlots.size() << " effect slots"; + + for (uint i = 0; i < 4; i++) { + effects.emplace_back(); alGenEffects(1, &effects[i]); if (alGetError() != AL_NO_ERROR || !alIsEffect(effects[i])) { logger.error() << "could not to create effect #" << i; @@ -552,6 +578,8 @@ void ALAudio::initEffects() { return; } } + logger.info() << "created " << effects.size() << " effects"; + for (uint i = 0; i < filters.size(); i++) { alGenFilters(1, &filters[i]); if (alGetError() != AL_NO_ERROR || !alIsFilter(filters[i])) { @@ -569,6 +597,7 @@ void ALAudio::initEffects() { return; } alEffectf(effects[0], AL_REVERB_DECAY_TIME, 1.0f); + alEffectf(effects[0], AL_REVERB_ROOM_ROLLOFF_FACTOR, 0.07f); // default is 0 // Create lowpass filter alFilteri(filters[0], AL_FILTER_TYPE, AL_FILTER_LOWPASS); @@ -700,26 +729,6 @@ std::unique_ptr ALAudio::create() { alcGetIntegerv(device, ALC_MAX_AUXILIARY_SENDS, 1, &sends); logger.info() << "device supports " << sends << " aux sends per source"; - if (effects) { - bool ok = get_proc_address("alAuxiliaryEffectSloti", alAuxiliaryEffectSloti) - && get_proc_address("alGenAuxiliaryEffectSlots", alGenAuxiliaryEffectSlots) - && get_proc_address("alGenEffects", alGenEffects) - && get_proc_address("alDeleteEffects", alDeleteEffects) - && get_proc_address("alIsEffect", alIsEffect) - && get_proc_address("alEffecti", alEffecti) - && get_proc_address("alEffectf", alEffectf) - && get_proc_address("alGenFilters", alGenFilters) - && get_proc_address("alDeleteFilters", alDeleteFilters) - && get_proc_address("alIsFilter", alIsFilter) - && get_proc_address("alFilteri", alFilteri) - && get_proc_address("alFilterf", alFilterf) - ; - if (!ok) { - logger.error() << "could not get effects extension function pointers"; - effects = false; - } - } - logger.info() << "initialized"; return std::make_unique(device, context, effects); } diff --git a/src/audio/AL/ALAudio.hpp b/src/audio/AL/ALAudio.hpp index 8551e6697..93cc7b31b 100644 --- a/src/audio/AL/ALAudio.hpp +++ b/src/audio/AL/ALAudio.hpp @@ -9,6 +9,7 @@ #include "typedefs.hpp" #include "audio/audio.hpp" +#include "audio/effects.hpp" #ifdef __APPLE__ #include @@ -180,11 +181,12 @@ namespace audio { std::vector allbuffers; std::vector freebuffers; uint maxSources = 256; + uint maxEffectSlots = 64; void initEffects(); public: - std::array effectSlots; - std::array effects; + std::vector effectSlots; + std::vector effects; std::array filters; bool useEffects; diff --git a/src/audio/effects.hpp b/src/audio/effects.hpp new file mode 100644 index 000000000..01d2eedd5 --- /dev/null +++ b/src/audio/effects.hpp @@ -0,0 +1,29 @@ +#pragma once + +#include +#include +#include +#include + +namespace audio { + struct Effect { + struct Property { + using Value = std::variant; + int id; + Value def; + Value min; + Value max; + }; + std::map properties; + }; + + class EffectControl { + public: + EffectControl(const Effect* effect) : effect(effect) {}; + virtual ~EffectControl() = default; + + virtual void set(const std::string& name, Effect::Property::Value value) = 0; + protected: + const Effect* effect = nullptr; + }; +}