casa  $Rev:20696$
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines
ImageUtilities.h
Go to the documentation of this file.
00001 //# ImageUtilities.h: Some utility functions handy for accessing images
00002 //# Copyright (C) 1996,1997,1999,2000,2001,2002
00003 //# Associated Universities, Inc. Washington DC, USA.
00004 //#
00005 //# This library is free software; you can redistribute it and/or modify it
00006 //# under the terms of the GNU Library General Public License as published by
00007 //# the Free Software Foundation; either version 2 of the License, or (at your
00008 //# option) any later version.
00009 //#
00010 //# This library is distributed in the hope that it will be useful, but WITHOUT
00011 //# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
00012 //# FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Library General Public
00013 //# License for more details.
00014 //#
00015 //# You should have received a copy of the GNU Library General Public License
00016 //# along with this library; if not, write to the Free Software Foundation,
00017 //# Inc., 675 Massachusetts Ave, Cambridge, MA 02139, USA.
00018 //#
00019 //# Correspondence concerning AIPS++ should be addressed as follows:
00020 //#        Internet email: aips2-request@nrao.edu.
00021 //#        Postal address: AIPS++ Project Office
00022 //#                        National Radio Astronomy Observatory
00023 //#                        520 Edgemont Road
00024 //#                        Charlottesville, VA 22903-2475 USA
00025 //#
00026 //#
00027 //# $Id: ImageUtilities.h 20229 2008-01-29 15:19:06Z gervandiepen $
00028 #ifndef IMAGES_IMAGEUTILITIES_H
00029 #define IMAGES_IMAGEUTILITIES_H
00030 
00031 
00032 #include <casa/aips.h>
00033 #include <components/ComponentModels/ComponentType.h>
00034 #include <components/ComponentModels/GaussianBeam.h>
00035 #include <coordinates/Coordinates/DirectionCoordinate.h>
00036 #include <images/Images/MaskSpecifier.h>
00037 #include <measures/Measures/Stokes.h>
00038 #include <lattices/Lattices/TiledShape.h>
00039 #include <casa/Utilities/PtrHolder.h>
00040 #include <casa/Containers/SimOrdMap.h>
00041 
00042 #include <memory>
00043 
00044 namespace casa { //# NAMESPACE CASA - BEGIN
00045 
00046 //# Forward Declarations
00047 template <class T> class ImageInterface;
00048 template <class T> class Vector;
00049 template <class T> class Quantum;
00050 template <class T> class MaskedArray;
00051 class LatticeBase;
00052 class CoordinateSystem;
00053 class Coordinate;
00054 class SkyComponent;
00055 class ImageInfo;
00056 class String;
00057 class IPosition;
00058 class LogIO;
00059 class Unit;
00060 class AxesSpecifier;
00061 
00062 //
00063 // <summary>
00064 // Utility functions for Image manipulation
00065 // </summary>
00066 //   
00067 //
00068 // <use visibility=export>
00069 //
00070 // <reviewed reviewer="" date="yyyy/mm/dd" tests="" demos="">
00071 // </reviewed>
00072 // 
00073 // <prerequisite>
00074 //   <li> IPosition
00075 //   <li> Arrays
00076 //   <li> Lattice
00077 // </prerequisite>
00078 //
00079 // <synopsis>
00080 // Some helpful static functions that are common to some of my image
00081 // analysis application  classes.
00082 // </synopsis>
00083 //
00084 // <motivation>
00085 // I needed some bits and pieces.  My goal isto move this rag-tag bunch
00086 // out of here into other classes as time goes on.  So far
00087 // I have eliminated 80% of the original !
00088 // </motivation>
00089 //
00090 // <todo asof="1996/11/27">
00091 //  <li>  
00092 // </todo>
00093  
00094 
00095 class ImageUtilities
00096 {
00097 public:
00098         // Open disk image (can be any registered image).  Exception
00099         // if fileName empty or file does not exist or file is not
00100         // of legal image type.   For aips++ images, the default mask is
00101         // applied.
00102         //  <group>
00103         static void openImage(
00104                 std::auto_ptr<ImageInterface<Float> >& image,
00105                 const String& fileName, LogIO& os
00106         );
00107 
00108         static void openImage(
00109                 ImageInterface<Float>*& image,
00110                 const String& fileName, LogIO& os
00111         );
00112 //  </group>
00113 
00114 // Copy MiscInfo, ImageInfo, brightness unit and logger (history) from in to out
00115    template <typename T, typename U>
00116    static void copyMiscellaneous (
00117                   ImageInterface<T>& out,
00118                   const ImageInterface<U>& in,
00119                   const Bool copyImageInfo = True
00120    );
00121 
00122 // Copy a mask from one image to another
00123    static void copyMask (ImageInterface<Float>& out,
00124                          const ImageInterface<Float>& in,
00125                          const String& maskOut, const String& maskIn,
00126                          AxesSpecifier axesSpecifier);
00127 
00128 // Add one degenerate axis for each of the specified coordinate types.
00129 // If the outfile string is given the new image is a PagedImage.
00130 // If the outfile string is empty, the new image is a TempImage.
00131    static void addDegenerateAxes (
00132                    LogIO& os,
00133                    PtrHolder<ImageInterface<Float> >& outImage,
00134                    const ImageInterface<Float>& inImage,
00135                    const String& outFile, Bool direction,
00136                    Bool spectral, const String& stokes,
00137                    Bool linear, Bool tabular, Bool overwrite
00138    );
00139 
00140 // Function to bin up (average data) one axis of an N-D MaskedArray. The interface
00141 // is pretty specific to a particular application. It's here because
00142 // its implemented with ImageRebin.  On input, the output MA *must*
00143 // have zero shape.   The input and output Coordinates must have the
00144 // same type and have only one axis (Linear,Spectral & Tabular).
00145 // The output coordinate is adjusted for the binning.   The binning
00146 // factor does not have to fit integrally into the shape of the specified
00147 // axis.
00148    template <typename T>
00149    static void bin (MaskedArray<T>& out, Coordinate& coordOut,
00150                     const MaskedArray<T>& in, const Coordinate& coordIn,
00151                     uInt axis, uInt bin);
00152 
00153 // This function converts pixel coordinates to world coordinates. You
00154 // specify a vector of pixel coordinates (<src>pixels</src>) for only one 
00155 // axis, the <src>pixelAxis</src>.    For the other pixel axes in the
00156 // <src>CoordinateSystem</src>, if a pixel axis "i" is  found in the 
00157 // <src>CursorAxes</src> vector, its pixel coordinate is set to 
00158 // the average of the selected region from the image for that axis
00159 // (<src>(blc(i)+trc(i))/2)</src>), otherwise it is set to the reference pixel.   
00160 // The vector of world coordinates for <src>pixelAxis</src> is returned as formatted 
00161 // Strings.  If for some reason it can't make the conversion, the element
00162 // element is returned as "?"    Returns <src>False</src> if the lengths of
00163 // <<src>blc</src> and <src>trc</src> are not equal to the number of pixel axes
00164 // in the coordinate system.
00165    static Bool pixToWorld (
00166                    Vector<String>& sWorld,
00167                    CoordinateSystem& cSys,
00168                    const Int& pixelAxis,
00169                    const Vector<Int>& cursorAxes,
00170                    const IPosition& blc,
00171                    const IPosition& trc,
00172                    const Vector<Double>& pixels,
00173                    const Int& prec,
00174                    const Bool usePrecForMixed=False
00175    );
00176 
00177 // Convert long axis names "Right Ascension", "Declination", "Frequency" and
00178 // "Velocity" to "RA", "Dec", "Freq", "Vel" respectively.  Unknown strings
00179 // are returned as given.
00180    static String shortAxisName (const String& axisName);
00181 
00182 // These functions convert between a vector of doubles holding SkyComponent values
00183 // (the output from SkyComponent::toPixel) and a SkyComponent.   The coordinate 
00184 // values are in the 'x' and 'y' frames.  It is possible that the x and y axes of 
00185 // the pixel array are lat/long (xIsLong=False)  rather than  long/lat.  
00186 // facToJy converts the brightness units from whatevers per whatever
00187 // to Jy per whatever (e.g. mJy/beam to Jy/beam).  It is unity if it
00188 // can't be done and you get a warning.  In the SkyComponent the flux
00189 // is integral.  In the parameters vector it is peak.
00190 //
00191 //   pars(0) = FLux     image units (e.g. Jy/beam).
00192 //   pars(1) = x cen    abs pix
00193 //   pars(2) = y cen    abs pix
00194 //   pars(3) = major    pix
00195 //   pars(4) = minor    pix
00196 //   pars(5) = pa radians (pos +x -> +y)
00197 //
00198 //  5 values for ComponentType::Gaussian, CT::Disk.  3 values for CT::Point.
00199 //
00200 // <group>
00201    static SkyComponent encodeSkyComponent(LogIO& os, Double& facToJy,
00202                                           const CoordinateSystem& cSys,
00203                                           const Unit& brightnessUnit,
00204                                           ComponentType::Shape type,
00205                                           const Vector<Double>& parameters,
00206                                           Stokes::StokesTypes stokes,
00207                                           Bool xIsLong, const GaussianBeam& beam);
00208 
00209     // for some reason, this method was in ImageAnalysis but also belongs here.
00210     // Obviously hugely confusing to have to methods with the same name and
00211     // which presumably are for the same thing in two different classes. I'm
00212     // moving ImageAnalysis' method here and also moving that implamentation to
00213     // here as well and also being consistent regarding callers (ie those that
00214     // called the ImageAnalysis method will now call this method). I couldn't
00215     // tell you which of the two implementations is the better one to use
00216     // for new code, but this version does call the version that already existed
00217     // in ImageUtilities, so this version seems to do a bit more.
00218     // I also hate having a class with anything like Utilities in the name,
00219     // but I needed to move this somewhere and can only tackle one issue
00220     // at a time.
00221     static casa::SkyComponent encodeSkyComponent(
00222         casa::LogIO& os, casa::Double& fluxRatio,
00223         const casa::ImageInterface<casa::Float>& im, 
00224         casa::ComponentType::Shape modelType,
00225         const casa::Vector<casa::Double>& parameters,
00226         casa::Stokes::StokesTypes stokes,
00227         casa::Bool xIsLong, casa::Bool deconvolveIt,
00228         const GaussianBeam& beam
00229     );
00230 
00231     // Deconvolve SkyComponent from beam
00232     // moved from ImageAnalysis. this needs to be moved to a more appropriate class at some point
00233     static SkyComponent deconvolveSkyComponent(
00234         LogIO& os, const SkyComponent& skyIn,
00235         const GaussianBeam& beam
00236     );
00237 
00238     /*
00239     // moved from ImageAnalysis. this needs to be moved to a more appropriate class at some point
00240     // Put beam into +x -> +y frame
00241     static GaussianBeam putBeamInXYFrame (
00242         const GaussianBeam& beam,
00243         const casa::DirectionCoordinate& dirCoord
00244     );
00245     */
00246 
00247     // moved from ImageAnalysis. this needs to be moved to a more appropriate class at some point
00248     static Vector<Double> decodeSkyComponent (
00249         const SkyComponent& sky, const ImageInfo& ii,
00250         const CoordinateSystem& cSys, const Unit& brightnessUnit,
00251         Stokes::StokesTypes stokes, Bool xIsLong
00252     );
00253 // </group>
00254 
00255     // moved from ImageAnalysis. this needs to be moved to a more appropriate class at some point
00256     // Deconvolve from beam
00257     // Returns True if the deconvolved source is a point source, False otherwise.
00258     /*
00259     static Bool deconvolveFromBeam(
00260         Angular2DGaussian& deconvolvedSize,
00261         const Angular2DGaussian& convolvedSize,
00262         Bool& successFit, LogIO& os,
00263         const GaussianBeam& beam, const Bool verbose=True
00264     );
00265     */
00266 
00267     /*
00268     static Bool deconvolveFromBeam(
00269         Quantity& majorFit, Quantity& minorFit,
00270         Quantity& paFit, casa::Bool& successFit, casa::LogIO& os,
00271         const Vector<Quantity>& sourceIn, const GaussianBeam& beam,
00272         const Bool verbose=True
00273     );
00274     */
00275 
00276 //
00277 // Convert 2d shape from world (world parameters=x, y, major axis, 
00278 // minor axis, position angle) to pixel (major, minor, pa).  
00279 // Can handle quantum units 'pix'.  If one width is 
00280 // in pixel units both must be in pixel units.  pixelAxes describes which
00281 // 2 pixel axes of the coordinate system our 2D shape is in.
00282 // If axes are not from the same coordinate type units must be pixels.
00283 // If doRef is True, then x and y are taken from the reference
00284 // value rather than the parameters vector.
00285 //
00286 // On input, pa is N->E (at ref pix) for celestial planes.
00287 // Otherwise pa is in pixel coordinate system +x -> +y
00288 // On output, pa (radians) is positive +x -> +y in pixel frame
00289    static void worldWidthsToPixel (LogIO& os, Vector<Double>& dParameters,
00290                                    const Vector<Quantum<Double> >& parameters,
00291                                    const CoordinateSystem& cSys,
00292                                    const IPosition& pixelAxes,
00293                                    Bool doRef=False); 
00294 
00295 
00296 // Convert 2d shape  from pixels (parameters=x,y, major axis, 
00297 // minor axis, position angle) to world (major, minor, pa)
00298 // at specified location. pixelAxes describes which
00299 // 2 pixel axes of the coordinate system our 2D shape is in.
00300 // If doRef is True, then x and y are taken from the reference
00301 // pixel rather than the paraneters vector.
00302 //
00303 // On input pa is positive for +x -> +y in pixel frame
00304 // On output pa is positive N->E
00305 // Returns True if major/minor exchanged themselves on conversion to world.
00306    static Bool pixelWidthsToWorld (LogIO& os,
00307                                    GaussianBeam& wParameters,
00308                                    const Vector<Double>& pParameters,
00309                                    const CoordinateSystem& cSys,
00310                                    const IPosition& pixelAxes,
00311                                    Bool doRef=False); 
00312 
00313    // write the specified image and add the specified pixels to it.
00314    // Currently no checks are done to ensure the pixel array size and
00315    // mapShape are compatible; the caller is responsible for this check.
00316    static void writeImage(
00317                 const TiledShape& mapShape,
00318                 const CoordinateSystem& coordinateInfo,
00319                 const String& imageName,
00320                 const Array<Float>& pixels, LogIO& log,
00321                 const Array<Bool>& pixelMask = Array<Bool>()
00322    );
00323 
00324    static GaussianBeam makeFakeBeam(
00325                    LogIO& logIO, const CoordinateSystem& csys,
00326                    Bool suppressWarnings = False
00327    );
00328 
00329    static void getUnitAndDoppler(
00330            String& xUnit, String& doppler,
00331            const uInt axis, const CoordinateSystem& csys
00332    );
00333 
00334 private:
00335 
00336 // Convert 2d sky shape (parameters=major axis, minor axis, position angle) 
00337 // from pixels to world at reference pixel. pixelAxes describes which
00338 // 2 pixel axes of the coordinate system our 2D shape is in.
00339 // On input pa is positive for +x -> +y in pixel frame
00340 // On output pa is positive N->E
00341 // Returns True if major/minor exchanged themselves on conversion to world.
00342    static Bool skyPixelWidthsToWorld (LogIO& os,
00343                                       GaussianBeam& wParameters,
00344                                       const CoordinateSystem& cSys,
00345                                       const Vector<Double>& pParameters,
00346                                       const IPosition& pixelAxes, Bool doRef);
00347 
00348 // Convert a length and position angle in world units (for a non-coupled 
00349 // coordinate) to pixels. The length is in some 2D plane in the 
00350 // CoordinateSystem specified  by pixelAxes.
00351    static Double worldWidthToPixel (LogIO& os, Double positionAngle,
00352                                     const Quantum<Double>& length,
00353                                     const CoordinateSystem& cSys,
00354                                     const IPosition& pixelAxes);
00355 
00356 
00357 
00358    static Quantum<Double> pixelWidthToWorld (LogIO& os, Double positionAngle,
00359                                              Double length,
00360                                              const CoordinateSystem& cSys,
00361                                              const IPosition& pixelAxes);
00362 };
00363 
00364 
00365 
00366 } //# NAMESPACE CASA - END
00367 
00368 #ifndef CASACORE_NO_AUTO_TEMPLATES
00369 #include <images/Images/ImageUtilities2.tcc>
00370 #endif //# CASACORE_NO_AUTO_TEMPLATES
00371 #endif