From 0c3bc722e3c5cd55790fdc9485cedd0c1aa4529c Mon Sep 17 00:00:00 2001
From: Edvard <edvardee@stud.ntnu.no>
Date: Mon, 20 May 2024 11:14:10 +0200
Subject: [PATCH] Unit tests for ChaosCanvas class

---
 .../controller/ExploreGameController.java     |  59 ++++---
 .../chaosgame/model/chaos/ChaosCanvas.java    |   4 +
 .../chaosgame/model/chaos/ExploreGame.java    |  30 ++--
 .../model/chaos/ChaosCanvasTest.java          | 162 +++++++++++++++---
 4 files changed, 183 insertions(+), 72 deletions(-)

diff --git a/src/main/java/org/example/chaosgame/controller/ExploreGameController.java b/src/main/java/org/example/chaosgame/controller/ExploreGameController.java
index c066851..de38924 100644
--- a/src/main/java/org/example/chaosgame/controller/ExploreGameController.java
+++ b/src/main/java/org/example/chaosgame/controller/ExploreGameController.java
@@ -53,13 +53,16 @@ public class ExploreGameController implements Observer, Subject, GameController
 
   private static final int WIDTH = 1200;
   private static final int HEIGHT = 800;
+  
+  private Vector2D minCoords = new Vector2D(-1.6, -1);
+  private Vector2D maxCoords = new Vector2D(1.6, 1);
 
   public ExploreGameController() {
     this.exploreJulia = new ExploreJulia(new Complex(-0.835, 0.2321));
     this.trans = List.of(exploreJulia);
     this.description  = new ChaosGameDescription(
-            new Vector2D(-1.6, -1),
-            new Vector2D(1.6, 1), trans);
+            minCoords,
+            maxCoords, trans);
     this.exploreGame = new ExploreGame(description, WIDTH, HEIGHT);
     this.chaosCanvas = exploreGame.getCanvas();
     this.pageObservers = new ArrayList<>();
@@ -90,10 +93,10 @@ public class ExploreGameController implements Observer, Subject, GameController
 //       Reset the position where the drag started
     Vector2D fractalRange = description.getMaxCoords().subtract(description.getMinCoords());
     Vector2D adjustedDragDistance = dragDistance.multiply(fractalRange).divide(new Vector2D(canvas.getWidth(), canvas.getHeight()));
-    Vector2D newMinCoords = description.getMinCoords().subtract(adjustedDragDistance);
-    Vector2D newMaxCoords = description.getMaxCoords().subtract(adjustedDragDistance);
-    description = new ChaosGameDescription(newMinCoords, newMaxCoords, trans);
-//   /* exploreGame.setGameDescription(new ChaosGameDescription(newMinCoords, newMaxCoords, trans),
+    minCoords = description.getMinCoords().subtract(adjustedDragDistance);
+    maxCoords = description.getMaxCoords().subtract(adjustedDragDistance);
+    description = new ChaosGameDescription(minCoords, maxCoords, trans);
+//   /* exploreGame.setGameDescription(new ChaosGameDescription(minCoords, maxCoords, trans),
 //            (int) canvas.getWidth(),(int) canvas.getHeight());*/
 //    exploreGame = new ExploreGame(description, (int) canvas.getWidth(),(int) canvas.getHeight());
 //    exploreGame.exploreFractals();
@@ -106,10 +109,10 @@ public class ExploreGameController implements Observer, Subject, GameController
   public void zoomButtonClicked(double scaleFactor) {
     cumulativeScaleFactor *= scaleFactor;
     Vector2D canvasCenter = chaosCanvas.transformIndicesToCoords(chaosCanvas.getWidth() / 2, chaosCanvas.getHeight() / 2);
-    Vector2D newMinCoords = canvasCenter.subtract(canvasCenter.subtract(description.getMinCoords()).scale(scaleFactor));
-    Vector2D newMaxCoords = canvasCenter.add(description.getMaxCoords().subtract(canvasCenter).scale(scaleFactor));
+    minCoords = canvasCenter.subtract(canvasCenter.subtract(description.getMinCoords()).scale(scaleFactor));
+    maxCoords = canvasCenter.add(description.getMaxCoords().subtract(canvasCenter).scale(scaleFactor));
 
-    description = new ChaosGameDescription(newMinCoords, newMaxCoords, trans);
+    description = new ChaosGameDescription(minCoords, maxCoords, trans);
     updateExplorePage();
 //    description = exploreGame.getDescription();
   }
