package alive;

/**
 * <ALIVE Project>
 * Experiment 1 Environment class
 *
 * Predator & Prey System
 *
 * By Rogerio Neves
 * LSI - POLI - USP
 */

import javax.vecmath.*;
import javax.media.j3d.*;

public class xp1_Environment extends Environment {
  Agent ag = null;
  int countCycles = 133;
  int count = 0;
  Agent a;

  // Interface
  java.awt.Scrollbar temp = new java.awt.Scrollbar();
  java.awt.Scrollbar rad = new java.awt.Scrollbar();
  java.awt.Scrollbar fr = new java.awt.Scrollbar();
  java.awt.Label lt = new java.awt.Label("------");
  java.awt.Label lr = new java.awt.Label("------");
  java.awt.Label lf = new java.awt.Label("-------");
  java.awt.Checkbox autoFeed = new java.awt.Checkbox("Auto Feed  Prob:", false);
  java.awt.Checkbox green = new java.awt.Checkbox("Green Only", false);
  java.awt.TextField feedProb = new java.awt.TextField("0.01");

  public xp1_Environment(EnvConfig cfg) { // pre-computations
    param = new double[7];
    paramName = new String[7];
    configureEnvironment(cfg);
    set(0,"temperature",25);  // uniform temperature
    set(1,"radiation",10);     // uniform radiation
    set(2,"friction",.001);
    set(3,"hunters",0);
    set(4,"food",0);
    set(5,"green",0);
    set(6,"red",0);
    temp.setValue((int)get("temperature"));
    rad.setValue((int)get("radiation"));
    fr.setMaximum(1010);
    fr.setValue((int)(get("friction")*1000));
    message("\n(xp1) started...  ");
    super.start();
  }

  public void createContent() {
    message("\nAdding agents...");
    double food = .05 * (config.xMax-config.xMin) *
        (config.yMax-config.yMin) *
        (config.zMax-config.zMin);
    if (food>config.POP_LIMIT/2) food = config.POP_LIMIT/2;
    for (int i = 0; i < food; i++) addFood();
    for (int i = 0; i < food/10.0; i++) addHunter();
  }
  public void createCustomUI() {
    java.awt.Button b1 = new java.awt.Button("+Food");
    java.awt.Button b2 = new java.awt.Button("+Hunter");
    b1.addActionListener(new java.awt.event.ActionListener() {
      public void actionPerformed(java.awt.event.ActionEvent e) {addFood();}});
    b2.addActionListener(new java.awt.event.ActionListener() {
      public void actionPerformed(java.awt.event.ActionEvent e) {addHunter();}});
    control.ui.add(new java.awt.Label("Temperature Radiation Friction"));
    control.ui.add(temp);
    control.ui.add(lt);
    control.ui.add(rad);
    control.ui.add(lr);
    control.ui.add(fr);
    control.ui.add(lf);
    control.ui.add(autoFeed);
    control.ui.add(feedProb);
    control.ui.add(green);
    control.ui.add(b1);
    control.ui.add(b2);
  }
  public void addFood() {
    do {
      a = new xp1_Food(this);
      if (a.get("energy")<0&&green.getState()) a.die();
    } while (a.get("energy")<0&&green.getState());
    //a.position.set(rnd(0,config.xMax),rnd(0,config.yMax),rnd(config.zMin,config.zMax));
    addAgent(a);
    a.highlightTime = 8;
  }
  public void addHunter() {
    Agent a = new xp1_Hunter(this);
    //a.set("w1",-1); a.set("w2",-1); a.set("w3",-1);
    addAgent(a);
    a.highlightTime = 8;
  }
  public void startUp() {
    System.out.print("\nElapsed\tHUNTERS\tFOOD\tGREEN\tRED\t");
  }
  public void update() { // Run-time computaions
      set("temperature", (double) temp.getValue());
      lt.setText(String.valueOf(temp.getValue())+"d");
      set("radiation", (double) rad.getValue());
      lr.setText(String.valueOf(rad.getValue())+" W");
      set("friction", (double) fr.getValue() / 1000);
      lf.setText(String.valueOf(get("friction")));
      if (autoFeed.getState()&&probability(getDouble(feedProb.getText()))) addFood();
    for (int i=0; i<agents.size();i++) {
      // the try block avoids null pointer operations
      try {
        ag = getAgent(i);
        if (ag!=null) ag.speed.scale(1-get("friction"));
      }
      catch (Exception e) { message("\n" + e.toString() + "\n"); }
    }
    if (count>0) count--;
    else {
      System.out.print("\n" + (int)elapsed + "\t"
                       + (int)get("hunters") + "\t"
                       + (int)get("food") + "\t"
                       + (int)get("green") + "\t"
                       + (int)get("red") + "\t");
      count = countCycles;
    }
    if (get("hunters")<1) alive = false;
  }

  // *** Main method: Makes experiment executable
  public static void main(String[] args) {
    EnvConfig cfg = new EnvConfig();
    new xp1_Environment(cfg);
  }
}
