LSST Applications g0265f82a02+0e5473021a,g02d81e74bb+0dd8ce4237,g1470d8bcf6+3ea6592b6f,g2079a07aa2+86d27d4dc4,g2305ad1205+5ca4c0b359,g295015adf3+d10818ec9d,g2a9a014e59+6f9be1b9cd,g2bbee38e9b+0e5473021a,g337abbeb29+0e5473021a,g3ddfee87b4+703ba97ebf,g487adcacf7+4fa16da234,g50ff169b8f+96c6868917,g52b1c1532d+585e252eca,g591dd9f2cf+ffa42b374e,g5a732f18d5+53520f316c,g64a986408d+0dd8ce4237,g858d7b2824+0dd8ce4237,g8a8a8dda67+585e252eca,g99cad8db69+d39438377f,g9ddcbc5298+9a081db1e4,ga1e77700b3+15fc3df1f7,ga8c6da7877+f1d96605c8,gb0e22166c9+60f28cb32d,gb6a65358fc+0e5473021a,gba4ed39666+c2a2e4ac27,gbb8dafda3b+e5339d463f,gc120e1dc64+da31e9920e,gc28159a63d+0e5473021a,gcf0d15dbbd+703ba97ebf,gdaeeff99f8+f9a426f77a,ge6526c86ff+889fc9d533,ge79ae78c31+0e5473021a,gee10cc3b42+585e252eca,gf18bd8381d+7268b93478,gff1a9f87cc+0dd8ce4237,w.2024.16
LSST Data Management Base Package
Loading...
Searching...
No Matches
Public Member Functions | Static Public Attributes | Static Protected Attributes | List of all members
lsst.meas.astrom.fitAffineWcs.FitAffineWcsTask Class Reference
Inheritance diagram for lsst.meas.astrom.fitAffineWcs.FitAffineWcsTask:

Public Member Functions

 fitWcs (self, matches, initWcs, bbox=None, refCat=None, sourceCat=None, exposure=None)
 

Static Public Attributes

 ConfigClass = FitAffineWcsConfig
 

Static Protected Attributes

str _DefaultName = "fitAffineWcs"
 

Detailed Description

Fit a TAN-SIP WCS given a list of reference object/source matches.

This WCS fitter should be used on top of a cameraGeom distortion model as
the model assumes that only a shift the WCS center position and a small
affine transform are required.

Definition at line 48 of file fitAffineWcs.py.

Member Function Documentation

◆ fitWcs()

lsst.meas.astrom.fitAffineWcs.FitAffineWcsTask.fitWcs ( self,
matches,
initWcs,
bbox = None,
refCat = None,
sourceCat = None,
exposure = None )
Fit a simple Affine transform with a shift to the matches and update
the WCS.

This method assumes that the distortion model of the telescope is
applied correctly and is accurate with only a slight rotation,
rotation, and "squish" required to fit to the reference locations.

Parameters
----------
matches : `list` of `lsst.afw.table.ReferenceMatch`
    The following fields are read:

    - match.first (reference object) coord
    - match.second (source) centroid

    The following fields are written:

    - match.first (reference object) centroid,
    - match.second (source) centroid
    - match.distance (on sky separation, in radians)

initWcs : `lsst.afw.geom.SkyWcs`
    initial WCS
bbox : `lsst.geom.Box2I`
    Ignored; present for consistency with FitSipDistortionTask.
refCat : `lsst.afw.table.SimpleCatalog`
    reference object catalog, or None.
    If provided then all centroids are updated with the new WCS,
    otherwise only the centroids for ref objects in matches are
    updated. Required fields are "centroid_x", "centroid_y",
    "coord_ra", and "coord_dec".
sourceCat : `lsst.afw.table.SourceCatalog`
    source catalog, or None.
    If provided then coords are updated with the new WCS;
    otherwise only the coords for sources in matches are updated.
    Required fields are "slot_Centroid_x", "slot_Centroid_y", and
    "coord_ra", and "coord_dec".
exposure : `lsst.afw.image.Exposure`
    Ignored; present for consistency with FitSipDistortionTask.

Returns
-------
result : `lsst.pipe.base.Struct`
    with the following fields:

    - ``wcs`` :  the fit WCS (`lsst.afw.geom.SkyWcs`)
    - ``scatterOnSky`` :  median on-sky separation between reference
      objects and sources in "matches" (`lsst.afw.geom.Angle`)

Definition at line 59 of file fitAffineWcs.py.

