tomwalters@0
|
1 % tool
|
tomwalters@0
|
2 %
|
tomwalters@0
|
3 % INPUT VALUES:
|
tomwalters@0
|
4 %
|
tomwalters@0
|
5 % RETURN VALUE:
|
tomwalters@0
|
6 %
|
tomwalters@0
|
7 %
|
bleeck@3
|
8 % (c) 2011, University of Southampton
|
bleeck@3
|
9 % Maintained by Stefan Bleeck (bleeck@gmail.com)
|
bleeck@3
|
10 % download of current version is on the soundsoftware site:
|
bleeck@3
|
11 % http://code.soundsoftware.ac.uk/projects/aimmat
|
bleeck@3
|
12 % documentation and everything is on http://www.acousticscale.org
|
bleeck@3
|
13
|
tomwalters@0
|
14
|
tomwalters@0
|
15 function pitch=combfrePtiPdots(framestruct_a);
|
tomwalters@0
|
16 % combined graphic of frequency axis and time interval axis
|
tomwalters@0
|
17 % on one axis
|
tomwalters@0
|
18 % plots one graphic that consists of two parts:
|
tomwalters@0
|
19 % the frequency profile and the interval profile on one axis
|
tomwalters@0
|
20
|
tomwalters@0
|
21 if nargin < 2
|
tomwalters@0
|
22 grafix=0; % for debugging
|
tomwalters@0
|
23 end
|
tomwalters@0
|
24 dot_scaler=200; % wie gross Punkte dargestellt werden sollen in Punkt
|
tomwalters@0
|
25
|
tomwalters@0
|
26 % wie weit die Intervallsumme runterskaliert werden muss, damit die Zahlen vernünftigt werden
|
tomwalters@0
|
27 norm_intervalhight=100;
|
tomwalters@0
|
28 % wie weit die spektrale Summe runterskaliert werden muss, damit die Zahlen vernünftigt werden
|
tomwalters@0
|
29 norm_spektralhight=10;
|
tomwalters@0
|
30
|
tomwalters@0
|
31 % how big must the contrast of the envelope be to be recognised as one pitch
|
tomwalters@0
|
32 envcontrast_threshold=0.15;
|
tomwalters@0
|
33
|
tomwalters@0
|
34 % A single factor, that can vary between
|
tomwalters@0
|
35 % 0 = complete attention to temporal structure
|
tomwalters@0
|
36 % 1 = complete attention to spectral structure
|
tomwalters@0
|
37 spectral_attention_factor=0.5;
|
tomwalters@0
|
38
|
tomwalters@0
|
39 if ~isstruct(framestruct_a)
|
tomwalters@0
|
40 framestruct.current_frame=framestruct_a;
|
tomwalters@0
|
41 else
|
tomwalters@0
|
42 framestruct=framestruct_a;
|
tomwalters@0
|
43 end
|
tomwalters@0
|
44
|
tomwalters@0
|
45 if isfield(framestruct_a,'plot_only_highest') % if only one dot per line shell be plotted
|
tomwalters@0
|
46 plot_only_highest=framestruct_a.plot_only_highest;
|
tomwalters@0
|
47 else
|
tomwalters@0
|
48 plot_only_highest=0;
|
tomwalters@0
|
49 end
|
tomwalters@0
|
50
|
tomwalters@0
|
51 if isfield(framestruct_a,'plot_bw') % on paper work with different colors
|
tomwalters@0
|
52 plot_bw=framestruct_a.plot_bw;
|
tomwalters@0
|
53 else
|
tomwalters@0
|
54 plot_bw=0;
|
tomwalters@0
|
55 end
|
tomwalters@0
|
56
|
tomwalters@0
|
57 if isfield(framestruct_a,'normalise') % normalize the frame to a fixed value to get rid of effects of loudness and strobing points
|
tomwalters@0
|
58 normalise=framestruct_a.normalise;
|
tomwalters@0
|
59 else
|
tomwalters@0
|
60 normalise=0;
|
tomwalters@0
|
61 end
|
tomwalters@0
|
62
|
tomwalters@0
|
63 % ob vorher die Region unten rechts rausgeworfen werden soll
|
tomwalters@0
|
64 if ~isfield(framestruct_a,'extract_pitch_region');
|
tomwalters@0
|
65 extract_pitch_region=0;
|
tomwalters@0
|
66 else
|
tomwalters@0
|
67 extract_pitch_region=framestruct_a.extract_pitch_region;
|
tomwalters@0
|
68 end
|
tomwalters@0
|
69
|
tomwalters@0
|
70 current_frame=framestruct.current_frame;
|
tomwalters@0
|
71
|
tomwalters@0
|
72 % Wheh normalized, it is assumed that the overall energy in the stimulus is
|
tomwalters@0
|
73 % always the same
|
tomwalters@0
|
74 if normalise
|
tomwalters@0
|
75 current_frame=normaliseto(current_frame,1);
|
tomwalters@0
|
76 end
|
tomwalters@0
|
77
|
tomwalters@0
|
78 pitch_current_frame=current_frame;
|
tomwalters@0
|
79 if extract_pitch_region
|
tomwalters@0
|
80 % schmeisse die physikalisch nicht sinnvollen Bereiche raus!
|
tomwalters@0
|
81 current_frame=extractpitchregion(current_frame);
|
tomwalters@0
|
82 end
|
tomwalters@0
|
83
|
tomwalters@0
|
84 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
tomwalters@0
|
85 % % hier werden die Quellen berechnet:
|
tomwalters@0
|
86 parameters=framestruct;
|
tomwalters@0
|
87 pitch=calcresidualprobability(pitch_current_frame,parameters);
|
tomwalters@0
|
88
|
tomwalters@0
|
89 % calculate the sum of the frequencies
|
tomwalters@0
|
90 fresumme=getfrequencysum(current_frame);
|
tomwalters@0
|
91
|
tomwalters@0
|
92 nrchannels=getnrchannels(current_frame);
|
tomwalters@0
|
93 smoothwidth=128/nrchannels;
|
tomwalters@0
|
94 % smooth the sum with a smoothwidth of 1
|
tomwalters@0
|
95 fresumme=smooth(fresumme,smoothwidth);
|
tomwalters@0
|
96
|
tomwalters@0
|
97 % calculate the sum from interval profile
|
tomwalters@0
|
98 intsumme=getsum(current_frame);
|
tomwalters@0
|
99
|
tomwalters@0
|
100 % scaling value, if in a movie
|
tomwalters@0
|
101 scale_summe=getsumscale(current_frame);
|
tomwalters@0
|
102
|
tomwalters@0
|
103 % start plotting:
|
tomwalters@0
|
104 % clf;
|
tomwalters@0
|
105
|
tomwalters@0
|
106 % bastel zwei lineare Funktionen zusammen: eine aus dem zeitlichen Verlauf,
|
tomwalters@0
|
107 % und eine aus dem spektralen.
|
tomwalters@0
|
108 minimum_time_interval=1;
|
tomwalters@0
|
109 maximum_time_interval=32;
|
tomwalters@0
|
110
|
tomwalters@0
|
111 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
tomwalters@0
|
112 % Die Intervallsumme muss von linear auf logarithmisch umgestellt werden
|
tomwalters@0
|
113 nr_points=getnrpoints(intsumme);
|
tomwalters@0
|
114 intervalsum=logsigx(intsumme,-maximum_time_interval/1000,-minimum_time_interval/1000,nr_points);
|
tomwalters@0
|
115 intervalsum=setstarttime(intervalsum,0);
|
tomwalters@0
|
116 % ab nun haben wir eine lineare Zeitachse mit logarithmischen Werten
|
tomwalters@0
|
117
|
tomwalters@0
|
118 global fnull;global stepsperoctave; % brauch ich unten in den Unterfunktionen
|
tomwalters@0
|
119 fnull=1000/maximum_time_interval; % per Definition die niedrigste Frequenz = Anfangsfrequenz der gesamten Achse
|
tomwalters@0
|
120
|
tomwalters@0
|
121 % soviel "cent" hat die Zeitachse.
|
tomwalters@0
|
122 stepsperoctave=log2(maximum_time_interval/minimum_time_interval)/getnrpoints(intervalsum); % soviel octaven/Pixel
|
tomwalters@0
|
123 intervalsum=setsr(intervalsum,1/stepsperoctave);
|
tomwalters@0
|
124 % intervalsum now goes from -32 to -1 ms in the interval profile
|
tomwalters@0
|
125 % empirische Werte zum Skalieren auf einen einheitlichen Wert (1)
|
tomwalters@0
|
126 intervalsum=scale(intervalsum,norm_intervalhight);
|
tomwalters@0
|
127
|
tomwalters@0
|
128
|
tomwalters@0
|
129 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
tomwalters@0
|
130 % Die Frequenzsumme
|
tomwalters@0
|
131 % plot the frequency profile in the same Graphic
|
tomwalters@0
|
132 cfs=getcf(current_frame);
|
tomwalters@0
|
133 minimum_fre=cfs(1); % the lowest frequency
|
tomwalters@0
|
134 maximum_fre=cfs(end); % the lowest frequency
|
tomwalters@0
|
135
|
tomwalters@0
|
136 total_length=f2p(maximum_fre); % gesamte Länge des Plots
|
tomwalters@0
|
137 start_fre_profile=f2p(minimum_fre); % Startpunkt der Frequenzachse
|
tomwalters@0
|
138 stop_int_profile=f2p(1000/minimum_time_interval); % Ende des Überlapps
|
tomwalters@0
|
139
|
tomwalters@0
|
140 nr_addpoints=total_length-stop_int_profile; % soviel Punkte müssen hinten an die Intervallachse
|
tomwalters@0
|
141 tsig=signal(zeros(floor(nr_addpoints),1),getsr(intervalsum)); % Ein Nullensignal mit den richtigen Daten
|
tomwalters@0
|
142 intervalsum=append(intervalsum,tsig); % hänge es an die Intervallsumme hinten an
|
tomwalters@0
|
143 % empirische Werte zum Skalieren auf einen einheitlichen Wert (1)
|
tomwalters@0
|
144
|
tomwalters@0
|
145 % glätte die Frequenzachse:
|
tomwalters@0
|
146 % intervalsum=smooth(intervalsum,smoothwidth);
|
tomwalters@0
|
147
|
tomwalters@0
|
148 % Die Frequenzsumme muss von erb (oder cfs) auf logarithmisch umgestellt werden
|
tomwalters@0
|
149 fresumme=erb2log(fresumme,cfs);
|
tomwalters@0
|
150
|
tomwalters@0
|
151 nr_addpoints=start_fre_profile; % soviel Punkte müssen vor die Frequenzsumme gehängt werden
|
tomwalters@0
|
152
|
tomwalters@0
|
153 % wieviel Punkte pro Octave in der Frequenzachse
|
tomwalters@0
|
154 freoctrelation=log2(maximum_fre/minimum_fre)/getnrpoints(fresumme); % soviel octaven/Pixel
|
tomwalters@0
|
155 fresumme=setsr(fresumme,1/freoctrelation); % anpassen der Zahl der Punkte auf die Intervalachse
|
tomwalters@0
|
156 fresumme=changesr(fresumme,getsr(intervalsum));
|
tomwalters@0
|
157
|
tomwalters@0
|
158 tsig=signal(zeros(floor(nr_addpoints),1),getsr(fresumme)); %
|
tomwalters@0
|
159 fresumme=scale(fresumme,norm_spektralhight);
|
tomwalters@0
|
160
|
tomwalters@0
|
161 fresumme=append(tsig,fresumme);
|
tomwalters@0
|
162 fresumme=setstarttime(fresumme,0);
|
tomwalters@0
|
163
|
tomwalters@0
|
164 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
tomwalters@0
|
165 % plot it both
|
tomwalters@0
|
166 if plot_bw
|
tomwalters@0
|
167 han=plot(intervalsum,'k--');
|
tomwalters@0
|
168 set(han,'linewidth',1);
|
tomwalters@0
|
169 else
|
tomwalters@0
|
170 plot(intervalsum,'b');
|
tomwalters@0
|
171 end
|
tomwalters@0
|
172 [intermaxpos,interminpos,intermax,intermin]=getminmax(intervalsum);
|
tomwalters@0
|
173 intermaxpos=time2bin(intervalsum,intermaxpos);
|
tomwalters@0
|
174 interminpos=time2bin(intervalsum,interminpos);
|
tomwalters@0
|
175 hold on
|
tomwalters@0
|
176 if plot_bw
|
tomwalters@0
|
177 plot(fresumme,'k');
|
tomwalters@0
|
178 else
|
tomwalters@0
|
179 plot(fresumme,'r');
|
tomwalters@0
|
180 end
|
tomwalters@0
|
181 [fremaxpos,freminpos,fremax,fremin]=getminmax(fresumme);
|
tomwalters@0
|
182 fremaxpos=time2bin(fresumme,fremaxpos);
|
tomwalters@0
|
183 freminpos=time2bin(fresumme,freminpos);
|
tomwalters@0
|
184 axis([1 getnrpoints(fresumme) 0 1])
|
tomwalters@0
|
185 % make x-Ticks
|
tomwalters@0
|
186 nr_labels=8;ti=50*power(2,[0:7]);tix=f2p(ti);ti=round(ti*10)/10;
|
tomwalters@0
|
187 set(gca,'XTick',tix);set(gca,'XTickLabel',ti);
|
tomwalters@0
|
188 xlabel('Frequency [Hz]');ylabel('PitchStrength');title('');
|
tomwalters@0
|
189
|
tomwalters@0
|
190
|
tomwalters@0
|
191
|
tomwalters@0
|
192 if plot_only_highest
|
tomwalters@0
|
193 n=1;
|
tomwalters@0
|
194 else
|
tomwalters@0
|
195 n=length(pitch):-1:1;
|
tomwalters@0
|
196 end
|
tomwalters@0
|
197
|
tomwalters@0
|
198 % if ~isempty(pitch) % only, when temporal pitches occure
|
tomwalters@0
|
199 frequencydots=sortstruct(pitch,'spektral_profile.activity');
|
tomwalters@0
|
200 for i=n
|
tomwalters@0
|
201 % Plotte die blauen Punkte (Intervalle)
|
tomwalters@0
|
202 pfre=pitch{i}.interval_profile.fre;
|
tomwalters@0
|
203 xx=f2p(pfre); %das liegt wegen Rundungsfehlern zu weit links??
|
tomwalters@0
|
204 xx=getmaximumrightof(xx-1,intermaxpos,interminpos,intermax,intermin);
|
tomwalters@0
|
205 hei=getbinvalue(intervalsum,xx);
|
tomwalters@0
|
206 if i==1
|
tomwalters@0
|
207 radius=max(2,dot_scaler*pitch{i}.residuumpitchstrength);
|
tomwalters@0
|
208 if plot_bw
|
tomwalters@0
|
209 plot(xx,hei,'k.','MarkerSize',radius/2,'Marker','^','MarkerFaceColor','k');
|
tomwalters@0
|
210 else
|
tomwalters@0
|
211 plot(xx,hei,'b.','MarkerSize',radius);
|
tomwalters@0
|
212 end
|
tomwalters@0
|
213 % text(xx+30,texthei*1.1,sprintf('%3.0f Hz %5.3f',pitch{i}.fre,pitch{i}.residuumpitchstrength)); % this is at a nice position
|
tomwalters@0
|
214 % if pitch{i}.envcontrast > envcontrast_threshold
|
tomwalters@0
|
215 a=text(xx+30,hei*1.2,sprintf('%3.0f Hz',pfre)); % this is at a nice position
|
tomwalters@0
|
216 set(a,'Color','b');
|
tomwalters@0
|
217 % end
|
tomwalters@0
|
218 else
|
tomwalters@0
|
219 radius=max(2,dot_scaler*pitch{i}.residuumpitchstrength);
|
tomwalters@0
|
220 plot(xx,hei,'b.','MarkerSize',radius);
|
tomwalters@0
|
221 end
|
tomwalters@0
|
222
|
tomwalters@0
|
223 % Plotte die roten Punkte (Frequenzen)
|
tomwalters@0
|
224 pfre=chan2fre(current_frame,frequencydots{i}.spektral_profile.position);
|
tomwalters@0
|
225 xx=f2p(pfre); % suche den Punkt auf dem nächsten Maximum um Rundungsfehler zu vermeiden
|
tomwalters@0
|
226 xx2=getmaximumrightof(xx-1,fremaxpos,freminpos,fremax,fremin);
|
tomwalters@0
|
227 if xx2/xx < 1.015 % wenn das nächste Maximum nah dran ist, dann wars ein Fehler
|
tomwalters@0
|
228 xx=xx2;
|
tomwalters@0
|
229 end
|
tomwalters@0
|
230 hei=getbinvalue(fresumme,xx);
|
tomwalters@0
|
231 radius=max(2,dot_scaler*frequencydots{i}.spektral_profile.hight);
|
tomwalters@0
|
232 if plot_bw
|
tomwalters@0
|
233 plot(xx,hei,'k.','MarkerSize',radius);
|
tomwalters@0
|
234 else
|
tomwalters@0
|
235 plot(xx,hei,'r.','MarkerSize',radius);
|
tomwalters@0
|
236 end
|
tomwalters@0
|
237 a=text(xx+30,hei*1.2,sprintf('%4.2f kHz',pfre/1000)); % this is at a nice position
|
tomwalters@0
|
238 set(a,'Color','r');
|
tomwalters@0
|
239
|
tomwalters@0
|
240 end
|
tomwalters@0
|
241
|
tomwalters@0
|
242 return
|
tomwalters@0
|
243
|
tomwalters@0
|
244
|
tomwalters@0
|
245
|
tomwalters@0
|
246 function f=p2f(pix)
|
tomwalters@0
|
247 global fnull;
|
tomwalters@0
|
248 global stepsperoctave;
|
tomwalters@0
|
249 f=fnull*power(2,(pix-1)*stepsperoctave);
|
tomwalters@0
|
250 return
|
tomwalters@0
|
251
|
tomwalters@0
|
252 function p=f2p(fre)
|
tomwalters@0
|
253 global fnull;
|
tomwalters@0
|
254 global stepsperoctave;
|
tomwalters@0
|
255 p=1/stepsperoctave*log2(fre/fnull)+1;
|
tomwalters@0
|
256 return
|