00001 //# ImageFFT.h: FFT an image 00002 //# Copyright (C) 1996,1997,1998,1999,2000,2001 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 //# $Id: ImageFFT.h 20291 2008-03-21 07:19:34Z gervandiepen $ 00027 00028 #ifndef IMAGES_IMAGEFFT_H 00029 #define IMAGES_IMAGEFFT_H 00030 00031 #include <casa/aips.h> 00032 #include <images/Images/ImageInterface.h> 00033 #include <imageanalysis/ImageTypedefs.h> 00034 00035 namespace casa { //# NAMESPACE CASA - BEGIN 00036 00037 class CoordinateSystem; 00038 class IPosition; 00039 template<class T> class Vector; 00040 00041 // <summary> 00042 // FFT an image 00043 // </summary> 00044 00045 // <use visibility=export> 00046 00047 // <reviewed reviewer="" date="yyyy/mm/dd" tests="" demos=""> 00048 // </reviewed> 00049 00050 // <prerequisite> 00051 // <li> <linkto class=LatticeFFT>LatticeFFT</linkto> 00052 // <li> <linkto class=ImageInterface>ImageInterface</linkto> 00053 // <li> <linkto class=TempImage>TempImage</linkto> 00054 // </prerequisite> 00055 00056 // <etymology> 00057 // Take the fast Fourier Transform of an image. 00058 // </etymology> 00059 00060 // <synopsis> 00061 // This class takes the FFT of an image. It can 00062 // take the FFT of just the sky plane(s) of an image or 00063 // the specified axes. 00064 // 00065 // When you specify axes, if any of them are a sky axis (DirectionCoordinate) 00066 // you must give both sky axes. 00067 // 00068 // Masked pixels are given the value 0.0 before the FFT is taken and the 00069 // mask is copied to the output. Note that it is the callers responsibility 00070 // to give the output a mask if the input is masked. Otherwise the mask 00071 // will not be copied to the output 00072 // 00073 // This class holds the FourierTransform internally in a 00074 // <linkto class=TempImage>TempImage</linkto> object. This is 00075 // in memory or on disk depending upon its size and the amount 00076 // of memory in your computer. The algorithm used 00077 // is that in <linkto class=TempLattice>TempLattice</linkto>. 00078 // 00079 // In generating the Fourier Coordinates, it is currently 00080 // assumed that there is no coordinate rotation. This 00081 // needs to be dealt with. 00082 // </synopsis> 00083 // 00084 // <example> 00085 // <srcblock> 00086 // 00087 // // Make a constant image 00088 // 00089 // IPosition shape(2, 10, 20); 00090 // PagedImage<Float> im1(shape, CoordinateUtil::defaultCoords2D(), "im1"); 00091 // im1.set(1.0); 00092 // 00093 // // Create output images with masks if needed 00094 // 00095 // PagedImage<Float> r1(shape, CoordinateUtil::defaultCoords2D(), "real1"); 00096 // PagedImage<Float> i1(shape, CoordinateUtil::defaultCoords2D(), "imag1"); 00097 // if (im1.isMasked()) { 00098 // LCPagedMask mask1 = LCPagedMask(RegionHandler::makeMask (r1, "mask0")); 00099 // mask1.set(True); 00100 // r1.defineRegion ("mask0", ImageRegion(mask1), RegionHandler::Masks); 00101 // r1.setDefaultMask("mask0"); 00102 // LCPagedMask mask2 = LCPagedMask(RegionHandler::makeMask (i1, "mask0")); 00103 // mask2.set(True); 00104 // i1.defineRegion ("mask0", ImageRegion(mask1), RegionHandler::Masks); 00105 // i1.setDefaultMask("mask0"); 00106 // } 00107 // // 00108 // // FFT 00109 // 00110 // ImageFFT fft; 00111 // fft.fftsky(im1); 00112 // 00113 // // The coordinates and mask will be updated 00114 // 00115 // fft.getReal(r1); 00116 // fft.getImag(i1); 00117 // </srcblock> 00118 // </example> 00119 00120 00121 // <motivation> 00122 // Taking the Fourier Transform of an image is a basic part of image analysis 00123 // </motivation> 00124 00125 // <todo asof="1999/09/23"> 00126 // <li> reverse transformations 00127 // </todo> 00128 00129 00130 class ImageFFT 00131 { 00132 public: 00133 ImageFFT (); 00134 00135 ImageFFT(const ImageFFT& other); 00136 00137 // Assignment (reference semantics) 00138 ImageFFT& operator=(const ImageFFT& other); 00139 00140 ~ImageFFT(); 00141 00142 // Do the FFT of the sky plane to the uv plane 00143 // Masked pixels are set to zero before the FT 00144 void fftsky (const ImageInterface<Float>& in); 00145 00146 void fftsky (const ImageInterface<Complex>& in); 00147 00148 00149 // Do the FFT of the specified pixel axes (True to FT). 00150 // The rest are iterated over. 00151 // Masked pixels are set to zero before the FT 00152 void fft (const ImageInterface<Float>& in, 00153 const Vector<Bool>& axes); 00154 00155 // Do the FFT of the specified pixel axes (True to FT). 00156 // The rest are iterated over 00157 // Masked pixels are set to zero before the FT 00158 void fft (const ImageInterface<Complex>& in, 00159 const Vector<Bool>& axes); 00160 00161 // Return the FFT (from the last call to fftsky or fft) in the 00162 // desired form. The CoordinateSystem, MiscInfo, ImageInfo, 00163 // history and units are copied/updated in the output image 00164 // from the image that was FFTd. If the input image is masked, 00165 // and the output image has a writable mask, the mask will 00166 // be transferred. Any output mask should be initialized to 00167 // True before calling these functions. 00168 // <group> 00169 void getComplex (ImageInterface<Complex>& out) const; 00170 void getReal (ImageInterface<Float>& out) const; 00171 void getImaginary (ImageInterface<Float>& out) const; 00172 void getAmplitude (ImageInterface<Float>& out) const; 00173 void getPhase (ImageInterface<Float>& out) const; 00174 // </group> 00175 00176 private: 00177 00178 SPIIC _tempImagePtr; 00179 SPIIF _floatImage; 00180 SPIIC _complexImage; 00181 Bool _done; 00182 00183 // Check axes for multi-dim FFT 00184 void checkAxes(const CoordinateSystem& cSys, uInt ndim, 00185 const Vector<Bool>& axes); 00186 00187 // Copy the mask to the output 00188 void copyMask (ImageInterface<Float>& out) const; 00189 void copyMask (ImageInterface<Complex>& out) const; 00190 void copyMask (ImageInterface<Float>& out, 00191 const ImageInterface<Float>& in) const; 00192 void copyMask (ImageInterface<Float>& out, 00193 const ImageInterface<Complex>& in) const; 00194 void copyMask (ImageInterface<Complex>& out, 00195 const ImageInterface<Float>& in) const; 00196 void copyMask (ImageInterface<Complex>& out, 00197 const ImageInterface<Complex>& in) const; 00198 00199 // Copy MiscInfo, ImageInfo, Unit, logSInk to output 00200 // <group> 00201 void copyMiscellaneous (ImageInterface<Float>& out) const; 00202 void copyMiscellaneous (ImageInterface<Complex>& out) const; 00203 // </group> 00204 00205 void _fftsky2 ( 00206 ImageInterface<Complex>& out, 00207 const ImageInterface<Float>& in, 00208 const Vector<Int>& pixelAxes 00209 ); 00210 00211 void _fftsky2 ( 00212 ImageInterface<Complex>& out, 00213 const ImageInterface<Complex>& in, 00214 const Vector<Int>& pixelAxes 00215 ); 00216 // FFT (Float) given axes 00217 void fft2(ImageInterface<Complex>& out, 00218 const ImageInterface<Float>& in, 00219 const Vector<Bool>& axes); 00220 00221 // FFT (Complex) given axes 00222 void fft3(ImageInterface<Complex>& out, 00223 const ImageInterface<Complex>& in, 00224 const Vector<Bool>& axes); 00225 00226 // Find the sky axes in this CoordinateSystem 00227 Bool _findSky( 00228 Int& dC, Vector<Int>& pixelAxes, 00229 Vector<Int>& worldAxes, const CoordinateSystem& cSys, 00230 Bool throwIt 00231 ); 00232 00233 // Overwrite the coordinate system with Fourier coordinates for sky axes only 00234 void _setSkyCoordinates ( 00235 ImageInterface<Complex>& out, 00236 const CoordinateSystem& csys, const IPosition& shape, 00237 uInt dC 00238 ); 00239 00240 // Overwrite the coordinate system with Fourier coordinates for all desginated axes 00241 void _setCoordinates ( 00242 ImageInterface<Complex>& out, 00243 const CoordinateSystem& cSys, 00244 const Vector<Bool>& axes, 00245 const IPosition& shape 00246 ); 00247 }; 00248 00249 } //# NAMESPACE CASA - END 00250 00251 #endif