How to find the exact frequencies from a spectrogram plot?
6 views (last 30 days)
Show older comments
I have a spectrogram plot generated from oscilloscope data. I want to know what the exact frequency is at Maximum intensity. How do I got about extracting this type of information from the spectrogram and accompanying [S,F,T] data.

clear;
close all;
clc;
%% Initialization
struct = readmatrix('filename.csv');
shift = struct(6,2); %Horizontal Offset [s]
samp_interval = struct(2,2); %Sampling interval [s]
Fs = 1/samp_interval; %Sampling frequency [Hz]
total_t = struct(1,2)*samp_interval; %Total sampling time [s]
time = (struct(:,4)-shift)*1e9; %time [ns]
voltage = struct(:,5)*1000; %raw voltage data [V]
%% Highpass filter
high = 3e11;
voltage = highpass(voltage,high,Fs);
%% Spectrogram Setup
nfft = 2^nextpow2(length(voltage)); %FFT size (reduces time domain aliasing)
%Number of frequency samples
nspec = 1024*30; %Number of windows
wind = blackman(nspec); %Reduces side lobes that hide weaker signals
noverlap = nspec/2; %Overlap of windows
%% FFT Computation
freq_fft = (0:(nfft/2-1))*(Fs/nfft);
volt_f = fft(voltage,nfft);
%% Spectrogram
[s,f,t] = spectrogram(voltage ,wind,noverlap,nspec,Fs,'yaxis');
%% Plots
figure(1)
spectrogram(voltage,wind,noverlap,nspec,Fs,'yaxis')
ylim([0 15]); yticks(0:1:15); colormap('jet')
% figure(2)
% plot(freq_fft,abs(volt_f(1:nfft/2)))
% title('Single-Sided Amplitude Spectrum of V(t)')
% xlabel('Frequency (Hz)')
% ylabel('|V(f)|')
% axis tight
Accepted Answer
Mathieu NOE
on 20 Apr 2023
hello
a FFT based method will always give you the result with a frequency resolution that depends on the fft length and sampling rate Fs
df = Fs/nfft , so you cannot get better than this accuracy with a fft approach (yes you could zero padd to increase the resolution but that has also its limits
better do this :
as your signal seems to be a simple tone (sinewave) , why not simply measure the time diffrence between consecutive zero crossing points ? (NB here the x values are obtained by linear interpolation for maximal precision).
also your amplitude does not seem to vary with time , so what do you mean by saying I want to plot the intensity vs time if possible.
would be nice to provide your data
so far , try this
% dummy data
n = 300;
x = 22*(0:n-1)/n;
y = sin(x+0.1*x.^2);
threshold = 0; %
t0_pos1 = find_zc(x,y,threshold);
period = diff(t0_pos1); % delta time of crossing points
freq = 1./period; % signal frequency
figure(1)
subplot(2,1,1),plot(x,y,'b.-',t0_pos1,threshold*ones(size(t0_pos1)),'*r','linewidth',2,'markersize',12);grid on
xlim([x(1) x(end)]);
title('Signal plot');
legend('signal','crossing points');
xlabel('time (s)')
ylabel('Amplitude')
subplot(2,1,2),plot(t0_pos1(2:end),freq,'b.-','linewidth',2,'markersize',12);grid on
xlim([x(1) x(end)]);
title('Signal rate (frequency)');
xlabel('time (s)')
ylabel('Hz')
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function [Zx] = find_zc(x,y,threshold)
% positive slope "zero" crossing detection, using linear interpolation
y = y - threshold;
zci = @(data) find(diff(sign(data))>0); %define function: returns indices of +ZCs
ix=zci(y); %find indices of + zero crossings of x
ZeroX = @(x0,y0,x1,y1) x0 - (y0.*(x0 - x1))./(y0 - y1); % Interpolated x value for Zero-Crossing
Zx = ZeroX(x(ix),y(ix),x(ix+1),y(ix+1));
end
2 Comments
More Answers (0)
See Also
Categories
Find more on Spectral Measurements in Help Center and File Exchange
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!