47 #pragma clang diagnostic push 48 #pragma clang diagnostic ignored "-Wunused-variable" 49 #pragma clang diagnostic pop 50 #include "boost/format.hpp" 51 #include "boost/filesystem/path.hpp" 53 #include "boost/functional/hash.hpp" 67 #include "boost/mpl/vector.hpp" 68 #include "boost/gil/gil_all.hpp" 92 typedef detail::MaskPlaneDict::value_type value_type;
93 typedef detail::MaskPlaneDict::const_iterator const_iterator;
96 : _dict(dict), _hash(_calcHash()) {}
99 bool operator==(MapWithHash
const& rhs)
const {
return _hash == rhs._hash; }
101 const_iterator
begin()
const {
return _dict.begin(); }
102 const_iterator
end()
const {
return _dict.end(); }
103 const_iterator
find(detail::MaskPlaneDict::key_type
const&
name)
const {
return _dict.find(name); }
110 bool empty()
const {
return _dict.empty(); }
112 void clear() { _dict.clear(); }
117 if (_dict.find(str) != _dict.end()) {
135 _hash = (_hash << 1) ^
143 bool operator!=(MapWithHash
const& lhs, MapWithHash
const& rhs) {
return !(lhs == rhs); }
154 friend class ::lsst::afw::image::DictState;
158 MaskDict(MapWithHash
const* dict) : MapWithHash(*dict) {}
173 for (MapWithHash::const_iterator
ptr = begin();
ptr !=
end(); ++
ptr) {
197 _dicts[_defaultMaskDict.get()] = _dictCounter++;
201 _defaultMaskDict.reset();
203 for (HandleList::iterator
ptr = _dicts.begin();
ptr != _dicts.end(); ++
ptr) {
209 template <
typename FunctorT>
210 void forEachMaskDict(FunctorT func) {
211 for (HandleList::const_iterator
ptr = _dicts.begin();
ptr != _dicts.end(); ++
ptr) {
218 static bool first =
true;
221 setInitMaskBits(_defaultMaskDict);
226 return _defaultMaskDict;
230 _defaultMaskDict = newDefaultMaskDict;
232 return _defaultMaskDict;
235 void addDict(MapWithHash* dict) { _dicts[dict] = _dictCounter++; }
237 void eraseDict(MapWithHash* dict) { _dicts.erase(dict); }
241 addDict(_defaultMaskDict.get());
243 return _defaultMaskDict;
251 static DictState _state;
268 MapWithHash mwh(mpd);
270 _state.addDict(dict.
get());
277 return _state.setDefaultDict(dict);
283 _state.addDict(dict.
get());
302 int id = it->second + 1;
304 for (
int i = 0; i <
id; ++i) {
305 MapWithHash::const_iterator
const it =
319 MapWithHash::const_iterator i = find(name);
321 return (i ==
end()) ? -1 : i->second;
334 dict->add(
"BAD", ++i);
335 dict->add(
"SAT", ++i);
336 dict->add(
"INTRP", ++i);
337 dict->add(
"CR", ++i);
338 dict->add(
"EDGE", ++i);
339 dict->add(
"DETECTED", ++i);
340 dict->add(
"DETECTED_NEGATIVE", ++i);
341 dict->add(
"SUSPECT", ++i);
342 dict->add(
"NO_DATA", ++i);
346 template <
typename MaskPixelT>
348 LOGL_DEBUG(
"afw.image.Mask",
"Number of mask planes: %d", getNumPlanesMax());
353 template <
typename MaskPixelT>
356 _initializePlanes(planeDefs);
360 template <
typename MaskPixelT>
364 _initializePlanes(planeDefs);
365 *
this = initialValue;
368 template <
typename MaskPixelT>
371 _initializePlanes(planeDefs);
375 template <
typename MaskPixelT>
379 _initializePlanes(planeDefs);
380 *
this = initialValue;
383 template <
typename MaskPixelT>
386 _initializePlanes(planeDefs);
390 template <
typename MaskPixelT>
393 _initializePlanes(planeDefs);
394 *
this = initialValue;
397 template <
typename MaskPixelT>
400 :
ImageBase<MaskPixelT>(rhs, bbox, origin, deep), _maskDict(rhs._maskDict) {}
402 template <
typename MaskPixelT>
404 :
ImageBase<MaskPixelT>(rhs, deep), _maskDict(rhs._maskDict) {}
406 template <
typename MaskPixelT>
409 template <
typename MaskPixelT>
412 template <
typename MaskPixelT>
415 :
image::
ImageBase<MaskPixelT>(array, deep, xy0), _maskDict(detail::MaskDict::makeMaskDict()) {}
417 template <
typename PixelT>
422 swap(_maskDict, rhs._maskDict);
425 template <
typename PixelT>
430 template <
typename MaskPixelT>
438 template <
typename MaskPixelT>
443 template <
typename MaskPixelT>
450 #ifndef DOXYGEN // doc for this section is already in header 452 template <
typename MaskPixelT>
458 *
this =
Mask(fitsfile, metadata, bbox, origin, conformMasks);
461 template <
typename MaskPixelT>
468 *
this =
Mask(fitsfile, metadata, bbox, origin, conformMasks);
471 template <
typename MaskPixelT>
476 typedef boost::mpl::vector<unsigned char, unsigned short, short, std::int32_t> fits_mask_types;
482 fits_read_image<fits_mask_types>(fitsfile, *
this, *metadata,
bbox, origin);
500 template <
typename MaskPixelT>
508 template <
typename MaskPixelT>
516 template <
typename MaskPixelT>
522 template <
typename MaskPixelT>
530 template <
typename MaskPixelT>
538 template <
typename MaskPixelT>
542 header ? header->deepCopy() : std::make_shared<dafBase::PropertySet>();
544 fitsfile.
writeImage(*
this, options, useHeader);
550 struct addPlaneFunctor {
554 detail::MaskPlaneDict::const_iterator
const it =
558 std::placeholders::_1),
560 if (it != dict->end()) {
564 if (dict->find(
_name) == dict->end()) {
574 template <
typename MaskPixelT>
577 MaskPlaneDict const& mpd = _maskPlaneDict()->getMaskPlaneDict();
578 for (MaskPlaneDict::const_iterator iter = mpd.
begin(); iter != mpd.
end(); ++iter) {
579 if (value & getBitMask(iter->second)) {
580 if (result.
size() > 0) {
583 result += iter->first;
589 template <
typename MaskPixelT>
591 int id = getMaskPlaneNoThrow(name);
594 id = _maskPlaneDict()->getUnusedPlane();
604 _state.forEachMaskDict(addPlaneFunctor(name,
id));
609 template <
typename MaskPixelT>
617 _maskPlaneDict()->add(name, planeId);
622 template <
typename MaskPixelT>
624 return _maskDict->getMaskPlaneDict();
627 template <
typename MaskPixelT>
635 _maskPlaneDict()->erase(name);
638 template <
typename MaskPixelT>
647 _maskDict = _maskDict->clone();
650 _maskDict->erase(name);
657 template <
typename MaskPixelT>
659 return (planeId >= 0 && planeId <
getNumPlanesMax()) ? (1 << planeId) : 0;
662 template <
typename MaskPixelT>
664 MaskPlaneDict const& mpd = _maskPlaneDict()->getMaskPlaneDict();
666 for (MaskPlaneDict::const_iterator i = mpd.
begin(); i != mpd.
end(); ++i) {
667 if (planeId == i->second) {
668 MaskPixelT
const bitmask = getBitMaskNoThrow(planeId);
679 template <
typename MaskPixelT>
681 int const plane = getMaskPlaneNoThrow(name);
691 template <
typename MaskPixelT>
696 template <
typename MaskPixelT>
701 template <
typename MaskPixelT>
703 MaskPixelT mpix = 0x0;
710 template <
typename MaskPixelT>
712 return _maskPlaneDict()->size();
715 template <
typename MaskPixelT>
717 _maskPlaneDict()->clear();
720 template <
typename MaskPixelT>
725 template <
typename MaskPixelT>
727 *
this &= ~getBitMask(planeId);
730 template <
typename MaskPixelT>
734 if (*_maskDict == *currentMD) {
742 MaskPixelT keepBitmask = 0;
743 MaskPixelT canonicalMask[
sizeof(MaskPixelT) * 8];
744 MaskPixelT currentMask[
sizeof(MaskPixelT) * 8];
747 for (MaskPlaneDict::const_iterator i = currentPlaneDict.
begin(); i != currentPlaneDict.
end(); i++) {
749 int const currentPlaneNumber = i->second;
750 int canonicalPlaneNumber = getMaskPlaneNoThrow(name);
752 if (canonicalPlaneNumber < 0) {
756 if (canonicalPlaneNumber == currentPlaneNumber) {
757 keepBitmask |= getBitMask(canonicalPlaneNumber);
759 canonicalMask[numReMap] = getBitMask(canonicalPlaneNumber);
760 currentMask[numReMap] = getBitMaskNoThrow(currentPlaneNumber);
767 for (
int r = 0; r != this->
getHeight(); ++r) {
772 MaskPixelT newPixel = pixel & keepBitmask;
773 for (
int i = 0; i < numReMap; i++) {
774 if (pixel & currentMask[i]) newPixel |= canonicalMask[i];
786 template <
typename MaskPixelT>
791 template <
typename MaskPixelT>
797 template <
typename MaskPixelT>
802 template <
typename MaskPixelT>
808 template <
typename MaskPixelT>
814 template <
typename MaskPixelT>
820 template <
typename MaskPixelT>
822 if (*_maskDict != *other._maskDict) {
827 template <
typename MaskPixelT>
830 [&val](MaskPixelT
const& l) -> MaskPixelT {
return l |
val; });
834 template <
typename MaskPixelT>
836 checkMaskDictionaries(rhs);
844 [](MaskPixelT
const& l, MaskPixelT
const& r) -> MaskPixelT {
return l | r; });
848 template <
typename MaskPixelT>
854 template <
typename MaskPixelT>
856 checkMaskDictionaries(rhs);
864 [](MaskPixelT
const& l, MaskPixelT
const& r) -> MaskPixelT {
return l & r; });
868 template <
typename MaskPixelT>
871 [&val](MaskPixelT
const& l) -> MaskPixelT {
return l ^
val; });
875 template <
typename MaskPixelT>
877 checkMaskDictionaries(rhs);
885 [](MaskPixelT
const& l, MaskPixelT
const& r) -> MaskPixelT {
return l ^ r; });
889 template <
typename MaskPixelT>
891 MaskPixelT
const bitMask = getBitMask(planeId);
893 for (
int x = x0;
x <= x1;
x++) {
898 template <
typename MaskPixelT>
906 NameList paramNames = metadata->paramNames(
false);
907 for (NameList::const_iterator i = paramNames.begin(); i != paramNames.end(); ++i) {
908 if (i->compare(0, maskPlanePrefix.size(), maskPlanePrefix) == 0) {
909 metadata->remove(*i);
913 MaskPlaneDict const& mpd = _maskPlaneDict()->getMaskPlaneDict();
916 for (MaskPlaneDict::const_iterator i = mpd.
begin(); i != mpd.
end(); ++i) {
918 int const planeNumber = i->second;
920 if (planeName !=
"") {
921 metadata->add(maskPlanePrefix + planeName, planeNumber);
926 template <
typename MaskPixelT>
933 NameList paramNames = metadata->paramNames(
false);
934 int numPlanesUsed = 0;
937 for (NameList::const_iterator i = paramNames.begin(); i != paramNames.end(); ++i) {
938 if (i->compare(0, maskPlanePrefix.size(), maskPlanePrefix) == 0) {
941 int const planeId = metadata->getAsInt(*i);
943 MaskPlaneDict::const_iterator plane = newDict.
find(planeName);
944 if (plane != newDict.
end() && planeId != plane->second) {
947 for (MaskPlaneDict::const_iterator j = newDict.
begin(); j != newDict.
end(); ++j) {
948 if (planeId == j->second) {
951 planeName % planeId % j->first));
961 newDict[planeName] = planeId;
967 template <
typename MaskPixelT>
975 template <
typename MaskPixelT>
978 template <
typename MaskPixelT>
static std::string interpret(MaskPixelT value)
Interpret a mask value as a comma-separated list of mask plane names.
afw::table::PointKey< int > dimensions
static void clearMaskPlaneDict()
Reset the maskPlane dictionary.
std::string const & _name
static int getMaskPlane(const std::string &name)
Return the mask plane number corresponding to a plane name.
Class for storing ordered metadata with comments.
int getHeight() const
Return the number of rows in the image.
std::map< std::string, int > MaskPlaneDict
Reports attempts to exceed implementation-defined length limits for some classes. ...
Options for writing an image to FITS.
Mask & operator=(MaskPixelT const rhs)
_view_t::x_iterator x_iterator
An iterator for traversing the pixels in a row.
bool operator!=(CoordKey const &lhs, CoordKey const &rhs)
Compare CoordKeys for equality using the constituent Keys.
bool operator==(CoordKey const &lhs, CoordKey const &rhs)
Compare CoordKeys for equality using the constituent Keys.
static void addMaskPlanesToMetadata(std::shared_ptr< lsst::daf::base::PropertySet >)
Given a PropertySet, replace any existing MaskPlane assignments with the current ones.
static int getNumPlanesUsed()
A simple struct that combines the two arguments that must be passed to most cfitsio routines and cont...
The base class for all image classed (Image, Mask, MaskedImage, ...)
void removeAndClearMaskPlane(const std::string &name, bool const removeFromDefault=false)
Clear all pixels of the specified mask and remove the plane from the mask plane dictionary; optionall...
int getUnusedPlane() const
static MaskPlaneDict parseMaskPlaneMetadata(std::shared_ptr< lsst::daf::base::PropertySet const > metadata)
Given a PropertySet that contains the MaskPlane assignments, setup the MaskPlanes.
x_iterator row_begin(int y) const
Return an x_iterator to the start of the y'th row.
#define LOGL_DEBUG(logger, message...)
Log a debug-level message using a varargs/printf style interface.
ImageBase< MaskPixelT >::PixelReference operator()(int x, int y)
get a reference to the specified pixel
iterator end() const
Return an STL compliant iterator to the end of the image.
LSST DM logging module built on log4cxx.
Mask(unsigned int width, unsigned int height, MaskPlaneDict const &planeDefs=MaskPlaneDict())
Construct a Mask initialized to 0x0.
int getMaskPlane(const std::string &name) const
A base class for image defects.
Represent a 2-dimensional array of bitmask pixels.
Lifetime-management for memory that goes into FITS memory files.
def format(config, name=None, writeSourceLine=True, prefix="", verbose=False)
void setMaskPlaneValues(const int plane, const int x0, const int x1, const int y)
Set the bit specified by "planeId" for pixels (x0, y) ...
A class used to request that array accesses be checked.
static MaskPixelT getPlaneBitMask(const std::vector< std::string > &names)
Return the bitmask corresponding to a vector of plane names OR'd together.
void swap(ImageBase &rhs)
MaskPlaneDict const & getMaskPlaneDict() const
Return the Mask's maskPlaneDict.
void setHdu(int hdu, bool relative=false)
Set the current HDU.
static void listMaskDicts()
static std::shared_ptr< MaskDict > incrDefaultVersion()
#define LSST_EXCEPT(type,...)
Create an exception with a given type.
static void removeMaskPlane(const std::string &name)
static std::shared_ptr< MaskDict > makeMaskDict()
static int getNumPlanesMax()
Mask & operator &=(Mask const &rhs)
AND a Mask into a Mask.
int getWidth() const
Return the number of columns in the image.
std::shared_ptr< MaskDict > clone() const
Reports invalid arguments.
Mask & operator|=(Mask const &rhs)
OR a Mask into a Mask.
x_iterator row_end(int y) const
Return an x_iterator to the end of the y'th row.
table::PointKey< int > pixel
ItemVariant const * other
static std::shared_ptr< MaskDict > setDefaultDict(std::shared_ptr< MaskDict > dict)
void conformMaskPlanes(const MaskPlaneDict &masterPlaneDict)
Adjust this mask to conform to the standard Mask class's mask plane dictionary, adding any new mask p...
void writeFits(std::string const &fileName, std::shared_ptr< lsst::daf::base::PropertySet const > metadata=std::shared_ptr< lsst::daf::base::PropertySet >(), std::string const &mode="w") const
Write a mask to a regular FITS file.
lsst::geom::Extent2I getDimensions() const
Return the image's size; useful for passing to constructors.
Mask & operator^=(Mask const &rhs)
XOR a Mask into a Mask.
void clearMaskPlane(int plane)
Clear the specified bit in all pixels.
void writeImage(ndarray::Array< T const, N, C > const &array)
Write an ndarray::Array to a FITS image HDU.
_view_t _getRawView() const
An integer coordinate rectangle.
void clearAllMaskPlanes()
Clear all the pixels.
Reports when the result of an operation cannot be represented by the destination type.
static int addMaskPlane(const std::string &name)
PixelReference operator()(int x, int y)
Reports errors that are due to events beyond the control of the program.
void printMaskPlanes() const
print the mask plane dictionary to std::cout