home *** CD-ROM | disk | FTP | other *** search
/ Power-Programmierung / CD2.mdf / c / library / dos / diverses / leda / src / plane / _subdivi.c < prev    next >
Encoding:
C/C++ Source or Header  |  1991-11-15  |  2.8 KB  |  152 lines

  1. /*******************************************************************************
  2. +
  3. +  LEDA  2.1.1                                                 11-15-1991
  4. +
  5. +
  6. +  _subdivision.c
  7. +
  8. +
  9. +  Copyright (c) 1991  by  Max-Planck-Institut fuer Informatik
  10. +  Im Stadtwald, 6600 Saarbruecken, FRG     
  11. +  All rights reserved.
  12. *******************************************************************************/
  13.  
  14.  
  15. #include <LEDA/subdivision.h>
  16.  
  17. #include <LEDA/prio.h>
  18.  
  19.  
  20. declare2(priority_queue,edge,point)
  21. typedef priority_queue(edge,point) X_structure;
  22.  
  23.  
  24. static real x_sweep;
  25.  
  26. int compare(segment& s1,segment& s2)
  27. {
  28.   if (s1 == s2) return 0;
  29.  
  30.   real sl1 = s1.slope();
  31.   real sl2 = s2.slope();
  32.  
  33.   if (s1.start() == s2.start()) return compare(sl1,sl2);
  34.  
  35.   if (s1.end() == s2.end()) return compare(sl2,sl1);
  36.  
  37.   double y1 = sl1*x_sweep+s1.y_abs();
  38.   double y2 = sl2*x_sweep+s2.y_abs();
  39.  
  40.   return (y1 > y2) ? 1 : -1;
  41.  
  42. }
  43.  
  44. SubDivision::SubDivision(const graph& G) : planar_map(G)
  45.   edge e;
  46.   segment s;
  47.   point p;
  48.   strip sp;
  49.   int count = 0;
  50.  
  51.   // compute strips
  52.  
  53.   X_structure X;
  54.  
  55.   // initialize X-structure
  56.  
  57.   forall_edges(e,*this) 
  58.   { point p = point(inf(source(e)));
  59.     point q = point(inf(target(e)));
  60.  
  61.     if (p.xcoord() < q.xcoord()) 
  62.     { X.insert(e,p);
  63.       X.insert(e,q);
  64.      }
  65.    }
  66.  
  67.  
  68.  
  69.  
  70.   // sweep
  71.  
  72.   strip Y;
  73.  
  74.   x_sweep = -MAXDOUBLE;
  75.  
  76.   strips.insert(x_sweep, Y);    
  77.  
  78.   while( !X.empty() )
  79.   { point    p = X.inf(X.find_min());
  80.     list(edge) L,R;
  81.  
  82.     while ( !X.empty() )
  83.     { pq_item it = X.find_min();
  84.       point    q = X.inf(it);
  85.       edge     e = X.key(it);
  86.  
  87.       if (q != p) break;
  88.  
  89.       if (q == point(inf(source(e))))  // left  end
  90.           L.append(e);    
  91.       else                             // right end
  92.           R.append(e);    
  93.  
  94.       X.del_item(it);
  95.      }
  96.  
  97.  
  98.     // Insert new strip into version List
  99.  
  100.     x_sweep = p.xcoord();
  101.  
  102.     edge e;
  103.     forall(e,R) Y = Y.del(segment(point(inf(source(e))),point(inf(target(e)))));
  104.     forall(e,L) Y = Y.insert(segment(point(inf(source(e))),
  105.                                      point(inf(target(e)))), adj_face(e));
  106.  
  107.     L.clear();
  108.     R.clear();
  109.  
  110.     strips.insert(x_sweep, Y);    
  111.  
  112.    }
  113.  
  114.    strips.insert(MAXDOUBLE, Y);    
  115.  
  116.  
  117.    // compute outer face
  118.  
  119.    seq_item sit = strips.min();
  120.    sit = strips.succ(sit);
  121.  
  122.    outer_face = Y.inf(strips.inf(sit).min());
  123.  
  124. }
  125.  
  126.  
  127.  
  128. face SubDivision::locate_point(point p) const
  129. {
  130.   seq_item sit = strips.locate(p.xcoord()); 
  131.   strip Y = strips.inf(strips.pred(sit));
  132.   x_sweep = p.xcoord();
  133.   p_dic_item it = Y.locate(segment(p,0,1));
  134.   return (it == nil) ? outer_face : Y.inf(it);
  135.  }
  136.  
  137.  
  138. void SubDivision::print_stripes() const
  139. { seq_item it1;
  140.   p_dic_item it2;
  141.  
  142.   forall_seq_items(it1,strips)
  143.   { strip sp = strips.inf(it1);
  144.     forall_items(it2,sp) 
  145.       cout << sp.key(it2) << " f = " << int(sp.inf(it2)) << "\n";
  146.     newline;
  147.   }
  148.   newline;
  149.  }
  150.