-
Notifications
You must be signed in to change notification settings - Fork 2
/
Copy pathnormalizePulses.m
91 lines (85 loc) · 3.46 KB
/
normalizePulses.m
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
function pulses = normalizePulses(pulses, signWindow, smoothWindow, upsamplingFactor, restoreFlag, centerFlag, shiftWindow)
% pulses = normalizePulses(pulses, signWindow=[10 0], smoothWindow=15, restoreFlag=true)
% normalizes pulses by 1. dividing by norm, 2. aliging to peak energy (envelope), and 3. flipping sign
%
% ARGS
% pulses - Npulses x Nsamples matrix of pulse shapes
% signWindow - n samples (preceding peak) to use for sign flipping
% smoothWindow - n samples with which to smooth pulse for RMS envelope estimation
% upsamplingFactor - for upsampling pulses - all other params (signWindow, smoothWindow)
% refer to the upsampled scale
% restoreFlag - downsample upsampled and aligned pulses or return upsampled pulses
% centerFlag -
% RETURNS
% normalized pulses
if ~exist('signWindow','var') || isempty(signWindow)
signWindow = [10 0];
end
if ~exist('smoothWindow', 'var') || isempty(smoothWindow)
smoothWindow = 15;
end
if ~exist('upsamplingFactor', 'var') || isempty(upsamplingFactor)
upsamplingFactor = 1;
end
if ~exist('restoreFlag', 'var') || isempty(restoreFlag)
restoreFlag = 1;
end
if ~exist('centerFlag', 'var') || isempty(centerFlag)
centerFlag = 1;
end
if ~exist('shiftWindow','var') || isempty(shiftWindow)
shiftWindow = [];
end
pulses = double(pulses);
% upsample if requested
if upsamplingFactor>1
try
pulses = resample(pulses', upsamplingFactor, 1, 100)';
catch ME
disp(ME.getReport())
end
end
[nPulses, pulseDur] = size(pulses);
if isempty(shiftWindow)
shiftIdx = 1:pulseDur;
else
shiftIdx = ceil(pulseDur/2) + [-shiftWindow:shiftWindow];
end
%% Center on max power and flip if negative lobe to left of max power
for ii = 1:nPulses
oldPulse = pulses(ii,:);
oldPulse = oldPulse./norm(oldPulse); % scale to unit norm
% center of mass
switch centerFlag
case 1
mIdx = argmax(smooth(oldPulse(shiftIdx).^2, smoothWindow)); % get max power then center on this
case 2
mIdx = argmax(smooth(abs(hilbert(oldPulse(shiftIdx))), smoothWindow)); % get max power then center on this
case 3
mIdx = argmax(smooth(abs(oldPulse(shiftIdx)), smoothWindow)); % get max power then center on this
case 4
mIdx = round(centerOfMass((1:pulseDur), smooth(oldPulse(shiftIdx).^2, smoothWindow)')); % get max power then center on this
case 5
mIdx = round(centerOfMass((1:pulseDur), smooth(abs(hilbert(oldPulse(shiftIdx))), smoothWindow)')); % get max power then center on this
case 6
mIdx = round(centerOfMass((1:pulseDur), smooth(abs(oldPulse(shiftIdx)), smoothWindow)')); % get max power then center on this
otherwise
error()
end
% max energy
lPad = pulseDur - mIdx - min(shiftIdx); %i.e. ((total_length/2) - C)
rPad = 2*pulseDur - pulseDur - lPad;
newPulse = [zeros(1,lPad) oldPulse zeros(1, rPad)];
if mean(newPulse(pulseDur-signWindow(1):pulseDur-signWindow(2)))<0
newPulse = -newPulse; % flip pulse if it starts neg.
end
pulses(ii,:) = newPulse(floor(pulseDur/2)+(1:pulseDur)); % cut normalized pulse to original duration
end
%% restore original pulse sampling
if upsamplingFactor>1 && restoreFlag==1
try
pulses = resample(pulses', 1, upsamplingFactor, 100)';
catch ME
disp(ME.getReport())
end
end