00001
00002 #include "sdet_edgel_regions.h"
00003
00004
00005
00006 #include <vcl_iostream.h>
00007 #include <vcl_algorithm.h>
00008 #include <vbl/vbl_qsort.h>
00009
00010 #include <vxl_config.h>
00011 #include <vil1/vil1_memory_image_of.h>
00012 #include <vul/vul_timer.h>
00013
00014 #include <vsol/vsol_box_2d.h>
00015 #include <vtol/vtol_edge.h>
00016 #include <vtol/vtol_edge_2d.h>
00017 #include <vtol/vtol_one_chain.h>
00018 #include <vtol/vtol_cycle_processor.h>
00019
00020 #include <vdgl/vdgl_edgel_chain.h>
00021 #include <vdgl/vdgl_interpolator.h>
00022 #include <vdgl/vdgl_digital_curve.h>
00023 #include <vtol/vtol_intensity_face.h>
00024
00025 #include <bdgl/bdgl_curve_algs.h>
00026 #include <btol/btol_edge_algs.h>
00027 #include <sdet/sdet_region_edge.h>
00028
00029 #define bytePixel(buf,x,y) (*((unsigned char*)buf->GetElementAddr(x,y)))
00030 #define shortPixel(buf,x,y) (*((short*)buf->GetElementAddr(x,y)))
00031
00032 #if 0 // not ported to vxl
00033
00034
00035 void edgel_regions::cache_bad_edges(CoolArrayP<Edge*>& bad_edges)
00036 {
00037 vcl_vector<Edge*> corrupt_edges;
00038 for (CoolArrayP<Edge*>::iterator eit = bad_edges.begin();
00039 eit != bad_edges.end(); eit++)
00040 corrupt_edges.push_back(*eit);
00041 corrupt_edges_.push_back(corrupt_edges);
00042 }
00043
00044 void edgel_regions::cache_bad_edges(vcl_vector<Edge*>& bad_edges)
00045 {
00046 vcl_vector<Edge*> corrupt_edges;
00047 for (vcl_vector<Edge*>::iterator eit = bad_edges.begin();
00048 eit != bad_edges.end(); eit++)
00049 corrupt_edges.push_back(*eit);
00050 corrupt_edges_.push_back(corrupt_edges);
00051 }
00052
00053 void edgel_regions::cache_bad_verts(CoolArrayP<Vertex*>& bad_verts)
00054 {
00055 vcl_vector<Vertex*> corrupt_verts;
00056 for (CoolArrayP<Vertex*>::iterator vit = bad_verts.begin();
00057 vit != bad_verts.end(); vit++)
00058 corrupt_verts.push_back(*vit);
00059 corrupt_vertices_.push_back(corrupt_verts);
00060 }
00061 #endif
00062
00063
00064 void sdet_edgel_regions::print_region_array()
00065 {
00066 vcl_cout << vcl_endl << vcl_endl;
00067 for (unsigned int y = 0; y<ys_; y++)
00068 {
00069 for (unsigned int x = 0; x<xs_; x++)
00070 if (region_label_array_[y][x]==EDGE
00071
00072 )
00073 vcl_cout << '*';
00074 else
00075 vcl_cout << region_label_array_[y][x] << ' ';
00076 vcl_cout << vcl_endl;
00077 }
00078 vcl_cout << vcl_endl << vcl_endl;
00079 }
00080
00081
00082 void sdet_edgel_regions::print_region_equivalence()
00083 {
00084 vcl_cout << "\nLabel Equivalence:\n"
00085 << "------------------\n";
00086 vcl_map<unsigned int, vcl_vector<unsigned int>*>::iterator rpf_iterator;
00087 for (rpf_iterator= region_pairs_forward_.begin();
00088 rpf_iterator!=region_pairs_forward_.end(); rpf_iterator++)
00089 {
00090 vcl_cout << (*rpf_iterator).first << " == ";
00091 vcl_vector<unsigned int>* labels = (*rpf_iterator).second;
00092 if (labels)
00093 {
00094 for (vcl_vector<unsigned int>::iterator lit = labels->begin();
00095 lit != labels->end(); lit++)
00096 vcl_cout << *lit << ' ';
00097 vcl_cout << vcl_endl;
00098 }
00099 }
00100 vcl_cout << vcl_endl;
00101 }
00102
00103
00104 void sdet_edgel_regions::print_reverse_region_equivalence()
00105 {
00106 vcl_cout << "\nReverse Label Equivalence:\n"
00107 << "--------------------------\n";
00108 vcl_map<unsigned int, vcl_vector<unsigned int>*>::iterator rpf_iterator;
00109 for (rpf_iterator= region_pairs_reverse_.begin();
00110 rpf_iterator!=region_pairs_reverse_.end(); rpf_iterator++)
00111 {
00112 vcl_cout << (*rpf_iterator).first << " == ";
00113 vcl_vector<unsigned int>* labels = (*rpf_iterator).second;
00114 if (labels)
00115 {
00116 for (vcl_vector<unsigned int>::iterator lit = labels->begin();
00117 lit != labels->end(); lit++)
00118 vcl_cout << *lit << ' ';
00119 vcl_cout << vcl_endl;
00120 }
00121 }
00122 vcl_cout << vcl_endl;
00123 }
00124
00125
00126 void sdet_edgel_regions::print_base_equivalence()
00127 {
00128 vcl_cout << "\nBase Label Equivalence:\n"
00129 << "-----------------------\n";
00130
00131 for (unsigned int i = min_region_label_; i<max_region_label_; i++)
00132 vcl_cout << i << " == " << this->BaseLabel(i) << vcl_endl;
00133 }
00134
00135
00136 void sdet_edgel_regions::print_intensity_data()
00137 {
00138 for (vcl_vector<vtol_intensity_face_sptr>::iterator fit =faces_->begin();
00139 fit != faces_->end(); fit++)
00140 {
00141 vtol_intensity_face_sptr const & f = *fit;
00142 vcl_cout << "IntFaceAt(" << f->Xo() << ' ' << f->Yo() << "):\n";
00143
00144 }
00145 }
00146
00147
00148
00149
00150
00151 unsigned int sdet_edgel_regions::X(unsigned int x)
00152 {
00153 return x-xo_;
00154 }
00155
00156
00157
00158
00159 unsigned int sdet_edgel_regions::Y(unsigned int y)
00160 {
00161 return y-yo_;
00162 }
00163
00164
00165
00166 float sdet_edgel_regions::Xf(float x)
00167 {
00168 float xu = (x-xo_)*s_;
00169 return xu;
00170 }
00171
00172
00173
00174 float sdet_edgel_regions::Yf(float y)
00175 {
00176 float yu = (y-yo_)*s_;
00177 return yu;
00178 }
00179
00180
00181
00182 sdet_edgel_regions::sdet_edgel_regions(int array_scale,bool verbose,
00183 bool debug)
00184 {
00185 debug_ = debug;
00186 verbose_ = verbose;
00187 s_ = array_scale;
00188 #ifdef DEBUG
00189 debug_data_ = debug_ ? new topo_debug_data : 0;
00190 #endif
00191 image_source_ = false;
00192 buf_source_ = false;
00193 buf_ = NULL;
00194 xo_=0;
00195 yo_=0;
00196 xend_ = 0;
00197 yend_ = 0;
00198 xs_ = 0;
00199 ys_ = 0;
00200 min_region_label_ = LABEL;
00201 max_region_label_ = LABEL;
00202 faces_ = new vcl_vector<vtol_intensity_face_sptr>;
00203 face_edge_index_ = NULL;
00204 intensity_face_index_ = NULL;
00205 failed_insertions_ = new vcl_vector<vtol_edge_2d_sptr>;
00206 ubuf_ = NULL;
00207 sbuf_ = NULL;
00208 }
00209
00210
00211
00212 sdet_edgel_regions::~sdet_edgel_regions()
00213 {
00214 if (face_edge_index_)
00215 {
00216 for (unsigned int i = 0; i<max_region_label_; i++)
00217 delete face_edge_index_[i];
00218 delete [] face_edge_index_;
00219 }
00220 delete failed_insertions_;
00221 delete [] ubuf_;
00222 delete [] sbuf_;
00223
00224 delete faces_;
00225 delete [] intensity_face_index_;
00226
00227 for (vcl_map<unsigned int, vcl_vector<vtol_edge_2d_sptr>* >::iterator
00228 mit = region_edge_adjacency_.begin();
00229 mit != region_edge_adjacency_.end(); mit++)
00230 {
00231 if ((*mit).second)
00232 (*mit).second->clear();
00233 delete (*mit).second;
00234 }
00235
00236 for (vcl_map<unsigned int, vcl_vector<unsigned int>* >::iterator
00237 mit = equivalence_set_.begin(); mit != equivalence_set_.end(); mit++)
00238 delete (*mit).second;
00239
00240 for (vcl_map<unsigned int, vcl_vector<unsigned int>* >::iterator
00241 mit = region_pairs_reverse_.begin();
00242 mit != region_pairs_reverse_.end(); mit++)
00243 delete (*mit).second;
00244
00245 for (vcl_map<unsigned int, vcl_vector<unsigned int>* >::iterator
00246 mit = region_pairs_forward_.begin();
00247 mit != region_pairs_forward_.end(); mit++)
00248 delete (*mit).second;
00249 }
00250
00251 bool sdet_edgel_regions::compute_edgel_regions(gevd_bufferxy* buf,
00252 vcl_vector<vtol_edge_2d_sptr>& sgrp,
00253 vcl_vector<vtol_intensity_face_sptr>& faces)
00254 {
00255 buf_ = buf;
00256 buf_source_=true;
00257 image_source_=false;
00258 return compute_edgel_regions(sgrp, faces);
00259 }
00260
00261
00262
00263
00264
00265
00266
00267
00268
00269 bool sdet_edgel_regions::
00270 compute_edgel_regions(vil1_image const& image,
00271 vcl_vector<vtol_edge_2d_sptr>& sgrp,
00272 vcl_vector<vtol_intensity_face_sptr>& faces)
00273 {
00274 #if 0
00275 image_ = image;
00276 buf_ = NULL;
00277 image_source_=true;
00278 buf_source_ = false;
00279 #endif
00280
00281
00282 image_ = 0;
00283 image_source_=false;
00284 buf_source_ = false;
00285 buf_ = new gevd_bufferxy(image);
00286 if(buf_)
00287 buf_source_ = true;
00288 else
00289 return false;
00290 return compute_edgel_regions(sgrp, faces);
00291 }
00292 bool sdet_edgel_regions::
00293 compute_edgel_regions(vil_image_resource_sptr const& image,
00294 vcl_vector<vtol_edge_2d_sptr>& sgrp,
00295 vcl_vector<vtol_intensity_face_sptr>& faces)
00296 {
00297 #if 0
00298 image_ = image;
00299 buf_ = NULL;
00300 image_source_=true;
00301 buf_source_ = false;
00302 #endif
00303
00304
00305 image_ = 0;
00306 image_source_=false;
00307 buf_source_ = false;
00308 buf_ = new gevd_bufferxy(image);
00309 if(buf_)
00310 buf_source_ = true;
00311 else
00312 return false;
00313 return compute_edgel_regions(sgrp, faces);
00314 }
00315
00316 bool sdet_edgel_regions::
00317 compute_edgel_regions(vcl_vector<vtol_edge_2d_sptr>& sgrp,
00318 vcl_vector<vtol_intensity_face_sptr>& faces)
00319 {
00320 #ifdef DEBUG
00321 if (debug_data_)
00322 {
00323 debug_data_->clear();
00324 if (buf_source_)
00325 debug_data_->set_buf(buf_);
00326 }
00327 #endif
00328 vul_timer t;
00329 if (!sgrp.size())
00330 return false;
00331
00332
00333 this->InitRegionArray(sgrp);
00334 if (debug_)
00335 this->print_region_array();
00336
00337 unsigned int y, x;
00338
00339
00340 for (y=0; y<ys_-1; y++)
00341 for (x=0; x<xs_-1; x++)
00342 this->UpdateConnectedNeighborhood(x,y);
00343
00344 if (debug_)
00345 this->print_region_array();
00346
00347 if (debug_)
00348 {
00349 this->print_region_equivalence();
00350 this->print_reverse_region_equivalence();
00351 }
00352 this->GrowEquivalenceClasses();
00353 this->PropagateEquivalence();
00354 if (debug_)
00355 this->print_base_equivalence();
00356 this->ApplyRegionEquivalence();
00357 if (debug_)
00358 vcl_cout << "After Label Equivalence\n";
00359 if (debug_)
00360 this->print_region_array();
00361
00362
00363 for (y=0; y<ys_-1; y++)
00364 for (x=0; x<xs_-1; x++)
00365 this->AssignEdgeLabels(x, y);
00366
00367
00368 this->CollectEdges();
00369 if (verbose_)
00370 vcl_cout << "Propagate Regions and Collect Edges("
00371 << max_region_label_-min_region_label_ << ") in "
00372 << t.real() << " msecs.\n"<< vcl_flush;
00373
00374
00375 this->CollectFaceEdges();
00376
00377
00378 this->ConstructFaces();
00379 if (!faces_||!faces_->size())
00380 return false;
00381
00382
00383 this->InsertFaceData();
00384
00385 if (debug_)
00386 this->print_intensity_data();
00387
00388 faces.clear();
00389 for (vcl_vector<vtol_intensity_face_sptr>::iterator fit = faces_->begin();
00390 fit != faces_->end(); fit++)
00391 faces.push_back(*fit);
00392
00393 if (verbose_)
00394 vcl_cout << "Compute Edgel Regions Total(" << faces_->size() << ") in "
00395 << t.real() << " msecs.\n"<< vcl_flush;
00396 return true;
00397 }
00398
00399
00400
00401
00402
00403 bool sdet_edgel_regions::InsertRegionEquivalence(unsigned int label_b,
00404 unsigned int label_a)
00405 {
00406 bool result = true;
00407 result = result && this->add_to_forward(label_b, label_a);
00408 result = result && this->add_to_reverse(label_a, label_b);
00409 return result;
00410 }
00411
00412
00413
00414
00415
00416 unsigned int sdet_edgel_regions::BaseLabel(unsigned int label)
00417 {
00418 vcl_map<unsigned int, unsigned int >::iterator lmtest;
00419 lmtest = label_map_.find(label);
00420 if ( lmtest != label_map_.end() )
00421 return lmtest->second;
00422 else
00423 return 0;
00424 }
00425
00426
00427
00428
00429
00430
00431 vil1_image sdet_edgel_regions::GetEdgeImage(vcl_vector<vtol_edge_2d_sptr>& sg)
00432 {
00433 if (!this->InitRegionArray(sg)) return NULL;
00434 unsigned char no_edge = 0, edge = 255;
00435
00436 vil1_memory_image_of<vxl_byte> image(xs_,ys_);
00437
00438 for (unsigned int y = 0; y<ys_; y++)
00439 for (unsigned int x = 0; x<xs_; x++)
00440 if (region_label_array_[y][x] == EDGE)
00441 image[y][x] = edge;
00442 else
00443 image[y][x] = no_edge;
00444 return image;
00445 }
00446
00447
00448
00449 void sdet_edgel_regions::PropagateEquivalence()
00450 {
00451 vcl_map<unsigned int, vcl_vector<unsigned int>* >::iterator esi;
00452
00453 for (esi = equivalence_set_.begin(); esi != equivalence_set_.end(); esi++)
00454 {
00455 unsigned int base = esi->first;
00456 vcl_vector<unsigned int>* labels = esi->second;
00457 if (!labels) continue;
00458 int len = labels->size();
00459 if (!len) continue;
00460 for (int i = 0; i<len; i++)
00461 label_map_[(*labels)[i]] = base;
00462 }
00463 for (unsigned int i = min_region_label_; i<max_region_label_; i++)
00464 if (label_map_.find(i) == label_map_.end())
00465 label_map_[i] = i;
00466 }
00467
00468
00469
00470
00471
00472 bool sdet_edgel_regions::
00473 merge_equivalence(vcl_map<unsigned int, vcl_vector<unsigned int>* >& tab,
00474 unsigned int cur_label,
00475 unsigned int label)
00476 {
00477 vcl_map<unsigned int, vcl_vector<unsigned int>* >::iterator hashi;
00478
00479 hashi = tab.find(label);
00480 if (hashi == tab.end()) {
00481 return false;
00482 }
00483
00484 vcl_vector<unsigned int>* labels = hashi->second;
00485
00486
00487 int len = labels->size();
00488 if (!len) {
00489 return false;
00490 }
00491
00492
00493 vcl_vector<unsigned int>* array;
00494
00495 hashi = equivalence_set_.find(cur_label);
00496 if ( hashi == equivalence_set_.end())
00497 {
00498
00499
00500 array = new vcl_vector<unsigned int>;
00501 equivalence_set_[cur_label] = array;
00502 }
00503 else
00504 {
00505
00506 array = hashi->second;
00507 }
00508
00509
00510 for (int i = 0; i<len; i++)
00511 {
00512 unsigned int l = (*labels)[i];
00513 bool found = false;
00514
00515 for (unsigned int j=0 ; j < array->size() ; j++)
00516 {
00517 if ((*array)[j] == l) found = true;
00518 }
00519
00520 if (!found)
00521 {
00522 array->push_back(l);
00523 }
00524 }
00525
00526 return true;
00527 }
00528
00529
00530
00531
00532
00533 bool sdet_edgel_regions::get_next_label(vcl_vector<unsigned int>* labels,
00534 unsigned int& label)
00535 {
00536
00537
00538 unsigned int tmp = label+1;
00539 if (!labels)
00540 if (tmp<max_region_label_)
00541 {
00542 label = tmp;
00543 return true;
00544 }
00545
00546
00547
00548
00549 for (unsigned int i = tmp; i<max_region_label_; i++)
00550 {
00551
00552 if (vcl_find(labels->begin(), labels->end(), i) == labels->end())
00553 {
00554 label = i;
00555 return true;
00556 }
00557 }
00558 return false;
00559 }
00560
00561
00562
00563
00564
00565
00566
00567
00568
00569
00570
00571
00572
00573
00574
00575 void sdet_edgel_regions::GrowEquivalenceClasses()
00576 {
00577 if ((max_region_label_-min_region_label_) < 2)
00578 return;
00579
00580 unsigned int cur_label = min_region_label_;
00581
00582 vcl_map<unsigned int, vcl_vector<unsigned int>* >::iterator mei;
00583 while (true)
00584 {
00585 bool merging = true;
00586 vcl_vector<unsigned int>* cur_set = NULL;
00587 unsigned int i = cur_label;
00588 int len = 0;
00589 int old_len;
00590 while (merging)
00591 {
00592 old_len = len;
00593 merging = false;
00594
00595
00596 bool find_forward =
00597 this->merge_equivalence(region_pairs_forward_, cur_label, i);
00598 if (find_forward)
00599 {
00600 delete region_pairs_forward_[i];
00601 region_pairs_forward_.erase(i);
00602 }
00603
00604 bool find_reverse =
00605 this->merge_equivalence(region_pairs_reverse_, cur_label, i);
00606 if (find_reverse)
00607 {
00608 delete region_pairs_reverse_[i];
00609 region_pairs_reverse_.erase(i);
00610 }
00611
00612
00613
00614 mei = equivalence_set_.find(cur_label);
00615 if (mei == equivalence_set_.end()) continue;
00616
00617
00618
00619
00620
00621
00622 cur_set = equivalence_set_[cur_label];
00623 if (!cur_set) continue;
00624 len = cur_set->size();
00625 if (!len) continue;
00626
00627
00628
00629
00630 if (len > old_len)
00631 {
00632 i = cur_label;
00633 vbl_qsort_ascending(*cur_set);
00634 }
00635
00636
00637
00638 for (int j = 0; j<len&&!merging; j++)
00639 if ((*cur_set)[j]>i)
00640 {
00641 i = (*cur_set)[j];
00642 merging = true;
00643 }
00644
00645
00646 }
00647
00648
00649 if (!get_next_label(cur_set, cur_label)) return;
00650 }
00651 }
00652
00653
00654
00655 bool sdet_edgel_regions::GroupContainsEdges(vcl_vector<vtol_edge_2d_sptr>& )
00656 {
00657 #if 0
00658 CoolString type(sg.GetSpatialGroupName());
00659 return type == CoolString("EdgelGroup") ||
00660 type == CoolString("FittedEdgeGroup");
00661 #endif
00662 return true;
00663 }
00664
00665
00666
00667
00668
00669
00670 bool sdet_edgel_regions::insert_edgel(float pre_x, float pre_y,
00671 float xedgel, float yedgel,
00672 sdet_region_edge_sptr const& re)
00673 {
00674
00675 float pre_xf = Xf(pre_x), pre_yf = Yf(pre_y),
00676 xedgelf = Xf(xedgel), yedgelf = Yf(yedgel);
00677
00678 float xf, yf;
00679 unsigned int xinterp, yinterp;
00680
00681 bool edge_insert = false;
00682 bool init = true, done = false;
00683 while (bdgl_curve_algs::line_gen(pre_xf, pre_yf, xedgelf, yedgelf,
00684 init, done, xf, yf))
00685 {
00686 xinterp = (unsigned int)xf;
00687 yinterp = (unsigned int)yf;
00688 if (out_of_bounds(xinterp, yinterp))
00689 {
00690 vcl_cout << "In sdet_edgel_regions::insert_edgel - out of bounds "
00691 << "at array(" << xinterp << ' ' << yinterp << ")\n";
00692 continue;
00693 }
00694
00695 region_label_array_[yinterp][xinterp] = EDGE;
00696
00697 if (!re) continue;
00698 sdet_region_edge_sptr const& old_re =
00699 edge_boundary_array_[yinterp][xinterp];
00700 if (old_re&&old_re->get_edge())
00701 {
00702 edge_boundary_array_[yinterp][xinterp] = re;
00703 edge_insert = true;
00704 }
00705 if (!old_re)
00706 {
00707 edge_boundary_array_[yinterp][xinterp] = re;
00708 edge_insert = true;
00709 }
00710 }
00711 return edge_insert;
00712 }
00713
00714 int sdet_edgel_regions::bytes_per_pix()
00715 {
00716 int bypp = 1;
00717 if (image_source_)
00718 {
00719 int bytes_per_comp = (image_.bits_per_component()+7)/8;
00720 bypp = image_.components() * bytes_per_comp;
00721 }
00722 if (buf_source_)
00723 bypp = buf_->GetBytesPixel();
00724 return bypp;
00725 }
00726
00727
00728
00729
00730
00731
00732
00733
00734 bool sdet_edgel_regions::InitRegionArray(vcl_vector< vtol_edge_2d_sptr>& sg)
00735 {
00736 if (!this->GroupContainsEdges(sg))
00737 return false;
00738 vsol_box_2d b = btol_edge_algs::bounding_box(sg);
00739
00740 xo_ = (unsigned int)b.get_min_x();
00741 yo_ = (unsigned int)b.get_min_y();
00742
00743 xend_ = (unsigned int)b.get_max_x();
00744 yend_ = (unsigned int)b.get_max_y();
00745
00746 xs_ = (this->GetXSize()-1)*s_+1;
00747 ys_ = (this->GetYSize()-1)*s_+1;
00748
00749
00750 vcl_cout << "bounding box(" << xo_ << ' ' << yo_ << ' ' << xs_ << ' ' << ys_
00751 << ")\n";
00752
00753
00754 edge_boundary_array_ = vbl_array_2d<sdet_region_edge_sptr>(ys_, xs_);
00755
00756 region_label_array_ = vbl_array_2d<unsigned int>(ys_, xs_);
00757
00758
00759 region_label_array_.fill(UNLABELED);
00760 edge_boundary_array_.fill(NULL);
00761
00762 switch (this->bytes_per_pix())
00763 {
00764 case 1:
00765 delete[] ubuf_; ubuf_ = new unsigned char[this->GetXSize()];
00766 break;
00767 case 2:
00768 delete[] sbuf_; sbuf_ = new unsigned short[this->GetXSize()];
00769 break;
00770 default:
00771 vcl_cout<<"In vtol_intensity_face::get_intensity(): "
00772 << "bytes/pixel not 1 or 2\n";
00773 }
00774
00775
00776 if (ubuf_)
00777 for (int x = 0; x<this->GetXSize(); ++x)
00778 ubuf_[x] = 0;
00779
00780 if (sbuf_)
00781 for (int x = 0; x<this->GetXSize(); ++x)
00782 sbuf_[x] = 0;
00783
00784
00785 int counter=0;
00786 for (vcl_vector<vtol_edge_2d_sptr >::iterator sgit = sg.begin();
00787 sgit != sg.end(); sgit++)
00788 {
00789 vtol_edge_2d_sptr e = (*sgit);
00790 if (!e)
00791 continue;
00792 e->set_id(counter++);
00793 vdgl_digital_curve* dc = e->curve()->cast_to_vdgl_digital_curve();
00794 if (!dc)
00795 continue;
00796
00797
00798
00799 sdet_region_edge_sptr const & re = new sdet_region_edge(e);
00800 region_edges_[e->get_id()] = re;
00801
00802 vdgl_edgel_chain_sptr xy= dc->get_interpolator()->get_edgel_chain();
00803
00804 int n_edgels = xy->size();
00805
00806
00807
00808
00809
00810
00811
00812 sdet_region_edge_sptr const& vre = new sdet_region_edge(NULL);
00813 float pex1, pey1, pex2, pey2;
00814 if (n_edgels>0)
00815 {
00816 pex1 = float((*xy)[0].x()); pex2 = float((*xy)[n_edgels-1].x());
00817 pey1 = float((*xy)[0].y()); pey2 = float((*xy)[n_edgels-1].y());
00818 this->insert_edgel(pex1, pey1,
00819 float(e->v1()->cast_to_vertex_2d()->x()),
00820 float(e->v1()->cast_to_vertex_2d()->y()),
00821 vre);
00822 this->insert_edgel(pex2, pey2,
00823 float(e->v2()->cast_to_vertex_2d()->x()),
00824 float(e->v2()->cast_to_vertex_2d()->y()),
00825 vre);
00826 }
00827 else
00828 {
00829 pex1 = float(e->v1()->cast_to_vertex_2d()->x());
00830 pey1 = float(e->v1()->cast_to_vertex_2d()->y());
00831 pex2 = float(e->v2()->cast_to_vertex_2d()->x());
00832 pey2 = float(e->v2()->cast_to_vertex_2d()->y());
00833 this->insert_edgel(pex1, pey1, pex1, pey1, vre);
00834 this->insert_edgel(pex1, pey1, pex2, pey2, vre);
00835 }
00836
00837
00838
00839
00840
00841
00842
00843 bool edge_insert = false;
00844 for (int k =0; k < n_edgels; k++)
00845 {
00846 bool inserted = this->insert_edgel(pex1, pey1,
00847 float((*xy)[k].x()),
00848 float((*xy)[k].y()), re);
00849 edge_insert = edge_insert || inserted;
00850 pex1 = float((*xy)[k].x());
00851 pey1 = float((*xy)[k].y());
00852 }
00853 if (!edge_insert)
00854 {
00855 vcl_cout << "Edge Insert Failed for (" << e->v1() << ' '
00856 << e->v2() << ")N: "<< n_edgels << vcl_endl;
00857 failed_insertions_->push_back(e);
00858 }
00859 }
00860 return true;
00861 }
00862
00863
00864
00865 unsigned char sdet_edgel_regions::label_code(unsigned int label)
00866 {
00867 unsigned char result;
00868 if (label<min_region_label_)
00869 result = label;
00870 else
00871 result = LABEL;
00872 return result;
00873 }
00874
00875
00876
00877
00878
00879 bool sdet_edgel_regions::add_to_forward(unsigned int key, unsigned int value)
00880 {
00881 bool result = true;
00882 vcl_map<unsigned int, vcl_vector<unsigned int>* >::iterator rpfi;
00883 rpfi = region_pairs_forward_.find(key);
00884
00885 if (rpfi !=region_pairs_forward_.end())
00886 {
00887 vcl_vector<unsigned int> * vec = region_pairs_forward_[key];
00888 bool found = false;
00889 for (unsigned int i =0 ; i < vec->size() ; i++)
00890 {
00891 if ((*vec)[i] == value)
00892 found = true;
00893 }
00894 if (!found)
00895 {
00896 vec->push_back(value);
00897 }
00898 }
00899 else
00900 {
00901 vcl_vector<unsigned int>* larray = new vcl_vector<unsigned int>;
00902 larray->push_back(value);
00903 region_pairs_forward_[key]=larray;
00904 }
00905 return result;
00906 }
00907
00908
00909
00910
00911
00912 bool sdet_edgel_regions::add_to_reverse(unsigned int key, unsigned int value)
00913 {
00914 bool result = true;
00915 vcl_map<unsigned int, vcl_vector<unsigned int>* >::iterator rpfi;
00916 rpfi = region_pairs_reverse_.find(key);
00917
00918 if (rpfi !=region_pairs_reverse_.end())
00919 {
00920 vcl_vector<unsigned int> * vec = region_pairs_reverse_[key];
00921 bool found = false;
00922 for (unsigned int i =0 ; i < vec->size() ; i++)
00923 {
00924 if ((*vec)[i] == value)
00925 found = true;
00926 }
00927 if (!found)
00928 {
00929 vec->push_back(value);
00930 }
00931 }
00932 else
00933 {
00934 vcl_vector<unsigned int>* larray = new vcl_vector<unsigned int>;
00935 larray->push_back(value);
00936 region_pairs_reverse_[key]=larray;
00937 }
00938 return result;
00939 }
00940
00941
00942
00943
00944
00945
00946
00947
00948
00949
00950 unsigned char
00951 sdet_edgel_regions::EncodeNeighborhood(unsigned int ul, unsigned int ur,
00952 unsigned int ll, unsigned int lr)
00953 {
00954 unsigned char nhood = 0;
00955
00956 unsigned char nul = label_code(ul);
00957 nul = nul<<6;
00958 nhood |= nul;
00959
00960 unsigned char nur = label_code(ur);
00961 nur = nur<<4;
00962 nhood |= nur;
00963
00964 unsigned char nll = label_code(ll);
00965 nll = nll << 2;
00966 nhood |= nll;
00967
00968 unsigned char nlr = label_code(lr);
00969 nhood |= nlr;
00970
00971 return nhood;
00972 }
00973
00974
00975
00976 void sdet_edgel_regions::insert_equivalence(unsigned int ll, unsigned int ur, unsigned int& lr)
00977 {
00978 if (ll!=ur)
00979 {
00980
00981 unsigned int smaller_label, larger_label;
00982
00983 if (ll>ur) { smaller_label = ur; larger_label = ll; }
00984 else { smaller_label = ll; larger_label = ur; }
00985 this->add_to_forward(larger_label, smaller_label);
00986 this->add_to_reverse(smaller_label, larger_label);
00987 lr = smaller_label;
00988 }
00989 else
00990 lr = ur;
00991 }
00992
00993
00994
00995
00996
00997
00998
00999
01000
01001
01002
01003
01004
01005
01006 void sdet_edgel_regions::UpdateConnectedNeighborhood(unsigned int x, unsigned int y)
01007 {
01008 unsigned int &ul = region_label_array_[y][x];
01009 unsigned int &ur = region_label_array_[y][x+1];
01010 unsigned int &ll = region_label_array_[y+1][x];
01011 unsigned int &lr = region_label_array_[y+1][x+1];
01012
01013 unsigned char nhood = this->EncodeNeighborhood(ul, ur, ll, lr);
01014 switch (int(nhood))
01015 {
01016 case 0:
01017
01018
01019 return;
01020 case 1:
01021
01022
01023 return;
01024 case 5:
01025
01026
01027 return;
01028 case 17:
01029
01030
01031 return;
01032 case 20:
01033
01034
01035 lr = max_region_label_++;
01036 return;
01037 case 21:
01038
01039
01040 return;
01041 case 22:
01042
01043
01044 return;
01045 case 68:
01046
01047
01048 return;
01049 case 72:
01050
01051
01052 return;
01053 case 133:
01054
01055
01056 return;
01057 case 136:
01058
01059
01060 return;
01061 case 160:
01062
01063
01064 ll = ul;
01065 lr = ul;
01066 return;
01067 case 161:
01068
01069
01070 ll = ul;
01071 return;
01072 case 168:
01073
01074
01075 insert_equivalence(ll, ur, lr);
01076 return;
01077 case 169:
01078
01079
01080 return;
01081 case 164:
01082
01083
01084 lr = ul;
01085 return;
01086 case 165:
01087
01088
01089 return;
01090 case 144:
01091
01092
01093 ll = ul;
01094 lr = ul;
01095 return;
01096 case 145:
01097
01098
01099 ll = ul;
01100 return;
01101 case 152:
01102
01103
01104 lr = ul;
01105 return;
01106 case 153:
01107
01108
01109 return;
01110 case 148:
01111
01112
01113 lr = max_region_label_++;
01114 return;
01115 case 149:
01116
01117
01118 return;
01119 case 96:
01120
01121
01122 ll = ur;
01123 lr = ur;
01124 return;
01125 case 97:
01126
01127
01128 ll = max_region_label_++;
01129 return;
01130 case 104:
01131
01132
01133 insert_equivalence(ll, ur, lr);
01134 return;
01135 case 105:
01136
01137
01138 return;
01139 case 100:
01140
01141
01142 lr = ur;
01143 return;
01144 case 101:
01145
01146
01147 return;
01148 case 80:
01149
01150
01151 ll = max_region_label_++;
01152 lr = ll;
01153 return;
01154 case 81:
01155
01156
01157 ll = max_region_label_++;
01158 return;
01159 case 88:
01160
01161
01162 lr = ll;
01163 return;
01164 case 89:
01165
01166
01167 return;
01168 case 84:
01169
01170
01171 lr = max_region_label_++;
01172 return;
01173 case 85:
01174
01175
01176 return;
01177 default:
01178 vcl_cout << "In sdet_edgel_regions::UpdateNeigborhood(..)"
01179 << "impossible pattern(" << x << ' ' << y << ") = " << (int)nhood << '\n'
01180 << int(label_code(ul)) << ' ' << int(label_code(ur)) << '\n'
01181 << int(label_code(ll)) << ' ' << int(label_code(lr)) << "\n\n";
01182 }
01183 }
01184
01185 static bool reg_edges_neq(sdet_region_edge_sptr