Loading [MathJax]/extensions/tex2jax.js
LSST Applications g04dff08e69+42feea4ef2,g0fba68d861+a0b9de4ea6,g1ec0fe41b4+f536777771,g1fd858c14a+42269675ea,g35bb328faa+fcb1d3bbc8,g4af146b050+bbef1ba6f0,g4d2262a081+8f21adb3a6,g53246c7159+fcb1d3bbc8,g5a012ec0e7+b20b785ecb,g60b5630c4e+43e3f0d37c,g6273192d42+e9a7147bac,g67b6fd64d1+4086c0989b,g78460c75b0+2f9a1b4bcd,g786e29fd12+cf7ec2a62a,g7b71ed6315+fcb1d3bbc8,g7bbe65ff3e+43e3f0d37c,g8352419a5c+fcb1d3bbc8,g87b7deb4dc+43704db330,g8852436030+eb2388797a,g89139ef638+4086c0989b,g9125e01d80+fcb1d3bbc8,g94187f82dc+43e3f0d37c,g989de1cb63+4086c0989b,g9d31334357+43e3f0d37c,g9f33ca652e+9b312035f9,gabe3b4be73+1e0a283bba,gabf8522325+fa80ff7197,gb1101e3267+61f2793e68,gb58c049af0+f03b321e39,gb89ab40317+4086c0989b,gc0bb628dac+834c1753f9,gcf25f946ba+eb2388797a,gd6cbbdb0b4+af3c3595f5,gde0f65d7ad+9e0145b227,ge278dab8ac+d65b3c2b70,ge410e46f29+4086c0989b,gf23fb2af72+37a5db1cfd,gf67bdafdda+4086c0989b,v29.0.0.rc7
LSST Data Management Base Package
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Modules Pages
wcsUtils.cc
Go to the documentation of this file.
1// -*- lsst-c++ -*-
2
3/*
4 * LSST Data Management System
5 * Copyright 2018 LSST Corporation.
6 *
7 * This product includes software developed by the
8 * LSST Project (http://www.lsst.org/).
9 *
10 * This program is free software: you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation, either version 3 of the License, or
13 * (at your option) any later version.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 *
20 * You should have received a copy of the LSST License Statement and
21 * the GNU General Public License along with this program. If not,
22 * see <http://www.lsstcorp.org/LegalNotices/>.
23 */
24
25#include <cmath>
26#include <memory>
27#include <vector>
28
29#include "lsst/afw/table/fwd.h"
34
35namespace lsst {
36namespace afw {
37namespace table {
38namespace {
39
40// Get the schema from a record
41Schema getSchema(BaseRecord const &record) { return record.getSchema(); }
42
43// Get the schema from a shared pointer to a record
44Schema getSchema(std::shared_ptr<const BaseRecord> const record) { return record->getSchema(); }
45
46// Get a value from a record
47template <typename Key>
48inline typename Key::Value getValue(BaseRecord const &record, Key const &key) {
49 return record.get(key);
50}
51
52// Get a value from a shared pointer to a record
53template <typename Key>
54inline typename Key::Value getValue(std::shared_ptr<const BaseRecord> const record, Key const &key) {
55 return record->get(key);
56}
57
58// Set a value in a record
59template <typename Key>
60inline void setValue(SimpleRecord &record, Key const &key, typename Key::Value const &value) {
61 record.set(key, value);
62}
63
64// Set a value in a shared pointer to a record
65template <typename Key>
66inline void setValue(std::shared_ptr<SimpleRecord> record, Key const &key, typename Key::Value const &value) {
67 record->set(key, value);
68}
69
70} // namespace
71
72template <typename ReferenceCollection>
73void updateRefCentroids(geom::SkyWcs const &wcs, ReferenceCollection &refList) {
74 if (refList.empty()) {
75 return;
76 }
77 auto const schema = getSchema(refList[0]);
78 CoordKey const coordKey(schema["coord"]);
79 Point2DKey const centroidKey(schema["centroid"]);
80 Key<Flag> const hasCentroidKey(schema["hasCentroid"]);
82 skyList.reserve(refList.size());
83 for (auto const &record : refList) {
84 skyList.emplace_back(getValue(record, coordKey));
85 }
86 std::vector<lsst::geom::Point2D> const pixelList = wcs.skyToPixel(skyList);
87 auto pixelPos = pixelList.cbegin();
88 for (auto &refObj : refList) {
89 setValue(refObj, centroidKey, *pixelPos);
90 setValue(refObj, hasCentroidKey, true);
91 ++pixelPos;
92 }
93}
94
95Eigen::Matrix2f calculateCoordCovariance(geom::SkyWcs const &wcs, lsst::geom::Point2D center,
96 Eigen::Matrix2f err) {
97 if (!std::isfinite(center.getX()) || !std::isfinite(center.getY())) {
98 return Eigen::Matrix2f::Constant(NAN);
99 }
100 // Get the derivative of the pixel-to-sky transformation, then use it to
101 // propagate the centroid uncertainty to coordinate uncertainty. Note that
102 // the calculation is done in arcseconds, then converted to radians in
103 // order to achieve higher precision.
104 const static double scale = 1.0 / 3600.0;
105 const static Eigen::Matrix2d cdMatrix{{scale, 0}, {0, scale}};
106
107 lsst::geom::SpherePoint skyCenter = wcs.pixelToSky(center);
108 auto localGnomonicWcs = geom::makeSkyWcs(center, skyCenter, cdMatrix);
109 auto measurementToLocalGnomonic = wcs.getTransform()->then(*localGnomonicWcs->getTransform()->inverted());
110
111 Eigen::Matrix2d localMatrix = measurementToLocalGnomonic->getJacobian(center);
112 Eigen::Matrix2f d = localMatrix.cast<float>() * scale * (lsst::geom::PI / 180.0);
113
114 Eigen::Matrix2f skyCov = d * err * d.transpose();
115
116 // Multiply by declination correction matrix in order to get sigma(RA) * cos(Dec) for the uncertainty
117 // in RA, and cov(RA, Dec) * cos(Dec) for the RA/Dec covariance:
118 float cosDec = std::cos(skyCenter.getDec().asRadians());
119 Eigen::Matrix2f decCorr{{cosDec, 0}, {0, 1.0}};
120 Eigen::Matrix2f skyCovCorr = decCorr * skyCov * decCorr;
121 return skyCovCorr;
122}
123
124template <typename SourceCollection>
125void updateSourceCoords(geom::SkyWcs const &wcs, SourceCollection &sourceList, bool include_covariance) {
126 if (sourceList.empty()) {
127 return;
128 }
129 auto const schema = getSchema(sourceList[0]);
130 Point2DKey const centroidKey(schema["slot_Centroid"]);
131 CovarianceMatrixKey<float, 2> const centroidErrKey(schema["slot_Centroid"], {"x", "y"});
132 CoordKey const coordKey(schema["coord"]);
134 pixelList.reserve(sourceList.size());
136 skyErrList.reserve(sourceList.size());
137
138 for (auto const &source : sourceList) {
139 lsst::geom::Point2D center = getValue(source, centroidKey);
140 pixelList.emplace_back(center);
141 if (include_covariance) {
142 auto err = getValue(source, centroidErrKey);
143 Eigen::Matrix2f skyCov = calculateCoordCovariance(wcs, center, err);
144 skyErrList.emplace_back(skyCov);
145 }
146 }
147
148 std::vector<lsst::geom::SpherePoint> const skyList = wcs.pixelToSky(pixelList);
149 auto skyCoord = skyList.cbegin();
150 auto skyErr = skyErrList.cbegin();
151 for (auto &source : sourceList) {
152 setValue(source, coordKey, *skyCoord);
153 if (include_covariance) {
154 CoordKey::ErrorKey const coordErrKey = CoordKey::getErrorKey(schema);
155 setValue(source, coordErrKey, *skyErr);
156 }
157 ++skyCoord;
158 ++skyErr;
159 }
160}
161
163template void updateRefCentroids(geom::SkyWcs const &, std::vector<std::shared_ptr<SimpleRecord>> &);
164template void updateRefCentroids(geom::SkyWcs const &, SimpleCatalog &);
165
166template void updateSourceCoords(geom::SkyWcs const &, std::vector<std::shared_ptr<SourceRecord>> &,
167 bool include_covariance);
168template void updateSourceCoords(geom::SkyWcs const &, SourceCatalog &, bool include_covariance);
170
171} // namespace table
172} // namespace afw
173} // namespace lsst
T cbegin(T... args)
Base class for all records.
Definition BaseRecord.h:31
A FunctorKey used to get or set celestial coordinates from a pair of lsst::geom::Angle keys.
Definition aggregates.h:292
CovarianceMatrixKey< float, 2 > ErrorKey
Definition aggregates.h:304
static ErrorKey getErrorKey(Schema const &schema)
A class used as a handle to a particular field in a table.
Definition Key.h:53
Defines the fields and offsets for a table.
Definition Schema.h:51
Record class that must contain a unique ID field and a celestial coordinate field.
Definition Simple.h:48
constexpr double asRadians() const noexcept
Return an Angle's value in radians.
Definition Angle.h:173
Point in an unspecified spherical coordinate system.
Definition SpherePoint.h:57
Angle getDec() const noexcept
Synonym for getLatitude.
T cos(T... args)
T emplace_back(T... args)
T get(T... args)
T isfinite(T... args)
SortedCatalogT< SimpleRecord > SimpleCatalog
Definition fwd.h:79
void updateRefCentroids(geom::SkyWcs const &wcs, ReferenceCollection &refList)
Update centroids in a collection of reference objects.
Definition wcsUtils.cc:73
Eigen::Matrix2f calculateCoordCovariance(geom::SkyWcs const &wcs, lsst::geom::Point2D center, Eigen::Matrix2f err)
Calculate covariance for sky coordinates.
Definition wcsUtils.cc:95
void updateSourceCoords(geom::SkyWcs const &wcs, SourceCollection &sourceList, bool include_covariance=true)
Update sky coordinates in a collection of source objects.
Definition wcsUtils.cc:125
SortedCatalogT< SourceRecord > SourceCatalog
Definition fwd.h:85
PointKey< double > Point2DKey
Definition aggregates.h:120
Point< double, 2 > Point2D
Definition Point.h:324
double constexpr PI
The ratio of a circle's circumference to diameter.
Definition Angle.h:40
T reserve(T... args)
T Value
the type returned by BaseRecord::get
Definition FieldBase.h:42