30#include "boost/format.hpp"
42template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
45 : _image(new
Image(width, height)),
46 _mask(new
Mask(width, height, planeDict)),
47 _variance(new
Variance(width, height)) {
53template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
64template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
73template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
80 : _image(), _mask(), _variance() {
82 *
this = reader.
read<ImagePixelT, MaskPixelT, VariancePixelT>(
bbox, origin, conformMasks, needAllHdus,
93 if (varianceMetadata) {
98template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
105 : _image(), _mask(), _variance() {
107 *
this = reader.
read<ImagePixelT, MaskPixelT, VariancePixelT>(
bbox, origin, conformMasks, needAllHdus,
118 if (varianceMetadata) {
123template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
126 ImageOrigin origin,
bool conformMasks,
bool needAllHdus,
130 : _image(), _mask(), _variance() {
132 *
this = reader.
read<ImagePixelT, MaskPixelT, VariancePixelT>(
bbox, origin, conformMasks, needAllHdus,
143 if (varianceMetadata) {
148template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
155template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
157 : _image(rhs._image), _mask(rhs._mask), _variance(rhs._variance) {
167template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
171template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
177 : _image(new
Image(*rhs.getImage(),
bbox, origin, deep)),
178 _mask(rhs._mask ? new
Mask(*rhs.getMask(),
bbox, origin, deep) : static_cast<
Mask*>(nullptr)),
179 _variance(rhs._variance ? new
Variance(*rhs.getVariance(),
bbox, origin, deep)
180 : static_cast<
Variance*>(nullptr)) {
184template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
188template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
192template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
196 _image.swap(rhs._image);
197 _mask.swap(rhs._mask);
198 _variance.swap(rhs._variance);
202template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
205 *_image = rhs.
image();
212template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
215 *_image = rhs.
image();
222template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
231template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
240template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
243 (*_image).scaledPlus(c, *rhs.
getImage());
245 (*_variance).scaledPlus(c * c, *rhs.
getVariance());
248template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
255template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
264template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
267 (*_image).scaledMinus(c, *rhs.
getImage());
269 (*_variance).scaledPlus(c * c, *rhs.
getVariance());
272template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
281template <
typename ImagePixelT,
typename VariancePixelT>
282struct productVariance {
283 double operator()(ImagePixelT lhs, ImagePixelT rhs, VariancePixelT varLhs, VariancePixelT varRhs) {
284 return lhs * lhs * varRhs + rhs * rhs * varLhs;
290template <
typename ImagePixelT,
typename VariancePixelT>
291struct scaledProductVariance {
293 scaledProductVariance(
double const c) :
_c(c) {}
294 double operator()(ImagePixelT lhs, ImagePixelT rhs, VariancePixelT varLhs, VariancePixelT varRhs) {
295 return _c *
_c * (lhs * lhs * varRhs + rhs * rhs * varLhs);
300template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
304 if (_image->getDimensions() != rhs._image->
getDimensions()) {
306 boost::str(boost::format(
"Images are of different size, %dx%d v %dx%d") %
307 _image->getWidth() % _image->getHeight() % rhs._image->
getWidth() % rhs._image->
getHeight()));
309 transform_pixels(_image->_getRawView(),
311 _variance->_getRawView(),
312 rhs._variance->_getRawView(),
313 _variance->_getRawView(),
314 productVariance<ImagePixelT, VariancePixelT>());
321template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
325 if (_image->getDimensions() != rhs._image->
getDimensions()) {
327 boost::str(boost::format(
"Images are of different size, %dx%d v %dx%d") %
328 _image->getWidth() % _image->getHeight() % rhs._image->
getWidth() % rhs._image->
getHeight()));
330 transform_pixels(_image->_getRawView(),
332 _variance->_getRawView(),
333 rhs._variance->_getRawView(),
334 _variance->_getRawView(),
335 scaledProductVariance<ImagePixelT, VariancePixelT>(c));
337 (*_image).scaledMultiplies(c, *rhs.
getImage());
341template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
345 *_variance *= rhs * rhs;
351template <
typename ImagePixelT,
typename VariancePixelT>
352struct quotientVariance {
353 double operator()(ImagePixelT lhs, ImagePixelT rhs, VariancePixelT varLhs, VariancePixelT varRhs) {
354 ImagePixelT
const rhs2 = rhs * rhs;
355 return (lhs * lhs * varRhs + rhs2 * varLhs) / (rhs2 * rhs2);
360template <
typename ImagePixelT,
typename VariancePixelT>
361struct scaledQuotientVariance {
363 scaledQuotientVariance(
double c) :
_c(c) {}
364 double operator()(ImagePixelT lhs, ImagePixelT rhs, VariancePixelT varLhs, VariancePixelT varRhs) {
365 ImagePixelT
const rhs2 = rhs * rhs;
366 return (lhs * lhs * varRhs + rhs2 * varLhs) / (
_c *
_c * rhs2 * rhs2);
371template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
375 if (_image->getDimensions() != rhs._image->
getDimensions()) {
377 boost::str(boost::format(
"Images are of different size, %dx%d v %dx%d") %
378 _image->getWidth() % _image->getHeight() % rhs._image->
getWidth() % rhs._image->
getHeight()));
380 transform_pixels(_image->_getRawView(),
382 _variance->_getRawView(),
383 rhs._variance->_getRawView(),
384 _variance->_getRawView(),
385 quotientVariance<ImagePixelT, VariancePixelT>());
392template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
396 if (_image->getDimensions() != rhs._image->
getDimensions()) {
398 str(boost::format(
"Images are of different size, %dx%d v %dx%d") %
399 _image->getWidth() % _image->getHeight() % rhs._image->
getWidth() % rhs._image->
getHeight()));
401 transform_pixels(_image->_getRawView(),
403 _variance->_getRawView(),
404 rhs._variance->_getRawView(),
405 _variance->_getRawView(),
406 scaledQuotientVariance<ImagePixelT, VariancePixelT>(c));
408 (*_image).scaledDivides(c, *rhs.
getImage());
409 *_mask |= *rhs._mask;
412template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
416 *_variance /= rhs * rhs;
420template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
427 writeFits(fitsfile, metadata, imageMetadata, maskMetadata, varianceMetadata);
430template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
437 writeFits(fitsfile, metadata, imageMetadata, maskMetadata, varianceMetadata);
449 hdr->set(
"INHERIT",
true);
450 hdr->set(
"EXTTYPE", exttype);
451 hdr->set(
"EXTNAME", exttype);
456template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
466template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
475 writeFits(fitsfile, imageOptions, maskOptions, varianceOptions, metadata, imageMetadata, maskMetadata,
479template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
488 writeFits(fitsfile, imageOptions, maskOptions, varianceOptions, metadata, imageMetadata, maskMetadata,
492template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
502 header = metadata->deepCopy();
504 header = std::make_shared<daf::base::PropertyList>();
509 "MaskedImage::writeFits can only write to an empty file");
511 if (fitsfile.
getHdu() < 1) {
519 processPlaneMetadata(imageMetadata.
get(), header,
"IMAGE");
520 _image->writeFits(fitsfile, imageOptions, header.
get(), _mask.get());
522 processPlaneMetadata(maskMetadata.
get(), header,
"MASK");
523 _mask->writeFits(fitsfile, maskOptions, header.
get());
525 processPlaneMetadata(varianceMetadata.
get(), header,
"VARIANCE");
526 _variance->writeFits(fitsfile, varianceOptions, header.
get(), _mask.get());
533template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
535 if (!_mask || _mask->getWidth() == 0 || _mask->getHeight() == 0) {
536 _mask = MaskPtr(
new Mask(_image->getBBox()));
539 if (_mask->getDimensions() != _image->getDimensions()) {
542 (boost::format(
"Dimension mismatch: Image %dx%d v. Mask %dx%d") % _image->getWidth() %
543 _image->getHeight() % _mask->getWidth() % _mask->getHeight())
548 if (!_variance || _variance->getWidth() == 0 || _variance->getHeight() == 0) {
549 _variance = VariancePtr(
new Variance(_image->getBBox()));
552 if (_variance->getDimensions() != _image->getDimensions()) {
554 pex::exceptions::LengthError,
555 (boost::format(
"Dimension mismatch: Image %dx%d v. Variance %dx%d") % _image->getWidth() %
556 _image->getHeight() % _variance->getWidth() % _variance->getHeight())
565template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
569 return iterator(_image->begin(), _mask->begin(), _variance->begin());
575 return iterator(imageBegin, maskBegin, varianceBegin);
579template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
586 return iterator(imageEnd, maskEnd, varianceEnd);
589template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
596 return iterator(imageEnd, maskEnd, varianceEnd);
599template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
609template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
619template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
626 return x_iterator(imageBegin, maskBegin, varianceBegin);
629template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
636 return x_iterator(imageEnd, maskEnd, varianceEnd);
639template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
646 return y_iterator(imageBegin, maskBegin, varianceBegin);
649template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
656 return y_iterator(imageEnd, maskEnd, varianceEnd);
659template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
669template <
typename ImagePixelT,
typename MaskPixelT,
typename VariancePixelT>
679template <
typename ImagePixelT1,
typename ImagePixelT2>
690#define INSTANTIATE2(ImagePixelT1, ImagePixelT2) \
691 template bool imagesOverlap<ImagePixelT1, ImagePixelT2>(MaskedImage<ImagePixelT1> const&, \
692 MaskedImage<ImagePixelT2> const&);
#define LSST_EXCEPT(type,...)
Create an exception with a given type.
afw::table::PointKey< int > dimensions
LSST DM logging module built on log4cxx.
#define INSTANTIATE2(ImagePixelT1, ImagePixelT2)
A simple struct that combines the two arguments that must be passed to most cfitsio routines and cont...
void createEmpty()
Create an empty image HDU with NAXIS=0 at the end of the file.
void setHdu(int hdu, bool relative=false)
Set the current HDU.
int countHdus()
Return the number of HDUs in the file.
int getHdu()
Return the current HDU (0-indexed; 0 is the Primary HDU).
void writeMetadata(daf::base::PropertySet const &metadata)
Read a FITS header into a PropertySet or PropertyList.
Lifetime-management for memory that goes into FITS memory files.
typename _view_t::iterator iterator
An STL compliant iterator.
int getWidth() const
Return the number of columns in the image.
lsst::geom::Extent2I getDimensions() const
Return the image's size; useful for passing to constructors.
x_iterator fast_iterator
A fast STL compliant iterator for contiguous images N.b.
typename _view_t::reverse_iterator reverse_iterator
An STL compliant reverse iterator.
int getHeight() const
Return the number of rows in the image.
typename _view_t::x_iterator x_iterator
An iterator for traversing the pixels in a row.
_view_t _getRawView() const
typename _view_t::y_iterator y_iterator
An iterator for traversing the pixels in a column.
Represent a 2-dimensional array of bitmask pixels.
An iterator to the MaskedImage.
A FITS reader class for MaskedImages and their components.
std::shared_ptr< daf::base::PropertyList > readImageMetadata()
Read the FITS header of one of the HDUs.
std::shared_ptr< daf::base::PropertyList > readPrimaryMetadata()
Read the FITS header of one of the HDUs.
std::shared_ptr< daf::base::PropertyList > readMaskMetadata()
Read the FITS header of one of the HDUs.
std::shared_ptr< daf::base::PropertyList > readVarianceMetadata()
Read the FITS header of one of the HDUs.
MaskedImage< ImagePixelT, MaskPixelT, VariancePixelT > read(lsst::geom::Box2I const &bbox=lsst::geom::Box2I(), ImageOrigin origin=PARENT, bool conformMasks=false, bool needAllHdus=false, bool allowUnsafe=false)
Read the full MaskedImage.
A class to manipulate images, masks, and variance as a single object.
void scaledPlus(double const c, MaskedImage const &rhs)
Add a scaled MaskedImage c*rhs to a MaskedImage.
lsst::afw::image::Image< VariancePixelT > Variance
void writeFits(std::string const &fileName, std::shared_ptr< daf::base::PropertySet const > metadata=std::shared_ptr< daf::base::PropertySet const >(), std::shared_ptr< daf::base::PropertySet const > imageMetadata=std::shared_ptr< daf::base::PropertySet const >(), std::shared_ptr< daf::base::PropertySet const > maskMetadata=std::shared_ptr< daf::base::PropertySet const >(), std::shared_ptr< daf::base::PropertySet const > varianceMetadata=std::shared_ptr< daf::base::PropertySet const >()) const
Write a MaskedImage to a regular FITS file.
MaskedImage(unsigned int width, unsigned int height, MaskPlaneDict const &planeDict=MaskPlaneDict())
Construct from a supplied dimensions.
void scaledDivides(double const c, MaskedImage const &rhs)
typename Mask< MaskPixelT >::MaskPlaneDict MaskPlaneDict
The Mask's MaskPlaneDict.
iterator begin() const
Return an iterator to the start of the image.
reverse_iterator rbegin() const
Return a reverse_iterator to the start of the image.
lsst::afw::image::Mask< MaskPixelT > Mask
y_iterator col_end(int x) const
Return an y_iterator to the end of the image.
void scaledMinus(double const c, MaskedImage const &rhs)
Subtract a scaled MaskedImage c*rhs from a MaskedImage.
x_iterator fast_iterator
A fast STL compliant iterator for contiguous images N.b.
MaskedImageIterator< typename Image::reverse_iterator, typename Mask::reverse_iterator, typename Variance::reverse_iterator > reverse_iterator
MaskedImageIterator< typename Image::iterator, typename Mask::iterator, typename Variance::iterator > iterator
MaskedImage & operator-=(ImagePixelT const rhs)
Subtract a scalar rhs from a MaskedImage.
x_iterator row_end(int y) const
Return an x_iterator to the end of the image.
void scaledMultiplies(double const c, MaskedImage const &rhs)
iterator end() const
Return an iterator to the end of the image.
void assign(MaskedImage const &rhs, lsst::geom::Box2I const &bbox=lsst::geom::Box2I(), ImageOrigin origin=PARENT)
Copy pixels from another masked image to a specified subregion of this masked image.
VariancePtr getVariance() const
Return a (shared_ptr to) the MaskedImage's variance.
MaskedImage & operator=(MaskedImage const &rhs)
Make the lhs use the rhs's pixels.
lsst::afw::image::Image< ImagePixelT > Image
x_iterator row_begin(int y) const
Return an x_iterator to the start of the image.
void swap(MaskedImage &rhs)
y_iterator col_begin(int x) const
Return an y_iterator to the start of the image.
reverse_iterator rend() const
Return a reverse_iterator to the end of the image.
MaskedImage & operator+=(ImagePixelT const rhs)
Add a scalar rhs to a MaskedImage.
MaskedImage & operator*=(ImagePixelT const rhs)
iterator at(int const x, int const y) const
Return an iterator at the point (x, y)
MaskedImage & operator/=(ImagePixelT const rhs)
MaskPtr getMask() const
Return a (shared_ptr to) the MaskedImage's mask.
ImagePtr getImage() const
Return a (shared_ptr to) the MaskedImage's image.
A pixel of a MaskedImage.
MaskPixelT mask() const
Return the mask part of a Pixel.
ImagePixelT image() const
Return the image part of a Pixel.
VariancePixelT variance() const
Return the variance part of a Pixel.
A single pixel of the same type as a MaskedImage.
VariancePixelT variance() const
ImagePixelT image() const
Class for storing ordered metadata with comments.
Class for storing generic metadata.
virtual std::shared_ptr< PropertySet > deepCopy() const
Make a deep copy of the PropertySet and all of its contents.
An integer coordinate rectangle.
Reports attempts to exceed implementation-defined length limits for some classes.
Reports errors in the logical structure of the program.
bool imagesOverlap(ImageBase< T1 > const &image1, ImageBase< T2 > const &image2)
Return true if the pixels for two images or masks overlap in memory.
Options for writing an image to FITS.