animals are playing arround now
This commit is contained in:
parent
be6e9da50d
commit
27d720dde9
|
|
@ -4,6 +4,8 @@ public class Cell {
|
|||
int posX;
|
||||
int posY;
|
||||
int state;
|
||||
int timeOfLifeSinceCut = 0;
|
||||
int GROWING_TIME = 50;
|
||||
|
||||
public Cell(int x, int y, int lifeState) {
|
||||
posX = x;
|
||||
|
|
@ -26,6 +28,16 @@ public class Cell {
|
|||
state = lifeState;
|
||||
}
|
||||
|
||||
public void updateCell() {
|
||||
if (state == 0) {
|
||||
timeOfLifeSinceCut++;
|
||||
if (timeOfLifeSinceCut > GROWING_TIME) {
|
||||
timeOfLifeSinceCut = 0;
|
||||
state = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public int getState() {
|
||||
return state;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -12,6 +12,11 @@ public class Sheep extends Agent {
|
|||
|
||||
int hunger;
|
||||
Random rand;
|
||||
int height;
|
||||
int width;
|
||||
private final int REPRODUCTION_RADIUS = 1; // Radius within which sheep can reproduce
|
||||
private final double REPRODUCTION_PROBABILITY = 0.1; // Probability of reproduction per turn
|
||||
|
||||
|
||||
Sheep(int x,int y){
|
||||
//first we call the constructor of the superClass(Animal)
|
||||
|
|
@ -35,24 +40,55 @@ public class Sheep extends Agent {
|
|||
} else {
|
||||
hunger++;
|
||||
}
|
||||
height = world.getHeight();
|
||||
width = world.getHeight();
|
||||
|
||||
// Check for reproduction
|
||||
for (Agent neighbor : neighbors) {
|
||||
if (neighbor instanceof Sheep && this.isInArea(neighbor.getX(), neighbor.getY(), REPRODUCTION_RADIUS)) {
|
||||
if (rand.nextDouble() < REPRODUCTION_PROBABILITY) {
|
||||
reproduce(world);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
this.moveRandom();
|
||||
return hunger>10;
|
||||
}
|
||||
|
||||
private void reproduce(Simulator world) {
|
||||
// Find a random adjacent cell
|
||||
int newX = x + rand.nextInt(3) - 1;
|
||||
int newY = y + rand.nextInt(3) - 1;
|
||||
|
||||
// Ensure the new position is within bounds and empty
|
||||
if (newX >= 0 && newX < world.getWidth() && newY >= 0 && newY < world.getHeight() && !world.getOccupied(newX, newY)) {
|
||||
world.setAgent(newX, newY, new Sheep(newX, newY));
|
||||
}
|
||||
}
|
||||
|
||||
private void moveRandom() {
|
||||
int direction = rand.nextInt(4);
|
||||
int nx = x;
|
||||
int ny = y;
|
||||
|
||||
if(direction == 0) {
|
||||
x+=1;
|
||||
nx+=1;
|
||||
}
|
||||
if(direction == 1) {
|
||||
y+=1;
|
||||
ny+=1;
|
||||
}
|
||||
if(direction == 2) {
|
||||
x-=1;
|
||||
nx-=1;
|
||||
}
|
||||
if(direction == 3) {
|
||||
y-=1;
|
||||
ny-=1;
|
||||
}
|
||||
// Ensure the sheep does not move out of bounds
|
||||
if (nx >= 0 && nx < width && ny >= 0 && ny < height) {
|
||||
x = nx;
|
||||
y = ny;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -1,5 +1,6 @@
|
|||
package backend;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
|
||||
import windowInterface.MyInterface;
|
||||
|
||||
|
|
@ -7,13 +8,13 @@ public class Simulator extends Thread {
|
|||
|
||||
private MyInterface mjf;
|
||||
|
||||
private final int COL_NUM = 100;
|
||||
private final int LINE_NUM = 100;
|
||||
private final int COL_NUM = 50;
|
||||
private final int LINE_NUM = 50;
|
||||
private final int LIFE_TYPE_NUM = 4;
|
||||
//Conway Radius : 1
|
||||
private final int LIFE_AREA_RADIUS = 1;
|
||||
//Animal Neighborhood Radius : 5
|
||||
private final int ANIMAL_AREA_RADIUS = 2;
|
||||
private final int ANIMAL_AREA_RADIUS = 3;
|
||||
private ArrayList<Integer> fieldSurviveValues;
|
||||
private ArrayList<Integer> fieldBirthValues;
|
||||
|
||||
|
|
@ -103,17 +104,15 @@ public class Simulator extends Thread {
|
|||
// only modify if sure of what you do
|
||||
// to modify agent behavior, see liveTurn method
|
||||
// in agent classes
|
||||
for(Agent agent : agents) {
|
||||
ArrayList<Agent> neighbors =
|
||||
this.getNeighboringAnimals(
|
||||
agent.getX(),
|
||||
agent.getY(),
|
||||
ANIMAL_AREA_RADIUS);
|
||||
if(!agent.liveTurn(
|
||||
neighbors,
|
||||
this)) {
|
||||
agents.remove(agent);
|
||||
}
|
||||
//Modified because of cross-modifications to the arraylist and java doesn't like that much
|
||||
for (int i = 0; i < agents.size(); i++) {
|
||||
Agent agent = agents.get(i);
|
||||
ArrayList<Agent> neighbors = this.getNeighboringAnimals(agent.getX(), agent.getY(), ANIMAL_AREA_RADIUS);
|
||||
|
||||
if (agent.liveTurn(neighbors, this)) {
|
||||
agents.remove(i);
|
||||
i--; // Adjust the index to account for the removed element
|
||||
}
|
||||
}
|
||||
//then evolution of the field
|
||||
// TODO : apply game rule to all cells of the field
|
||||
|
|
@ -131,7 +130,9 @@ public class Simulator extends Thread {
|
|||
* and the count is in the birth list,
|
||||
* then the cell becomes alive
|
||||
*/
|
||||
world.makeStep();
|
||||
if (!clickActionFlag)
|
||||
world.makeStep();
|
||||
else updateCells();
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
@ -152,7 +153,52 @@ public class Simulator extends Thread {
|
|||
* method called when clicking on a cell in the interface
|
||||
*/
|
||||
public void clickCell(int x, int y) {
|
||||
world.clickCell(x, y);;
|
||||
if (clickActionFlag) {
|
||||
setAgent(x, y);
|
||||
} else {
|
||||
world.clickCell(x, y);;
|
||||
}
|
||||
}
|
||||
|
||||
public void setAgent(int x, int y) {
|
||||
int cellValue = getCell(x, y); // Assuming you have a method getCell(x, y) to retrieve the cell value
|
||||
String agentType = null;
|
||||
int indexOfAgent = 0;
|
||||
for (int i = 0; i < agents.size(); i++) {
|
||||
Agent agent = agents.get(i);
|
||||
if (agent.getX() == x && agent.getY() == y) {
|
||||
if (agent instanceof Sheep) {
|
||||
agentType = "Sheep";
|
||||
} else {
|
||||
agentType = "Wolf";
|
||||
}
|
||||
indexOfAgent = i;
|
||||
}
|
||||
}
|
||||
|
||||
// If the cell is empty (0), set it to 1 (food)
|
||||
if (cellValue == 0 && agentType == null) {
|
||||
setCell(x, y, 1); // Set the cell to indicate food
|
||||
} else if (cellValue == 1) { // If the cell has food (1), replace it with a sheep
|
||||
agents.add(new Sheep(x, y)); // Add a new Sheep object to the agents list
|
||||
setCell(x, y, 0);
|
||||
} else if (agentType == "Sheep") {//If the cell is occupied by a sheep, turn it into a wolf
|
||||
agents.remove(indexOfAgent);
|
||||
agents.add(new Wolf(x, y));
|
||||
} else if (agentType == "Wolf") {//If the cell is occupied by a wolf, loop back to cell = 0
|
||||
agents.remove(indexOfAgent);
|
||||
setCell(x, y, 0);
|
||||
}
|
||||
}
|
||||
|
||||
public void setAgent(int x, int y, Agent agent) {
|
||||
agents.add(agent);
|
||||
setCell(x, y, 0); // Clear the cell if it had food
|
||||
}
|
||||
|
||||
|
||||
public void removeAgent(Agent agent) {
|
||||
agents.remove(agent);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -164,6 +210,15 @@ public class Simulator extends Thread {
|
|||
public int getCell(int x, int y) {
|
||||
return world.getCell(x, y);
|
||||
}
|
||||
|
||||
private void updateCells() {
|
||||
for (int y = 0; y < getHeight(); y++) {
|
||||
for (int x = 0; x < getWidth(); x++) {
|
||||
world.updateCell(x, y);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* @return list of Animals in simulated world
|
||||
|
|
@ -171,6 +226,15 @@ public class Simulator extends Thread {
|
|||
public ArrayList<Agent> getAnimals(){
|
||||
return agents;
|
||||
}
|
||||
public boolean getOccupied(int x, int y) {
|
||||
for (Agent agent : agents) {
|
||||
if (agent.getX() == x && agent.getY() == y) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* selects Animals in a circular area of simulated world
|
||||
* @param x center
|
||||
|
|
@ -188,7 +252,7 @@ public class Simulator extends Thread {
|
|||
}
|
||||
return inArea;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* set value of cell
|
||||
* @param x coord of cell
|
||||
|
|
@ -205,8 +269,22 @@ public class Simulator extends Thread {
|
|||
* the simulated world in its present state
|
||||
*/
|
||||
public ArrayList<String> getSaveState() {
|
||||
//TODO : complete method with proper return
|
||||
return null;
|
||||
ArrayList<String> lines = new ArrayList<>();
|
||||
|
||||
// Iterate over the world and construct the lines
|
||||
for (int y = 0; y < LINE_NUM; y++) {
|
||||
StringBuilder lineBuilder = new StringBuilder();
|
||||
for (int x = 0; x < COL_NUM; x++) {
|
||||
lineBuilder.append(getCell(x, y)).append(";");
|
||||
}
|
||||
// Remove the last semicolon
|
||||
if (lineBuilder.length() > 0) {
|
||||
lineBuilder.deleteCharAt(lineBuilder.length() - 1);
|
||||
}
|
||||
lines.add(lineBuilder.toString());
|
||||
}
|
||||
|
||||
return lines;
|
||||
}
|
||||
/**
|
||||
*
|
||||
|
|
@ -249,14 +327,6 @@ public class Simulator extends Thread {
|
|||
* to be alive in new state
|
||||
*/
|
||||
public void generateRandom(float chanceOfLife) {
|
||||
//TODO : complete method
|
||||
/*
|
||||
* Advice :
|
||||
* as you should probably have a separate class
|
||||
* representing the field of cells...
|
||||
* maybe just make a constructor in there
|
||||
* and use it here
|
||||
*/
|
||||
world.generateRandom(chanceOfLife);
|
||||
}
|
||||
|
||||
|
|
@ -318,15 +388,57 @@ public class Simulator extends Thread {
|
|||
}
|
||||
|
||||
public ArrayList<String> getAgentsSave() {
|
||||
//TODO : Same idea as the other save method, but for agents
|
||||
return null;
|
||||
ArrayList<String> lines = new ArrayList<>();
|
||||
|
||||
StringBuilder sheepCoordinates = new StringBuilder();
|
||||
StringBuilder wolfCoordinates = new StringBuilder();
|
||||
|
||||
for (Agent agent : agents) {
|
||||
String coordinates = agent.getX() + "," + agent.getY();
|
||||
if (agent instanceof Sheep) {
|
||||
if (sheepCoordinates.length() > 0) {
|
||||
sheepCoordinates.append(";");
|
||||
}
|
||||
sheepCoordinates.append(coordinates);
|
||||
} else if (agent instanceof Wolf) {
|
||||
if (wolfCoordinates.length() > 0) {
|
||||
wolfCoordinates.append(";");
|
||||
}
|
||||
wolfCoordinates.append(coordinates);
|
||||
}
|
||||
}
|
||||
|
||||
lines.add(sheepCoordinates.toString());
|
||||
lines.add(wolfCoordinates.toString());
|
||||
|
||||
return lines;
|
||||
}
|
||||
|
||||
public void loadAgents(ArrayList<String> stringArray) {
|
||||
//TODO : Same idea as other load methods, but for agent list
|
||||
|
||||
agents.clear();
|
||||
|
||||
// Load sheeps
|
||||
String sheepLine = stringArray.get(0);
|
||||
String[] sheepCoords = sheepLine.split(";");
|
||||
for (String coord : sheepCoords) {
|
||||
String[] xy = coord.split(",");
|
||||
int x = Integer.parseInt(xy[0]);
|
||||
int y = Integer.parseInt(xy[1]);
|
||||
agents.add(new Sheep(x, y));
|
||||
}
|
||||
|
||||
// Load wolves
|
||||
String wolfLine = stringArray.get(1);
|
||||
String[] wolfCoords = wolfLine.split(";");
|
||||
for (String coord : wolfCoords) {
|
||||
String[] xy = coord.split(",");
|
||||
int x = Integer.parseInt(xy[0]);
|
||||
int y = Integer.parseInt(xy[1]);
|
||||
agents.add(new Wolf(x, y));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* used by label in interface to show the active click action
|
||||
* @return String representation of click action
|
||||
|
|
|
|||
|
|
@ -0,0 +1,98 @@
|
|||
package backend;
|
||||
|
||||
import java.awt.Color;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Random;
|
||||
|
||||
// example of basic animal.
|
||||
// do not hesitate to make it more complex
|
||||
// and DO add at least another species that interact with it
|
||||
// for example wolves that eat Sheep
|
||||
public class Wolf extends Agent {
|
||||
|
||||
int hunger;
|
||||
Random rand;
|
||||
private final int REPRODUCTION_RADIUS = 1; // Radius within which sheep can reproduce
|
||||
private final double REPRODUCTION_PROBABILITY = 0.2; // Probability of reproduction per turn
|
||||
|
||||
Wolf(int x,int y){
|
||||
//first we call the constructor of the superClass(Animal)
|
||||
//with the values we want.
|
||||
// here we decide that a Sheep is initially white using this constructor
|
||||
super(x,y,Color.red);
|
||||
// we give our sheep a hunger value of zero at birth
|
||||
hunger = 0;
|
||||
//we initialize the random number generator we will use to move randomly
|
||||
rand = new Random();
|
||||
}
|
||||
|
||||
/**
|
||||
* action of the animal
|
||||
* it can interact with the cells or with other animals
|
||||
* as you wish
|
||||
*/
|
||||
public boolean liveTurn(ArrayList<Agent> neighbors, Simulator world) {
|
||||
boolean ateSheep = false;
|
||||
|
||||
// Check for neighboring sheep to eat
|
||||
for (Agent neighbor : neighbors) {
|
||||
if (neighbor instanceof Sheep) {
|
||||
// Eat the sheep (remove from the list)
|
||||
world.removeAgent(neighbor);
|
||||
hunger = 0; // Reset hunger
|
||||
ateSheep = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// If no sheep were eaten, increase hunger
|
||||
if (!ateSheep) {
|
||||
hunger++;
|
||||
}
|
||||
|
||||
|
||||
// Check for reproduction
|
||||
for (Agent neighbor : neighbors) {
|
||||
if (neighbor instanceof Wolf && this.isInArea(neighbor.getX(), neighbor.getY(), REPRODUCTION_RADIUS)) {
|
||||
if (rand.nextDouble() < REPRODUCTION_PROBABILITY) {
|
||||
reproduce(world);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Move randomly
|
||||
this.moveRandom();
|
||||
|
||||
return hunger>10;
|
||||
}
|
||||
|
||||
private void reproduce(Simulator world) {
|
||||
// Find a random adjacent cell
|
||||
int newX = x + rand.nextInt(3) - 1;
|
||||
int newY = y + rand.nextInt(3) - 1;
|
||||
|
||||
// Ensure the new position is within bounds and empty
|
||||
if (newX >= 0 && newX < world.getWidth() && newY >= 0 && newY < world.getHeight() && world.getCell(newX, newY) == 0) {
|
||||
world.setAgent(newX, newY, new Wolf(newX, newY));
|
||||
}
|
||||
}
|
||||
|
||||
private void moveRandom() {
|
||||
int direction = rand.nextInt(4);
|
||||
if(direction == 0) {
|
||||
x+=1;
|
||||
}
|
||||
if(direction == 1) {
|
||||
y+=1;
|
||||
}
|
||||
if(direction == 2) {
|
||||
x-=1;
|
||||
}
|
||||
if(direction == 3) {
|
||||
y-=1;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
|
@ -37,6 +37,10 @@ public class World {
|
|||
}
|
||||
}
|
||||
|
||||
public void updateCell(int x, int y) {
|
||||
grid.getCell(x, y).updateCell();
|
||||
}
|
||||
|
||||
public void makeStep() {
|
||||
|
||||
Grid nextGrid = new Grid(width,height);
|
||||
|
|
|
|||
Loading…
Reference in New Issue