import java.applet.Applet; import java.awt.event.*; import java.awt.*; public class ConvexIntersector { public ConvexIntersector() {} public static int orientation(Complex z1,Complex z2,Complex z3) { double x1,x2,x3; x1=z1.x*z2.y+z2.x*z3.y+z3.x*z1.y; x2=z1.y*z2.x+z2.y*z3.x+z3.y*z1.x; if(x1x2) return(-1); return(0); } public static int inside(Complex z,Quad Q) { int i1,i2,i3; int o1,o2; for(int i=0;i<4;++i) { i1=(i+0)%4; i2=(i+1)%4; i3=(i+2)%4; o1=orientation(Q.z[i1],Q.z[i2],z); o2=orientation(Q.z[i2],Q.z[i3],z); if(o1!=o2) return(0); } return(1); } /**A return of 1 in this routine indicates that the three points are very nearly colinear*/ public static int degenerate(Complex z1,Complex z2,Complex z3) { double x1,x2,x3; x1=z1.x*z2.y+z2.x*z3.y+z3.x*z1.y; x2=z1.y*z2.x+z2.y*z3.x+z3.y*z1.x; x3=Math.abs(x1-x2); if(x3<.00001) return(1); return(0); } /* a return of 1 means that the segments (z1,z2) and (z3,z4) nearly determine the same line */ public static int checkSame(Complex z1,Complex z2,Complex z3,Complex z4) { if(degenerate(z1,z2,z3)==0) return(0); if(degenerate(z1,z2,z4)==0) return(0); return(1); } /**checks if the ray (z1,z2) crosses the segment (z3,z4). 1 means yes.*/ public static int checkCross(Complex z1,Complex z2,Complex z3,Complex z4) { int test1,test2; if(degenerate(z1,z2,z3)==1) return(1); if(degenerate(z1,z2,z4)==1) return(1); if(orientation(z1,z2,z3)!=orientation(z1,z2,z4)) return(1); return(0); } /**assuming that the lines cross, this finds the intersection*/ public static Complex findCross(Complex z1,Complex z2,Complex z3,Complex z4) { double x1=z1.x; double y1=z1.y; double x2=z2.x; double y2=z2.y; double x3=z3.x; double y3=z3.y; double x4=z4.x; double y4=z4.y; double n1=x2*x3*y1 - x2*x4*y1 - x1*x3*y2 + x1*x4*y2 - x1*x4*y3 + x2*x4*y3 + x1*x3*y4 - x2*x3*y4; double n2=x2*y1*y3 - x4*y1*y3 - x1*y2*y3 + x4*y2*y3 - x2*y1*y4 + x3*y1*y4 + x1*y2*y4 - x3*y2*y4; double d=x3*y1 - x4*y1 - x3*y2 + x4*y2 - x1*y3 + x2*y3 + x1*y4 - x2*y4; Complex w=new Complex(n1/d,n2/d); return(w); } /**This routine determines if the line (z1,z2) lies on an edge of the polygon. A return of 1 means yes.*/ public static int checkEdge(Complex z1,Complex z2,PolyWedge P) { Complex z3=new Complex(); Complex z4=new Complex(); Complex W=new Complex(); Complex[] Z=new Complex[2]; int i2,test; int count=0; double d; for(int i1=0;i10) d=Complex.dist(W,Z[count-1]); if((count<2)&&(d>0.000000001)) { Z[count]=W; ++count; } } } if(count==0) return(null); Complex[] ZZ=new Complex[count]; for(int i=0;ilast) return(1); return(-1); } if(first==n) { if(last==n-1) return(1); return(-1); } if(last==n) { if(first==n-1) return(-1); return(1); } return(0); } /**This routine only works for special polygons, which are not too far from being convex. The vertices v0,v1 are already assumed to be in order, and then the vertices v2,v3... are assumed to be dihedrally permuted from their correct order.*/ public static PolyWedge makeConvex(PolyWedge P) { if(P.count==3) return(P); PolyWedge Q=new PolyWedge(); Q.count=P.count; int first=findFirst(P); int last=findLast(P); int test=determineSense(first,last,P.count-1); Q.z[0]=P.z[0]; Q.z[1]=P.z[1]; if(test==+1) { int k=first; for(int i=0;iP.count-1) k=2; } } if(test==-1) { int k=first; for(int i=0;i