BandpassPlotter.h
1 //-*-C++-*-
2 /***************************************************************************
3  *
4  * Copyright (C) 2004 by Willem van Straten
5  * Licensed under the Academic Free License version 2.1
6  *
7  ***************************************************************************/
8 
9 // psrchive/Util/pgutil/BandpassPlotter.h
10 
11 #ifndef __fft_BandpassPlotter_h
12 #define __fft_BandpassPlotter_h
13 
14 #include "templates.h"
15 #include "myfinite.h"
16 
17 #include <cpgplot.h>
18 #include <algorithm>
19 
20 namespace fft {
21 
22  template<class Data, class Info>
23  class BandpassPlotter {
24 
25  public:
26 
28  BandpassPlotter ()
29  {
30  user_max = user_min = 0;
31  user_fmax = user_fmin = 0;
32 
33  ignore_fraction = 0.0;
34 
35  logarithmic = false;
36  xlabel_ichan = false;
37  histogram = false;
38 
39  title = "Original Bandpass";
40  }
41 
43  virtual ~BandpassPlotter() { }
44 
46  virtual void plot (Data* data, Info* info) const;
47 
49  template<class T>
50  void plot (std::vector< std::vector<T> >& data, double timespan, Info* info) const;
51 
53  virtual void preprocess (std::vector<float>& bandpass) const { }
54 
56  void set_minmax (float min, float max)
57  { user_min = min; user_max = max; }
58 
60  void set_fminmax (float min, float max)
61  {
62  if (!myfinite(min) || !myfinite(max))
63  throw Error (InvalidParam, "BandpassPlotter::set_fminmax", "min=%f max=%f", min, max);
64  user_fmin = min;
65  user_fmax = max;
66  }
67 
69  float ignore_fraction;
70 
72  bool logarithmic;
73 
75  bool histogram;
76 
78  bool xlabel_ichan;
79 
80  std::string title;
81 
82  protected:
83  float user_min, user_max;
84  float user_fmin, user_fmax;
85 
86  };
87 
88 }
89 
90 void log (std::vector<float>& data)
91 {
92  for (unsigned i=0; i<data.size(); i++)
93  if (data[i] > 0)
94  data[i] = log10 (data[i]);
95  else
96  data[i] = 0.0;
97 }
98 
99 template<class Data, class Info>
100 void fft::BandpassPlotter<Data,Info>::plot (Data* data, Info* info) const
101 {
102  unsigned ipol, npol = data->get_npol ();
103  unsigned nchan = 0;
104 
105  float min = 0;
106  float max = 0;
107  for (ipol=0; ipol<npol; ipol++)
108  {
109  std::vector<float> pband = data->get_passband (ipol);
110 
111  this->preprocess (pband);
112  if (logarithmic)
113  log (pband);
114 
115  if (ipol == 0)
116  nchan = pband.size();
117 
118  minmax (pband, min, max, ipol);
119  }
120 
121  if (user_min != user_max)
122  {
123  min = user_min;
124  max = user_max;
125  }
126 
127  double freq = info->get_centre_frequency();
128  double bw = info->get_bandwidth();
129 
130  double fmin = freq - bw/2;
131  double fmax = freq + bw/2;
132 
133  std::string xlabel = "Frequency (MHz)";
134 
135  if (xlabel_ichan)
136  {
137  fmin = 0;
138  fmax = nchan;
139  xlabel = "Frequency channel";
140  }
141 
142  float wfmin = fmin;
143  float wfmax = fmax;
144 
145  if (user_fmin != user_fmax)
146  {
147  std::cerr << "BandpassPlotter set min=" << user_fmin << " max=" << user_fmax << std::endl;
148  wfmin = user_fmin;
149  wfmax = user_fmax;
150  }
151 
152  float fbuf = fabs(0.05 * ( wfmax - wfmin ));
153 
154  cpgsci(1);
155  cpgswin (wfmin-fbuf, wfmax+fbuf, min, max);
156 
157  // std::cerr << "npol=" << npol << std::endl;
158 
159  for (unsigned ipol=0; ipol<npol; ipol++)
160  {
161  std::vector<float> pband = data->get_passband (ipol);
162  this->preprocess (pband);
163  if (logarithmic)
164  log (pband);
165 
166  // std::cerr << "ipol=" << ipol << " nchan=" << nchan << std::endl;
167 
168  double fstep = bw/(nchan-1);
169  if (xlabel_ichan)
170  fstep = 1.0;
171 
172  cpgsci(ipol+2);
173 
174  std::vector<float> xaxis (nchan);
175  float offset = 0;
176  if (histogram)
177  offset = 0.5;
178 
179  for (unsigned ichan=0; ichan<nchan; ichan++)
180  xaxis[ichan] = fmin + (ichan+offset)*fstep;
181 
182  float* x = &xaxis[0];
183  float* y = &pband[0];
184 
185  if (histogram)
186  cpgbin (nchan, x, y, true);
187  else
188  cpgline (nchan, x, y);
189  }
190 
191  cpgsci (1);
192 
193  if (logarithmic)
194  {
195  cpgbox("BCNST", 0.0, 0, "BCNSTL2", 0.0, 0);
196  cpglab(xlabel.c_str(), "Logarithmic Scale", title.c_str());
197  }
198  else
199  {
200  cpgbox("BCNST", 0.0, 0, "BCNST", 0.0, 0);
201  cpglab(xlabel.c_str(), "Linear Scale", title.c_str());
202  }
203 }
204 
205 
206 template<class Data, class Info>
207 template<class T>
208 void fft::BandpassPlotter<Data,Info>::plot (std::vector< std::vector<T> >& data,
209  double timespan, Info* info) const
210 {
211  unsigned ntime = data.size();
212  unsigned nchan = data[0].size();
213 
214  std::vector<float> plotarray (ntime * nchan);
215 
216  float min = 0;
217  float max = 0;
218 
219  unsigned jchan = 0;
220 
221  unsigned ignore_ichan = (unsigned) (ignore_fraction * nchan);
222 
223  for (unsigned itime=0; itime<ntime; itime++) {
224  std::vector<float>& pband = data[itime];
225  this->preprocess (pband);
226 
227  minmax (pband.begin()+ignore_ichan, pband.end()-ignore_ichan,
228  min, max, itime);
229 
230  for (unsigned ichan=0; ichan<nchan; ichan++)
231  plotarray[ichan+jchan] = pband[ichan];
232 
233  jchan += nchan;
234  }
235 
236  //std::cerr << "min=" << min << " max=" << max << std::endl;
237  float diff = max - min;
238  min -= .1 * diff;
239  max += .1 * diff;
240  //std::cerr << "min=" << min << " max=" << max << std::endl;
241 
242  if (user_max)
243  max = user_max;
244 
245  double freq = info->get_centre_frequency();
246  double bw = info->get_bandwidth();
247 
248  double fmin = freq - bw/2;
249  double fmax = freq + bw/2;
250 
251  cpgsci(1);
252  cpgswin(fmin, fmax, 0, timespan);
253  cpgbox("BCNST", 0.0, 0, "BCNST", 0.0, 0);
254  cpglab("Frequency (MHz)", "Time (s)", "Dynamic Spectrum");
255 
256  float fstep = bw/nchan;
257  float tstep = timespan/ntime;
258  float tmin = 0.0;
259 
260  float offset_fmin = fmin - 0.5*fstep;
261  float offset_tmin = tmin - 0.5*tstep;
262  float trf[6] = {offset_fmin, fstep, 0.0,
263  offset_tmin, 0.0, tstep};
264 
265  cpgimag(&plotarray[0], nchan, ntime, 1, nchan, 1, ntime, min, max, trf);
266 
267 }
268 
269 #endif
const ScalarMath log(const ScalarMath &x)

Generated using doxygen 1.8.17