import java.util.ArrayList;

public class ActionList {
	private ArrayList<Action> actions;
	private SerialCom serialCom;
	
	public ActionList(SerialCom serialCom) {
		this.serialCom = serialCom;
		actions = new ArrayList<>();
		actions.add(new Action());
	}
	public ActionList(int[] leftDeltaArray, int[] rightDeltaArray, long[] leftDelaiArray, long[] rightDelaiArray) {
		if(leftDelaiArray.length != rightDelaiArray.length
				|| leftDelaiArray.length != leftDelaiArray.length
				|| leftDelaiArray.length != rightDelaiArray.length)
			throw new InvalidActionListArrays();
		actions = new ArrayList<>();
		for(int i=0; i<leftDeltaArray.length; i++)
			actions.add(new Action(leftDeltaArray[i], rightDeltaArray[i], leftDelaiArray[i], rightDelaiArray[i]));
		actions.add(new Action());
	}
	
	public void addToActionList(int i, int j, int step) {
		switch (j * 10 + i) {
		case 00: //ACTION_LEFT_PLUS;
			addToLastAction(step, 0);
			break;
		case 02: //ACTION_LEFT_MINUS;
			addToLastAction(-step, 0);
			break;
		case 20: //ACTION_RIGHT_PLUS;
			addToLastAction(0, step);
			break;
		case 22: //ACTION_RIGHT_MINUS;
			addToLastAction(0, -step);
			break;
		case 10: //ACTION_FORWARD;
			addToLastAction(step, step);
			break;
		case 12: //ACTION_BACKWARD;
			addToLastAction(-step, -step);
			break;
		case 01: //ACTION_CLOCKWISE;
			addToLastAction(step, -step);
			break;
		case 21: //ACTION_ANTI_CLOCKWISE;
			addToLastAction(-step, step);
			break;
		default:
			throw new InvalidInputException();
		}
	}
	
	public void completeAction() {
		if(!actions.get(actions.size() - 1).isEmpty())
			actions.add(new Action());
	}
	
	public void completeActionAndAddPause(long delai) {
		if(actions.get(actions.size() - 1).isEmpty())
			actions.set(actions.size() - 1, new Action(0, 0, delai, delai));
		else
			actions.add(new Action(0, 0, delai, delai));
		completeAction();
	}
	
	private void addToLastAction(int deltaL, int deltaR) {
		actions.get(actions.size() - 1).addDeltaL(deltaL);
		actions.get(actions.size() - 1).addDeltaR(deltaR);
		SerialCommands.sendDeltas(serialCom, deltaL, deltaR);
	}
	
	public void revertLastAction() {
		if(actions.size() <= 0)
			return;

		Action toRevert = null;
		if(actions.get(actions.size() - 1).isEmpty()) {
			actions.remove(actions.size() - 1);
			if(actions.size() != 0) {
				toRevert = actions.get(actions.size() - 1);
				actions.set(actions.size() - 1, new Action());
			}
			else
				actions.add(new Action());
		} else {
			toRevert = actions.get(actions.size() - 1);
			actions.set(actions.size() - 1, new Action());
		}
		if(toRevert != null)
			SerialCommands.sendDeltas(serialCom, -toRevert.getDeltaL(), -toRevert.getDeltaR());
	}
	
	public String getLeftDeltaArray() {
		String str = "{";
		for(Action action : actions) {
			if(!action.isEmpty())
				str += String.valueOf(action.getDeltaL()) + ", ";
		}
		str = str.substring(0, str.length() - 2) + "}";
		return str;
	}
	public String getRightDeltaArray() {
		String str = "{";
		for(Action action : actions) {
			if(!action.isEmpty())
				str += String.valueOf(action.getDeltaR()) + ", ";
		}
		str = str.substring(0, str.length() - 2) + "}";
		return str;
	}
	public String getLeftDelaiArray() {
		String str = "{";
		for(Action action : actions) {
			if(!action.isEmpty())
				str += String.valueOf(action.getDeltaR()) + "L, ";
		}
		str = str.substring(0, str.length() - 2) + "}";
		return str;
	}
	public String getRightDelaiArray() {
		String str = "{";
		for(Action action : actions) {
			if(!action.isEmpty())
				str += String.valueOf(action.getDeltaR()) + "L, ";
		}
		str = str.substring(0, str.length() - 2) + "}";
		return str;
	}
	
	@Override
	public String toString() {
		String str = "";
		for(Action action : actions)
			str += action.toString() + "\n";
		str = str.substring(0, str.length() - 1); // remove last \n
		return str;
	}
}
