Ocean
Loading...
Searching...
No Matches
CameraCalibrator.h
Go to the documentation of this file.
1/*
2 * Copyright (c) Meta Platforms, Inc. and affiliates.
3 *
4 * This source code is licensed under the MIT license found in the
5 * LICENSE file in the root directory of this source tree.
6 */
7
8#ifndef META_OCEAN_CV_CALIBRATION_CAMERA_CALIBRATOR_H
9#define META_OCEAN_CV_CALIBRATION_CAMERA_CALIBRATOR_H
10
15
16#include "ocean/base/Frame.h"
17#include "ocean/base/Worker.h"
18
21
23
24namespace Ocean
25{
26
27namespace CV
28{
29
30namespace Calibration
31{
32
33/**
34 * This class implements a camera calibrator using a couple of images of a calibration board.
35 * @ingroup cvcalibration
36 */
37class OCEAN_CV_CALIBRATION_EXPORT CameraCalibrator
38{
39 public:
40
41 /**
42 * This class holds the properties of the initial camera used during the calibration.
43 */
45 {
46 public:
47
48 /**
49 * Creates initial camera properties with default parameters.
50 */
52
53 /**
54 * Creates initial camera properties.
55 * @param anyCameraType The type of the initial camera to be used, AnyCameraType::INVALID to determine the camera type automatically
56 */
57 explicit inline InitialCameraProperties(const AnyCameraType anyCameraType);
58
59 /**
60 * Creates initial camera properties.
61 * @param anyCameraType The type of the initial camera to be used, AnyCameraType::INVALID to determine the camera type automatically
62 * @param minFovX The minimal horizontal field of view of the initial camera, in radian, with range (0, maxFovX)
63 * @param maxFovX The maximal horizontal field of view of the initial camera, in radian, with range (minFovX, PI)
64 */
65 inline InitialCameraProperties(const AnyCameraType anyCameraType, const Scalar minFovX, const Scalar maxFovX);
66
67 /**
68 * Returns the type of the initial camera to be used.
69 * @return The camera type, AnyCameraType::INVALID to determine the camera type automatically
70 */
71 inline AnyCameraType anyCameraType() const;
72
73 /**
74 * Returns the minimal horizontal field of view of the initial camera.
75 * @return Minimal horizontal field of view, in radian
76 */
77 inline Scalar minFovX() const;
78
79 /**
80 * Returns the maximal horizontal field of view of the initial camera.
81 * @return Maximal horizontal field of view, in radian
82 */
83 inline Scalar maxFovX() const;
84
85 protected:
86
87 /// The type of the initial camera to be used, AnyCameraType::INVALID to determine the camera type automatically.
88 AnyCameraType anyCameraType_ = AnyCameraType::INVALID;
89
90 /// The minimal horizontal field of view of the initial camera, in radian, with range (0, maxFovX_).
91 Scalar minFovX_ = Numeric::deg2rad(20);
92
93 /// The maximal horizontal field of view of the initial camera, in radian, with range (minFovX_, PI)
94 Scalar maxFovX_ = Numeric::deg2rad(175);
95 };
96
97 /**
98 * Definition of individual calibration stages.
99 */
100 enum CalibrationStage : uint32_t
101 {
102 /// The calibration stage is unknown.
103 CS_UNKNOWN = 0u,
104 /// The calibration stage is determining the initial camera field of view.
106 /// The calibration stage is calibrating the camera.
107 CS_CALIBRATE_CAMERA
108 };
109
110 /**
111 * Definition of individual image results.
112 */
113 enum ImageResult : uint32_t
114 {
115 /// An error occurred during the handling of the image.
116 IR_ERROR = 0u,
117 /// The image was handled but the calibration board was not detected.
119 /// The calibration board was detected successfully.
120 IR_BOARD_WAS_DETECTED
121 };
122
123 /**
124 * Alias for the camera's optimization strategy.
125 */
127
128 public:
129
130 /**
131 * Default constructor creating an invalid camera calibrator.
132 */
133 CameraCalibrator() = default;
134
135 /**
136 * Creates a new camera calibrator.
137 * @param metricCalibrationBoard The metric calibration board which will be visible in the camera images, must be valid
138 * @param initialCameraProperties The initial camera properties which can be used to jump start the calibration, must be valid
139 */
140 explicit CameraCalibrator(const MetricCalibrationBoard& metricCalibrationBoard, const InitialCameraProperties& initialCameraProperties = InitialCameraProperties());
141
142 /**
143 * Handles a new image.
144 * @param imageId The unique id of the image, must be valid
145 * @param frame The frame to handle, must be valid
146 * @param worker Optional worker object to distribute the computation
147 * @return The result of the image handling
148 */
149 ImageResult handleImage(const size_t imageId, const Frame& frame, Worker* worker = nullptr);
150
151 /**
152 * Finalizes the calibration and determines the precise camera profile.
153 * This function should be called after all images have been handled.
154 * If the calibration stage transitions from CS_DETERMINE_INITIAL_CAMERA_FOV to CS_CALIBRATE_CAMERA, the observations will be cleared and an additional iteration is required.
155 * @param needAdditionalIteration True, if the calibration requires an additional iteration (all images need to be processed again); False, if the calibration is complete
156 * @return True, if succeeded
157 */
158 bool finalize(bool& needAdditionalIteration);
159
160 /**
161 * Returns the current calibration stage.
162 * @return The calibrator's calibration stage
163 */
164 inline CalibrationStage calibrationStage() const;
165
166 /**
167 * Returns the metric calibration board of this calibrator.
168 * @return The calibrator's calibration board
169 */
170 inline const MetricCalibrationBoard& metricCalibrationBoard() const;
171
172 /**
173 * Returns the calibrator's current camera profile.
174 * @param projectionError Optional resulting projection error, with range [0, infinity)
175 * @return The calibrator's current camera profile, nullptr if the camera profile has not been determined yet
176 */
177 inline SharedAnyCamera camera(Scalar* projectionError = nullptr) const;
178
179 /**
180 * Returns whether this calibrator holds at least one valid observation.
181 * @return True, if so
182 */
183 inline bool hasObservations() const;
184
185 /**
186 * Returns all observations which have been made so far.
187 * @return The calibration board observations
188 */
189 inline const CalibrationBoardObservations& observations() const;
190
191 /**
192 * Returns the latest observation which has been made.
193 * @return The latest calibration board observation
194 */
195 inline const CalibrationBoardObservation& latestObservation() const;
196
197 /**
198 * Returns the overall number of correspondences which have been gathered so far.
199 * @return The number of correspondences across all observations
200 */
201 size_t numberCorrespondences() const;
202
203 protected:
204
205 /**
206 * Determines the initial camera pose based on marker candidates with known marker coordinate.
207 * @param camera The camera profile defining the projection, must be valid
208 * @param points The points which have been detected in the image, must be valid
209 * @param board_T_camera The resulting initial camera pose, with default camera pointing towards the negative z-space with y-axis upwards
210 * @param usedMarkerCandidateIndices The resulting indices of the marker candidates which have been used to determine the initial pose
211 * @return True, if succeeded
212 */
213 bool determineInitialPoseWithValidMarkerCandidates(const AnyCamera& camera, const Points& points, HomogenousMatrix4& board_T_camera, Indices32& usedMarkerCandidateIndices) const;
214
215 /**
216 * Optimizes the camera pose using known valid marker candidates with known marker coordinates and iteratively adds additional correspondences from neighboring marker candidates.
217 * The area around the valid marker candidates is iteratively growing until no additional marker candidates can be added.<br>
218 * The growing strategy helps with handling fisheye cameras.
219 * @param camera The camera profile defining the projection, must be valid
220 * @param board_T_camera The initial camera pose to improve, with default camera pointing towards the negative z-space with y-axis upwards, must be valid
221 * @param points The points which have been detected in the image
222 * @param pointsDistributionArray The distribution array of the points, must be valid
223 * @param validMarkerCandidateIndices The indices of the marker candidates which have been used to determine the initial pose, must be valid
224 * @param maximalProjectionError The maximal projection error between image point and reprojected object point, in pixel, with range [0, infinity)
225 * @param board_T_optimizedCamera The resulting optimized camera pose, with default camera pointing towards the negative z-space with y-axis upwards
226 * @param objectPointIds The resulting ids of the object points which have been used to determine the optimized camera pose
227 * @param objectPoints The resulting object points which have been used to determine the optimized camera pose, one for each object point id
228 * @param imagePoints The resulting image points which have been used to determine the optimized camera pose, one for each object point id
229 */
230 bool optimizeCameraPoseWithAdditionalPointsFromMarkerCandidates(const AnyCamera& camera, const HomogenousMatrix4& board_T_camera, const Points& points, const Geometry::SpatialDistribution::DistributionArray& pointsDistributionArray, const Indices32& validMarkerCandidateIndices, const Scalar maximalProjectionError, HomogenousMatrix4& board_T_optimizedCamera, CalibrationBoard::ObjectPointIds& objectPointIds, Vectors3& objectPoints, Vectors2& imagePoints) const;
231
232 /**
233 * Determines additional 2D/3D correspondences for a valid observation of a calibration board which has not yet used all possible marker points of the calibration board.
234 * @param calibrationBoard The calibration board which has been observed, must be valid
235 * @param observation The observation of the calibration board, must be valid
236 * @param points The points which have been detected in the image
237 * @param pointsDistributionArray The distribution array of the points, must be valid
238 * @param additionalObjectPointIds The resulting ids of additional object points which are not part of the provided observation but which are part of the calibration board
239 * @param additionalObjectPoints The resulting additional object points, one for each object point id
240 * @param additionalImagePoints The resulting additional image points, one for each object point id
241 * @param maximalProjectionError The maximal projection error between image point and reprojected object point, in pixel, with range [0, infinity)
242 * @return True, if succeeded
243 */
244 bool determineAdditionalCorrespondences(const MetricCalibrationBoard& calibrationBoard, const CalibrationBoardObservation& observation, const Points& points, const Geometry::SpatialDistribution::DistributionArray& pointsDistributionArray, CalibrationBoard::ObjectPointIds& additionalObjectPointIds, Vectors3& additionalObjectPoints, Vectors2& additionalImagePoints, const Scalar maximalProjectionError);
245
246 /**
247 * Optimizes the camera profile based on all marker points from known valid marker candidates with known marker coordinates.
248 * @param camera The camera profile to optimize, must be valid
249 * @param board_T_camera The initial camera pose to improve, with default camera pointing towards the negative z-space with y-axis upwards, must be valid
250 * @param points The points which have been detected in the image
251 * @param validMarkerCandidateIndices The indices of the marker candidates with known marker coordinates, at least one
252 * @param optimizationStrategy The optimization strategy to be used
253 * @param board_T_optimizedCamera Optional resulting optimized camera pose, nullptr if not of interest
254 * @param estimatorType The estimator type to be used
255 * @param initialError Optional resulting initial projection error, with range [0, infinity)
256 * @param finalError Optional resulting final projection error, with range [0, infinity)
257 * @return The resulting optimized camera profile, nullptr if the camera profile could not be determined
258 */
259 SharedAnyCamera optimizeCamera(const AnyCamera& camera, const HomogenousMatrix4& board_T_camera, const Points& points, const Indices32& validMarkerCandidateIndices, const OptimizationStrategy optimizationStrategy, HomogenousMatrix4* board_T_optimizedCamera = nullptr, const Geometry::Estimator::EstimatorType estimatorType = Geometry::Estimator::ET_SQUARE, Scalar* initialError = nullptr, Scalar* finalError = nullptr) const;
260
261 /**
262 * Determines the initial field of view of the camera for a single image of a calibration board.
263 * @param width The width of the image in pixel, with range [1, infinity)
264 * @param height The height of the image in pixel, with range [1, infinity)
265 * @param points The points which have been detected in the image
266 * @param markerCandidates The marker candidates which have been detected in the image with valid border indices (and signs), at least one
267 * @param initialCameraProperties The initial camera properties which can be used to jump start the calibration
268 * @return The resulting initial camera profile, nullptr if the initial camera profile could not be determined
269 */
270 static SharedAnyCamera determineInitialCameraFieldOfView(const unsigned int width, const unsigned int height, const Points& points, const MarkerCandidates& markerCandidates, const InitialCameraProperties& initialCameraProperties);
271
272 /**
273 * Determines the precise camera profile based on several observations of a calibration board.
274 * @param observations The observations of the calibration board, must be valid
275 * @param numberObservations The number of observations, with range [1, infinity)
276 * @param optimizationStrategy The optimization strategy to be used
277 * @param board_T_optimizedCameras Optional resulting camera poses, one for each observation, with default camera pointing towards the negative z-space with y-axis upwards; nullptr if not of interest
278 * @param estimatorType The estimator type to be used
279 * @param startWithFocalLength True, to start the optimization with a camera profile containing only the focal length (resetting distortion parameters); False, to use the full camera profile from the observations as initial guess
280 * @param distortionConstrainmentFactor The factor used to constrain higher-order distortion parameters based on lower-order ones during optimization, with range [0, infinity); 0 to disable constrainment
281 * @param initialError Optional resulting initial projection error, with range [0, infinity)
282 * @param finalError Optional resulting final projection error, with range [0, infinity)
283 * @return The resulting precise camera profile, nullptr if the camera profile could not be determined
284 */
285 static SharedAnyCamera determinePreciseCamera(const CalibrationBoardObservation* observations, const size_t numberObservations, const OptimizationStrategy optimizationStrategy, HomogenousMatrices4* board_T_optimizedCameras = nullptr, const Geometry::Estimator::EstimatorType estimatorType = Geometry::Estimator::ET_SQUARE, const bool startWithFocalLength = true, const Scalar distortionConstrainmentFactor = Scalar(2), Scalar* initialError = nullptr, Scalar* finalError = nullptr);
286
287 protected:
288
289 /// The current calibration stage.
290 CalibrationStage calibrationStage_ = CS_UNKNOWN;
291
292 /// The metric calibration board which is used for calibration.
294
295 /// The initial camera properties which can be used to jump start the calibration.
297
298 /// The current frame with pixel format FORMAT_Y8.
300
301 /// The point detector which is used to detect the marker points of the calibration board.
303
304 /// The marker candidates which have been detected in the current image.
306
307 /// The random generator to be used.
309
310 /// Reusable frame object to avoid memory re-allocations.
312
313 /// The observations which have been made so far.
315
316 /// The final camera profile.
318
319 /// The resulting projection error of the final camera profile, with range [0, infinity)
320 Scalar cameraProjectionError_ = Numeric::maxValue();
321};
322
327
329 anyCameraType_(anyCameraType)
330{
331 // nothing to do here
332}
333
335 anyCameraType_(anyCameraType),
336 minFovX_(minFovX),
337 maxFovX_(maxFovX)
338{
339 // nothing to do here
340}
341
343{
344 return anyCameraType_;
345}
346
348{
349 ocean_assert(minFovX_ <= maxFovX_);
350 return minFovX_;
351}
352
354{
355 ocean_assert(minFovX_ <= maxFovX_);
356 return maxFovX_;
357}
358
363
368
369inline SharedAnyCamera CameraCalibrator::camera(Scalar* projectionError) const
370{
371 if (projectionError != nullptr)
372 {
373 *projectionError = cameraProjectionError_;
374 }
375
376 return camera_;
377}
378
380{
381 return !observations_.empty();
382}
383
388
390{
391 return observations_.back();
392}
393
394}
395
396}
397
398}
399
400#endif // META_OCEAN_CV_CALIBRATION_CAMERA_CALIBRATOR_H
This class implements the abstract base class for all AnyCamera objects.
Definition AnyCamera.h:131
std::vector< ObjectPointId > ObjectPointIds
Definition of a vector holding object point ids.
Definition CalibrationBoard.h:224
This class implements an observation of a calibration board.
Definition CalibrationBoardObservation.h:45
This class holds the properties of the initial camera used during the calibration.
Definition CameraCalibrator.h:45
Scalar maxFovX() const
Returns the maximal horizontal field of view of the initial camera.
Definition CameraCalibrator.h:353
AnyCameraType anyCameraType() const
Returns the type of the initial camera to be used.
Definition CameraCalibrator.h:342
Scalar minFovX() const
Returns the minimal horizontal field of view of the initial camera.
Definition CameraCalibrator.h:347
InitialCameraProperties()
Creates initial camera properties with default parameters.
Definition CameraCalibrator.h:323
This class implements a camera calibrator using a couple of images of a calibration board.
Definition CameraCalibrator.h:38
size_t numberCorrespondences() const
Returns the overall number of correspondences which have been gathered so far.
CalibrationStage calibrationStage() const
Returns the current calibration stage.
Definition CameraCalibrator.h:359
CameraCalibrator()=default
Default constructor creating an invalid camera calibrator.
bool finalize(bool &needAdditionalIteration)
Finalizes the calibration and determines the precise camera profile.
SharedAnyCamera optimizeCamera(const AnyCamera &camera, const HomogenousMatrix4 &board_T_camera, const Points &points, const Indices32 &validMarkerCandidateIndices, const OptimizationStrategy optimizationStrategy, HomogenousMatrix4 *board_T_optimizedCamera=nullptr, const Geometry::Estimator::EstimatorType estimatorType=Geometry::Estimator::ET_SQUARE, Scalar *initialError=nullptr, Scalar *finalError=nullptr) const
Optimizes the camera profile based on all marker points from known valid marker candidates with known...
ImageResult handleImage(const size_t imageId, const Frame &frame, Worker *worker=nullptr)
Handles a new image.
CalibrationStage calibrationStage_
The current calibration stage.
Definition CameraCalibrator.h:290
InitialCameraProperties initialCameraProperties_
The initial camera properties which can be used to jump start the calibration.
Definition CameraCalibrator.h:296
const MetricCalibrationBoard & metricCalibrationBoard() const
Returns the metric calibration board of this calibrator.
Definition CameraCalibrator.h:364
Frame yFrame_
The current frame with pixel format FORMAT_Y8.
Definition CameraCalibrator.h:299
SharedAnyCamera camera_
The final camera profile.
Definition CameraCalibrator.h:317
ImageResult
Definition of individual image results.
Definition CameraCalibrator.h:114
@ IR_BOARD_WAS_NOT_DETECTED
The image was handled but the calibration board was not detected.
Definition CameraCalibrator.h:118
CameraCalibrator(const MetricCalibrationBoard &metricCalibrationBoard, const InitialCameraProperties &initialCameraProperties=InitialCameraProperties())
Creates a new camera calibrator.
bool determineInitialPoseWithValidMarkerCandidates(const AnyCamera &camera, const Points &points, HomogenousMatrix4 &board_T_camera, Indices32 &usedMarkerCandidateIndices) const
Determines the initial camera pose based on marker candidates with known marker coordinate.
bool determineAdditionalCorrespondences(const MetricCalibrationBoard &calibrationBoard, const CalibrationBoardObservation &observation, const Points &points, const Geometry::SpatialDistribution::DistributionArray &pointsDistributionArray, CalibrationBoard::ObjectPointIds &additionalObjectPointIds, Vectors3 &additionalObjectPoints, Vectors2 &additionalImagePoints, const Scalar maximalProjectionError)
Determines additional 2D/3D correspondences for a valid observation of a calibration board which has ...
PointDetector pointDetector_
The point detector which is used to detect the marker points of the calibration board.
Definition CameraCalibrator.h:302
CalibrationBoardObservations observations_
The observations which have been made so far.
Definition CameraCalibrator.h:314
static SharedAnyCamera determineInitialCameraFieldOfView(const unsigned int width, const unsigned int height, const Points &points, const MarkerCandidates &markerCandidates, const InitialCameraProperties &initialCameraProperties)
Determines the initial field of view of the camera for a single image of a calibration board.
RandomGenerator randomGenerator_
The random generator to be used.
Definition CameraCalibrator.h:308
bool optimizeCameraPoseWithAdditionalPointsFromMarkerCandidates(const AnyCamera &camera, const HomogenousMatrix4 &board_T_camera, const Points &points, const Geometry::SpatialDistribution::DistributionArray &pointsDistributionArray, const Indices32 &validMarkerCandidateIndices, const Scalar maximalProjectionError, HomogenousMatrix4 &board_T_optimizedCamera, CalibrationBoard::ObjectPointIds &objectPointIds, Vectors3 &objectPoints, Vectors2 &imagePoints) const
Optimizes the camera pose using known valid marker candidates with known marker coordinates and itera...
CalibrationStage
Definition of individual calibration stages.
Definition CameraCalibrator.h:101
@ CS_DETERMINE_INITIAL_CAMERA_FOV
The calibration stage is determining the initial camera field of view.
Definition CameraCalibrator.h:105
Frame reusableMarkerCoordinateUsageFrame_
Reusable frame object to avoid memory re-allocations.
Definition CameraCalibrator.h:311
Scalar cameraProjectionError_
The resulting projection error of the final camera profile, with range [0, infinity)
Definition CameraCalibrator.h:320
SharedAnyCamera camera(Scalar *projectionError=nullptr) const
Returns the calibrator's current camera profile.
Definition CameraCalibrator.h:369
const CalibrationBoardObservation & latestObservation() const
Returns the latest observation which has been made.
Definition CameraCalibrator.h:389
const CalibrationBoardObservations & observations() const
Returns all observations which have been made so far.
Definition CameraCalibrator.h:384
bool hasObservations() const
Returns whether this calibrator holds at least one valid observation.
Definition CameraCalibrator.h:379
static SharedAnyCamera determinePreciseCamera(const CalibrationBoardObservation *observations, const size_t numberObservations, const OptimizationStrategy optimizationStrategy, HomogenousMatrices4 *board_T_optimizedCameras=nullptr, const Geometry::Estimator::EstimatorType estimatorType=Geometry::Estimator::ET_SQUARE, const bool startWithFocalLength=true, const Scalar distortionConstrainmentFactor=Scalar(2), Scalar *initialError=nullptr, Scalar *finalError=nullptr)
Determines the precise camera profile based on several observations of a calibration board.
MetricCalibrationBoard metricCalibrationBoard_
The metric calibration board which is used for calibration.
Definition CameraCalibrator.h:293
MarkerCandidates markerCandidates_
The marker candidates which have been detected in the current image.
Definition CameraCalibrator.h:305
This class extends the calibration board with metric information.
Definition MetricCalibrationBoard.h:39
This class implements a point detector for marker points.
Definition PointDetector.h:39
This class implements Ocean's image class.
Definition Frame.h:1879
EstimatorType
Definition of individual robust estimator types.
Definition Estimator.h:34
OptimizationStrategy
Definition of individual optimization strategies for how the camera parameters can be optimized.
Definition NonLinearOptimizationCamera.h:37
This class implements a distribution array.
Definition SpatialDistribution.h:228
This class implements a generator for random numbers.
Definition RandomGenerator.h:42
This class implements a worker able to distribute function calls over different threads.
Definition Worker.h:33
std::vector< Index32 > Indices32
Definition of a vector holding 32 bit index values.
Definition Base.h:96
std::vector< Point > Points
Definition of a vector holding points.
Definition cv/calibration/Point.h:31
std::vector< MarkerCandidate > MarkerCandidates
Definition of a vector holding marker candidates.
Definition MarkerCandidate.h:33
std::vector< CalibrationBoardObservation > CalibrationBoardObservations
Definition of a vector holding CalibrationBoardObservation objects.
Definition CalibrationBoardObservation.h:37
std::vector< Vector2 > Vectors2
Definition of a vector holding Vector2 objects.
Definition Vector2.h:64
float Scalar
Definition of a scalar type.
Definition Math.h:129
std::shared_ptr< AnyCamera > SharedAnyCamera
Definition of a shared pointer holding an AnyCamera object with Scalar precision.
Definition AnyCamera.h:61
std::vector< HomogenousMatrix4 > HomogenousMatrices4
Definition of a vector holding HomogenousMatrix4 objects.
Definition HomogenousMatrix4.h:73
std::vector< Vector3 > Vectors3
Definition of a vector holding Vector3 objects.
Definition Vector3.h:65
AnyCameraType
Definition of individual camera types.
Definition AnyCamera.h:112
The namespace covering the entire Ocean framework.
Definition Accessor.h:15