@@ -118,10 +121,11 @@ public class ExploreGameController implements Observer, Subject, GameController
     if (task != null) {
       task.cancel();
       task = null;
+      System.out.println("Task stopped");
     }
   }
   public void onScroll(ScrollEvent event) throws Exception {
-//    stopTask();
+    stopTask();
     mouseX = event.getX();
     mouseY = event.getY();
     double scaleBase = event.isControlDown() ? 2 : 1.1;
@@ -155,14 +159,14 @@ public class ExploreGameController implements Observer, Subject, GameController
 
 
     Vector2D canvasCenter = chaosCanvas.transformIndicesToCoords((int) mouseX, (int) mouseY);
-    Vector2D newMinCoords = canvasCenter.subtract(canvasCenter.subtract(description.getMinCoords()).scale(scaleFactor));
-    Vector2D newMaxCoords = canvasCenter.add(description.getMaxCoords().subtract(canvasCenter).scale(scaleFactor));
+    minCoords = canvasCenter.subtract(canvasCenter.subtract(description.getMinCoords()).scale(scaleFactor));
+    maxCoords = canvasCenter.add(description.getMaxCoords().subtract(canvasCenter).scale(scaleFactor));
 
-//    updateExploreGame(newMinCoords, newMaxCoords,trans);
+//    updateExploreGame(minCoords, maxCoords,trans);
 //    juliaTask = new SetJuliaTask(real, img, exploreGame, explorePage);
 
 //    task = exploreGame.call(canvas);
-    description = new ChaosGameDescription(newMinCoords, newMaxCoords, trans);
+//    description = new ChaosGameDescription(minCoords, maxCoords, trans);
     updateExplorePage();
 //    description = exploreGame.getDescription();
   }
@@ -192,19 +196,18 @@ public class ExploreGameController implements Observer, Subject, GameController
 
 
   private void updateExplorePage() {
-//    System.out.println("Update Explore Game");
-//    exploreGame.setExploreGame(description, (int) canvas.getWidth(),(int) canvas.getHeight());
-    exploreGame.removeObserver(this);
-    exploreGame = new ExploreGame(description, (int) canvas.getWidth(),(int) canvas.getHeight());
-    exploreGame.registerObserver(this);
+    this.description.setMinCoords(minCoords);
+    this.description.setMaxCoords(maxCoords);
+    this.description.setTransforms(trans);
+    this.exploreGame = new ExploreGame(description, (int) canvas.getWidth(),(int) canvas.getHeight());
+    this.exploreGame.registerObserver(this);
     this.chaosCanvas = exploreGame.getCanvas();
     exploreGame.exploreFractals();
     explorePage.updateCanvas(this.chaosCanvas);
-//    explorePage.updateCanvas(this.chaosCanvas);
-    canvas.setTranslateX(0);
-    canvas.setTranslateY(0);
-    canvas.setScaleY(1);
-    canvas.setScaleX(1);
+    this.canvas.setTranslateX(0);
+    this.canvas.setTranslateY(0);
+    this.canvas.setScaleX(1);
+    this.canvas.setScaleY(1);
   }
   public void homeButtonClicked() {
     notifyObservers();
@@ -241,11 +244,11 @@ public class ExploreGameController implements Observer, Subject, GameController
   }
 
   public void resetImage() {
-    Vector2D newMinCoords = new Vector2D(-1.6, -1);
-    Vector2D newMaxCoords = new Vector2D(1.6, 1);
+    minCoords = new Vector2D(-1.6, -1);
+    maxCoords = new Vector2D(1.6, 1);
     description = new ChaosGameDescription(
-            newMinCoords,
-            newMaxCoords, trans);
+            minCoords,
+            maxCoords, trans);
 //    exploreGame.removeObserver(this);
 //    exploreGame = new ExploreGame(description, (int) canvas.getWidth(),(int) canvas.getHeight());
 //    exploreGame.registerObserver(this);
