I'm trying to calibrate an ultrasonic speaker with the aim of emitting predictable signals, but alas I keep running into trouble, probably due to my lack of DSP-fu.
A little background
I want to be able to playback sounds as close as possible to a calibrated recording I have. As far as I understand the theory, I need to find the speakers transfer function and deconvolve the signals I want to emit with it. Something like this (in the frequency domain):
X -> H -> XH
Where X
is the emitted signal H
is the speakers transfer function and XH
is X
times H
. A division (./
) should now give me H
.
Now, in order to emit a calibrated signal, it should be divided by H
:
X/H -> H -> X
What's been done
- Placed speaker and a calibrated microphone 1 m apart on tripods.
- Recorded 30+ linear sweeps 150KHz-20KHz, 20ms long, and recorded @ 500 KS/s.
- Aligned and averaged signals with the Matlab/Octave script below, under the script the resulting signal can be seen.
files = dir('Mandag*');
rng = [1.5e6, 1.52e6];
[X, fs] = wavread(files(1).name, rng);
X = X(:,1);
for i=2:length(files)
[Y, fs] = wavread(files(i).name, rng);
sig = Y(:,1);
[x, off] = max(xcorr(X', sig'));
off = length(X) - off;
if(off < 0)
sig = [zeros(1, -off), sig(1:end+off)'];
elseif (off > 0)
sig = [sig(off:end)', zeros(1, off-1)];
end
X = X + sig';
end
X = X/length(files);
Fourier transformed
X
andXH
and did the calculations mentioned above, the result looks plausible. Below is a normalized plot ofH
(purple) andX/H
(green).
The plot has been truncated to the relevant frequencies.
Please let me know if I'm going about this the wrong way.
My question
After calculating X/H
I need to transform it back to the time domain, I assumed this would be a simple ifft(X./H)
and wavwrite
, but all my attempts so far have failed to get any plausible answer. A frequency vector Hf
, H
, and X
can be found here in mat7-binary format.
Maybe I'm just tired and there is a simple solution here, but at the moment I can't see it. Any help/advice is much appreciated.