diff options
Diffstat (limited to 'fitsy/hcompress.C')
-rw-r--r-- | fitsy/hcompress.C | 119 |
1 files changed, 119 insertions, 0 deletions
diff --git a/fitsy/hcompress.C b/fitsy/hcompress.C new file mode 100644 index 0000000..577ec47 --- /dev/null +++ b/fitsy/hcompress.C @@ -0,0 +1,119 @@ +// Copyright (C) 1999-2018 +// Smithsonian Astrophysical Observatory, Cambridge, MA, USA +// For conditions of distribution and use, see copyright notice in "copyright" + +#include <iostream> +#include <sstream> +#include <iomanip> +using namespace std; + +// Note: currently, hcompress will not work with float or double data with +// BLANK defined, due to the fact that the decompress code takes a int() and +// not an unsigned int() + +#include "hcompress.h" +#include "util.h" + +extern "C" { + int fits_hdecompress(unsigned char *input, int smooth, int *a, int *ny, int *nx, int *scale, int *status); + int fits_hdecompress64(unsigned char *input, int smooth, long long *a, int *ny, int *nx, int *scale, int *status); +} + +template<class T> FitsHcompressm<T>::FitsHcompressm(FitsFile* fits) + : FitsCompressm<T>(fits) +{ + // hcompress parameters + smooth_ = 0; + char name[] = "ZNAME "; + char val[] = "ZVAL "; + for (int ii=0; ii<9; ii++) { + name[5] = '0'+ii; + val[4] = '0'+ii; + if (fits->find(name)) { + char* str = fits->getString(name); + if (!strncmp(str,"SMOOTH",4)) + smooth_ = fits->getInteger(val,4); + } + } + + FitsCompressm<T>::uncompress(fits); +} + +template <class T> int FitsHcompressm<T>::compressed(T* dest, char* sptr, + char* heap, + int kkstart, int kkstop, + int jjstart, int jjstop, + int iistart, int iistop) +{ + double zs = FitsCompressm<T>::bscale_; + if (FitsCompressm<T>::zscale_) + zs = FitsCompressm<T>::zscale_->value(sptr,0); + + double zz = FitsCompressm<T>::bzero_; + if (FitsCompressm<T>::zzero_) + zz = FitsCompressm<T>::zzero_->value(sptr,0); + + int blank = FitsCompressm<T>::blank_; + if (FitsCompressm<T>::zblank_) + blank = (int)FitsCompressm<T>::zblank_->value(sptr,0); + + int icnt=0; + unsigned char* ibuf = (unsigned char*)((FitsBinColumnArray*)FitsCompressm<T>::compress_)->get(heap, sptr, &icnt); + + // ibuf can be NULL + if (!ibuf || !icnt) + return 0; + + int ocnt = FitsCompressm<T>::tilesize_; + int nx,ny,scale; + int status=0; + int ll=0; + + switch (FitsCompressm<T>::bitpix_) { + case 8: + case 16: + { + int* obuf = new int[ocnt]; + if (fits_hdecompress(ibuf, smooth_, obuf, &nx, &ny, &scale, &status)) { + internalError("Fitsy++ hcompress bad inflate result"); + return 0; + } + for (int kk=kkstart; kk<kkstop; kk++) + for (int jj=jjstart; jj<jjstop; jj++) + for (int ii=iistart; ii<iistop; ii++,ll++) + dest[kk*FitsCompressm<T>::width_*FitsCompressm<T>::height_ + jj*FitsCompressm<T>::width_ + ii] = FitsCompressm<T>::getValue(obuf+ll,zs,zz,blank); + + if (obuf) + delete [] obuf; + } + break; + case 32: + case -32: + case -64: + { + long long* obuf = new long long[ocnt]; + if (fits_hdecompress64(ibuf, smooth_, obuf, &nx, &ny, &scale, &status)) { + internalError("Fitsy++ hcompress bad inflate result"); + return 0; + } + for (int kk=kkstart; kk<kkstop; kk++) + for (int jj=jjstart; jj<jjstop; jj++) + for (int ii=iistart; ii<iistop; ii++,ll++) + dest[kk*FitsCompressm<T>::width_*FitsCompressm<T>::height_ + jj*FitsCompressm<T>::width_ + ii] = FitsCompressm<T>::getValue((int*)obuf+ll,zs,zz,blank); + + if (obuf) + delete [] obuf; + } + break; + } + + return 1; +} + +template class FitsHcompressm<unsigned char>; +template class FitsHcompressm<short>; +template class FitsHcompressm<unsigned short>; +template class FitsHcompressm<int>; +template class FitsHcompressm<long long>; +template class FitsHcompressm<float>; +template class FitsHcompressm<double>; |