diff --git a/src/main/java/org/example/chaosgame/model/chaos/ChaosCanvas.java b/src/main/java/org/example/chaosgame/model/chaos/ChaosCanvas.java
index 56e4134..cf6f4d4 100644
--- a/src/main/java/org/example/chaosgame/model/chaos/ChaosCanvas.java
+++ b/src/main/java/org/example/chaosgame/model/chaos/ChaosCanvas.java
@@ -164,4 +164,8 @@ public class ChaosCanvas {
   public void setHeight(int height) {
     this.height = height;
   }
+
+  public AffineTransform2D getTransformCoordsToIndices() {
+    return transformCoordsToIndices;
+  }
 }
diff --git a/src/main/java/org/example/chaosgame/model/chaos/ExploreGame.java b/src/main/java/org/example/chaosgame/model/chaos/ExploreGame.java
index 6caad1a..6313615 100644
--- a/src/main/java/org/example/chaosgame/model/chaos/ExploreGame.java
+++ b/src/main/java/org/example/chaosgame/model/chaos/ExploreGame.java
@@ -1,15 +1,18 @@
 package org.example.chaosgame.model.chaos;
 
+import javafx.application.Platform;
 import javafx.concurrent.Task;
 import javafx.scene.canvas.Canvas;
 import org.example.chaosgame.controller.observer.Observer;
 import org.example.chaosgame.controller.observer.Subject;
 import org.example.chaosgame.model.linalg.Vector2D;
 import org.example.chaosgame.model.transformations.Transform2D;
+import org.example.chaosgame.view.components.AlertUtility;
 
 import java.util.ArrayList;
 import java.util.List;
 import java.util.stream.IntStream;
+import java.util.stream.Stream;
 
 /**
  * Class for exploring julia sets.
@@ -32,8 +35,7 @@ public class ExploreGame extends Task implements Subject {
    * @param height Height of the canvas
    */
   public ExploreGame(ChaosGameDescription description, int width, int height) {
-    this.description = description;
-    this.canvas = new ChaosCanvas(width, height, description.getMinCoords(), description.getMaxCoords());
+    setExploreGame(description, width, height);
     this.gameObservers = new ArrayList<>();
   }
 
