Isis 3 Programmer Reference
RosettaOsirisCameraDistortionMap.cpp
1
7/* SPDX-License-Identifier: CC0-1.0 */
8
9
10#include "RosettaOsirisCameraDistortionMap.h"
11
12using namespace std;
13
14namespace Isis {
25 CameraDistortionMap(parent) {
26 // Initialize to the identity transform
29 m_toUnDistortedX(0, 1) = 1.0;
30 m_toUnDistortedY(1, 0) = 1.0;
31
33 m_boresightLine = 0.0;
34 m_pixelPitch = 1.0;
35 }
36
69 bool RosettaOsirisCameraDistortionMap::SetFocalPlane(const double dx, const double dy) {
70 p_focalPlaneX = dx;
71 p_focalPlaneY = dy;
72
73 // The equations are in pixel coordinates so convert
74 double dxPixel = focalXToLine(dx);
75 double dyPixel = focalYToSample(dy);
76
78 xTerms(0) = 1.0;
79 xTerms(1) = dxPixel;
80 xTerms(2) = dxPixel*dxPixel;
81 xTerms(3) = dxPixel*dxPixel*dxPixel;
82
84 yTerms(0) = 1.0;
85 yTerms(1) = dyPixel;
86 yTerms(2) = dyPixel*dyPixel;
87 yTerms(3) = dyPixel*dyPixel*dyPixel;
88
89 double ux = LinearAlgebra::dotProduct(
91 yTerms);
92 double uy = LinearAlgebra::dotProduct(
94 yTerms);
95
98
99 return true;
100 }
101
136 bool RosettaOsirisCameraDistortionMap::SetUndistortedFocalPlane(const double ux, const double uy) {
137 // image coordinates prior to introducing distortion
140
141 // The equations are in pixel coordinates so convert
142 double uxPixel = focalXToLine(ux);
143 double uyPixel = focalYToSample(uy);
144
145 // Loop setup
146 double tolerance = 1e-7;
147 int iteration = 1;
148 int maxIterations = 20;
149 bool done = false;
150
151 LinearAlgebra::Vector undistortedCoordinate = LinearAlgebra::zeroVector(2);
152 undistortedCoordinate(0) = uxPixel;
153 undistortedCoordinate(1) = uyPixel;
154 // Use the undistorted coordinate as the initial point
155 LinearAlgebra::Vector distortedCoordinate = undistortedCoordinate;
156
161
166
167 // Compute the term vectors
168 // These are recomputed at the END of each iteration, so compute them
169 // before the first iteration
170 xTerms(0) = 1.0;
171 xTerms(1) = distortedCoordinate(0);
172 xTerms(2) = distortedCoordinate(0)*distortedCoordinate(0);
173 xTerms(3) = distortedCoordinate(0)*distortedCoordinate(0)*distortedCoordinate(0);
174
175 yTerms(0) = 1.0;
176 yTerms(1) = distortedCoordinate(1);
177 yTerms(2) = distortedCoordinate(1)*distortedCoordinate(1);
178 yTerms(3) = distortedCoordinate(1)*distortedCoordinate(1)*distortedCoordinate(1);
179
180 delXTerms(1) = 1.0;
181 delXTerms(2) = 2.0*distortedCoordinate(0);
182 delXTerms(3) = 3.0*distortedCoordinate(0)*distortedCoordinate(0);
183
184 delYTerms(1) = 1.0;
185 delYTerms(2) = 2.0*distortedCoordinate(1);
186 delYTerms(3) = 3.0*distortedCoordinate(1)*distortedCoordinate(1);
187
188 // Compute the object function, the distance between the redistorted and undistorted
189 objectFuncValue(0) = undistortedCoordinate(0)
191 yTerms );
192 objectFuncValue(1) = undistortedCoordinate(1)
194 yTerms );
195
196 while(!done) {
197
198 // Compute the negative jacobian
199 // The variable terms and object function value have already been
200 // computed priort to checking for convergence at the end of the
201 // previous iteration. These are not needed to check for convergence
202 // so, compute them now.
204 yTerms );
206 delYTerms );
208 yTerms );
210 delYTerms );
211
212 // Invert the negative jacobian
213 // If it is not invertible, then fail
214 double det = negJacobian(0, 0) * negJacobian(1, 1) - negJacobian(1, 0) * negJacobian(0, 1);
215 if ( fabs(det) < 1e-15 ) {
216 return false;
217 }
218 negInvJacobian(0, 0) = negJacobian(1, 1) / det;
219 negInvJacobian(0, 1) = - negJacobian(0, 1) / det;
220 negInvJacobian(1, 0) = - negJacobian(1, 0) / det;
221 negInvJacobian(1, 1) = negJacobian(0, 0) / det;
222
223 // Compute the update step
224 updateStep = LinearAlgebra::multiply(negInvJacobian, objectFuncValue);
225
226 // Update and check for convergence
227 distortedCoordinate += updateStep;
228
229 // Compute the term vectors
230 xTerms(0) = 1.0;
231 xTerms(1) = distortedCoordinate(0);
232 xTerms(2) = distortedCoordinate(0)*distortedCoordinate(0);
233 xTerms(3) = distortedCoordinate(0)*distortedCoordinate(0)*distortedCoordinate(0);
234
235 yTerms(0) = 1.0;
236 yTerms(1) = distortedCoordinate(1);
237 yTerms(2) = distortedCoordinate(1)*distortedCoordinate(1);
238 yTerms(3) = distortedCoordinate(1)*distortedCoordinate(1)*distortedCoordinate(1);
239
240 delXTerms(1) = 1.0;
241 delXTerms(2) = 2.0*distortedCoordinate(0);
242 delXTerms(3) = 3.0*distortedCoordinate(0)*distortedCoordinate(0);
243
244 delYTerms(1) = 1.0;
245 delYTerms(2) = 2.0*distortedCoordinate(1);
246 delYTerms(3) = 3.0*distortedCoordinate(1)*distortedCoordinate(1);
247
248 // Compute the object function, the distance between the redistorted and undistorted
249 objectFuncValue(0) = undistortedCoordinate(0)
251 yTerms );
252 objectFuncValue(1) = undistortedCoordinate(1)
254 yTerms );
255
256 if ( LinearAlgebra::magnitude(objectFuncValue) < tolerance ||
257 iteration > maxIterations ) {
258 done = true;
259 }
260 iteration++;
261 }
262
263 p_focalPlaneX = lineToFocalX( distortedCoordinate(0) );
264 p_focalPlaneY = sampleToFocalY( distortedCoordinate(1) );
265
266 return true;
267 }
268
269
278
279
288
289
297 void RosettaOsirisCameraDistortionMap::setBoresight(double sample, double line) {
298 m_boresightSample = sample;
299 m_boresightLine = line;
300 }
301
302
310 m_pixelPitch = pitch;
311 }
312
313
324
325
336
337
346 return ( ( line - m_boresightLine ) * m_pixelPitch );
347 }
348
349
358 return ( ( sample - m_boresightSample) * m_pixelPitch );
359 }
360}
Distort/undistort focal plane coordinates.
double p_focalPlaneX
Distorted focal plane x.
double p_undistortedFocalPlaneX
Undistorted focal plane x.
double p_undistortedFocalPlaneY
Undistorted focal plane y.
double p_focalPlaneY
Distorted focal plane y.
static Vector zeroVector(int size)
Returns a vector of given length that is filled with zeroes.
static Matrix multiply(const Matrix &matrix1, const Matrix &matrix2)
Returns the product of two matrices.
static Matrix zeroMatrix(int rows, int columns)
Returns a matrix with given dimensions that is filled with zeroes.
static double magnitude(const Vector &vector)
Computes the magnitude (i.e., the length) of the given vector using the Euclidean norm (L2 norm).
boost::numeric::ublas::vector< double > Vector
Definition for an Isis::LinearAlgebra::Vector of doubles.
boost::numeric::ublas::matrix< double > Matrix
Definition for an Isis::LinearAlgebra::Matrix of doubles.
static double dotProduct(const Vector &vector1, const Vector &vector2)
Computes the dot product of the given vectors.
void setPixelPitch(double pitch)
Set the pixel pitch for converting from focal plane coordinates to pixel coordinates.
LinearAlgebra::Matrix m_toUnDistortedY
Matrix for computing undistorted Y coordinates.
void setUnDistortedYMatrix(LinearAlgebra::Matrix yMat)
Set the matrix for converting from distorted to undistorted lines.
double focalYToSample(double y)
Convert a focal plane y coordinate to a pixel space sample coordinate.
LinearAlgebra::Matrix m_toUnDistortedX
Matrix for computing undistorted X coordinates.
double m_pixelPitch
Camera pixel pitch for converting focal plane coordinates to pixel coordinates.
double focalXToLine(double x)
Convert a focal plane x coordinate to a pixel space line coordinate.
void setUnDistortedXMatrix(LinearAlgebra::Matrix xMat)
Set the matrix for converting from distorted to undistorted samples.
void setBoresight(double sample, double line)
Set the boresight location for converting from focal plane coordinates to pixel coordinates.
double sampleToFocalY(double sample)
Convert pixel space sample coordinate to a focal plane y coordinate.
virtual bool SetUndistortedFocalPlane(const double ux, const double uy)
Compute distorted focal plane x/y given an undistorted focal plane x/y.
double m_boresightSample
Camera boresight sample coordinate for converting focal plane coordinates to pixel coordinates.
virtual bool SetFocalPlane(const double dx, const double dy)
Compute undistorted focal plane x/y given a distorted focal plane x/y.
double m_boresightLine
Camera boresight line coordinate for converting focal plane coordinates to pixel coordinates.
double lineToFocalX(double line)
Convert pixel space line coordinate to a focal plane x coordinate.
RosettaOsirisCameraDistortionMap(Camera *parent)
Create a camera distortion map.
This is free and unencumbered software released into the public domain.
Definition Apollo.h:16
Namespace for the standard library.