1 #include <iostream>
2 #include <cstdio>
3 #include <sstream>
4 #include "bwm_site_mgr.h"
5 //:
6 // \file
7 #include <bwm/io/bwm_site_sptr.h>
8 #include <bwm/io/bwm_site.h>
9 #include "bwm_observer_mgr.h"
10 #include "bwm_tableau_mgr.h"
11 #include "bwm_tableau_video.h"
12 #include "bwm_tableau_fiducial.h"
13
14 #include "bwm_observable_mesh.h"
15 #include "bwm_world.h"
16 #include "bwm_def.h"
17 #include "algo/bwm_utils.h"
18 #include "video/bwm_video_site_io.h"
19 #include "video/bwm_video_corr.h"
20 #include "video/bwm_video_cam_istream.h"
21 #include "vpgl/vpgl_perspective_camera.h"
22 #include <bpgl/algo/bpgl_project.h>
23 #include <depth_map/depth_map_scene.h>
24 #include "vgl/vgl_point_3d.h"
25 #include "vgl/vgl_vector_3d.h"
26 #include "vgl/vgl_box_3d.h"
27 #include <vgl/algo/vgl_rotation_3d.h>
28 #include "vnl/vnl_double_3.h"
29 #include "vnl/vnl_quaternion.h"
30 #ifdef _MSC_VER
31 # include "vcl_msvc_warnings.h"
32 #endif
33
34 #include "vul/vul_file.h"
35 #include "vul/vul_string.h"
36 #include "vgui/vgui_tableau_sptr.h"
37
38 #ifdef WIN32
39 #define _LIB
40 #endif
41 #include <expatpp.h> // for accessing methods in parent class of bwm_io_config_parser
42
43 bwm_site_mgr* bwm_site_mgr::instance_ = nullptr;
44
instance()45 bwm_site_mgr* bwm_site_mgr::instance()
46 {
47 if (!instance_) {
48 instance_ = new bwm_site_mgr();
49 }
50 return bwm_site_mgr::instance_;
51 }
52
bwm_site_mgr()53 bwm_site_mgr::bwm_site_mgr(): site_name_(""), site_dir_(""), pyr_exe_(""),
54 camera_path_(""), video_path_("")
55 {
56 tk_name_ = vgui::toolkit_name();
57 #ifdef HAS_MFC
58 site_create_process_ = new bwm_site_process();
59 #endif
60 object_types_.resize(OBJ_UNDEF);
61 object_types_[MESH_FEATURE] = BWM_MESH_FEATURE_STR;
62 object_types_[MESH_IMAGE_PROCESSING] = BWM_MESH_IMAGE_PROCESSING_STR;
63 object_types_[MESH_TERRAIN] = BWM_MESH_TERRAIN_STR;
64 object_types_[VSOL] = BWM_OBJ_VSOL_STR;
65 }
66
~bwm_site_mgr()67 bwm_site_mgr::~bwm_site_mgr()
68 {
69 #ifdef HAS_MFC
70 delete site_create_process_;
71 #endif
72 }
73
init_site()74 void bwm_site_mgr::init_site()
75 {
76 if(tk_name_ != "mfc"){
77 std::cout << tk_name_ << " lacks functionality to create" << std::endl;
78 return;
79 }
80 // delete the active tableaux
81 for (unsigned i=0; i<active_tableaus_.size(); i++)
82 delete active_tableaus_[i];
83 active_tableaus_.clear();
84
85 // delete the inactive tableaux
86 for (unsigned i=0; i<inactive_tableaus_.size(); i++)
87 delete inactive_tableaus_[i];
88 inactive_tableaus_.clear();
89
90 // clear the objects
91 site_objs_.clear();
92 #ifdef HAS_MFC
93 if (site_create_process_) {
94 delete site_create_process_;
95 this->site_create_process_ = new bwm_site_process();
96 }
97 #endif
98 site_name_="";
99 site_dir_="";
100 pyr_exe_="";
101
102 bwm_observer_mgr::instance()->clear();
103 bwm_world::instance()->clear();
104
105 timer_.mark();
106 }
107
create_site_dialog(vgui_dialog_extensions & site_dialog,std::string & site_name,std::string & site_dir,std::string & pyr_exe_dir,std::vector<std::string> & files,bool * pyr_v,bool * act_v,std::vector<std::string> & pyr_levels,std::vector<std::string> & objs,int * choices,double & lat,double & lon,double & elev)108 void bwm_site_mgr::create_site_dialog(vgui_dialog_extensions &site_dialog,
109 std::string &site_name,
110 std::string &site_dir,
111 std::string &pyr_exe_dir,
112 std::vector<std::string> &files,
113 bool* pyr_v, bool* act_v,
114 std::vector<std::string> &pyr_levels,
115 std::vector<std::string> &objs,
116 int* choices,
117 double &lat, double &lon, double &elev)
118 {
119 std::string ext;
120 site_dialog.field("SITE NAME:", site_name);
121 site_dialog.line_break();
122 site_dialog.dir("DIRECTORY:", ext, site_dir);
123 site_dialog.line_break();
124 site_dialog.file("Pyramid exe path:", ext, pyr_exe_dir);
125 site_dialog.line_break();
126 //site_dialog.line_break();
127 site_dialog.set_modal(true);
128
129 // add a bunch of images
130 site_dialog.message("Please Choose the Images for this site:");
131 site_dialog.line_break();
132 for (unsigned i=0; i<files.size(); i++) {
133 site_dialog.file("Image Path:", ext, files[i]);
134 site_dialog.checkbox("Do Pyramid?", pyr_v[i]);
135 site_dialog.field("Levels:", pyr_levels[i]);
136 site_dialog.checkbox("Is Active?", act_v[i]);
137 site_dialog.line_break();
138 }
139
140 site_dialog.message("Please Choose the objects to add to the site:");
141 site_dialog.line_break();
142
143 std::vector<std::string> obj_types(4);
144 for (unsigned i=0; i<objs.size(); i++) {
145 site_dialog.file("Enter input object:", ext, objs[i]);
146 site_dialog.choice("Type:", object_types_, choices[i]);
147 site_dialog.line_break();
148 }
149
150 //site_dialog.line_break();
151 site_dialog.message("Enter the LVCS origin for this site:");
152 site_dialog.line_break();
153 site_dialog.field("Lat:", lat);
154 site_dialog.field("Lon:", lon);
155 site_dialog.field("Elev:", elev);
156 site_dialog.line_break();
157 site_dialog.set_ok_button("CREATE");
158 }
159
160
161 //: create a dialog box to create site to add images, objects, etc..
create_site()162 void bwm_site_mgr::create_site()
163 {
164 if(tk_name_ != "mfc"){
165 std::cout << tk_name_ << " lacks functionality to create a site" << std::endl;
166 return;
167 }
168 vgui_dialog_extensions site_dialog("CrossCut Site Creation");
169
170 std::string site_name, site_dir, pyr_exe_path;
171
172 int num_images = 3;
173 std::vector<std::string> files(num_images);
174 bool pyr[3] = {false, false, false};
175 bool act[3] = {true, true, true};
176 std::vector<std::string> levels(num_images, "7");
177
178 int num_objs = 3;
179 std::vector<std::string> objs(num_objs);
180 int choices[3] = {0, 0, 0};
181 double lat=0.0, lon=0.0, elev=0.0;
182
183 create_site_dialog(site_dialog, site_name, site_dir, pyr_exe_path, files, pyr,
184 act, levels, objs, choices, lat, lon, elev);
185
186 if (!site_dialog.ask()) {
187 return;
188 }
189 else
190 {
191 // collect the parameters
192 std::cout << "name:" << site_name << '\n'
193 << "dir:" << site_dir << std::endl;
194
195 // make sure site name is filled
196 while (site_name.size() == 0) {
197 vgui_dialog error ("Error");
198 error.message ("Please enter a valid SITE NAME! " );
199 error.ask();
200 if (! site_dialog.ask())
201 return;
202 }
203
204 // make sure site directory is filled and valid
205 while ((site_dir.size() == 0) || !vul_file::is_directory(site_dir)) {
206 vgui_dialog error ("Error");
207 error.message ("Please enter a valid SITE DIRECTORY! " );
208 error.ask();
209 if (! site_dialog.ask())
210 return;
211 }
212
213 // check if the levels are numbers
214 bool not_int = true;
215 while (not_int) {
216 not_int = false;
217 for (unsigned i=0; i<levels.size(); i++) {
218 int l = vul_string_atoi(levels[i].c_str());
219 if (l == 0) {
220 not_int = true;
221 break;
222 }
223 }
224 if (not_int) {
225 vgui_dialog error ("Error");
226 error.message ("Please enter an integer level value! " );
227 error.ask();
228 if (! site_dialog.ask())
229 return;
230 }
231 else {
232 not_int = false;
233 }
234 }
235 }
236
237 std::vector<bool> pyramid;
238 std::vector<bool> active;
239 for (unsigned j=0; j<files.size(); j++) {
240 pyramid.push_back(pyr[j]);
241 active.push_back(act[j]);
242 }
243
244 std::vector<std::pair<std::string, std::string> > objects;
245 for (unsigned obj=0; obj<objs.size(); obj++) {
246 std::pair<std::string, std::string> pair(objs[obj], object_types_[choices[obj]]);
247 objects.push_back(pair);
248 }
249
250 bwm_site_sptr site = new bwm_site(site_name, site_dir, files, pyramid, active,
251 levels, objects, new vsol_point_3d(lat, lon, elev));
252
253 // temporarily setting the exe path, will find a better solution later - Gamze
254 site->pyr_exe_path_ = pyr_exe_path;
255 #ifdef HAS_MFC
256 site_create_process_->set_site(site);
257 site_create_process_->StartBackgroundTask();
258 #else
259 vgui_dialog error ("Error");
260 error.message ("Site is not created! MFC (Windows platforms) is needed for this task!" );
261 error.ask();
262 if (! site_dialog.ask())
263 return;
264 std::cout << "Site is not created MFC (Windows) is needed for this task!" << std::endl;
265 #endif
266 }
267
268 //: create a dialog box to create site to add images, objects, etc..
edit_site()269 void bwm_site_mgr::edit_site()
270 {
271 if(tk_name_ != "mfc"){
272 std::cout << tk_name_ << " lacks functionality to edit" << std::endl;
273 return;
274 }
275 bwm_io_config_parser* parser = nullptr;
276 parser = parse_config();
277 if (parser == nullptr) {
278 std::cerr << "Site File is not a valid XML site!\n";
279 return;
280 }
281
282 vgui_dialog_extensions site_edit_dialog("Edit World Model Site");
283 bwm_site_sptr site = parser->site();
284
285 // new creation vars
286 int num_images = 3;
287 std::vector<std::string> files(num_images);
288 bool pyr[3] = {false, false, false};
289 bool act[3] = {true, true, true};
290 std::vector<std::string> levels(num_images, "7");
291
292 int num_objs = 3;
293 std::vector<std::string> objs(num_objs);
294 int choices[3] = {0, 0, 0};
295 double lat=0.0, lon=0.0, elev=0.0;
296
297 // previously created obj vars
298 bool act_old[30];
299 bool tab_remove[30];
300 std::vector<std::string> cam;
301 std::string ext;
302
303 site_edit_dialog.file("Pyramid Exe Path:", ext, site->pyr_exe_path_);
304 site_edit_dialog.line_break();
305
306 // first place the existing tableaux on the dialog
307 std::vector<bwm_io_tab_config* > tableaus;
308 site->tableaus(tableaus);
309 cam.resize(tableaus.size());
310 if (tableaus.size() > 0)
311 {
312 site_edit_dialog.message("EXISTING IMAGES:");
313 site_edit_dialog.line_break();
314
315 for (unsigned i=0; i<tableaus.size(); i++)
316 {
317 bwm_io_tab_config* t = tableaus[i];
318 if (t->type_name.compare(IMAGE_TABLEAU_TAG) == 0)
319 {
320 bwm_io_tab_config_img* img_tab = static_cast<bwm_io_tab_config_img* > (t);
321 bool active = img_tab->status;
322 std::string name = img_tab->name;
323 std::string path = img_tab->img_path;
324 site_edit_dialog.message((" -- "+path).c_str());
325 tab_remove[i] = false;
326 site_edit_dialog.checkbox("Remove", tab_remove[i]);
327 act_old[i] = active;
328 site_edit_dialog.checkbox("Active", act_old[i]);
329 #if 0
330 std::string ext = "*.RPG";
331 site_edit_dialog.file("Add Camera:", ext, cam[i]);
332 #endif // 0
333 site_edit_dialog.line_break();
334 }
335 else if (t->type_name.compare(CAMERA_TABLEAU_TAG) == 0)
336 {
337 bwm_io_tab_config_cam* cam_tab = static_cast<bwm_io_tab_config_cam* > (t);
338 bool active = cam_tab->status;
339 site_edit_dialog.message((" -- "+cam_tab->img_path).c_str());
340 tab_remove[i] = false;
341 site_edit_dialog.checkbox("Remove ", tab_remove[i]);
342 act_old[i] = active;
343 site_edit_dialog.checkbox("Active ", act_old[i]);
344 site_edit_dialog.line_break();
345 }
346 }
347 }
348
349 // add a bunch of images
350 site_edit_dialog.message("ADD NEW:");
351 site_edit_dialog.line_break();
352 for (unsigned i=0; i<files.size(); i++) {
353 std::string ext;
354 site_edit_dialog.file("Image Path:", ext, files[i]);
355 site_edit_dialog.checkbox("Do Pyramid?", pyr[i]);
356 site_edit_dialog.field("Levels:", levels[i]);
357 site_edit_dialog.checkbox("Is Active?", act[i]);
358 site_edit_dialog.line_break();
359 }
360
361 site_edit_dialog.line_break();
362
363 // put the existing objects
364 std::vector<std::pair<std::string, std::string> > object_paths;
365 bool obj_remove[30];
366 parser->site()->objects(object_paths);
367
368 if (object_paths.size() > 0) {
369 site_edit_dialog.message("EXISTING OBJECTS:");
370 site_edit_dialog.line_break();
371
372 for (unsigned i=0; i<object_paths.size(); i++) {
373 site_edit_dialog.message((" -- " + object_paths[i].first).c_str());
374 std::string object_type = object_paths[i].second;
375 site_edit_dialog.message(("Type: " + object_type).c_str());
376 obj_remove[i] = false;
377 site_edit_dialog.checkbox("Remove ", obj_remove[i]);
378 site_edit_dialog.line_break();
379 }
380 }
381 // create new objects
382 site_edit_dialog.message("ADD OBJECTS:");
383 site_edit_dialog.line_break();
384 for (unsigned i=0; i<objs.size(); i++) {
385 site_edit_dialog.file("Object:", ext, objs[i]);
386 site_edit_dialog.choice("Type:", object_types_, choices[i]);
387 site_edit_dialog.line_break();
388 }
389
390 // lvcs
391 site_edit_dialog.line_break();
392 site_edit_dialog.message("LVCS origin for this site:");
393 site_edit_dialog.line_break();
394
395 lat = lon = elev = 0.0;
396 if (parser->site()->lvcs_) {
397 lat = parser->site()->lvcs_->x();
398 lon = parser->site()->lvcs_->y();
399 elev = parser->site()->lvcs_->z();
400 }
401 site_edit_dialog.field("Lat:", lat);
402 site_edit_dialog.field("Lon:", lon);
403 site_edit_dialog.field("Elev:", elev);
404
405 site_edit_dialog.line_break();
406 site_edit_dialog.set_ok_button("EDIT");
407 if (!site_edit_dialog.ask()) {
408 return;
409 }
410 else
411 {
412 // check if the level values are integer
413
414 // create a removal list for the tableaux that are marked for removal
415 std::vector<unsigned> removal;
416 for (unsigned t=0; t<tableaus.size(); t++) {
417 tableaus[t]->status = act_old[t];
418 if (tab_remove[t])
419 removal.push_back(t);
420 }
421 site->remove_ = removal;
422
423 // delete objects that are marked for removal
424 std::vector<std::pair<std::string, std::string> > undeleted_objs;
425 bool deleted = false;
426 for (unsigned i=0; i<object_paths.size(); i++) {
427 if (!obj_remove[i]) {
428 undeleted_objs.push_back(object_paths[i]);
429 }
430 else
431 deleted = true;
432 }
433 if (deleted) {
434 site->objects_.clear();
435 site->objects_ = undeleted_objs;
436 }
437
438 // create an updated site
439 std::vector<bool> pyramid;
440 std::vector<bool> active;
441 for (unsigned j=0; j<files.size(); j++) {
442 pyramid.push_back(pyr[j]);
443 active.push_back(act[j]);
444 }
445
446 std::vector<std::pair<std::string, std::string> > objects;
447 for (unsigned obj=0; obj<objs.size(); obj++) {
448 std::pair<std::string, std::string> pair(objs[obj], object_types_[choices[obj]]);
449 objects.push_back(pair);
450 }
451 #if 0
452 std::vector<std::vector<std::pair<std::string, vsol_point_2d> > > corr = parser->correspondences();
453 for (unsigned i=0; i<corr.size(); i++) {
454 bwm_corr_sptr c = new bwm_corr();
455 if (parser->corresp_mode().compare("IMAGE_TO_IMAGE") == 0)
456 c->set_mode(true);
457 else {
458 c->set_mode(false);
459 c->set_world_point(parser->corresp_world_pts()[i]);
460 }
461 }
462 site->corresp_mode = parser->corresp_mode();
463 site->corr_type_ = parser->corresp_type();
464 // std::vector<vsol_point_3d> corresp_world_pts() {return corresp_world_pts_; }
465 #endif // 0
466
467 site->add(files, pyramid, active, levels, objects, new vsol_point_3d(lat, lon, elev));
468 #ifdef HAS_MFC
469 site_create_process_->set_site(site);
470 site_create_process_->StartBackgroundTask();
471 #endif
472 }
473 }
474
475
load_site()476 void bwm_site_mgr::load_site()
477 {
478 bwm_io_config_parser* parser = parse_config();
479
480 if (parser)
481 {
482 init_site();
483 bwm_site_sptr site = parser->site();
484 std::vector<bwm_io_tab_config* > tableaus;
485 site->tableaus(tableaus);
486
487 site_name_ = site->name_;
488 site_dir_ = site->path_;
489 pyr_exe_ = site->pyr_exe_path_;
490
491 // get the lvcs
492 vsol_point_3d_sptr lvcs = site->lvcs_;
493 // if LVCS is not set, do not use it
494 if (!lvcs||*lvcs == vsol_point_3d(0, 0, 0))
495 lvcs = nullptr;
496 else {
497 double lat = lvcs->x();
498 double lon = lvcs->y();
499 double elev = lvcs->z();
500 bwm_world::instance()->set_lvcs(lat, lon, elev);
501 }
502
503 // create the active tableaux
504 for (unsigned i=0; i<tableaus.size(); i++)
505 {
506 bwm_io_tab_config* t = tableaus[i];
507 if (t->status) {
508 // create an active tableau
509 bwm_tableau_img* tab = tableau_factory_.create_tableau(t);
510 bwm_tableau_mgr::instance()->add_tableau(tab, t->name);
511 active_tableaus_.push_back(t->clone());
512 }
513 else // inactive tableau
514 inactive_tableaus_.push_back(t->clone());
515 }
516
517 // create the correspondences
518 std::vector<std::vector<std::pair<std::string, vsol_point_2d> > > corresp;
519 corresp = site->corresp_;
520 if (corresp.size() > 0) {
521 std::string mode = site->corr_mode_;
522 std::string type = site->corr_type_;
523
524 if (type.compare("MULTIPLE") == 0)
525 bwm_observer_mgr::instance()->set_n_corrs(bwm_observer_mgr::MULTIPLE_CORRS);
526 else if (type.compare("SINGLE") == 0)
527 bwm_observer_mgr::instance()->set_n_corrs(bwm_observer_mgr::SINGLE_PT_CORR);
528 else
529 std::cerr << "ERROR: Undefined Correspondence type=" << type << '\n';
530
531 if (mode == "WORLD_TO_IMAGE") {
532 if (corresp.size() > 0) {
533 if (site->corresp_world_pts_.size() > 0)
534 bwm_world::instance()->set_world_pt(site->corresp_world_pts_[0].get_p());
535 else
536 std::cerr << "There is something wrong, the more is W-to-I but there is no world point\n";
537 }
538 bwm_observer_mgr::instance()->set_corr_mode(bwm_observer_mgr::WORLD_TO_IMAGE);
539 }
540 else if (mode == "IMAGE_TO_IMAGE") {
541 bwm_observer_mgr::instance()->set_corr_mode(bwm_observer_mgr::IMAGE_TO_IMAGE);
542 }
543
544 for (unsigned i=0; i<corresp.size(); i++)
545 {
546 bwm_corr_sptr corr = new bwm_corr();
547 std::vector<std::pair<std::string, vsol_point_2d> > elm = corresp[i];
548
549 if (mode == "WORLD_TO_IMAGE") {
550 corr->set_mode(false);
551 corr->set_world_pt(site->corresp_world_pts_[i].get_p());
552 //sets the same pt each time FIXME -JLM
553 //bwm_world::instance()->set_world_pt(corr->world_pt());
554 }
555 else if (mode == "IMAGE_TO_IMAGE") {
556 corr->set_mode(true);
557 }
558
559 std::string tab_name;
560 double X, Y;
561 for (unsigned j=0; j<elm.size(); j++) {
562 tab_name = elm[j].first;
563 X = elm[j].second.x();
564 Y = elm[j].second.y();
565 bwm_tableau_mgr::instance()->add_corresp(tab_name, corr, X, Y);
566 #if 0 // commented out
567 vgui_tableau_sptr tab = this->find_tableau(tab_name);
568 if (tab) {
569 if ((tab->type_name().compare("bwm_tableau_proj_cam") == 0) ||
570 (tab->type_name().compare("bwm_tableau_rat_cam") == 0)) {
571 bwm_tableau_cam* tab_cam = static_cast<bwm_tableau_cam*> (tab.as_pointer());
572 bwm_observer_cam* obs = tab_cam->observer();
573 if (obs) {
574 corr->set_match(obs, X, Y);
575 obs->add_cross(X, Y, 3);
576 }
577 }
578 }
579 #endif // 0
580 }
581 bwm_observer_mgr::instance()->set_corr(corr);
582 }
583 }
584 // create the objects
585 std::vector<std::pair<std::string, std::string> > objs;
586 site->objects(objs);
587 for (unsigned i=0; i<objs.size(); i++)
588 {
589 std::string path = objs[i].first;
590 std::string type = objs[i].second;
591 if (path.size() > 0)
592 {
593 if (!vul_file::exists(path))
594 std::cerr << "ERROR: The object file \"" << path << "\" could not be found!\n";
595 else {
596 if (type.compare(object_types_[VSOL]) == 0) {
597 // will be implemented later!!!
598 }
599 else {
600 // comes here if it is a mesh
601 bwm_observable_mesh_sptr mesh = new bwm_observable_mesh();
602 mesh->load_from(path);
603 if (mesh) {
604 bwm_observable_mesh_sptr obj = new bwm_observable_mesh();
605 obj->set_site(site_name_);
606 bwm_observer_mgr::instance()->attach(obj);
607 if (type.compare(object_types_[MESH_FEATURE]) == 0)
608 obj->set_mesh_type(bwm_observable_mesh::BWM_MESH_FEATURE);
609 else if (type.compare(object_types_[MESH_IMAGE_PROCESSING]) == 0)
610 obj->set_mesh_type(bwm_observable_mesh::BWM_MESH_IMAGE_PROCESSING);
611 else if (type.compare(object_types_[MESH_TERRAIN]) == 0)
612 obj->set_mesh_type(bwm_observable_mesh::BWM_MESH_TERRAIN );
613 obj->set_object(mesh->get_object()->clone());
614 bwm_world::instance()->add(obj);
615 }
616 }
617 }
618 }
619 }
620 delete parser;
621 bwm_tableau_mgr::instance()->redraw();
622 }
623 }
624
625 //: saves the site to an XML file
save_site()626 void bwm_site_mgr::save_site()
627 {
628 bwm_site_sptr site = new bwm_site();
629
630 if ((this->site_name_.size() > 0) &&
631 (this->site_dir_.size() > 0) &&
632 (vul_file::exists(this->site_dir_)))
633 {
634 vgui_dialog_extensions d("Saving the Site");
635 d.message(("Saving the site " + site_name_).c_str());
636 d.message(("under: " + site_dir_).c_str());
637 d.line_break();
638 if (!d.ask()) {
639 return;
640 }
641 site->name_ = this->site_name_;
642 site->path_ = this->site_dir_;
643 site->pyr_exe_path_ = this->pyr_exe_;
644 }
645 else
646 {
647 // ask the path for saving the site
648 std::string site_name, site_dir, pyr_exe, ext;
649 vgui_dialog_extensions d("Save the Site!");
650 d.field("Site name:", site_name);
651 d.line_break();
652 d.dir("Site dir:", ext, site_dir);
653 d.line_break();
654 //d.file("Pyramid exe path:" , ext, pyr_exe);
655 //d.line_break();
656 d.line_break();
657 if (!d.ask())
658 return;
659
660 if (!vul_file::is_directory(site_dir)) {
661 std::cerr << "Please enter a directory for the site\n";
662 return;
663 }
664
665 site->name_ = this->site_name_ = site_name;
666 site->path_ = this->site_dir_ = site_dir;
667 site->pyr_exe_path_ = this->pyr_exe_;
668 }
669
670 long time = timer_.real();
671 std::stringstream strm;
672 strm << std::fixed << time;
673 std::string str(strm.str());
674 std::string site_path = site_dir_ + "\\" + site_name_ + "_v" + str + ".xml";
675 std::ofstream s(site_path.data());
676
677 // get the tableaux
678 for (unsigned i=0; i<active_tableaus_.size(); i++) {
679 if (active_tableaus_[i]->type_name.compare("CameraTableau") == 0) {
680 std::string new_cam_path = bwm_tableau_mgr::instance()->save_camera(active_tableaus_[i]->name);
681 bwm_io_tab_config_cam* t = static_cast<bwm_io_tab_config_cam*> (active_tableaus_[i]);
682 t->cam_path = new_cam_path;
683 }
684 site->tableaus_.push_back(active_tableaus_[i]->clone());
685 }
686
687 // add the inactive tableaux
688 for (unsigned i=0; i<inactive_tableaus_.size(); i++) {
689 site->tableaus_.push_back(inactive_tableaus_[i]->clone());
690 }
691
692 // add the correspondences if any
693 bwm_observer_mgr* obs_mgr = bwm_observer_mgr::instance();
694 if (obs_mgr->corr_mode() == bwm_observer_mgr::IMAGE_TO_IMAGE)
695 site->corr_mode_ = "IMAGE_TO_IMAGE";
696 else {
697 site->corr_mode_ = "WORLD_TO_IMAGE";
698 }
699
700 if (obs_mgr->n_corrs() == bwm_observer_mgr::MULTIPLE_CORRS)
701 site->corr_type_ = "MULTIPLE";
702 else
703 site->corr_type_ = "SINGLE";
704
705 std::vector<bwm_corr_sptr> c_list = bwm_observer_mgr::instance()->correspondences();
706 for (unsigned i=0; i<c_list.size(); i++) {
707 site->corresp_.push_back(c_list[i]->match_list());
708 site->corresp_world_pts_.push_back(c_list[i]->world_pt());
709 }
710
711 // add the objects
712 // ask one camera tableau to save its objects
713 std::vector<bwm_observable_sptr> objs = bwm_world::instance()->objects();
714 std::string obj_path = site_dir_ + "\\" + site_name_ + "_objects\\";
715 vul_file::make_directory(obj_path);
716 for (unsigned i=0; i<objs.size(); i++) {
717 if (objs[i]) {
718 std::stringstream strm;
719 strm << std::fixed << i;
720 std::string str(strm.str());
721 std::string fname = obj_path + "mesh_" + str + ".ply";
722 objs[i]->save(fname.c_str());
723 site->objects_.push_back(std::pair<std::string, std::string>(fname, object_types_[MESH_FEATURE]));
724 }
725 }
726
727 site->x_write(s);
728 }
729
load_video_site()730 void bwm_site_mgr::load_video_site()
731 {
732 std::string site_path = bwm_utils::select_file();
733 if (!site_path.size())
734 {
735 std::cerr << "In bwm_site_mgr::load_video_site() - no site path specified\n";
736 return;
737 }
738
739 bwm_video_site_io cio;
740 if (!cio.open(site_path))
741 {
742 std::cerr << "In bwm_site_mgr::load_video_site() - load failed in XML parse\n";
743 return;
744 }
745 site_name_ = cio.name();
746 std::string frame_glob = cio.video_path();
747 std::string camera_glob = cio.camera_path();
748 bwm_io_tab_config_video* v = new bwm_io_tab_config_video(site_name_, true, frame_glob, camera_glob);
749 active_tableaus_.push_back(v);
750 bwm_tableau_img* t = tableau_factory_.create_tableau(v);
751 if (!t)
752 return;
753 bwm_tableau_video* vt = static_cast<bwm_tableau_video*> (t);
754 vt->set_corrs(cio.corrs());
755 bwm_tableau_mgr::instance()->add_tableau(t, site_name_);
756
757 site_dir_ = cio.site_directory();
758 video_path_ = cio.video_path();
759 camera_path_ = cio.camera_path();
760 std::vector<std::string> obj_types = cio.object_types();
761 std::vector<std::string> obj_paths = cio.object_paths();
762 unsigned nobj = obj_types.size();
763 if (!nobj) return;
764 bwm_tableau_mgr::instance()->set_draw_mode_face();
765 for (unsigned i = 0; i<nobj; ++i) {
766 if (obj_types[i]!="mesh_feature") continue;
767 bwm_observable_mesh_sptr mesh = new bwm_observable_mesh();
768 mesh->load_from(obj_paths[i]);
769 if (mesh) {
770 bwm_observable_mesh_sptr obj = new bwm_observable_mesh();
771 bwm_observer_mgr::instance()->attach(obj);
772 obj->set_path(obj_paths[i]);
773 obj->set_mesh_type(bwm_observable_mesh::BWM_MESH_FEATURE);
774 obj->set_object(mesh->get_object()->clone());
775 bwm_world::instance()->add(obj);
776 }
777 }
778 }
779
save_video_site()780 void bwm_site_mgr::save_video_site()
781 {
782 //for now - only support one video observer
783
784 //also for now if the site was initialized with just a directory containing
785 //mesh objects the saved site file will have a null directory path
786 //but with the individual object paths included inside the objects scope.
787 //the effect is the same it is just that the file is somewhat more verbose
788 // it is not clear where an object directory path should go bwm_world?
789
790 bool found = false;
791 std::vector<bwm_observer_cam*> obsvs =
792 bwm_observer_mgr::instance()->observers_cam();
793 bwm_observer_video* obv = nullptr;
794
795 for (std::vector<bwm_observer_cam*>::iterator oit = obsvs.begin();
796 oit != obsvs.end()&&!found; ++oit)
797 if ((*oit)->type_name()=="bwm_observer_video")
798 {
799 obv = static_cast<bwm_observer_video*>(*oit);
800 found =true;
801 }
802
803 if (!found)
804 {
805 std::cerr << "In bwm_site_mgr::save_video_site() - no observer of type video\n";
806 return;
807 }
808
809 bwm_video_site_io vio;
810
811 if ((this->site_name_.size() > 0) &&
812 (this->site_dir_.size() > 0) &&
813 (vul_file::exists(this->site_dir_)))
814 {
815 vgui_dialog d("Saving the Video Site");
816 d.message(("Saving the site " + site_name_).c_str());
817 d.message(("under: " + site_dir_).c_str());
818 d.line_break();
819 if (!d.ask()) {
820 return;
821 }
822 vio.set_name(this->site_name_);
823 vio.set_site_directory(this->site_dir_);
824 vio.set_video_path(this->video_path_);
825 vio.set_camera_path(this->camera_path_);
826 }
827 else
828 {
829 // ask the path for saving the site
830 std::string ext = "png";
831 vgui_dialog_extensions d("Save the Video Site!"); //Still will NOT work in Linux!
832 d.field("Video Site Name:", this->site_name_);
833 d.line_break();
834 d.dir("Video Site Dir:", ext, this->site_dir_);
835 d.line_break();
836 d.line_break();
837 if (!d.ask())
838 return;
839 if (!vul_file::is_directory(this->site_dir_)) {
840 std::cerr << "Please enter a directory for the video site\n";
841 return;
842 }
843
844 vio.set_name(this->site_name_);
845 vio.set_site_directory(this->site_dir_);
846 vio.set_video_path(obv->image_path());
847 vio.set_camera_path(obv->camera_path());
848 }
849
850 std::vector<bwm_observable_sptr> objs = bwm_world::instance()->objects();
851 std::vector<std::string> obj_types;
852 std::vector<std::string> obj_paths;
853 std::string obj_dir = site_dir_ + "/" + site_name_ + "_objects/";
854 vul_file::make_directory(obj_dir);
855 unsigned iobj = 0;
856 for (std::vector<bwm_observable_sptr>::iterator oit = objs.begin();
857 oit != objs.end(); ++oit, ++iobj)
858 if ((*oit)->type_name()=="bwm_observable_mesh") {
859 std::stringstream strm;
860 strm << std::fixed << iobj;
861 std::string str(strm.str());
862 std::string path = obj_dir + "mesh_" + str + ".ply";
863 obj_types.push_back("mesh_feature");
864 obj_paths.push_back(path);
865 (*oit)->save(path.c_str());
866 }
867 else
868 std::cout << "Can't save object of type " << (*oit)->type_name() << '\n';
869 vio.set_object_types(obj_types);
870 vio.set_object_paths(obj_paths);
871
872 std::vector<bwm_video_corr_sptr> corrs = obv->corrs();
873 vio.set_corrs(corrs);
874 long time = timer_.real();
875 std::stringstream strm;
876 strm << std::fixed << time;
877 std::string ver(strm.str());
878 std::string site_path = site_dir_ + "/" + site_name_ + "_v" + ver + ".xml";
879 vio.x_write(site_path);
880 }
881
load_img_tableau()882 void bwm_site_mgr::load_img_tableau()
883 {
884 vgui_dialog/*_extensions*/ params ("Image Tableau");
885 std::string ext, name, img_file, empty="";
886 params.field("Tableau Name", name);
887 // params.line_break();
888 params.file("Image...", ext, img_file);
889 //params.line_break();
890 params.set_modal(true);
891 if (!params.ask())
892 return;
893
894 if (img_file == "") {
895 bwm_utils::show_error("Please specify an image file (prefix).");
896 return;
897 }
898
899 bwm_io_tab_config_img img(name, true, img_file);
900 bwm_tableau_img* tab = tableau_factory_.create_tableau(&img);
901 bwm_tableau_mgr::instance()->add_tableau(tab, name);
902 active_tableaus_.push_back(img.clone());
903
904 tab->post_redraw();
905 }
906
load_video_tableau()907 void bwm_site_mgr::load_video_tableau()
908 {
909 static std::string video_path = "";
910 static std::string camera_glob = "";
911 std::string name = "none";
912 std::string ext = "";
913 if(tk_name_ == "mfc"){
914 vgui_dialog_extensions params ("Video Tableau");
915 params.field("Tableau Name", name);
916 params.line_break();
917 params.dir("Frame Glob or File", ext, video_path);
918 params.line_break();
919 params.dir("Camera Glob", ext, camera_glob);
920 params.line_break();
921 params.set_modal(true);
922 if (!params.ask())
923 return;
924 }else{
925 vgui_dialog params ("Video Tableau");
926 params.field("Tableau Name", name);
927 params.line_break();
928 params.file("Frame Glob or File", ext, video_path);
929 params.line_break();
930 params.file("Camera Glob", ext, camera_glob);
931 params.line_break();
932 params.set_modal(true);
933 if (!params.ask())
934 return;
935 }
936 if (video_path == "") {
937 bwm_utils::show_error("Please specify a video path");
938 return;
939 }
940
941 bwm_io_tab_config_video* video = new bwm_io_tab_config_video(name, true, video_path, camera_glob);
942 active_tableaus_.push_back(video);
943 bwm_tableau_img* t = tableau_factory_.create_tableau(video);
944 bwm_tableau_mgr::instance()->add_tableau(t, name);
945 }
946
load_cam_tableau()947 void bwm_site_mgr::load_cam_tableau()
948 {
949
950 std::string ext, name, img_file, cam_file, empty="";
951 //std::string ext, name, cam_file, empty="";
952 //static std::string img_file = "";
953 static int camera_type = 0;
954 std::vector<std::string> types;
955 types.push_back("generic");
956 types.push_back("rational");
957 types.push_back("projective");
958 types.push_back("perspective");
959 types.push_back("identity");
960 if(tk_name_ == "mfc"){
961 vgui_dialog_extensions params ("Camera Tableau");
962 params.field("Tableau Name", name);
963 params.line_break();
964 params.file("Image...", ext, img_file);
965 params.line_break();
966 params.choice("Camera Type",types, camera_type);
967 params.line_break();
968 params.file("Camera...", ext, cam_file);
969 params.line_break();
970 if (!params.ask())
971 return;
972 }else{
973 vgui_dialog params ("Camera Tableau");
974 params.field("Tableau Name", name);
975 params.line_break();
976 params.file("Image...", ext, img_file);
977 params.line_break();
978 params.choice("Camera Type",types, camera_type);
979 params.line_break();
980 params.file("Camera...", ext, cam_file);
981 params.line_break();
982 if (!params.ask())
983 return;
984 }
985 if ((img_file == "") || (cam_file == "" && camera_type != 4)) { // for identity camera type, cam_file can be empty ?
986 vgui_dialog error ("Error");
987 error.message ("Please specify an input file (prefix)." );
988 error.ask();
989 return;
990 }
991
992 std::string cam_str;
993 switch (camera_type)
994 {
995 case 0:
996 cam_str = "generic";
997 break;
998 case 1:
999 cam_str = "rational";
1000 break;
1001 case 2:
1002 cam_str = "projective";
1003 break;
1004 case 3:
1005 cam_str = "perspective";
1006 break;
1007 case 4:
1008 cam_str = "identity";
1009 break;
1010 case 5:
1011 cam_str = "geo";
1012 break;
1013 default:
1014 cam_str = "unknown";
1015 }
1016
1017 bwm_io_tab_config_cam* cam = new bwm_io_tab_config_cam(name, true, img_file, cam_file, cam_str);
1018 active_tableaus_.push_back(cam);
1019 bwm_tableau_img* t = tableau_factory_.create_tableau(cam);
1020 bwm_tableau_mgr::instance()->add_tableau(t, name);
1021 }
1022 // a tableau for specifying the image locations of 3-d fiducial data
load_fiducial_tableau()1023 void bwm_site_mgr::load_fiducial_tableau()
1024 {
1025 std::string ext, name, img_file, fid_file, empty="";
1026 if (tk_name_ == "mfc") {
1027 vgui_dialog_extensions params("Fiducial Tableau (fid xor img )");
1028 params.field("Tableau Name", name);
1029 params.line_break();
1030 params.file("Image...", ext, img_file);
1031 params.line_break();
1032 params.file("Fiducials...", ext, fid_file);
1033 params.line_break();
1034 if (!params.ask())
1035 return;
1036 }else {
1037 vgui_dialog params("Fiducial Tableau (fid xor img )");
1038 params.field("Tableau Name", name);
1039 params.line_break();
1040 params.file("Image...", ext, img_file);
1041 params.line_break();
1042 params.file("Fiducials...", ext, fid_file);
1043 params.line_break();
1044 if (!params.ask())
1045 return;
1046 }
1047 // the fid file contains the data to populate a fiducial tableau (like a site file)
1048 // initially just load a composite fiducial placement image and save the resulting
1049 // fiducial correspondences to a fid file path defined by the fiducial tableau popup
1050 // the state of the tableau is restored by loading the fid file
1051 if ((img_file == "" && fid_file == "")||(img_file != "" && fid_file != "")) {
1052 vgui_dialog error ("Error");
1053 error.message ("only one of img_file and fid file can be entered");
1054 error.ask();
1055 return;
1056 }
1057
1058 bwm_io_tab_config_fiducial* fid = new bwm_io_tab_config_fiducial(name, true, img_file, fid_file);
1059 active_tableaus_.push_back(fid);
1060 bwm_tableau_fiducial* t = dynamic_cast<bwm_tableau_fiducial*>(tableau_factory_.create_tableau(fid));
1061 if (!t) {
1062 std::cerr << "factory can't create the fiducial tableau" << std::endl;
1063 return;
1064 }
1065 bwm_tableau_mgr::instance()->add_tableau(t, name);
1066 }
1067
parse_config(std::string const & path)1068 bwm_io_config_parser* bwm_site_mgr::parse_config(std::string const& path)
1069 {
1070 std::string fname = path;
1071 if(fname == "")
1072 fname = bwm_utils::select_file();
1073
1074 if (fname.size() == 0)
1075 return nullptr;
1076
1077 bwm_io_config_parser* parser = new bwm_io_config_parser();
1078 std::FILE* xmlFile = std::fopen(fname.c_str(), "r");
1079 if (!xmlFile) {
1080 std::cerr << fname.c_str() << " error on opening\n";
1081 delete parser;
1082 return nullptr;
1083 }
1084 if (!parser->parseFile(xmlFile)) {
1085 std::cerr << XML_ErrorString(parser->XML_GetErrorCode()) << " at line "
1086 << parser->XML_GetCurrentLineNumber() << '\n';
1087
1088 delete parser;
1089 return nullptr;
1090 }
1091 std::cout << "finished!" << std::endl;
1092 return parser;
1093 }
site_parser(std::string const & path)1094 bwm_io_config_parser* bwm_site_mgr::site_parser(std::string const& path){
1095 return this->parse_config(path);
1096 }
1097
write_vrml_header(std::ofstream & str)1098 static void write_vrml_header(std::ofstream& str)
1099 {
1100 str << "#VRML V2.0 utf8\n"
1101 << "Background {\n"
1102 << " skyColor [ 0 0 0 ]\n"
1103 << " groundColor [ 0 0 0 ]\n"
1104 << "}\n";
1105 }
1106
write_vrml_points(std::ofstream & str,std::vector<vgl_point_3d<double>> const & pts3d,double rad=2.0)1107 static void write_vrml_points(std::ofstream& str,
1108 std::vector<vgl_point_3d<double> > const& pts3d, double rad=2.0)
1109 {
1110 int n = pts3d.size();
1111 for (int i =0; i<n; i++)
1112 str << "Transform {\n"
1113 << "translation " << pts3d[i].x() << ' ' << pts3d[i].y() << ' '
1114 << ' ' << pts3d[i].z() << '\n'
1115 << "children [\n"
1116 << "Shape {\n"
1117 << " appearance Appearance{\n"
1118 << " material Material\n"
1119 << " {\n"
1120 << " diffuseColor " << 0 << ' ' << 1.0 << ' ' << 0.0 << '\n'
1121 << " transparency " << 0.0 << '\n'
1122 << " }\n"
1123 << " }\n"
1124 << " geometry Sphere\n"
1125 << "{\n"
1126 << " radius " << rad << '\n'
1127 << " }\n"
1128 << " }\n"
1129 << " ]\n"
1130 << "}\n";
1131 }
1132
1133 static void
write_vrml_cameras(std::ofstream & str,std::vector<vpgl_perspective_camera<double>> const & cams,double rad=2.0)1134 write_vrml_cameras(std::ofstream& str,
1135 std::vector<vpgl_perspective_camera<double> > const& cams, double rad=2.0)
1136 {
1137 str << "#VRML V2.0 utf8\n"
1138 << "Background {\n"
1139 << " skyColor [ 0 0 0 ]\n"
1140 << " groundColor [ 0 0 0 ]\n"
1141 << "}\n";
1142 int n = cams.size();
1143 for (int i =0; i<n; i++) {
1144 vgl_point_3d<double> cent = cams[i].get_camera_center();
1145 str << "Transform {\n"
1146 << "translation " << cent.x() << ' ' << cent.y() << ' '
1147 << ' ' << cent.z() << '\n'
1148 << "children [\n"
1149 << "Shape {\n"
1150 << " appearance Appearance{\n"
1151 << " material Material\n"
1152 << " {\n"
1153 << " diffuseColor " << 1 << ' ' << 1.0 << ' ' << 0.0 << '\n'
1154 << " transparency " << 0.0 << '\n'
1155 << " }\n"
1156 << " }\n"
1157 << " geometry Sphere\n"
1158 << "{\n"
1159 << " radius " << rad << '\n'
1160 << " }\n"
1161 << " }\n"
1162 << " ]\n"
1163 << "}\n";
1164 vgl_vector_3d<double> r = cams[i].principal_axis();
1165 std::cout<<"principal axis :" <<r<<std::endl;
1166 vnl_double_3 yaxis(0.0, 1.0, 0.0), pvec(r.x(), r.y(), r.z());
1167 vgl_rotation_3d<double> rot(yaxis, pvec);
1168 vnl_quaternion<double> q = rot.as_quaternion();
1169
1170 vnl_double_3 axis = q.axis();
1171 std::cout<<"quaternion "<<axis<< " angle "<<q.angle()<<"\n\n";
1172 double ang = q.angle();
1173 str << "Transform {\n"
1174 << " translation " << cent.x()+6*rad*r.x() << ' ' << cent.y()+6*rad*r.y()
1175 << ' ' << cent.z()+6*rad*r.z() << '\n'
1176 << " rotation " << axis[0] << ' ' << axis[1] << ' ' << axis[2] << ' ' << ang << '\n'
1177 << "children [\n"
1178 << " Shape {\n"
1179 << " appearance Appearance{\n"
1180 << " material Material\n"
1181 << " {\n"
1182 << " diffuseColor 1 0 0\n"
1183 << " transparency 0\n"
1184 << " }\n"
1185 << " }\n"
1186 << " geometry Cylinder\n"
1187 << "{\n"
1188 << " radius "<<rad/3<<'\n'
1189 << " height " << 12*rad << '\n'
1190 << " }\n"
1191 << " }\n"
1192 << "]\n"
1193 << "}\n";
1194 }
1195 }
1196
1197 #ifdef DEBUG
1198 static void
write_vrml_box(std::ofstream & str,vgl_box_3d<double> box)1199 write_vrml_box(std::ofstream& str,vgl_box_3d<double> box)
1200 {
1201 str << "#VRML V2.0 utf8\n"
1202 << "Background {\n"
1203 << " skyColor [ 0 0 0 ]\n"
1204 << " groundColor [ 0 0 0 ]\n"
1205 << "}\n"
1206 << "Transform {\n"
1207 << "translation " << box.centroid_x() << ' ' << box.centroid_y() << ' '
1208 << ' ' << box.centroid_z() << '\n'
1209 << "children [\n"
1210 << "Shape {\n"
1211 << " appearance Appearance{\n"
1212 << " material Material\n"
1213 << " {\n"
1214 << " diffuseColor " << 1 << ' ' << 1.0 << ' ' << 0.0 << '\n'
1215 << " transparency " << 0.0 << '\n'
1216 //<< "\t\tfilled FALSE\n"
1217 << " }\n"
1218 << " }\n"
1219 << " geometry Box\n"
1220 << "{\n"
1221 << " size " << box.width() <<' '<<box.depth()<<' '<<box.height()<< '\n'
1222 << " }\n"
1223 << " }\n"
1224 << " ]\n"
1225 << "}\n";
1226 }
1227 #endif
1228
save_video_world_points_vrml_impl(std::ofstream & os)1229 static void save_video_world_points_vrml_impl(std::ofstream& os)
1230 {
1231 bool found = false;
1232 std::vector<bwm_observer_cam*> obsvs =
1233 bwm_observer_mgr::instance()->observers_cam();
1234 bwm_observer_video* obv = nullptr;
1235
1236 for (std::vector<bwm_observer_cam*>::iterator oit = obsvs.begin();
1237 oit != obsvs.end()&&!found; ++oit)
1238 if ((*oit)->type_name()=="bwm_observer_video")
1239 {
1240 obv = static_cast<bwm_observer_video*>(*oit);
1241 found =true;
1242 }
1243
1244 if (!found)
1245 {
1246 std::cerr << "In bwm_site_mgr::save_video_world_points_vrml() - no observer of type video\n";
1247 return;
1248 }
1249 std::vector<vgl_point_3d<double> > pts;
1250 std::vector<bwm_video_corr_sptr> corrs = obv->corrs();
1251 for (std::vector<bwm_video_corr_sptr>::iterator cit = corrs.begin();
1252 cit!= corrs.end(); ++cit)
1253 {
1254 bwm_video_corr_sptr corr = *cit;
1255 if (!corr || !corr->world_pt_valid()) continue;
1256 vgl_point_3d<double> pt = corr->world_pt();
1257 pts.push_back(pt);
1258 }
1259 if (!pts.size())
1260 return;
1261 write_vrml_header(os);
1262 write_vrml_points(os, pts);
1263 }
1264
save_video_world_points_vrml_impl(std::ofstream & os,vgl_box_3d<double> & box,double res)1265 static void save_video_world_points_vrml_impl(std::ofstream& os, vgl_box_3d<double> & box, double res)
1266 {
1267 bool found = false;
1268 std::vector<bwm_observer_cam*> obsvs =
1269 bwm_observer_mgr::instance()->observers_cam();
1270 bwm_observer_video* obv = nullptr;
1271
1272 for (std::vector<bwm_observer_cam*>::iterator oit = obsvs.begin();
1273 oit != obsvs.end()&&!found; ++oit)
1274 if ((*oit)->type_name()=="bwm_observer_video")
1275 {
1276 obv = static_cast<bwm_observer_video*>(*oit);
1277 found =true;
1278 }
1279
1280 if (!found)
1281 {
1282 std::cerr << "In bwm_site_mgr::save_video_world_points_vrml() - no observer of type video\n";
1283 return;
1284 }
1285 std::vector<vgl_point_3d<double> > pts;
1286 std::vector<bwm_video_corr_sptr> corrs = obv->corrs();
1287 int cnt=0;
1288 for (std::vector<bwm_video_corr_sptr>::iterator cit = corrs.begin();
1289 cit!= corrs.end(); ++cit)
1290 {
1291 if ((++cnt)%10==0)
1292 {
1293 bwm_video_corr_sptr corr = *cit;
1294 if (!corr || !corr->world_pt_valid()) continue;
1295 vgl_point_3d<double> pt = corr->world_pt();
1296 if (box.contains(pt))
1297 pts.push_back(pt);
1298 }
1299 }
1300 if (!pts.size())
1301 return;
1302 write_vrml_header(os);
1303 write_vrml_points(os, pts,res);
1304 }
1305
save_video_world_points_vrml()1306 void bwm_site_mgr::save_video_world_points_vrml()
1307 {
1308 std::string ext = ".wrl";
1309 std::string path;
1310 vgui_dialog vrml_dialog("Write World Points");
1311 vrml_dialog.file("VRML file", ext, path);
1312 if (!vrml_dialog.ask())
1313 return;
1314 std::ofstream os(path.c_str());
1315 save_video_world_points_vrml_impl(os);
1316 }
1317
save_video_cameras_vrml_impl(std::ofstream & os)1318 static void save_video_cameras_vrml_impl(std::ofstream& os)
1319 {
1320 bool found = false;
1321 std::vector<bwm_observer_cam*> obsvs =
1322 bwm_observer_mgr::instance()->observers_cam();
1323 bwm_observer_video* obv = nullptr;
1324
1325 for (std::vector<bwm_observer_cam*>::iterator oit = obsvs.begin();
1326 oit != obsvs.end()&&!found; ++oit)
1327 if ((*oit)->type_name()=="bwm_observer_video")
1328 {
1329 obv = static_cast<bwm_observer_video*>(*oit);
1330 found =true;
1331 }
1332
1333 if (!found)
1334 {
1335 std::cerr << "In bwm_site_mgr::save_video_cameras_vrml() - no observer of type video\n";
1336 return;
1337 }
1338 bwm_video_cam_istream_sptr cam_istr = obv->camera_stream();
1339 if (!cam_istr||!cam_istr->is_valid()||!cam_istr->is_seekable()) {
1340 std::cerr << "Invalid or non-seekable camera stream\n";
1341 return;
1342 }
1343 //to return to starting state
1344 unsigned cam_number = cam_istr->camera_number();
1345 cam_istr->seek_camera(0);
1346 std::vector<vpgl_perspective_camera<double> > cams;
1347 while (true) {
1348 vpgl_perspective_camera<double>* cam = cam_istr->current_camera();
1349 cams.push_back(*cam);
1350 if (!cam_istr->advance())
1351 break;
1352 }
1353 //restore the camera stream to initial position
1354 cam_istr->seek_camera(cam_number);
1355 if (!cams.size())
1356 return;
1357 write_vrml_cameras(os, cams);
1358 }
1359
save_video_cameras_vrml_impl(std::ofstream & os,vgl_box_3d<double> box,double res)1360 static void save_video_cameras_vrml_impl(std::ofstream& os, vgl_box_3d<double> box, double res)
1361 {
1362 bool found = false;
1363 std::vector<bwm_observer_cam*> obsvs =
1364 bwm_observer_mgr::instance()->observers_cam();
1365 bwm_observer_video* obv = nullptr;
1366
1367 for (std::vector<bwm_observer_cam*>::iterator oit = obsvs.begin();
1368 oit != obsvs.end()&&!found; ++oit)
1369 if ((*oit)->type_name()=="bwm_observer_video")
1370 {
1371 obv = static_cast<bwm_observer_video*>(*oit);
1372 found =true;
1373 }
1374
1375 if (!found)
1376 {
1377 std::cerr << "In bwm_site_mgr::save_video_cameras_vrml() - no observer of type video\n";
1378 return;
1379 }
1380 bwm_video_cam_istream_sptr cam_istr = obv->camera_stream();
1381 if (!cam_istr||!cam_istr->is_valid()||!cam_istr->is_seekable()) {
1382 std::cerr << "Invalid or non-seekable camera stream\n";
1383 return;
1384 }
1385 //to return to starting state
1386 unsigned cam_number = cam_istr->camera_number();
1387 cam_istr->seek_camera(0);
1388 std::vector<vpgl_perspective_camera<double> > cams;
1389 int cnt=0;
1390 while (true) {
1391 vpgl_perspective_camera<double>* cam = cam_istr->current_camera();
1392 std::cout<<cam->get_camera_center();
1393 if (cnt++>170 )
1394 if (box.contains(cam->get_camera_center()))
1395 cams.push_back(*cam);
1396
1397 if (!cam_istr->advance())
1398 break;
1399 }
1400 //restore the camera stream to initial position
1401 cam_istr->seek_camera(cam_number);
1402 if (!cams.size())
1403 return;
1404 write_vrml_cameras(os, cams, res);
1405 }
1406
save_video_cameras_vrml()1407 void bwm_site_mgr::save_video_cameras_vrml()
1408 {
1409 std::string ext = ".wrl";
1410 std::string path;
1411 vgui_dialog vrml_dialog("Write World Points");
1412 vrml_dialog.file("VRML file", ext, path);
1413 if (!vrml_dialog.ask())
1414 return;
1415 std::ofstream os(path.c_str());
1416 write_vrml_header(os);
1417 save_video_cameras_vrml_impl(os);
1418 }
1419
save_video_cams_and_world_pts_vrml()1420 void bwm_site_mgr::save_video_cams_and_world_pts_vrml()
1421 {
1422 std::string ext = ".wrl";
1423 std::string path;
1424 vgui_dialog vrml_dialog("Write World Points");
1425 vrml_dialog.file("VRML file", ext, path);
1426 vrml_dialog.checkbox("Default Params for saving ", defaultparam_);
1427 vrml_dialog.field("X min:", xmin_);
1428 vrml_dialog.field("X max:", xmax_);
1429 vrml_dialog.field("Y min:", ymin_);
1430 vrml_dialog.field("Y max:", ymax_);
1431 vrml_dialog.field("Z min:", zmin_);
1432 vrml_dialog.field("Z max:", zmax_);
1433 vrml_dialog.field("Resolution", res_);
1434
1435 if (!vrml_dialog.ask())
1436 return;
1437 vgl_box_3d<double> box(xmin_,ymin_,zmin_,xmax_,ymax_,zmax_);
1438 std::ofstream os(path.c_str());
1439 write_vrml_header(os);
1440 if (defaultparam_)
1441 {
1442 save_video_world_points_vrml_impl(os);
1443 save_video_cameras_vrml_impl(os);
1444 }
1445 else
1446 {
1447 save_video_world_points_vrml_impl(os,box,res_);
1448 save_video_cameras_vrml_impl(os,box,res_*5);
1449 #ifdef DEBUG
1450 write_vrml_box(os, box);
1451 #endif
1452 }
1453 }
1454
1455 //: compute 3-d parameters, site bounding box and GSD
compute_3d_world_params()1456 void bwm_site_mgr::compute_3d_world_params()
1457 {
1458 std::string path = "";
1459 std::string ext = "*.txt";
1460 vgui_dialog par_dlg("World Params");
1461 par_dlg.file("Param File", ext, path);
1462 if (!par_dlg.ask())
1463 return;
1464 vgl_box_3d<double> bb;
1465 double gsd = 0;
1466
1467 bool found = false;
1468 std::vector<bwm_observer_cam*> obsvs =
1469 bwm_observer_mgr::instance()->observers_cam();
1470 bwm_observer_video* obv = nullptr;
1471
1472 for (std::vector<bwm_observer_cam*>::iterator oit = obsvs.begin();
1473 oit != obsvs.end()&&!found; ++oit)
1474 if ((*oit)->type_name()=="bwm_observer_video")
1475 {
1476 obv = static_cast<bwm_observer_video*>(*oit);
1477 found =true;
1478 }
1479
1480 if (!found)
1481 {
1482 std::cerr << "In bwm_site_mgr::compute_world_params() - no observer of type video\n";
1483 return;
1484 }
1485 std::vector<bwm_video_corr_sptr> corrs = obv->corrs();
1486 if (!corrs.size()) {
1487 std::cerr << "In bwm_site_mgr::compute_world_params() - no correspondences\n";
1488 return;
1489 }
1490 bwm_video_cam_istream_sptr cam_istr = obv->camera_stream();
1491 if (!cam_istr || !cam_istr->is_valid() || !cam_istr->is_seekable()) {
1492 std::cerr << "In bwm_site_mgr::compute_world_params() - no correspondences\n";
1493 return;
1494 }
1495 //Add world points to bounding box
1496 std::vector<bwm_video_corr_sptr>::iterator cit = corrs.begin();
1497 for (; cit != corrs.end(); ++cit)
1498 {
1499 bwm_video_corr_sptr c = *cit;
1500 if (!c) continue;
1501 if (c->world_pt_valid())
1502 bb.add(c->world_pt());
1503 }
1504 //to restore cam stream state
1505 unsigned cam_number = cam_istr->camera_number();
1506 cam_istr->seek_camera(0);
1507 vpgl_perspective_camera<double>* cam = cam_istr->current_camera();
1508 //project the bounding box
1509 vgl_box_2d<double> bb_2d = bpgl_project::project_bounding_box(*cam, bb);
1510 //get the number of pixels on the diagonal
1511 double w = bb_2d.width(), h = bb_2d.height();
1512 double diag2 = std::sqrt(w*w + h*h);
1513 //get the length of the 3-d bb diagonal
1514 double w3 = bb.width(), h3 = bb.height(), d3 = bb.depth();
1515 double diag3 = std::sqrt(w3*w3 + h3*h3 + d3*d3);
1516 gsd = diag3/diag2;
1517 std::ofstream os(path.c_str());
1518 if (!os.is_open()) {
1519 std::cerr << "In bwm_site_mgr::compute_world_params() - invalid parameter output path\n";
1520 return;
1521 }
1522 os << "World Bounding Box\n"
1523 << bb << '\n'
1524 << "Ground Sample Distance(GSD): " << gsd << '\n'
1525 << "Bounding box size in GSD units\n"
1526 << "Xsize:" << static_cast<unsigned>(bb.width()/gsd)
1527 << " Ysize:" << static_cast<unsigned>(bb.height()/gsd)
1528 << " Zsize:" << static_cast<unsigned>(bb.depth()/gsd) << '\n';
1529 os.close();
1530 //restore camera stream state
1531 cam_istr->seek_camera(cam_number);
1532 }
1533
load_depth_map_scene()1534 void bwm_site_mgr::load_depth_map_scene()
1535 {
1536 std::string path = bwm_utils::select_file();
1537 std::string dir = vul_file::dirname(path);
1538 depth_map_scene scene;
1539 vsl_b_ifstream is(path.c_str());
1540 if (!is) {
1541 std::cout << "invalid binary stream for path " << path << std::endl;
1542 return;
1543 }
1544 scene.b_read(is);
1545 std::string name = "depth_map";
1546 std::string ifile = scene.image_path();
1547 std::string ipath;
1548 if (!vul_file::exists(ifile)) {
1549 // loaded depth_map_scene doesn't have image path, use the jpg having same name instead
1550 std::cerr << "\n WARNING: loaded depth_map_scene does not have image path" << std::endl;
1551 std::string temp = vul_file::strip_extension(vul_file::strip_directory(path.c_str())) + ".jpg";
1552 scene.set_image_path(temp);
1553 ipath = dir + '/' + temp;
1554 }
1555 else
1556 ipath = ifile;
1557 bwm_io_tab_config* tab = new bwm_io_tab_config_cam(name, true, ipath , "not_needed" , "perspective");
1558 active_tableaus_.push_back(tab);
1559 bwm_tableau_img* t = tableau_factory_.create_tableau(tab);
1560 bwm_tableau_mgr::instance()->add_tableau(t, name);
1561 bwm_tableau_cam* tc = reinterpret_cast<bwm_tableau_cam*>(t);
1562 vpgl_camera<double>* cam = new vpgl_perspective_camera<double>(scene.cam());
1563 tc->observer()->set_camera(cam, "");
1564 tc->observer()->set_depth_map_scene(scene);
1565 tc->observer()->display_depth_map_scene();
1566 }
1567
save_depth_map_scene()1568 void bwm_site_mgr::save_depth_map_scene()
1569 {
1570 std::cerr << "bwm_site_mgr::save_depth_map_scene() not yet implemented!!!\n";
1571 }
1572