@@ -51,9 +53,9 @@ public class ExploreGame extends Task implements Subject {
     yStream.parallel().forEach(y -> {
 //    for (int y = 0; y < canvas.getHeight(); y++) {
       for (int x = 0; x < canvas.getWidth(); x++) {
-//        if (isCancelled()) {
-//          break;
-//        }
+        if (isCancelled()) {
+          break;
+        }
         int iter = 0;
         currentPoint = canvas.transformIndicesToCoords(x, y);
         Vector2D tempPoint = currentPoint;
@@ -83,7 +85,7 @@ public class ExploreGame extends Task implements Subject {
   }
   public void setExploreGame(ChaosGameDescription description, int width, int height) {
     this.description = description;
-    setChaosCanvas(description.getMinCoords(), description.getMaxCoords(), width, height);
+    this.canvas = new ChaosCanvas(width, height, description.getMinCoords(), description.getMaxCoords());
   }
 
   public ChaosCanvas getCanvas() {
@@ -107,18 +109,14 @@ public class ExploreGame extends Task implements Subject {
   @Override
   public void notifyObservers() {
     List<Observer> gameObservers = new ArrayList<>(this.gameObservers);
-    for (Observer gameObserver : gameObservers) {
-      try {
-        gameObserver.update();
-      } catch (Exception e) {
-        System.out.println("Message: " + e.getMessage());
-      }
-
-    }
+    Platform.runLater(() -> {
+      gameObservers.forEach(Observer::update);
+    });
   }
 
-  public Task call() throws Exception {
-    System.out.println("Task called");
+  @Override
+  public Task call() {
+    exploreFractals();
     return this;
   }
   public void stopTask() {
diff --git a/src/test/java/org/example/chaosgame/model/chaos/ChaosCanvasTest.java b/src/test/java/org/example/chaosgame/model/chaos/ChaosCanvasTest.java
index 6df0e36..bfbef04 100644
--- a/src/test/java/org/example/chaosgame/model/chaos/ChaosCanvasTest.java
+++ b/src/test/java/org/example/chaosgame/model/chaos/ChaosCanvasTest.java
@@ -1,78 +1,184 @@
 package org.example.chaosgame.model.chaos;
 
-import org.junit.jupiter.api.AfterEach;
-import org.junit.jupiter.api.BeforeEach;
-import org.junit.jupiter.api.Test;
+import org.example.chaosgame.model.linalg.Vector2D;
+import org.example.chaosgame.model.transformations.AffineTransform2D;
+import org.junit.jupiter.api.*;
 
 import static org.junit.jupiter.api.Assertions.*;
 
 class ChaosCanvasTest {
+  private static ChaosCanvas chaosCanvas;
+  private static Vector2D minCoords;
+  private static Vector2D maxCoords;
+  private static final int WIDTH = 100;
+  private static final int HEIGHT = 100;
 
   @BeforeEach
   void setUp() {
+    minCoords = new Vector2D(0, 0);
+    maxCoords = new Vector2D(1, 1);
+    chaosCanvas = new ChaosCanvas(WIDTH, HEIGHT, minCoords, maxCoords);
   }
 
   @AfterEach
   void tearDown() {
-  }
-
-  @Test
-  void getPixel() {
-  }
-
-  @Test
-  void putPixel() {
-  }
-
-  @Test
-  void testPutPixel() {
-  }
-
-  @Test
-  void transformIndicesToCoords() {
-  }
-
-  @Test
-  void getCanvasArray() {
+    minCoords = null;
+    maxCoords = null;
+    chaosCanvas = null;
+  }
+
+  @Nested
+  @DisplayName("Test getPixel")
+  class TestGetPixel {
+    @Test
+    @DisplayName("Test positive getPixel")
+    void getPixel() {
+      double pixel = chaosCanvas.getPixel(new Vector2D(0, 0));
+      assertEquals(0.0, pixel);
+    }
+
+    @Test
+    @DisplayName("Test negative getPixel")
+    void getPixelFail() {
+      double pixel = chaosCanvas.getPixel(new Vector2D(0, 0));
+      assertNotEquals(1.0, pixel);
+    }
+  }
+
+  @Nested
+  @DisplayName("Test putPixel")
+  class TestPutPixel {
+    @Test
+    @DisplayName("Test positive putPixel(Vector2D)")
+    void putPixel() {
+      chaosCanvas.putPixel(new Vector2D(0, 0));
+      assertEquals(1.0, chaosCanvas.getPixel(new Vector2D(0, 0)));
+    }
+
+    @Test
+    @DisplayName("Test negative putPixel(Vector2D)")
+    void putPixelFail() {
+      chaosCanvas.putPixel(new Vector2D(0, 0));
+      assertNotEquals(0.0, chaosCanvas.getPixel(new Vector2D(0, 0)));
+    }
+
+    @Test
+    @DisplayName("Test positive putPixel(int, int, double)")
+    void putPixelInt() {
+      chaosCanvas.putPixel(0, 0, 1.0);
+      assertEquals(1.0, chaosCanvas.getPixel(new Vector2D(0, 1)));
+    }
+
+    @Test
+    @DisplayName("Test negative putPixel(int, int, double)")
+    void putPixelIntFail() {
+      chaosCanvas.putPixel(0, 0, 1.0);
+      assertNotEquals(0.0, chaosCanvas.getPixel(new Vector2D(0, 1)));
+    }
+  }
+
+  @Nested
+  @DisplayName("Test transformIndicesToCoords")
+  class TestTransformIndicesToCoords {
+    @Test
+    @DisplayName("Test positive transformIndicesToCoords")
+    void transformIndicesToCoords() {
+      Vector2D coords = chaosCanvas.transformIndicesToCoords(0, 0);
+      assertEquals(0.0, coords.getX());
+      assertEquals(1.0, coords.getY());
+    }
+
+    @Test
+    @DisplayName("Test negative transformIndicesToCoords")
+    void transformIndicesToCoordsFail() {
+      Vector2D coords = chaosCanvas.transformIndicesToCoords(0, 0);
+      assertNotEquals(1.0, coords.getX());
+      assertNotEquals(0.0, coords.getY());
+    }
+  }
+
+  @Nested
+  @DisplayName("Test clearCanvas")
+  class TestClearCanvas {
+    @Test
+    @DisplayName("Test positive clearCanvas")
+    void clearCanvas() {
+      chaosCanvas.putPixel(new Vector2D(0, 0));
+      chaosCanvas.clearCanvas();
+      assertEquals(0.0, chaosCanvas.getPixel(new Vector2D(0, 0)));
+    }
+
+    @Test
+    @DisplayName("Test negative clearCanvas")
+    void clearCanvasFail() {
+      chaosCanvas.putPixel(new Vector2D(0, 0));
+      chaosCanvas.clearCanvas();
+      double[][] canvas = chaosCanvas.getCanvasArray();
+      for (double[] row : canvas) {
+        for (double value : row) {
+          assertNotEquals(1.0, value);
+        }
+      }
+    }
   }
 
   @Test
   void getWidth() {
+    assertEquals(WIDTH, chaosCanvas.getWidth());
   }
 
   @Test
   void getHeight() {
+    assertEquals(HEIGHT, chaosCanvas.getHeight());
   }
 
   @Test
   void getMinCoords() {
+    assertEquals(minCoords, chaosCanvas.getMinCoords());
   }
 
   @Test
   void getMaxCoords() {
+    assertEquals(maxCoords, chaosCanvas.getMaxCoords());
   }
 
   @Test
   void setMinCoords() {
+    Vector2D newMinCoords = new Vector2D(-1, -1);
+    chaosCanvas.setMinCoords(newMinCoords);
+    assertEquals(newMinCoords, chaosCanvas.getMinCoords());
   }
 
   @Test
   void setMaxCoords() {
+    Vector2D newMaxCoords = new Vector2D(2, 2);
+    chaosCanvas.setMaxCoords(newMaxCoords);
+    assertEquals(newMaxCoords, chaosCanvas.getMaxCoords());
   }
 
   @Test
   void setTransformCoordsToIndices() {
-  }
-
-  @Test
-  void clearCanvas() {
+    Vector2D newMinCoords = new Vector2D(-1, -1);
+    Vector2D newMaxCoords = new Vector2D(2, 2);
+    chaosCanvas.setMinCoords(newMinCoords);
+    chaosCanvas.setMaxCoords(newMaxCoords);
+    chaosCanvas.setTransformCoordsToIndices();
+    AffineTransform2D transform = chaosCanvas.getTransformCoordsToIndices();
+    assertNotNull(transform);
+    assertEquals(transform, chaosCanvas.getTransformCoordsToIndices());
   }
 
   @Test
   void setWidth() {
+    int newWidth = 200;
+    chaosCanvas.setWidth(newWidth);
+    assertEquals(newWidth, chaosCanvas.getWidth());
   }
 
   @Test
   void setHeight() {
+    int newHeight = 200;
+    chaosCanvas.setHeight(newHeight);
+    assertEquals(newHeight, chaosCanvas.getHeight());
   }
-}
\ No newline at end of file
+}
-- 
GitLab