1 // Copyright (c) 2018, ETH Zurich and UNC Chapel Hill.
2 // All rights reserved.
3 //
4 // Redistribution and use in source and binary forms, with or without
5 // modification, are permitted provided that the following conditions are met:
6 //
7 // * Redistributions of source code must retain the above copyright
8 // notice, this list of conditions and the following disclaimer.
9 //
10 // * Redistributions in binary form must reproduce the above copyright
11 // notice, this list of conditions and the following disclaimer in the
12 // documentation and/or other materials provided with the distribution.
13 //
14 // * Neither the name of ETH Zurich and UNC Chapel Hill nor the names of
15 // its contributors may be used to endorse or promote products derived
16 // from this software without specific prior written permission.
17 //
18 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
19 // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
21 // ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE
22 // LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
23 // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
24 // SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
25 // INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
26 // CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
27 // ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
28 // POSSIBILITY OF SUCH DAMAGE.
29 //
30 // Author: Johannes L. Schoenberger (jsch-at-demuc-dot-de)
31
32 #ifndef COLMAP_SRC_UTIL_OPTION_MANAGER_H_
33 #define COLMAP_SRC_UTIL_OPTION_MANAGER_H_
34
35 #include <memory>
36
37 #include <boost/program_options.hpp>
38
39 #include "util/logging.h"
40
41 namespace colmap {
42
43 struct ImageReaderOptions;
44 struct SiftExtractionOptions;
45 struct SiftMatchingOptions;
46 struct ExhaustiveMatchingOptions;
47 struct SequentialMatchingOptions;
48 struct VocabTreeMatchingOptions;
49 struct SpatialMatchingOptions;
50 struct TransitiveMatchingOptions;
51 struct ImagePairsMatchingOptions;
52 struct BundleAdjustmentOptions;
53 struct IncrementalMapperOptions;
54 struct RenderOptions;
55
56 namespace mvs {
57 struct PatchMatchOptions;
58 struct StereoFusionOptions;
59 struct PoissonMeshingOptions;
60 struct DelaunayMeshingOptions;
61 } // namespace mvs
62
63 class OptionManager {
64 public:
65 OptionManager(bool add_project_options = true);
66
67 // Create "optimal" set of options for different reconstruction scenarios.
68 // Note that the existing options are modified, so if your parameters are
69 // already low quality, they will be further modified.
70 void ModifyForIndividualData();
71 void ModifyForVideoData();
72 void ModifyForInternetData();
73
74 // Create "optimal" set of options for different quality settings.
75 // Note that the existing options are modified, so if your parameters are
76 // already low quality, they will be further degraded.
77 void ModifyForLowQuality();
78 void ModifyForMediumQuality();
79 void ModifyForHighQuality();
80 void ModifyForExtremeQuality();
81
82 void AddAllOptions();
83 void AddLogOptions();
84 void AddRandomOptions();
85 void AddDatabaseOptions();
86 void AddImageOptions();
87 void AddExtractionOptions();
88 void AddMatchingOptions();
89 void AddExhaustiveMatchingOptions();
90 void AddSequentialMatchingOptions();
91 void AddVocabTreeMatchingOptions();
92 void AddSpatialMatchingOptions();
93 void AddTransitiveMatchingOptions();
94 void AddImagePairsMatchingOptions();
95 void AddBundleAdjustmentOptions();
96 void AddMapperOptions();
97 void AddPatchMatchStereoOptions();
98 void AddStereoFusionOptions();
99 void AddPoissonMeshingOptions();
100 void AddDelaunayMeshingOptions();
101 void AddRenderOptions();
102
103 template <typename T>
104 void AddRequiredOption(const std::string& name, T* option,
105 const std::string& help_text = "");
106 template <typename T>
107 void AddDefaultOption(const std::string& name, T* option,
108 const std::string& help_text = "");
109
110 void Reset();
111 void ResetOptions(const bool reset_paths);
112
113 bool Check();
114
115 void Parse(const int argc, char** argv);
116 bool Read(const std::string& path);
117 bool ReRead(const std::string& path);
118 void Write(const std::string& path) const;
119
120 std::shared_ptr<std::string> project_path;
121 std::shared_ptr<std::string> database_path;
122 std::shared_ptr<std::string> image_path;
123
124 std::shared_ptr<ImageReaderOptions> image_reader;
125 std::shared_ptr<SiftExtractionOptions> sift_extraction;
126
127 std::shared_ptr<SiftMatchingOptions> sift_matching;
128 std::shared_ptr<ExhaustiveMatchingOptions> exhaustive_matching;
129 std::shared_ptr<SequentialMatchingOptions> sequential_matching;
130 std::shared_ptr<VocabTreeMatchingOptions> vocab_tree_matching;
131 std::shared_ptr<SpatialMatchingOptions> spatial_matching;
132 std::shared_ptr<TransitiveMatchingOptions> transitive_matching;
133 std::shared_ptr<ImagePairsMatchingOptions> image_pairs_matching;
134
135 std::shared_ptr<BundleAdjustmentOptions> bundle_adjustment;
136 std::shared_ptr<IncrementalMapperOptions> mapper;
137
138 std::shared_ptr<mvs::PatchMatchOptions> patch_match_stereo;
139 std::shared_ptr<mvs::StereoFusionOptions> stereo_fusion;
140 std::shared_ptr<mvs::PoissonMeshingOptions> poisson_meshing;
141 std::shared_ptr<mvs::DelaunayMeshingOptions> delaunay_meshing;
142
143 std::shared_ptr<RenderOptions> render;
144
145 private:
146 template <typename T>
147 void AddAndRegisterRequiredOption(const std::string& name, T* option,
148 const std::string& help_text = "");
149 template <typename T>
150 void AddAndRegisterDefaultOption(const std::string& name, T* option,
151 const std::string& help_text = "");
152
153 template <typename T>
154 void RegisterOption(const std::string& name, const T* option);
155
156 std::shared_ptr<boost::program_options::options_description> desc_;
157
158 std::vector<std::pair<std::string, const bool*>> options_bool_;
159 std::vector<std::pair<std::string, const int*>> options_int_;
160 std::vector<std::pair<std::string, const double*>> options_double_;
161 std::vector<std::pair<std::string, const std::string*>> options_string_;
162
163 bool added_log_options_;
164 bool added_random_options_;
165 bool added_database_options_;
166 bool added_image_options_;
167 bool added_extraction_options_;
168 bool added_match_options_;
169 bool added_exhaustive_match_options_;
170 bool added_sequential_match_options_;
171 bool added_vocab_tree_match_options_;
172 bool added_spatial_match_options_;
173 bool added_transitive_match_options_;
174 bool added_image_pairs_match_options_;
175 bool added_ba_options_;
176 bool added_mapper_options_;
177 bool added_patch_match_stereo_options_;
178 bool added_stereo_fusion_options_;
179 bool added_poisson_meshing_options_;
180 bool added_delaunay_meshing_options_;
181 bool added_render_options_;
182 };
183
184 ////////////////////////////////////////////////////////////////////////////////
185 // Implementation
186 ////////////////////////////////////////////////////////////////////////////////
187
188 template <typename T>
AddRequiredOption(const std::string & name,T * option,const std::string & help_text)189 void OptionManager::AddRequiredOption(const std::string& name, T* option,
190 const std::string& help_text) {
191 desc_->add_options()(name.c_str(),
192 boost::program_options::value<T>(option)->required(),
193 help_text.c_str());
194 }
195
196 template <typename T>
AddDefaultOption(const std::string & name,T * option,const std::string & help_text)197 void OptionManager::AddDefaultOption(const std::string& name, T* option,
198 const std::string& help_text) {
199 desc_->add_options()(
200 name.c_str(),
201 boost::program_options::value<T>(option)->default_value(*option),
202 help_text.c_str());
203 }
204
205 template <typename T>
AddAndRegisterRequiredOption(const std::string & name,T * option,const std::string & help_text)206 void OptionManager::AddAndRegisterRequiredOption(const std::string& name,
207 T* option,
208 const std::string& help_text) {
209 desc_->add_options()(name.c_str(),
210 boost::program_options::value<T>(option)->required(),
211 help_text.c_str());
212 RegisterOption(name, option);
213 }
214
215 template <typename T>
AddAndRegisterDefaultOption(const std::string & name,T * option,const std::string & help_text)216 void OptionManager::AddAndRegisterDefaultOption(const std::string& name,
217 T* option,
218 const std::string& help_text) {
219 desc_->add_options()(
220 name.c_str(),
221 boost::program_options::value<T>(option)->default_value(*option),
222 help_text.c_str());
223 RegisterOption(name, option);
224 }
225
226 template <typename T>
RegisterOption(const std::string & name,const T * option)227 void OptionManager::RegisterOption(const std::string& name, const T* option) {
228 if (std::is_same<T, bool>::value) {
229 options_bool_.emplace_back(name, reinterpret_cast<const bool*>(option));
230 } else if (std::is_same<T, int>::value) {
231 options_int_.emplace_back(name, reinterpret_cast<const int*>(option));
232 } else if (std::is_same<T, double>::value) {
233 options_double_.emplace_back(name, reinterpret_cast<const double*>(option));
234 } else if (std::is_same<T, std::string>::value) {
235 options_string_.emplace_back(name,
236 reinterpret_cast<const std::string*>(option));
237 } else {
238 LOG(FATAL) << "Unsupported option type";
239 }
240 }
241
242 } // namespace colmap
243
244 #endif // COLMAP_SRC_UTIL_OPTION_MANAGER_H_
245