aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChris Robinson <[email protected]>2021-10-24 11:51:39 -0700
committerChris Robinson <[email protected]>2021-10-24 11:51:39 -0700
commit49a36334bd8255094d780ffb78cce75135190533 (patch)
tree9abef164c0f597d945b1576e2bc6f1c6f240ec15
parent096bed35fabf4d912ae62809cecb3819d2b91e5f (diff)
Use a tri-state optional for the stereo output mode
-rw-r--r--alc/alc.cpp41
-rw-r--r--alc/alu.h4
-rw-r--r--alc/panning.cpp9
-rw-r--r--core/device.h6
4 files changed, 40 insertions, 20 deletions
diff --git a/alc/alc.cpp b/alc/alc.cpp
index 8f065bd2..2745869d 100644
--- a/alc/alc.cpp
+++ b/alc/alc.cpp
@@ -1522,8 +1522,7 @@ ALCenum UpdateDeviceParams(ALCdevice *device, const int *attrList)
{
ALCenum gainLimiter{device->LimiterState};
uint new_sends{device->NumAuxSends};
- al::optional<bool> hrtfreq{};
- al::optional<bool> uhjreq{};
+ al::optional<StereoEncoding> stereomode{};
DevFmtChannels oldChans;
DevFmtType oldType;
int hrtf_id{-1};
@@ -1546,6 +1545,7 @@ ALCenum UpdateDeviceParams(ALCdevice *device, const int *attrList)
al::optional<DevFmtType> opttype;
al::optional<DevAmbiLayout> optlayout;
al::optional<DevAmbiScaling> optscale;
+ al::optional<bool> opthrtf;
uint aorder{0u};
uint freq{0u};
@@ -1608,11 +1608,11 @@ ALCenum UpdateDeviceParams(ALCdevice *device, const int *attrList)
case ALC_HRTF_SOFT:
TRACE_ATTR(ALC_HRTF_SOFT, attrList[attrIdx + 1]);
if(attrList[attrIdx + 1] == ALC_FALSE)
- hrtfreq = al::make_optional(false);
+ opthrtf = al::make_optional(false);
else if(attrList[attrIdx + 1] == ALC_TRUE)
- hrtfreq = al::make_optional(true);
+ opthrtf = al::make_optional(true);
else
- hrtfreq = al::nullopt;
+ opthrtf = al::nullopt;
break;
case ALC_HRTF_ID_SOFT:
@@ -1663,6 +1663,12 @@ ALCenum UpdateDeviceParams(ALCdevice *device, const int *attrList)
UpdateClockBase(device);
+ if(!stereomode && opthrtf)
+ {
+ auto mode = *opthrtf ? StereoEncoding::Hrtf : StereoEncoding::Normal;
+ stereomode = al::make_optional(mode);
+ }
+
if(loopback)
{
device->Frequency = freq;
@@ -1758,7 +1764,7 @@ ALCenum UpdateDeviceParams(ALCdevice *device, const int *attrList)
device->DitherSeed = DitherRNGSeed;
/*************************************************************************
- * Update device format request if HRTF is requested
+ * Update device format request if HRTF or UHJ is requested
*/
device->mHrtfStatus = ALC_HRTF_DISABLED_SOFT;
if(device->Type != DeviceType::Loopback)
@@ -1767,15 +1773,18 @@ ALCenum UpdateDeviceParams(ALCdevice *device, const int *attrList)
{
const char *hrtf{hrtfopt->c_str()};
if(al::strcasecmp(hrtf, "true") == 0)
- hrtfreq = al::make_optional(true);
+ stereomode = al::make_optional(StereoEncoding::Hrtf);
else if(al::strcasecmp(hrtf, "false") == 0)
- hrtfreq = al::make_optional(false);
+ {
+ if(!stereomode || *stereomode == StereoEncoding::Hrtf)
+ stereomode = al::make_optional(StereoEncoding::Normal);
+ }
else if(al::strcasecmp(hrtf, "auto") != 0)
ERR("Unexpected hrtf value: %s\n", hrtf);
}
- /* If the app or user wants HRTF, try to set stereo playback. */
- if(hrtfreq && hrtfreq.value())
+ /* If the app or user wants HRTF or UHJ, try to set stereo playback. */
+ if(stereomode && *stereomode != StereoEncoding::Normal)
{
device->FmtChans = DevFmtStereo;
device->Flags.set(ChannelsRequest);
@@ -1852,16 +1861,18 @@ ALCenum UpdateDeviceParams(ALCdevice *device, const int *attrList)
if(auto encopt = device->configValue<std::string>(nullptr, "stereo-encoding"))
{
const char *mode{encopt->c_str()};
- if(al::strcasecmp(mode, "uhj") == 0)
- uhjreq = al::make_optional(true);
- else if(al::strcasecmp(mode, "panpot") == 0)
- uhjreq = al::make_optional(false);
+ if(al::strcasecmp(mode, "panpot") == 0)
+ stereomode = al::make_optional(StereoEncoding::Normal);
+ else if(al::strcasecmp(mode, "uhj") == 0)
+ stereomode = al::make_optional(StereoEncoding::Uhj);
+ else if(al::strcasecmp(mode, "hrtf") == 0)
+ stereomode = al::make_optional(StereoEncoding::Hrtf);
else
ERR("Unexpected stereo-encoding: %s\n", mode);
}
}
- aluInitRenderer(device, hrtf_id, hrtfreq, uhjreq.value_or(false));
+ aluInitRenderer(device, hrtf_id, stereomode);
device->NumAuxSends = new_sends;
TRACE("Max sources: %d (%d + %d), effect slots: %d, sends: %d\n",
diff --git a/alc/alu.h b/alc/alu.h
index addf6942..7b92bba1 100644
--- a/alc/alu.h
+++ b/alc/alu.h
@@ -7,6 +7,8 @@ struct ALCcontext;
struct ALCdevice;
struct EffectSlot;
+enum class StereoEncoding : unsigned char;
+
constexpr float GainMixMax{1000.0f}; /* +60dB */
@@ -20,7 +22,7 @@ void aluInit(void);
* Set up the appropriate panning method and mixing method given the device
* properties.
*/
-void aluInitRenderer(ALCdevice *device, int hrtf_id, al::optional<bool> hrtfreq, bool useuhj);
+void aluInitRenderer(ALCdevice *device, int hrtf_id, al::optional<StereoEncoding> stereomode);
void aluInitEffectPanning(EffectSlot *slot, ALCcontext *context);
diff --git a/alc/panning.cpp b/alc/panning.cpp
index 151e86e8..83b6716d 100644
--- a/alc/panning.cpp
+++ b/alc/panning.cpp
@@ -822,7 +822,7 @@ void InitUhjPanning(ALCdevice *device)
} // namespace
-void aluInitRenderer(ALCdevice *device, int hrtf_id, al::optional<bool> hrtfreq, bool useuhj)
+void aluInitRenderer(ALCdevice *device, int hrtf_id, al::optional<StereoEncoding> stereomode)
{
/* Hold the HRTF the device last used, in case it's used again. */
HrtfStorePtr old_hrtf{std::move(device->mHrtf)};
@@ -837,7 +837,7 @@ void aluInitRenderer(ALCdevice *device, int hrtf_id, al::optional<bool> hrtfreq,
if(device->FmtChans != DevFmtStereo)
{
old_hrtf = nullptr;
- if(hrtfreq && hrtfreq.value())
+ if(stereomode && *stereomode == StereoEncoding::Hrtf)
device->mHrtfStatus = ALC_HRTF_UNSUPPORTED_FORMAT_SOFT;
const char *layout{nullptr};
@@ -925,7 +925,8 @@ void aluInitRenderer(ALCdevice *device, int hrtf_id, al::optional<bool> hrtfreq,
/* If there's no request for HRTF or UHJ and the device is headphones, or
* if HRTF is explicitly requested, try to enable it.
*/
- if((!hrtfreq && !useuhj && device->Flags.test(DirectEar)) || hrtfreq.value_or(false))
+ if((!stereomode && device->Flags.test(DirectEar))
+ || (stereomode && *stereomode == StereoEncoding::Hrtf))
{
if(device->mHrtfList.empty())
device->enumerateHrtfs();
@@ -973,7 +974,7 @@ void aluInitRenderer(ALCdevice *device, int hrtf_id, al::optional<bool> hrtfreq,
}
old_hrtf = nullptr;
- if(useuhj)
+ if(stereomode && *stereomode == StereoEncoding::Uhj)
{
device->mUhjEncoder = std::make_unique<UhjEncoder>();
TRACE("UHJ enabled\n");
diff --git a/core/device.h b/core/device.h
index 5e2a3bfd..88d146aa 100644
--- a/core/device.h
+++ b/core/device.h
@@ -57,6 +57,12 @@ enum class RenderMode : unsigned char {
Hrtf
};
+enum class StereoEncoding : unsigned char {
+ Normal,
+ Uhj,
+ Hrtf
+};
+
struct InputRemixMap {
struct TargetMix { Channel channel; float mix; };