Exemplo n.º 1
0
Arquivo: DFT.cpp Projeto: LuaAV/LuaAV
void STFT::inverse(float * dst){
	//printf("STFT::inverse(float *)\n");
	if(Bin::MagFreq == mSpctFormat){
		//mem::copy(bins1(), mPhases, numBins()); // not correct, need to unwrap frequencies
		for(uint32_t i=1; i<numBins()-1; ++i) bins()[i] = mPhases[i];
	}	
	
	DFT::inverse(0);	// result goes into mBuf
	
	// undo zero-phase windowing rotation?
	if(mRotateForward) mem::rotateHalf(mBuf, sizeWin());
	
	// apply secondary window to smooth ends?
	if(mWindowInverse){
		arr::mulBartlett(mBuf, sizeWin());
	}

	if(overlapping()){	//inverse windows overlap?
	
		// scale inverse so overlap-add is normalized
		//arr::mul(mBuf, gen::val(mInvWinMul), sizeWin());
		slice(mBuf, sizeWin()) *= mInvWinMul;
	
		// shift old output left while adding new output
		arr::add(mBufInv, mBuf, mBufInv + sizeHop(), sizeWin() - sizeHop());
	}

	// copy remaining non-overlapped portion of new output
	uint32_t sizeOverlap = sizeWin() - sizeHop();
	mem::deepCopy(mBufInv + sizeOverlap, mBuf + sizeOverlap, sizeHop());

	// copy output if external buffer provided
	if(dst) mem::deepCopy(dst, mBufInv, sizeWin());	
}
Exemplo n.º 2
0
void STFT::inverse(float * dst){
	//printf("STFT::inverse(float *)\n");
	if(MAG_FREQ == mSpctFormat){
		// 2pi / hopRate: converts Hz to phase diff in radians
		double factor = M_2PI * unitsHop();

		// 2pi / overlap: expected phase diff of fundamental due to overlap
		double expdp1 = double(sizeHop())/sizeWin() * M_2PI;
		double fund = binFreq();

		for(unsigned k=1; k<numBins()-1; ++k){
			double t = bin(k)[1];		// freq
			t -= k*fund;				// freq to freq deviation
			t *= factor;				// freq deviation to phase diff
			t += k*expdp1;				// add expected phase diff due to overlap
			mAccums[k] += t;			// accumulate phase diff
			//bin(k)[1] = mAccums[k];		// copy accum phase for inverse xfm
			bufInvFrq()[2*k] = bin(k)[0];
			bufInvFrq()[2*k+1] = mAccums[k];
		}

		bufInvFrq()[0] = bin(0)[0];
		bufInvFrq()[2*(numBins()-1)] = bin(numBins()-1)[0];
	}

	DFT::inverse();	// result goes into bufInvPos()

	// undo zero-phase windowing rotation?
	if(mRotateForward) mem::rotateRight(sizeWin()/2, bufInvPos(), sizeDFT());

	// apply secondary window to smooth ends?
	if(mWindowInverse){
		arr::mulBartlett(bufInvPos(), sizeWin());
	}

	if(overlapping()){	//inverse windows overlap?

		// scale inverse so overlap-add is normalized
		for(unsigned i=0; i<sizeWin(); ++i){
			bufInvPos()[i] *= mInvWinMul;
		}

		// shift old output left while adding new output
		arr::add(mBufInv, bufInvPos(), mBufInv + sizeHop(), sizeWin() - sizeHop());
	}

	// copy remaining non-overlapped portion of new output
	unsigned sizeOverlap = sizeWin() - sizeHop();
	mem::deepCopy(mBufInv + sizeOverlap, bufInvPos() + sizeOverlap, sizeHop());

	// copy output if external buffer provided
	if(dst) mem::deepCopy(dst, mBufInv, sizeWin());	
}
Exemplo n.º 3
0
Arquivo: DFT.cpp Projeto: LuaAV/LuaAV
// input is sizeWin
void STFT::forward(float * input){ //printf("STFT::forward(float *)\n");

	arr::mul(input, mFwdWin, sizeWin());	// apply forward window
	if(mRotateForward) mem::rotateHalf(input, sizeWin()); // do zero-phase windowing rotation?
	DFT::forward(input);					// do forward transform
	
	// compute frequency estimates?
	if(Bin::MagFreq == mSpctFormat){
		
		// This will effectively subtract the expected phase difference from the computed.
		// This extra step seems to give more precise frequency estimates.
		slice(mPhases, numBins()) += float(M_2PI * sizeHop()) / sizeDFT();
		
		// compute relative frequencies
		//arr::phaseToFreq(phs, mPhases, numBins(), unitsHop());
		float factor = 1.f / (M_2PI * unitsHop());
		for(uint32_t i=1; i<numBins()-1; ++i){
			float dp = scl::wrapPhase(bins()[i][1] - mPhases[i]);	// wrap phase into [-pi, pi)
			mPhases[i] = bins()[i][1];							// prev phase = curr phase
			bins()[i][1] = dp*factor;
		}
		
		// compute absolute frequencies by adding respective bin center frequency
		slice(mBuf, numBins(), 2) += gen::RAdd<float>(binFreq());
	}
}
Exemplo n.º 4
0
STFT::STFT(unsigned winSize, unsigned hopSize, unsigned padSize, WindowType winType, SpectralType specType, unsigned numAuxA)
:	DFT(0, 0, specType, numAuxA),
	mSlide(winSize, hopSize), mFwdWin(0), mPhases(0), mAccums(0),
	mWinType(winType),
	mWindowInverse(true), mRotateForward(false)
{
	mBufInv = 0;
	resize(winSize, padSize);
	sizeHop(hopSize);
}
Exemplo n.º 5
0
Arquivo: DFT.cpp Projeto: LuaAV/LuaAV
STFT::STFT(uint32_t winSize, uint32_t hopSize, uint32_t padSize, WinType::type windowType, Bin::t binT, uint32_t numAuxA) :
	DFT(0, 0, binT, numAuxA),
	mSlide(winSize, hopSize), mFwdWin(0), mPhases(0),
	mWinType(windowType),
	mWindowInverse(true), mRotateForward(false)
{
	mBufInv = 0;
	resize(winSize, padSize);
	sizeHop(hopSize);
}
Exemplo n.º 6
0
void STFT::inverse(float * dst){
	//printf("STFT::inverse(float *)\n");
	if(MAG_FREQ == mSpctFormat){
		// TODO:
		for(uint32_t i=1; i<numBins()-1; ++i) bin(i)[1] = mPhases[i];
	}	
	
	DFT::inverse(0);	// result goes into bufPos()
	
	// undo zero-phase windowing rotation?
	if(mRotateForward) mem::rotateHalf(bufPos(), sizeWin());

	// apply secondary window to smooth ends?
	if(mWindowInverse){
		arr::mulBartlett(bufPos(), sizeWin());
	}

	if(overlapping()){	//inverse windows overlap?
	
		// scale inverse so overlap-add is normalized
		//slice(mBuf, sizeWin()) *= mInvWinMul;
		for(unsigned i=0; i<sizeWin(); ++i){
			bufPos()[i] *= mInvWinMul;
		}
	
		// shift old output left while adding new output
		arr::add(mBufInv, bufPos(), mBufInv + sizeHop(), sizeWin() - sizeHop());
	}

	// copy remaining non-overlapped portion of new output
	uint32_t sizeOverlap = sizeWin() - sizeHop();
	mem::deepCopy(mBufInv + sizeOverlap, bufPos() + sizeOverlap, sizeHop());

	// copy output if external buffer provided
	if(dst) mem::deepCopy(dst, mBufInv, sizeWin());	
}
Exemplo n.º 7
0
Arquivo: DFT.cpp Projeto: LuaAV/LuaAV
void STFT::computeInvWinMul(){

	// compute sum of overlapping elements of forward window
	if(overlapping()){
		float sum = 0.f;
		for(uint32_t i=0; i<sizeWin(); i+=sizeHop()){
			sum += mFwdWin[i] * (mWindowInverse ? scl::bartlett(2*i/(float)sizeWin() - 1.f): 1.f);
		}
		mInvWinMul = 1/sum;
	}
	
	// if no overlap, then do not scale output
	else{
		mInvWinMul = 1;
	}

	//printf("mInvWinMul: %f\n", mInvWinMul);
}
Exemplo n.º 8
0
// input is sizeWin
void STFT::forward(const float * src){ //printf("STFT::forward(float *)\n");

	if(src != bufPos()) mem::deepCopy(bufPos(), src, sizeWin());

	// apply forward window
	arr::mul(bufPos(), mFwdWin, sizeWin());
	
	// do zero-phase windowing rotation?
	if(mRotateForward) mem::rotateHalf(bufPos(), sizeWin());

	DFT::forward(bufPos());
	
	// compute frequency estimates?
	if(MAG_FREQ == mSpctFormat){
		
//		// This will effectively subtract the expected phase difference from the computed.
//		// This extra step seems to give more precise frequency estimates.
//		{
//			float expdp = float(M_2PI * sizeHop()) / sizeDFT();
//			for(uint32_t i=0; i<numBins(); ++i){
//				mPhases[i] += expdp;
//			}
//		}
		
		// compute frequency estimates
		float factor = 1.f / (M_2PI * unitsHop()); // converts phase difference from radians to Hz
		
		// expected phase difference of fundamental
		float expdp1 = float(sizeHop())/sizeWin() * M_2PI;

		for(uint32_t i=1; i<numBins()-1; ++i){
			float ph = bin(i)[1];						// current phase
			float dp = ph - mPhases[i] - i*expdp1;		// compute phase difference
			dp = scl::wrapPhase(dp);					// wrap back into [-pi, pi)
			mPhases[i] = ph;							// save current phase
			bin(i)[1] = dp*factor;						// convert phase diff to freq
		}
		
		// compute absolute frequencies by adding respective bin center frequency
		for(uint32_t i=0; i<numBins(); ++i){
			bins()[i][1] += binFreq()*i;
		}
	}
}
Exemplo n.º 9
0
// input is sizeWin
void STFT::forward(const float * src){ //printf("STFT::forward(float *)\n");

	if(src) mem::deepCopy(bufFwdPos(), src, sizeWin());

	// apply forward window
	arr::mul(bufFwdPos(), mFwdWin, sizeWin());
	
	// do zero-phase windowing rotation?
	if(mRotateForward) mem::rotateLeft(sizeWin()/2, bufFwdPos(), sizeDFT());

	DFT::forward();
	
	// compute frequency estimates?
	if(MAG_FREQ == mSpctFormat){

		// hopRate / 2pi: converts phase diff from radians to Hz
		double factor = 1. / (M_2PI * unitsHop());
		
		// 2pi / overlap: expected phase diff of fundamental due to overlap
		double expdp1 = double(sizeHop())/sizeWin() * M_2PI;
		double fund = binFreq();

		bin(0)[1] = 0.;
		bin(numBins()-1)[1] = spu() * 0.5;

		for(unsigned k=1; k<numBins()-1; ++k){
			float ph = bin(k)[1];		// current phase
			double t = ph - mPhases[k];	// compute phase diff
			mPhases[k] = ph;			// save current phase
			t -= k*expdp1;				// subtract expected phase diff due to overlap
			t = scl::wrapPhase(t);		// wrap back into [-pi, pi)
			t *= factor;				// convert phase diff to freq deviation
			t += k*fund;				// freq deviation to freq
			bin(k)[1] = t;
		}
	}
}
Exemplo n.º 10
0
// The principle here is to configure things so that after the phase
// accumulation step, the synthesis bin phases equal the analysis bin phases.
// To do this, we first zero the phase accumulators and then compute new
// instantaneous frequencies which after conversion yield a phase increment
// equal to the analysis bin phase.
STFT& STFT::resetPhases(){
	mem::deepZero(mAccums, numBins());

	// hopRate / 2pi: converts phase diff from radians to Hz
	double factor = 1. / (M_2PI * unitsHop());

	// 2pi / overlap: expected phase diff of fundamental due to overlap
	double expdp1 = double(sizeHop())/sizeWin() * M_2PI;
	double fund = binFreq();

	bin(0)[1] = 0.;
	bin(numBins()-1)[1] = spu() * 0.5;

	for(unsigned k=1; k<numBins()-1; ++k){
		double t = mPhases[k];		// the phase diff is simply the analysis phase
		t -= k*expdp1;				// subtract expected phase diff due to overlap
		t = scl::wrapPhase(t);		// wrap back into [-pi, pi)
		t *= factor;				// convert phase diff to freq deviation
		t += k*fund;				// freq deviation to freq
		bin(k)[1] = t;
	}

	return *this;
}
Exemplo n.º 11
0
void DFT::print(FILE * f, const char * a){
	fprintf(f, "DFT, Win, Hop: %d, %d, %d samples\n", (int)sizeDFT(), (int)sizeWin(), (int)sizeHop());
	fprintf(f, "# bins:        %d\n", (int)numBins());
	fprintf(f, "Freq res:      %f units/sample\n", freqRes());
	fprintf(f, "Bin freq:      %f units\n", binFreq());
	fprintf(f, "Data format:   %s\n", toString(mSpctFormat));
	fprintf(f, "Precise:       %s\n", mPrecise ? "true" : "false");	
	fprintf(f, "Aux buffers:   %d\n", (int)mNumAux);
	//printf("buf, pad, inv, aux: %p %p %p %p", mBuf, mPadOA, mBufInv, mAux);
	fprintf(f, "%s", a);
}
Exemplo n.º 12
0
Arquivo: DFT.cpp Projeto: LuaAV/LuaAV
void DFT::onResync(double r){
	DFTBase<float>::onResync(r);
	mSyncHop.ups((double)sizeHop() * ups());
	//printf("[%p] hop: %d, ups: %f\n", this, sizeHop(), spu());
}