Aufgrund einer Wartung wird GitLab am 25.01 zwischen 8:00 und 9:00 Uhr kurzzeitig nicht zur Verfügung stehen. / Due to maintenance, GitLab will be temporarily unavailable on 25.01 between 8:00 and 9:00 am.

Commit a70e734b authored by Dipl.-Ing. Jonas Stienen's avatar Dipl.-Ing. Jonas Stienen
Browse files

Intermediate progress on moving dsp elements to ITADSP project

parent 4bc04fe6
Copyright 2015-2016 Institute of Technical Acoustics, RWTH Aachen University
Copyright 2015-2017 Institute of Technical Acoustics, RWTH Aachen University
Any usage and distribution is prohibited, unless explicitly granted by the authors.
\ No newline at end of file
......@@ -3,20 +3,23 @@
VACore implements the core functionality for real-time auralization of virtual environments and sophisticated reproduction of various types. It can be
created using a factory method and exposes the IVACore abstract class methods. Manage the core by the C++ interface (directly or over TCP/IP network in VANet) or via various binding interfaces, i.e. for Matlab (VAMatlab).
### License
Copyright 2015-2016 Institute of Technical Acoustics, RWTH Aachen University. Any usage and distribution is prohibited, unless explicitly granted by the authors.
Copyright 2015-2017 Institute of Technical Acoustics, RWTH Aachen University. Any usage and distribution is prohibited, unless explicitly granted by the authors.
See [License](LICENSE.md) file for more information
### Quick build guide
VACore uses CMake configuration files to create project files for your preferred development environment. It requires the VistaCMakeCommon extension package, which can be downloaded from [devhub.com](http://devhub.com).
Further packages are required, such as the VistaCoreLibs and the ITACoreLibs.
### Additional software
Some applications like the VAServer and the VAGUI are using the VACore to manage the auralization and reproduction. Also, bindings for C++ and Matlab exist, where you can connect to the VACore via network connection.
### Help
VACore is an in-house development of ITA and not for use to anyone else. Help is only provided within projects where ITA is involved.
### Quick build guide
It is recommended to clone and follow the build guide of the parent project [VA](https://git.rwth-aachen.de/ita/VA), which includes this project as a submodule.
......@@ -115,9 +115,11 @@ void GetAirAbsorptionMagnitudes(CVAThirdOctaveMagnitudes& oMags, double dDistanc
}
void CalculateAirAbsorptionAttenuation( CVAThirdOctaveMagnitudes& oAirAbsMags, double dDistance, double dTemperature, double dStaticPressure, double dHumidity )
void CalculateAirAbsorptionAttenuation( CITAThirdOctaveMagnitudeSpectrum& oAirAbsMags, double dDistance, double dTemperature, double dStaticPressure, double dHumidity )
{
GetAirAbsorptionMagnitudesThirdOctave( oAirAbsMags.fGains, dDistance, dTemperature, dStaticPressure, dHumidity );
std::vector< float > vfGains( oAirAbsMags.GetNumBands() );
GetAirAbsorptionMagnitudesThirdOctave( &vfGains[ 0 ], dDistance, dTemperature, dStaticPressure, dHumidity );
oAirAbsMags.SetMagnitudes( vfGains );
return;
}
......
......@@ -2,14 +2,14 @@
*
* VVV VVV A
* VVV VVV AAA Virtual Acoustics
* VVV VVV AAA Real-time auralisation for virtual reality
* VVV VVV AAA Real-time auralisation for virtual reality
* VVV VVV AAA
* VVVVVV AAA (c) Copyright Institut fr Technische Akustik (ITA)
* VVVV AAA RWTH Aachen (http://www.akustik.rwth-aachen.de)
*
* ---------------------------------------------------------------------------------
*
* Datei: VAAtmosphere.h
* Datei: VAAtmosphere.h
*
* Zweck: Atmosphrische Schallausbreitungsmodelle
*
......@@ -17,28 +17,28 @@
*
* ---------------------------------------------------------------------------------
*/
// $Id: VAAtmosphere.h 4095 2015-05-06 12:30:21Z stienen $
#ifndef __VA_ATMOSPHERE__
#define __VA_ATMOSPHERE__
#include "VAThirdOctaveMagnitudes.h"
#include "ITAThirdOctaveMagnitudeSpectrum.h"
//! Luftschall-Dmpfungsfaktoren in Terzen berechnen (nach ISO 9613-1:1993)
// (ACHTUNG: Andere Bedeutung als in Raven: Dmpfungsfaktoren! 1=>Keine Dmpfung)
void GetAirAbsorptionMagnitudesThirdOctave(float* pfAirAbsCoeffs, // Absorptionskoeffizienten [Faktor/m] (nicht Dezibel!)
double dDistance, // Abstand [m]
double dTemperature, // Temperatur [C]
double dPressure, // Statischer Luftdruck [Pa]
double dHumidity); // Luftfeuchtigkeit [%]
void GetAirAbsorptionMagnitudesThirdOctave( float* pfAirAbsCoeffs, // Absorptionskoeffizienten [Faktor/m] (nicht Dezibel!)
double dDistance, // Abstand [m]
double dTemperature, // Temperatur [C]
double dPressure, // Statischer Luftdruck [Pa]
double dHumidity ); // Luftfeuchtigkeit [%]
// In dB/m
void GetAirAbsorptionAttenuationThirdOctaveDecibel(float* pfAirAbsCoeffs, // Absorptionskoeffizienten [Faktor/m] (nicht Dezibel!)
double dDistance, // Abstand [m]
double dTemperature, // Temperatur [C]
double dPressure, // Statischer Luftdruck [Pa]
double dHumidity); // Luftfeuchtigkeit [%]
void GetAirAbsorptionAttenuationThirdOctaveDecibel( float* pfAirAbsCoeffs, // Absorptionskoeffizienten [Faktor/m] (nicht Dezibel!)
double dDistance, // Abstand [m]
double dTemperature, // Temperatur [C]
double dPressure, // Statischer Luftdruck [Pa]
double dHumidity ); // Luftfeuchtigkeit [%]
//! Berechnung der Luftschall-Absorption in Terzen
/**
......@@ -52,7 +52,7 @@ void GetAirAbsorptionAttenuationThirdOctaveDecibel(float* pfAirAbsCoeffs, // Ab
* \param fStaticPressure Statischer Luftdruck [Pa]
* \param fHumidity Luftfeuchtigkeit [%]
*/
void CalculateAirAbsorptionAttenuation( CVAThirdOctaveMagnitudes& oAirAbsMags, double dDistance, double dTemperature, double dStaticPressure, double dHumidity );
void CalculateAirAbsorptionAttenuation( CITAThirdOctaveMagnitudeSpectrum& oAirAbsMags, double dDistance, double dTemperature, double dStaticPressure, double dHumidity );
//! Berechnung der Luftschall-Dmpfung in Terzen als Faktoren (von Jonas implementiert)
/**
......@@ -66,6 +66,6 @@ void CalculateAirAbsorptionAttenuation( CVAThirdOctaveMagnitudes& oAirAbsMags, d
* \param fStaticPressure Statischer Luftdruck [Pa]
* \param fHumidity Luftfeuchtigkeit [%]
*/
void GetAirAbsorptionMagnitudes( CVAThirdOctaveMagnitudes& oMags, double dDistance, double dTemperature, double dStaticPressure, double dHumidity );
void GetAirAbsorptionMagnitudes( CITAThirdOctaveMagnitudeSpectrum& oMags, double dDistance, double dTemperature, double dStaticPressure, double dHumidity );
#endif // __VA_ATMOSPHERE__
This diff is collapsed.
#include "VAThirdOctaveFIRFilterGenerator.h"
#include <ITAConstants.h>
#include <ITAFastMath.h>
#include <ITANumericUtils.h>
#include <ITAStringUtils.h>
#include <spline.h>
// Debug:
#include <iomanip>
#include <iostream>
#include <fstream>
// Debugging flags
#define DUMP_INTERPOLATED_MAGNITUDES 0
CVAThirdOctaveFIRFilterGenerator::CVAThirdOctaveFIRFilterGenerator( double dSamplerate, int iFilterLength )
: m_dSamplerate( dSamplerate )
, m_iFilterLength( iFilterLength )
, m_ypp( nullptr )
, m_pfInputFreqs( nullptr )
, m_pfInputData( nullptr )
, m_pfBuf1( nullptr )
, m_pfBuf2( nullptr )
, m_bWindow( false )
{
m_iInputFreqs = CVAThirdOctaveMagnitudes::nBands + 2;
m_pfInputFreqs = fm_falloc( m_iInputFreqs, true );
m_pfInputFreqs[ 0 ] = 0; // Left margin
for( int i = 0; i < CVAThirdOctaveMagnitudes::nBands; i++ )
m_pfInputFreqs[ i + 1 ] = CVAThirdOctaveMagnitudes::fCenterFreqs[ i ];
m_pfInputFreqs[ m_iInputFreqs - 1 ] = ( float ) dSamplerate / 2; // Right margin: Nyquist frequency
m_pfInputData = fm_falloc( m_iInputFreqs, true );
// DFT frequency bandwidth
m_fDeltaF = ( float ) dSamplerate / ( float ) iFilterLength;
// Number of symetric DFT coefficients;
m_iDFTCoeffs = iFilterLength / 2 + 1;
m_pfBuf1 = fm_falloc( 2 * m_iDFTCoeffs, false );
m_pfBuf2 = fm_falloc( iFilterLength, false );
m_pfWindow = fm_falloc( iFilterLength, false );
// Windowing function (Hann window)
float c = 2 * ITAConstants::PI_F / ( float ) ( m_iFilterLength - 1 );
for( int i = 0; i < m_iFilterLength; i++ )
{
m_pfWindow[ i ] = 0.5F * ( 1 - cos( c*i ) );
}
m_ifft.plan( ITAFFT::IFFT_C2R, iFilterLength, m_pfBuf1, m_pfBuf2 );
m_sDumpFilename = "interpolated_magnitudes.csv";
}
CVAThirdOctaveFIRFilterGenerator::~CVAThirdOctaveFIRFilterGenerator()
{
fm_free( m_pfInputFreqs );
fm_free( m_pfInputData );
fm_free( m_pfBuf1 );
fm_free( m_pfBuf2 );
fm_free( m_pfWindow );
}
int CVAThirdOctaveFIRFilterGenerator::GetFilterLength() const
{
return m_iFilterLength;
}
int CVAThirdOctaveFIRFilterGenerator::GetLatency() const
{
// Latency = Half DFT period (ceil)
return uprdiv( m_iFilterLength, 2 );
}
double CVAThirdOctaveFIRFilterGenerator::GetAverageRuntime() const
{
return m_sw.mean();
}
void CVAThirdOctaveFIRFilterGenerator::SetDumpFilename( const std::string& sFilename )
{
m_sDumpFilename = sFilename;
}
void CVAThirdOctaveFIRFilterGenerator::GenerateFilter( const CVAThirdOctaveMagnitudes& oTOMagnitudes, float* pfFilterCoeffs )
{
m_sw.start();
// [fwe] Intermediate bugfix. Wrong filter for identity
const float EPSILON = 0.001F;
bool bZero = true;
bool bIdent = true;
for( int i = 0; i<CVAThirdOctaveMagnitudes::nBands; i++ )
{
bZero &= ( oTOMagnitudes[ i ] > -EPSILON ) && ( oTOMagnitudes[ i ] < EPSILON );
bIdent &= ( oTOMagnitudes[ i ] > 1 - EPSILON ) && ( oTOMagnitudes[ i ] < 1 + EPSILON );
}
if( bZero )
{
for( int i = 0; i < m_iFilterLength; i++ )
pfFilterCoeffs[ i ] = 0;
return;
}
if( bIdent )
{
for( int i = 0; i < m_iFilterLength; i++ )
pfFilterCoeffs[ i ] = 0;
pfFilterCoeffs[ m_iFilterLength / 2 ] = 1;
return;
}
// 1st step: Interpolate the magnitudes
m_pfInputData[ 0 ] = 1;
memcpy( &m_pfInputData[ 1 ], &oTOMagnitudes.fGains, CVAThirdOctaveMagnitudes::nBands*sizeof( float ) );
m_pfInputData[ m_iInputFreqs - 1 ] = 0;
// Initialize cubic spline interpolation
m_ypp = spline_cubic_set( m_iInputFreqs,
m_pfInputFreqs,
m_pfInputData,
1, // Left boundary condition => 1st derivative m=0
0,
1, // Right boundary condition => 1st derivative m=0
0 );
float fDummy;
float fScale = 1 / ( float ) m_iFilterLength;
// No DC offset, ever!
m_pfBuf1[ 0 ] = 0;
m_pfBuf1[ 1 ] = 0;
#if (DUMP_INTERPOLATED_MAGNITUDES==1)
std::ofstream coeffs_file;
coeffs_file.open(m_sDumpFilename);
coeffs_file << "# 1/3 magnitudes: " << FloatArrayToString(pfThirdOctaveMagnitudes, CVAThirdOctaveMagnitudes::nBands, 3) << std::endl;
coeffs_file << "# Num DFT coeffs: " << m_iDFTCoeffs << std::endl;
coeffs_file << "# DFT bin bandwidth: " << m_fDeltaF << " Hz" << std::endl << std::endl;
#endif
for( int i = 1; i < m_iDFTCoeffs; i++ )
{
float x = spline_cubic_val( m_iInputFreqs,
m_pfInputFreqs,
i*m_fDeltaF,
m_pfInputData,
m_ypp,
&fDummy,
&fDummy );
#if (DUMP_INTERPOLATED_MAGNITUDES==1)
//std::setprecision(12) << std::ios::fixed <<
coeffs_file << (i*m_fDeltaF) << "\t"
<< x << std::endl;
#endif
// Phase-shift by half the FFT-period: Negate all odd DFT coefficients
m_pfBuf1[ 2 * i ] = ( ( i % 2 ) == 0 ) ? x*fScale : -x*fScale;
m_pfBuf1[ 2 * i + 1 ] = 0;
}
#if (DUMP_INTERPOLATED_MAGNITUDES==1)
coeffs_file.close();
#endif
// DEBUG:
//std::cout << FloatArrayToString(m_pfBuf1, m_iDFTCoeffs*2, 3) << std::endl;
// 2nd step: Convert into time-domain (out-of-place C2R-IFFT)
m_ifft.execute();
// 3rd (optional) step: Hann window in the time-domain (optional)
if( m_bWindow )
{
for( int i = 0; i < m_iFilterLength; i++ )
pfFilterCoeffs[ i ] = m_pfBuf2[ i ] * m_pfWindow[ i ];
}
else
{
for( int i = 0; i < m_iFilterLength; i++ )
pfFilterCoeffs[ i ] = m_pfBuf2[ i ];
}
//writeAudiofile()
// TODO: Minimum-phase?
m_sw.stop();
}
/*
* --------------------------------------------------------------------------------------------
*
* VVV VVV A
* VVV VVV AAA Virtual Acoustics (VA)
* VVV VVV AAA Real-time auralisation for virtual reality
* VVV VVV AAA
* VVVVVV AAA (c) Copyright Institute of Technical Acoustics (ITA), 2015-2017
* VVVV AAA RWTH Aachen University (http://www.akustik.rwth-aachen.de)
*
* --------------------------------------------------------------------------------------------
*/
#ifndef IW_VA_THIRDOCTAVE_FIRFILTERGENERATOR
#define IW_VA_THIRDOCTAVE_FIRFILTERGENERATOR
#include "VAThirdOctaveMagnitudes.h"
#include <ITAFFT.h>
#include <ITAStopWatch.h>
#include <string.h>
#include <vector>
/**
* Diese Klasse erzeugt FIR-Filter (Impulsantworten) aus Terzband-Betragsspektren.
* Hierzu wird ein linear-phasiges FIR-Filter mittels Spline-Interpolation erzeugt.
* Die Filter erzeugen eine Latenz der halben Filterlnge.
*/
class CVAThirdOctaveFIRFilterGenerator
{
public:
// Design methods
enum
{
LINEAR_PHASE = 0,
MINIMUM_PHASE
};
// Konstruktor
CVAThirdOctaveFIRFilterGenerator( double dSamplerate, int iFilterLength );
// Destruktor
~CVAThirdOctaveFIRFilterGenerator();
// Filterlnge zurckgeben [Samples]
int GetFilterLength() const;
// Latenz in den Filtern zurckgeben [Samples]
int GetLatency() const;
// Mittlere Laufzeit der Erzeuger-Methode zurckgeben
double GetAverageRuntime() const;
// Dateiname fr Debug-Ausgaben setzen
void SetDumpFilename( const std::string& sFilename );
// Filter erzeugen
void GenerateFilter( const CVAThirdOctaveMagnitudes& oTOMagnitudes, float* pfFilterCoeffs );
private:
double m_dSamplerate; // Abtastrate der Ausgabefilter [Hz]
int m_iFilterLength; // Lnge der Ausgabefilter
int m_iDFTCoeffs; // Anzahl symetrischer DFT-Koeffizienten
float m_fDeltaF; // DFT-Frequenzauflsung [Hz]
int m_iInputFreqs; // Anzahl Frequenzsttzstellen fr Interpolation (31 Terzen + 2 Rnder)
float* m_pfInputFreqs; // Frequenzsttzstellen der Eingabedaten (Terzen)
float* m_pfInputData; // Zwischenspeicher fr die Interpolation
float* m_ypp; // Interpolationsdaten
float* m_pfBuf1;
float* m_pfBuf2;
bool m_bWindow; // Apply window?
float* m_pfWindow;
ITAFFT m_ifft;
std::string m_sDumpFilename;
mutable ITAStopWatch m_sw;
};
#endif // IW_VA_THIRDOCTAVE_FIRFILTERGENERATOR
/*
*
* VVV VVV A
* VVV VVV AAA Virtual Acoustics
* VVV VVV AAA Real-time auralisation for virtual reality
* VVV VVV AAA
* VVVVVV AAA (c) Copyright Institut fr Technische Akustik (ITA)
* VVVV AAA RWTH Aachen (http://www.akustik.rwth-aachen.de)
*
* ---------------------------------------------------------------------------------
*
* Datei: VAThirdOctaveFilterbank.cpp
*
* Zweck: Frontend fr Terzfilterbanken
*
* Autor(en): Frank Wefers (Frank.Wefers@akustik.rwth-aachen.de)
*
* ---------------------------------------------------------------------------------
*/
// $Id: VAThirdOctaveFilterbank.cpp 3629 2014-08-13 12:23:44Z fwefers $
#include "VAThirdOctaveFilterbank.h"
#include "VAThirdOctaveFilterbankFIR.h"
#include "VAThirdOctaveFilterbankIIR.h"
#include <cassert>
CVAThirdOctaveFilterbank* CVAThirdOctaveFilterbank::Create(double dSamplerate,
int iBlocklength,
int iMethod)
{
switch (iMethod) {
case FIR_SPLINE_LINEAR_PHASE:
return new CVAThirdOctaveFilterbankFIR(dSamplerate, iBlocklength);
case IIR_BIQUADS_ORDER10:
return new CVAThirdOctaveFilterbankIIR(dSamplerate, iBlocklength);
default:
assert( false );
return nullptr;
}
}
/*
*
* VVV VVV A
* VVV VVV AAA Virtual Acoustics
* VVV VVV AAA Real-time auralisation for virtual reality
* VVV VVV AAA
* VVVVVV AAA (c) Copyright Institut für Technische Akustik (ITA)
* VVVV AAA RWTH Aachen (http://www.akustik.rwth-aachen.de)
*
* ---------------------------------------------------------------------------------
*
* Datei: VAThirdOctaveFilterbank.h
*
* Zweck: Frontend für Terzfilterbanken
*
* Autor(en): Frank Wefers (Frank.Wefers@akustik.rwth-aachen.de)
*
* ---------------------------------------------------------------------------------
*/
// $Id: VAThirdOctaveFilterbank.h 2999 2012-12-10 09:50:15Z stienen $
#ifndef __VA_THIRDOCTAVEFILTERBANK__
#define __VA_THIRDOCTAVEFILTERBANK__
#include "VAThirdOctaveMagnitudes.h"
//! Terzbandspektrum-Filterbank zur digitalen Filterung
/**
* Diese Oberklasse für Filterbänke, die zur Realisierung der Filterung von Terzbandspektren dient,
* definiert die Schnittstellen zur Nutzung einer solchen Filterbank.
*
* Sie wird durch die Realisierungsmethoden (#FilterbankRealisationMethods) mittels Factory Method
* erstellt und kann dann Eingabesamples im Process()-Schritt filtern.
*
* Die Datensätze der Terzbandspektren werden durch die Klasse \CVAThirdOctaveMagnitues verwaltet.
*
*/
class CVAThirdOctaveFilterbank {
public:
//! Realisierungsmethoden
enum {
FIR_SPLINE_LINEAR_PHASE = 0, //!< Linearphasiges FIR Filter mit Spline-Interpolation
IIR_BIQUADS_ORDER10 //!< Rekursives IIR Filter umgesetzt durch kaskadierte Biquads
} FilterbankRealisationMethods;
//! Factory method zum erzeugen einer Filterbank
/**
* \param dSamplerate Samplingrate
* \param iBlocklength Blockgröße
* \param iMethod Realisierungsmethode, eines von #FilterbankRealisationMethods (default: linearphasiges FIR Filter)
*
* \return Zeiger auf die erzeugte Terzfilterbank
*/
static CVAThirdOctaveFilterbank* Create(double dSamplerate,
int iBlocklength,
int iMethod=FIR_SPLINE_LINEAR_PHASE);
//! Destruktor
virtual ~CVAThirdOctaveFilterbank() {};
//! Idealer Übertrager setzen
/**
* \param bSmoothChangeover Überbenden (default, true) oder direktes Umschalten (false)
*/
virtual void SetIdentity(bool bSmoothChangeover=true) {
CVAThirdOctaveMagnitudes oIdentity;
SetGains(oIdentity, bSmoothChangeover);
};
//! Verstärkungsfaktoren setzen
/**
* \param oGains Neue Verstärkungsfaktoren
* \param bSmoothChangeover Überbenden (default, true) oder direktes Umschalten (false)
*/
virtual void SetGains(const CVAThirdOctaveMagnitudes& oGains, bool bSmoothChangeover=true)=0;
//! Latenz (Verzögerung) der Filterbank zurückgeben
/**
* \return Latenz (Verzögerung) in ganzzahligen Sample
*/
int GetLatency() const;
//! Löscht alle internen Puffer
virtual void Clear()=0;
//! Filtert einen Block Samples (muss die angegebene Blocklänge haben, s.o.)
/**
* \pfInputSamples Eingabesamples (Anzahl = Blocklänge)
* \pfOutputSamples Ausgabesamples (Anzahl = Blocklänge)
*/
virtual void Process(const float* pfInputSamples, float* pfOutputSamples)=0;
protected:
//! Standardkonstruktor (Deaktiviert, FactoryMethod Create() benutzen)
CVAThirdOctaveFilterbank() {};
};
#endif // __VA_THIRDOCTAVEFILTERBANK__
/*
*
* VVV VVV A
* VVV VVV AAA Virtual Acoustics
* VVV VVV AAA Real-time auralisation for virtual reality
* VVV VVV AAA
* VVVVVV AAA (c) Copyright Institut fr Technische Akustik (ITA)
* VVVV AAA RWTH Aachen (http://www.akustik.rwth-aachen.de)
*
* ---------------------------------------------------------------------------------
*
* Datei: VAThirdOctaveFilterbankCoefficients.h
*
* Zweck: Biquad-Parameter fr Terzfilterbanken
*
* Autor(en): Frank Wefers (Frank.Wefers@akustik.rwth-aachen.de)
*
* ---------------------------------------------------------------------------------
*/
// $Id: VAThirdOctaveFilterbankCoefficients.h 3000 2012-12-10 10:19:37Z stienen $
#ifndef __VA_THIRDOCTAVEFILTERBANKCOEFFICIENTS__
#define __VA_THIRDOCTAVEFILTERBANKCOEFFICIENTS__
const double FB_SAMPLINGRATE = 44100; //!< Samplingrate
const int FB_NUM_BANDS = 30; //!< Anzahl Frequenzbnder
const int FB_NUM_BIQUADS_PER_BAND = 5; //!< Anzahl Biquads pro Frequenzband
//!< Parameters (g, b0, b1, b2, a0, a1) for biquad bandpasses, 10th order Buttworth design, Zugriff: [Band][Biquad][Param]
const float FB_BIQUAD_PARAMS[30][5][6] = {
{ // Band 1, center frequency 25.1 Hz
{ 0.000412886359F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999701032925F, 0.999716977654F },
{ 0.000412886359F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999762381947F, 0.999772667553F },
{ 0.000412801159F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999272014143F, 0.999286684169F },
{ 0.000412801159F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999366290299F, 0.999377465320F },
{ 0.000412768629F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999161660004F, 0.999174462741F }
},
{ // Band 2, center frequency 31.6 Hz
{ 0.000519775953F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999618435430F, 0.999643704564F },
{ 0.000519775953F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999697516620F, 0.999713818333F },
{ 0.000519640943F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999078838244F, 0.999102087287F },
{ 0.000519640943F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999198613647F, 0.999216322640F },
{ 0.000519589402F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.998940532405F, 0.998960821195F }
},
{ // Band 3, center frequency 39.8 Hz
{ 0.000654331930F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999511423741F, 0.999551470536F },
{ 0.000654331930F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999613897140F, 0.999639732824F },
{ 0.000654118003F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.998832888172F, 0.998869731376F },
{ 0.000654118003F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.998985439915F, 0.999013503629F },
{ 0.000654036346F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.998659776098F, 0.998691927308F }
},
{ // Band 4, center frequency 50.1 Hz
{ 0.000823711945F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999371902235F, 0.999435368417F },
{ 0.000823711945F, 1.000000000000F, 0.000000000000F, -1.000000000000F, -1.999505526285F, 0.999546471025F },
{ 0.000823372990F, 1.000000000000F