Isis 3 Programmer Reference
SpectralDefinition2D.cpp
1 
6 /* SPDX-License-Identifier: CC0-1.0 */
7 
8 #include "SpectralDefinition2D.h"
9 
10 #include <cassert>
11 #include <QList>
12 
13 #include "ProcessBySample.h"
14 #include "Spectel.h"
15 
16 namespace Isis {
17 
27  ProcessBySample importCube;
29  m_spectelList = NULL;
30  m_sectionList = NULL;
31  Cube *smileCube = importCube.SetInputCube(smileDefFilename.expanded(), cai);
32 
33  try {
34  // Check to see if input definition has the correct format
35  if (smileCube->lineCount() != 2) {
36  QString msg = QObject::tr("Input calibration file [%1] must have 2 lines: "
37  "one containing wavelength centers and one containing widths").
38  arg(smileDefFilename.toString());
39  throw IException(IException::User, msg, _FILEINFO_);
40  }
41 
44 
45  m_ns = smileCube->sampleCount();
46  m_nl = 0;
47  m_nb = smileCube->bandCount();
48 
49  m_sectionList->append(1); //first section will always be band 1
50  importCube.SetProcessingDirection(ProcessByBrick::BandsFirst);
51  importCube.Progress()->SetText("Importing Spectral Definition Cube");
52  importCube.ProcessCubeInPlace(*this, false);
53  importCube.Finalize();
54 
55  m_numSections = m_sectionList->length();
56 
57  } catch (IException &e) {
58  //delete dynamically allocated memory, since destructor won't be called.
59  if (m_spectelList != NULL) {
60  delete m_spectelList;
61  }
62  if (m_sectionList != NULL) {
63  delete m_sectionList;
64  }
65  QString msg = QObject::tr("Unable to open input cube [%1] and read it into a spectral "
66  "definition.").arg(smileDefFilename.toString());
67  throw IException(e, IException::Unknown, msg, _FILEINFO_);
68  }
69  }
70 
72  return m_numSections;
73  }
74 
75 
77  int SpectralDefinition2D::sectionNumber(int s, int l, int b) const {
78  if (m_sectionList->contains(b)) {
79  return m_sectionList->indexOf(b);
80  }
81  else if (m_sectionList->size() == 1) {
82  return 0;
83  }
84  else {
85  for (int i=0; i<m_sectionList->size()-1; i++ ) {
86  if ( (b > m_sectionList->at(i)) && (b < m_sectionList->at(i+1)) ) {
87  return i;
88  }
89  }
90  return m_sectionList->size() - 1;
91  }
92  }
93 
94 
97  delete m_spectelList;
98  delete m_sectionList;
99  }
100 
101 
113  Spectel SpectralDefinition2D::findSpectel(const int sample, const int line,
114  const int band) const {
115  // There is no DN, since the imported image's DNs are centers and widths
116 
117  // TODO:
118  // Test the QList bounds ourselves and throw an ISIS exception if not valid. QList.at does
119  // not throw if invalid. It aborts using assert
120  return m_spectelList->at(sample - 1)->at(band - 1);
121  }
122 
123 
124  Spectel SpectralDefinition2D::findSpectelByWavelength(const double wavelength,
125  const int sectionNumber) const {
126  // Can not search a 2D definistion with only one value (i.e. wavelength), so abort
127  // NOTE: This is ignored for code coverage until a good way to test it is found
128  // May not want to use the assert, but this function should not be called
129 
130  assert(0);
131  return Spectel();
132  }
133 
134  // TODO: If the requested wavelength is outside all the definitioin wavelength we should do something
135  Spectel SpectralDefinition2D::findSpectel(const Spectel &inSpectel,
136  const int sectionNumber) const {
137  double diff;
138  double bestdiff = DBL_MAX;
139  double bestband = 0;
140  double wavelength = inSpectel.centerWavelength();
141  QList<Spectel> *spectrum = m_spectelList->at(inSpectel.sample()-1);
142 
143  //only search in correct section
144  int start = m_sectionList->at(sectionNumber) - 1; //bands are 1-indexed, but are stored as 0-indexed
145  int end;
146  if (sectionNumber == m_sectionList->size()-1) { //we're in the last section
147  end = spectrum->length();
148  }
149  else {
150  end = m_sectionList->at(sectionNumber + 1) - 1;
151  }
152 
153  for (int i=start; i<end; i++) {
154  diff = spectrum->at(i).centerWavelength() - wavelength;
155  if (std::abs(diff) < std::abs(bestdiff)) {
156  bestdiff = diff;
157  bestband = i;
158  }
159  }
160 
161  // TODO: QList aborts if at(arg) is out of bounds do the necessary error check and throw if needed
162  return spectrum->at(bestband);
163  }
164 
173  QString temp;
174  for (int samp=0; samp<m_spectelList->size(); samp++) {
175  for(int band=0; band<m_spectelList->at(samp)->size(); band++){
176  Spectel spec = m_spectelList->at(samp)->at(band);
177  temp+="Spectel at (s,b) (";
178  temp+= QString::number(samp);
179  temp+= ", ";
180  temp+= QString::number(band);
181  temp+=") : Wavelength=";
182  temp+=QString::number(spec.centerWavelength());
183  temp+=" Width=";
184  temp+=QString::number(spec.filterWidth());
185  temp+="\n";
186  }
187  }
188  return temp;
189  }
190 
191 
192  // TODO: Test for equal wavelengths within a single section (currently ignored)
196 
197  // Each time we come back to the first band allocate space for this new spectrum of spectels
198  if (in.Band() == 1) {
199  QList<Spectel> *tempList = new QList<Spectel>;
200  m_spectelList->append(tempList);
201  }
202 
203  // Store the spectel
204  Spectel temp(in.Sample(), Isis::NULL8, in.Band(), Isis::NULL8, in[0], in[1]);
205  m_spectelList->at(in.Sample()-1)->append(temp);
206 
207  // Check for sections (change in wavelength direction) in the first spectrum only
208  // TODO: Consider doing this for all spectrums as a saftey check
209  // The first two spectels define the initial wavelength direction.
210  if (in.Sample() == 1) {
211 
212  QList<Spectel> *spectrum = m_spectelList->at(in.Sample()-1);
213  int index = in.Band() - 1;
214 
215  if ((index > 1) && // We now have at least 3 saved
216  (index != m_sectionList->last()) && // Don't look for a switch until one after the most recent
217  (((spectrum->at(index-2).centerWavelength() <
218  spectrum->at(index-1).centerWavelength()) && // previous 2 are ascending
219  (spectrum->at(index-1).centerWavelength() >
220  spectrum->at(index).centerWavelength())) || // previous and this are descending
221  ((spectrum->at(index-2).centerWavelength() >
222  spectrum->at(index-1).centerWavelength()) && // previous 2 are descending
223  (spectrum->at(index-1).centerWavelength() <
224  spectrum->at(index).centerWavelength())))) { // previous and this are ascending
225 
226  m_sectionList->append(in.Band());
227  }
228  }
229  }
230 }
Isis::SpectralDefinition2D::m_sectionList
QList< int > * m_sectionList
The list of sections.
Definition: SpectralDefinition2D.h:59
Isis::SpectralDefinition2D::sectionNumber
int sectionNumber(int s, int l, int b) const
returns section number given (s,l,b)
Definition: SpectralDefinition2D.cpp:77
Isis::ProcessBySample::ProcessCubeInPlace
void ProcessCubeInPlace(const Functor &funct, bool threaded=true)
Definition: ProcessBySample.h:62
Isis::Spectel
Stores information about a "Spectral pixel" or spectel.
Definition: Spectel.h:26
QList
This is free and unencumbered software released into the public domain.
Definition: BoxcarCachingAlgorithm.h:13
Isis::FileName
File name manipulation and expansion.
Definition: FileName.h:100
Isis::IException::Unknown
@ Unknown
A type of error that cannot be classified as any of the other error types.
Definition: IException.h:118
Isis::Spectel::centerWavelength
double centerWavelength() const
Gets central wavelength of spectel.
Definition: Spectel.cpp:95
Isis::SpectralDefinition2D::toString
QString toString()
Returns QString representation of SpectralDefinition2D.
Definition: SpectralDefinition2D.cpp:172
Isis::SpectralDefinition::m_nb
int m_nb
Number of bands in input Cube.
Definition: SpectralDefinition.h:60
Isis::Spectel::filterWidth
double filterWidth() const
Gets wavelength width associated with spectel.
Definition: Spectel.cpp:107
Isis::SpectralDefinition2D::m_spectelList
QList< QList< Spectel > * > * m_spectelList
Internally represent the samples x 2 lines x n bands calibration file Outside list is the sample inde...
Definition: SpectralDefinition2D.h:55
Isis::SpectralDefinition2D::operator()
void operator()(Buffer &in) const
Internal function used to help read-in a calibration cube.
Definition: SpectralDefinition2D.cpp:195
Isis::Buffer
Buffer for reading and writing cube data.
Definition: Buffer.h:53
Isis::SpectralDefinition2D::m_numSections
int m_numSections
The number of sections of this Spectral Definition.
Definition: SpectralDefinition2D.h:57
Isis::FileName::expanded
QString expanded() const
Returns a QString of the full file name including the file path, excluding the attributes.
Definition: FileName.cpp:196
Isis::Cube::lineCount
int lineCount() const
Definition: Cube.cpp:1734
Isis::SpectralDefinition2D::~SpectralDefinition2D
~SpectralDefinition2D()
destructor
Definition: SpectralDefinition2D.cpp:96
Isis::SpectralDefinition2D::SpectralDefinition2D
SpectralDefinition2D(FileName smileDefFilename)
Construct a SpectralDefinition2D object using a filename.
Definition: SpectralDefinition2D.cpp:26
Isis::SpectralDefinition::m_nl
int m_nl
Number of lines in input Cube.
Definition: SpectralDefinition.h:57
Isis::Progress::SetText
void SetText(const QString &text)
Changes the value of the text string reported just before 0% processed.
Definition: Progress.cpp:61
Isis::Cube::sampleCount
int sampleCount() const
Definition: Cube.cpp:1807
Isis::Process::Progress
Isis::Progress * Progress()
This method returns a pointer to a Progress object.
Definition: Process.h:259
Isis::Cube
IO Handler for Isis Cubes.
Definition: Cube.h:167
Isis::IException
Isis exception class.
Definition: IException.h:91
Isis::Cube::bandCount
virtual int bandCount() const
Returns the number of virtual bands for the cube.
Definition: Cube.cpp:1410
Isis::FileName::toString
QString toString() const
Returns a QString of the full file name including the file path, excluding the attributes with any Is...
Definition: FileName.cpp:515
Isis::Buffer::Band
int Band(const int index=0) const
Returns the band position associated with a shape buffer index.
Definition: Buffer.cpp:162
Isis::ProcessByBrick::Finalize
void Finalize()
Cleans up by closing cubes and freeing memory.
Definition: ProcessByBrick.cpp:679
Isis::ProcessByBrick::SetProcessingDirection
void SetProcessingDirection(ProcessingDirection direction)
Set the direction the data will be read, either all lines in a single band proceeding to the next ban...
Definition: ProcessByBrick.cpp:380
Isis::CubeAttributeInput
Manipulate and parse attributes of input cube filenames.
Definition: CubeAttribute.h:381
Isis::SpectralDefinition2D::sectionCount
virtual int sectionCount() const
Returns the number of sections in the calibration image.
Definition: SpectralDefinition2D.cpp:71
Isis::Buffer::Sample
int Sample(const int index=0) const
Returns the sample position associated with a shape buffer index.
Definition: Buffer.cpp:127
Isis::SpectralDefinition::m_ns
int m_ns
Number of samples in input Cube.
Definition: SpectralDefinition.h:54
Isis::ProcessBySample
Process cubes by sample.
Definition: ProcessBySample.h:37
Isis::SpectralDefinition2D::findSpectel
Spectel findSpectel(const int sample, const int line, const int band) const
Get the Spectel at some sample, line, band (associated with your input/calibration file)
Definition: SpectralDefinition2D.cpp:113
Isis::ProcessBySample::SetInputCube
Isis::Cube * SetInputCube(const QString &parameter, int requirements=0)
Opens an input cube specified by the user and verifies requirements are met.
Definition: ProcessBySample.cpp:37
Isis
This is free and unencumbered software released into the public domain.
Definition: Apollo.h:16
Isis::IException::User
@ User
A type of error that could only have occurred due to a mistake on the user's part (e....
Definition: IException.h:126