56LOG_LOGGER _log =
LOG_GET(
"lsst.jointcal.Associations");
127 item->clearBeforeAssoc();
174 ms->setFittedStar(
fs);
181 for (
auto const &
mstar : catalog) {
183 if (
mstar->getFittedStar())
continue;
207 if (refCat.size() == 0) {
209 " reference catalog is empty : stop here "));
217 raErrKey = refCat.getSchema()[
"coord_raErr"];
218 decErrKey = refCat.getSchema()[
"coord_decErr"];
221 auto fluxKey = refCat.getSchema().find<
double>(fluxField).key;
225 fluxErrKey = refCat.getSchema().find<
double>(fluxField +
"Err").key;
228 << fluxField <<
"Err"
229 <<
") not found in reference catalog. Not using ref flux errors.");
239 LOGLS_WARN(_log,
"Not loading proper motions: (pm_ra,pm_dec) fields not found in reference catalog.");
241 LOGLS_WARN(_log,
"Not loading proper motions: RA/Dec proper motion values must be `geom:Angle`: "
245 pmRaErrKey = refCat.getSchema().find<
float>(
"pm_raErr").key;
246 pmDecErrKey = refCat.getSchema().find<
float>(
"pm_decErr").key;
248 LOGLS_WARN(_log,
"Not loading proper motions: error fields not available: " <<
ex.what());
253 pmRaDecCovKey = refCat.getSchema().find<
float>(
"pm_ra_pm_dec_Cov").key;
255 LOGLS_WARN(_log,
"No ra/dec proper motion covariances in refcat: " <<
ex.what());
259 for (
size_t i = 0;
i < refCat.size();
i++) {
260 auto const &record = refCat.get(
i);
262 auto coord = record->get(coordKey);
263 double flux = record->
get(fluxKey);
265 if (fluxErrKey.isValid()) {
334 "Associated " << starMatchList->size() <<
" reference stars among " <<
refStarList.
size());
338 selectFittedStars(minMeasurements);
339 normalizeFittedStars();
342void Associations::selectFittedStars(
int minMeasurements) {
364 if (!fittedStar->getRefStar() && fittedStar->getMeasurementCount() < minMeasurements) {
365 fittedStar->getMeasurementCount()--;
366 mi = catalog.
erase(mi);
376 if ((*fi)->getMeasurementCount() == 0) {
384 LOGLS_INFO(_log,
"Total, valid number of Measured stars: " << totalMeasured <<
", " << validMeasured);
387void Associations::normalizeFittedStars() {
392 fittedStar->setFlux(0.0);
393 fittedStar->getMag() = 0.0;
399 MeasuredStarList &catalog = ccdImage->getCatalogForFit();
400 for (
auto &mi : catalog) {
401 auto fittedStar = mi->getFittedStar();
402 if (fittedStar ==
nullptr)
404 pex::exceptions::RuntimeError,
405 "All measuredStars must have a fittedStar: did you call selectFittedStars()?"));
406 auto point = toCommonTangentPlane->apply(*mi);
407 fittedStar->x += point.x;
408 fittedStar->y += point.y;
409 fittedStar->getFlux() += mi->getFlux();
413 _maxMeasuredStars = 0;
415 auto measurementCount = fi->getMeasurementCount();
416 _maxMeasuredStars += measurementCount;
417 fi->x /= measurementCount;
418 fi->y /= measurementCount;
419 fi->getFlux() /= measurementCount;
420 fi->getMag() = utils::nanojanskyToABMagnitude(fi->getFlux());
428 while (iter !=
end) {
439 LOGLS_INFO(_log,
"Removed " <<
count <<
" fittedStars that had no associated measuredStar.");
443void Associations::assignMags() {
446 for (
auto const &
mstar : catalog) {
448 if (!
fstar)
continue;
459 "DeprojectFittedStars: Fitted stars are already in sidereal coordinates, nothing done ");
470 return item->getCatalogForFit().size() > 0;
483void Associations::collectMCStars(
int realization) {
498 AstrometryTransformIdentity gti;
502 DicStarList mctruthlist(mctruth);
506 for (smI = starMatchList->begin(); smI != starMatchList->end(); smI++) {
507 StarMatch &sm = *smI;
508 BaseStar *bs = sm.s1;
509 MeasuredStar *mstar =
dynamic_cast<MeasuredStar *
>(bs);
511 DicStar *dstar =
dynamic_cast<DicStar *
>(bs);
513 mcstar->GetMCInfo().iflux = dstar->getval(
"iflux");
514 mcstar->GetMCInfo().tflux = dstar->getval(
"sflux");
521 LOGLS_FATAL(_log,
"CollectMCStars Unable to match MCTruth w/ catalog!");
#define LOGLS_WARN(logger, message)
#define LOGLS_FATAL(logger, message)
#define LOGLS_INFO(logger, message)
#define LOGLS_DEBUG(logger, message)
#define LOGLS_TRACE(logger, message)
table::Key< int > detector
#define LSST_EXCEPT(type,...)
Combinatorial searches for linear transformations to go from list1 to list2.
table::Key< table::Array< std::uint8_t > > wcs
constexpr double asArcseconds() const noexcept
size_t nFittedStarsWithAssociatedRefStar() const
Return the number of fittedStars that have an associated refStar.
void cleanFittedStars()
Remove FittedStars that have no measured stars; this can happen after outlier rejection.
void computeCommonTangentPoint()
Sets a shared tangent point for all ccdImages, using the mean of the centers of all ccdImages.
lsst::sphgeom::Circle computeBoundingCircle() const
Return the bounding circle in on-sky (RA, Dec) coordinates containing all CcdImages.
int nCcdImagesValidForFit() const
return the number of CcdImages with non-empty catalogs to-be-fit.
void createCcdImage(afw::table::SourceCatalog &catalog, const std::shared_ptr< lsst::afw::geom::SkyWcs > &wcs, const std::shared_ptr< lsst::afw::image::VisitInfo > &visitInfo, const lsst::geom::Box2I &bbox, const std::string &filter, const std::shared_ptr< afw::image::PhotoCalib > &photoCalib, const std::shared_ptr< afw::cameraGeom::Detector > &detector, int visit, int ccd, const lsst::jointcal::JointcalControl &control)
Create a ccdImage from an exposure catalog and metadata, and add it to the list.
void associateCatalogs(double matchCutInArcsec=0, bool useFittedList=false, bool enlargeFittedList=true)
incrementaly builds a merged catalog of all image catalogs
void setCommonTangentPoint(lsst::geom::Point2D const &commonTangentPoint)
Shared tangent point for all ccdImages (decimal degrees).
Point getCommonTangentPoint() const
Shared tangent point for all ccdImages (decimal degrees).
void collectRefStars(afw::table::SimpleCatalog &refCat, geom::Angle matchCut, std::string const &fluxField, float refCoordinateErr, bool rejectBadFluxes=false)
Collect stars from an external reference catalog and associate them with fittedStars.
CcdImageList ccdImageList
FittedStarList fittedStarList
void prepareFittedStars(int minMeasurements)
Prepare the fittedStar list by making quality cuts and normalizing measurements.
void deprojectFittedStars()
Sends back the fitted stars coordinates on the sky FittedStarsList::inTangentPlaneCoordinates keeps t...
The base class for handling stars. Used by all matching routines.
Handler of an actual image from a single CCD.
MeasuredStarList const & getCatalogForFit() const
Gets the catalog to be used for fitting, which may have been cleaned-up.
FittedStars are objects whose position or flux is going to be fitted, and which come from the associa...
A list of FittedStar s. Such a list is typically constructed by Associations.
bool inTangentPlaneCoordinates
rectangle with sides parallel to axes.
Sources measured on images.
A list of MeasuredStar. They are usually filled in Associations::createCcdImage.
Objects used as position/flux anchors (e.g.
void applyTransform(const Operator &op)
enables to apply a geometrical transform if Star is Basestar or derives from it.
The transformation that handles pixels to sideral transformations (Gnomonic, possibly with polynomial...
This one is the Tangent Plane (called gnomonic) projection (from celestial sphere to tangent plane)
static ConvexPolygon convexHull(std::vector< UnitVector3d > const &points)
Circle getBoundingCircle() const override
SpherePoint averageSpherePoint(std::vector< SpherePoint > const &coords)
AngleUnit constexpr degrees
constexpr double radToDeg(double x) noexcept
BaseStarList & Measured2Base(MeasuredStarList &This)
::std::list< StarMatch >::iterator StarMatchIterator
BaseStarList & Fitted2Base(FittedStarList &This)
std::unique_ptr< StarMatchList > listMatchCollect(const BaseStarList &list1, const BaseStarList &list2, const AstrometryTransform *guess, double maxDist)
assembles star matches.
BaseStarList & Ref2Base(RefStarList &This)
std::string sourceFluxField
"name of flux field in source catalog" ;