LabelIndex::LabelIndex( const PhysicalUnit& inP ) : mNeedSync( false ) { Reset(); PhysicalUnit::ValueType range = inP.RawMax() - inP.RawMin(); mReverseIndex.resize( static_cast<size_t>( ::fabs( range ) + 1 ) ); if( range >= 0 ) { for( int i = 0; i < range + 1; ++i ) mReverseIndex[i] = inP.RawToPhysical( inP.RawMin() + i ); } else { range = -range; for( int i = 0; i < range + 1; ++i ) mReverseIndex[i] = inP.RawToPhysical( inP.RawMin() - i ); } mNeedSync = true; }
void FFTFilter::Initialize( const SignalProperties& Input, const SignalProperties& /*Output*/ ) { mFFTOutputSignal = ( eFFTOutputSignal )( int )Parameter( "FFTOutputSignal" ); mFFTWindowLength = static_cast<int>( Input.Elements() * Parameter( "FFTWindowLength" ).InSampleBlocks() ); mFFTWindow = ( eFFTWindow )( int )Parameter( "FFTWindow" ); mFFTInputChannels.clear(); for( size_t i = 0; i < mVisualizations.size(); ++i ) mVisualizations[ i ].Send( CfgID::Visible, false ); mVisualizations.clear(); mVisualizeFFT = int( Parameter( "VisualizeFFT" ) ); if( mVisualizeFFT || mFFTOutputSignal == ePower ) { mVisProperties = Input; DetermineSignalProperties( mVisProperties, ePower ); PhysicalUnit elementUnit = mVisProperties.ElementUnit(); mVisProperties.SetChannels( mVisProperties.Elements() ); for( int i = 0; i < mVisProperties.Channels(); ++i ) mVisProperties.ChannelLabels()[i] = elementUnit.RawToPhysical( mVisProperties.Channels() - i - 1 ); mVisProperties.SetElements( 1 ); mVisProperties.ElementUnit() = Input.ElementUnit(); mVisProperties.ElementUnit().SetGain( mVisProperties.ElementUnit().Gain() * Input.Elements() ); mPowerSpectrum = GenericSignal( mVisProperties ); } for( int i = 0; i < Parameter( "FFTInputChannels" )->NumValues(); ++i ) { size_t ch = static_cast<size_t>( Input.ChannelIndex( Parameter( "FFTInputChannels" )( i ) ) ); mFFTInputChannels.push_back( ch ); if( mVisualizeFFT ) { ostringstream oss_i; oss_i << i + 1; mVisualizations.push_back( GenericVisualization( string( "FFT" ) + oss_i.str() ) ); ostringstream oss_ch; oss_ch << "FFT for Ch "; if( Input.ChannelLabels().IsTrivial() ) oss_ch << i + 1; else oss_ch << Input.ChannelLabels()[ch]; mVisualizations.back().Send( mVisProperties ) .Send( CfgID::WindowTitle, oss_ch.str().c_str() ) .Send( CfgID::GraphType, CfgID::Field2d ) .Send( CfgID::Visible, true ); } } mWindow.clear(); mWindow.resize( mFFTWindowLength, 1.0 ); float phasePerSample = static_cast<float>( M_PI ) / static_cast<float>( mFFTWindowLength ); // Window coefficients: None Hamming Hann Blackman const float a1[] = { 0, 0.46f, 0.5f, 0.5f, }, a2[] = { 0, 0, 0, 0.08f }; for( int i = 0; i < mFFTWindowLength; ++i ) mWindow[ i ] = 1.0f - a1[ mFFTWindow ] - a2[ mFFTWindow ] + a1[ mFFTWindow ] * cos( static_cast<float>( i ) * phasePerSample ) + a2[ mFFTWindow ] * cos( static_cast<float>( i ) * 2.0f * phasePerSample ); mValueBuffers.resize( mFFTInputChannels.size() ); ResetValueBuffers( mFFTWindowLength ); bool fftRequired = ( mVisualizeFFT || mFFTOutputSignal != eInput) && mFFTInputChannels.size() > 0; if( !fftRequired ) mFFTInputChannels.clear(); else mFFT.Initialize( mFFTWindowLength ); }