/** \page page_how_to_use How to use * * This page gives an introduction to the usage of OpenGV including a description of the interface and explicit examples. More information can be found in [17]. However, in order to have a smooth communication and full understanding of the functionality and documentation of the library, we first need to clearly define the meaning of a couple of words in the present context. * * \section sec_vocabulary Vocabulary * * * * \section sec_organization Organization of the library * * The library-structure is best analyzed at the hand of the namespace or directory hierarchy (as a matter of fact, there is no difference between the two): * * * \section sec_interface Interface * * You will quickly notice that all methods in OpenGV use a variable called adapter as a function-call parameter. OpenGV is designed based on the adapter pattern. "Adapters" in OpenGV are used as "visitors" to all geometric vision methods. They contain the landmarks, bearing-vectors, poses, correspondences etc. used as an input to the different methods (or references to the alike), and allow to access those elements with a unified interface. Adapters are derived from a base-class that defines the unified interface and they have to implement the related functions for accessing bearing-vectors, world-points, camera-transformations, viewpoint-poses, etc. There are three adapter-base-classes: * * * * The derived adapters have the task of transforming the data from the user-format to OpenGV types. This gives the library great flexibility. Users have to implement only a couple of adapters for the specific data-format they are using, and can then access the full functionality of the library. OpenGV currently contains adapters that simply hold references to OpenGV types (no transformation needed) plus adapters for mexArrays used within the Matlab-interface. Further adapters are planned, such as for instance an adapter for OpenCV keypoint and match-types including a camera model. The user would then be able to chose whether normalization of keypoints is done "on-demand" or "once for all" at the beginning, which is more efficient in sample-consensus problems. * * Note that adapters containing the tag "Central" in their name are adapters for a single camera (i.e. view-points with only one camera having identity transformation). Adapters having the tag "Noncentral" in their name are meant for view-points with multiple cameras (e.g., multi-camera systems, generalized cameras). * * Please check out the doxygen documentation on the above base-classes, they contain important documentation on the functions that need to be overloaded for a proper implementation of an adapter. * * \section sec_conventions Conventions, problem types, and examples * * As already mentioned, the entire library is assuming calibrated cameras/viewpoints, and it operates with 3D unit bearing vectors expressed in the camera frame. Calibrated means that the configuration of the multi-camera system (i.e. the inter-camera transformations) is known. The following introduces the different problems that can be solved with the library, and outlines the conventions for transformations (translations and rotations) in their context. Note that all problems have solutions for both the minimal and non-minimal cases, and may also be solved as sample-consensus or non-linear optimization problems. The code samples are mostly taken from the test files, which you can compile along with the library by setting BUILD_TESTS in CMakeLists.txt to ON. * * * * Note that there are more unit-tests in the test-directory. It shows the usage of all the methods contained in the library. * * \section sec_threshold Some words about the sample-consensus-classes * * All the above mentioned Ransac-methods make use of a number of super-classes such that only the basic functions need to be implemented in the derived SacProblem (SampleConsensusProblem). The basic functions are responsible for getting valid samples for model instantiation, model instantiation itself, as well as model verification. SamplesConsensusProblem is the base-class for any problem we want to solve, and contains a virtual interface for the basic methods that need to be implemented. The base-class SampleConsensus is then for the sample-consensus method itself, calling the basic functions. So far only the Ransac is implemented [15]. * * \subsection sec_ransac Ransac threshold * * Since the entire library is operating in 3D, we also need a way to compute and threshold reprojection errors in 3D. What we are looking at is the angle \f$ q \f$ between the original bearing-vector \f$ \mathbf{f}_{meas} \f$ and the reprojected one \f$ \mathbf{f}_{repr} \f$. By adopting a certain threshold angle \f$ q_{threshold} \f$, we hence constrain the \f$ \mathbf{f}_{repr} \f$ to lie within a cone of axis \f$ \mathbf{f}_{meas} \f$ and of opening angle \f$ q_{threshold} \f$. * * \image html reprojectionError.png * \image latex reprojectionError.pdf "" width=0.45\columnwidth * * The threshold-angle \f$ q_{threshold} \f$ can be easily obtained from classical reprojection error-thresholds expressed in pixels \f$ \psi \f$ by assuming a certain focal length \f$ l \f$. We then have \f$ q_{threshold} = \arctan{\frac{\psi}{l}} \f$. * * The threshold we are using in the end is still not quite this one, but a value derived from it in analogy with the computation of reprojection errors. The most efficient way to compute a "reprojection error" is given by taking the scalar product of \f$ \mathbf{f}_{meas} \f$ and \f$ \mathbf{f}_{repr} \f$, which equals to \f$ \cos q \f$. Since this value is between -1 and 1, and we actually want an error that minimizes to 0, we take \f$ \epsilon = 1 - \mathbf{f}_{meas}^{T}\mathbf{f}_{repr} = 1 - \cos q \f$. The threshold error is therefore given by * * \f$ \epsilon_{threshold} = 1 - \cos{q_{threshold}} = 1 - \cos({\arctan{\frac{\psi}{l}}}) \f$ * * In the ransac-examples in the test-folder, you will often see something like this. * \code ransac.threshold_ = 1.0 - cos(atan(sqrt(2.0)*0.5/800.0)); \endcode * * This notably corresponds to the above computation of our "reprojection-error"-threshold, with a focal length of 800.0 and a reprojection error in pixels of 0.5*sqrt(2.0). * * \section sec_multi The "Multi"-stuff * * As you go deeper into the code you might notice that there are a number of elements (mostly in the relative-pose context) that contain the tag "multi" in their name. The adapter base-class used here is called RelativeMultiAdapterBase. The idea of this adapter is to hold multiple sets of bearing-vector correspondences originating from pairs of cameras. A pair of cameras is, as the name says, a set of two cameras in different viewpoints. The correspondences are accessed via a multi-index (a pair-index referring to a specific pair of cameras, and a correspondence-index refering to the correspondence within the camera-pair). * * Subsets of camera-pairs can be identified in a number of problems, such as * * * The multi-adapters keep track of these camera-pair-wise correspondence groups. The benefit of it appears when moving towards random sample-consensus schemes. Have a look at the "opengv/sac/"-folder, it contains the MultiSampleConsensus, MultiRansac, and MultiSampleConsensusProblem classes. They employ the multi-indices, and the derived MultiSampleConsensusProblems exploit the fact that the correspondences are grouped: * * * * All this stuff is highly experimental, so you probably shouldn't pay too much attention to it for the moment ;) * */