# Why am I not getting the correct Phase angle when doing FFT

16 views (last 30 days)
Aubai on 18 Apr 2018
Answered: Wick on 2 May 2018
Dear All,
I would like to generate a Sine Signal that have the same Phase angle as a given measured Sine signal. in order to do so I tried the following:
- if the input signal (measured voltage for example) is U (nx1), I have calculated the FFT of the input signal as following:
* Calculate FFT on a specific number of cycles (in this example FFT for one period T)
* through a for loop with a step of ts (one index per loop) re-calculate the FFT till the end of the signal.
* After that extract the phase of the fundamental frequency of all calculated FFTs
* Generate a Sine Signal using this phase angle value.
* Compare between both signal measured (original) and the generated Sine Signal
Can any one tell me why am I getting a very small phase different between the generated Sine and the measured one?
My Code looks like this:
Temp.Input.Sig = FamosDaten.U1N(:,2);% Sine wave in pu
Temp.Input.t = FamosDaten.U1N(:,1);% time in sec
Temp.Input.Finit = 50;%in Hz
Temp.Input.Cycle = 1;% number of cycles on which FFT will be calcualted
Temp.Input.Un = 400;% in V L-L
%if rem(length(Temp.Input.Sig),2)
% Temp.Input.Sig = Temp.Input.Sig(1:end-1);
% Temp.Input.t = Temp.Input.t(1:end-1);
%end
Temp.Estimate.ts = mean(diff(Temp.Input.t));
Temp.Estimate.Points = (1/Temp.Input.Finit)/Temp.Estimate.ts;
Temp.Estimate.Periods = length(Temp.Input.Sig)/Temp.Estimate.Points;
FFT.Input.Sig = Temp.Input.Sig;
FFT.Input.t = Temp.Input.t;
FFT.Input.Finit = Temp.Input.Finit;
FFT.Input.Cycle = Temp.Input.Cycle;
FFT.Cal.ts = mean(diff(FFT.Input.t));
FFT.Cal.Points = fix((1/FFT.Input.Finit)/FFT.Cal.ts)*FFT.Input.Cycle;
FFT.Cal.Periods = fix(length(FFT.Input.Sig)/FFT.Cal.Points);
for i = 1:length(FFT.Input.Sig)-FFT.Cal.Points
FFT.Cal.Sig(:,i) = FFT.Input.Sig(i:(i+(FFT.Cal.Points)));
FFT.Cal.t(:,i) = FFT.Input.t(i:(i+(FFT.Cal.Points)));
end
[FFT.Results] = FFT_Final_02032018(FFT.Cal.Sig,FFT.Input.t,FFT.Cal.ts);
Temp.Output.Sine = cos(FFT.Results.Angle);
Temp.Output.Sig = Temp.Input.Sig(1:length(Temp.Output.Sine));
Temp.Output.t = Temp.Input.t(1:length(Temp.Output.Sine));
%%the function FFT_Final_02032018 is doing FFT like this:
%function [Results] = FFT_Final_02032018(data,time,dt)
data = FFT.Cal.Sig;
time = FFT.Input.t;
[r,c] = size(data);
DFT_complex = fft(data,r)/r;
format_DFT = size(DFT_complex);
DFT.amp_inst = [abs(DFT_complex(1,:));abs(2*DFT_complex(2:floor(format_DFT(1)/2)+1,:))];
DFT.alpha = ([angle(zeros(1,format_DFT(2)));angle(DFT_complex(2:floor(format_DFT(1)/2)+1,:))])
Temp.MAX = max(DFT.amp_inst);
DFT.Mag_max_Indx = arrayfun(@(x) find(DFT.amp_inst(:,x) == Temp.MAX(x)), 1:format_DFT(2),'UniformOutput', true);
DFT.Anlage = arrayfun(@(x) DFT.alpha(DFT.Mag_max_Indx(x),x),1:format_DFT(2),'UniformOutput', true);
FFT.Results.Amplitude = DFT.amp_inst;
FFT.Results.Angle = DFT.Anlage;
the results looks like the attached Figure

Wick on 2 May 2018
Without seeing your data I'm guessing you're not measuring the frequency at exactly the frequency the signal was generated at. This line makes me suspicious:
FFT.Cal.Points = fix((1/FFT.Input.Finit)/FFT.Cal.ts)*FFT.Input.Cycle;
That tells me you're not setting the time interval to be exactly the period of the original signal cut into 2^n chunks. Instead, you're building it from "about" the right number of points. So in your DFT you're actually calculating the power and phase at a slightly offset frequency from what the real signal is. So, as per any FFT, there's a spread function where the amplitude will decrease and the phase will slowly change. That explains why both the amplitude and phase of the calculated signal don't match the input.