package pathfinder;
import java.util.*;

/**
 * @author Radoslav Menkyna
 * Sample application that finds shortest path in specific graph.
 * It is an example of class deprecation problem class Display is deprecated
 * and users should use display2 instead.
 * Problem is solved by 4 aspect oriented design patterns 
 */
public class Main {
    
    /** Creates a new instance of Main */
    public Main() {
    }
    
    /**
     * @param args the command line arguments
     */
    public static void main(String[] args) {
   
        LinkedList<Wall> ll = new LinkedList<Wall>();
        Iterator itll;
        
        Random rn=new Random();
      for(int i=0;i<=12;i=i+2){
    	  //int a=rn.nextInt(7);
    	  ll.add(new Wall(i,rn.nextInt(9),-rn.nextInt(9)));
      }
      ll.add(new Wall(13,0,0));
//    ll.add(new Wall(0,0,0));
//    ll.add(new Wall(2,6,-2));
//    ll.add(new Wall(4,-1,-6));
//    ll.add(new Wall(6,4,-5));
//    ll.add(new Wall(8,2,-4));
//    ll.add(new Wall(10,5,-3));
//    ll.add(new Wall(11,0,0));
//    
//    ll.add(new Wall(0,0,0));
//    ll.add(new Wall(2,6,-2));
//    ll.add(new Wall(4,-1,-8));
//    ll.add(new Wall(6,4,-5));
//    ll.add(new Wall(8,2,-4));
//    ll.add(new Wall(10,5,-3));
//    ll.add(new Wall(11,0,0));
        
//      ll.add(new Wall(0,0,0));
//    ll.add(new Wall(2,6,-2));
//    ll.add(new Wall(4,-1,-8));
//    ll.add(new Wall(6,4,-5));
//    ll.add(new Wall(8,2,-7));
//    ll.add(new Wall(10,5,-3));
//    ll.add(new Wall(11,0,0));
    
    Wall pom;
    PathPoint pomPathPoint = new PathPoint(0,0,0,new Point((float)0.0,(float)0.0));         // pomocne body cesty 
    PathPoint pomPathPoint2 = new PathPoint(0,0,0,new Point((float)0.0,(float)0.0));
    LinkedList<PathPoint> y1= new LinkedList<PathPoint>();                            // zoznamy na ulozenie bodov            
    LinkedList<PathPoint> y2= new LinkedList<PathPoint>();        
    y1.add(new PathPoint(0,0,0,new Point((float)0.0,(float)0.0)));                               //vlozenie zaciatocnych bodov                               
    y2.add(new PathPoint(0,0,0,new Point((float)0.0,(float)0.0)));
    int k=0;
   for (itll = ll.iterator(); itll.hasNext(); ) {             //cyklus cez vsetky mury            
        k++;
        pom=(Wall)itll.next();
        //pom.tlac();     
        if(ll.indexOf(pom)==0) pom=(Wall)itll.next();          // start preskocime
        pom.tlac();
  
        for(int j=0; j<ll.indexOf(pom);j++){                    //cyklus pre body na ceste
        
            boolean colision1=false;
            boolean colision2=false;
            boolean colision3=false;
            boolean colision4=false;               
            if (k>1){ 
               

                for (int l=j+1; l<k;l++){                         // cyklus cez mury ktore stoja v ceste a kontrola kolizii
                      Wall PomWall=(Wall)ll.get(l);
                    Line line1=new Line(new Point(PomWall.getX(),PomWall.getY1()),new Point(PomWall.getX(),PomWall.getY2()));
                    Line line2=new Line(((PathPoint)y1.get(j)).retPoint(),new Point(pom.getX(),pom.getY1()));
                    Line line3=new Line(((PathPoint)y1.get(j)).retPoint(),new Point(pom.getX(),pom.getY2()));
                    Line line4=new Line(((PathPoint)y2.get(j)).retPoint(),new Point(pom.getX(),pom.getY1()));
                    Line line5=new Line(((PathPoint)y2.get(j)).retPoint(),new Point(pom.getX(),pom.getY2()));
                    Point intersec;
                    intersec=line1.intersect(line2);
                    if((intersec.getY()<PomWall.getY1())&&(intersec.getY()>PomWall.getY2())) colision1=true;
                    intersec=line1.intersect(line3);
                    if((intersec.getY()<PomWall.getY1())&&(intersec.getY()>PomWall.getY2())) colision2=true;
                    intersec=line1.intersect(line4);
                    if((intersec.getY()<PomWall.getY1())&&(intersec.getY()>PomWall.getY2())) colision3=true;
                    intersec=line1.intersect(line5);
                    if((intersec.getY()<PomWall.getY1())&&(intersec.getY()>PomWall.getY2())) colision4=true;
                    
                }
            }
            if (!colision1){
                if ((pomPathPoint.distance==0.0)
                || ((PathPoint)y1.get(j)).distance(new Point(pom.getX(),pom.getY1()))<pomPathPoint.distance){
                pomPathPoint.x=pom.getX();
                pomPathPoint.y=pom.getY1();
                pomPathPoint.distance=((PathPoint)y1.get(j)).distance(new Point(pom.getX(),pom.getY1()));
                pomPathPoint.zBodu=(((PathPoint)y1.get(j)).retPoint());
                pomPathPoint.index1=1;
                pomPathPoint.index2=j;
                }

            }
            if (!colision2){
                if ((pomPathPoint2.distance==0.0)
                || ((PathPoint)y1.get(j)).distance(new Point(pom.getX(),pom.getY2()))<pomPathPoint2.distance){
                pomPathPoint2.x=pom.getX();
                pomPathPoint2.y=pom.getY2();
                pomPathPoint2.distance=((PathPoint)y1.get(j)).distance(new Point(pom.getX(),pom.getY2()));
                pomPathPoint2.zBodu=(((PathPoint)y1.get(j)).retPoint());
                pomPathPoint2.index1=1;
                pomPathPoint2.index2=j;
            }
            }
            if (!colision3){
                if ((pomPathPoint.distance==0.0)
                || ((PathPoint)y2.get(j)).distance(new Point(pom.getX(),pom.getY1()))<pomPathPoint.distance){
                pomPathPoint.x=pom.getX();
                pomPathPoint.y=pom.getY1();
                pomPathPoint.distance=((PathPoint)y2.get(j)).distance(new Point(pom.getX(),pom.getY1()));
                pomPathPoint.zBodu=(((PathPoint)y2.get(j)).retPoint());
                pomPathPoint.index1=2;
                pomPathPoint.index2=j;
                }

            }
            if (!colision4){
                if ((pomPathPoint2.distance==0.0)
                    || ((PathPoint)y2.get(j)).distance(new Point(pom.getX(),pom.getY2()))<pomPathPoint2.distance){
                    pomPathPoint2.x=pom.getX();
                    pomPathPoint2.y=pom.getY2();
                    pomPathPoint2.distance=((PathPoint)y2.get(j)).distance(new Point(pom.getX(),pom.getY2()));
                    pomPathPoint2.zBodu=(((PathPoint)y2.get(j)).retPoint());
                    pomPathPoint2.index1=2;
                    pomPathPoint2.index2=j;
                    }
            }
        }
        y1.add(pomPathPoint);
        y2.add(pomPathPoint2);
       pomPathPoint = new PathPoint(0,0,0,new Point((float)0.0,(float)0.0));         // pomocne body cesty
       pomPathPoint2 = new PathPoint(0,0,0,new Point((float)0.0,(float)0.0));
     }
        System.out.println();
        for (Iterator tlac=y1.iterator();tlac.hasNext();) ((PathPoint)tlac.next()).tlac(); 
        for (Iterator tlac=y2.iterator();tlac.hasNext();) ((PathPoint)tlac.next()).tlac(); 
        
        PathPoint tmpPoint=(PathPoint)y1.getLast();
        ArrayList<PathPoint> DispPoints= new ArrayList<PathPoint>();
        boolean success;
        do{
            success=false;
            tmpPoint.tlac();
            DispPoints.add(tmpPoint);
            if (tmpPoint.index1==1){tmpPoint=(PathPoint)y1.get(tmpPoint.index2); success=true; }
            if((!success)&&(tmpPoint.index1==2))tmpPoint=(PathPoint)y2.get(tmpPoint.index2);
            
        } while (tmpPoint.index1!=0);
         tmpPoint.tlac();
         DispPoints.add(tmpPoint);
           System.out.println();
        
    
         //for (Iterator tlac=DispPoints.iterator();tlac.hasNext();) ((PathPoint)tlac.next()).tlac(); 
        
        Display a = new Display();
        a.displayGraph(ll,DispPoints);  
 }
      
 }



