Search code examples
python-3.xwavelet

How to translate cwt time scale to actual scale


I converted a 1sec audio file to a morlet wavelet using this code:

import matplotlib.pyplot as plt
import soundfile as sf
import skimage.io
from scipy import signal
from scipy.io import wavfile
import numpy as np
from ssqueezepy import cwt
from ssqueezepy.visuals import plot, imshow

[data1, sample_rate1] = sf.read(input_file)
duration = len(data1)/sample_rate1

time = np.arange(0, duration, 1/sample_rate1) #time vector
            

Wx, scales = cwt(data1, 'morlet')
Wx = abs(Wx) # remove complex component
imshow(Wx,  abs=1)

However, I get the x-axis being shown in the thousands....how does the actual time correspond to the x-axis being generated by the ssqueezepy cwt code? Here is my plot of my 1sec audio file:

enter image description here


Solution

  • The reason why you get the x-axis values in the thousands is because this is the actual number of samples in your array.

    You are dealing with a 1-second signal, sampled at 96,000 Hz: therefore, you end up with 96,000 samples.

    If you want to display the actual time in seconds on the abcissa, you may use the extent argument in imshow as outlined in this SO post. You may also want to display the actual scales returned by the cwt function on the y-axis:

    SR = 96000
    number_of_samples_in_array = 96000
    time_samples = np.linspace(0, number_of_samples_in_array/SR, SR)
    imshow(Wx,abs=1,extent=[time_samples[0], time_samples[-1],scales[0],scales[-1]])
    

    I ran this snippet on an 3-seconds wav file sampled at 22050 Hz (CantinaBand3.wav available here) and this is what I get:

    enter image description here

    Note how the scales go up all the way to the Nyquist frequency (11,025 Hz). In your case, the y-axis should go from 0 to 48,000 Hz.