import ddf.minim.signals.*;
import ddf.minim.*;
import ddf.minim.analysis.*;
import ddf.minim.effects.*;

boolean virgin = true;
float SCREENSIZE = 400;
float GRAV = .1;
float PULL = .1;
HashSet pullers = new HashSet();
HashSet flies = new HashSet();
;// = new HashSet();
float health;
spider   s = new spider((int)SCREENSIZE/2,(int)SCREENSIZE/2,null);
lin zlin = null;

AudioSnippet fxchomp;
AudioSnippet fxover;
AudioSnippet fxswing;



void setup(){
  frameRate(40);
  size(400,400);
   Minim.start(this);

  strokeWeight(2);
putPullers();
  textFont(loadFont("AkbarPlain-20.vlw"));

 fxchomp =  Minim.loadSnippet("chomp.mp3");
 fxover =  Minim.loadSnippet("over.mp3");
 fxswing =  Minim.loadSnippet("swing.mp3");

}

void stop()
{

     fxchomp.close();
     fxover.close();
    fxswing.close();
  super.stop();
}


void putPullers(){
  zlin = null;
  pullers = new HashSet(); 
 pullers.add(new puller(SCREENSIZE/4,SCREENSIZE/4));
  pullers.add(new puller(SCREENSIZE/2,SCREENSIZE/4));
  pullers.add(new puller(SCREENSIZE*3/4,SCREENSIZE/4));
  pullers.add(new puller(SCREENSIZE/4,SCREENSIZE/2));
  pullers.add(new puller(SCREENSIZE*3/4,SCREENSIZE/2));
  pullers.add(new puller(SCREENSIZE/4,SCREENSIZE*3/4));
  pullers.add(new puller(SCREENSIZE/2,SCREENSIZE*3/4));
  pullers.add(new puller(SCREENSIZE*3/4,SCREENSIZE*3/4));

}


boolean gameOn = true;
int score; 
int hiscore  = -1;
void startgame(){
  putPullers();

  flies   = new HashSet();
  score = 0;
  health = SCREENSIZE;
  gameOn = true;
  virgin = false;
}


void draw(){

  background(128);

  if(! gameOn){
    fill(200);
    stroke(0);
    rect(130,250,160,50);
    fill(255);
    text("click to play" ,160,280);
  }

  if(gameOn && health <= 0){
if(! virgin){           fxover.rewind();      fxover.play(); }
    gameOn  =false; 
    if(score > hiscore){
    hiscore = score;
    }
  }


  if(gameOn){
    health -=.8;




    if(random(0,100) < 3){
      flies.add(new fly()); 
    }
  }
  fill(255,128,128);
  stroke(128,0,0);
  rect(2,2,health,20);

  fill(255);
  text("score: "+score,20,20);
  if(hiscore != -1){
    text("high score: "+hiscore,220,20);
  }

  Iterator it = pullers.iterator();
  while(it.hasNext()){
    puller p = (puller)it.next();
    p.move();
    p.bounds();
    p.draw(); 
  }
  if(zlin != null){
    stroke(200);
    line(s.fx,s.fy,zlin.p.x,zlin.p.y) ;
  }

  s.move();
  s.draw();
  s.bounds();

  it = flies.iterator();
  while(it.hasNext()){
    fly f = (fly)it.next();
    f.move();
    if(f.bounds()) {
      it.remove();
    }
    f.draw();
    if(f.hitSpider()){
       fxchomp.rewind();      fxchomp.play();
      it.remove();
      if(gameOn){
        health += 80; 
        score += 10;
      }
    }
  }

  if(! gameOn){

    fill(255);
    if(virgin){
    text("alienbill productions presents",40,100); 
    text("a kirkjerk game",100,125); 
    }

    text("MANSPIDER",150,200); 
if(! virgin){
     text("last score: "+score,160,240); 
}

if(virgin){
    text("click to webswing rides on the leaf pods",20,220); 
    text("collect flies for score and health!",30,240); 
  text("a glorioustrainwreck",10,340); 
    text("for poppenkast games!",160,360);
}
  }

}

puller lastp = null;


void mousePressed(){
  if(gameOn){
    puller p = findHotPuller();
    if(p == null || p == lastp){
      zlin = null;
      lastp = null;
    }
    else {
       fxswing.rewind();      fxswing.play();

      //health -= 10;
      zlin = new lin(p);
      lastp = p; 
    }
  } 


}

void mouseClicked(){
  if(!gameOn){
    //    rect(130,250,160,50);
    if(mouseX >= 130 && mouseX <= 130+160 && mouseY >= 250 && mouseY <= 300){
      startgame();
    }
  }
}

puller findHotPuller(){
  Iterator it = pullers.iterator();
  while(it.hasNext()){
    puller p = (puller)it.next();
    if(p.isHot){
      return p; 
    }
  }
  return null;
}

class lin{
  puller p ;   
  lin(puller pp){
    p = pp;
  }
  void pullSpider(){

    s.xs += .005 * (p.x - s.fx);
    s.ys += .005 * (p.y - s.fy);
    /*
     if(s.x < p.x){
     s.xs += PULL * distance(s.x,p.x);
     } else {
     s.xs -= PULL;
     
     }
     if(s.y < p.y){
     s.ys += PULL;
     } else {
     s.ys -= PULL;
     
     }
     */
  }

}

class fly{
  float x,y, xs;

  fly(){
    y = random(10,SCREENSIZE-10);
    if(random(-1,1) < 0){
      x = -10;
      xs = 2 + random(-1,1);
    } 
    else {
      x = SCREENSIZE+10;
      xs = -2 - random(-1,1);

    }
  }
  void move(){
    x += xs;
  }

  void draw(){

    stroke(255);
    fill(0);

    ellipse(x-2,y-random(0,2),5,5);
    ellipse(x+2,y-random(0,2),5,5);


    stroke(0);
    fill(0);
    ellipse(x,y,5,5);
  }

  boolean bounds(){
    if(xs > 0 && x >  SCREENSIZE+10){
      return true; 
    }
    if(xs < 0 && x <  -10){
      return true;
    }
    return false;
  }
  boolean hitSpider(){
    if(distance(x,y,s.fx,s.fy) < 15) {
      return true; 
    } 
    else {
      return false; 
    }
  }


}


class spider {

  void draw(){
    stroke(0);
    fill(255,180,180);
    ellipse(fx,fy,20,20);
    fill(50);

    triangle(fx-10,fy+2,fx+10,fy+2,fx,fy+12);
    fill(255,180,180);
    noStroke();
    ellipse(fx,fy+4,3,3);
    fill(0);
    ellipse(fx-3,fy-4,3,3);
    ellipse(fx+3,fy-4,3,3);


  }

  spider(int x, int y, String s){
    // super(x,y,s);
    fy = y; 
    fx = x;

  }
  float xs,ys, fy,fx;
  float sz = 40;
  void move(){
    if(zlin != null){
      zlin.pullSpider();
    }


    ys += GRAV;

    xs *= .97;
    ys *= .97;
    fy+=ys;
    fx+=xs;
  }

  void bounds(){
    if(fx  <  (sz/4)){
      xs = abs(xs)*.5;
      fx = (sz/4);
    } 
    if(fx  >= SCREENSIZE - (sz/4)){
      xs = -abs(xs)*.5;
      fx = SCREENSIZE - (sz/4);
    } 
    if(fy  <  (sz/4)){
      ys = abs(ys)*.5;
      fy = (sz/4);
    } 
    if(fy  >= SCREENSIZE - (sz/4)){
      ys = -abs(ys)*.5;
      fy = SCREENSIZE - (sz/4);
      //fy = SCREENSIZE;
    } 
  }
}





class puller {
  float x,y,xs,ys;  
  boolean isHot;
  puller(float px, float py){
    x = px;
    y = random(20,SCREENSIZE-20);
    xs = random(-3,3); 
    //ys = random(-3,3); 
  }
  void move(){
    x = x + xs;
    y = y + ys;
  }
  void bounds(){
    if(x < 0) {
      x = 0 ; 
      xs = abs(xs);
    }
    if(y < 0) {
      y = 0 ; 
      ys = abs(ys);
    }
    if(x > SCREENSIZE) {
      x = SCREENSIZE ; 
      xs = -abs(xs);
    }
    if(y > SCREENSIZE) {
      y = SCREENSIZE ; 
      ys = -abs(ys);
    }
  }

  void draw(){

    fill(128,255,128); 
    if(distance(x,y,mouseX,mouseY) < 30){
      isHot = true;
      stroke(255,128,128);
    } 
    else {
      isHot = false;
      fill(0,255,0);
      stroke(0);
    }
    ellipse(x,y,20,20);

  }




}









/************************/
float distance(float x1, float y1,float x2, float y2){
  return sqrt(pow(x1-x2,2) + pow(y1-y2,2) ) ;
}