65 exposure=None):
66 """Fit a simple Affine transform with a shift to the matches and update
67 the WCS.
68
69 This method assumes that the distortion model of the telescope is
70 applied correctly and is accurate with only a slight rotation,
71 rotation, and "squish" required to fit to the reference locations.
72
73 Parameters
74 ----------
75 matches : `list` of `lsst.afw.table.ReferenceMatch`
76 The following fields are read:
77
78 - match.first (reference object) coord
79 - match.second (source) centroid
80
81 The following fields are written:
82
83 - match.first (reference object) centroid,
84 - match.second (source) centroid
85 - match.distance (on sky separation, in radians)
86
87 initWcs : `lsst.afw.geom.SkyWcs`
88 initial WCS
89 bbox : `lsst.geom.Box2I`
90 Ignored; present for consistency with FitSipDistortionTask.
91 refCat : `lsst.afw.table.SimpleCatalog`
92 reference object catalog, or None.
93 If provided then all centroids are updated with the new WCS,
94 otherwise only the centroids for ref objects in matches are
95 updated. Required fields are "centroid_x", "centroid_y",
96 "coord_ra", and "coord_dec".
97 sourceCat : `lsst.afw.table.SourceCatalog`
98 source catalog, or None.
99 If provided then coords are updated with the new WCS;
100 otherwise only the coords for sources in matches are updated.
101 Required fields are "slot_Centroid_x", "slot_Centroid_y", and
102 "coord_ra", and "coord_dec".
103 exposure : `lsst.afw.image.Exposure`
104 Ignored; present for consistency with FitSipDistortionTask.
105
106 Returns
107 -------
108 result : `lsst.pipe.base.Struct`
109 with the following fields:
110
111 - ``wcs`` : the fit WCS (`lsst.afw.geom.SkyWcs`)
112 - ``scatterOnSky`` : median on-sky separation between reference
113 objects and sources in "matches" (`lsst.afw.geom.Angle`)
114 """
115 # Create a data-structure that decomposes the input Wcs frames and
116 # appends the new transform.
117 wcsMaker = TransformedSkyWcsMaker(initWcs)
118
119 # Grab the initial transformations going back from sky coordinates
120 # and forward from pixel coordinates.
121 back = wcsMaker.frameDict.getMapping(wcsMaker.frameMax, wcsMaker.frameMax-1)
122 forward = wcsMaker.lastMapBeforeSky
123
124 # Create containers for the data going into the Affine fit. This will
125 # be done by approximating the solution to Ax=b where x will be the
126 # affine parameters and a linear shift. The approximate solution is
127 # calculated using a least squares minimization of the Ax=b equation.
128 #
129 # This is looking to find the affine transform of the following form:
130 # [x', y'] = [[a, b], [c, d]] [x, y] + [s, t]
131 #
132 # where a,b,c,d are the parameters of the affine transform, and s,t
133 # are linear shift parameters.
134 #
135 # To solve for these unknown parameters the unknown matrix x in the
136 # equation Ax=b will be of the form:
137 # [a, b, c, d, s, t].
138 #
139 # This implies that each constraining point will correspond to two rows
140 # in the A matrix in the following form:
141 # [x_i, y_i, 0, 0, 1, 0]
142 # [0, 0, x_i, y_i, 0, 1].
143 #
144 # The corresponding output points in the b vector will have the form:
145 # [x'_i, y'_i, x'_(i+i), y'_(i+1)....]
146 A = np.zeros((len(matches)*2, 6), dtype=float)
147 b = np.empty(len(matches)*2, dtype=float)
148
149 # Constant terms related to the shift in x and and y parameters.
150 A[::2, 4] = 1
151 A[1::2, 5] = 1
152
153 # loop over each of the matches and populate the matrices.
154 for i, match in enumerate(matches):
155 refCoord = match.first.getCoord()
156 b[i*2:i*2+2] = back.applyForward(refCoord)
157
158 srcCentroid = match.second.getCentroid()
159 val = forward.applyForward(srcCentroid)
160 A[i*2, :2] = val
161 A[i*2+1, 2:4] = val
162
163 # solve for the affine and shift parameters
164 # The lapack_driver parameter is set to the quickest routine tested for
165 # this application at the time of writing.
166 fit = lstsq(A, b, lapack_driver='gelsy')[0]
167
168 self.log.debug("Linear shift in x: %.3f, y: %.3f, "
169 "Affine matrix: [[%.6f, %.6f], [%.6f, %.6f]]...",
170 fit[4], fit[5],
171 fit[0], fit[1], fit[2], fit[3])
172
173 # create the final wcs
174 wcs = wcsMaker.makeWcs(fit[4:], fit[:4].reshape((2, 2)))
175
176 # Copied from other fit*WcsTasks.
177 if refCat is not None:
178 self.log.debug("Updating centroids in refCat")
179 lsst.afw.table.updateRefCentroids(wcs, refList=refCat)
180 else:
181 self.log.warning("Updating reference object centroids in match list; refCat is None")
183 wcs,
184 refList=[match.first for match in matches])
185
186 if sourceCat is not None:
187 self.log.debug("Updating coords in sourceCat")
188 lsst.afw.table.updateSourceCoords(wcs, sourceList=sourceCat)
189 else:
190 self.log.warning("Updating source coords in match list; sourceCat is None")
192 wcs,
193 sourceList=[match.second for match in matches])
194 setMatchDistance(matches)
195
196 stats = makeMatchStatisticsInRadians(wcs,
197 matches,
198 lsst.afw.math.MEDIAN)
199 scatterOnSky = stats.getValue() * radians
200
201 self.log.debug("In fitter scatter %.4f", scatterOnSky.asArcseconds())
202
203 return lsst.pipe.base.Struct(
204 wcs=wcs,
205 scatterOnSky=scatterOnSky,
206 )
207
208
void updateRefCentroids(geom::SkyWcs const &wcs, ReferenceCollection &refList)
Update centroids in a collection of reference objects.
Definition wcsUtils.cc:73
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

Member Data Documentation

◆ _DefaultName

str lsst.meas.astrom.fitAffineWcs.FitAffineWcsTask._DefaultName = "fitAffineWcs"
staticprotected

Definition at line 56 of file fitAffineWcs.py.

◆ ConfigClass

lsst.meas.astrom.fitAffineWcs.FitAffineWcsTask.ConfigClass = FitAffineWcsConfig
static

Definition at line 55 of file fitAffineWcs.py.


The documentation for this class was generated from the following file: