From 8df5299925bd24461e8cf408840a49e4adf77331 Mon Sep 17 00:00:00 2001
From: Yanis O <oualanyanis01@gmail.com>
Date: Wed, 27 Nov 2024 18:57:51 +0100
Subject: [PATCH] =?UTF-8?q?Les=20patients=20vont=20voir=20les=20m=C3=A9dec?=
 =?UTF-8?q?ins=20lorsqu'ils=20sont=20infect=C3=A9s?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

---
 src/main/java/controller/Controller.java      |   4 +-
 src/main/java/model/Scenario.java             |   7 +-
 .../java/model/doctorviruspatient/Doctor.java |   4 +-
 .../model/doctorviruspatient/Patient.java     | 278 +++++++++++-------
 .../java/model/doctorviruspatient/Virus.java  |  13 +-
 5 files changed, 187 insertions(+), 119 deletions(-)

diff --git a/src/main/java/controller/Controller.java b/src/main/java/controller/Controller.java
index 6bb9183..00cb8b4 100644
--- a/src/main/java/controller/Controller.java
+++ b/src/main/java/controller/Controller.java
@@ -146,8 +146,8 @@ public class Controller {
     */
 
       
-    entityCounts.put((pos, b) -> new Patient(pos), 10);
-    entityCounts.put((pos, b) -> new Virus(pos), 1);
+    entityCounts.put((pos, b) -> new Patient(pos), 70);
+    entityCounts.put((pos, b) -> new Virus(pos), 6);
     entityCounts.put((pos, b) -> new Doctor(pos), 3);
     
     Model model = new DoctorVirusPatientScenario(columnCount, rowCount, entityCounts);
diff --git a/src/main/java/model/Scenario.java b/src/main/java/model/Scenario.java
index 92af675..b0943a4 100644
--- a/src/main/java/model/Scenario.java
+++ b/src/main/java/model/Scenario.java
@@ -85,7 +85,12 @@ public class Scenario implements Board<Square>{
 
   @Override
   public void clearCaseFrom(Entity entity, Position position) {
-    matrix.get(position.x(), position.y()).getEntities().removeIf(element -> element.equals(entity));
+    if(!matrix.get(position.x(), position.y()).getEntities().removeIf(element -> element.equals(entity))){
+      System.out.println("didn't clear, tried to clear : x:" + position.x() + " y : " + position.y());
+      for(Entity e : getStates(position).getEntities()){
+        System.out.println(e);
+      }
+    }
   }
 
   public Position getNearestEntity(Position fromPos, Class<?> entityType, List<Entity> exclusionList) {
diff --git a/src/main/java/model/doctorviruspatient/Doctor.java b/src/main/java/model/doctorviruspatient/Doctor.java
index 82f4df7..0b8bd43 100644
--- a/src/main/java/model/doctorviruspatient/Doctor.java
+++ b/src/main/java/model/doctorviruspatient/Doctor.java
@@ -12,7 +12,7 @@ import util.Position;
 import util.PositionUtil;
 
 public class Doctor implements Entity {
-    private final int priority = 0;
+    private final int priority = 1;
     Position position;
     private int age;
     private final Color viewColor = Color.RED;
@@ -28,7 +28,7 @@ public class Doctor implements Entity {
 
     @Override
     public List<Position> nextTurn(Board<Square> board) {
-        interactWithAdjacentPositions(PositionUtil.generateAdjacentPositions(position, board), board);
+        interactWithAdjacentPositions(PositionUtil.generateAllAdjacentPositions(position, board), board);
         return List.of();
     }
 
diff --git a/src/main/java/model/doctorviruspatient/Patient.java b/src/main/java/model/doctorviruspatient/Patient.java
index 9e62399..4db5754 100644
--- a/src/main/java/model/doctorviruspatient/Patient.java
+++ b/src/main/java/model/doctorviruspatient/Patient.java
@@ -1,70 +1,90 @@
 package model.doctorviruspatient;
 
 import java.util.ArrayList;
-import java.util.Collections;
 import java.util.List;
 import java.util.Objects;
+import java.util.Random;
 
 import javafx.scene.paint.Color;
 import model.Board;
 import model.Entity;
 import model.Square;
+import util.PathGenerator;
 import util.Position;
 import util.PositionUtil;
 
 public class Patient implements Entity {
-    private final int priority = 0;
-    Position position;
+    private final int priority = 1;
+    private Position position;
     private int age;
     private final Color viewColor = Color.BLUE;
     private Virus carriedVirus;
-    List<Entity> visitedPatients;
+    private List<Entity> visitedPatients;
     private static int patientsCount = 0;
     private int patientID;
     private Position ennemy;
+    private boolean isAsymptomatic;
     private boolean wandering;
 
+    // Attributs pour le chemin
+    private List<Position> path;
+    private int pathIndex;
+    private static final int MAX_STEPS_IN_DIRECTION = 5;
+    private static final int MINIMUM_ROAD_LENGTH = 10;
+
     public Patient(Position p) {
         this.wandering = true;
         patientID = patientsCount;
         patientsCount += 1;
-        this.visitedPatients = new ArrayList<Entity>();
+        this.visitedPatients = new ArrayList<>();
         this.position = p;
+        Random r = new Random();
+        int randomNumber = r.nextInt(10);
+        this.isAsymptomatic = randomNumber == 1;
+        // Initialiser le chemin
+        this.path = new ArrayList<>();
+        this.pathIndex = 0;
     }
 
     public Patient(Position p, int age) {
         this.wandering = true;
         patientID = patientsCount;
         patientsCount += 1;
-        this.visitedPatients = new ArrayList<Entity>();
+        this.visitedPatients = new ArrayList<>();
         this.position = p;
         this.age = age;
+        Random r = new Random();
+        int randomNumber = r.nextInt(10);
+        this.isAsymptomatic = randomNumber == 1;
+        // Initialiser le chemin
+        this.path = new ArrayList<>();
+        this.pathIndex = 0;
     }
 
     @Override
     public List<Position> nextTurn(Board<Square> board) {
-        if(isInfected()){
-            return moveToDoctor();
+        if (isInfected() && !isAsymptomatic) {
+            return moveToDoctor(board);
         }
         updateWanderingStatus(board);
-    
+
         if (wandering) {
             return performWandering(board);
         }
-    
+
         resetVisitedPatientsIfNecessary();
-    
+
         Position target = determineTarget(board);
-    
+
         if (target == null) {
             visitedPatients.clear();
             return List.of();
         }
-    
+
         Position nextPos = determineNextPosition(target, board);
-    
+
         if (nextPos != null && board.doesPositionExist(nextPos)) {
-            
+
             List<Position> adjacentPositions = PositionUtil.generateAllAdjacentPositions(nextPos, board);
             List<Position> result = interactWithAdjacentPositions(adjacentPositions, board);
             result.addAll(moveToPosition(nextPos, board));
@@ -72,116 +92,153 @@ public class Patient implements Entity {
             result.add(position);
             return result;
         }
-    
+
         return List.of();
     }
-    
-    
+
     private void updateWanderingStatus(Board<Square> board) {
-    if (board.getStepNumber() % 8 == 0) {
-        wandering = false;
+        if (board.getStepNumber() % 8 == 0) {
+            wandering = false;
+            // Réinitialiser le chemin lorsque le patient arrête d'errer
+            this.path.clear();
+            this.pathIndex = 0;
+        }
     }
-}
-private List<Position> moveToDoctor(){
-    return List.of();
-}
-private List<Position> performWandering(Board<Square> board) {
-    List<Position> adjacentPositions = PositionUtil.generateAdjacentPositions(position, board);
-    Collections.shuffle(adjacentPositions);
 
-    Position oldPosition = position;
-    Position newPosition = adjacentPositions.get(0);
-
-    moveEntityOnBoard(oldPosition, newPosition, board);
-    return List.of(newPosition, oldPosition);
-}
+    private List<Position> moveToDoctor(Board<Square> board) {
+        for (Position p : PositionUtil.generateAllAdjacentPositions(position, board)) {
+            if (!board.doesPositionExist(p)) continue;
+            if (board.doesSquareContainEntity(p, Doctor.class)) return List.of();
+        }
+        Position nearestDoctor = board.getNearestEntity(position, Doctor.class, null);
+        Position nextPos = PositionUtil.getNextPositionTowards(position, nearestDoctor, board);
+        if (nextPos == null) return List.of();
 
-private void resetVisitedPatientsIfNecessary() {
-    if (visitedPatients.size() - 1 >= patientsCount) {
-        visitedPatients.clear();
+        List<Position> changedPositions = new ArrayList<>();
+        changedPositions.addAll(moveToPosition(nextPos, board));
+        return changedPositions;
     }
-}
 
-private Position determineTarget(Board<Square> board) {
-    return board.getNearestEntity(position, Patient.class, getVisitedPatients());
-}
+    private List<Position> performWandering(Board<Square> board) {
+        if (path == null || path.isEmpty() || pathIndex >= path.size()) {
+            generateNewPath(board);
+            if (path.isEmpty()) {
+                return List.of();
+            }
+        }
 
-private Position determineNextPosition(Position target, Board<Square> board) {
-    int enemyDistance = PositionUtil.getManhattanDistance(target, position);
+        Position nextPosition = path.get(pathIndex);
 
-    if (ennemy != null && enemyDistance < 2) {
-        return PositionUtil.getNextPositionAwayFrom(position, target, board);
-    } else if (target != null) {
-        return PositionUtil.getNextPositionTowards(position, target, board);
+        if (board.doesPositionExist(nextPosition) && board.isPositionFree(nextPosition, priority)) {
+            List<Position> changedPositions = moveSelfOnBoard(nextPosition, board);
+            pathIndex++;
+            return changedPositions;
+        } else {
+            // Si la position n'est pas libre ou n'existe pas, générer un nouveau chemin
+            generateNewPath(board);
+            return List.of();
+        }
     }
-    return null;
-}
 
-private List<Position> moveToPosition(Position nextPos, Board<Square> board) {
-    if (!board.isPositionFree(nextPos, priority)) {
-        nextPos = findAlternativePosition(nextPos, board);
+    private void generateNewPath(Board<Square> board) {
+        PathGenerator pathGenerator = new PathGenerator(board, position, MAX_STEPS_IN_DIRECTION, MINIMUM_ROAD_LENGTH);
+        this.path = pathGenerator.generate();
+        // Supprimer la position actuelle du chemin si elle est présente
+        if (!path.isEmpty() && path.get(0).equals(position)) {
+            path.remove(0);
+        }
+        this.pathIndex = 0;
     }
 
-    if (nextPos != null) {
-        Position oldPosition = position;
-        moveEntityOnBoard(oldPosition, nextPos, board);
+    private void resetVisitedPatientsIfNecessary() {
+        if (visitedPatients.size() - 1 >= patientsCount) {
+            visitedPatients.clear();
+        }
     }
-    
-    return List.of(new Position(this.position.x(), this.position.y()), nextPos);
-}
 
-private Position findAlternativePosition(Position currentPos, Board<Square> board) {
-    List<Position> adjacentPositions = PositionUtil.generateAdjacentPositions(position, board);
-    for (Position p : adjacentPositions) {
-        if (ennemy != null) {
-            Position awayPos = PositionUtil.getNextPositionAwayFrom(p, ennemy, board);
-            if (p.equals(awayPos)) {
-                // Si la position reste la même après avoir tenté de s'éloigner, on continue
-                continue;
-            }
-        }
-        if (board.isPositionFree(p, priority)) {
-            return p;
+    private Position determineTarget(Board<Square> board) {
+        return board.getNearestEntity(position, Patient.class, getVisitedPatients());
+    }
+
+    private Position determineNextPosition(Position target, Board<Square> board) {
+        int enemyDistance = PositionUtil.getManhattanDistance(target, position);
+
+        if (ennemy != null && enemyDistance < 2) {
+            return PositionUtil.getNextPositionAwayFrom(position, target, board);
+        } else if (target != null) {
+            return PositionUtil.getNextPositionTowards(position, target, board);
         }
+        return null;
     }
-    return null;
-}
 
+    private List<Position> moveToPosition(Position nextPos, Board<Square> board) {
+        List<Position> changedPosition = new ArrayList<>();
+        if (!board.isPositionFree(nextPos, priority)) {
+            nextPos = findAlternativePosition(nextPos, board);
+        }
 
-private void moveEntityOnBoard(Position oldPosition, Position newPosition, Board<Square> board) {
-    board.clearCaseFrom(this, oldPosition);
-    board.addEntityAtSquare(this, newPosition);
-    this.position = newPosition;
-}
+        if (nextPos != null) {
+            changedPosition.addAll(moveSelfOnBoard(nextPos, board));
+        }
 
-private List<Position> interactWithAdjacentPositions(List<Position> adjacentPositions, Board<Square> board) {
-    List<Position> result = new ArrayList<>();
-    for (Position p : adjacentPositions) {
-        if (board.doesSquareContainEntity(p, Patient.class)) {
-            handleEncounterWithPatient(p, board);
-            if (isInfected()) {
-                result.addAll(adjacentPositions);
+        return changedPosition;
+    }
+
+    private Position findAlternativePosition(Position currentPos, Board<Square> board) {
+        List<Position> adjacentPositions = PositionUtil.generateAdjacentPositions(position, board);
+        for (Position p : adjacentPositions) {
+            if (ennemy != null) {
+                Position awayPos = PositionUtil.getNextPositionAwayFrom(p, ennemy, board);
+                if (p.equals(awayPos)) {
+                    continue;
+                }
+            }
+            if (board.isPositionFree(p, priority)) {
+                return p;
             }
         }
+        return null;
     }
-    return result;
-}
 
-private void handleEncounterWithPatient(Position p, Board<Square> board) {
-    this.wandering = true;
-    Patient patient = (Patient) board.getStates(p).getEntities().stream()
-        .filter(entity -> entity instanceof Patient)
-        .findFirst()
-        .orElse(null);
-    if(isInfected()){
-        patient.infect(carriedVirus);
+    private List<Position> moveSelfOnBoard(Position newPosition, Board<Square> board) {
+        if(!board.isPositionFree(newPosition, priority))return List.of();
+        Position oldPosition = new Position(this.position.x(), this.position.y());
+        board.clearCaseFrom(this, oldPosition);
+        board.addEntityAtSquare(this, newPosition);
+        this.position = newPosition;
+        return List.of(oldPosition, this.position);
     }
-    if (patient != null) {
-        this.ennemy = patient.getPosition();
-        visitedPatients.add(patient);
+
+    private List<Position> interactWithAdjacentPositions(List<Position> adjacentPositions, Board<Square> board) {
+        List<Position> result = new ArrayList<>();
+        for (Position p : adjacentPositions) {
+            if (board.doesSquareContainEntity(p, Patient.class)) {
+                handleEncounterWithPatient(p, board);
+                if (isInfected()) {
+                    result.addAll(adjacentPositions);
+                }
+            }
+        }
+        return result;
     }
-}
 
+    private void handleEncounterWithPatient(Position p, Board<Square> board) {
+        this.wandering = true;
+        // Réinitialiser le chemin lorsqu'un patient est rencontré
+        this.path.clear();
+        this.pathIndex = 0;
+        Patient patient = (Patient) board.getStates(p).getEntities().stream()
+                .filter(entity -> entity instanceof Patient)
+                .findFirst()
+                .orElse(null);
+        if (isInfected()) {
+            patient.infect(carriedVirus);
+        }
+        if (patient != null) {
+            this.ennemy = patient.getPosition();
+            visitedPatients.add(patient);
+        }
+    }
 
     @Override
     public Position getPosition() {
@@ -191,7 +248,6 @@ private void handleEncounterWithPatient(Position p, Board<Square> board) {
     @Override
     public void setPosition(Position p) {
         this.position = p;
-
     }
 
     @Override
@@ -219,46 +275,46 @@ private void handleEncounterWithPatient(Position p, Board<Square> board) {
         return this.priority;
     }
 
-    public boolean isInfected(){
+    public boolean isInfected() {
         return this.carriedVirus != null;
     }
 
-    public void infect(Virus virus){
-        if(this.carriedVirus != null) return;
+    public void infect(Virus virus) {
+        if (this.carriedVirus != null) return;
         this.carriedVirus = virus;
     }
 
-    public Virus getVirus(){
+    public Virus getVirus() {
         return this.carriedVirus;
     }
-    
-    public List<Entity> getVisitedPatients(){
+
+    public List<Entity> getVisitedPatients() {
         return this.visitedPatients;
     }
 
-    public boolean hasVisited(Patient patient){
+    public boolean hasVisited(Patient patient) {
         return this.getVisitedPatients().contains(patient);
     }
 
-    public int getPatientId(){
+    public int getPatientId() {
         return this.patientID;
     }
 
-    public void cure(){
-        if(this.carriedVirus.tryToKill()){
+    public void cure() {
+        if (this.carriedVirus.tryToKill()) {
             this.carriedVirus = null;
         }
     }
 
     @Override
     public boolean equals(Object obj) {
-        if(obj instanceof Patient){
+        if (obj instanceof Patient) {
             Patient other = (Patient) obj;
             return this.patientID == other.getPatientId();
-        }else{
+        } else {
             return false;
         }
-        
+
     }
 
     @Override
diff --git a/src/main/java/model/doctorviruspatient/Virus.java b/src/main/java/model/doctorviruspatient/Virus.java
index 4c66b0e..5bf9f69 100644
--- a/src/main/java/model/doctorviruspatient/Virus.java
+++ b/src/main/java/model/doctorviruspatient/Virus.java
@@ -12,7 +12,7 @@ import util.Position;
 import util.PositionUtil;
 
 public class Virus implements Entity {
-    private final int priority = 0;
+    private final int priority = 2;
     private Position position;
     private int age;
     private final Color viewColor = Color.LIMEGREEN;
@@ -21,9 +21,11 @@ public class Virus implements Entity {
     private static final int MAX_STEPS_IN_DIRECTION = 5;
     private static final int MINIMUM_ROAD_LENGTH = 10;
     private int health;
+    private int variantId;
 
     public Virus(Position p) {
-        this.health = 8;
+        this.variantId = 0;
+        this.health = 50;
         this.position = p;
         this.path = new ArrayList<>();
         this.age = 0;
@@ -40,6 +42,9 @@ public class Virus implements Entity {
 
     @Override
     public List<Position> nextTurn(Board<Square> board) {
+        if(board.getStepNumber() % 50 == 0){
+            evolve();
+        }
         // Génère un nouveau chemin si nécessaire
         if (path == null || path.isEmpty() || pathIndex >= path.size()) {
             generateNewPath(board);
@@ -88,7 +93,9 @@ public class Virus implements Entity {
     }
 
     // Les autres méthodes restent inchangées
-
+    private void evolve(){
+        
+    }
     @Override
     public Position getPosition() {
         return this.position;
-- 
GitLab