home *** CD-ROM | disk | FTP | other *** search
- /*******************************************************************************
- +
- + LEDA 2.1.1 11-15-1991
- +
- +
- + _subdivision.c
- +
- +
- + Copyright (c) 1991 by Max-Planck-Institut fuer Informatik
- + Im Stadtwald, 6600 Saarbruecken, FRG
- + All rights reserved.
- +
- *******************************************************************************/
-
-
- #include <LEDA/subdivision.h>
-
- #include <LEDA/prio.h>
-
-
- declare2(priority_queue,edge,point)
- typedef priority_queue(edge,point) X_structure;
-
-
- static real x_sweep;
-
- int compare(segment& s1,segment& s2)
- {
- if (s1 == s2) return 0;
-
- real sl1 = s1.slope();
- real sl2 = s2.slope();
-
- if (s1.start() == s2.start()) return compare(sl1,sl2);
-
- if (s1.end() == s2.end()) return compare(sl2,sl1);
-
- double y1 = sl1*x_sweep+s1.y_abs();
- double y2 = sl2*x_sweep+s2.y_abs();
-
- return (y1 > y2) ? 1 : -1;
-
- }
-
- SubDivision::SubDivision(const graph& G) : planar_map(G)
- {
- edge e;
- segment s;
- point p;
- strip sp;
- int count = 0;
-
- // compute strips
-
- X_structure X;
-
- // initialize X-structure
-
- forall_edges(e,*this)
- { point p = point(inf(source(e)));
- point q = point(inf(target(e)));
-
- if (p.xcoord() < q.xcoord())
- { X.insert(e,p);
- X.insert(e,q);
- }
- }
-
-
-
-
- // sweep
-
- strip Y;
-
- x_sweep = -MAXDOUBLE;
-
- strips.insert(x_sweep, Y);
-
- while( !X.empty() )
- { point p = X.inf(X.find_min());
- list(edge) L,R;
-
- while ( !X.empty() )
- { pq_item it = X.find_min();
- point q = X.inf(it);
- edge e = X.key(it);
-
- if (q != p) break;
-
- if (q == point(inf(source(e)))) // left end
- L.append(e);
- else // right end
- R.append(e);
-
- X.del_item(it);
- }
-
-
- // Insert new strip into version List
-
- x_sweep = p.xcoord();
-
- edge e;
- forall(e,R) Y = Y.del(segment(point(inf(source(e))),point(inf(target(e)))));
- forall(e,L) Y = Y.insert(segment(point(inf(source(e))),
- point(inf(target(e)))), adj_face(e));
-
- L.clear();
- R.clear();
-
- strips.insert(x_sweep, Y);
-
- }
-
- strips.insert(MAXDOUBLE, Y);
-
-
- // compute outer face
-
- seq_item sit = strips.min();
- sit = strips.succ(sit);
-
- outer_face = Y.inf(strips.inf(sit).min());
-
- }
-
-
-
- face SubDivision::locate_point(point p) const
- {
- seq_item sit = strips.locate(p.xcoord());
- strip Y = strips.inf(strips.pred(sit));
- x_sweep = p.xcoord();
- p_dic_item it = Y.locate(segment(p,0,1));
- return (it == nil) ? outer_face : Y.inf(it);
- }
-
-
- void SubDivision::print_stripes() const
- { seq_item it1;
- p_dic_item it2;
-
- forall_seq_items(it1,strips)
- { strip sp = strips.inf(it1);
- forall_items(it2,sp)
- cout << sp.key(it2) << " f = " << int(sp.inf(it2)) << "\n";
- newline;
- }
- newline;
- }
-