/**
 *
 * FSSP.java
 * 
 *
 */

import de.tubs.cs.sc.casim.State;
import de.tubs.cs.sc.casim.Cell;
import de.tubs.cs.sc.casim.Lattice;
import java.awt.Color;

/**
 * FSSP
 */
public class FSSP extends State {
    /**
     * (1) add state variables here
     * i.e. int condition;
     */
    private boolean readyToFire;
    private boolean leftBorder;
    private boolean rightBorder;
    private boolean fire;
    private int fastR;
    private int fastL;
    private int slowR;
    private int slowL;
    /**
     * (2) add initialization of state variables here
     */
    public void FSSP() {
	readyToFire = false;
	fire = false;
	leftBorder = false;
	rightBorder = false;
	fastR = 0; 
	fastL = 0;
	slowR = 0; 
	slowL = 0;
    }
    /**
     * (3) add lattice initialization here
     * access is (StateClass)l.getState(...)
     */
    public static void initialize(Lattice l, int option) {

	((FSSP)l.getState(0)).fastR = 1;
	((FSSP)l.getState(0)).slowR = 3;
	((FSSP)l.getState(0)).readyToFire = true;
	((FSSP)l.getState(0)).leftBorder = true;
	((FSSP)l.getState(l.getX()-1)).readyToFire = true;
	((FSSP)l.getState(l.getX()-1)).rightBorder = true;
	
    }
    /**
     * (4) add drawing color definition here
     * an array of Color's is recommended
     * returning null means the cell will not be drawn
     */
    public Color getColor() {
	if(slowL != 0 || slowR != 0) { return Color.red; }
	if(fastL != 0 || fastR != 0) { return Color.blue; }
	if(readyToFire) { return Color.gray; }
	if(fire) { return Color.pink; }
	
      	return null;
    }
    /**
     * (5) add state variables copy code here
     * do a field to field copy from s to this
     */
    public void copy(State s) {
	FSSP source = (FSSP)s;
	slowL = source.slowL;
	slowR = source.slowR;
	fastL = source.fastL;
	fastR = source.fastR;
	readyToFire = source.readyToFire;
	fire = source.fire;
    }
    /**
     * (6) add transion function code here
     * evaluating the new state of the cell
     * use i.e. cell.getNeighbors to get the neighborhood set
     */
    public void  transition(Cell cell) {	
	State nb[] = cell.getNeighbors();
	if( readyToFire && ((FSSP)nb[1]).readyToFire && ((FSSP)nb[2]).readyToFire ) {
	    slowR = 0;
	    slowL = 0;
	    fastR = 0;
	    fastL = 0;
	    fire = true;
	    readyToFire = false;
	    return;
	}
	
	if( fastL == 1 && slowR == 1 ) {
	    readyToFire = true;
	    slowL = 4;
	    fastL = 2;
	    
	}
	if( ((FSSP)nb[1]).fastL == 1 && ((FSSP)nb[1]).slowR == 1 ) {
	    readyToFire = true;
	    slowR = 3;
	    fastR = 1;
	    return;
	}

	if( fastR == 1 && slowL == 1) {
	    readyToFire = true;
	    slowR = 4;
	    fastR = 2;
	}

	if( ((FSSP)nb[2]).fastR == 1 && ((FSSP)nb[2]).slowL == 1) {
	    readyToFire = true;
	    slowL = 3;
	    fastL = 1;
	    return;
	}
	
	if(slowL != 0) { slowL--; }
	if(slowR != 0) { slowR--; }
	if(fastL != 0) { fastL--; }
	if(fastR != 0) { fastR--; }
	

	if( ((FSSP)nb[1]).slowR == 1 ) { slowR = 3; }
	if( ((FSSP)nb[1]).fastR == 1 && ((FSSP)nb[1]).slowL != 1) { fastR = 1; }
	if( ((FSSP)nb[2]).slowL == 1) { slowL = 3; }
	if( ((FSSP)nb[2]).fastL == 1 && ((FSSP)nb[2]).slowR != 1) { fastL = 1; }
	if( ((FSSP)nb[1]).slowR == 1 && readyToFire ) {
	    slowR = 0;
	    slowL = 3;
	}
	if( ((FSSP)nb[2]).slowL == 1 && readyToFire ) {
	    slowL = 0;
	    slowR = 3;
	}
	if( ((FSSP)nb[1]).fastR == 1 && readyToFire ) {
	    fastR = 0;
	    fastL = 1;
	}
	if( ((FSSP)nb[2]).fastL == 1 && readyToFire ) {
	    fastL = 0;
	    fastR = 1;
	} 
	if( ((FSSP)nb[2]).fastL == 1 && ((FSSP)nb[1]).slowR == 1 ) {
	    readyToFire = true;
	    fastL = 1;
	    fastR = 1;
	    slowR = 3;
	    slowL = 3;
	}
	if( ((FSSP)nb[2]).slowL == 1 && ((FSSP)nb[1]).fastR == 1) {
	    readyToFire = true;
	    fastL = 1;
	    fastR = 1;
	    slowR = 3;
	    slowL = 3;
	}
	if( readyToFire && ((FSSP)nb[1]).slowR == 1 && ((FSSP)nb[2]).slowL == 1) {
	    slowR = 3;
	    slowL = 3;
	}
	if( readyToFire && ((FSSP)nb[1]).fastR == 1 && ((FSSP)nb[2]).fastL == 1) {
	    fastR = 1;
	    fastL = 1;
	}
	
	    
    }
    /**
     * (7) add code for definition of constant states here
     * if the state class is used in lattices with constant boundary
     * conditions, it should return the constant state
     */
    public State getConstant() {
      	return null;
    }
}


