Commit 09ad8b6b authored by Stuart Sides's avatar Stuart Sides
Browse files

New Horizons MVIC and LORRI camera and ingest ref#1962,2120,2122

git-svn-id: http://subversion.wr.usgs.gov/repos/prog/isis3/trunk@5866 41f8697f-d340-4b68-9986-7bafba869bb8
parent b0207e34
Loading
Loading
Loading
Loading
+3 −2
Original line number Diff line number Diff line
@@ -24,11 +24,12 @@ void IsisMain() {
  ProcessImportFits pfits;

  pfits.setFitsFile(FileName(ui.GetFileName("FROM")));
  pfits.setProcessFileStructure(0);

  Cube *output = pfits.SetOutputCube("TO");

  // Add instrument group if any keywords were put into it.
  PvlGroup instGrp = pfits.standardInstrumentGroup();
  PvlGroup instGrp = pfits.standardInstrumentGroup(pfits.fitsLabel(0));
  if (instGrp.keywords() > 0) {
    
    output->label()->findObject("IsisCube") += instGrp;
@@ -36,7 +37,7 @@ void IsisMain() {

  // Save the input FITS label in the Cube original labels
  Pvl pvl;
  pvl += pfits.fitsLabel();
  pvl += pfits.fitsLabel(0);
  OriginalLabel originals(pvl);
  output->write(originals);

+2 −2
Original line number Diff line number Diff line
@@ -4,8 +4,8 @@ include $(ISISROOT)/make/isismake.tsts

commands:
	$(APPNAME) from=$(INPUT)/WFPC2u5780205r_c0fx.fits \
	to=$(OUTPUT)/fitsTruth.cub \
	> /dev/null;
	to=$(OUTPUT)/fitsTruth.cub
#	> /dev/null;
	raw2isis from=$(INPUT)/WFPC2u5780205r_c0fx.fits \
	to=$(OUTPUT)/rawTruth.cub \
	SAMPLES=200 LINES=200 BANDS=4 SKIP=23040 \
+117 −57
Original line number Diff line number Diff line
@@ -23,14 +23,16 @@
#include "ProcessImportFits.h"

#include <iostream>
#include <math.h>

#include <QDebug>
#include <QString>
#include <sstream>

#include "Preference.h"
#include "IException.h"
#include "IString.h"
#include "LineManager.h"
#include "Preference.h"
#include "Pvl.h"
#include "PvlGroup.h"
#include "PixelType.h"
@@ -43,7 +45,8 @@ namespace Isis {
   * Constructor for ProcessImportFits
   */
  ProcessImportFits::ProcessImportFits() {
    m_fitsLabel = NULL;
    m_fitsLabels = NULL;
    m_headerSizes = NULL;
  }


@@ -51,35 +54,45 @@ namespace Isis {
   * Destructor for ProcessImportFits
   */
  ProcessImportFits::~ProcessImportFits() {
    delete m_fitsLabel;
    delete m_fitsLabels;
    delete m_headerSizes;
    m_file.close();
  }


  /**
   * Extract the FITS label from the file
   * Extract all the FITS labels from the file. This includes the main and all extensions
   *
   */
  void ProcessImportFits::extractFitsLabel() {
  void ProcessImportFits::extractFitsLabels() {

    // The main FITS label starts at the beginning of the file
    // Each FITS keyword in the lable is store in 80 bytes (space padded to 80 if necessary)

    m_fitsLabel = new PvlGroup("FitsLabels");
    m_fitsLabels = new QList< PvlGroup * >;
    m_headerSizes = new QList < int >;

    // Read in the FITS labels and convert to PVL
    // Process each FITS label area. Storing each in its own PvlGroup
    char readBuf[81];
    IString line = "";
    unsigned int place = 0;
    unsigned int place;

    // The main FITS label starts at the beginning of the file
    // FITS extension labels start after the previous data and on a 2080 byte boundry 
    // Each FITS keyword in all lables is store in 80 bytes (space padded to 80 if necessary)

    // Start at the beginning of the file for the main FITS label
    m_file.seekg(0, std::ios_base::beg);

    // Read the first label line (80 chars)
    // We are assuming the file pointer is set to the beginning of the first/next label
    while (m_file.read(readBuf, 80) && m_file.gcount() == 80) {

      PvlGroup *fitsLabel = new PvlGroup("FitsLabels");

    // Read the first line
    m_file.seekg(0);
    m_file.read(readBuf, 80);
      readBuf[80] = '\0';
      line = readBuf;
    place += 80;
      place = 80;

      // Process each fits label record (80 bytes) and place keyword, value pairs into PvlKeywords 
      // with any associated comments
      while (line.substr(0, 3) != "END") {

        // Check for blank lines
@@ -117,59 +130,112 @@ namespace Isis {
              }
            }
          }
        m_fitsLabel->addKeyword(label);
          fitsLabel->addKeyword(label);
        }

      // Read the next line
      m_file.seekg(place);
        // Read the next label line
        m_file.read(readBuf, 80);
        readBuf[80] = '\0';
      place += 80;
        line = readBuf;
        place += 80;
      }

      // Save off the PvlGroup and the number of records read from this label
      m_fitsLabels->push_back(fitsLabel);
      m_headerSizes->push_back((int)ceil(place / 2880.0));

      // The file pointer should be pointing at the end of the record that contained "END"
      // Move the file pointer past the padding after the "END"
      std::streamoff jump;
      jump = m_headerSizes->last() * 2880 - place;
      m_file.seekg(jump, std::ios_base::cur);

      // NOTE: For now we only handle image data (i.e., keywords BITPIX & NAXIS & NAXISx must exist)
      // Does this look like a label for a FITS image? Stop after the first label that does not
      // because we don't know how to move the file pointer past a non-image data.
      if (fitsLabel->hasKeyword("BITPIX") && fitsLabel->hasKeyword("NAXIS") && 
          fitsLabel->hasKeyword("NAXIS1")) {

        int bytesPerPixel = 0;
        bytesPerPixel = (int)((*fitsLabel)["BITPIX"]);
        bytesPerPixel = fabs(bytesPerPixel);
        bytesPerPixel /= 8;

        unsigned int axis1 = 1;
        axis1 = toInt((*fitsLabel)["NAXIS1"]);

        unsigned int axis2 = 1;
        if (fitsLabel->hasKeyword("NAXIS2")) {
          axis2 = toInt((*fitsLabel)["NAXIS2"]);
        }

    // Save off the number of header records read
    m_headers = (int)((place + 2881) / 2880);
        unsigned int axis3 = 1;
        if (fitsLabel->hasKeyword("NAXIS3")) {
          axis3 = toInt((*fitsLabel)["NAXIS3"]);
        }

        jump = (int)(ceil(bytesPerPixel * axis1 * axis2 * axis3 / 2880.0) * 2880.0);
        m_file.seekg(jump, std::ios_base::cur);
      }
      // Do we have at least on header that looks like it has image data? If so, we can continue,
      // but ignore the rest of the file because we don't know how to skip over a non-image data.
      else if (m_fitsLabels->size() > 1) {
        m_fitsLabels->pop_back();
        m_headerSizes->pop_back();
        break;
      }
      else {
        QString msg = QObject::tr("The FITS file does not contain a section header that looks "
                                  "like it describes an image [%1]").arg(m_name.toString());
        throw IException(IException::User, msg, _FILEINFO_);
      }
    }
  }


  /**
   * Supplies the FITS label 
   * Supplies the requested FITS label 
   * 
   * @param FITS label after being converted to a PvlGroup
   * @param labelNumber FITS label number. zero (0) is the first/main label
   * @return PvlGroup version of a FITS label corrisponding to requested label number
   */
  PvlGroup ProcessImportFits::fitsLabel() const {
    if (!m_fitsLabel) {
  PvlGroup ProcessImportFits::fitsLabel(int labelNumber) const {
    if (!m_fitsLabels) {
      QString msg = QObject::tr("The FITS label has not been initialized, call setFitsFile first");
      throw IException(IException::Programmer, msg, _FILEINFO_);
    }
    else if (m_fitsLabels->size() < labelNumber) {
      QString msg = QObject::tr("The requested FITS label number does not exist from file [%1]").arg(m_name.toString());
      throw IException(IException::Programmer, msg, _FILEINFO_);
    }

    return *m_fitsLabel;
    return *(*m_fitsLabels)[labelNumber];
  }


  /**
   * Return a populated instrument group 
   *  
   * @param a FITS label after being converted to a PvlGroup
   * @return an instrument group filled with keywords from the FITS label
   */
  PvlGroup ProcessImportFits::standardInstrumentGroup() const {
  PvlGroup ProcessImportFits::standardInstrumentGroup(PvlGroup fitsLabel) const {

    // NOTE: This needs to be changed over to use translation files

    // Attempt to extract the standard instrument group keywords
    PvlGroup inst("Instrument");
    if (m_fitsLabel->hasKeyword("DATE-OBS")) {
      inst += PvlKeyword("StartTime", (*m_fitsLabel)["DATE-OBS"][0]);
    if (fitsLabel.hasKeyword("DATE-OBS")) {
      inst += PvlKeyword("StartTime", fitsLabel["DATE-OBS"][0]);
    }
    if (m_fitsLabel->hasKeyword("OBJECT")) {
      inst += PvlKeyword("Target", (*m_fitsLabel)["OBJECT"][0]);
    if (fitsLabel.hasKeyword("OBJECT")) {
      inst += PvlKeyword("Target", fitsLabel["OBJECT"][0]);
    }
    if (m_fitsLabel->hasKeyword("INSTRUME")) {
      inst += PvlKeyword("InstrumentId", (*m_fitsLabel)["INSTRUME"][0]);
    if (fitsLabel.hasKeyword("INSTRUME")) {
      inst += PvlKeyword("InstrumentId", fitsLabel["INSTRUME"][0]);
    }
    if (m_fitsLabel->hasKeyword("OBSERVER")) {
      inst += PvlKeyword("SpacecraftName", (*m_fitsLabel)["OBSERVER"][0]);
    if (fitsLabel.hasKeyword("OBSERVER")) {
      inst += PvlKeyword("SpacecraftName", fitsLabel["OBSERVER"][0]);
    }

    return inst;
@@ -192,32 +258,34 @@ namespace Isis {
    }

    // Get the FITS labels internalized
    extractFitsLabel();
    extractFitsLabels();

    // Check to make sure it is a FITS file we can handle
    PvlGroup label = fitsLabel();
    PvlGroup label = fitsLabel(0);
    if (label["SIMPLE"][0] == "F") {
      QString msg = QObject::tr("The file [%1] can not be processed. It is an unsupported format.").
          arg(fitsFile.toString());
      throw IException(IException::User, msg, _FILEINFO_);
    }

    setProcessFileStructure(label);

    m_file.close();
  }


  /**
   * Sets all the Process file structure parameters. Mostly based on the FITS labels 
   * Sets the Process file structure parameters based on the FITS labels of choice 
   *  
   * @param labelNumber FITS label number. zero (0) is the first/main label
   * 
   */
  void ProcessImportFits::setProcessFileStructure(PvlGroup label) {
  void ProcessImportFits::setProcessFileStructure(int labelNumber) {

    PvlGroup label = *(*m_fitsLabels)[labelNumber];

    SetFileHeaderBytes(m_headers * 2880);
    SetFileHeaderBytes((*m_headerSizes)[labelNumber] * 2880);
    SaveFileHeader();

    // Find pixel type, there are several unsupported possiblites
    // Find pixel type. NOTE: There are several unsupported possiblites
    Isis::PixelType type;
    QString msg = "";
    switch (toInt(label["BITPIX"][0])) {
@@ -268,28 +336,20 @@ namespace Isis {
    if (label.hasKeyword("BZERO")) {
      SetBase(toDouble(label["BZERO"][0]));
    }
    else {
      SetBase(0.0);
    }
    if (label.hasKeyword("BSCALE")) {
      SetMultiplier(toDouble(label["BSCALE"][0]));
    }
    else {
      SetMultiplier(1.0);
    }

    // Byte order
    SetByteOrder(Isis::Msb);

  }






} // end namespace Isis








+12 −9
Original line number Diff line number Diff line
@@ -22,8 +22,11 @@
 *   http://www.usgs.gov/privacy.html.
 */


#include "ProcessImport.h"

template <typename T> class QList;

namespace Isis {
  /**
   * @brief Import a FITS file
@@ -37,7 +40,7 @@ namespace Isis {
   * @author 2013-10-08 Stuart Sides
   *
   * @internal
   *
   *   @history 2014-06-06 Stuart Sides - Added ability to read and process the FITS extension
   */

  class ProcessImportFits : public ProcessImport {
@@ -46,16 +49,16 @@ namespace Isis {
      ProcessImportFits();
      ~ProcessImportFits();

      PvlGroup standardInstrumentGroup() const;
      PvlGroup fitsLabel() const;
      PvlGroup standardInstrumentGroup(PvlGroup fitsLabel) const;
      PvlGroup fitsLabel(int labelNumber) const;
      void setFitsFile(FileName fitsFile);
      void setProcessFileStructure(int labelNumber);

    private:
      void extractFitsLabel();
      void setProcessFileStructure(PvlGroup label);
      void extractFitsLabels();

      //! Holds the PvlGroup with the converted FITS labels
      PvlGroup *m_fitsLabel;
      //! Holds the PvlGroups with the converted FITS labels from the main and all extensions
      QList<PvlGroup *> *m_fitsLabels;

      //! The name of the input FITS file
      FileName m_name;
@@ -63,8 +66,8 @@ namespace Isis {
      //! The stream used to read the FITS file
      std::ifstream m_file;

      //! The number of 2880 byte header records before the first data
      int m_headers;
      //! The number of 2880 byte header records before each data section
      QList<int> *m_headerSizes;
  };
};

+2 −6
Original line number Diff line number Diff line
@@ -1531,13 +1531,9 @@ namespace Isis {

        // Don't read type 5 ck here
        if (ic[2] == 5) break;
        if (ic[2] != 3) {
          QString msg = "Time fetching method only works on type 3 and 5 ck";
          throw IException(IException::Programmer, msg, _FILEINFO_);
        }

//      
        // Check times for type 3 ck segment if spacecraft matches
        if (ic[0] == spCode) {
        if (ic[0] == spCode && ic[2] == 3) {
          sct2e_c((int) spCode / 1000, dc[0], &segStartEt);
          sct2e_c((int) spCode / 1000, dc[1], &segStopEt);
          NaifStatus::CheckErrors();
Loading