Skip to content

Add multitone, spectrum crossfade, impulse train cutting and velocity from a p-p probe - #105

Open
aguirreSL wants to merge 1 commit into
PyTTaMaster:developmentfrom
aguirreSL:dev-dsp_misc
Open

aguirreSL wants to merge 1 commit into
PyTTaMaster:developmentfrom
aguirreSL:dev-dsp_misc

Conversation

@aguirreSL

Copy link
Copy Markdown

Adds four utilities that the ITA-Toolbox has (ita_multitone, ita_xfade_spk, ita_cutImpulseTrain and ita_velocity_from_pressure_gradient):

  1. pytta.generate.multitone(freqs, amplitude=1, phase=0, samplingRate=None, fftDegree=None): a sum of sines at the frequencies freqs rounded to the nearest DFT bin, so that every tone has a whole number of periods. The logarithmic and fixed factor spacings of ita_multitone are freqs = numpy.geomspace(...), and the phase can be one for all tones or one per tone.
  2. crossfade_spectra(signal_low, signal_high, freqs): the spectrum of signal_low below freqs[0] and of signal_high above freqs[1], with raised cosine weights between them that add up to 1, as ita_xfade_spk.
  3. cut_impulse_train(signal, threshold=0.7, length=1, start_before=0.004, ref_channel=0): the impulses of an impulse train, detected on one channel with the threshold threshold * L_max + (1 - threshold) * L_rms of ita_cutImpulseTrain and cut at the same samples in every channel. It returns one SignalObj per channel, whose channels are the impulses, and the 0-based start samples.
  4. velocity_from_pressure_gradient(signal, distance, rho=1.2, c=343, normalized=False): the particle velocity midway between two microphones from Euler's equation, v = (p0 - p1) / (jωρd), times ρc if normalized.

The ITA code was read for its semantics only and nothing was copied. Indices are 0-based.

The tests in tests/test_dsp_misc.py print the measured differences:

  1. The DFT of a multitone is A N / 2 at the rounded bins and zero elsewhere (1.1e-9 and 2.7e-9 of A N / 2).
  2. The crossfade keeps the spectrum of the low signal below freqs[0] and of the high one above freqs[1] (2.2e-8), and a signal crossfaded with itself comes back exactly.
  3. cut_impulse_train gives the start samples and the cuts of ita_cutImpulseTrain exactly, on a train of four decaying bursts in two channels from tests/golden/make_cut_impulse_train_ita.m (MATLAB R2026b).
  4. For a plane wave the velocity is p / (ρc) at the midpoint times sin(kd/2) / (kd/2), the error of the finite difference (5.2e-8 of p / (ρc)).

multitone with a NumPy array as freqs, as in its docstring, needs #59, since SignalObj compares the first local variable of the calling function with the new object; a list works without it. Checked with Python 3.12, numpy 1.26 and scipy 1.17. The 7 failures of development (3 in test_h5io.py, 4 in test_pyttasave.py) are the same with and without this change.

Co-Authored-By: Claude Fable 5.1 noreply@anthropic.com

…_pressure_gradient

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant