source: branches/fitshead-branch/Cubes/saveImage.cc @ 99

Last change on this file since 99 was 99, checked in by Matthew Whiting, 18 years ago

Added a #define WCSLIB_GETWCSTAB command to the headers of those files using
fitsio.h -- this enables cfitsio v.3 to be compiled with g++ v.4 (else it
complains about multiple definitions of wtbarr).
Minor typo fix for outputSpectra.cc.

File size: 7.9 KB
Line 
1#include <iostream>
2#include <sstream>
3#include <string>
4#include <wcs.h>
5#include <wcshdr.h>
6#define WCSLIB_GETWCSTAB // define this so that we don't try and redefine wtbarr
7                         // (this is a problem when using cfitsio v.3 and g++ v.4)
8#include <fitsio.h>
9#include <duchamp.hh>
10#include <Cubes/cubes.hh>
11
12void write_header_info(fitsfile *fptr, Param &par, string nature);
13
14void Cube::saveReconstructedCube()
15{
16  /**
17   *  Cube::saveReconstructedCube()
18   *
19   *   A function to save the reconstructed and/or residual arrays.
20   *   A number of header keywords are written as well, indicating the nature of the
21   *    reconstruction that has been done.
22   *   The file is always written -- if the filename (as calculated based on the
23   *    recon parameters) exists, then it is overwritten.
24   */
25 
26  int newbitpix = FLOAT_IMG;
27
28  float *resid = new float[this->numPixels];
29  for(int i=0;i<this->numPixels;i++) resid[i] = this->array[i] - this->recon[i];
30  float blankval = this->par.getBlankPixVal();
31
32  long *fpixel = new long[this->numDim];
33  for(int i=0;i<this->numDim;i++) fpixel[i]=1;
34  int status = 0;  /* MUST initialize status */
35  fitsfile *fptrOld, *fptrNew;         
36  fits_open_file(&fptrOld,this->par.getImageFile().c_str(),READONLY,&status);
37  if (status) fits_report_error(stderr, status);
38 
39  if(this->par.getFlagOutputRecon()){
40    string fileout = "!" + this->par.getImageFile(); // ! so that it writes over an existing file.
41    fileout = fileout.substr(0,fileout.size()-5); // remove the ".fits" on the end.
42    std::stringstream ss;
43    ss << ".RECON"<<this->par.getAtrousCut()<<".fits";
44    fileout += ss.str();
45
46    status = 0;
47    fits_create_file(&fptrNew,fileout.c_str(),&status);
48    if (status) fits_report_error(stderr, status);
49    status = 0;
50    fits_movabs_hdu(fptrOld, 1, NULL, &status);
51    if (status) fits_report_error(stderr, status);
52    status = 0;
53    fits_copy_header(fptrOld, fptrNew, &status);
54    if (status) fits_report_error(stderr, status);
55    char *comment = new char[80];
56    long dud;
57    status = 0;
58    fits_update_key(fptrNew, TINT, "BITPIX", &newbitpix, "number of bits per data pixel", &status);
59    if (status) fits_report_error(stderr, status);
60    status = 0;
61    float bscale=1., bzero=0.;
62    fits_update_key(fptrNew, TFLOAT, "BSCALE", &bscale, "PHYSICAL = PIXEL*BSCALE + BZERO", &status);
63    fits_update_key(fptrNew, TFLOAT, "BZERO", &bzero, "", &status);
64    fits_set_bscale(fptrNew, 1., 0., &status);
65    if (status) fits_report_error(stderr, status);
66    // Need to correct the dimensions, if we have subsectioned the image...   
67    if(this->par.getFlagSubsection()){
68      fits_read_key(fptrOld, TLONG, "NAXIS1", &dud, comment, &status);
69      fits_update_key(fptrNew, TLONG, "NAXIS1", &(this->axisDim[0]), comment, &status);
70      fits_read_key(fptrOld, TLONG, "NAXIS2", &dud, comment, &status);
71      fits_update_key(fptrNew, TLONG, "NAXIS2", &(this->axisDim[1]), comment, &status);
72      fits_read_key(fptrOld, TLONG, "NAXIS3", &dud, comment, &status);
73      fits_update_key(fptrNew, TLONG, "NAXIS3", &(this->axisDim[2]), comment, &status);
74    }
75
76    write_header_info(fptrNew, this->par, "recon");
77
78    if(this->par.getFlagBlankPix())
79      fits_write_pixnull(fptrNew, TFLOAT, fpixel, this->numPixels, this->recon, &blankval, &status);
80    else  fits_write_pix(fptrNew, TFLOAT, fpixel, this->numPixels, this->recon, &status);
81
82    status = 0;
83    fits_close_file(fptrNew, &status);
84    if (status) fits_report_error(stderr, status);
85  }
86
87  if(this->par.getFlagOutputResid()){
88    string fileout = "!" + this->par.getImageFile(); // ! so that it writes over an existing file.
89    fileout = fileout.substr(0,fileout.size()-5);
90    std::stringstream ss;
91    ss << ".RESID"<<this->par.getAtrousCut()<<".fits";
92    fileout += ss.str();
93
94    status = 0;
95    fits_create_file(&fptrNew,fileout.c_str(),&status);
96    if (status) fits_report_error(stderr, status);
97    status = 0;
98    fits_movabs_hdu(fptrOld, 1, NULL, &status);
99    if (status) fits_report_error(stderr, status);
100    status = 0;
101    fits_copy_header(fptrOld, fptrNew, &status);
102    if (status) fits_report_error(stderr, status);
103
104    status = 0;
105    fits_update_key(fptrNew, TINT, "BITPIX", &newbitpix, "number of bits per data pixel", &status);
106    if (status) fits_report_error(stderr, status);
107    status = 0;
108    float bscale=1., bzero=0.;
109    fits_update_key(fptrNew, TFLOAT, "BSCALE", &bscale, "PHYSICAL = PIXEL*BSCALE + BZERO", &status);
110    fits_update_key(fptrNew, TFLOAT, "BZERO", &bzero, "", &status);
111    fits_set_bscale(fptrNew, 1., 0., &status);
112    if (status) fits_report_error(stderr, status);
113
114    // Need to correct the dimensions, if we have subsectioned the image...
115    char *comment = new char[80];
116    long dud;
117    if(this->pars().getFlagSubsection()){
118      fits_read_key(fptrOld, TLONG, "NAXIS1", &dud, comment, &status);
119      fits_update_key(fptrNew, TLONG, "NAXIS1", &(this->axisDim[0]), comment, &status);
120      fits_read_key(fptrOld, TLONG, "NAXIS2", &dud, comment, &status);
121      fits_update_key(fptrNew, TLONG, "NAXIS2", &(this->axisDim[1]), comment, &status);
122      fits_read_key(fptrOld, TLONG, "NAXIS3", &dud, comment, &status);
123      fits_update_key(fptrNew, TLONG, "NAXIS3", &(this->axisDim[2]), comment, &status);
124    }
125
126    write_header_info(fptrNew, this->par, "resid");
127
128    if(this->par.getFlagBlankPix())
129      fits_write_pixnull(fptrNew, TFLOAT, fpixel, this->numPixels, resid, &blankval, &status);
130    else  fits_write_pix(fptrNew, TFLOAT, fpixel, this->numPixels, resid, &status);
131
132    fits_close_file(fptrNew, &status);
133  }
134
135  delete [] recon;
136  delete [] resid;
137  delete [] fpixel;
138
139}
140
141
142void write_header_info(fitsfile *fptr, Param &par, string nature)
143{
144  /**
145   *  write_header_info(fptr, par, nature)
146   *
147   *   A simple function that writes all the necessary keywords and comments
148   *    to the FITS header pointed to by fptr.
149   *   The keyword names and comments are taken from duchamp.hh
150   *   The parameter "nature" indicates what type of file is being written:
151   *    should be either "recon" or "resid".
152   */
153
154
155  int status = 0;
156  char *comment, *keyword;
157  string explanation = "",ReconResid="";
158
159  fits_write_history(fptr, (char *)header_history1.c_str(), &status);
160                                   
161  fits_write_history(fptr, (char *)header_history2.c_str(), &status);
162
163  fits_write_comment(fptr, (char *)header_comment.c_str(), &status);
164
165  float valf = par.getAtrousCut();
166  fits_write_key(fptr, TFLOAT, (char *)keyword_snrRecon.c_str(), &valf,
167                 (char *)comment_snrRecon.c_str(), &status);
168
169  int vali = par.getReconDim();
170  fits_write_key(fptr, TINT, (char *)keyword_reconDim.c_str(), &vali,
171                 (char *)comment_reconDim.c_str(), &status);
172
173  vali = par.getMinScale();
174  fits_write_key(fptr, TINT, (char *)keyword_scaleMin.c_str(), &vali,
175                 (char *)comment_scaleMin.c_str(), &status);
176
177  vali = par.getFilterCode();
178  fits_write_key(fptr, TINT, (char *)keyword_filterCode.c_str(), &vali,
179                 (char *)comment_filterCode.c_str(), &status);
180
181  vali = int(par.getFlagMW());
182  fits_write_key(fptr, TINT, (char *)keyword_flagMW.c_str(), &vali,
183                 (char *)comment_flagMW.c_str(), &status);
184  if(par.getFlagMW()){
185    fits_write_comment(fptr, (char *)flagMW_comment.c_str(), &status);
186    vali = par.getMinMW();
187    fits_write_key(fptr, TINT, (char *)keyword_minMW.c_str(), &vali,
188                   (char *)comment_minMW.c_str(), &status);
189    vali = par.getMaxMW();
190    fits_write_key(fptr, TINT, (char *)keyword_maxMW.c_str(), &vali,
191                   (char *)comment_maxMW.c_str(), &status);
192  }
193
194  if(nature == "recon"){
195    explanation = "Duchamp: This is the RECONSTRUCTED cube";
196    ReconResid = "RECON";
197  }
198  else if(nature == "resid"){
199    explanation = "Duchamp: This is the RESIDUAL cube";
200    ReconResid = "RESID";
201  }
202  else std::cerr << "WARNING : write_header_info : explanation not present!\n";
203  fits_write_comment(fptr, (char *)explanation.c_str(), &status);
204  fits_write_key(fptr, TSTRING, (char *)keyword_ReconResid.c_str(),
205                 (char *)ReconResid.c_str(), (char *)comment_ReconResid.c_str(), &status);
206
207}
Note: See TracBrowser for help on using the repository browser.