00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013 # ifndef shape_bcell2d_hpp
00014 # define shape_bcell2d_hpp
00015
00016
00017 # include <realroot/Seq.hpp>
00018 # include <shape/point.hpp>
00019 # include <shape/edge.hpp>
00020 # include <shape/bounding_box.hpp>
00021 # include <shape/bcell.hpp>
00022 # include <shape/graph.hpp>
00023
00024 # define TMPL template<class C, class V>
00025 # define TMPL1 template<class V>
00026 # define SELF bcell2d<C,V>
00027 # define REF REF_OF(V)
00028 # undef Topology
00029 # undef Mesher2d
00030 # undef Point
00031 # undef Edge
00032
00033 namespace mmx {
00034 namespace shape {
00035
00036
00037
00038
00039 TMPL class mesher2d;
00040 TMPL class bcell2d;
00041
00042
00043 TMPL
00044 class bcell2d : public bcell<C,REF> {
00045 public:
00046
00047 typedef topology<C,V> Topology;
00048
00049
00050 typedef typename topology<C,V>::Point Point;
00051 typedef typename topology<C,V>::Edge Edge;
00052 typedef bounding_box<C,REF> BoundingBox;
00053 typedef bcell<C,REF> Cell;
00054
00055 bcell2d(void) ;
00056 bcell2d(const BoundingBox & bx): Cell(bx) {}
00057 bcell2d(double xmin, double xmax): Cell(xmin,xmax) {};
00058 bcell2d(double xmin, double xmax, double ymin, double ymax): Cell(xmin,xmax,ymin,ymax) {} ;
00059
00060
00061 virtual ~bcell2d(void) ;
00062
00063
00064
00065
00066
00067
00068
00069
00070 virtual void split_position(int& v, double& t);
00071
00072 virtual Point* pair(Point * p, int & sgn) = 0;
00073 virtual Point* starting_point( int sgn)=0 ;
00074
00075 bool is_corner (void) const ;
00076
00077 virtual unsigned nb_intersect(void) const {
00078 return (this->n_intersections.size()+
00079 this->s_intersections.size()+
00080 this->e_intersections.size()+
00081 this->w_intersections.size() );
00082 }
00083
00084 virtual Seq<Point *> intersections() const{
00085
00086
00087
00088
00089
00090 Seq<Point *> r;
00091 r<< this->s_intersections;
00092 r<< this->e_intersections;
00093 r<< this->n_intersections.reversed();
00094 r<< this->w_intersections.reversed();
00095 return ( r );
00096 }
00097
00098 virtual Seq<Point *> intersections(int i) const{
00099 switch(i) {
00100 case 0:
00101 return s_intersections;
00102 case 1:
00103 return e_intersections;
00104 case 2:
00105 return n_intersections.reversed();
00106 case 3:
00107 return w_intersections.reversed();
00108 default:
00109 return (Seq<Point *>());
00110 }
00111
00112 }
00113
00114 inline bool is_border(void) const {
00115 return ( this->s_neighbors.size()==0 ||
00116 this->e_neighbors.size()==0 ||
00117 this->n_neighbors.size()==0 ||
00118 this->w_neighbors.size()==0 );
00119 }
00120
00121
00122 Seq<Point *> s_intersections ;
00123 Seq<Point *> e_intersections ;
00124 Seq<Point *> n_intersections ;
00125 Seq<Point *> w_intersections ;
00126 Seq<Point *> m_singular ;
00127
00128
00129
00130 gNode<bcell2d*>* m_gnode;
00131
00132 int side(Point *p) {
00133 Seq<Point*> all;
00134 int s,i,a;
00135 s = s_intersections.size();
00136 all = this->intersections();
00137 a = all.size();
00138 i = all.search(p);
00139 if (i==-1) return (-1);
00140 else return
00141 ( i<s ? 0 :
00142 ( i<s+(int)e_intersections.size() ? 1 :
00143 ( i<a-(int)w_intersections.size() ? 2 :
00144 3 )));
00145 }
00146
00147 inline void disconnect();
00148 inline void connect0(SELF * a, SELF * b);
00149 inline void connect1(SELF * a, SELF * b) ;
00150 inline void join0( SELF * b) ;
00151 inline void join1( SELF * b) ;
00152
00153
00154 virtual Seq<bcell2d *> neighbors() {
00155 Seq<bcell2d *> r;
00156 r<< this->s_neighbors;
00157 r<< this->e_neighbors;
00158 r<< this->n_neighbors;
00159 r<< this->w_neighbors;
00160 return ( r ); }
00161
00162 Seq<bcell2d *> s_neighbors ;
00163 Seq<bcell2d *> e_neighbors ;
00164 Seq<bcell2d *> n_neighbors ;
00165 Seq<bcell2d *> w_neighbors ;
00166
00167 virtual bcell2d * neighbor(Point * p) {
00168 foreach( bcell2d *c, this->s_neighbors )
00169 if ( c->n_intersections.member(p) )
00170 {
00171 return c;
00172 }
00173 foreach( bcell2d *c, this->e_neighbors )
00174 if ( c->w_intersections.member(p) )
00175 {
00176 return c;
00177 }
00178 foreach( bcell2d *c, this->n_neighbors )
00179 if ( c->s_intersections.member(p) )
00180 {
00181 return c;
00182 }
00183 foreach( bcell2d *c, this->w_neighbors )
00184 if ( c->e_intersections.member(p) )
00185 {
00186 return c;
00187 }
00188
00189
00190
00191 return NULL;
00192 }
00193
00194 };
00195
00196 TMPL void
00197 SELF::split_position(int& v, double& s) {
00198 double sx = (this->xmax()-this->xmin());
00199 double sy = (this->ymax()-this->ymin());
00200 if(sx<sy) {
00201 v=1;
00202 s=(this->ymax()+this->ymin())/2;
00203 } else {
00204 v=0;
00205 s=(this->xmax()+this->xmin())/2;
00206 }
00207 }
00208
00209 TMPL SELF::bcell2d(void) { }
00210
00211 TMPL SELF::~bcell2d(void) {}
00212
00213
00214
00215
00216
00217
00218
00219
00220
00221
00222
00223
00224
00225
00226
00227
00228
00229
00230
00231
00232
00233
00234
00235
00236
00237
00238
00239
00240
00241
00242
00243
00244
00245
00246
00247
00248
00249
00250
00251
00252
00253
00254
00257
00258 TMPL inline void
00259 SELF::join0(SELF * b)
00260 {
00261 this->e_neighbors << b;
00262 b->w_neighbors << this;
00263 }
00264
00265 TMPL inline void
00266 SELF::join1(SELF * b)
00267 {
00268 b->s_neighbors << this;
00269 this->n_neighbors << b;
00270 }
00271
00272 TMPL inline void
00273 SELF::connect0(SELF * a, SELF * b)
00274 {
00275 int i;
00276 bool flag;
00277
00278
00279 b->e_neighbors= this->e_neighbors ;
00280 foreach(SELF* cl,b->e_neighbors) {
00281 i= cl->w_neighbors.search(this);
00282 cl->w_neighbors[i]= b;
00283 }
00284 a->w_neighbors= this->w_neighbors ;
00285 foreach(SELF* cl,a->w_neighbors) {
00286 i= cl->e_neighbors.search(this);
00287 cl->e_neighbors[i]= a;
00288 }
00289
00290
00291 foreach(SELF* cl,this->s_neighbors) {
00292 flag=false;
00293 if ( check_overlap(cl,a,0))
00294 {
00295
00296 a->s_neighbors<< cl;
00297 i= cl->n_neighbors.search(this);
00298 cl->n_neighbors[i]= a;
00299 flag=true;
00300 }
00301 if ( check_overlap(cl,b,0) )
00302 {
00303
00304 b->s_neighbors<< cl;
00305 if (!flag)
00306 {
00307 i= cl->n_neighbors.search(this);
00308 cl->n_neighbors[i]= b;
00309 }
00310 else
00311 cl->n_neighbors << b;
00312 }
00313 }
00314 foreach(SELF* cl,this->n_neighbors) {
00315 flag=false;
00316 if ( check_overlap(cl,a,0))
00317 {
00318 a->n_neighbors<< cl;
00319 i= cl->s_neighbors.search(this);
00320 cl->s_neighbors[i]= a;
00321 flag=true;
00322 }
00323 if ( check_overlap(cl,b,0) )
00324 {
00325 b->n_neighbors<< cl;
00326 if (!flag)
00327 {
00328 i= cl->s_neighbors.search(this);
00329 cl->s_neighbors[i]= b;
00330 }
00331 else
00332 cl->s_neighbors << b;
00333 }
00334 }
00335 }
00336
00337 TMPL inline void
00338 SELF::connect1(SELF * a, SELF * b)
00339 {
00340 int i;
00341 bool flag;
00342
00343
00344 a->s_neighbors= this->s_neighbors ;
00345 foreach(SELF* cl,a->s_neighbors) {
00346 i= cl->n_neighbors.search(this);
00347 cl->n_neighbors[i]= a;
00348 }
00349 b->n_neighbors= this->n_neighbors ;
00350 foreach(SELF* cl,b->n_neighbors) {
00351 i= cl->s_neighbors.search(this);
00352 cl->s_neighbors[i]= b;
00353 }
00354
00355
00356 foreach(SELF* cl,this->w_neighbors) {
00357 flag=false;
00358 if ( check_overlap(cl,a,1))
00359 {
00360
00361 a->w_neighbors<< cl;
00362 i= cl->e_neighbors.search(this);
00363 cl->e_neighbors[i]= a;
00364 flag=true;
00365 }
00366 if ( check_overlap(cl,b,1) )
00367 {
00368
00369 b->w_neighbors<< cl;
00370 if (!flag)
00371 {
00372 i= cl->e_neighbors.search(this);
00373 cl->e_neighbors[i]= b;
00374 }
00375 else
00376 cl->e_neighbors << b;
00377 }
00378 }
00379 foreach(SELF* cl,this->e_neighbors) {
00380 flag=false;
00381 if ( check_overlap(cl,a,1))
00382 {
00383 a->e_neighbors<< cl;
00384 i= cl->w_neighbors.search(this);
00385 cl->w_neighbors[i]= a;
00386 flag=true;
00387 }
00388 if ( check_overlap(cl,b,1) )
00389 {
00390 b->e_neighbors<< cl;
00391 if (!flag)
00392 {
00393 i= cl->w_neighbors.search(this);
00394 cl->w_neighbors[i]= b;
00395 }
00396 else
00397 cl->w_neighbors << b;
00398 }
00399 }
00400 }
00401
00402 TMPL
00403 inline bool check_overlap(SELF * a, SELF * b, int v)
00404 {
00405 if (v==0)
00406 return !( a->xmax()<= b->xmin() ||
00407 b->xmax()<= a->xmin() );
00408 else
00409 return !( a->ymax()<= b->ymin() ||
00410 b->ymax()<= a->ymin() );
00411 }
00412
00413 TMPL inline void
00414 SELF::disconnect()
00415 {
00416 this->e_neighbors.clear();
00417 this->w_neighbors.clear();
00418 this->n_neighbors.clear();
00419 this->s_neighbors.clear();
00420 }
00421
00422 TMPL bool
00423 SELF::is_corner() const {
00424
00425 if (this->s_neighbors.size()==0 &&
00426 this->e_neighbors.size()==0 )
00427 return true;
00428 else if (this->e_neighbors.size()==0 &&
00429 this->n_neighbors.size()==0 )
00430 return true;
00431 else if (this->n_neighbors.size()==0 &&
00432 this->w_neighbors.size()==0 )
00433 return true;
00434 else if (this->w_neighbors.size()==0 &&
00435 this->s_neighbors.size()==0 )
00436 return true;
00437
00438 return false;
00439 }
00440
00441
00442 TMPL
00443 inline void print_neighbors(SELF * a)
00444 {
00445 std::cout<< "Cell : " << a <<std::endl;
00446 std::cout<< "EAST, " <<a->e_neighbors.size() << std::endl;
00447 foreach(SELF* cl,a->e_neighbors)
00448 std::cout<< cl << std::endl;
00449 std::cout<< "WEST, " <<a->w_neighbors.size() << std::endl;
00450 foreach(SELF* cl,a->w_neighbors)
00451 std::cout<< cl << std::endl;
00452 std::cout<< "NORTH, " <<a->n_neighbors.size() << std::endl;
00453 foreach(SELF* cl,a->n_neighbors)
00454 std::cout<< cl << std::endl;
00455 std::cout<< "SOUTH, " <<a->s_neighbors.size() <<std::endl;
00456 foreach(SELF* cl,a->s_neighbors)
00457 std::cout<< cl << std::endl;
00458 }
00459
00460 TMPL
00461 inline void print_intersections(SELF * a)
00462 {
00463 typedef typename topology<C,V>::Point Point;
00464 std::cout<< "Cell : " << a <<std::endl;
00465 std::cout<< "EAST, " <<a->e_intersections.size() << std::endl;
00466 foreach(Point* cl,a->e_intersections)
00467 std::cout<< cl->x()<<" "<<cl->y() << std::endl;
00468 std::cout<< "WEST, " <<a->w_intersections.size() << std::endl;
00469 foreach(Point* cl,a->w_intersections)
00470 std::cout<< cl->x()<<" "<<cl->y() << std::endl;
00471 std::cout<< "NORTH, " <<a->n_intersections.size() << std::endl;
00472 foreach(Point* cl,a->n_intersections)
00473 std::cout<< cl->x()<<" "<<cl->y() << std::endl;
00474 std::cout<< "SOUTH, " <<a->s_intersections.size() <<std::endl;
00475 foreach(Point* cl,a->s_intersections)
00476 std::cout<< cl->x()<<" "<<cl->y() << std::endl;
00477 }
00478
00479
00480 } ;
00481 } ;
00482 # undef TMPL
00483 # undef TMPL1
00484 # undef SELF
00485 # undef REF
00486 # endif // shape_cell2d_hpp