diff --git a/aabc/ABeeSolver.java b/aabc/ABeeSolver.java
new file mode 100644
index 0000000000000000000000000000000000000000..0265404c0baf23077319fc80e7fbdd5147b2037c
--- /dev/null
+++ b/aabc/ABeeSolver.java
@@ -0,0 +1,39 @@
+package aabc;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import baseOptiAgent.BaseAgent;
+import baseOptiAgent.Env;
+import baseOptiAgent.Result;
+import baseOptiAgent.Solver;
+import eval.Eval;
+
+public class ABeeSolver extends Solver{
+
+	public ABeeSolver(Eval _eval, int _maxCycle, int _maxEval) {
+		super(_eval, _maxCycle, _maxEval);
+		name = "A-Bee";
+	}
+
+	@Override
+	public Result solve() {
+		
+		// [PARAM]
+		int nbrAgent = 100;
+		int maxTry = 200;
+		
+		// [INIT]
+		BeeEnv env = new BeeEnv(eval);
+		
+		List<Bee> agents = new ArrayList<Bee>();
+		for (int i_agent = 0; i_agent < nbrAgent; i_agent++) {
+			agents.add(new Bee(eval, i_agent, env, maxTry));
+		}
+		
+		env.initAgent(agents);
+		
+		return findSolution(agents, env, 3);
+	}
+
+}
diff --git a/aabc/Bee.java b/aabc/Bee.java
index b70dab1e18871b15a6e9f10cd58d9d8a7f184b8e..7c58b77b17dc064366a1b0faa2437563723a3247 100644
--- a/aabc/Bee.java
+++ b/aabc/Bee.java
@@ -7,8 +7,9 @@ import baseOptiAgent.BaseAgent;
 import eval.Eval;
 
 public class Bee extends BaseAgent{
-	
-	Env env;
+
+
+	BeeEnv env;
 	
 	int maxCount;
 	
@@ -17,16 +18,17 @@ public class Bee extends BaseAgent{
 	
 	// EMPLOYED
 	List<List<Double>> randomAgents;
-	double group; // 0.1..0.5
+	double groupValue;
 	
 	// ONLOOKERS
 	double bestFitness;
 	//List<List<Double>> randomAgents;
-	//double group;
+	//double groupValue;
+
+	
+	public Bee(Eval _eval, int _id, BeeEnv _env, int _maxCount) {
+		super(_eval, _id);
 
-	public Bee(int _id, Eval _eval, Env _env, int _maxCount) {
-		id = _id;
-		eval = _eval;
 		env = _env;
 		
 		maxCount = _maxCount;
@@ -56,12 +58,12 @@ public class Bee extends BaseAgent{
 
 		if (phase == Phase.EMPLOYED) {
 			randomAgents = env.getRandomAgents(id);
-			group = env.getGroup(fitness);
+			groupValue = env.getGroup(this.getFitness());
 		}
 		else if (phase == Phase.ONLOOKERS) {
 			randomAgents = env.getRandomAgents(id);
-			bestFitness = env.bestFitness();
-			group = env.getGroup(fitness);
+			groupValue = env.getGroup(this.getFitness());
+			bestFitness = env.getBestFitness();
 		}
 		else if (phase == Phase.SCOUTS) {
 		}
@@ -72,23 +74,21 @@ public class Bee extends BaseAgent{
 
 		List<Double> newVector = new ArrayList<Double>(vector);
 		
-		for (int i = 0; i < vector.size(); i++) {
-			if(Math.random() <= group) {
-				newVector.set(i, vector.get(i) + 2 * (Math.random() - 0.5) * (vector.get(i) - randomAgents.get(i).get(i)));
+		
+		for (int i_dim = 0; i_dim < eval.getDim(); i_dim ++) {
+			if(Math.random() < groupValue) {
+				newVector.set(
+						i_dim,
+							vector.get(i_dim) 
+							+ 2 * (Math.random() - 0.5) 
+								* (vector.get(i_dim) - randomAgents.get(i_dim).get(i_dim))
+						);
 			}
 		}
-		this.boundValue(newVector);
 		
-		double newEval = evaluate(newVector);
-		double newFit = fitness(newEval);
-		if (fitness < newFit) {
-			//System.out.println("Update from : "+evaluate+" to "+newEval);
-			vector = newVector;
-			evaluate = newEval;
-			fitness = newFit;
-			return true;
-		}
-		return false;
+		boundValue(newVector);
+		
+		return compareAndUpdate(newVector);
 	}
 	
 	private void employedPhase() {
@@ -96,6 +96,9 @@ public class Bee extends BaseAgent{
 		if (!res) {
 			stuckCount ++;
 		}
+		else {
+			stuckCount = 0;
+		}
 	}
 	
 	private void onlookerPhase() {
@@ -113,6 +116,7 @@ public class Bee extends BaseAgent{
 			stuckCount = 0;
 			
 			
+			double oldEval = evaluate;
 			vector = generateRandomVector();
 			evaluate = this.evaluate(vector);
 			fitness = this.fitness(evaluate);
diff --git a/aabc/Env.java b/aabc/BeeEnv.java
similarity index 56%
rename from aabc/Env.java
rename to aabc/BeeEnv.java
index 403bea660922848160fb6f2441e654dbb51565e7..4958605039c4f898f681fff294d7c81e4d3c7c9a 100644
--- a/aabc/Env.java
+++ b/aabc/BeeEnv.java
@@ -4,15 +4,14 @@ import java.util.ArrayList;
 import java.util.List;
 import java.util.Random;
 
+import baseOptiAgent.Env;
 import eval.Eval;
 
-public class Env {
+public class BeeEnv extends Env{
 
 	private List<Bee> agents;
 	
-	private Eval eval;
-	
-	public Env(Eval _eval) {
+	public BeeEnv(Eval _eval) {
 		eval = _eval;
 	}
 	
@@ -20,38 +19,48 @@ public class Env {
 		agents = new ArrayList<Bee>(_agents);
 	}
 	
-	private List<Double> getRandomAgent(int id) {
+	public List<List<Double>> getRandomAgents(int id) {
 		if (agents.size() == 1) {
 			throw new java.lang.Error("Cannot return random agent because the environment only know 1 agent.");
 		}
 		
 		Random rand = new Random();
+		
+		List<List<Double>> randomAgents = new ArrayList<List<Double>>();
+
 		Bee randomagent = agents.get(rand.nextInt(agents.size()));
 		while (randomagent.getId() == id) {
 			randomagent = agents.get(rand.nextInt(agents.size()));
 		}
-		return randomagent.getVector();
-	}
-	
-	public List<List<Double>> getRandomAgents(int id) {
-		List<List<Double>> res = new ArrayList<List<Double>>();
-		for(int i = 0; i < eval.getDim(); i++) {
-			res.add(this.getRandomAgent(id));
+		for (int i = 0; i < eval.getDim(); i++) {
+			randomAgents.add(randomagent.getVector());
 		}
-		return res;
+		
+		/*
+		for (int i = 0; i < eval.getDim(); i++) {
+			Bee randomagent = agents.get(rand.nextInt(agents.size()));
+			while (randomagent.getId() == id) {
+				randomagent = agents.get(rand.nextInt(agents.size()));
+			}
+			randomAgents.add(randomagent.getVector());
+		}
+		*/
+
+		return randomAgents;
 	}
 	
 	public double getGroup(double fitness) {
-		int count = 0;
-		for(Bee bee: agents) {
-			if(bee.getFitness() > fitness) {
-				count ++;
+		int res = 0;
+		for(Bee bee : agents) {
+			if (bee.getFitness() > fitness) {
+				res ++;
 			}
 		}
-		return Math.ceil((double)count * (double)5 / (double) agents.size())/10;
+		return Math.ceil((double)res * 5.0 / (double) agents.size()) /10 ;
 	}
-	
-	public double bestFitness() {
+
+	@Override
+	public double getBestFitness() {
 		double res = agents.get(0).getFitness();
 		for(Bee agent: agents) {
 			if (res < agent.getFitness()) {
@@ -60,8 +69,9 @@ public class Env {
 		}
 		return res;
 	}
-	
-	public double bestEval() {
+
+	@Override
+	public double getBestEval() {
 		Bee res = agents.get(0);
 		for(Bee agent: agents) {
 			if (res.getFitness() < agent.getFitness()) {
diff --git a/aabc/MainBee.java b/aabc/MainBee.java
deleted file mode 100644
index dfa47d2bcdfb47a7c4f4fb29daa8bdc03388603b..0000000000000000000000000000000000000000
--- a/aabc/MainBee.java
+++ /dev/null
@@ -1,105 +0,0 @@
-package aabc;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.List;
-
-import eval.Eval;
-import eval.fun.Rastrigin;
-import eval.fun.SchwefelFunction1_2;
-import eval.fun.StepFunction;
-
-public class MainBee {
-	public static void main(String[] args) {
-		// [PARAM]
-		
-		int nbrAgent = 100;
-		int maxTry = 200;
-	
-		int res = 0;
-		int nbrTry = 1;
-		
-		long startTime = System.currentTimeMillis();
-		for (int i = 0; i < nbrTry; i++) {
-			// [INIT]
-			
-			//Eval eval = new StepFunction();
-			//Eval eval = new SchwefelFunction1_2();
-			//Eval eval = new SchwefelFunction();
-			Eval eval = new Rastrigin();
-			
-
-			Env env = new Env(eval);
-			
-			List<Bee> agents = new ArrayList<Bee>();
-			for (int i_agent = 0; i_agent < nbrAgent; i_agent++) {
-				agents.add(new Bee(i_agent, eval, env, maxTry));
-			}
-			
-			env.initAgent(agents);
-			
-			res += findSolution(nbrAgent, env, eval, agents);
-			System.out.println("run : "+i);
-			System.out.println("Nbr eval :"+eval.getCount());
-		}
-		long estimatedTime = System.currentTimeMillis() - startTime;
-		
-		System.out.println("Time : "+estimatedTime/1000+ "s "+estimatedTime%1000+"ms");
-		System.out.println(res);
-		System.out.println("Average cycle : "+(double)res/(double)nbrTry);
-
-	}
-	
-	private static int findSolution(
-			int nbrAgent,
-			Env env,
-			Eval eval,
-			List<Bee> agents
-			) {
-		
-		// [RUN]
-		
-		int cycle = 0;
-		double bestSol = 0;
-		
-		do  {
-			do {
-				for (Bee agent : agents) {
-					agent.perceive();
-				}
-				for (Bee agent : agents) {
-					agent.decide();
-					agent.act();
-
-				}
-			}while (agents.get(0).getPhase() != Phase.EMPLOYED);
-			
-			if(cycle == 0) {
-				bestSol = env.bestEval();
-			}
-			else if (env.bestEval() < bestSol) {
-				bestSol = env.bestEval();
-				System.out.println("Improve : "+bestSol+" at :"+cycle);
-			}
-			
-			cycle ++;
-			//System.out.println("Cycle : "+cycle+" Value : "+env.bestEval());
-			
-			/*
-			// Pas à Pas
-			try {
-				System.in.read();
-			} catch (IOException e) {
-				// TODO Auto-generated catch block
-				e.printStackTrace();
-			}
-			*/
-			
-			
-			
-		} while(Math.abs(env.bestEval()-eval.getObjective())>eval.getErrorDelta());
-
-		return cycle;
-		
-	}
-}
diff --git a/amakaque/SMAgent.java b/amakaque/SMAgent.java
index f4261203cf8e5c6bf3158bed927a5bf358c05014..debf14e92f3ed8c10255f01c7d0203503b5f049a 100644
--- a/amakaque/SMAgent.java
+++ b/amakaque/SMAgent.java
@@ -59,9 +59,10 @@ public class SMAgent extends BaseAgent {
 	 * Init the SM with random starting point within the env dimension
 	 */	
 	public SMAgent(int _id, double _pr, SMEnv _env, Eval _eval) {
+		super(_eval, _id);
+		
 		env = _env;
-		eval = _eval;
-		id = _id;
+		
 		if (id == 0) {
 			isLL = true;
 			isGL = true;
diff --git a/ant/Ant.java b/ant/Ant.java
index ef4a793a794d14d980bd231cafcfcc5730bffc41..3534a06ff202235eb812343df0f3c37620f6f0b4 100644
--- a/ant/Ant.java
+++ b/ant/Ant.java
@@ -22,7 +22,8 @@ public class Ant extends BaseAgent{
 	private List<Double> archiveProba;
 	
 	public Ant(int _id, Eval _eval, AntEnv _env, double _evaporationRate) {
-		eval = _eval;
+		super(_eval, _id);
+
 		env = _env;
 
 		evaporationRate = _evaporationRate;
@@ -35,9 +36,6 @@ public class Ant extends BaseAgent{
 		evaluate = evaluate(vector);
 		
 		phase = Phase.EVALUATE;
-		
-		id = _id;
-	
 	}
 	
     private void nextPhase() {
diff --git a/bacteria/BFOSolver.java b/bacteria/BFOSolver.java
new file mode 100644
index 0000000000000000000000000000000000000000..134b54ad7d8820f9e8e66d3bfca17a2b046fa10a
--- /dev/null
+++ b/bacteria/BFOSolver.java
@@ -0,0 +1,59 @@
+package bacteria;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import baseOptiAgent.Result;
+import baseOptiAgent.Solver;
+import eval.Eval;
+
+public class BFOSolver extends Solver{
+
+	public BFOSolver(Eval _eval, int _maxCycle, int _maxEval) {
+		super(_eval, _maxCycle, _maxEval);
+		name = "BFO";
+	}
+
+	@Override
+	public Result solve() {
+		
+		// [PARAM]
+		int nbrAgent = 50;
+		
+		int maxChemotaxis = 100;
+		int maxSwim = 4;
+		double stepSize = 0.1;
+		double dAttractant = 0.1;
+		double wAttractant = 0.2;
+		double hRepellant = 0.1;
+		double wRepellan = 10;
+		double ped = 0.25;
+		int maxRepr = 4;
+		
+		// [INIT]
+		BacEnv env = new BacEnv();
+		
+		List<Bacteria> agents = new ArrayList<Bacteria>();
+		for (int i_agent = 0; i_agent < nbrAgent; i_agent++) {
+			agents.add(new Bacteria(
+					i_agent,
+					eval,
+					env,
+					maxChemotaxis,
+					maxSwim,
+					stepSize,
+					dAttractant,
+					wAttractant,
+					hRepellant,
+					wRepellan,
+					ped,
+					maxRepr
+					));
+		}
+		
+		env.initAgent(agents);
+		
+		return findSolution(agents, env, 4);
+	}
+
+}
diff --git a/bacteria/BacEnv.java b/bacteria/BacEnv.java
new file mode 100644
index 0000000000000000000000000000000000000000..9dfa0b678ae0de86d1eb928e67c66fed29b2c522
--- /dev/null
+++ b/bacteria/BacEnv.java
@@ -0,0 +1,77 @@
+package bacteria;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Comparator;
+import java.util.List;
+import java.util.Random;
+
+import baseOptiAgent.Env;
+
+public class BacEnv extends Env{
+
+	List<Bacteria> agents;
+	
+	public void initAgent(List<Bacteria> _agents) {
+		agents = new ArrayList<Bacteria>(_agents);
+	}
+	
+	public void sortAgents() {
+		Collections.sort(agents, new Comparator<Bacteria>(){
+		    public int compare(Bacteria s1, Bacteria s2) {
+		        return ((Double) s1.getHealth()).compareTo(((Double) s2.getHealth()));
+		    }
+		});
+	}
+	
+	public List<Double> getNewGenValue(int id){
+		if(id < (agents.size() / 2 )) {
+			return agents.get(id).getVector();
+		}
+		return agents.get(id/2).getVector();
+	}
+	
+	public double getNewGenFit(int id){
+		if(id < (agents.size() / 2 )) {
+			return agents.get(id).getFitness();
+		}
+		return agents.get(id/2).getFitness();
+	}
+	
+	public double getNewGenEval(int id){
+		if(id < (agents.size() / 2 )) {
+			return agents.get(id).getEvaluate();
+		}
+		return agents.get(id/2).getEvaluate();
+	}
+	
+	public List<List<Double>> getValues(){
+		List<List<Double>> res = new ArrayList<List<Double>>();
+		for(Bacteria agent : agents) {
+			res.add(agent.getVector());
+		}
+		return res;
+	}
+
+	@Override
+	public double getBestFitness() {
+		double res = agents.get(0).getFitness();
+		for(Bacteria agent: agents) {
+			if (res < agent.getFitness()) {
+				res = agent.getFitness();
+			}
+		}
+		return res;
+	}
+
+	@Override
+	public double getBestEval() {
+		Bacteria res = agents.get(0);
+		for(Bacteria agent: agents) {
+			if (res.getFitness() < agent.getFitness()) {
+				res = agent;
+			}
+		}
+		return res.getEvaluate();
+	}
+}
diff --git a/bacteria/Bacteria.java b/bacteria/Bacteria.java
index 8cea99d4092976940878228c417b7b4309a1f79a..061eaaa0481b40ed03d25771822c8ec0095a3aa4 100644
--- a/bacteria/Bacteria.java
+++ b/bacteria/Bacteria.java
@@ -1,7 +1,248 @@
 package bacteria;
 
+import java.util.ArrayList;
+import java.util.List;
+
 import baseOptiAgent.BaseAgent;
+import bee.BeeEnv;
+import eval.Eval;
 
 public class Bacteria extends BaseAgent{
 
+	private BacEnv env;
+	
+	private List<Double> del;
+	
+	private double health;
+	
+	private Phase phase;
+	
+	private int repCount;
+	
+	// [PARAM]
+	private int maxChemotaxis;
+	private int maxSwim;
+	private double stepSize;
+	
+	private double dAttractant;
+	private double wAttractant;
+	private double hRepellant;
+	private double wRepellant;
+	
+	private int maxRepr;
+	
+	private double ped; // [0,1] -> probability elimination
+	
+	// SWARFMING
+	List<List<Double>> bacteriaValues;
+	
+	// REPRODUCTION
+	List<Double> nextGenValue;
+	double nextGenFit;
+	double nectGenEval;
+	
+	public Bacteria(int _id, Eval _eval, BacEnv _env, 
+			int _maxChemotaxis,
+			int _maxSwim,
+			double _stepSize,
+			double _dAttractant,
+			double _wAttractant,
+			double _hRepellant,
+			double _wRepellant,
+			double _ped,
+			int _maxRepr
+			) {
+		super(_eval, _id);
+		env = _env;
+		
+		maxChemotaxis = _maxChemotaxis;
+		maxSwim = _maxSwim;
+		stepSize = _stepSize;
+		
+		dAttractant = _dAttractant;
+		wAttractant = _wAttractant;
+		hRepellant = _hRepellant;
+		wRepellant = _wRepellant;
+		ped = _ped;
+		maxRepr = _maxRepr;
+		
+		phase = Phase.CHEMOTAXIS;
+		
+		repCount = 0;
+		
+
+		vector = generateRandomVector();
+		evaluate = this.evaluate(vector);
+		fitness = this.fitness(evaluate);
+	}
+	
+	private void generateDel() {
+		del = new ArrayList<Double>();
+		double norm = 0;
+		
+		for(int i = 0; i < eval.getDim(); i++) {
+			del.add((Math.random() - 0.5) * 2);
+			norm += (del.get(i) * del.get(i));
+		}
+		norm = Math.sqrt(norm);
+		for(int i = 0; i < eval.getDim(); i++) {
+			del.set(i, del.get(i)/norm);
+		}
+	}
+	
+	private double computeJcc() {
+		double jcc = 0;
+		
+		for(int i = 0; i < bacteriaValues.size(); i++ ) {
+			
+			double tmp = 0;
+			for(int m = 0; m < eval.getDim(); m++) {
+				tmp += Math.pow(vector.get(m) - bacteriaValues.get(i).get(m), 2);
+			}
+			jcc += (-dAttractant * Math.exp(-wAttractant * tmp));
+		}
+		
+
+		for(int i = 0; i < bacteriaValues.size(); i++ ) {
+			
+			double tmp = 0;
+			for(int m = 0; m < eval.getDim(); m++) {
+				tmp += Math.pow(vector.get(m) - bacteriaValues.get(i).get(m), 2);
+			}
+			jcc += (-hRepellant * Math.exp(-wRepellant * tmp));
+		}
+		
+		return jcc;
+	}
+	
+	private void chemotaxis() {
+
+		int chemo = 0;
+		
+		health = 0;
+		
+		while(chemo < maxChemotaxis) {
+			
+			generateDel();
+
+			double jcc = computeJcc();
+			double jlast = fitness + jcc;
+			
+			int swim = 0;
+			
+			while (chemo < maxChemotaxis && swim < maxSwim && fitness + jcc <= jlast) {
+				swim ++;
+				jlast = fitness + jcc;
+				
+				List<Double> newVector = new ArrayList<Double>();
+				
+				for(int i = 0; i < eval.getDim(); i++) {
+					newVector.add(vector.get(i) + stepSize * del.get(i));
+				}
+				
+				boundValue(newVector);
+				compareAndUpdate(newVector);
+				jcc = computeJcc();
+				health = getHealth() + fitness + jcc;
+
+				
+			}
+			chemo++;
+		}
+	}
+	
+	private void reproduction() {
+		vector = nextGenValue;
+		evaluate = nectGenEval;
+		fitness = nextGenFit;
+		repCount ++;
+	}
+	
+	private void elimination() {
+		
+		if(repCount >= maxRepr) {
+			return;
+		}
+		repCount = 0;
+		
+		
+		// Elimination
+		if(Math.random() > ped) {
+			// PASS
+		}
+		else {
+			vector = generateRandomVector();
+			evaluate = this.evaluate(vector);
+			fitness = this.fitness(evaluate);
+		}
+	}
+	
+	private void nextPhase() {
+		if(phase == Phase.CHEMOTAXIS) {
+			phase = Phase.ENV;
+		}
+		else if (phase == Phase.ENV) {
+			phase = Phase.REPRODUCTION;
+		}
+		else if (phase == Phase.REPRODUCTION) {
+			phase = Phase.ELIMINATION;
+		}
+		else {
+			phase = Phase.CHEMOTAXIS;
+		}
+	}
+	
+	@Override
+	public void perceive() {
+		if(phase == Phase.CHEMOTAXIS) {
+			bacteriaValues = env.getValues();
+		}
+		else if (phase == Phase.ENV) {
+			
+		}
+		else if (phase == Phase.REPRODUCTION) {
+			nextGenValue = env.getNewGenValue(id);
+			nextGenFit = env.getNewGenFit(id);
+			nectGenEval = env.getNewGenEval(id);
+		}
+		else {
+
+		}
+	}
+	
+	@Override
+	public void act() {
+		if(id == 0) {
+			System.out.println(" ");
+			System.out.println(" ");
+			System.out.println(" ");
+		}
+		System.out.println(this);
+		if(phase == Phase.CHEMOTAXIS) {
+			chemotaxis();
+		}
+		else if (phase == Phase.ENV) {
+			if(id == 0) {
+				env.sortAgents();
+			}
+		}
+		else if (phase == Phase.REPRODUCTION) {
+			reproduction();
+		}
+		else {
+			elimination();
+		}
+		nextPhase();
+	}
+
+	public double getHealth() {
+		return health;
+	}
+	
+	@Override
+	public String toString() {
+		return "["+id+"] Eval / Fit -> "+this.evaluate+" / "+this.fitness+"\n"
+				+ "Vec -> "+this.vector;
+	}
+	
 }
diff --git a/bacteria/Phase.java b/bacteria/Phase.java
new file mode 100644
index 0000000000000000000000000000000000000000..ba82f09dc753a1b173eea3a249473ebee20e7275
--- /dev/null
+++ b/bacteria/Phase.java
@@ -0,0 +1,8 @@
+package bacteria;
+
+public enum Phase {
+	CHEMOTAXIS,
+	ENV,
+	REPRODUCTION,
+	ELIMINATION
+}
diff --git a/baseOptiAgent/BaseAgent.java b/baseOptiAgent/BaseAgent.java
index 6f3cc37252f75b36dc0b0936f9c5495f3835b86f..7fe08b335bb1f55854caefa0e745ead556bbb92e 100644
--- a/baseOptiAgent/BaseAgent.java
+++ b/baseOptiAgent/BaseAgent.java
@@ -16,12 +16,17 @@ public abstract class BaseAgent extends Agent{
 	
 	protected int id;
 	
+	public BaseAgent(Eval _eval, int _id) {
+		eval = _eval;
+		id = _id;
+	}
+	
 	protected void boundValue(List<Double> vector) {
 		for(int i = 0; i < vector.size(); i++) {
 			if (vector.get(i) > eval.getMax(i)) {
 				vector.set(i, eval.getMax(i));
 			}
-			else if (vector.get(i) > eval.getMax(i)) {
+			else if (vector.get(i) < eval.getMin(i)) {
 				vector.set(i, eval.getMin(i));
 			}
 		}
diff --git a/baseOptiAgent/Ihm.java b/baseOptiAgent/Ihm.java
index 5306e9cf70f43ddf68e645ed70d6f1d23484a0a8..bd97c55f1e7e505f89f59c0202cc4a7410253082 100644
--- a/baseOptiAgent/Ihm.java
+++ b/baseOptiAgent/Ihm.java
@@ -2,43 +2,63 @@ package baseOptiAgent;
 
 import java.io.FileWriter;
 import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
 import java.util.stream.Stream;
 
+import aabc.ABeeSolver;
 import amakaque.SMSolver;
 import ant.AntSolver;
+import bacteria.BFOSolver;
 import bee.BeeSolver;
 import eval.Eval;
+import eval.fun.AxisParallelHyper_Ellipsoid;
+import eval.fun.Beale;
+import eval.fun.Cigar;
 import eval.fun.Rastrigin;
+import eval.fun.SchwefelFunction1_2;
+import firefly.FASolver;
 
 public class Ihm {
 	public static void main(String[] args) {
+		
+		// [PARAM]
+		
 		//Eval eval = new StepFunction();
 		//Eval eval = new SchwefelFunction1_2();
 		//Eval eval = new SchwefelFunction();
 		Eval eval = new Rastrigin();
+		//Eval eval = new Cigar();
+		//Eval eval = new AxisParallelHyper_Ellipsoid();
+		//Eval eval = new Beale();
 		
-		int maxCycle = 200000;
-		int maxEval = 1000000;
-
-		Solver solver = new SMSolver(eval, maxCycle, maxEval);
+		int maxCycle = 200_000;
+		int maxEval = 1_000_000;
+		
+		/*
+		// [INIT]
+		//Solver solver = new SMSolver(eval, maxCycle, maxEval);
 		//Solver solver = new BeeSolver(eval, maxCycle, maxEval);
 		//Solver solver = new AntSolver(eval, maxCycle, maxEval);
+		//Solver solver = new ABeeSolver(eval, maxCycle, maxEval);
+		Solver solver = new FASolver(eval, maxCycle, maxEval);
 		
+		// [SOLVING]
 		Result res = solver.solve();
 		
+		
+		// [RESULT]
+		
 		System.out.println("Cycle : "+res.totalCycle+" Out of "+maxCycle);
 		System.out.println("Eval : "+res.totalEval+" Out of "+maxEval);
 		System.out.println("Solution found "+res.optiFound);
 		
-		/*
-		System.out.println("Solution : ");
-		for (Integer name: res.cycle.keySet()) {
-		    System.out.println(name + " " + res.cycle.get(name));
-		}
+		writeEval(res);
 		*/
 		
-		writeEval(res);
-	
+
+		
+		startAll(maxCycle, maxEval);
 	}
 	
 	private static void writeEval(Result res) {
@@ -53,8 +73,69 @@ public class Ihm {
 			csvWriter.flush();
 			csvWriter.close();
 		} catch (IOException e) {
-			// TODO Auto-generated catch block
 			e.printStackTrace();
 		}
 	}
+	
+	private static void startAll(int maxCycle, int maxEval) {
+		//Eval eval = new StepFunction();
+		//Eval eval = new SchwefelFunction1_2();
+		//Eval eval = new SchwefelFunction();
+		Eval eval = new Rastrigin();
+		//Eval eval = new Cigar();
+		//Eval eval = new AxisParallelHyper_Ellipsoid();
+		//Eval eval = new Beale();
+		
+
+		eval = new SchwefelFunction1_2();
+		Solver solver = new SMSolver(eval, maxCycle, maxEval);
+		Result res = solver.solve();
+		writeEval(res);
+		
+		eval = new SchwefelFunction1_2();
+		solver = new BeeSolver(eval, maxCycle, maxEval);
+		res = solver.solve();
+		writeEval(res);
+		
+		eval = new SchwefelFunction1_2();
+		solver = new AntSolver(eval, maxCycle, maxEval);
+		res = solver.solve();
+		writeEval(res);
+		
+		eval = new SchwefelFunction1_2();
+		solver = new ABeeSolver(eval, maxCycle, maxEval);
+		res = solver.solve();
+		writeEval(res);
+		
+		eval = new SchwefelFunction1_2();
+		solver = new FASolver(eval, maxCycle, maxEval);
+		res = solver.solve();
+		writeEval(res);
+		
+		eval = new SchwefelFunction1_2();
+		solver = new BFOSolver(eval, maxCycle, maxEval);
+		res = solver.solve();
+		writeEval(res);
+		
+		System.out.println(res.optiFound);
+		System.out.println(res.totalCycle);
+		System.out.println(res.totalEval);
+		System.out.println(res.cycle);
+		System.out.println(res.cycle.get(0).getBestSolution());
+		System.out.println(res.cycle.get(0).getEval());
+		
+		System.out.println("Done");
+	}
+	
+	private void benchmarkAlgo(int maxCycle, int maxEval) {
+		
+		int nbrTry = 100;
+				
+		for(int i = 0; i < nbrTry; i++) {
+			Eval eval = new Rastrigin();
+			Solver solver = new SMSolver(eval, maxCycle, maxEval);
+			Result res = solver.solve();
+		}
+		
+	}
 }
diff --git a/baseOptiAgent/Solver.java b/baseOptiAgent/Solver.java
index 4fe866f9fdbdbf75ecad6881c1d3c6cbabc115e6..f7bec412d524251a038ec92860038602ec0bd8e4 100644
--- a/baseOptiAgent/Solver.java
+++ b/baseOptiAgent/Solver.java
@@ -70,7 +70,6 @@ public abstract class Solver {
 		res.totalCycle = cycle;
 		res.totalEval = eval.getCount();
 		res.optiFound = Math.abs(env.getBestEval()-eval.getObjective())<=eval.getErrorDelta();
-		
 		return res;
 	}
 	
diff --git a/bee/Bee.java b/bee/Bee.java
index a1ee2cefcc5fc5f4d2a35178608ec8b4ad3b144a..07a36ffeb63d508a4d76d304ccb8984e5136f514 100644
--- a/bee/Bee.java
+++ b/bee/Bee.java
@@ -23,8 +23,8 @@ public class Bee extends BaseAgent{
 	//List<Double> randomAgent;
 
 	public Bee(int _id, Eval _eval, BeeEnv _env, int _maxCount) {
-		id = _id;
-		eval = _eval;
+		super(_eval, _id);
+
 		env = _env;
 		
 		maxCount = _maxCount;
@@ -81,6 +81,9 @@ public class Bee extends BaseAgent{
 		if (!res) {
 			stuckCount ++;
 		}
+		else {
+			stuckCount = 0;
+		}
 	}
 	
 	private void onlookerPhase() {
diff --git a/eval/fun/AxisParallelHyper_Ellipsoid.java b/eval/fun/AxisParallelHyper_Ellipsoid.java
new file mode 100644
index 0000000000000000000000000000000000000000..3eaf94ddd9b6c3c692f122fbb2401bd7bdb32968
--- /dev/null
+++ b/eval/fun/AxisParallelHyper_Ellipsoid.java
@@ -0,0 +1,37 @@
+package eval.fun;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.concurrent.atomic.AtomicInteger;
+
+import eval.Eval;
+
+public class AxisParallelHyper_Ellipsoid extends Eval{
+
+	public AxisParallelHyper_Ellipsoid() {
+		count = new AtomicInteger(0);
+		
+		dim = 30;
+		objective = (double) 0;
+		errorDelta = 0.000_01;
+		
+		min = new ArrayList<Double>();
+		max = new ArrayList<Double>();
+		for (int i = 0; i < dim; i++) {
+			min.add((double) -5.12);
+			max.add((double) 5.12);
+		}
+	}
+
+	@Override
+	public double evaluate(List<Double> value) {
+		count.getAndIncrement();
+		double result = 0;
+		
+		for(int i_dim = 0; i_dim < dim; i_dim++ ) {
+			result += (i_dim * value.get(i_dim) * value.get(i_dim));
+		}
+		
+		return result;
+	}
+}
\ No newline at end of file
diff --git a/eval/fun/Beale.java b/eval/fun/Beale.java
new file mode 100644
index 0000000000000000000000000000000000000000..f11a3aa16f68b6b4e9e8b4a3cf64e0dde90b3f07
--- /dev/null
+++ b/eval/fun/Beale.java
@@ -0,0 +1,39 @@
+package eval.fun;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.concurrent.atomic.AtomicInteger;
+
+import eval.Eval;
+
+public class Beale extends Eval{
+
+	public Beale() {
+		count = new AtomicInteger(0);
+		
+		dim = 2;
+		objective = (double) 0;
+		errorDelta = 0.000_01;
+		
+		min = new ArrayList<Double>();
+		max = new ArrayList<Double>();
+		for (int i = 0; i < dim; i++) {
+			min.add((double) -4.5);
+			max.add((double) 4.5);
+		}
+	}
+
+	@Override
+	public double evaluate(List<Double> value) {
+		count.getAndIncrement();
+		
+		double x = value.get(0);
+		double y = value.get(1);
+		
+		double result = 
+				Math.pow(1.5 - x * (1 - y), 2)
+				+ Math.pow(2.25 - x * (1 - y * y), 2)
+				+ Math.pow(2.625 - x * (1 - y * y * y), 2);
+		return result;
+	}
+}
\ No newline at end of file
diff --git a/eval/fun/Cigar.java b/eval/fun/Cigar.java
new file mode 100644
index 0000000000000000000000000000000000000000..74dfc512a7ed799b50dc0106dcd05c22bea96bb6
--- /dev/null
+++ b/eval/fun/Cigar.java
@@ -0,0 +1,39 @@
+package eval.fun;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.concurrent.atomic.AtomicInteger;
+
+import eval.Eval;
+
+public class Cigar extends Eval{
+
+	
+	public Cigar() {
+		count = new AtomicInteger(0);
+		
+		dim = 30;
+		objective = (double) 0;
+		errorDelta = 0.000_01;
+		
+		min = new ArrayList<Double>();
+		max = new ArrayList<Double>();
+		for (int i = 0; i < dim; i++) {
+			min.add((double) -10);
+			max.add((double) 10);
+		}
+	}
+
+	@Override
+	public double evaluate(List<Double> value) {
+		count.getAndIncrement();
+		double result = value.get(0) * value.get(0);
+		
+		double other = 0;
+		for(int i_dim = 0; i_dim < dim; i_dim++ ) {
+			other += value.get(i_dim) * value.get(i_dim);
+		}
+		
+		return result + 100_000 * other;
+	}
+}
diff --git a/eval/fun/SchwefelFunction1_2.java b/eval/fun/SchwefelFunction1_2.java
index b4a3fecdf7eb79e39bbbd3f0add92425a2bc6708..f20c23a8339ec2a9a173c0b7809445b23222f4bf 100644
--- a/eval/fun/SchwefelFunction1_2.java
+++ b/eval/fun/SchwefelFunction1_2.java
@@ -39,6 +39,5 @@ public class SchwefelFunction1_2 extends Eval{
 		
 		return result;
 	}
-	
 
 }
diff --git a/eval/twoDFun/Squared.java b/eval/twoDFun/Squared.java
new file mode 100644
index 0000000000000000000000000000000000000000..e540ba4f5626e4d36daeb7829e380912e196ae26
--- /dev/null
+++ b/eval/twoDFun/Squared.java
@@ -0,0 +1,36 @@
+package eval.twoDFun;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.concurrent.atomic.AtomicInteger;
+
+import eval.Eval;
+
+public class Squared extends Eval{
+
+	public Squared() {
+		count = new AtomicInteger(0);
+		
+		dim = 2;
+		objective = (double) 0;
+		errorDelta = 0.000_01;
+		
+		min = new ArrayList<Double>();
+		max = new ArrayList<Double>();
+		for (int i = 0; i < dim; i++) {
+			min.add(-500.0);
+			max.add(500.0);
+		}
+	}
+
+	@Override
+	public double evaluate(List<Double> value) {
+		count.getAndIncrement();
+		
+		double x = value.get(0);
+		double y = value.get(1);
+		
+		double result = Math.abs(x) * Math.abs(y) + Math.abs(x) + Math.abs(y);
+		return result;
+	}
+}
\ No newline at end of file
diff --git a/firefly/Calibration.java b/firefly/Calibration.java
new file mode 100644
index 0000000000000000000000000000000000000000..f0c874f2f2c67e8daec3b736f44e12326de76c1d
--- /dev/null
+++ b/firefly/Calibration.java
@@ -0,0 +1,103 @@
+package firefly;
+
+import java.io.FileWriter;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+
+import baseOptiAgent.BaseAgent;
+import baseOptiAgent.Cycle;
+import baseOptiAgent.Result;
+import baseOptiAgent.Solver;
+import eval.Eval;
+import eval.fun.Rastrigin;
+
+public class Calibration {
+	public static void main(String[] args) {
+		
+		// [PARAM]
+		int maxCycle = 200_000;
+		int maxEval = 1_000_000;
+		
+		
+		double wr = 0;
+		double afe = 0;
+		double bestSol = 0;
+		
+		int nbrTry = 10;
+
+		// [INIT]
+		int nbrAgent = 50;
+		double bMax = 1; // [0, 1]
+		double y = 0.2; // [0.1, 10] théoriquement [0, inf)
+		double randomAlpha = 1; // [0, 1]
+		
+		for (int i = 0; i < nbrTry; i++) {
+			
+			//Eval eval = new StepFunction();
+			//Eval eval = new SchwefelFunction1_2();
+			//Eval eval = new SchwefelFunction();
+			Eval eval = new Rastrigin();
+			//Eval eval = new Cigar();
+			//Eval eval = new AxisParallelHyper_Ellipsoid();
+			//Eval eval = new Beale();
+			
+			// [INIT]
+			FAEnv env = new FAEnv(bMax, y);
+			
+			List<Firefly> agents = new ArrayList<Firefly>();
+			for (int i_agent = 0; i_agent < nbrAgent; i_agent++) {
+				agents.add(new Firefly(i_agent, eval, env, randomAlpha));
+			}
+			env.initAgent(agents);
+			
+			solve(env, agents, eval, maxCycle, maxEval);
+			
+			if(Math.abs(env.getBestEval()-eval.getObjective())<=eval.getErrorDelta()) {
+				wr++;
+			}
+			afe += eval.getCount();
+			bestSol += env.getBestEval();
+			System.out.println("done");
+			
+		}
+		wr = wr / (double) nbrTry;
+		afe = afe / (double) nbrTry;
+		bestSol = bestSol / (double) nbrTry;
+		System.out.println("wr " + wr);
+		System.out.println("afe "+afe);
+		System.out.println("best sol "+bestSol);
+		
+	}
+	
+	private static void solve(FAEnv env, List<Firefly> agents, Eval eval, int maxCycle, int maxEval) {
+		int cycleModulo = 2;
+		int cycle = 0;
+		
+		double bestEval = env.getBestEval();
+		
+		do  {
+			for(int i = 0; i < cycleModulo; i++) {
+				for (BaseAgent agent : agents) {
+					agent.perceive();
+				}
+				for (BaseAgent agent : agents) {
+					agent.decide();
+					agent.act();
+				}
+			}
+			
+			double nextEval = env.getBestEval();
+			
+			if (nextEval < bestEval) {
+				bestEval = nextEval;
+			}
+			
+			cycle ++;
+		} while(
+				Math.abs(env.getBestEval()-eval.getObjective())>eval.getErrorDelta()
+				&& cycle < maxCycle
+				&& eval.getCount() < maxEval
+				);
+	}
+}
diff --git a/firefly/FAEnv.java b/firefly/FAEnv.java
new file mode 100644
index 0000000000000000000000000000000000000000..e859b353ff0f3fe9c934ddbc236384468eb7d867
--- /dev/null
+++ b/firefly/FAEnv.java
@@ -0,0 +1,90 @@
+package firefly;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import baseOptiAgent.Env;
+
+public class FAEnv extends Env{
+
+	private List<Firefly> agents;
+	private List<List<Double>> attractiveness;
+	
+	private double bMax;
+	private double y;
+	
+	public FAEnv(double _bMax, double _y) {
+		bMax = _bMax;
+		y = _y;
+	}
+	
+	
+	public void initAgent(List<Firefly> _agents) {
+		agents = new ArrayList<Firefly>(_agents);
+	}
+	
+	private double distance(List<Double> a, List<Double> b) {
+		double res = 0;
+		for(int i = 0; i < a.size(); i++) {
+			res += Math.pow(a.get(i) - b.get(i), 2);
+		}
+		return Math.sqrt(res);
+	}
+	
+	public void computeAttractiveness() {
+		attractiveness = new ArrayList<List<Double>>();
+		
+		for(int i = 0; i < agents.size(); i++) {
+			List<Double> tmp = new ArrayList<Double>();
+			for(int j = 0; j < i; j++) {
+				double dist = distance(agents.get(i).getVector(), agents.get(j).getVector());
+				tmp.add(bMax * Math.exp(-y * dist));
+			}
+			attractiveness.add(tmp);
+		}
+		
+	}
+	
+	public List<List<Double>> getAttractiveness() {
+		return attractiveness;
+	}
+	
+	public List<Double> getFitness() {
+		List<Double> res = new ArrayList<Double>();
+		for(int i = 0; i < agents.size(); i++) {
+			res.add(agents.get(i).getFitness());
+		}
+		return res;		
+	}
+	
+	public List<List<Double>> getValues(){
+		List<List<Double>> res = new ArrayList<List<Double>>();
+		for(int i = 0; i < agents.size(); i++) {
+			res.add(agents.get(i).getVector());
+		}
+		return res;		
+		
+	}
+	
+	@Override
+	public double getBestFitness() {
+		double res = agents.get(0).getFitness();
+		for(Firefly agent: agents) {
+			if (res < agent.getFitness()) {
+				res = agent.getFitness();
+			}
+		}
+		return res;
+	}
+
+	@Override
+	public double getBestEval() {
+		Firefly res = agents.get(0);
+		for(Firefly agent: agents) {
+			if (res.getFitness() < agent.getFitness()) {
+				res = agent;
+			}
+		}
+		return res.getEvaluate();
+	}
+}
diff --git a/firefly/FASolver.java b/firefly/FASolver.java
new file mode 100644
index 0000000000000000000000000000000000000000..4652b6e60c90fe730b4fd957254a059c87563950
--- /dev/null
+++ b/firefly/FASolver.java
@@ -0,0 +1,41 @@
+package firefly;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import baseOptiAgent.Result;
+import baseOptiAgent.Solver;
+import eval.Eval;
+
+public class FASolver extends Solver{
+
+	public FASolver(Eval _eval, int _maxCycle, int _maxEval) {
+		super(_eval, _maxCycle, _maxEval);
+		name = "Firefly";
+	}
+
+	@Override
+	public Result solve() {
+		
+		// [PARAM]
+		int nbrAgent = 10;
+		double bMax = 0.2; // [0, 1]
+		double y = 1; // [0.1, 10] théoriquement [0, inf)
+		double randomAlpha = 0.5; // [0, 1]
+		
+		// [INIT]
+		FAEnv env = new FAEnv(bMax, y);
+		
+		List<Firefly> agents = new ArrayList<Firefly>();
+		for (int i_agent = 0; i_agent < nbrAgent; i_agent++) {
+			agents.add(new Firefly(i_agent, eval, env, randomAlpha));
+		}
+		
+		env.initAgent(agents);
+		
+		Result res = findSolution(agents, env, 2);
+		
+		return res;
+	}
+
+}
diff --git a/firefly/Firefly.java b/firefly/Firefly.java
new file mode 100644
index 0000000000000000000000000000000000000000..a25254831d5087d352c21333f0f4690d360e4ed4
--- /dev/null
+++ b/firefly/Firefly.java
@@ -0,0 +1,119 @@
+package firefly;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import baseOptiAgent.BaseAgent;
+import eval.Eval;
+
+public class Firefly extends BaseAgent{
+	
+	FAEnv env;
+	
+	Phase phase;
+	
+	double randomAlpha;
+	
+	//CYCLE
+	List<List<Double>> agents;
+	List<List<Double>> attractiveness;
+	List<Double> agentsFit;
+	
+
+	public Firefly(int _id, Eval _eval, FAEnv _env, double _randomAlpha) {
+		super(_eval, _id);
+
+		env = _env;
+		
+		randomAlpha = _randomAlpha;
+		
+		phase = Phase.COMPUTE_DIST;
+		
+		vector = generateRandomVector();
+		evaluate = this.evaluate(vector);
+		fitness = this.fitness(evaluate);
+	}
+	
+	private void nextPhase() {
+		if (phase == Phase.COMPUTE_DIST) {
+			phase = Phase.CYCLE;
+		}
+		else {
+			phase = Phase.COMPUTE_DIST;
+		}
+	}
+	
+	@Override
+	public void perceive() {
+		if(phase == Phase.COMPUTE_DIST) {
+			if(id == 0) {
+				
+			}
+		}
+		else {
+			agents = env.getValues();
+			attractiveness = env.getAttractiveness();
+			agentsFit = env.getFitness();
+		}
+	}
+	
+	@Override
+	public void act() {
+		if(phase == Phase.COMPUTE_DIST) {
+			if(id == 0) {
+				env.computeAttractiveness();
+			}
+		}
+		else {
+			mainAct();
+		}
+		nextPhase();
+	}
+	
+	private void mainAct() {
+		int update = 0;
+		
+		for(int i = 0; i < agents.size(); i++ ) {
+
+			if( i != id &&  agentsFit.get(i) > fitness ) {
+				
+				double att;
+				if(i<id) {
+					att = attractiveness.get(id).get(i);
+				}
+				else {
+					att = attractiveness.get(i).get(id);
+				}
+				
+				List<Double> newvector = new ArrayList<Double>();
+				
+				for(int dim = 0; dim < eval.getDim(); dim ++) {
+					newvector.add(
+							vector.get(dim) // TODO Both variant without (1-att)
+							+ att * (agents.get(i).get(dim) - vector.get(dim))
+							+ (Math.random()-0.5) * randomAlpha * (eval.getMax(dim) - eval.getMin(dim))
+							);
+					update ++;
+				}
+				this.boundValue(newvector);
+				this.compareAndUpdate(newvector);
+			}
+		}
+		
+		if(update == 0) {
+			List<Double> newvector = new ArrayList<Double>();
+			
+			
+			for(int dim = 0; dim < eval.getDim(); dim ++) {
+				newvector.add(
+						vector.get(dim)
+						+ (Math.random()-0.5)* randomAlpha
+						);
+				update ++;
+			}
+			this.boundValue(newvector);
+			this.compareAndUpdate(newvector);
+		}
+		
+	}
+}
diff --git a/firefly/Phase.java b/firefly/Phase.java
new file mode 100644
index 0000000000000000000000000000000000000000..d975c2a538f21f86e6ccc7eea0456cc6287db459
--- /dev/null
+++ b/firefly/Phase.java
@@ -0,0 +1,6 @@
+package firefly;
+
+public enum Phase {
+	COMPUTE_DIST,
+	CYCLE
+}
diff --git a/smac/Main.java b/smac/Main.java
new file mode 100644
index 0000000000000000000000000000000000000000..cd1a870d8d06588cbe801de22c271be73318d4df
--- /dev/null
+++ b/smac/Main.java
@@ -0,0 +1,42 @@
+package smac;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import eval.Eval;
+import eval.twoDFun.Squared;
+import mas.core.Agent;
+import mas.core.Cyclable;
+import mas.environment.TwoDContinuosGrid;
+import mas.implementation.schedulers.variations.TwoDCycling;
+import mas.ui.MainWindow;
+import mas.ui.SchedulerToolbar;
+
+public class Main {
+
+    public static void main(String[] args) {
+
+        int nAgents = 50;
+        double perception = 50.0;
+        double maxDensity = 0.3;
+        int maxInactivity = 5;
+        double bMax = 1;
+        double vision = 1;
+
+        List<Smagent> agents = new ArrayList<Smagent>();
+        Eval eval = new Squared();
+        
+        SmacEnv env = new SmacEnv(perception);
+
+        for(int i = 0; i<nAgents ; i++){
+        	agents.add(new Smagent(eval,i, env, nAgents, maxDensity, maxInactivity, bMax, vision));
+        }
+        
+        env.initAgents(agents);
+
+        TwoDCycling scheduler = new TwoDCycling(agents.toArray(new Smagent[agents.size()]));
+
+        MainWindow.instance();
+        MainWindow.addToolbar(new SchedulerToolbar("Amas", scheduler));
+    }
+}
diff --git a/smac/Phase.java b/smac/Phase.java
new file mode 100644
index 0000000000000000000000000000000000000000..43360ab6613cd41dc5b386003997c37c53b78c43
--- /dev/null
+++ b/smac/Phase.java
@@ -0,0 +1,6 @@
+package smac;
+
+public enum Phase {
+	CYCLING,
+	DIST
+}
diff --git a/smac/SmacEnv.java b/smac/SmacEnv.java
new file mode 100644
index 0000000000000000000000000000000000000000..3eae3d83818c6db88e31db0b9964d16e5e5882b2
--- /dev/null
+++ b/smac/SmacEnv.java
@@ -0,0 +1,91 @@
+package smac;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import baseOptiAgent.Env;
+
+public class SmacEnv extends Env{
+
+	private List<Smagent> agents;
+	private List<List<Double>> distance;
+	
+	private double maxDist;
+	
+	public SmacEnv(double _maxDist) {
+		maxDist = _maxDist;
+	}
+	
+	public void initAgents(List<Smagent> _agents) {
+		agents = _agents;
+	}
+	
+	private double dist(List<Double> a, List<Double> b) {
+		double res = 0;
+		for(int i = 0; i < a.size(); i++) {
+			res += Math.pow(a.get(i) - b.get(i), 2);
+		}
+		return Math.sqrt(res);
+	}
+	
+	public void computeDistance() {
+		distance = new ArrayList<List<Double>>();
+		for(int i_agent = 0; i_agent < agents.size(); i_agent ++) {
+			List<Double> tmpDist = new ArrayList<Double>();
+			for(int j_agent = 0; j_agent < agents.size(); j_agent ++) {
+				tmpDist.add(0.0);
+			}
+			distance.add(tmpDist);
+		}
+		
+		for(int i_agent = 0; i_agent < agents.size(); i_agent ++) {
+			for(int j_agent = 0; j_agent < i_agent; j_agent ++) {
+				double dist = dist(agents.get(i_agent).getVector(), agents.get(j_agent).getVector());
+				distance.get(i_agent).set(j_agent, dist);
+				distance.get(j_agent).set(i_agent, dist);
+			}
+		}
+	}
+	
+	public List<List<Double>> getNei(int id){
+		List<List<Double>> res = new ArrayList<List<Double>>();
+		for(int i_agent = 0; i_agent < agents.size(); i_agent ++) {
+			if(distance.get(id).get(i_agent) <= maxDist) {
+				res.add(agents.get(i_agent).getVector());
+			}
+		}
+		return res;
+	}
+	
+	public List<Double> getFit(int id){
+		List<Double> res = new ArrayList<Double>();
+		for(int i_agent = 0; i_agent < agents.size(); i_agent ++) {
+			if(distance.get(id).get(i_agent) <= maxDist) {
+				res.add(agents.get(i_agent).getFitness());
+			}
+		}
+		return res;
+	}
+	
+	@Override
+	public double getBestFitness() {
+		double res = agents.get(0).getFitness();
+		for(Smagent agent: agents) {
+			if (res < agent.getFitness()) {
+				res = agent.getFitness();
+			}
+		}
+		return res;
+	}
+
+	@Override
+	public double getBestEval() {
+		Smagent res = agents.get(0);
+		for(Smagent agent: agents) {
+			if (res.getFitness() < agent.getFitness()) {
+				res = agent;
+			}
+		}
+		return res.getEvaluate();
+	}
+}
diff --git a/smac/Smagent.java b/smac/Smagent.java
new file mode 100644
index 0000000000000000000000000000000000000000..42dd93d7c487a9c41f77b62bc8e54a1f943d6e47
--- /dev/null
+++ b/smac/Smagent.java
@@ -0,0 +1,209 @@
+package smac;
+
+
+import java.util.ArrayList;
+import java.util.List;
+
+import baseOptiAgent.BaseAgent;
+import eval.Eval;
+import mas.ui.VUI;
+import mas.ui.drawables.DrawableImage;
+
+public class Smagent extends BaseAgent{
+	
+	private int nbrAgent;
+	
+    private DrawableImage image;
+    
+    private double maxDensity;
+    
+    private Phase phase;
+    
+    private SmacEnv env;
+    
+    private int countInactivity;
+    private int maxInactivity;
+    
+    private double bMax;
+    private double vision;
+    
+    // PHASE CYCLING
+    private List<List<Double>> neiValue;
+    private List<Double> neiFit;
+	
+	public Smagent(Eval _eval, int _id, SmacEnv _env, 
+			int _nbrAgent,
+			double _maxDensity,
+			int _maxInactivity,
+			double _bMax,
+			double _vision
+			
+			) {
+		super(_eval, _id);
+		
+		env = _env;
+		
+		maxInactivity = _maxInactivity;
+		bMax = _bMax;
+		vision = _vision;
+		
+		vector = generateRandomVector();
+		evaluate = this.evaluate(vector);
+		fitness = this.fitness(evaluate);
+
+        image = VUI.get().createImage(vector.get(0), vector.get(1), "example/randomants/ressources/ant.png");
+        
+        nbrAgent = _nbrAgent;
+        maxDensity = _maxDensity;
+        
+        phase = Phase.DIST;
+        
+        countInactivity = 0;
+	}
+
+	@Override
+	public void perceive() {
+		if(phase == Phase.DIST) {
+			if(id == 0) {
+				env.computeDistance();
+			}
+		}
+		else {
+			neiValue = env.getNei(id);
+			neiFit = env.getFit(id);
+		}
+	}
+	
+	public void actionPhase() {
+		/*
+		 * neiValue List<List<Double>> -> Contain all neighbors vectors 
+		 * neiFit List<Double> -> Contain all neighbors fitness
+		 */
+
+		int update = 0; // count if the agent will update himself
+		// TODO : REWORK UPDATE
+		
+		double randStepSize = 1; 
+		
+		if((double) neiValue.size()/ (double) nbrAgent < maxDensity) { // Seuil densité bas
+			
+			
+			for(int i = 0; i < neiValue.size(); i++) {
+				
+				/*
+				 * ### Go closer to other agents ###
+				 * if other has better fitness
+				 * - compute attractivness ( FA with fitness ?)
+				 * 
+				 * Generate new solution : currentPos + attractivness * (other - currentPos) +- randomValue
+				 * 
+				 * Evaluate new solution, if better use it instead of the current one
+				 */
+				
+				if(neiFit.get(i) > fitness) { // Other have better fitness
+					
+					// TODO : compute attractiveness
+					double attractiveness = bMax * Math.exp(-vision * 1 / neiFit.get(i)); 
+					
+					List<Double> newvector = new ArrayList<Double>();
+					
+					for(int dim = 0; dim < eval.getDim(); dim ++) {
+						newvector.add(
+								vector.get(dim) // TODO Variant with vector.get(dim) * (1 - attractiveness)
+								+ attractiveness * (neiValue.get(i).get(dim) - vector.get(dim))
+								+ (Math.random()-0.5) * randStepSize
+								);
+					}
+					boundValue(newvector); // minValue <= newvector <= maxValue 
+					if (compareAndUpdate(newvector)) {//Evaluate, update if better
+						update ++;
+					}; 
+				}
+			}
+			
+			if(neiValue.size() == 0) { // no one's arround
+				/*
+				 * ### Explore around ###
+				 * Generate new solution : currentPos +- randomValue
+				 * Evaluate new solution, if better use it instead of the current one
+				 */
+				List<Double> newvector = new ArrayList<Double>();
+				
+				for(int dim = 0; dim < eval.getDim(); dim ++) {
+					newvector.add(
+							vector.get(dim)
+							+ (Math.random()-0.5) * randStepSize
+							);
+				}
+				boundValue(newvector); // minValue <= newvector <= maxValue 
+				if (compareAndUpdate(newvector)) {//Evaluate, update if better
+					update ++;
+				}; 
+			}
+		}
+		else { // TODO : Seuil densité haut (& not local best ?)
+			for(int i = 0; i < neiValue.size(); i++) {
+				
+				/*
+				 * compute the repulsion
+				 * 
+				 * Generate new solution : currentPos + repulsion * (other - currentPos) +- randomValue
+				 * 
+				 * Evaluate new solution, and use it
+				 */
+
+			}
+		}
+		
+		if (update == 0) {
+			countInactivity ++;
+		}
+		else {
+			countInactivity = 0;
+		}
+		
+		if (countInactivity > maxInactivity) { // TODO : no update in a while & not best
+			/*
+			 * Find a new place to go : (?)
+			 * 	- Randomly generate new solution <- THIS
+			 *  - Go forward Global best solution
+			 *  - Find promising place
+			 */
+			vector = generateRandomVector();
+			evaluate = this.evaluate(vector);
+			fitness = this.fitness(evaluate);
+		}
+	}
+	
+	
+	private void nextPhase() {
+		if(phase == Phase.DIST) {
+			phase = Phase.CYCLING;
+		}
+		else {
+			phase = Phase.DIST;
+		}
+	}
+	
+	@Override
+	public void act() {
+		if(phase == Phase.DIST) {
+			
+		}
+		else {
+			actionPhase();
+	        image.move(vector.get(0), vector.get(1));
+	        //System.out.println(this);
+		}
+		nextPhase();
+	}
+	
+	
+	@Override
+	public String toString() {
+		return "[AGENT] pos -> "+this.vector.get(0)+" / "+this.vector.get(1)+"\n"
+				+"Fit -> "+fitness+" / "+" Eval -> "+evaluate;
+	}
+	
+
+}