aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChris Robinson <[email protected]>2014-11-24 01:53:45 -0800
committerChris Robinson <[email protected]>2014-11-24 01:53:45 -0800
commitd6ebf5d1b6450c53b6ad781d31f54f2e608729ca (patch)
tree8eed78a9b2e69259e1398257460910b20e22539c
parent13608d4d61884a21ca5790b22fa121c2359253ed (diff)
Make CalcHrtfDelta more generic
-rw-r--r--Alc/ALu.c43
-rw-r--r--Alc/hrtf.c35
-rw-r--r--Alc/hrtf.h1
3 files changed, 40 insertions, 39 deletions
diff --git a/Alc/ALu.c b/Alc/ALu.c
index 85948084..51148b9d 100644
--- a/Alc/ALu.c
+++ b/Alc/ALu.c
@@ -137,6 +137,42 @@ static inline ALvoid aluMatrixVector(ALfloat *vector, ALfloat w, ALfloat (*restr
}
+/* Calculates the fade time from the changes in gain and listener to source
+ * angle between updates. The result is a the time, in seconds, for the
+ * transition to complete.
+ */
+static ALfloat CalcFadeTime(ALfloat oldGain, ALfloat newGain, const ALfloat olddir[3], const ALfloat newdir[3])
+{
+ ALfloat gainChange, angleChange, change;
+
+ /* Calculate the normalized dB gain change. */
+ newGain = maxf(newGain, 0.0001f);
+ oldGain = maxf(oldGain, 0.0001f);
+ gainChange = fabsf(log10f(newGain / oldGain) / log10f(0.0001f));
+
+ /* Calculate the angle change only when there is enough gain to notice it. */
+ angleChange = 0.0f;
+ if(gainChange > 0.0001f || newGain > 0.0001f)
+ {
+ /* No angle change when the directions are equal or degenerate (when
+ * both have zero length).
+ */
+ if(newdir[0] != olddir[0] || newdir[1] != olddir[1] || newdir[2] != olddir[2])
+ {
+ ALfloat dotp = aluDotproduct(olddir, newdir);
+ angleChange = acosf(clampf(dotp, -1.0f, 1.0f)) / F_PI;
+ }
+ }
+
+ /* Use the largest of the two changes, and apply a significance shaping
+ * function to it. The result is then scaled to cover a 15ms transition
+ * range.
+ */
+ change = maxf(angleChange * 25.0f, gainChange) * 2.0f;
+ return minf(change, 1.0f) * 0.015f;
+}
+
+
static void UpdateDryStepping(DirectParams *params, ALuint num_chans)
{
ALuint i, j;
@@ -997,12 +1033,11 @@ ALvoid CalcSourceParams(ALvoice *voice, const ALsource *ALSource, const ALCconte
/* Check to see if the HRIR is already moving. */
if(voice->Direct.Moving)
{
- /* Calculate the normalized HRTF transition factor (delta). */
- delta = CalcHrtfDelta(voice->Direct.LastGain, DryGain,
- voice->Direct.LastDir, Position);
+ delta = CalcFadeTime(voice->Direct.LastGain, DryGain,
+ voice->Direct.LastDir, Position);
/* If the delta is large enough, get the moving HRIR target
* coefficients, target delays, steppping values, and counter. */
- if(delta > 0.001f)
+ if(delta > 0.000015f)
{
ALuint counter = GetMovingHrtfCoeffs(Device->Hrtf,
ev, az, dirfact, DryGain, delta, voice->Direct.Counter,
diff --git a/Alc/hrtf.c b/Alc/hrtf.c
index 8561902e..54e16cc7 100644
--- a/Alc/hrtf.c
+++ b/Alc/hrtf.c
@@ -88,39 +88,6 @@ static void CalcAzIndices(ALuint azcount, ALfloat az, ALuint *azidx, ALfloat *az
*azmu = az - floorf(az);
}
-/* Calculates the normalized HRTF transition factor (delta) from the changes
- * in gain and listener to source angle between updates. The result is a
- * normalized delta factor that can be used to calculate moving HRIR stepping
- * values.
- */
-ALfloat CalcHrtfDelta(ALfloat oldGain, ALfloat newGain, const ALfloat olddir[3], const ALfloat newdir[3])
-{
- ALfloat gainChange, angleChange, change;
-
- // Calculate the normalized dB gain change.
- newGain = maxf(newGain, 0.0001f);
- oldGain = maxf(oldGain, 0.0001f);
- gainChange = fabsf(log10f(newGain / oldGain) / log10f(0.0001f));
-
- // Calculate the angle change only when there is enough gain to notice it.
- angleChange = 0.0f;
- if(gainChange > 0.0001f || newGain > 0.0001f)
- {
- // No angle change when the directions are equal or degenerate (when
- // both have zero length).
- if(newdir[0] != olddir[0] || newdir[1] != olddir[1] || newdir[2] != olddir[2])
- {
- ALfloat dotp = olddir[0]*newdir[0] + olddir[1]*newdir[1] + olddir[2]*newdir[2];
- angleChange = acosf(clampf(dotp, -1.0f, 1.0f)) / F_PI;
- }
- }
-
- // Use the largest of the two changes for the delta factor, and apply a
- // significance shaping function to it.
- change = maxf(angleChange * 25.0f, gainChange) * 2.0f;
- return minf(change, 1.0f);
-}
-
/* Calculates static HRIR coefficients and delays for the given polar
* elevation and azimuth in radians. Linear interpolation is used to
* increase the apparent resolution of the HRIR data set. The coefficients
@@ -246,7 +213,7 @@ ALuint GetMovingHrtfCoeffs(const struct Hrtf *Hrtf, ALfloat elevation, ALfloat a
}
// Calculate the stepping parameters.
- steps = maxf(floorf(delta*(Hrtf->sampleRate*0.015f) + 0.5f), 1.0f);
+ steps = maxf(floorf(delta*Hrtf->sampleRate + 0.5f), 1.0f);
delta = 1.0f / steps;
/* Calculate 4 blending weights for 2D bilinear interpolation. */
diff --git a/Alc/hrtf.h b/Alc/hrtf.h
index 938bf552..3eaa4e28 100644
--- a/Alc/hrtf.h
+++ b/Alc/hrtf.h
@@ -21,7 +21,6 @@ ALCboolean FindHrtfFormat(enum DevFmtChannels *chans, ALCuint *srate);
void FreeHrtfs(void);
ALuint GetHrtfIrSize(const struct Hrtf *Hrtf);
-ALfloat CalcHrtfDelta(ALfloat oldGain, ALfloat newGain, const ALfloat olddir[3], const ALfloat newdir[3]);
void GetLerpedHrtfCoeffs(const struct Hrtf *Hrtf, ALfloat elevation, ALfloat azimuth, ALfloat dirfact, ALfloat gain, ALfloat (*coeffs)[2], ALuint *delays);
ALuint GetMovingHrtfCoeffs(const struct Hrtf *Hrtf, ALfloat elevation, ALfloat azimuth, ALfloat dirfact, ALfloat gain, ALfloat delta, ALint counter, ALfloat (*coeffs)[2], ALuint *delays, ALfloat (*coeffStep)[2], ALint *delayStep);