4 #include "astrometry/solver.h" 5 #include "astrometry/index.h" 6 #include "astrometry/starkd.h" 7 #include "astrometry/fitsioutils.h" 8 #include "astrometry/fitstable.h" 17 #include "boost/format.hpp" 24 #pragma clang diagnostic push 25 #pragma clang diagnostic ignored "-Wunused-variable" 28 #pragma clang diagnostic pop 36 namespace astrometryNet {
46 char const *indexName)
48 float *
col =
static_cast<float*
>(fitstable_read_column_inds(tag, colName, type, starinds, nstars));
51 str(
boost::format(
"Unable to read data for %s from %s") % colName % indexName));
64 char const* isStarCol,
73 size_t const nMag = magColInfoList.
size();
75 for (
auto mc = magColInfoList.
cbegin(); mc != magColInfoList.
cend(); ++mc) {
76 if (mc->filterName.empty()) {
78 "Magnitude names cannot be empty strings.");
82 if (mc->magCol.empty()) {
84 "Magnitude column names cannot be empty strings.");
89 auto icrsCoord = ctrCoord.
toIcrs();
91 double decDeg = icrsCoord.getLatitude().asDegrees();
93 radecdeg2xyzarr(raDeg, decDeg, xyz);
94 double r2 = deg2distsq(radius.
asDegrees());
99 "centroid on some exposure; invalid unless \"hasCentroid\" is true)",
"pixels");
100 auto hasCentroidKey = schema.addField<afwTable::Flag>(
"hasCentroid",
101 "true if centroid field has been set");
108 for (
auto mc = magColInfoList.
cbegin(); mc != magColInfoList.
cend(); ++mc) {
112 schema.addField<
double>(
113 mc->filterName +
"_flux",
114 mc->filterName +
" flux"));
117 schema.addField<
double>(
118 mc->filterName +
"_fluxSigma",
119 mc->filterName +
" flux uncertainty (sigma)"));
125 resolvedKey = schema.addField<afwTable::Flag>(
127 "set if the reference object is resolved");
131 variableKey = schema.addField<afwTable::Flag>(
133 "set if the reference object is variable");
137 "set if the reference object can be used in photometric calibration");
152 index_t* ind = (*pind);
154 double *radecs = NULL;
155 int *starinds = NULL;
157 startree_search_for(ind->starkd, xyz, r2, NULL, &radecs, &starinds, &nstars);
168 bool* stargal = NULL;
170 if (idCol || nMag || isStarCol || isVarCol) {
171 fitstable_t* tag = startree_get_tagalong(ind->starkd);
172 tfits_type flt = fitscolumn_float_type();
173 tfits_type boo = fitscolumn_boolean_type();
174 tfits_type i64 = fitscolumn_i64_type();
178 "astrometry_net_data index file %s does not contain a tag-along table, " 179 "so can't retrieve extra columns. idCol=%s, isStarCol=%s, isVarCol=%s") %
180 ind->indexname % idCol % isStarCol % isVarCol);
181 msg +=
", mag columns=[";
182 for (
unsigned int i=0; i<nMag; i++) {
186 msg +=
" name='" + magColInfoList[i].filterName +
187 "', mag='" + magColInfoList[i].magCol +
188 "', magErr='" + magColInfoList[i].magErrCol +
"'";
190 msg +=
" ]. You may need to edit the $ASTROMETRY_NET_DATA_DIR/andConfig.py file to set idColumn=None, etc.";
195 id =
static_cast<int64_t*
>(fitstable_read_column_inds(tag, idCol, i64, starinds, nstars));
198 str(
boost::format(
"Unable to read data for %s from %s") % idCol % ind->indexname));
201 if (
id && uniqueIds) {
211 for (
int i=0; i<nstars; i++) {
213 if (uids.
insert(
id[i]).second) {
217 starinds[nkeep] = starinds[i];
218 radecs[nkeep*2+0] = radecs[i*2+0];
219 radecs[nkeep*2+1] = radecs[i*2+1];
239 for (
auto mc = magColInfoList.
cbegin(); mc != magColInfoList.
cend(); ++mc) {
240 char const* col = mc->magCol.c_str();
241 mag.
push_back(read_column(tag, col, flt, starinds, nstars, ind->indexname));
243 char const* col = mc->magErrCol.c_str();
244 magErr.
push_back(read_column(tag, col, flt, starinds, nstars, ind->indexname));
254 uint8_t* sg =
static_cast<uint8_t*
>(fitstable_read_column_inds(
255 tag, isStarCol, fitscolumn_u8_type(), starinds, nstars));
256 stargal =
static_cast<bool*
>(malloc(nstars));
259 str(
boost::format(
"Unable to read data for %s from %s") % isStarCol % ind->indexname));
261 for (
int j=0; j<nstars; j++) {
262 stargal[j] = (sg[j] > 0);
267 var =
static_cast<bool*
>(fitstable_read_column_inds(tag, isVarCol, boo, starinds, nstars));
270 str(
boost::format(
"Unable to read data for %s from %s") % isVarCol % ind->indexname));
275 for (
int i=0; i<nstars; i++) {
291 src->set(hasCentroidKey,
false);
293 assert(fluxKey.size() == nMag);
295 assert(fluxErrKey.
size() == magErr.
size());
299 for (
auto mc = magColInfoList.
cbegin(); mc != magColInfoList.
cend(); ++mc, ++j) {
307 src->set(fluxKey[j], flux);
312 src->set(fluxErrKey[ej], fluxErr);
316 assert(ej == fluxErrKey.
size());
318 bool photometric =
true;
320 src->set(resolvedKey, !stargal[i]);
321 photometric &= stargal[i];
324 src->set(variableKey, var[i]);
325 photometric &= (!var[i]);
327 src->set(photometricKey, photometric);
331 for (
size_t j=0; j<mag.
size(); ++j) {
334 for (
size_t j=0; j<magErr.
size(); ++j) {
Defines the fields and offsets for a table.
lsst::afw::table::SimpleCatalog getCatalogImpl(std::vector< index_t *> inds, lsst::afw::coord::Coord const &ctrCoord, lsst::afw::geom::Angle const &radius, const char *idCol, std::vector< MagColInfo > const &magColInfoList, const char *starGalCol, const char *varCol, bool uniqueIds=true)
Implementation for index_t::getCatalog method.
lsst::afw::geom::Angle getLongitude() const
The main access method for the longitudinal coordinate.
static PointKey addFields(Schema &schema, std::string const &name, std::string const &doc, std::string const &unit)
Add a pair of _x, _y fields to a Schema, and return a PointKey that points to them.
static Schema makeMinimalSchema()
Return a minimal schema for Simple tables and records.
afw::table::Schema schema
double fluxErrFromABMagErr(double magErr, double mag)
Compute flux error in Janskys from AB magnitude error and AB magnitude.
AngleUnit constexpr degrees
constant with units of degrees
virtual IcrsCoord toIcrs() const
Convert ourself to ICRS: RA, Dec (basically J2000)
Include files required for standard LSST Exception handling.
double fluxFromABMag(double mag)
Compute flux in Janskys from AB magnitude.
A class representing an angle.
A base class for image defects.
Custom catalog class for record/table subclasses that are guaranteed to have an ID, and should generally be sorted by that ID.
def format(config, name=None, writeSourceLine=True, prefix="", verbose=False)
A polymorphic functor base class for generating record IDs for a table.
#define LSST_EXCEPT(type,...)
Create an exception with a given type and message and optionally other arguments (dependent on the ty...
A class used as a handle to a particular field in a table.
Record class that must contain a unique ID field and a celestial coordinate field.
constexpr double asDegrees() const noexcept
Return an Angle's value in degrees.
This is the base class for spherical coordinates.
SortedCatalogT< SimpleRecord > SimpleCatalog
A class to handle Icrs coordinates (inherits from Coord)
static std::shared_ptr< SimpleTable > make(Schema const &schema, std::shared_ptr< IdFactory > const &idFactory)
Construct a new table.