USGS

Isis 3.0 Application Source Code Reference

Home

CamTools.h

Go to the documentation of this file.
00001 #ifndef CamTools_h
00002 #define CamTools_h
00003 /**
00004  * @file
00005  * $Revision: 1.10 $
00006  * $Date: 2009/08/25 01:37:55 $
00007  *
00008  *   Unless noted otherwise, the portions of Isis written by the USGS are
00009  *   public domain. See individual third-party library and package descriptions
00010  *   for intellectual property information, user agreements, and related
00011  *   information.
00012  *
00013  *   Although Isis has been used by the USGS, no warranty, expressed or
00014  *   implied, is made by the USGS as to the accuracy and functioning of such
00015  *   software and related material nor shall the fact of distribution
00016  *   constitute any such warranty, and no responsibility is assumed by the
00017  *   USGS in connection therewith.
00018  *
00019  *   For additional information, launch
00020  *   $ISISROOT/doc//documents/Disclaimers/Disclaimers.html
00021  *   in a browser or see the Privacy & Disclaimers page on the Isis website,
00022  *   http://isis.astrogeology.usgs.gov, and the USGS privacy and disclaimers on
00023  *   http://www.usgs.gov/privacy.html.
00024  */
00025 
00026 #include <string>
00027 #include <vector>
00028 #include <iostream>
00029 #include <iomanip>
00030 #include <sstream>
00031 
00032 #include "Pvl.h"
00033 #include "PvlKeyword.h"
00034 #include "SpecialPixel.h"
00035 #include "ImagePolygon.h"
00036 #include "iException.h"
00037 
00038 namespace Isis {
00039 
00040   /**
00041    * @brief Checks value of key, produces appropriate value
00042    *
00043    * This function checks the value of the keyword for specialness
00044    * and will create the appropriate keyword if it is special.
00045    *
00046    * @param keyname Name of keyword to create
00047    * @param value   Keyword value
00048    * @param unit    Optional unit qualifer with value
00049    *
00050    * @return PvlKeyword Returns newly created keyword/value
00051    */
00052   inline PvlKeyword ValidateKey(const std::string keyname,
00053                                 const double &value,
00054                                 const std::string &unit = "") {
00055     if(IsSpecial(value)) {
00056       return (PvlKeyword(keyname, "NULL"));
00057     }
00058     else {
00059       return (PvlKeyword(keyname, value, unit));
00060     }
00061   }
00062 
00063   /**
00064    * @brief Checks proper value of a NULLed keyword
00065    *
00066    * If the keyword is a NULL keyword, ensure it has proper value.
00067    *
00068    * @param keyname Name of keyword to create
00069    * @param key     Keyword/value set
00070    * @param unit    Optional unit qualifer with value
00071    *
00072    * @return PvlKeyword Returns newly created keyword/value
00073    */
00074 
00075   inline PvlKeyword ValidateKey(const std::string keyname, PvlKeyword &key,
00076                                 const std::string &unit = "") {
00077     if(key.IsNull()) {
00078       return (PvlKeyword(keyname, "NULL"));
00079     }
00080     else {
00081       return (ValidateKey(keyname, (double) key, unit));
00082     }
00083   }
00084 
00085 
00086   /** Returns degree to radian conversion factor */
00087   inline double DegToRad(const double ang) {
00088     return (ang * rpd_c());
00089   }
00090   /** Returns radians to degrees conversion factor */
00091   inline double RadToDeg(const double ang) {
00092     return (ang * dpr_c());
00093   }
00094 
00095   /**  A very useful, typesafe way to delete pointers in STL container
00096    *   Courtesy Scott Meyers, "Effective STL", Item 7, pg 37-40 */
00097   struct DeleteObject {
00098     template <typename T>
00099     void operator()(const T *ptr) const {
00100       delete ptr;
00101     }
00102   };
00103 
00104   /**
00105    * @brief Collect Band geometry
00106    *
00107    * This produces the geometry and polygon information from an image cube.  It
00108    * has some special processing that accounts for band independant geometrical
00109    * image cubes.  It processes each band and creates unique geometry and
00110    * ploygon values consider this situation.  The resulting polygon is a union
00111    * of all bands, which is a (usually) slightly better footprint of the acutal
00112    * footprint for the product.
00113    *
00114    * The other major advantage to this class is the corner latitude/longitude
00115    * points are based upon the extents of each independant band data as the
00116    * furthest point from the center of the polygon location (if requested by the
00117    * user).
00118    *
00119    * @ingroup Utility
00120    * @author 2008-09-10 Kris Becker
00121    *
00122    * @internal
00123    *   @history 2009-02-26 Kris Becker - Removed unconditional computation of
00124    *                           polygon even when the user did not request it.
00125    *                           Reorganized some keywords to their relevant group
00126    *                           locations.
00127    *   @history 2009-05-29 Kris Becker - Added _pixinx parameter
00128    *   @history 2009-06-22 Kris Becker - Added hasLimb() method to check for the
00129    *                           presence of a planet limb; Added
00130    *                           getProjGeometry() method.
00131    *   @history 2009-08-04 Christopher Austin - fixed ImagePolygon::Create call
00132    *                           for the updated sampinc/lineinc implementation
00133    *   @history 2009-08-12 Kris Becker - Modified so that images that include
00134    *                           poles are not converted to 180 domain when
00135    *                           projected
00136    *   @history 2009-08-24 Kris Becker - Added ability to disable use of shape
00137    *                           model when creating polygons that contains a limb
00138    *   @history 2011-02-17 Jai Rideout - Replaced pixinc with sinc and linc.
00139    */
00140   class BandGeometry {
00141 
00142     public:
00143       BandGeometry() : _nLines(0), _nSamps(0), _nBands(0), _sampleInc(1),
00144         _lineInc(1), _radius(1.0), _isBandIndependent(true),
00145         _hasCenterGeom(false), _gBandList(), _polys(),
00146         _combined(0), _mapping() {  }
00147       ~BandGeometry() {
00148         destruct();
00149       }
00150 
00151       void setSampleInc(const int sampleInc) {
00152         _sampleInc = sampleInc;
00153       }
00154       void setLineInc(const int lineInc) {
00155         _lineInc = lineInc;
00156       }
00157       int getSampleInc() const {
00158         return (_sampleInc);
00159       }
00160       int getLineInc() const {
00161         return (_lineInc);
00162       }
00163       void setMaxIncidence(const double maxinc) {
00164         _maxIncidence = maxinc;
00165       }
00166       void setMaxEmission(const double maxema) {
00167         _maxEmission = maxema;
00168       }
00169       int size() const {
00170         return (_gBandList.size());
00171       }
00172       bool isPointValid(const double &sample, const double &line, const Camera *camera = 0) const;
00173       bool isBandIndependent() const {
00174         return (_isBandIndependent);
00175       }
00176       bool hasCenterGeometry() const;
00177       bool hasLimb() const;
00178       void collect(Camera &camera, Cube &cube, bool doGeometry, bool doPolygon,
00179           bool increasePrecision);
00180       void generateGeometryKeys(PvlObject &pband);
00181       void generatePolygonKeys(PvlObject &pband);
00182 
00183     private:
00184       // Internal structure to contain geometric properties
00185       struct GProperties {
00186         GProperties() : lines(0), samples(0), bands(0),
00187           band(0),  realBand(0), target(""),
00188           centerLine(0.0), centerSamp(0.0),
00189           centerLatitude(Null), centerLongitude(Null), radius(Null),
00190           rightAscension(Null), declination(Null),
00191           centroidLatitude(Null), centroidLongitude(Null),
00192           centroidLine(Null), centroidSample(Null), centroidRadius(Null),
00193           surfaceArea(Null), phase(Null), emi(Null), inc(Null),
00194           sampRes(Null), lineRes(Null), grRes(Null),
00195           solarLongitude(Null), northAzimuth(Null), offNader(Null),
00196           subSolarAzimuth(Null), subSolarGroundAzimuth(Null),
00197           subSpacecraftAzimuth(Null), subSpacecraftGroundAzimuth(Null),
00198           localSolartime(Null), targetCenterDistance(Null), slantDistance(Null),
00199           subSolarLatitude(Null), subSolarLongitude(Null),
00200           subSpacecraftLatitude(Null), subSpacecraftLongitude(Null),
00201           startTime(""), endTime(""),
00202           parallaxx(Null), parallaxy(Null),
00203           shadowx(Null), shadowy(Null),
00204           upperLeftLongitude(Null), upperLeftLatitude(Null),
00205           lowerLeftLongitude(Null), lowerLeftLatitude(Null),
00206           lowerRightLongitude(Null), lowerRightLatitude(Null),
00207           upperRightLongitude(Null), upperRightLatitude(Null),
00208           hasLongitudeBoundary(false), hasNorthPole(false), hasSouthPole(false) { }
00209         ~GProperties() { }
00210 
00211         int lines, samples, bands;
00212         int band, realBand;
00213         std::string target;
00214         double centerLine, centerSamp;
00215         double centerLatitude, centerLongitude;
00216         double radius;
00217         double rightAscension, declination;
00218         double centroidLatitude, centroidLongitude;
00219         double centroidLine, centroidSample;
00220         double centroidRadius, surfaceArea;
00221         double phase, emi, inc;
00222         double sampRes, lineRes, grRes;
00223         double solarLongitude, northAzimuth, offNader;
00224         double subSolarAzimuth, subSolarGroundAzimuth;
00225         double subSpacecraftAzimuth, subSpacecraftGroundAzimuth;
00226         double localSolartime, targetCenterDistance, slantDistance;
00227         double subSolarLatitude, subSolarLongitude;
00228         double subSpacecraftLatitude, subSpacecraftLongitude;
00229         std::string startTime, endTime;
00230         double parallaxx, parallaxy, shadowx, shadowy;
00231         double upperLeftLongitude, upperLeftLatitude;
00232         double lowerLeftLongitude, lowerLeftLatitude;
00233         double lowerRightLongitude, lowerRightLatitude;
00234         double upperRightLongitude, upperRightLatitude;
00235         bool hasLongitudeBoundary, hasNorthPole, hasSouthPole;
00236       };
00237 
00238       typedef std::vector<GProperties> BandPropertiesList;
00239       typedef BandPropertiesList::iterator BandPropertiesListIter;
00240       typedef BandPropertiesList::const_iterator BandPropertiesListConstIter;
00241 
00242       // Internal structure to contain geometric properties
00243       typedef std::vector<geos::geom::Geometry *> BandPolygonList;
00244       typedef BandPolygonList::iterator BandPolygonListIter;
00245       typedef BandPolygonList::const_iterator BandPolygonListConstIter;
00246 
00247 
00248       int _nLines;
00249       int _nSamps;
00250       int _nBands;
00251       int _sampleInc;
00252       int _lineInc;
00253       double _maxEmission;
00254       double _maxIncidence;
00255       double _radius;
00256       bool _isBandIndependent;
00257       bool _hasCenterGeom;
00258       BandPropertiesList _gBandList;
00259       BandPolygonList _polys;
00260       geos::geom::Geometry *_combined;
00261       GProperties _summary;
00262       Pvl _mapping;
00263 
00264       void destruct();
00265       GProperties getGeometrySummary() const;
00266       Pvl getProjGeometry(Camera &camera,  geos::geom::MultiPolygon *footprint,
00267                           GProperties &g);
00268       double getRadius() const;
00269       double getPixelResolution() const;
00270       double getPixelsPerDegree(double pixres, double radius) const;
00271       bool isDistShorter(double bestDist, double lat1, double lon1,
00272                          double lat2, double lon2, double radius,
00273                          double &thisDist) const;
00274       geos::geom::MultiPolygon *makeMultiPolygon(geos::geom::Geometry *g) const;
00275 
00276 
00277   };
00278 
00279 } // Namespace Isis
00280 
00281 #endif