From 2d8eae4d1be28f76e99677272c48465932b7e2f2 Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sat, 8 Feb 2025 11:34:33 +0100
Subject: [PATCH 01/26] switched green & yellow moved gloabal variables into
 load function of spriteprovider

---
 src/editor/SpriteProvider.cpp | 44 ++++++++++++++++++++++++++++++++
 src/editor/SpriteProvider.hpp | 47 +++--------------------------------
 2 files changed, 47 insertions(+), 44 deletions(-)

diff --git a/src/editor/SpriteProvider.cpp b/src/editor/SpriteProvider.cpp
index 0bd10da..bc0d124 100644
--- a/src/editor/SpriteProvider.cpp
+++ b/src/editor/SpriteProvider.cpp
@@ -37,6 +37,50 @@ void SpriteProvider::initialize(const std::string& path)
         return;
     }
 
+/**
+ * Provides all terrain tile names.
+ * They are necessary to create the correct path to 
+ * the hdf5 dataset that contains the pixels for a given terrain tile.
+ */
+const std::vector<std::string> tile_names({"plain",
+                                  "water",
+                                  "forest",
+                                  "mountain",
+                                  "bridge_horizontal",
+                                  "bridge_vertical",
+                                  "street_horizontal",
+                                  "street_vertical",
+                                  "street_crossing",
+                                  "street_junction_right",
+                                  "street_junction_left",
+                                  "street_junction_down",
+                                  "street_junction_up",
+                                  "street_corner_top_left",
+                                  "street_corner_top_right",
+                                  "street_corner_bottom_left",
+                                  "street_corner_bottom_right",
+                                  "riff",
+                                  "cliff_top",
+                                  "cliff_bottom",
+                                  "cliff_left",
+                                  "cliff_right",
+                                  "cliff_corner_top_left",
+                                  "cliff_corner_top_right",
+                                  "cliff_corner_bottom_left",
+                                  "cliff_corner_bottom_right",
+                                  "cliff_inverse_corner_top_left",
+                                  "cliff_inverse_corner_top_right",
+                                  "cliff_inverse_corner_bottom_left",
+                                  "cliff_inverse_corner_bottom_right"});
+
+    /**
+ * Provides the names for all factions in the game.
+ * The names can be used to create the path to the hdf5 dataset
+ * containing the buildings for a given faction.
+ */
+const std::vector<std::string> faction_names(
+      {"red", "blue", "green", "yellow", "purple", "neutral"});
+
     HighFive::File file(path, HighFive::File::ReadOnly);
     sprites.reserve(60); // we now that we will load 60 sprites
 
diff --git a/src/editor/SpriteProvider.hpp b/src/editor/SpriteProvider.hpp
index 35ebe31..018deff 100644
--- a/src/editor/SpriteProvider.hpp
+++ b/src/editor/SpriteProvider.hpp
@@ -15,50 +15,6 @@
 namespace editor
 {
 
-/**
- * Provides all tile names.
- * They are necessary to create the correct path to 
- * the hdf5 dataset that contains the pixels for a given tile.
- */
-const std::vector<std::string> tile_names({"plain",
-                                  "water",
-                                  "forest",
-                                  "mountain",
-                                  "bridge_horizontal",
-                                  "bridge_vertical",
-                                  "street_horizontal",
-                                  "street_vertical",
-                                  "street_crossing",
-                                  "street_junction_right",
-                                  "street_junction_left",
-                                  "street_junction_down",
-                                  "street_junction_up",
-                                  "street_corner_top_left",
-                                  "street_corner_top_right",
-                                  "street_corner_bottom_left",
-                                  "street_corner_bottom_right",
-                                  "riff",
-                                  "cliff_top",
-                                  "cliff_bottom",
-                                  "cliff_left",
-                                  "cliff_right",
-                                  "cliff_corner_top_left",
-                                  "cliff_corner_top_right",
-                                  "cliff_corner_bottom_left",
-                                  "cliff_corner_bottom_right",
-                                  "cliff_inverse_corner_top_left",
-                                  "cliff_inverse_corner_top_right",
-                                  "cliff_inverse_corner_bottom_left",
-                                  "cliff_inverse_corner_bottom_right"});
-
-/**
- * Provides the names for all factions in the game.
- * The names can be used to create the path to the hdf5 dataset
- * containing the buildings for a given faction.
- */
-const std::vector<std::string> faction_names(
-      {"red", "blue", "yellow", "green", "purple", "neutral"});
-
 /**
  * SpriteProvider is only used in a static context.
  * SpriteProvider allows us to get the QPixmap for a given tile type
@@ -73,12 +29,14 @@ public:
      * SpriteProvider is only used in a static context
      */
     SpriteProvider() = delete;
+
     /**
      * Allows you to retrieve the QPixmap of any tile given its id.
      * @param id The id of the tile type whose sprite you want to get.
      * @return The QPixmap for the provided tile id.
      */
     static QPixmap get_sprite(uint8_t id);
+
     /**
      * Always call initialize at the start of the program, to load
      * all of the sprites from the Spritesheet under the provided path.
@@ -98,6 +56,7 @@ private:
      * @return The QPixmap object that was created from the provided pixels.
      */
     static QPixmap load_pixmap(std::vector<std::vector<std::vector<uint32_t>>> pixels, int index);
+
     /**
      * Holds all of the game's sprites for quick access.
      */
-- 
GitLab


From 6496c417d706c7e0550d4f25ef515aef11f63a27 Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sat, 8 Feb 2025 12:01:09 +0100
Subject: [PATCH 02/26] renamed AutomateButton -> AdvancedPlacementSwitch

---
 .../{AutomateButton.cpp => AdvancedPlacementSwitch.cpp}     | 6 +++---
 .../{AutomateButton.hpp => AdvancedPlacementSwitch.hpp}     | 4 ++--
 src/editor/TopBar.cpp                                       | 4 ++--
 3 files changed, 7 insertions(+), 7 deletions(-)
 rename src/editor/{AutomateButton.cpp => AdvancedPlacementSwitch.cpp} (62%)
 rename src/editor/{AutomateButton.hpp => AdvancedPlacementSwitch.hpp} (70%)

diff --git a/src/editor/AutomateButton.cpp b/src/editor/AdvancedPlacementSwitch.cpp
similarity index 62%
rename from src/editor/AutomateButton.cpp
rename to src/editor/AdvancedPlacementSwitch.cpp
index c828616..126e67d 100644
--- a/src/editor/AutomateButton.cpp
+++ b/src/editor/AdvancedPlacementSwitch.cpp
@@ -5,7 +5,7 @@
 * @author Nils Jonathan Friedrich Eckardt implementation
 */
 
-#include "AutomateButton.hpp"
+#include "AdvancedPlacementSwitch.hpp"
 #include "EventHandler.hpp"
 #include <QMessageBox>
 #include <QEvent>
@@ -13,12 +13,12 @@
 namespace editor
 {
 
-AutomateButton::AutomateButton(const QString text, QWidget* parent) : QCheckBox(text,parent)
+AdvancedPlacementSwitch::AdvancedPlacementSwitch(const QString text, QWidget* parent) : QCheckBox(text,parent)
 {
     setChecked(false);
 }
 
-void AutomateButton::mousePressEvent(QMouseEvent *event)
+void AdvancedPlacementSwitch::mousePressEvent(QMouseEvent *event)
 {
     QCheckBox::mousePressEvent(event);
     EventHandler::send([](EventHandler* e) { e->onCheckBoxToggled(); });
diff --git a/src/editor/AutomateButton.hpp b/src/editor/AdvancedPlacementSwitch.hpp
similarity index 70%
rename from src/editor/AutomateButton.hpp
rename to src/editor/AdvancedPlacementSwitch.hpp
index 1163d0c..781d184 100644
--- a/src/editor/AutomateButton.hpp
+++ b/src/editor/AdvancedPlacementSwitch.hpp
@@ -14,9 +14,9 @@
 namespace editor
 {
 
-class AutomateButton : public QCheckBox {
+class AdvancedPlacementSwitch : public QCheckBox {
 public:
-    AutomateButton(const QString text, QWidget *parent = nullptr);
+    AdvancedPlacementSwitch(const QString text, QWidget *parent = nullptr);
 protected:
     void mousePressEvent(QMouseEvent *event) override;
 };
diff --git a/src/editor/TopBar.cpp b/src/editor/TopBar.cpp
index 5e5f52c..04c6800 100644
--- a/src/editor/TopBar.cpp
+++ b/src/editor/TopBar.cpp
@@ -17,7 +17,7 @@
 #include "ZoomInButton.hpp"
 #include "ZoomInfo.hpp"
 #include "ZoomOutButton.hpp"
-#include "AutomateButton.hpp"
+#include "AdvancedPlacementSwitch.hpp"
 
 namespace editor
 {
@@ -41,7 +41,7 @@ TopBar::TopBar(const std::string& level_name, QWidget* parent) : QToolBar(parent
     QPushButton* zoom_in = new ZoomInButton(right_container);
     QPushButton* zoom_out = new ZoomOutButton(right_container);
     QPushButton* zoom_info = new ZoomInfo(right_container);
-    AutomateButton* checkedBox = new AutomateButton("Kacheln automatisch setzen", container);
+    AdvancedPlacementSwitch* checkedBox = new AdvancedPlacementSwitch("Kacheln automatisch setzen", container);
     left_layout->addWidget(checkedBox);
     right_layout->addStretch();
     right_layout->addWidget(zoom_out);
-- 
GitLab


From 2e657c8e639e7e8ee4776ed05c2b38099c4be7bd Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sat, 8 Feb 2025 12:01:33 +0100
Subject: [PATCH 03/26] eliminated all compiler warnings for level editor

---
 src/editor/EventHandler.hpp  | 15 +++++++--------
 src/editor/LevelScene.cpp    |  9 +++++----
 src/editor/LevelScene.hpp    |  6 +++---
 src/editor/Tile.cpp          |  6 +++---
 src/editor/Tile.hpp          |  6 +++---
 src/editor/ZoomInButton.cpp  |  2 +-
 src/editor/ZoomInButton.hpp  |  2 +-
 src/editor/ZoomOutButton.cpp |  2 +-
 src/editor/ZoomOutButton.hpp |  2 +-
 9 files changed, 25 insertions(+), 25 deletions(-)

diff --git a/src/editor/EventHandler.hpp b/src/editor/EventHandler.hpp
index ebc317b..f0fba25 100644
--- a/src/editor/EventHandler.hpp
+++ b/src/editor/EventHandler.hpp
@@ -59,47 +59,46 @@ public:
      * by the level name edit field.
      * @param new_name The new level name.
      */
-    virtual void onLevelNameUpdated(std::string new_name){};
+    virtual void onLevelNameUpdated(std::string){};
 
     /**
      * Overwrite this event method to handle the dispatch of a request to write 
      * the level to disk by the save button.
      * @param file_path The path to the file into which the level should be written.
      */
-    virtual void onLevelWriteRequested(QString file_path){};
+    virtual void onLevelWriteRequested(QString){};
 
     /**
      * Overwrite this event method to handle the dispatch of a new tile index due
      * to the mouse entering its boundaries.
      * @param index The index of the entered tile.
      */
-    virtual void onTileEntered(int index){};
+    virtual void onTileEntered(int){};
 
     /**
      * Overwrite this event method to handle the dispatch of a new tile index due
      * to the mouse leaving its boundaries.
      * @param index The index of the exited tile.
      */
-    virtual void onTileExited(int index){};
+    virtual void onTileExited(int){};
 
     /**
      * Overwrite this event method to handle the dispatch of a new tile index due
      * to the user clicking it.
      * @param index The index of the clicked tile.
      */
-    virtual void onTileClicked(int index){};
+    virtual void onTileClicked(int){};
 
     /**
      * Overwrite this event method to handle the dispatch of a new tile_id due to 
      * the user selecting a different tile type in the TileSelector on the right.
      * @param tile_id Id of the tile to use when an existing tile is clicked on the levelmap.
      */
-    virtual void onNewTileIdSelected(uint8_t tile_id){};
+    virtual void onNewTileIdSelected(uint8_t){};
 
     /**
      * Overwrite this event method to handle the change of tile placement method due
      * to the user selecting automatic tile placement assisstance.
-     * @param isToggled Boolean that enables tile placing assisstment.
      */
     virtual void onCheckBoxToggled(){};
 
@@ -108,7 +107,7 @@ public:
      * the user pressing the zoom in or zoom out button.
      * @param delta Amount to zoom in or out, e.g 0.2 => 20% in, -0.2 => 20% out.
      */
-    virtual void onZoomed(double delta){}
+    virtual void onZoomed(double){}
 
 private:
     /**
diff --git a/src/editor/LevelScene.cpp b/src/editor/LevelScene.cpp
index 836e917..650fc14 100644
--- a/src/editor/LevelScene.cpp
+++ b/src/editor/LevelScene.cpp
@@ -13,6 +13,7 @@
 #include <QPoint>
 #include <boost/property_tree/ptree.hpp>
 #include <boost/property_tree/xml_parser.hpp>
+#include <stdexcept>
 
 
 #include "highfive/H5File.hpp"
@@ -25,13 +26,12 @@ LevelScene::LevelScene(
     const std::string& name, int width, int height, std::vector<uint8_t> tile_ids,
     const std::string& file_path, QWidget* parent)
     : QGraphicsScene(parent), m_name(name), m_width(width), m_height(height), m_tile_ids(tile_ids),
-      m_file_path(file_path), m_selected_tile_id(2)
+      m_file_path(file_path), m_selected_tile_id(2), m_advanced_tile_placement(false)
 {
     setSceneRect(0, 0, m_width * 16, m_height * 16);
-    m_advanced_tile_placement = false;
     m_tile_occupants = {};
     m_tile_occupants.reserve(tile_ids.size());
-    for (int index = 0; index < tile_ids.size(); index++)
+    for (size_t index = 0; index < tile_ids.size(); index++)
     {
         int   x = (index % m_width) * 16;
         int   y = (index / m_width) * 16;
@@ -184,7 +184,7 @@ void LevelScene::onTileEntered(int index)
         delete m_tile_occupants[index];
         m_tile_occupants[index] = nullptr;
     }
-    if (!is_border(index) && m_selected_tile_id > 0 || is_border(index))
+    if ((!is_border(index) && m_selected_tile_id > 0) || is_border(index))
     {
         m_tile_occupants[index] = occupy_tile(index, m_selected_tile_id);
     }
@@ -483,6 +483,7 @@ int LevelScene::calcDir(int i, int index){
     if(i==5) return (index + m_width - 1);
     if(i==6) return (index - 1);
     if(i==7) return (index - m_width - 1);
+    throw std::invalid_argument("i has to be 0 <= i <= 7");
 }
 
 bool LevelScene::isntIdentical(int16_t id, int index){
diff --git a/src/editor/LevelScene.hpp b/src/editor/LevelScene.hpp
index 4f69c7e..4327c8a 100644
--- a/src/editor/LevelScene.hpp
+++ b/src/editor/LevelScene.hpp
@@ -44,14 +44,14 @@ private:
     void placeRoad(int index, bool updateFlag);
     int calcDir(int i, int index);
     QGraphicsPixmapItem* occupy_tile(int index, uint8_t tile_id);
-    uint8_t m_selected_tile_id;
     std::string m_name;
-    bool m_advanced_tile_placement;
     int m_width;
     int m_height;
     std::vector<uint8_t> m_tile_ids;
-    std::vector<QGraphicsPixmapItem*> m_tile_occupants;
     std::string m_file_path;
+    uint8_t m_selected_tile_id;
+    bool m_advanced_tile_placement;
+    std::vector<QGraphicsPixmapItem*> m_tile_occupants;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/Tile.cpp b/src/editor/Tile.cpp
index bf33267..42846f9 100644
--- a/src/editor/Tile.cpp
+++ b/src/editor/Tile.cpp
@@ -18,19 +18,19 @@ Tile::Tile(int index, uint8_t id) : QGraphicsPixmapItem(SpriteProvider::get_spri
     this->setAcceptHoverEvents(true);
 }
 
-void Tile::hoverEnterEvent(QGraphicsSceneHoverEvent* event)
+void Tile::hoverEnterEvent(QGraphicsSceneHoverEvent*)
 {
     int index = this->m_index;
     EventHandler::send([index](EventHandler* e) { e->onTileEntered(index); });
 }
 
-void Tile::hoverLeaveEvent(QGraphicsSceneHoverEvent* event)
+void Tile::hoverLeaveEvent(QGraphicsSceneHoverEvent*)
 {
     int index = this->m_index;
     EventHandler::send([index](EventHandler* e) { e->onTileExited(index); });
 }
 
-void Tile::mousePressEvent(QGraphicsSceneMouseEvent* event)
+void Tile::mousePressEvent(QGraphicsSceneMouseEvent*)
 {
     int index = this->m_index;
     EventHandler::send([index](EventHandler* e) { e->onTileClicked(index); });
diff --git a/src/editor/Tile.hpp b/src/editor/Tile.hpp
index c842945..d92d6fe 100644
--- a/src/editor/Tile.hpp
+++ b/src/editor/Tile.hpp
@@ -17,9 +17,9 @@ public:
     Tile(int index, uint8_t id);
 
 private:
-    void hoverEnterEvent(QGraphicsSceneHoverEvent *event) override;
-    void hoverLeaveEvent(QGraphicsSceneHoverEvent *event) override;
-    void mousePressEvent(QGraphicsSceneMouseEvent *event) override;
+    void hoverEnterEvent(QGraphicsSceneHoverEvent*) override;
+    void hoverLeaveEvent(QGraphicsSceneHoverEvent*) override;
+    void mousePressEvent(QGraphicsSceneMouseEvent*) override;
     int m_index;
 };
 
diff --git a/src/editor/ZoomInButton.cpp b/src/editor/ZoomInButton.cpp
index 3f15b79..1031780 100644
--- a/src/editor/ZoomInButton.cpp
+++ b/src/editor/ZoomInButton.cpp
@@ -17,7 +17,7 @@ ZoomInButton::ZoomInButton(QWidget* parent) : QPushButton("+", parent)
     setFixedWidth(20);
 }
 
-void ZoomInButton::mousePressEvent(QMouseEvent* event)
+void ZoomInButton::mousePressEvent(QMouseEvent*)
 {
     EventHandler::send([](EventHandler* e) { e->onZoomed(0.25); });
 }
diff --git a/src/editor/ZoomInButton.hpp b/src/editor/ZoomInButton.hpp
index 99332ab..cc73ded 100644
--- a/src/editor/ZoomInButton.hpp
+++ b/src/editor/ZoomInButton.hpp
@@ -16,7 +16,7 @@ class ZoomInButton : public QPushButton {
 public:
     ZoomInButton(QWidget* parent = nullptr);
 private:
-    void mousePressEvent(QMouseEvent* event) override;
+    void mousePressEvent(QMouseEvent*) override;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/ZoomOutButton.cpp b/src/editor/ZoomOutButton.cpp
index aec5b32..98e5aa6 100644
--- a/src/editor/ZoomOutButton.cpp
+++ b/src/editor/ZoomOutButton.cpp
@@ -17,7 +17,7 @@ ZoomOutButton::ZoomOutButton(QWidget* parent) : QPushButton("-", parent)
     setFixedWidth(20);
 }
 
-void ZoomOutButton::mousePressEvent(QMouseEvent* event)
+void ZoomOutButton::mousePressEvent(QMouseEvent*)
 {
     EventHandler::send([](EventHandler* e) { e->onZoomed(-0.25); });
 }
diff --git a/src/editor/ZoomOutButton.hpp b/src/editor/ZoomOutButton.hpp
index e13c570..b522223 100644
--- a/src/editor/ZoomOutButton.hpp
+++ b/src/editor/ZoomOutButton.hpp
@@ -16,7 +16,7 @@ class ZoomOutButton : public QPushButton {
 public:
     ZoomOutButton(QWidget* parent = nullptr);
 private:
-    void mousePressEvent(QMouseEvent* event) override;
+    void mousePressEvent(QMouseEvent*) override;
 };
 
 } // namespace editor
\ No newline at end of file
-- 
GitLab


From 23d8c3a14a0d4bc10f229949e08d9d42335e905e Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sat, 8 Feb 2025 12:03:59 +0100
Subject: [PATCH 04/26] renamed onCheckboxToggled -> onAdvancedPlacementToggled

---
 src/editor/AdvancedPlacementSwitch.cpp | 2 +-
 src/editor/EventHandler.hpp            | 2 +-
 src/editor/LevelScene.cpp              | 2 +-
 src/editor/LevelScene.hpp              | 2 +-
 4 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/src/editor/AdvancedPlacementSwitch.cpp b/src/editor/AdvancedPlacementSwitch.cpp
index 126e67d..4812746 100644
--- a/src/editor/AdvancedPlacementSwitch.cpp
+++ b/src/editor/AdvancedPlacementSwitch.cpp
@@ -21,7 +21,7 @@ AdvancedPlacementSwitch::AdvancedPlacementSwitch(const QString text, QWidget* pa
 void AdvancedPlacementSwitch::mousePressEvent(QMouseEvent *event)
 {
     QCheckBox::mousePressEvent(event);
-    EventHandler::send([](EventHandler* e) { e->onCheckBoxToggled(); });
+    EventHandler::send([](EventHandler* e) { e->onAdvancedPlacementToggled(); });
 }
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/EventHandler.hpp b/src/editor/EventHandler.hpp
index f0fba25..67d4e1e 100644
--- a/src/editor/EventHandler.hpp
+++ b/src/editor/EventHandler.hpp
@@ -100,7 +100,7 @@ public:
      * Overwrite this event method to handle the change of tile placement method due
      * to the user selecting automatic tile placement assisstance.
      */
-    virtual void onCheckBoxToggled(){};
+    virtual void onAdvancedPlacementToggled(){};
 
     /**
      * Overwrite this event method to handle the dispatch of a new delta due to 
diff --git a/src/editor/LevelScene.cpp b/src/editor/LevelScene.cpp
index 650fc14..74e6519 100644
--- a/src/editor/LevelScene.cpp
+++ b/src/editor/LevelScene.cpp
@@ -279,7 +279,7 @@ void LevelScene::onNewTileIdSelected(uint8_t tile_id)
     m_selected_tile_id = tile_id;
 }
 
-void LevelScene::onCheckBoxToggled()
+void LevelScene::onAdvancedPlacementToggled()
 {
     m_advanced_tile_placement = !m_advanced_tile_placement;
 }
diff --git a/src/editor/LevelScene.hpp b/src/editor/LevelScene.hpp
index 4327c8a..c04b2a7 100644
--- a/src/editor/LevelScene.hpp
+++ b/src/editor/LevelScene.hpp
@@ -38,7 +38,7 @@ private:
     void onTileExited(int index) override;
     void onTileClicked(int index) override;
     void onNewTileIdSelected(uint8_t tile_id) override;
-    void onCheckBoxToggled() override;
+    void onAdvancedPlacementToggled() override;
     void setTile(int index, uint8_t id);
     void placeCliff(bool placedLand, int index);
     void placeRoad(int index, bool updateFlag);
-- 
GitLab


From 9b694049b65e0dc1d5f043d561b9c0ff140193d1 Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sat, 8 Feb 2025 12:17:19 +0100
Subject: [PATCH 05/26] fixed top level file comments

---
 src/editor/AdvancedPlacementSwitch.cpp | 3 ++-
 src/editor/AdvancedPlacementSwitch.hpp | 3 ++-
 src/editor/EventHandler.hpp            | 4 ++--
 src/editor/LevelNameEdit.cpp           | 2 +-
 src/editor/LevelNameEdit.hpp           | 2 +-
 src/editor/LevelScene.cpp              | 1 +
 src/editor/LevelScene.hpp              | 3 ++-
 src/editor/TileButton.cpp              | 2 +-
 src/editor/TileButton.hpp              | 2 +-
 9 files changed, 13 insertions(+), 9 deletions(-)

diff --git a/src/editor/AdvancedPlacementSwitch.cpp b/src/editor/AdvancedPlacementSwitch.cpp
index 4812746..0572c37 100644
--- a/src/editor/AdvancedPlacementSwitch.cpp
+++ b/src/editor/AdvancedPlacementSwitch.cpp
@@ -1,8 +1,9 @@
 /**
-* TileSelector.cpp
+* AdvancedPlacementSwitch.cpp
 *
 * @date 06.02.2025
 * @author Nils Jonathan Friedrich Eckardt implementation
+* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) small changes
 */
 
 #include "AdvancedPlacementSwitch.hpp"
diff --git a/src/editor/AdvancedPlacementSwitch.hpp b/src/editor/AdvancedPlacementSwitch.hpp
index 781d184..e96ef0f 100644
--- a/src/editor/AdvancedPlacementSwitch.hpp
+++ b/src/editor/AdvancedPlacementSwitch.hpp
@@ -1,8 +1,9 @@
 /**
-* TileSelector.hpp
+* AdvancedPlacementSwitch.hpp
 *
 * @date 06.02.2025
 * @author Nils Jonathan Friedrich Eckardt implementation
+* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) small changes
 */
 
 #pragma once
diff --git a/src/editor/EventHandler.hpp b/src/editor/EventHandler.hpp
index 67d4e1e..17835b6 100644
--- a/src/editor/EventHandler.hpp
+++ b/src/editor/EventHandler.hpp
@@ -1,9 +1,9 @@
 /**
-* EventHandler.cpp
+* EventHandler.hpp
 *
 * @date 29.01.2025
 * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-* @author Nils Jonathan Friedrich Eckardt onCheckBoxToggle added
+* @author Nils Jonathan Friedrich Eckardt onAdvancedPlaement added
 */
 
 #pragma once
diff --git a/src/editor/LevelNameEdit.cpp b/src/editor/LevelNameEdit.cpp
index c6debb4..8d38b81 100644
--- a/src/editor/LevelNameEdit.cpp
+++ b/src/editor/LevelNameEdit.cpp
@@ -1,5 +1,5 @@
 /**
-* EventHandler.cpp
+* LevelNameEdit.cpp
 *
 * @date 29.01.2025
 * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
diff --git a/src/editor/LevelNameEdit.hpp b/src/editor/LevelNameEdit.hpp
index 1ce0265..650a8b2 100644
--- a/src/editor/LevelNameEdit.hpp
+++ b/src/editor/LevelNameEdit.hpp
@@ -1,5 +1,5 @@
 /**
-* EventHandler.cpp
+* LevelNameEdit.hpp
 *
 * @date 29.01.2025
 * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
diff --git a/src/editor/LevelScene.cpp b/src/editor/LevelScene.cpp
index 74e6519..4425b67 100644
--- a/src/editor/LevelScene.cpp
+++ b/src/editor/LevelScene.cpp
@@ -4,6 +4,7 @@
 * @date 28.01.2025
 * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
 * @author Nils Jonathan Friedrich Eckardt implemented advanced placement
+*         (onTileClicked, setTile, placeCliff, placeRoad, calcDir)
 */
 
 #include "LevelScene.hpp"
diff --git a/src/editor/LevelScene.hpp b/src/editor/LevelScene.hpp
index c04b2a7..f1ed73d 100644
--- a/src/editor/LevelScene.hpp
+++ b/src/editor/LevelScene.hpp
@@ -3,7 +3,8 @@
 *
 * @date 28.01.2025
 * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-* @author Nils Jonathan Friedrich Eckardt minor changes
+* @author Nils Jonathan Friedrich Eckardt implementing advanced placement
+*         (onTileClicked, setTile, placeCliff, placeRoad, calcDir)
 */
 
 #pragma once
diff --git a/src/editor/TileButton.cpp b/src/editor/TileButton.cpp
index b302955..8d3a392 100644
--- a/src/editor/TileButton.cpp
+++ b/src/editor/TileButton.cpp
@@ -1,5 +1,5 @@
 /**
-* TileSelector.cpp
+* TileButton.cpp
 *
 * @date 29.01.2025
 * @author Nils Jonathan Friedrich Eckardt implementation
diff --git a/src/editor/TileButton.hpp b/src/editor/TileButton.hpp
index 52e1fca..6260cf0 100644
--- a/src/editor/TileButton.hpp
+++ b/src/editor/TileButton.hpp
@@ -1,5 +1,5 @@
 /**
-* TileSelector.hpp
+* TileButton.hpp
 *
 * @date 29.01.2025
 * @author Nils Jonathan Friedrich Eckardt implementation
-- 
GitLab


From 371aaef9eb55939fff1d07fa8d9f2817731a4bf8 Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sat, 8 Feb 2025 12:34:01 +0100
Subject: [PATCH 06/26] added doc comments for AdvancedPlacementSwitch

---
 src/editor/AdvancedPlacementSwitch.hpp | 16 +++++++++++++++-
 1 file changed, 15 insertions(+), 1 deletion(-)

diff --git a/src/editor/AdvancedPlacementSwitch.hpp b/src/editor/AdvancedPlacementSwitch.hpp
index e96ef0f..214e54c 100644
--- a/src/editor/AdvancedPlacementSwitch.hpp
+++ b/src/editor/AdvancedPlacementSwitch.hpp
@@ -3,7 +3,7 @@
 *
 * @date 06.02.2025
 * @author Nils Jonathan Friedrich Eckardt implementation
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) small changes
+* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) small changes, doc comments
 */
 
 #pragma once
@@ -15,10 +15,24 @@
 namespace editor
 {
 
+/**
+ * The AdvancedPlacementSwitch is displayed in the TopBar and allows the user to switch between
+ * regular tile placement and advanced tile placement.
+ */
 class AdvancedPlacementSwitch : public QCheckBox {
 public:
+    /**
+     * Creates an AdvancedPlacementSwitch as QCheckBox using the provided text and parent.
+     * @param text The description to display next to the CheckBox.
+     * @param parent The parent for this widget.
+     */
     AdvancedPlacementSwitch(const QString text, QWidget *parent = nullptr);
 protected:
+    /**
+     * Receives a QMouseEvent when the QCheckBox is pressed and subsequently emits
+     * the onAdvancedPlacementToggled event method.
+     * @param event The QMouseEvent for the CheckBox Pressing.
+     */
     void mousePressEvent(QMouseEvent *event) override;
 };
 
-- 
GitLab


From 0bdc2c2f4e9a100aea75d70791e9b8042f38cf41 Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sat, 8 Feb 2025 12:34:16 +0100
Subject: [PATCH 07/26] improved doc comments for LevelNameEdit and LevelView

---
 src/editor/LevelNameEdit.hpp | 5 +++++
 src/editor/LevelView.hpp     | 3 +++
 2 files changed, 8 insertions(+)

diff --git a/src/editor/LevelNameEdit.hpp b/src/editor/LevelNameEdit.hpp
index 650a8b2..824d336 100644
--- a/src/editor/LevelNameEdit.hpp
+++ b/src/editor/LevelNameEdit.hpp
@@ -26,6 +26,11 @@ public:
      */
     LevelNameEdit(const std::string& level_name, QWidget* parent = nullptr);
 protected:
+    /**
+     * Receives a QKeyEvent when the user presses a key to change the content of the QLineEdit.
+     * The onLevelNameUpdated event method is subsequently emitted. 
+     * @param event The QKeyEvent for the Key Press.
+     */
     void keyPressEvent(QKeyEvent* event) override;
 };
 
diff --git a/src/editor/LevelView.hpp b/src/editor/LevelView.hpp
index 13d4bea..78dca53 100644
--- a/src/editor/LevelView.hpp
+++ b/src/editor/LevelView.hpp
@@ -30,14 +30,17 @@ public:
      * @param parent The widget to set as this widget's parent.
      */
     LevelView(LevelScene* scene, QWidget* parent = nullptr);
+
 private:
     /**
      * The current value by which the contained scene is scaled up or down.
      * E.g 2.0 => twice the size, 0.5 => half the size
      */
     double scale_val;
+
     /**
      * Zoom by the specified delta.
+     * @param delta The amount by which to zoom.
      */
     void onZoomed(double delta) override;
 };
-- 
GitLab


From 22d7fe6f11bb92227dd33930f29ddf8065ca1e8d Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sat, 8 Feb 2025 19:16:55 +0100
Subject: [PATCH 08/26] added doc comments for MainWindow, SaveButton, TIle,
 TopBar, ZoomInButton, ZoomInfo, ZoomOutButton

---
 src/editor/MainWindow.hpp    | 29 +++++++++++++++++++++++++++++
 src/editor/SaveButton.hpp    | 18 ++++++++++++++++++
 src/editor/Tile.hpp          | 35 +++++++++++++++++++++++++++++++++++
 src/editor/TileSelector.hpp  |  2 +-
 src/editor/TopBar.hpp        | 17 +++++++++++++++++
 src/editor/ZoomInButton.hpp  | 14 ++++++++++++++
 src/editor/ZoomInfo.hpp      | 14 ++++++++++++++
 src/editor/ZoomOutButton.hpp | 14 ++++++++++++++
 8 files changed, 142 insertions(+), 1 deletion(-)

diff --git a/src/editor/MainWindow.hpp b/src/editor/MainWindow.hpp
index 8f1844b..36c16b6 100644
--- a/src/editor/MainWindow.hpp
+++ b/src/editor/MainWindow.hpp
@@ -15,12 +15,41 @@
 namespace editor 
 {
 
+/**
+ * MainWindow is the top level Widget of the LevelEditor. 
+ * All other Widgets are children of MainWindow. 
+ * MainWindow is instantiated on the stack in main.cpp.
+ * Thus, MainWindow is freed automatically at application exit together
+ * with all of the other widgets (descendants), because of the way memory management works in QT.
+ * MainWindow inherits from EventHandler so that it can override onLevelNameUpadated in order
+ * to change the window title when the level name is changed.
+ */
 class MainWindow : public QMainWindow, public EventHandler {
 public:
+    /**
+     * Creates a MainWindow from the given LevelScene and parent.
+     * @param level The LevelScene of the level that should be edited.
+     * @param parent The parent widget for the MainWindow.
+     */
     MainWindow(LevelScene* level, QWidget *parent = nullptr);
+
 private:
+    /**
+     * Updates the Window Title with the new_name.
+     * @param new_name The new level name.
+     */
     void onLevelNameUpdated(std::string new_name) override;
+
+    /**
+     * The widht of the level that is being edited.
+     * Unit: number of tiles.
+     */
     int m_level_width;
+
+    /**
+     * The height of the level that is being edited.
+     * Unit: number of tiles.
+     */ 
     int level_height;
 };
 
diff --git a/src/editor/SaveButton.hpp b/src/editor/SaveButton.hpp
index f139961..a117f40 100644
--- a/src/editor/SaveButton.hpp
+++ b/src/editor/SaveButton.hpp
@@ -12,10 +12,28 @@
 namespace editor
 {
 
+/**
+ * The Save Button is displayed on the top right in the TopBar. 
+ * Clicking it opens the file save dialog. 
+ * It is not responsible for writing the level itself. 
+ * Instead it collects the desired file path from the file save dialog and
+ * emits the onLevelWriteRequested event method which is overwritten by the LevelScene.
+ */
 class SaveButton : public QPushButton {
 public:
+    /**
+     * Creates a SaveButton with the given title and parent.
+     * @param title The title to display inside the SaveButton.
+     * @param parent The parent that should be set for the SaveButton.
+     */
     SaveButton(const std::string& title, QWidget *parent = nullptr);
+
 protected:
+    /**
+     * Opens the file save dialog, collects the desired file path and emits
+     * the onLevelWriteRequested event method.
+     * @param event The QMouseEvent for the mouse press.
+     */
     void mousePressEvent(QMouseEvent* event) override;
 };
 
diff --git a/src/editor/Tile.hpp b/src/editor/Tile.hpp
index d92d6fe..b978d12 100644
--- a/src/editor/Tile.hpp
+++ b/src/editor/Tile.hpp
@@ -12,14 +12,49 @@
 namespace editor
 {
 
+/**
+ * The bottom (static) Layer of the LevelScene consists of Tile instances.
+ * The purpose of the Tile object is to notify the QGraphicsScene when the mouse
+ * enters/leaves/presses a specific tile of the map.
+ * Thus Tile subclasses QGraphicsPixmapItem and overrides hoverEnterEvent, hoverLeaveEvent
+ * and mousePressEvent.
+ * Every Tile is instantiated with its index so that it can send that index to the LevelScene
+ * in case it registers a hover/enter/press event.
+ */
 class Tile : public QGraphicsPixmapItem {
 public:
+    /**
+     * Creates a Tile instance for the given index with the given tile id.
+     * @param index The index of the tile if you were to linearize the level map.
+     * @param id The tile id, e.g. 0 -> grass, 1-> water, ...
+     */
     Tile(int index, uint8_t id);
 
 private:
+    /**
+     * When a hover enter event is received it
+     * emits the onTileEntered event method with the tile's index.
+     * The LevelScene overwrites the onTileEntered event method.
+     */
     void hoverEnterEvent(QGraphicsSceneHoverEvent*) override;
+
+    /**
+     * When a hover leave event is received it
+     * emits the onTileExited event method with the tile's index.
+     * The LevelScene overwrites the onTileExited event method.
+     */
     void hoverLeaveEvent(QGraphicsSceneHoverEvent*) override;
+
+    /**
+     * When a mouse press event is received it
+     * emits the onTileClicked event method with the tile's index.
+     * The LevelScene overwrites the onTileClicked event method.
+     */
     void mousePressEvent(QGraphicsSceneMouseEvent*) override;
+
+    /**
+     * The index of the tile if you were to linearize the level map.
+     */
     int m_index;
 };
 
diff --git a/src/editor/TileSelector.hpp b/src/editor/TileSelector.hpp
index 5abd400..2b0ebd8 100644
--- a/src/editor/TileSelector.hpp
+++ b/src/editor/TileSelector.hpp
@@ -2,8 +2,8 @@
 * TileSelector.cpp
 *
 * @date 28.01.2025
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) skeleton
 * @author Nils Jonathan Friedrich Eckardt implementation
+* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) skeleton
 */
 
 #pragma once
diff --git a/src/editor/TopBar.hpp b/src/editor/TopBar.hpp
index a65f453..105157d 100644
--- a/src/editor/TopBar.hpp
+++ b/src/editor/TopBar.hpp
@@ -12,8 +12,25 @@
 namespace editor
 {
 
+/**
+ * The TopBar provides key functionality for the LevelEditor:
+ * - LineEdit for setting the level name
+ * - CheckBox for toggling advanced placement on and off
+ * - ZoomInButton
+ * - ZoomOutButton
+ * - ZoomInfo (displays current zoom percentage)
+ * - SaveButon
+ * TopBar inherits from QToolBar to ensure the QT look and fell.
+ */
 class TopBar : public QToolBar {
 public: 
+    /**
+     * Creates a TopBar with the provided level_name and parent.
+     * The level_name is needed to prefill the LineEdit in the TopBar with
+     * the current level name.
+     * @param level_name The current name of the level.
+     * @param parent The parent to set for the TopBar.
+     */
     TopBar(const std::string& level_name, QWidget *parent = nullptr);
 };
 
diff --git a/src/editor/ZoomInButton.hpp b/src/editor/ZoomInButton.hpp
index cc73ded..4faef07 100644
--- a/src/editor/ZoomInButton.hpp
+++ b/src/editor/ZoomInButton.hpp
@@ -12,10 +12,24 @@
 namespace editor
 {
 
+/**
+ * The ZoomInButton is a part of the TopBar.
+ * It listens to mouse presses and emits the onZoomed event method
+ * with a delta of 0.25 in case of a mouse press.
+ */
 class ZoomInButton : public QPushButton {
 public:
+    /**
+     * Creates a ZoomInButton with the provided parent.
+     * @param parent The parent to set for the ZoomInButton.
+     */
     ZoomInButton(QWidget* parent = nullptr);
+
 private:
+    /**
+     * When a mouse press event is received,
+     * it emits the onZoomed event method with a delta of 0.25.
+     */
     void mousePressEvent(QMouseEvent*) override;
 };
 
diff --git a/src/editor/ZoomInfo.hpp b/src/editor/ZoomInfo.hpp
index f539182..74b36dc 100644
--- a/src/editor/ZoomInfo.hpp
+++ b/src/editor/ZoomInfo.hpp
@@ -14,11 +14,25 @@
 namespace editor
 {
 
+/**
+ * ZoomInfo inherits from QPushButton, but doesn't actually act as a button. 
+ * It just displays the current zoom percentage.
+ * To update the text that is displayed in case of a zoom change, it 
+ * inherits from EventHandler and overwrites the onZoomed event method.
+ */
 class ZoomInfo : public QPushButton, public EventHandler {
 public:
     ZoomInfo(QWidget* parent = nullptr);
 private:
+    /**
+     * The percentage by which the LevelMap is zoomed in/out at the moment.
+     */
     double current_scale;
+
+    /**
+     * Updates the zoom info text to correctly display the updated zoom percentage.
+     * @param delta The percentage to add/subtract to the current zoom percentage.
+     */
     void onZoomed(double delta) override;
 };
 
diff --git a/src/editor/ZoomOutButton.hpp b/src/editor/ZoomOutButton.hpp
index b522223..00969ea 100644
--- a/src/editor/ZoomOutButton.hpp
+++ b/src/editor/ZoomOutButton.hpp
@@ -12,10 +12,24 @@
 namespace editor
 {
 
+/**
+ * The ZoomOutButton is a part of the TopBar.
+ * It listens to mouse presses and emits the onZoomed event method
+ * with a delta of -0.25 in case of a mouse press.
+ */
 class ZoomOutButton : public QPushButton {
 public:
+    /**
+    * Creates a ZoomInButton with the provided parent.
+    * @param parent The parent to set for the ZoomInButton.
+    */
     ZoomOutButton(QWidget* parent = nullptr);
+
 private:
+    /**
+     * When a mouse press event is received,
+     * it emits the onZoomed event method with a delta of 0.25.
+     */
     void mousePressEvent(QMouseEvent*) override;
 };
 
-- 
GitLab


From dfd16984062e2e7e7495ccabb0375a2641dffcaa Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sun, 9 Feb 2025 00:06:12 +0100
Subject: [PATCH 09/26] improved level saving usability

---
 src/editor/EventHandler.hpp |  3 +-
 src/editor/LevelScene.cpp   | 62 +++++++++++++++++++++++++++----------
 src/editor/LevelScene.hpp   |  2 +-
 src/editor/SaveButton.cpp   | 10 ++----
 src/editor/SaveButton.hpp   |  8 ++---
 5 files changed, 54 insertions(+), 31 deletions(-)

diff --git a/src/editor/EventHandler.hpp b/src/editor/EventHandler.hpp
index 17835b6..88acc02 100644
--- a/src/editor/EventHandler.hpp
+++ b/src/editor/EventHandler.hpp
@@ -64,9 +64,8 @@ public:
     /**
      * Overwrite this event method to handle the dispatch of a request to write 
      * the level to disk by the save button.
-     * @param file_path The path to the file into which the level should be written.
      */
-    virtual void onLevelWriteRequested(QString){};
+    virtual void onLevelWriteRequested(){};
 
     /**
      * Overwrite this event method to handle the dispatch of a new tile index due
diff --git a/src/editor/LevelScene.cpp b/src/editor/LevelScene.cpp
index 4425b67..9fc4e5f 100644
--- a/src/editor/LevelScene.cpp
+++ b/src/editor/LevelScene.cpp
@@ -12,11 +12,12 @@
 #include <QGraphicsPixmapItem>
 #include <QPixmap>
 #include <QPoint>
+#include <QMessageBox>
+#include <QFileDialog>
 #include <boost/property_tree/ptree.hpp>
 #include <boost/property_tree/xml_parser.hpp>
 #include <stdexcept>
 
-
 #include "highfive/H5File.hpp"
 #include "SpriteProvider.hpp"
 
@@ -29,23 +30,31 @@ LevelScene::LevelScene(
     : QGraphicsScene(parent), m_name(name), m_width(width), m_height(height), m_tile_ids(tile_ids),
       m_file_path(file_path), m_selected_tile_id(2), m_advanced_tile_placement(false)
 {
-    setSceneRect(0, 0, m_width * 16, m_height * 16);
-    m_tile_occupants = {};
-    m_tile_occupants.reserve(tile_ids.size());
+    setSceneRect(0, 0, m_width * 16, m_height * 16); // set dimensions of the QGraphicsScene
+
+    // iterate over all of the level map's tile id and build the two layers 
+    // bottom layer (static) -> Tile classes (QGraphicsPixmapItem descendants)
+    // top layer (dynamic) -> direct QGraphicsPixmapItems (also stored in m_tile_occupants)
+    m_tile_occupants = {}; // holds QGraphicsPixmapItems of top layer (nullptr if top pximap item not needed)
+    m_tile_occupants.reserve(tile_ids.size()); // size will be same as tile ids array at the end
     for (size_t index = 0; index < tile_ids.size(); index++)
     {
         int   x = (index % m_width) * 16;
         int   y = (index / m_width) * 16;
         Tile* tile = new Tile(index, is_border(index) ? tile_ids[index] : 0);
         addItem(tile);
-        tile->setZValue(0);
+        tile->setZValue(0); // bottom layer always has z value 0
         tile->setPos(x, y);
         if (!is_border(index) && tile_ids[index] > 0)
         {
+            // if index is not on border and tile id is not grass the top layer is needed
+            // the top QGraphicsPixmapItem also needs to be stored to be able to switch
+            // it out for a different one later
             m_tile_occupants.push_back(occupy_tile(index, tile_ids[index]));
         }
         else
         {
+            // top layer not needed
             m_tile_occupants.push_back(nullptr);
         }
     }
@@ -53,7 +62,6 @@ LevelScene::LevelScene(
 
 LevelScene* LevelScene::empty(const std::string& name, int width, int height, QWidget* parent)
 {
-    // + 2 because of surrounding the map with cliffs
     std::vector<uint8_t> tile_ids;
     tile_ids.reserve(width*height);
 
@@ -64,7 +72,7 @@ LevelScene* LevelScene::empty(const std::string& name, int width, int height, QW
     }
     tile_ids.push_back(23); // cliff corner top right 
 
-    // create main rows with cliff at start and end
+    // create main rows with cliff at start and end grass in the middle
     for (int i = 0; i < height - 2; i++) {
         tile_ids.push_back(21); // cliff right
         for (int j = 0; j < width - 2; j++) {
@@ -80,7 +88,7 @@ LevelScene* LevelScene::empty(const std::string& name, int width, int height, QW
     }
     tile_ids.push_back(25); // cliff corner bottom right 
 
-    return new LevelScene(name, width, height, tile_ids, "../res/level_new.h5", parent);
+    return new LevelScene(name, width, height, tile_ids, "", parent);
 }
 
 LevelScene* LevelScene::fromFile(const std::string& file_path, QWidget* parent)
@@ -147,8 +155,24 @@ void LevelScene::onLevelNameUpdated(std::string new_name)
     m_name = new_name;
 }
 
-void LevelScene::onLevelWriteRequested(QString file_path)
+void LevelScene::onLevelWriteRequested()
 {
+    if (m_file_path.empty()) {
+        // create a nice file name from the levelname
+        // it will be displayed in the file save dialog
+        std::string filepath = m_name;
+        std::replace(filepath.begin(), filepath.end(), ' ', '-');
+        std::transform(filepath.begin(), filepath.end(), filepath.begin(), std::towlower);
+        filepath = "/" + filepath + ".h5";
+
+        // get path at which the level should be written to
+        m_file_path = QFileDialog::getSaveFileName(
+            (QWidget*) parent(), "Level Speichern", QDir::currentPath() + QString(filepath.c_str()), "HDF5 Files (*.h5 *.hdf5)").toStdString();
+    }
+    if (m_file_path.empty()) {
+        return; // if still empty dialog was canceled
+    }
+
     boost::property_tree::ptree pt;
 
     // Add data to the property tree
@@ -162,11 +186,16 @@ void LevelScene::onLevelWriteRequested(QString file_path)
     std::string xml_data = xmlStream.str();
 
     // write level to hdf5
-    HighFive::File file(file_path.toStdString(), HighFive::File::Truncate);
-    file.createDataSet<std::string>("metadata", HighFive::DataSpace::From(xmlStream))
-        .write(xml_data);
-    file.createDataSet<uint8_t>("tilesarray", HighFive::DataSpace::From(m_tile_ids))
-        .write(m_tile_ids);
+    try {
+        HighFive::File file(m_file_path, HighFive::File::Overwrite);
+        file.createDataSet<std::string>("metadatas", HighFive::DataSpace::From(xmlStream))
+            .write(xml_data);
+        file.createDataSet<uint8_t>("tilesarray", HighFive::DataSpace::From(m_tile_ids))
+            .write(m_tile_ids);
+        QMessageBox::information((QWidget*) parent(), "Saved", "Level map saved successfully.");
+    } catch (const HighFive::Exception& e) {
+        QMessageBox::critical((QWidget*) parent(), "Save failed", "Saving the level map failed.\nPlease make sure that you have write permissions for the selected path.");
+    }
 }
 
 void LevelScene::onTileEntered(int index)
@@ -291,8 +320,9 @@ QGraphicsPixmapItem* LevelScene::occupy_tile(int index, uint8_t tile_id)
     int                  y = (index / m_width) * 16;
     QPixmap              tile_occupant = SpriteProvider::get_sprite(tile_id);
     QGraphicsPixmapItem* tile_occupant_item = addPixmap(tile_occupant);
-    tile_occupant_item->setZValue(tile_id < 50 ? 1 : 2 + index);
-    tile_occupant_item->setPos(x, tile_id < 50 ? y : y - 16);
+    bool is_building_tile = tile_id >= 50;
+    tile_occupant_item->setZValue(is_building_tile ? 2 + index : 1);
+    tile_occupant_item->setPos(x, is_building_tile ? y - 16 : y);
     return tile_occupant_item;
 }
 
diff --git a/src/editor/LevelScene.hpp b/src/editor/LevelScene.hpp
index f1ed73d..69e23ec 100644
--- a/src/editor/LevelScene.hpp
+++ b/src/editor/LevelScene.hpp
@@ -34,7 +34,7 @@ private:
     bool is_water_tile(uint8_t id);
     bool isntIdentical(int16_t id, int index);
     void onLevelNameUpdated(std::string new_name) override;
-    void onLevelWriteRequested(QString file_path) override;
+    void onLevelWriteRequested() override;
     void onTileEntered(int index) override;  
     void onTileExited(int index) override;
     void onTileClicked(int index) override;
diff --git a/src/editor/SaveButton.cpp b/src/editor/SaveButton.cpp
index 9f13aa9..62a74b0 100644
--- a/src/editor/SaveButton.cpp
+++ b/src/editor/SaveButton.cpp
@@ -19,15 +19,9 @@ SaveButton::SaveButton(const std::string& title, QWidget* parent)
 {
 }
 
-void SaveButton::mousePressEvent(QMouseEvent* event)
+void SaveButton::mousePressEvent(QMouseEvent*)
 {
-    QPushButton::mousePressEvent(event);
-    QString file_path = QFileDialog::getSaveFileName(
-        this, "Level Speichern", QDir::currentPath(), "HDF5 Files (*.h5)");
-    if (!file_path.isEmpty())
-    {
-        EventHandler::send([file_path](EventHandler* e) { e->onLevelWriteRequested(file_path); });
-    }
+    EventHandler::send([](EventHandler* e) { e->onLevelWriteRequested();});
 }
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/SaveButton.hpp b/src/editor/SaveButton.hpp
index a117f40..bb16b5e 100644
--- a/src/editor/SaveButton.hpp
+++ b/src/editor/SaveButton.hpp
@@ -30,11 +30,11 @@ public:
 
 protected:
     /**
-     * Opens the file save dialog, collects the desired file path and emits
-     * the onLevelWriteRequested event method.
-     * @param event The QMouseEvent for the mouse press.
+     * When a mouse press event is received,
+     * it emits the onLevelWriteRequested event method. 
+     * onLevelWriteRequested is overwritten by LevelScene.
      */
-    void mousePressEvent(QMouseEvent* event) override;
+    void mousePressEvent(QMouseEvent*) override;
 };
 
 } // namespace editor
\ No newline at end of file
-- 
GitLab


From 4fef29d1ccd16f72ac7e58727cdd4a85a5d726ef Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sun, 9 Feb 2025 00:07:07 +0100
Subject: [PATCH 10/26] introduced full fledged command line application for
 launching editor

---
 src/editor/main.cpp | 102 +++++++++++++++++++++++++++++++++++---------
 1 file changed, 83 insertions(+), 19 deletions(-)

diff --git a/src/editor/main.cpp b/src/editor/main.cpp
index 2688bf6..5276755 100644
--- a/src/editor/main.cpp
+++ b/src/editor/main.cpp
@@ -6,7 +6,12 @@
 */
 
 #include <QApplication>
+#include <QCommandLineParser>
+#include <filesystem>
 
+
+
+#include "highfive/H5File.hpp"
 #include "SpriteProvider.hpp"
 #include "MainWindow.hpp"
 #include "LevelScene.hpp"
@@ -22,37 +27,96 @@ using namespace editor;
  * If a width and height was provided, it create a blank level with the given dimensions.
  */
 
+struct LevelOptions {
+    int width;
+    int height;
+    std::string level_filepath;
+};
+
+std::optional<LevelOptions> loadLevelOptions(int argc, char* argv[]) {
+    QCoreApplication::setApplicationVersion("1.0.0");
+    QCoreApplication app(argc, argv);
+    QCommandLineParser parser;
+    std::string top_section = R"(QT Level Editor for creating/editing Maps of Advanced Wars.
+
+Examples:
+  ./editor                         Create new level  map (default 20x20).
+  ./editor --width 15 --height 15  Create new level map (15x15).
+  ./editor --edit ./level.h5       Edit existing level map.)";
+
+    parser.addVersionOption();
+    parser.addHelpOption();
+    parser.setApplicationDescription(top_section.c_str());
+    parser.addOption(QCommandLineOption("width", "The width of the new level map (default 20, minimum: 3).", "number-of-tiles", "20"));
+    parser.addOption(QCommandLineOption("height", "The height of the new level map (default 20, minimum: 3).", "number-of-tiles", "20"));
+    parser.addOption(QCommandLineOption("edit", "The path to the HDF5 level map file that you want to edit. If edit is not set, a new level map is created.", "filepath"));
+    parser.process(app);
+
+    // QT Parser does not exit when unexpected positional arguments are provided,
+    // so have to do it by hand. 0 positional arguments are expected.
+    if (parser.positionalArguments().size() > 0) {
+        std::cerr << "Command not recognized.\n" << std::endl;
+        parser.showHelp(1); // shows the help info and quits the application with exit code 1
+        return std::nullopt;
+    }
+
+    bool width_ok;
+    bool height_ok;
+    LevelOptions options;
+    options.width = parser.value("width").toUInt(&width_ok);
+    options.height = parser.value("height").toUInt(&height_ok);
+    if (!width_ok || options.width < 3) {
+        std::cerr << "You provided an invalid level width: '" << parser.value("width").toStdString() << "'\nThe level width has to be a valid number >= 3." << std::endl;
+        return std::nullopt;
+    }
+    if (!height_ok || options.height < 3) {
+        std::cerr << "You provided an invalid level height: '" << parser.value("height").toStdString() << "'\nThe level height has to be a valid number >= 3." << std::endl;
+        return std::nullopt;
+    }
+    options.level_filepath = parser.value("edit").toStdString();
+    if (!options.level_filepath.empty() && !std::filesystem::exists(options.level_filepath)) {
+        std::cerr << "The level map file path: '" << options.level_filepath <<"' does not exist." << std::endl;
+        return std::nullopt;
+    }
+    return options;
+}
+
+
 int main(int argc, char* argv[])
 {
-    if (argc < 2)
-    { // no arguments provided
-        std::cerr << "Bitte uebergben Sie den Pfad zu dem Level, das sie bearbeiten wollen oder "
-                     "die Breite und Hoehe des Levels, das sie neu erstellen wollen."
-                  << std::endl;
-        return 1;
-    }
-    if (argc > 3)
-    { // more than 2 arguments provided
-        std::cerr << "Zuviele Kommandozeilenargumente." << std::endl;
+    std::optional<LevelOptions> level_options = loadLevelOptions(argc, argv);
+    if (!level_options.has_value()) {
         return 1;
     }
 
-    // programm starts
     QApplication app(argc, argv);
 
     // SpriteProvider is initialized once and can then be used from anywhere in the application
     // to get the QGraphicsPixmap for a specific tile.
-    SpriteProvider::initialize("../res/spritesheet.h5");
-
+    if (!std::filesystem::exists("../res/spritesheet.h5")) {
+        std::cerr << "The spritesheet was not found.\nIt was expected in: ../res/spritesheet.h5" << std::endl;
+        return 1;
+    }
+    try {
+        SpriteProvider::initialize("../res/spritesheet.h5");
+    } catch (const HighFive::Exception&) {
+        std::cerr << "Loading the spritesheet failed.\nPlease make sure that it is not corrupted.\nIt was loaded from: ../res/spritesheet.h5" << std::endl;
+        return 1;
+    }
 
+    // initialize LevelScene
     LevelScene* level;
-    if (argc == 2)
-    { // 1 argument provided => create Level from file
-        level = LevelScene::fromFile(argv[1]);
+    if (!level_options.value().level_filepath.empty()) {
+        try {
+            level = LevelScene::fromFile(level_options.value().level_filepath);
+        }
+        catch (const HighFive::Exception&) {
+            std::cerr << "Loading an existing level map from '" << level_options.value().level_filepath << "' failed.\nPlease make sure that the hdf5 level file is not corrupted." << std::endl;
+            return 1;
+        }
     }
-    else
-    { // 2 arguments provided => create blank level with given width and height
-        level = LevelScene::empty("Mein Level", std::stoi(argv[1]), std::stoi(argv[2]));
+    else {
+        level = LevelScene::empty("My Level", level_options.value().width, level_options.value().height);
     }
 
     MainWindow window(level);
-- 
GitLab


From 4fdcadbcf704aad332474d8952026a56d512154e Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sun, 9 Feb 2025 01:54:57 +0100
Subject: [PATCH 11/26] changed includes in LevelScene

---
 src/editor/LevelScene.cpp | 4 ++++
 src/editor/LevelScene.hpp | 6 +-----
 2 files changed, 5 insertions(+), 5 deletions(-)

diff --git a/src/editor/LevelScene.cpp b/src/editor/LevelScene.cpp
index 9fc4e5f..9f5cdfc 100644
--- a/src/editor/LevelScene.cpp
+++ b/src/editor/LevelScene.cpp
@@ -9,6 +9,9 @@
 
 #include "LevelScene.hpp"
 
+#include <string>
+#include <algorithm>
+#include <iostream>
 #include <QGraphicsPixmapItem>
 #include <QPixmap>
 #include <QPoint>
@@ -20,6 +23,7 @@
 
 #include "highfive/H5File.hpp"
 #include "SpriteProvider.hpp"
+#include "Tile.hpp"
 
 namespace editor
 {
diff --git a/src/editor/LevelScene.hpp b/src/editor/LevelScene.hpp
index 69e23ec..f118122 100644
--- a/src/editor/LevelScene.hpp
+++ b/src/editor/LevelScene.hpp
@@ -10,13 +10,9 @@
 #pragma once
 
 #include <QGraphicsScene>
-#include <QMouseEvent>
-#include <QWidget>
-#include <QGraphicsRectItem>
-#include <QGraphicsSceneMouseEvent>
+#include <QGraphicsPixmapItem>
 
 #include "EventHandler.hpp"
-#include "Tile.hpp"
 
 namespace editor
 {
-- 
GitLab


From 0627fb0449112a02fa412eb4358093474201eee1 Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sun, 9 Feb 2025 01:55:23 +0100
Subject: [PATCH 12/26] added documentation to main.cpp

---
 src/editor/main.cpp | 60 +++++++++++++++++++++++++++++++++++++--------
 1 file changed, 50 insertions(+), 10 deletions(-)

diff --git a/src/editor/main.cpp b/src/editor/main.cpp
index 5276755..ac663e0 100644
--- a/src/editor/main.cpp
+++ b/src/editor/main.cpp
@@ -9,8 +9,6 @@
 #include <QCommandLineParser>
 #include <filesystem>
 
-
-
 #include "highfive/H5File.hpp"
 #include "SpriteProvider.hpp"
 #include "MainWindow.hpp"
@@ -19,28 +17,56 @@
 using namespace editor;
 
 /**
- * The main function starts the program.
- * It checks if any command line arguments were provided.
- * If not it terminates. 
- * Otherwise if a path to a hdf5 level file was provided it 
- * starts the level editor and loads the level from the file for editing.
- * If a width and height was provided, it create a blank level with the given dimensions.
+ * For launching the level editor, we implemented a full fledged command line application
+ * with the help of QCommandLineParser.
+ * The command line application that is used for launching the level editor supports command like:
+ * ./editor --help
+ * ./editor --version
+ * ./editor --width
+ * ./editor --width 20 --height 20
+ * ./editor --edit ../res/level-file-to-edit.h5
  */
 
+/**
+ * Holds the launch options for the level editor.
+ * They are constructed from the provided command line options
+ * in the loadLevelOptions function.
+ */
 struct LevelOptions {
     int width;
     int height;
     std::string level_filepath;
 };
 
+/**
+ * loadLevelOptions implements a full fledged command line application for retrieving the 
+ * level options. 
+ * For that purpose it creates a QCoreApplication and QCommandLineParser object.
+ * QCoreApplication is just used for loading the level options.
+ * It is destroyed at function exit.
+ * Through QCommandLineParser we support commands like --help, --version
+ * loadLevelOptions also makes sure that the optionally provided arguments for width, height and
+ * level h5 file path are valid.
+ * All of these arguments have default values: width/height: 20, level h5 file path: ''
+ * @param argc The number of command line arguments provided by the user.
+ * @param argv All of the command line arguments provided by the user.
+ * @returns If the user provided options are valid, they will be returned inside an optional, 
+ *          else an empty optional will be returned.
+ */
 std::optional<LevelOptions> loadLevelOptions(int argc, char* argv[]) {
-    QCoreApplication::setApplicationVersion("1.0.0");
+    // Sperately from the QApplication we use for the Level Editor UI, we use QCoreApplication for
+    // the command line application for launching the editor.
+    // The reason is that using QApplication is very slow, because it has to initialize all of the internal UI stuff.
+    // That is not what you want if only a simple ./editor --help was executed.
     QCoreApplication app(argc, argv);
+    QCoreApplication::setApplicationVersion("1.0.0");
     QCommandLineParser parser;
+
+    // application description with examples for help output of ./editor --help
     std::string top_section = R"(QT Level Editor for creating/editing Maps of Advanced Wars.
 
 Examples:
-  ./editor                         Create new level  map (default 20x20).
+  ./editor                         Create new level map (default 20x20).
   ./editor --width 15 --height 15  Create new level map (15x15).
   ./editor --edit ./level.h5       Edit existing level map.)";
 
@@ -60,6 +86,8 @@ Examples:
         return std::nullopt;
     }
 
+    // make sure that provided with, height and level file path are valid
+    // if yes add them to the level options struct
     bool width_ok;
     bool height_ok;
     LevelOptions options;
@@ -78,6 +106,7 @@ Examples:
         std::cerr << "The level map file path: '" << options.level_filepath <<"' does not exist." << std::endl;
         return std::nullopt;
     }
+
     return options;
 }
 
@@ -119,6 +148,17 @@ int main(int argc, char* argv[])
         level = LevelScene::empty("My Level", level_options.value().width, level_options.value().height);
     }
 
+    // We create the MainWindow on the Stack. Thus it will be destructed 
+    // automatically at exit. The way memory management works in QT is that
+    // you can set a parent on every Widget class you create. If the parent gets
+    // destroyed all its children are destroyed as well. It is acutally save in both
+    // directions. It doesn't matter if you destroy the child first and the parent later.
+    // In our case, because all of the widgets in our application are eventual descendants of
+    // MainWindow, they are all automatically cleaned up at program exit. For that reason
+    // memory management for the level editor is very simple.
+    // For more info on QT Object Trees & Ownership
+    // @see https://doc.qt.io/qt-5/objecttrees.html
+
     MainWindow window(level);
     window.resize(1300, 800);
     window.show();
-- 
GitLab


From 1ab735a3e89e7a465b1d3ed95b102a5164b2bf08 Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sun, 9 Feb 2025 02:01:31 +0100
Subject: [PATCH 13/26] removed old dead code (forward declaration of Tile)

---
 src/editor/EventHandler.hpp | 3 ---
 1 file changed, 3 deletions(-)

diff --git a/src/editor/EventHandler.hpp b/src/editor/EventHandler.hpp
index 88acc02..e1fbe67 100644
--- a/src/editor/EventHandler.hpp
+++ b/src/editor/EventHandler.hpp
@@ -18,9 +18,6 @@
 namespace editor
 {
 
-// forward declaration of Tile
-class Tile;
-
 /**
  * EventHandler is the backbone in the architecture that makes interaction possible.
  * 
-- 
GitLab


From 18c0736b3c3bbf514ead59effde0b665c6952f9d Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sun, 9 Feb 2025 03:23:52 +0100
Subject: [PATCH 14/26] added doc comments for LevelScene

---
 src/editor/LevelNameEdit.hpp |   1 +
 src/editor/LevelScene.cpp    |   9 +-
 src/editor/LevelScene.hpp    | 172 +++++++++++++++++++++++++++++++++++
 3 files changed, 181 insertions(+), 1 deletion(-)

diff --git a/src/editor/LevelNameEdit.hpp b/src/editor/LevelNameEdit.hpp
index 824d336..9530adc 100644
--- a/src/editor/LevelNameEdit.hpp
+++ b/src/editor/LevelNameEdit.hpp
@@ -25,6 +25,7 @@ public:
      * @param parent The Widget that should be set as the parent of this Widget.
      */
     LevelNameEdit(const std::string& level_name, QWidget* parent = nullptr);
+
 protected:
     /**
      * Receives a QKeyEvent when the user presses a key to change the content of the QLineEdit.
diff --git a/src/editor/LevelScene.cpp b/src/editor/LevelScene.cpp
index 9f5cdfc..02a70ed 100644
--- a/src/editor/LevelScene.cpp
+++ b/src/editor/LevelScene.cpp
@@ -189,7 +189,7 @@ void LevelScene::onLevelWriteRequested()
     boost::property_tree::write_xml(xmlStream, pt);
     std::string xml_data = xmlStream.str();
 
-    // write level to hdf5
+    // write level to hdf5 file
     try {
         HighFive::File file(m_file_path, HighFive::File::Overwrite);
         file.createDataSet<std::string>("metadatas", HighFive::DataSpace::From(xmlStream))
@@ -210,6 +210,7 @@ void LevelScene::onTileEntered(int index)
     }
     if (is_border(index) && !is_water_tile(m_selected_tile_id))
     {
+        // only water tiles can be set on the border
         return;
     }
     if (m_tile_occupants[index] != nullptr)
@@ -233,6 +234,12 @@ void LevelScene::onTileExited(int index)
     if (m_tile_occupants[index] != nullptr)
     {
         removeItem(m_tile_occupants[index]);
+        // Interestingly QGraphicsScene does take ownership of the QGraphicsPixmapItems that
+        // are added to it, but inside removeItem it gives that ownership back without destroying it.
+        // I first assumed that removeItem would also destroy the Pixmap Items, but valgrind taught me 
+        // otherwise. :)
+        // So therefore we delete it explicitly. That is probably the only place in the entire application
+        // where we explicitly free memory.
         delete m_tile_occupants[index];
         m_tile_occupants[index] = nullptr;
     }
diff --git a/src/editor/LevelScene.hpp b/src/editor/LevelScene.hpp
index f118122..d015768 100644
--- a/src/editor/LevelScene.hpp
+++ b/src/editor/LevelScene.hpp
@@ -17,37 +17,209 @@
 namespace editor
 {
 
+/**
+ * The LevelScene is a Container for all of the individual tiles (QGraphicsPixmapItems) 
+ * of the level map.
+ * LevelScene is responsible for rendering/updating the map on user actions.
+ * It also privdes the static factory methods empty, fromFile for creating empty level maps, 
+ * laoding a level map from a hdf5 file.
+ * 
+ * LevelScene inherits from EventHandler overwriting many event methods:
+ * - onLevelNameUpdated 
+ *   To keep the current level name for when the level map should be saved.
+ * - onLevelWriteRequested 
+ *   To write the level map to a hdf5 file when the save button is pressed. 
+ * - onTileEntered
+ *   To render the currently selected tile from the tile selector on the entered tile.
+ * - onTileExited
+ *   To render the old tile again if the currently selected tile id was not set on this tile.
+ * - onTileClicked
+ *   To set the currently selected tile id on that tile. Maybe do advanced placement changes.
+ * - onNewTileIdSelected
+ *   To update the currently selected tile id.
+ * - onAdvancedPlacmentToggled
+ *   To toggle advanced placement on or off.
+ * 
+ * How does the rendering work?
+ * LevelScene implements a two layer approach. 
+ * The bottom layer is static. It is created out of Tile (Tile.cpp) objects. These Tile objects
+ * inherit from QGraphicsPixmapItems to override onmouse enter, exit and press.
+ * LevelScene receives those events in onTileEntered, onTileExited, onTileClicked. 
+ * The bottom layer is only grass and water cliffs on the borders.
+ * The bottom layer always gets a z value of 0.
+ * For non grass tile ids, QGraphicsPixmapItems are created on the second layer with a z value of 1
+ * for terrain tiles and 2 + index for building tiles.
+ * These Items are also saved in m_tile_occupants. The second layer is dynamic, by keeping pointers
+ * to its Pixmap Items we can remove them and switch them around.
+ */
 class LevelScene : public QGraphicsScene, public EventHandler {
 public:
+    /**
+     * It builds a LevelScene from the provided vector of tile ids and width and height.
+     * It creates the bottom layer of Tile objects and builds a second layer of QGraphicsPixmapItems on top,
+     * if the tile id is > 0 and the tile is not on the border.
+     * @param name The name of the level.
+     * @param width The width of the level. Unit: number of tiles
+     * @param height The height of the level. Unit: number of tiles
+     * @param tile_ids A vector of tile ids that define the level map.
+     * @param file_path The path to the file from which the level was loaded, empty string if level was just created.
+     * @param parent The parent to set for the LevelScene.
+     */
     LevelScene(const std::string& name, int width, int height, std::vector<uint8_t> tile_ids, const std::string& file_path, QWidget *parent = nullptr);
+
+    /**
+     * Uses the LevelScene constructor internally to create an empty LevelScene (only grass, water cliffs on the borders).
+     * @param name The name of the new level.
+     * @param width The width of the new level. Unit: number of tiles
+     * @param height The height of the new level. Unit: number of tiles
+     * @param parent The parent to set for the newly created LevelScene.
+     * @return An empty LevelScene.
+     */
     static LevelScene* empty(const std::string& name, int width, int height, QWidget *parent = nullptr);
+
+    /**
+     * Uses the LevelScene constructor internally to create a LevelScene from an hdf5 file.
+     * @param file_path The path to the hdf5 file from which the LevelScene should be loaded.
+     * @param parent The parent to set for the newly created LevelScene.
+     * @return A LevelScene that was loaded from a file.
+     */
     static LevelScene* fromFile(const std::string& file_path, QWidget *parent = nullptr);
+
+    /**
+     * Gets the name of the level.
+     * @return The current name of the level.
+     */
     std::string getName();
+
+    /**
+     * Gets the width of the level.
+     * @return The width of the level. Unit: number of tiles.
+     */
     int getWidth();
+
+    /**
+     * Gets the height of the level.
+     * @return The height of the level. Unit: number of tiles.
+     */
     int getHeight();
+
 private:
+    /**
+     * Checks if the given index corresponds to a border tile.
+     * @param index The position of an individual tile if you linearized the level map.
+     * @return True or False if the given index corresponds to a border tile.
+     */
     bool is_border(int index);
+
+    /**
+     * Checks if the tile id corresponds to a water tile.
+     * @param id The tile id to check.
+     * @return True or false if the given tile id corresponds to a water tile.
+     */
     bool is_water_tile(uint8_t id);
+
     bool isntIdentical(int16_t id, int index);
+
+    /**
+     * Updates the level name stored in LevelScene to new_name.
+     * The onLevelNameUpdated event method is emitted by the LevelNameEdit Widget.
+     * @param new_name The new name of the level.
+     */
     void onLevelNameUpdated(std::string new_name) override;
+
+    /**
+     * Writes the level to the file from which it was loaded initially. 
+     * If it was created from scratch, a path to the desired location is 
+     * obtained from the QT file save dialog.
+     * The onLevelWriteRequested event method is emitted by the SaveButton.
+     */
     void onLevelWriteRequested() override;
+
+    /**
+     * Renders the currently selcted tile (m_selected_tile_id) on the provided index.
+     * The onTileEntered event method is emitted by the Tile object.
+     * @param index The position of an individual tile if you were to linearized the level map.
+     */
     void onTileEntered(int index) override;  
+
+    /**
+     * Renders the old tile id from m_tile_ids at index again if the selected tile id was
+     * not set onto that tile.
+     * The onTileExited event method is emitted by the Tile object.
+     * @param index The position of an individual tile if you were to linearized the level map.
+     */
     void onTileExited(int index) override;
+
     void onTileClicked(int index) override;
+
+    /**
+     * Saves the newly selected tile_id inside LevelScene.
+     * The onNewTileIdSelected event method is emitted by the TileButton which
+     * is part of the TileSelector on the right of the level editor.
+     * @param tile_id The newly selected tile id.
+     */
     void onNewTileIdSelected(uint8_t tile_id) override;
+
+    /**
+     * Toggles LevelScene's internal m_advanced_placement member.
+     * This event method is emitted by the Advanced Placement CheckBox in the TopBar.
+     */
     void onAdvancedPlacementToggled() override;
     void setTile(int index, uint8_t id);
     void placeCliff(bool placedLand, int index);
     void placeRoad(int index, bool updateFlag);
     int calcDir(int i, int index);
+
+    /**
+     * Places a new QGraphicsPixmapItem using the given tile_id at the given index.
+     * It correclty sets its position and z value (1 -> terrain tile, 2 + index -> building tile)
+     * @param index The position of an individual tile if you were to linearized the level map.
+     * @param tile_id The id that corresponds to a type of tile to use.
+     * @return A pointer to the QGraphicsPixmapItem, that was added to the level scene.
+     */
     QGraphicsPixmapItem* occupy_tile(int index, uint8_t tile_id);
+
+    /**
+     * The name of the level.
+     */
     std::string m_name;
+
+    /**
+     * The width of the level. Unit: number of tiles.
+     */
     int m_width;
+
+    /**
+     * The height of the level. Unit: number of tiles.
+     */
     int m_height;
+
+    /**
+     * The tile id of every tile. (linearized representation)
+     */
     std::vector<uint8_t> m_tile_ids;
+
+    /**
+     * The path from which the LevelScene was loaded (empty if created from scratch).
+     */
     std::string m_file_path;
+
+    /**
+     * The currently selected tile id. Tells the LevelScene which tiles need to be set
+     * if a tile is clicked.
+     */
     uint8_t m_selected_tile_id;
+
+    /**
+     * Activates/deactivates adavanced placement.
+     */
     bool m_advanced_tile_placement;
+
+    /**
+     * Holds pointers to all of the QGraphicsPixmapItems of the top layer. 
+     * It holds nullptrs in places at which just the bottom layer is present.
+     * The length of m_tile_occupants is the same as m_tile_ids.
+     */
     std::vector<QGraphicsPixmapItem*> m_tile_occupants;
 };
 
-- 
GitLab


From a7e4d454782107d1701f6360f3c482d873947b6c Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sun, 9 Feb 2025 18:00:31 +0100
Subject: [PATCH 15/26] removed util/writelevel

---
 CMakeLists.txt          | 13 -------------
 src/util/writelevel.cpp | 30 ------------------------------
 2 files changed, 43 deletions(-)
 delete mode 100644 src/util/writelevel.cpp

diff --git a/CMakeLists.txt b/CMakeLists.txt
index 235d271..8114013 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -156,19 +156,6 @@ target_include_directories(editor
         ${highfive_SOURCE_DIR}/include
 )
 
-
-# writelevel
-add_executable(writelevel ${PROJECT_SOURCE_DIR}/src/util/writelevel.cpp)
-target_include_directories(writelevel
-    PRIVATE
-        ${highfive_SOURCE_DIR}/include
-)
-target_link_libraries(writelevel
-        ${HDF5_LIBRARIES}
-    )
-
-target_include_directories(advanced_wars PRIVATE ${highfive_SOURCE_DIR}/include)
-
 # Ressourcen kopieren (plattformübergreifend)
 foreach(FONT ${FONT_FILES})
     add_custom_command(
diff --git a/src/util/writelevel.cpp b/src/util/writelevel.cpp
deleted file mode 100644
index a4c8c24..0000000
--- a/src/util/writelevel.cpp
+++ /dev/null
@@ -1,30 +0,0 @@
-#include <boost/property_tree/ptree.hpp>
-#include <boost/property_tree/xml_parser.hpp>
-#include <highfive/H5File.hpp>
-
-int main()
-{
-    boost::property_tree::ptree pt;
-
-    // Add data to the property tree
-    pt.put("level.width", "15");
-    pt.put("level.height", "10");
-    pt.put("level.name", "Alpha");
-
-    std::ostringstream xmlStream;
-    boost::property_tree::write_xml(xmlStream, pt);
-    std::string          xml_data = xmlStream.str();
-    std::vector<uint8_t> levelmap = {
-        2,  3,  3, 3, 2,  2,  2, 3, 3, 3, 3, 1, 0, 0, 0,  0, 2, 3, 0, 0, 0,  3, 3, 3, 3,
-        0,  4,  0, 0, 0,  0,  0, 0, 0, 0, 0, 0, 3, 3, 0,  0, 1, 0, 0, 2, 0,  0, 0, 0, 76,
-        76, 51, 3, 0, 0,  0,  1, 0, 3, 3, 0, 0, 0, 0, 0,  0, 0, 3, 0, 0, 57, 1, 3, 0, 0,
-        50, 0,  0, 0, 76, 77, 0, 3, 0, 0, 0, 1, 0, 0, 55, 0, 0, 0, 0, 0, 0,  0, 3, 3, 0,
-        0,  1,  3, 0, 0,  0,  0, 0, 0, 0, 0, 0, 0, 3, 3,  3, 1, 0, 3, 3, 2,  3, 3, 0, 0,
-        0,  0,  0, 0, 0,  0,  4, 0, 0, 2, 3, 3, 3, 3, 0,  3, 2, 2, 3, 2, 3,  1, 3, 2, 2,
-    };
-
-    HighFive::File file("level.h5", HighFive::File::Truncate);
-    file.createDataSet<std::string>("metadata", HighFive::DataSpace::From(xmlStream))
-        .write(xml_data);
-    file.createDataSet<uint8_t>("tilesarray", HighFive::DataSpace::From(levelmap)).write(levelmap);
-}
-- 
GitLab


From a7137715de276646df188b5896e7034855abff4d Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sun, 9 Feb 2025 18:44:22 +0100
Subject: [PATCH 16/26] attached level metadata to tilesarray dataset

---
 documentation/LevelEditor.md | 21 +++++--------
 src/editor/LevelScene.cpp    | 57 +++++++++---------------------------
 src/game/level/Level.cpp     | 23 ++++++---------
 3 files changed, 31 insertions(+), 70 deletions(-)

diff --git a/documentation/LevelEditor.md b/documentation/LevelEditor.md
index ff2e611..d84c1c7 100644
--- a/documentation/LevelEditor.md
+++ b/documentation/LevelEditor.md
@@ -16,21 +16,16 @@ For more details on the individual classes, take a look at the documentation in
 
 ## Level Specification
 
-The level is stored in two datasets named 'metadata', 'tilesarray' in the level hdf5 file (level.h5).  
-The metadata dataset is in XML format. It provides the level height, width and name.  
-The tilesarray dataset is a giant array<uint8_t> which defines the level map through an array of tile ids.
+The level is stored in a dataset called 'tilesarray' in the level hdf5 file.  
+The tilesarray dataset is a giant array<uint8_t> which defines the level map through an array of tile ids.  
+The attached attributes of the dataset define the level metadata.
 
-### 1. metadata dataset (XML)
-```xml
-<?xml version="1.0" encoding="ASCII"?>
-<level>
-    <width>20</width> <!-- Breite des Levels -->
-    <height>20</height> <!-- Hoehe des Levels -->
-    <name>Geiles Level<name><!-- Name des Levels -->
-</level>
-```
+### 1. tilesarray attributes
+- width (int) The width of the level in number of tiles.
+- height (int) The height of the level in number of tiles.
+- name (string) The name of the level.
 
-### 2. tilesarray dataset
+### 2. tilesarray data
 The length of the tiles array is level width x level height (see level metadata).  
 From the individual values inside the tiles array you can determine the IDs of the buildings and terrains.  
 0 - 29 are terrain IDs => Mapping see enum in src/game/Tile.hpp  
diff --git a/src/editor/LevelScene.cpp b/src/editor/LevelScene.cpp
index 02a70ed..30ee581 100644
--- a/src/editor/LevelScene.cpp
+++ b/src/editor/LevelScene.cpp
@@ -98,22 +98,17 @@ LevelScene* LevelScene::empty(const std::string& name, int width, int height, QW
 LevelScene* LevelScene::fromFile(const std::string& file_path, QWidget* parent)
 {
     HighFive::File file(file_path, HighFive::File::ReadOnly);
+    HighFive::DataSet tilesarray_set = file.getDataSet("tilesarray");
 
-    // read level metadata
-    std::string level_metadata;
-    file.getDataSet("metadata").read(level_metadata);
-
-    // read tilesarray
+    int width;
+    int height;
+    std::string name;
     std::vector<uint8_t> level_tilesarray;
-    file.getDataSet("tilesarray").read(level_tilesarray);
 
-    // extract metadata from xml
-    std::istringstream          xmlStream(level_metadata);
-    boost::property_tree::ptree pt;
-    boost::property_tree::read_xml(xmlStream, pt);
-    int         width = pt.get<int>("level.width");
-    int         height = pt.get<int>("level.height");
-    std::string name = pt.get<std::string>("level.name");
+    tilesarray_set.getAttribute("width").read(width);
+    tilesarray_set.getAttribute("height").read(height);
+    tilesarray_set.getAttribute("name").read(name);
+    tilesarray_set.read(level_tilesarray);
 
     return new LevelScene(name, width, height, level_tilesarray, file_path, parent);
 }
@@ -177,28 +172,18 @@ void LevelScene::onLevelWriteRequested()
         return; // if still empty dialog was canceled
     }
 
-    boost::property_tree::ptree pt;
-
-    // Add data to the property tree
-    pt.put("level.width", m_width);
-    pt.put("level.height", m_height);
-    pt.put("level.name", m_name);
-
-    // convert property tree to xml string
-    std::ostringstream xmlStream;
-    boost::property_tree::write_xml(xmlStream, pt);
-    std::string xml_data = xmlStream.str();
-
     // write level to hdf5 file
     try {
         HighFive::File file(m_file_path, HighFive::File::Overwrite);
-        file.createDataSet<std::string>("metadatas", HighFive::DataSpace::From(xmlStream))
-            .write(xml_data);
-        file.createDataSet<uint8_t>("tilesarray", HighFive::DataSpace::From(m_tile_ids))
-            .write(m_tile_ids);
+        HighFive::DataSet tilesarray_set = file.createDataSet<std::vector<uint8_t>>("tilesarray", m_tile_ids);
+        tilesarray_set.write(m_tile_ids);
+        tilesarray_set.createAttribute<int>("width", m_width).write(m_width);
+        tilesarray_set.createAttribute<int>("height", m_height).write(m_height);
+        tilesarray_set.createAttribute<std::string>("name", m_name).write(m_name);
         QMessageBox::information((QWidget*) parent(), "Saved", "Level map saved successfully.");
     } catch (const HighFive::Exception& e) {
         QMessageBox::critical((QWidget*) parent(), "Save failed", "Saving the level map failed.\nPlease make sure that you have write permissions for the selected path.");
+        throw e;
     }
 }
 
@@ -337,20 +322,6 @@ QGraphicsPixmapItem* LevelScene::occupy_tile(int index, uint8_t tile_id)
     return tile_occupant_item;
 }
 
-
-
-
-
-
-
-
-
-
-
-
-
-
-
 void LevelScene::placeCliff(bool placedLand, int index){
 	const int16_t IdToSum[12] = {12,3,9,6,2,1,4,8,13,14,11,7};
 	const int16_t SumToId[16] = {1,23,22,19,24,24,21,29,25,20,25,28,18,26,27,0};
diff --git a/src/game/level/Level.cpp b/src/game/level/Level.cpp
index 70661db..29dff19 100644
--- a/src/game/level/Level.cpp
+++ b/src/game/level/Level.cpp
@@ -62,22 +62,17 @@ Level::Level(
 std::shared_ptr<Level> Level::loadLevel(const std::string& path, Engine& engine)
 {
     HighFive::File file(path, HighFive::File::ReadOnly);
+    HighFive::DataSet tilesarray_set = file.getDataSet("tilesarray");
 
-    // read level metadata
-    std::string level_metadata;
-    file.getDataSet("metadata").read(level_metadata);
-
-    // read tilesarray
+    int width;
+    int height;
+    std::string name;
     std::vector<uint8_t> level_tilesarray;
-    file.getDataSet("tilesarray").read(level_tilesarray);
-
-    // extract metadata from xml
-    std::istringstream          xmlStream(level_metadata);
-    boost::property_tree::ptree pt;
-    boost::property_tree::read_xml(xmlStream, pt);
-    int         width = pt.get<int>("level.width");
-    int         height = pt.get<int>("level.height");
-    std::string name = pt.get<std::string>("level.name");
+
+    tilesarray_set.getAttribute("width").read(width);
+    tilesarray_set.getAttribute("height").read(height);
+    tilesarray_set.getAttribute("name").read(name);
+    tilesarray_set.read(level_tilesarray); 
 
     // if level is smaler than 20x20 surround with water tiles
     if (width < 20 || height < 20)
-- 
GitLab


From 0e5fb4e741528b95144a2e32785ee2191301871c Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sun, 9 Feb 2025 19:01:29 +0100
Subject: [PATCH 17/26] updated documentation

---
 documentation/LevelEditor.md          | 2 +-
 documentation/architecture.svg        | 3 ---
 documentation/system-architecture.svg | 3 +++
 src/editor/EventHandler.hpp           | 2 +-
 4 files changed, 5 insertions(+), 5 deletions(-)
 delete mode 100644 documentation/architecture.svg
 create mode 100644 documentation/system-architecture.svg

diff --git a/documentation/LevelEditor.md b/documentation/LevelEditor.md
index d84c1c7..6ff8889 100644
--- a/documentation/LevelEditor.md
+++ b/documentation/LevelEditor.md
@@ -12,7 +12,7 @@ To receive Events from EventHandler a class needs to inherit from EventHandler a
 The available event methods, as well as the info on which class emits which event method and which class overwrites which event method can be seen in the below diagramm.  
 The formless diagramm below demonstrates how the classes form the Application.  
 For more details on the individual classes, take a look at the documentation in their header files.
-![Formless System Architecture Diagramm](./architecture.svg)
+![Formless System Architecture Diagramm](./system-architecture.svg)
 
 ## Level Specification
 
diff --git a/documentation/architecture.svg b/documentation/architecture.svg
deleted file mode 100644
index 9f4af7e..0000000
--- a/documentation/architecture.svg
+++ /dev/null
@@ -1,3 +0,0 @@
-<svg version="1.1" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1688.7907986111109 1234.7222222222222" width="1688.7907986111109" height="1234.7222222222222"><!-- svg-source:excalidraw --><metadata></metadata><defs><style class="style-fonts">
-      @font-face { font-family: Virgil; src: url(data:font/woff2;base64,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); }
-      @font-face { font-family: Excalifont; src: url(data:font/woff2;base64,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); }</style></defs><rect x="0" y="0" width="1688.7907986111109" height="1234.7222222222222" fill="#ffffff"></rect><g stroke-linecap="round" transform="translate(181.33333333333303 468.429292929293) rotate(0 496.5 313.5)"><path d="M32 0 C392.22 -1.22, 750.78 -1.96, 961 0 M32 0 C350.37 -2.95, 668.6 -2.73, 961 0 M961 0 C981.11 -0.8, 992.43 10.61, 993 32 M961 0 C982.35 -1.02, 994.77 10.24, 993 32 M993 32 C990.27 180.3, 990.44 329.77, 993 595 M993 32 C993.61 250.68, 993.46 469.57, 993 595 M993 595 C994.01 615.74, 983.64 626.88, 961 627 M993 595 C994.03 614.05, 981.9 627.65, 961 627 M961 627 C646.22 628.26, 332.93 627.51, 32 627 M961 627 C711.11 624.58, 460.9 624.42, 32 627 M32 627 C10.59 626.53, 0.77 616.89, 0 595 M32 627 C9.28 624.92, -0.3 617.43, 0 595 M0 595 C0.03 426.99, -0.11 258.91, 0 32 M0 595 C-1.21 479.68, -1.88 365.05, 0 32 M0 32 C1.86 10.09, 9.1 -1, 32 0 M0 32 C0.31 11.97, 10.76 0.02, 32 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(519.9999999999998 397.3181818181819) rotate(0 98.72837829589844 35)"><text x="0" y="24.668" font-family="Virgil, Segoe UI Emoji" font-size="28px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">MainWindow.cpp</text><text x="0" y="59.668" font-family="Virgil, Segoe UI Emoji" font-size="28px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QMainWindow)</text></g><g stroke-linecap="round"><g transform="translate(180.33333333333303 529.4292929292931) rotate(0 497 -1)"><path d="M-0.62 0.95 C165.13 0.91, 827.6 -0.38, 993.57 -0.8 M1.25 0.4 C166.89 0.12, 826.77 -1.62, 992.4 -2.3" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(602.7777777777776 480.429292929293) rotate(0 55.43994903564453 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">TopBar.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QToolBar)</text></g><g stroke-linecap="round" transform="translate(210.33333333333303 482.429292929293) rotate(0 117 17)"><path d="M8.5 0 C82.95 -0.86, 159.8 -1.13, 225.5 0 M8.5 0 C71.09 -0.8, 134.25 -1.35, 225.5 0 M225.5 0 C232.33 0.33, 232.7 2.76, 234 8.5 M225.5 0 C233.15 -1.94, 232.78 3.56, 234 8.5 M234 8.5 C234.21 14.51, 234.75 16.2, 234 25.5 M234 8.5 C234.01 14.79, 233.84 21.05, 234 25.5 M234 25.5 C234.43 31.84, 231.54 35.7, 225.5 34 M234 25.5 C235.6 32.53, 230.89 33.21, 225.5 34 M225.5 34 C143.1 32.42, 65.1 32.35, 8.5 34 M225.5 34 C151.33 35.67, 76.52 36.47, 8.5 34 M8.5 34 C1.77 32.02, 1.93 31.63, 0 25.5 M8.5 34 C3.25 34.52, 1.32 30.23, 0 25.5 M0 25.5 C0.55 19.94, -1 13.59, 0 8.5 M0 25.5 C-0.13 21.51, -0.72 16.51, 0 8.5 M0 8.5 C1.94 3.8, 4.48 -0.8, 8.5 0 M0 8.5 C1.85 3.76, 3.37 -0.05, 8.5 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(217.33333333333303 491.429292929293) rotate(0 0.5 10)"><path d="M0.25 0 C0.42 0.01, 0.61 -0.02, 0.75 0 M0.25 0 C0.35 0, 0.45 0.01, 0.75 0 M0.75 0 C0.89 -0.04, 0.36 0.81, 1 0.25 M0.75 0 C1.55 0.25, 1.22 -0.63, 1 0.25 M1 0.25 C1 7.43, 1.16 12.83, 1 19.75 M1 0.25 C1.04 6.11, 1.06 12.31, 1 19.75 M1 19.75 C1.88 18.99, 0.8 19.82, 0.75 20 M1 19.75 C1.15 20.78, 1.32 19.55, 0.75 20 M0.75 20 C0.64 20.01, 0.47 20, 0.25 20 M0.75 20 C0.64 19.99, 0.54 20.01, 0.25 20 M0.25 20 C-0.51 19.6, 0.64 20.51, 0 19.75 M0.25 20 C0.6 21.07, 0.74 19.62, 0 19.75 M0 19.75 C-0.27 15.59, 0.89 10.28, 0 0.25 M0 19.75 C-0.15 15.03, 0.3 11.21, 0 0.25 M0 0.25 C0.96 -0.63, 0.37 0.04, 0.25 0 M0 0.25 C-1.04 -0.02, 0.34 1.02, 0.25 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(229.33333333333303 372.429292929293) rotate(0 -1 53.5)"><path d="M-0.81 -1.05 C-1.22 16.8, -1.36 89.29, -1.4 107.47 M0.96 1.01 C0.36 18.47, -1.65 88.06, -2.03 105.59" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(229.33333333333303 372.429292929293) rotate(0 -1 53.5)"><path d="M-9.97 81.88 C-8.59 92.11, -2.98 101.84, -2.03 105.59 M-9.97 81.88 C-6.47 90.15, -4.54 100.94, -2.03 105.59" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(229.33333333333303 372.429292929293) rotate(0 -1 53.5)"><path d="M7.13 82.33 C1.89 92.27, 0.88 101.83, -2.03 105.59 M7.13 82.33 C4.08 90.57, -0.53 101.19, -2.03 105.59" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(149.33333333333303 347.429292929293) rotate(0 87.659912109375 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">LevelNameEdit.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QLineEdit)</text></g><g stroke-linecap="round" transform="translate(1063.333333333333 486.429292929293) rotate(0 47.5 12)"><path d="M6 0 C34.28 0.89, 60.18 0.43, 89 0 M6 0 C25.62 0.6, 43.35 0.53, 89 0 M89 0 C94.69 0.9, 93.44 1.88, 95 6 M89 0 C92.78 0.44, 96.27 1.45, 95 6 M95 6 C93.88 9.47, 95.27 10.92, 95 18 M95 6 C95.28 9.11, 95.1 13.08, 95 18 M95 18 C94.21 21.66, 93.22 22.3, 89 24 M95 18 C96.62 23.93, 91.93 23.49, 89 24 M89 24 C56.56 26.15, 25.69 22.71, 6 24 M89 24 C58.42 24.22, 27.9 24.91, 6 24 M6 24 C1.19 22.28, 1.69 21.82, 0 18 M6 24 C2.56 23.95, 2.28 23.17, 0 18 M0 18 C-0.32 13.43, 1.18 8.69, 0 6 M0 18 C-0.43 13.94, 0.08 10.5, 0 6 M0 6 C-1.16 0.67, 0.99 1.82, 6 0 M0 6 C2.11 3.57, 0.77 -2.16, 6 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1085.333333333333 488.429292929293) rotate(0 23.97998046875 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">Save</text></g><g stroke-linecap="round"><g transform="translate(1242.333333333333 488.429292929293) rotate(0 -40.5 2)"><path d="M0.21 0.91 C-13.54 1.66, -68.62 4.36, -81.99 4.83 M-1.14 0.34 C-14.57 0.73, -66.61 2.39, -79.79 3.15" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1242.333333333333 488.429292929293) rotate(0 -40.5 2)"><path d="M-56.69 -6.4 C-63.1 -4.72, -71.17 1.88, -79.79 3.15 M-56.69 -6.4 C-63.31 -3.12, -69.07 -0.07, -79.79 3.15" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1242.333333333333 488.429292929293) rotate(0 -40.5 2)"><path d="M-55.96 10.69 C-62.66 6.49, -70.99 7.21, -79.79 3.15 M-55.96 10.69 C-62.69 9.23, -68.65 7.53, -79.79 3.15" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(1247.333333333333 477.429292929293) rotate(0 129.68988037109375 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">SaveButton.cpp (QButton)</text></g><g stroke-linecap="round" transform="translate(1005.333333333333 484.429292929293) rotate(0 13.5 17.5)"><path d="M6.75 0 C9.92 -0.2, 16.31 1.38, 20.25 0 M6.75 0 C11.62 -0.38, 16.32 -0.58, 20.25 0 M20.25 0 C26.35 -1.97, 28.5 1.66, 27 6.75 M20.25 0 C24.01 -1.02, 27.24 2.84, 27 6.75 M27 6.75 C28.85 14.28, 28.08 22.09, 27 28.25 M27 6.75 C26.92 14.38, 27.65 22.43, 27 28.25 M27 28.25 C26.26 31.42, 22.96 35.3, 20.25 35 M27 28.25 C29.18 33.03, 25.2 33.24, 20.25 35 M20.25 35 C15.67 35.81, 12.98 35.93, 6.75 35 M20.25 35 C16.03 34.72, 10.87 34.5, 6.75 35 M6.75 35 C2.9 34.03, -0.39 33.16, 0 28.25 M6.75 35 C0.73 33.52, -2.27 30.99, 0 28.25 M0 28.25 C1.12 23.57, 1.49 15.7, 0 6.75 M0 28.25 C0.53 21.91, 0.3 15.73, 0 6.75 M0 6.75 C0.21 2.02, 1.34 -0.13, 6.75 0 M0 6.75 C-0.3 1.59, 1.63 1.72, 6.75 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1012.333333333333 489.429292929293) rotate(0 6.5 12.5)"><text x="6.5" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="middle" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">+</text></g><g stroke-linecap="round" transform="translate(912.333333333333 484.429292929293) rotate(0 40.5 17.5)"><path d="M8.75 0 C22.56 0.4, 37.31 -1.91, 72.25 0 M8.75 0 C23.05 -1.57, 38.12 0.11, 72.25 0 M72.25 0 C79.86 -0.3, 79.84 2.62, 81 8.75 M72.25 0 C78.7 -1.52, 83.27 4.93, 81 8.75 M81 8.75 C80.09 13.85, 80.67 21.49, 81 26.25 M81 8.75 C81.41 11.99, 80.31 16.06, 81 26.25 M81 26.25 C80.07 33.14, 79.58 34.9, 72.25 35 M81 26.25 C80.75 30.39, 78.08 34.73, 72.25 35 M72.25 35 C51.55 36.58, 32.98 33.29, 8.75 35 M72.25 35 C48.97 35.89, 24.15 35.79, 8.75 35 M8.75 35 C4.36 35.12, -0.4 31.08, 0 26.25 M8.75 35 C3.76 33.6, 1.1 34.33, 0 26.25 M0 26.25 C-1.35 23.1, 1.08 17.8, 0 8.75 M0 26.25 C0.84 21.29, 0.31 17.23, 0 8.75 M0 8.75 C-1.1 1.96, 3.44 -0.83, 8.75 0 M0 8.75 C-0.18 4.03, 2.99 -1.76, 8.75 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(926.8633397420244 489.429292929293) rotate(0 25.969993591308594 12.5)"><text x="25.969993591308594" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="middle" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">100%</text></g><g stroke-linecap="round" transform="translate(872.333333333333 483.429292929293) rotate(0 14.5 17.5)"><path d="M7.25 0 C10.22 0.81, 16.13 0.62, 21.75 0 M7.25 0 C10.45 0.04, 13.83 -0.2, 21.75 0 M21.75 0 C28.53 -1.66, 30.01 3.94, 29 7.25 M21.75 0 C25.25 -2.12, 27.32 2.65, 29 7.25 M29 7.25 C27.46 15.36, 29.95 22.12, 29 27.75 M29 7.25 C29.49 11.1, 29 15.36, 29 27.75 M29 27.75 C30.06 31.65, 24.8 35.36, 21.75 35 M29 27.75 C30.26 30.8, 26.27 32.76, 21.75 35 M21.75 35 C15.99 33.78, 11.09 33.83, 7.25 35 M21.75 35 C15.58 34.65, 9.83 34.46, 7.25 35 M7.25 35 C3.59 36.96, -1.4 33.4, 0 27.75 M7.25 35 C4.66 34.8, 1.38 33.03, 0 27.75 M0 27.75 C-1.77 20.42, 0.62 11.76, 0 7.25 M0 27.75 C-0.43 21.36, -0.19 15.55, 0 7.25 M0 7.25 C0.64 1.25, 0.77 1.31, 7.25 0 M0 7.25 C1.24 3.09, 4.53 0.82, 7.25 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(882.723340352376 488.429292929293) rotate(0 4.109992980957031 12.5)"><text x="4.109992980957031" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="middle" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">-</text></g><g stroke-linecap="round"><g transform="translate(1025.333333333333 418.429292929293) rotate(0 0.5 33.5)"><path d="M-0.62 -0.01 C-0.55 11.31, 0.02 56.24, 0.23 67.4 M1.26 -1.07 C1.73 9.93, 2.79 53.94, 2.54 65.49" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1025.333333333333 418.429292929293) rotate(0 0.5 33.5)"><path d="M-6.11 42.04 C-3.77 47.5, -0.6 54.94, 2.54 65.49 M-6.11 42.04 C-2.46 49.71, -1.44 56.21, 2.54 65.49" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1025.333333333333 418.429292929293) rotate(0 0.5 33.5)"><path d="M10.99 41.96 C8.45 47.36, 6.73 54.82, 2.54 65.49 M10.99 41.96 C9.59 49.67, 5.56 56.2, 2.54 65.49" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g stroke-linecap="round"><g transform="translate(948.333333333333 390.429292929293) rotate(0 -1.5 45)"><path d="M0.31 -0.19 C-0.53 14.85, -3.52 75.53, -3.92 90.75 M-0.99 -1.34 C-1.55 13.32, -1.46 73.9, -1.7 89.03" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(948.333333333333 390.429292929293) rotate(0 -1.5 45)"><path d="M-10.09 65.48 C-7.04 73.14, -2.17 85.36, -1.7 89.03 M-10.09 65.48 C-5.72 74.54, -2.43 83.73, -1.7 89.03" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(948.333333333333 390.429292929293) rotate(0 -1.5 45)"><path d="M7.01 65.59 C3.37 73.25, 1.54 85.43, -1.7 89.03 M7.01 65.59 C4.61 74.74, 1.14 83.9, -1.7 89.03" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g stroke-linecap="round"><g transform="translate(857.333333333333 427.429292929293) rotate(0 12.5 27)"><path d="M-0.25 -0.42 C3.93 8.8, 21.72 45.57, 25.74 54.77 M1.81 -1.68 C5.85 7.24, 21.12 43.96, 25.18 53.04" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(857.333333333333 427.429292929293) rotate(0 12.5 27)"><path d="M8.05 34.83 C13.31 42.52, 21.32 45.8, 25.18 53.04 M8.05 34.83 C13.65 41.12, 20.02 48.33, 25.18 53.04" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(857.333333333333 427.429292929293) rotate(0 12.5 27)"><path d="M23.77 28.08 C23.46 38.12, 25.93 43.77, 25.18 53.04 M23.77 28.08 C23.58 36.73, 24.22 46.39, 25.18 53.04" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(975.333333333333 397.429292929293) rotate(0 142.2398681640625 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">ZoomInButton.cpp (QButton)</text></g><g transform="translate(919.333333333333 368.429292929293) rotate(0 154.099853515625 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">ZoomInfoBUtton.cpp (QButton)</text></g><g transform="translate(739.333333333333 400.429292929293) rotate(0 98.07991027832031 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">ZoomOutBUtton.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">   (QButton)</text></g><g stroke-linecap="round" transform="translate(908.333333333333 528.4292929292931) rotate(0 132.5 282.5)"><path d="M32 0 C107.68 -0.2, 181.93 -0.74, 233 0 M32 0 C84.58 -0.32, 139.55 0.62, 233 0 M233 0 C254.72 0.92, 264.11 9.95, 265 32 M233 0 C252.46 0, 264.98 12.59, 265 32 M265 32 C263.46 146.81, 263.79 261.73, 265 533 M265 32 C264.71 216.17, 264.44 399.83, 265 533 M265 533 C264.79 556.25, 253.75 564.54, 233 565 M265 533 C263.43 553.47, 254.63 565.31, 233 565 M233 565 C181.87 565.95, 131.39 567.04, 32 565 M233 565 C163.75 564.45, 93.71 565.49, 32 565 M32 565 C11.87 566.97, 1.46 553.94, 0 533 M32 565 C11.74 566.93, 0.6 554.32, 0 533 M0 533 C0.22 423.53, -0.28 314.91, 0 32 M0 533 C0.18 386.7, 0.13 240.44, 0 32 M0 32 C1.34 10.17, 11.54 1.36, 32 0 M0 32 C1.77 12.9, 12.25 -0.5, 32 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(1223.333333333333 582.4292929292931) rotate(0 -23 -1.4999999999999858)"><path d="M-0.37 -0.23 C-8.08 -0.87, -38.83 -2.82, -46.38 -3.35 M0.44 -0.83 C-7.08 -1.44, -37.63 -2.46, -45.34 -2.83" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1223.333333333333 582.4292929292931) rotate(0 -23 -1.4999999999999858)"><path d="M-23.38 -9.83 C-29.77 -8.69, -35.99 -5.47, -45.34 -2.83 M-23.38 -9.83 C-28.55 -8.18, -32.93 -6.81, -45.34 -2.83" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1223.333333333333 582.4292929292931) rotate(0 -23 -1.4999999999999858)"><path d="M-24.02 5.92 C-30.3 2.77, -36.34 1.69, -45.34 -2.83 M-24.02 5.92 C-29.02 4.08, -33.27 1.95, -45.34 -2.83" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(1225.333333333333 568.4292929292931) rotate(0 77.17992401123047 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">TileSelector.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QScrollArea)</text></g><g stroke-linecap="round" transform="translate(180.33333333333303 533.4292929292931) rotate(0 363 279.5)"><path d="M32 0 C215.92 1.83, 398.86 2.46, 694 0 M32 0 C180.91 0.52, 329.24 0.39, 694 0 M694 0 C714.71 1.49, 727.21 9.49, 726 32 M694 0 C713.4 -1.3, 728.05 11.18, 726 32 M726 32 C723.76 180.22, 724.95 328.51, 726 527 M726 32 C725.6 187.45, 725.35 343.49, 726 527 M726 527 C727.77 546.98, 713.79 560.64, 694 559 M726 527 C724.33 547.44, 716.28 559.42, 694 559 M694 559 C523.33 555.73, 351.72 556.14, 32 559 M694 559 C519.52 556.36, 345.02 556.09, 32 559 M32 559 C8.95 560.86, 1.46 549.67, 0 527 M32 559 C8.93 559.29, 2.04 546.92, 0 527 M0 527 C-1.75 411.71, -0.93 296.78, 0 32 M0 527 C-1.1 389.49, -1.21 251.32, 0 32 M0 32 C-0.11 9.35, 9.88 0.55, 32 0 M0 32 C0.53 12.21, 12.51 -0.56, 32 0" stroke="#e03131" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(512.333333333333 1130.429292929293) rotate(0 0 -16.5)"><path d="M-0.52 -0.22 C-0.41 -5.75, 0.34 -27.1, 0.47 -32.65 M0.22 -0.81 C0.31 -6.27, 0.31 -28.04, 0.28 -33.44" stroke="#e03131" stroke-width="1" fill="none"></path></g><g transform="translate(512.333333333333 1130.429292929293) rotate(0 0 -16.5)"><path d="M5.96 -17.94 C4.03 -21.41, 3.36 -25.88, 0.28 -33.44 M5.96 -17.94 C4.57 -20.88, 3.41 -24.45, 0.28 -33.44" stroke="#e03131" stroke-width="1" fill="none"></path></g><g transform="translate(512.333333333333 1130.429292929293) rotate(0 0 -16.5)"><path d="M-5.33 -17.92 C-4.24 -21.34, -1.87 -25.81, 0.28 -33.44 M-5.33 -17.92 C-4.39 -20.85, -3.22 -24.43, 0.28 -33.44" stroke="#e03131" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(454.33333333333303 1133.429292929293) rotate(0 74.98992156982422 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#e03131" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">LevelView.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#e03131" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QGraphicsView)</text></g><g stroke-linecap="round" transform="translate(315.33333333333303 578.4292929292931) rotate(0 241 228.5)"><path d="M32 0 C146.33 -1.42, 257.76 -0.74, 450 0 M32 0 C115.45 1.81, 200.12 1.28, 450 0 M450 0 C471.46 -0.74, 482.45 8.99, 482 32 M450 0 C471.62 -1.64, 480.4 12.52, 482 32 M482 32 C480.83 137.55, 482.65 241.93, 482 425 M482 32 C481.31 143.38, 481.08 253.68, 482 425 M482 425 C483.61 444.62, 472.21 457.89, 450 457 M482 425 C483.83 445.93, 470.94 456.08, 450 457 M450 457 C293.51 457.25, 135.32 457.52, 32 457 M450 457 C297.48 456.29, 143.84 456.54, 32 457 M32 457 C11.7 455.78, 1 448.29, 0 425 M32 457 C9.59 455.68, 2.19 444.24, 0 425 M0 425 C0.5 336.06, 0.98 247.97, 0 32 M0 425 C-0.88 281.81, -0.96 139.85, 0 32 M0 32 C1.23 12.56, 12.45 -0.4, 32 0 M0 32 C-1.03 11.67, 9 1.82, 32 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(738.333333333333 1131.429292929293) rotate(0 -1 -48)"><path d="M-1.1 -1.19 C-1.57 -17.1, -1.85 -80.14, -2.02 -95.86 M0.52 0.8 C-0.18 -14.85, -2.4 -77.84, -2.98 -94.24" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(738.333333333333 1131.429292929293) rotate(0 -1 -48)"><path d="M6.4 -71.07 C1.06 -79.68, -0.15 -88.38, -2.98 -94.24 M6.4 -71.07 C3.17 -78.61, 0.8 -86.65, -2.98 -94.24" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(738.333333333333 1131.429292929293) rotate(0 -1 -48)"><path d="M-10.69 -70.46 C-9.77 -79.14, -4.72 -88.06, -2.98 -94.24 M-10.69 -70.46 C-8.09 -78.14, -4.63 -86.39, -2.98 -94.24" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(669.333333333333 1135.429292929293) rotate(0 82.77991485595703 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">LevelScene.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QGraphicsScene)</text></g><g stroke-linecap="round" transform="translate(320.33333333333303 588.4292929292931) rotate(0 21.5 18.5)"><path d="M9.25 0 C20.01 0.76, 26 0.03, 33.75 0 M9.25 0 C19.41 -0.24, 28.62 0.61, 33.75 0 M33.75 0 C40.46 1.11, 42.64 3.02, 43 9.25 M33.75 0 C37.82 1.09, 45.27 3.31, 43 9.25 M43 9.25 C43.43 14.75, 41.78 17.92, 43 27.75 M43 9.25 C42.23 14.12, 42.47 17.97, 43 27.75 M43 27.75 C42.57 33.29, 38.49 35.69, 33.75 37 M43 27.75 C42.31 36, 39.42 35.78, 33.75 37 M33.75 37 C27.37 37.9, 18.55 36.99, 9.25 37 M33.75 37 C27.4 37.24, 20.28 36.69, 9.25 37 M9.25 37 C3.16 35.98, -0.62 34.77, 0 27.75 M9.25 37 C4.45 38.28, 0.77 35.29, 0 27.75 M0 27.75 C-0.84 21.83, -1.11 18.45, 0 9.25 M0 27.75 C-0.9 22.6, -0.63 17.73, 0 9.25 M0 9.25 C1.28 2.3, 2.36 0.79, 9.25 0 M0 9.25 C-2.17 0.79, 1.37 -1.65, 9.25 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(366.33333333333303 590.4292929292931) rotate(0 19.5 17.5)"><path d="M8.75 0 C14.48 0.81, 22.09 1.13, 30.25 0 M8.75 0 C12.41 -0.36, 17.27 -0.4, 30.25 0 M30.25 0 C34.66 -1.31, 38.4 4.72, 39 8.75 M30.25 0 C35.58 -1.22, 38.69 2.57, 39 8.75 M39 8.75 C38.03 13.32, 38.56 17.7, 39 26.25 M39 8.75 C38.91 14.66, 39.09 20.93, 39 26.25 M39 26.25 C38.38 32.93, 37.27 36.11, 30.25 35 M39 26.25 C39.77 33.46, 35.99 33.98, 30.25 35 M30.25 35 C20.98 36.73, 13.64 35.46, 8.75 35 M30.25 35 C22.23 34.84, 16.11 34.56, 8.75 35 M8.75 35 C2.19 35.79, -1.89 30.09, 0 26.25 M8.75 35 C1.2 33.35, 2.23 34.3, 0 26.25 M0 26.25 C1.13 21.77, 0.87 18.25, 0 8.75 M0 26.25 C0.17 20.64, 0.41 15.47, 0 8.75 M0 8.75 C0.37 1, 0.95 -0.63, 8.75 0 M0 8.75 C-2.27 1.68, 4.22 0.85, 8.75 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(407.33333333333303 592.4292929292931) rotate(0 19 17.5)"><path d="M8.75 0 C12.21 -2.07, 17.95 -1.52, 29.25 0 M8.75 0 C16.34 -0.65, 25.62 -0.32, 29.25 0 M29.25 0 C35.97 -0.96, 38.17 2.3, 38 8.75 M29.25 0 C33.65 0.31, 37.44 3.84, 38 8.75 M38 8.75 C36.31 13.46, 36.3 18.34, 38 26.25 M38 8.75 C37.77 15.63, 37.75 20.41, 38 26.25 M38 26.25 C38.81 33.71, 34.44 36.29, 29.25 35 M38 26.25 C36.95 33.87, 35.7 34.47, 29.25 35 M29.25 35 C23.99 34.96, 19.58 35.62, 8.75 35 M29.25 35 C21.64 35.48, 13.28 35.95, 8.75 35 M8.75 35 C3.6 36.06, -0.03 32.15, 0 26.25 M8.75 35 C5.01 36.72, 1.66 32.54, 0 26.25 M0 26.25 C-0.4 20.69, -0.62 14.43, 0 8.75 M0 26.25 C0.97 20.51, -0.01 14.56, 0 8.75 M0 8.75 C-1.06 2.61, 1.97 -0.09, 8.75 0 M0 8.75 C0.27 2.26, 2.31 1.34, 8.75 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(443.33333333333303 593.4292929292931) rotate(0 23.5 17)"><path d="M8.5 0 C17.98 -0.54, 28.48 -0.79, 38.5 0 M8.5 0 C19.1 1.21, 28.52 0.08, 38.5 0 M38.5 0 C42.26 -1.06, 46.69 1.89, 47 8.5 M38.5 0 C44.07 0.27, 46.34 2.23, 47 8.5 M47 8.5 C46.21 15.46, 47.84 21.78, 47 25.5 M47 8.5 C47.86 14.93, 46.52 21.43, 47 25.5 M47 25.5 C45.53 32.33, 42.39 35.3, 38.5 34 M47 25.5 C46.76 33.3, 44.05 32.47, 38.5 34 M38.5 34 C26.79 33.78, 16.8 33.96, 8.5 34 M38.5 34 C27.54 33.62, 17.45 34.1, 8.5 34 M8.5 34 C2.5 34.19, -1.45 32.42, 0 25.5 M8.5 34 C0.87 34.71, -0.54 31.19, 0 25.5 M0 25.5 C-1.11 20.88, -0.96 15.77, 0 8.5 M0 25.5 C0.22 22.14, 0.65 18.26, 0 8.5 M0 8.5 C1.52 1.2, 3.35 -0.48, 8.5 0 M0 8.5 C0.5 1.77, 2.59 1.99, 8.5 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(90.33333333333303 598.4292929292931) rotate(0 114.5 3.5)"><path d="M-0.45 0.03 C37.84 1.39, 190.79 5.94, 229.13 7.13 M1.52 -1.01 C39.7 0.66, 190.32 7.14, 228.25 8.74" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(90.33333333333303 598.4292929292931) rotate(0 114.5 3.5)"><path d="M204.41 16.28 C210.51 14.68, 216.69 13.51, 228.25 8.74 M204.41 16.28 C211.84 13.8, 219.78 11.53, 228.25 8.74" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(90.33333333333303 598.4292929292931) rotate(0 114.5 3.5)"><path d="M205.14 -0.8 C210.91 1.89, 216.9 5.01, 228.25 8.74 M205.14 -0.8 C212.18 2.06, 219.89 5.13, 228.25 8.74" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(10.33333333333303 578.4292929292931) rotate(0 111.31987762451172 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">Tile.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QGraphicsPixmapItem)</text></g><g stroke-linecap="round" transform="translate(922.4242424242425 541.7929292929294) rotate(0 39.545454545454504 38.18181818181817)"><path d="M19.09 0 C31.99 0.05, 47.15 -0.53, 60 0 M19.09 0 C29.75 0.09, 39.48 -0.85, 60 0 M60 0 C70.78 -0.88, 78.34 7.86, 79.09 19.09 M60 0 C74.4 -2.27, 77.32 8.05, 79.09 19.09 M79.09 19.09 C80.58 28.26, 77.27 36.91, 79.09 57.27 M79.09 19.09 C79.94 28.61, 79.51 37.47, 79.09 57.27 M79.09 57.27 C79.29 69.54, 73.18 75.68, 60 76.36 M79.09 57.27 C77.93 70.21, 73.15 75.2, 60 76.36 M60 76.36 C48.22 76.64, 36.6 74.93, 19.09 76.36 M60 76.36 C45.42 76.38, 28.85 75.34, 19.09 76.36 M19.09 76.36 C5.78 75.7, 1.48 71.62, 0 57.27 M19.09 76.36 C7.67 76.59, 1.84 68.94, 0 57.27 M0 57.27 C1.15 50.14, 0.65 40.5, 0 19.09 M0 57.27 C0.89 49.78, -0.19 41.24, 0 19.09 M0 19.09 C1.96 5.63, 7.56 -1.36, 19.09 0 M0 19.09 C0.71 8.1, 6.47 0.09, 19.09 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(1014.2424242424242 544.5202020202021) rotate(0 44.09090909090912 39.09090909090909)"><path d="M19.55 0 C31.27 1.47, 41.22 -0.04, 68.64 0 M19.55 0 C30.45 0.13, 39.41 -0.6, 68.64 0 M68.64 0 C83.62 -0.73, 89.38 5.16, 88.18 19.55 M68.64 0 C82.38 1.74, 88.28 6.61, 88.18 19.55 M88.18 19.55 C88.44 29.55, 88.97 39.15, 88.18 58.64 M88.18 19.55 C88.86 30.86, 87.55 41.71, 88.18 58.64 M88.18 58.64 C86.87 73.14, 81.14 78.81, 68.64 78.18 M88.18 58.64 C90.11 71.8, 83.64 77.52, 68.64 78.18 M68.64 78.18 C50.29 76.91, 30.26 79.58, 19.55 78.18 M68.64 78.18 C58.95 78.16, 48.2 78.52, 19.55 78.18 M19.55 78.18 C6.42 77.91, -1.93 73.64, 0 58.64 M19.55 78.18 C5.16 76.73, 1.25 73.78, 0 58.64 M0 58.64 C-0.15 44.9, -1.77 29.35, 0 19.55 M0 58.64 C-0.53 47.68, -0.01 39.17, 0 19.55 M0 19.55 C0.14 6.1, 5.94 -0.56, 19.55 0 M0 19.55 C1.96 5.38, 6.93 1.77, 19.55 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(931.5151515151517 629.0656565656567) rotate(0 37.727272727272634 46.81818181818181)"><path d="M18.86 0 C28.49 -1.64, 41.56 1.46, 56.59 0 M18.86 0 C32.64 0.5, 45.79 -0.05, 56.59 0 M56.59 0 C68.38 1.18, 73.81 5.68, 75.45 18.86 M56.59 0 C67.39 0.5, 77.53 6.45, 75.45 18.86 M75.45 18.86 C77 33.49, 75.66 51.63, 75.45 74.77 M75.45 18.86 C75.63 37.14, 76.59 53.14, 75.45 74.77 M75.45 74.77 C75.74 89.12, 67.65 92, 56.59 93.64 M75.45 74.77 C74.97 87.93, 70.99 94.76, 56.59 93.64 M56.59 93.64 C46.03 93.4, 29.78 92.11, 18.86 93.64 M56.59 93.64 C43.36 94.39, 30.19 93.63, 18.86 93.64 M18.86 93.64 C4.94 93.41, 1.49 86.93, 0 74.77 M18.86 93.64 C7.83 93.32, -1.17 87.17, 0 74.77 M0 74.77 C2.1 57.55, 0.34 38.86, 0 18.86 M0 74.77 C-1.16 57.05, 0.43 41.23, 0 18.86 M0 18.86 C1.7 5.85, 5.21 0.68, 18.86 0 M0 18.86 C-1.03 6.63, 4.97 1, 18.86 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(1023.3333333333335 634.5202020202021) rotate(0 54.545454545454504 50)"><path d="M25 0 C38.24 -0.34, 52.52 -0.4, 84.09 0 M25 0 C43.22 -0.14, 60.61 -0.07, 84.09 0 M84.09 0 C99.74 -0.15, 109.55 6.65, 109.09 25 M84.09 0 C101.51 1.87, 110.05 8.18, 109.09 25 M109.09 25 C111.11 39.03, 107.98 57.73, 109.09 75 M109.09 25 C108.98 44.18, 109.07 62.82, 109.09 75 M109.09 75 C107.94 92.54, 102.02 101.39, 84.09 100 M109.09 75 C110.7 92.61, 103 99.39, 84.09 100 M84.09 100 C71.63 101.14, 57.62 98.14, 25 100 M84.09 100 C70.64 99.85, 58.84 100.65, 25 100 M25 100 C6.4 99.65, 1.6 93.59, 0 75 M25 100 C6.74 101.89, -2.03 93.21, 0 75 M0 75 C-0.09 58.47, 0.35 46.96, 0 25 M0 75 C-0.44 56.37, 0.39 39.04, 0 25 M0 25 C1.64 6.41, 7.17 1.87, 25 0 M0 25 C-0.39 7.74, 6.9 1.81, 25 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(1222.4242424242425 672.7020202020203) rotate(0 -43.18181818181813 0.45454545454543904)"><path d="M-0.83 0.99 C-15.56 1.08, -73.16 1.91, -87.42 1.72 M0.94 0.46 C-13.52 0.72, -70.58 0, -85.27 0.02" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1222.4242424242425 672.7020202020203) rotate(0 -43.18181818181813 0.45454545454543904)"><path d="M-61.72 -8.39 C-68.95 -7.12, -78.2 -2.25, -85.27 0.02 M-61.72 -8.39 C-67.58 -6.74, -70.89 -4.31, -85.27 0.02" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1222.4242424242425 672.7020202020203) rotate(0 -43.18181818181813 0.45454545454543904)"><path d="M-61.83 8.71 C-69.18 3.48, -78.39 1.85, -85.27 0.02 M-61.83 8.71 C-67.58 6.77, -70.87 5.62, -85.27 0.02" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(1226.9696969696972 658.1565656565658) rotate(0 125.56987762451172 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">TileButton.cpp (QButton)</text></g><g transform="translate(1318.8888888888887 918.6111111111111) rotate(0 53.07018280029297 17.5)"><text x="0" y="24.668" font-family="Virgil, Segoe UI Emoji" font-size="28px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">main.cpp</text></g><g transform="translate(1284.4444444444448 785.8333333333335) rotate(0 139.84982299804688 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">SpriteProvider.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(stores all QPixmap Sprites)</text></g><g stroke-linecap="round"><g transform="translate(1268.888888888889 792.5000000000001) rotate(0 -78.8888888888888 -39.44444444444446)"><path d="M-0.72 1.11 C-27.09 -11.74, -131.06 -65.01, -157.21 -78.23 M1.11 0.65 C-25.46 -12.45, -131.29 -66.53, -157.86 -80.01" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1268.888888888889 792.5000000000001) rotate(0 -78.8888888888888 -39.44444444444446)"><path d="M-133.05 -76.97 C-140.74 -77.35, -151.08 -79.2, -157.86 -80.01 M-133.05 -76.97 C-142.62 -78.36, -149.77 -80.05, -157.86 -80.01" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1268.888888888889 792.5000000000001) rotate(0 -78.8888888888888 -39.44444444444446)"><path d="M-140.81 -61.73 C-145.36 -67.94, -152.71 -75.68, -157.86 -80.01 M-140.81 -61.73 C-147.57 -68.47, -151.97 -75.57, -157.86 -80.01" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(1183.3333333333335 726.9444444444446) rotate(0 112.28987121582031 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">QPixmap get_sprite(id)</text></g><g transform="translate(933.3333333333333 818.0555555555557) rotate(0 112.28987121582031 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">QPixmap get_sprite(id)</text></g><g stroke-linecap="round"><g transform="translate(1272.2222222222224 836.784364824992) rotate(0 -393.33333333333337 -97.142182412496)"><path d="M0.45 0.38 C-130.53 -32.13, -655.33 -161.77, -786.53 -194.17 M-0.77 -0.46 C-131.85 -32.84, -656.28 -160.56, -787.41 -192.57" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1272.2222222222224 836.784364824992) rotate(0 -393.33333333333337 -97.142182412496)"><path d="M-762.56 -195.31 C-768.09 -194.31, -774.72 -193.98, -787.41 -192.57 M-762.56 -195.31 C-769.74 -193.76, -777.78 -192.73, -787.41 -192.57" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1272.2222222222224 836.784364824992) rotate(0 -393.33333333333337 -97.142182412496)"><path d="M-766.62 -178.69 C-771.26 -181.85, -776.88 -185.66, -787.41 -192.57 M-766.62 -178.69 C-772.53 -182.55, -779.25 -186.94, -787.41 -192.57" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g stroke-linecap="round"><g transform="translate(1034.4444444444446 784.7222222222223) rotate(0 1.6666666666667425 15.555555555555543)"><path d="M0.18 0.32 C0.72 5.52, 2.69 26.35, 3.2 31.54 M-0.38 0.01 C0.08 5.03, 2.16 25.7, 2.7 30.79" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g stroke-linecap="round"><g transform="translate(1351.1111111111113 908.0555555555557) rotate(0 10.201238247079914 -28.333333333333258)"><path d="M-0.46 0.92 C2.78 -8.25, 16.75 -46.17, 20.2 -55.79 M1.5 0.36 C4.49 -9.08, 16.16 -48.13, 19.14 -57.45" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1351.1111111111113 908.0555555555557) rotate(0 10.201238247079914 -28.333333333333258)"><path d="M20.4 -32.48 C21.63 -41.95, 21.1 -51, 19.14 -57.45 M20.4 -32.48 C20.49 -39.78, 19.35 -46.28, 19.14 -57.45" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1351.1111111111113 908.0555555555557) rotate(0 10.201238247079914 -28.333333333333258)"><path d="M4.06 -37.51 C11.24 -45.08, 16.68 -52.29, 19.14 -57.45 M4.06 -37.51 C8.96 -43.4, 12.59 -48.42, 19.14 -57.45" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(1361.1111111111109 878.1000000000004) rotate(0 158.83984375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">initialize (load hdf5 spritesheet)</text></g><g stroke-linecap="round"><g transform="translate(1305.5555555555557 936.9444444444446) rotate(0 -63.33333333333337 -0.5555555555555429)"><path d="M-0.43 0.11 C-21.48 -0.3, -105.83 -1.88, -126.74 -2.19 M1.55 -0.87 C-19.63 -1.19, -106.43 -1.24, -127.72 -1.22" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1305.5555555555557 936.9444444444446) rotate(0 -63.33333333333337 -0.5555555555555429)"><path d="M-104.23 -9.77 C-110.24 -7.71, -118.44 -3.97, -127.72 -1.22 M-104.23 -9.77 C-109.28 -8.07, -116.44 -5.49, -127.72 -1.22" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1305.5555555555557 936.9444444444446) rotate(0 -63.33333333333337 -0.5555555555555429)"><path d="M-104.23 7.33 C-110.28 4.87, -118.48 4.08, -127.72 -1.22 M-104.23 7.33 C-109.11 4.8, -116.27 3.14, -127.72 -1.22" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(1203.3333333333335 930.2777777777778) rotate(0 55.729949951171875 25)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">construct</text><text x="0" y="42.62" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">MainWindow</text></g><g transform="translate(542.2222222222224 121.38888888888903) rotate(0 113.79843139648438 17.5)"><text x="0" y="24.668" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="28px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">EventHandler.cpp</text></g><g transform="translate(511.1111111111113 154.16666666666674) rotate(0 155.94985961914062 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#f08c00" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onLevelNameUpdated(new_name)</text></g><g transform="translate(834.4444444444443 1134.1666666666667) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#f08c00" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(560 378.61111111111126) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#f08c00" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(835.5555555555554 1156.388888888889) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1971c2" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(835.5555555555554 1179.7222222222222) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#2f9e44" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(835.5555555555554 1199.7222222222222) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#e03131" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(508.88888888888914 182.5000000000001) rotate(0 164.08982849121094 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#2f9e44" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onLevelWriteRequested(file_path)</text></g><g transform="translate(564.4444444444448 209.16666666666686) rotate(0 102.21990203857422 37.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1971c2" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onTileEntered(index)</text><text x="0" y="42.62" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1971c2" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onTileExited(index)</text><text x="0" y="67.62" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1971c2" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onTileClicked(index)</text></g><g stroke-linecap="round" transform="translate(467.77777777777806 95.83333333333348) rotate(0 190 127.2222222222222)"><path d="M32 0 C99.31 1.79, 168.77 1.21, 348 0 M32 0 C134.98 1.12, 238.33 0.36, 348 0 M348 0 C368.49 1.03, 378.15 12.6, 380 32 M348 0 C367.35 0.61, 377.88 9.94, 380 32 M380 32 C380.1 84.74, 379.31 141.3, 380 222.44 M380 32 C379.97 96.79, 379.78 163.12, 380 222.44 M380 222.44 C379.4 245.48, 370.62 255.32, 348 254.44 M380 222.44 C380.23 242.57, 371.38 252.49, 348 254.44 M348 254.44 C272.94 254.7, 197.6 254.59, 32 254.44 M348 254.44 C245.83 254.63, 142.8 255.15, 32 254.44 M32 254.44 C10.8 252.83, -1.78 243.8, 0 222.44 M32 254.44 C12.95 253.63, 0.02 245.45, 0 222.44 M0 222.44 C-2.03 149.77, -3.34 73.88, 0 32 M0 222.44 C-0.58 178.42, 0.62 131.73, 0 32 M0 32 C-1.19 9.19, 11.9 -1.93, 32 0 M0 32 C0.07 9.73, 11.54 -1.03, 32 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(544.4444444444446 281.38888888888897) rotate(0 118.32988739013672 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#e03131" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onNewTileIdSelected(id)</text></g><g transform="translate(572.2222222222222 305.83333333333354) rotate(0 83.0199203491211 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onZoomed(delta)</text></g><g transform="translate(186.66666666666674 321.38888888888897) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#f08c00" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(1274.4444444444446 680.2777777777778) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#e03131" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(10 552.5000000000001) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1971c2" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(1306.6666666666665 499.16666666666674) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#2f9e44" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(786.6666666666665 381.38888888888897) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(1048.8888888888887 418.05555555555566) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(462.2222222222224 1178.0555555555557) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(962.2222222222224 342.50000000000017) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(532.2222222222224 55.83333333333326) rotate(0 133.99624633789062 20)"><text x="0" y="14.096" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="16px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">connects emitters and overwriters</text><text x="0" y="34.096000000000004" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="16px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">makes interaction possible</text></g><g transform="translate(20.000000000000114 191.38888888888897) rotate(0 224.7923583984375 40)"><text x="0" y="14.096" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="16px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">Legende:</text><text x="0" y="34.096000000000004" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="16px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits] -&gt; dispatches event handler event method</text><text x="0" y="54.096000000000004" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="16px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites] -&gt; inherits from EventHandler and</text><text x="0" y="74.096" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="16px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">                    overwrites event method</text></g><g transform="translate(40.00000000000023 10) rotate(0 184.9500732421875 67.5)"><text x="0" y="31.716" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="36px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">Formless </text><text x="0" y="76.71600000000001" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="36px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">System Architecture </text><text x="0" y="121.71600000000001" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="36px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">Diagramm</text></g></svg>
\ No newline at end of file
diff --git a/documentation/system-architecture.svg b/documentation/system-architecture.svg
new file mode 100644
index 0000000..6b3df19
--- /dev/null
+++ b/documentation/system-architecture.svg
@@ -0,0 +1,3 @@
+<svg version="1.1" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 1688.7907986111109 1234.7222222222222" width="1688.7907986111109" height="1234.7222222222222"><!-- svg-source:excalidraw --><metadata></metadata><defs><style class="style-fonts">
+      @font-face { font-family: Virgil; src: url(data:font/woff2;base64,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); }
+      @font-face { font-family: Excalifont; src: url(data:font/woff2;base64,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); }</style></defs><rect x="0" y="0" width="1688.7907986111109" height="1234.7222222222222" fill="#ffffff"></rect><g stroke-linecap="round" transform="translate(181.33333333333303 468.429292929293) rotate(0 496.5 313.5)"><path d="M32 0 C392.22 -1.22, 750.78 -1.96, 961 0 M32 0 C350.37 -2.95, 668.6 -2.73, 961 0 M961 0 C981.11 -0.8, 992.43 10.61, 993 32 M961 0 C982.35 -1.02, 994.77 10.24, 993 32 M993 32 C990.27 180.3, 990.44 329.77, 993 595 M993 32 C993.61 250.68, 993.46 469.57, 993 595 M993 595 C994.01 615.74, 983.64 626.88, 961 627 M993 595 C994.03 614.05, 981.9 627.65, 961 627 M961 627 C646.22 628.26, 332.93 627.51, 32 627 M961 627 C711.11 624.58, 460.9 624.42, 32 627 M32 627 C10.59 626.53, 0.77 616.89, 0 595 M32 627 C9.28 624.92, -0.3 617.43, 0 595 M0 595 C0.03 426.99, -0.11 258.91, 0 32 M0 595 C-1.21 479.68, -1.88 365.05, 0 32 M0 32 C1.86 10.09, 9.1 -1, 32 0 M0 32 C0.31 11.97, 10.76 0.02, 32 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(519.9999999999998 397.3181818181819) rotate(0 98.72837829589844 35)"><text x="0" y="24.668" font-family="Virgil, Segoe UI Emoji" font-size="28px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">MainWindow.cpp</text><text x="0" y="59.668" font-family="Virgil, Segoe UI Emoji" font-size="28px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QMainWindow)</text></g><g stroke-linecap="round"><g transform="translate(180.33333333333303 529.4292929292931) rotate(0 497 -1)"><path d="M-0.62 0.95 C165.13 0.91, 827.6 -0.38, 993.57 -0.8 M1.25 0.4 C166.89 0.12, 826.77 -1.62, 992.4 -2.3" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(602.7777777777776 480.429292929293) rotate(0 55.43994903564453 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">TopBar.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QToolBar)</text></g><g stroke-linecap="round" transform="translate(210.33333333333303 482.429292929293) rotate(0 117 17)"><path d="M8.5 0 C82.95 -0.86, 159.8 -1.13, 225.5 0 M8.5 0 C71.09 -0.8, 134.25 -1.35, 225.5 0 M225.5 0 C232.33 0.33, 232.7 2.76, 234 8.5 M225.5 0 C233.15 -1.94, 232.78 3.56, 234 8.5 M234 8.5 C234.21 14.51, 234.75 16.2, 234 25.5 M234 8.5 C234.01 14.79, 233.84 21.05, 234 25.5 M234 25.5 C234.43 31.84, 231.54 35.7, 225.5 34 M234 25.5 C235.6 32.53, 230.89 33.21, 225.5 34 M225.5 34 C143.1 32.42, 65.1 32.35, 8.5 34 M225.5 34 C151.33 35.67, 76.52 36.47, 8.5 34 M8.5 34 C1.77 32.02, 1.93 31.63, 0 25.5 M8.5 34 C3.25 34.52, 1.32 30.23, 0 25.5 M0 25.5 C0.55 19.94, -1 13.59, 0 8.5 M0 25.5 C-0.13 21.51, -0.72 16.51, 0 8.5 M0 8.5 C1.94 3.8, 4.48 -0.8, 8.5 0 M0 8.5 C1.85 3.76, 3.37 -0.05, 8.5 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(217.33333333333303 491.429292929293) rotate(0 0.5 10)"><path d="M0.25 0 C0.42 0.01, 0.61 -0.02, 0.75 0 M0.25 0 C0.35 0, 0.45 0.01, 0.75 0 M0.75 0 C0.89 -0.04, 0.36 0.81, 1 0.25 M0.75 0 C1.55 0.25, 1.22 -0.63, 1 0.25 M1 0.25 C1 7.43, 1.16 12.83, 1 19.75 M1 0.25 C1.04 6.11, 1.06 12.31, 1 19.75 M1 19.75 C1.88 18.99, 0.8 19.82, 0.75 20 M1 19.75 C1.15 20.78, 1.32 19.55, 0.75 20 M0.75 20 C0.64 20.01, 0.47 20, 0.25 20 M0.75 20 C0.64 19.99, 0.54 20.01, 0.25 20 M0.25 20 C-0.51 19.6, 0.64 20.51, 0 19.75 M0.25 20 C0.6 21.07, 0.74 19.62, 0 19.75 M0 19.75 C-0.27 15.59, 0.89 10.28, 0 0.25 M0 19.75 C-0.15 15.03, 0.3 11.21, 0 0.25 M0 0.25 C0.96 -0.63, 0.37 0.04, 0.25 0 M0 0.25 C-1.04 -0.02, 0.34 1.02, 0.25 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(229.33333333333303 372.429292929293) rotate(0 -1 53.5)"><path d="M-0.81 -1.05 C-1.22 16.8, -1.36 89.29, -1.4 107.47 M0.96 1.01 C0.36 18.47, -1.65 88.06, -2.03 105.59" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(229.33333333333303 372.429292929293) rotate(0 -1 53.5)"><path d="M-9.97 81.88 C-8.59 92.11, -2.98 101.84, -2.03 105.59 M-9.97 81.88 C-6.47 90.15, -4.54 100.94, -2.03 105.59" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(229.33333333333303 372.429292929293) rotate(0 -1 53.5)"><path d="M7.13 82.33 C1.89 92.27, 0.88 101.83, -2.03 105.59 M7.13 82.33 C4.08 90.57, -0.53 101.19, -2.03 105.59" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(149.33333333333303 347.429292929293) rotate(0 87.659912109375 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">LevelNameEdit.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QLineEdit)</text></g><g stroke-linecap="round" transform="translate(1063.333333333333 486.429292929293) rotate(0 47.5 12)"><path d="M6 0 C34.28 0.89, 60.18 0.43, 89 0 M6 0 C25.62 0.6, 43.35 0.53, 89 0 M89 0 C94.69 0.9, 93.44 1.88, 95 6 M89 0 C92.78 0.44, 96.27 1.45, 95 6 M95 6 C93.88 9.47, 95.27 10.92, 95 18 M95 6 C95.28 9.11, 95.1 13.08, 95 18 M95 18 C94.21 21.66, 93.22 22.3, 89 24 M95 18 C96.62 23.93, 91.93 23.49, 89 24 M89 24 C56.56 26.15, 25.69 22.71, 6 24 M89 24 C58.42 24.22, 27.9 24.91, 6 24 M6 24 C1.19 22.28, 1.69 21.82, 0 18 M6 24 C2.56 23.95, 2.28 23.17, 0 18 M0 18 C-0.32 13.43, 1.18 8.69, 0 6 M0 18 C-0.43 13.94, 0.08 10.5, 0 6 M0 6 C-1.16 0.67, 0.99 1.82, 6 0 M0 6 C2.11 3.57, 0.77 -2.16, 6 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1085.333333333333 488.429292929293) rotate(0 23.97998046875 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">Save</text></g><g stroke-linecap="round"><g transform="translate(1242.333333333333 488.429292929293) rotate(0 -40.5 2)"><path d="M0.21 0.91 C-13.54 1.66, -68.62 4.36, -81.99 4.83 M-1.14 0.34 C-14.57 0.73, -66.61 2.39, -79.79 3.15" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1242.333333333333 488.429292929293) rotate(0 -40.5 2)"><path d="M-56.69 -6.4 C-63.1 -4.72, -71.17 1.88, -79.79 3.15 M-56.69 -6.4 C-63.31 -3.12, -69.07 -0.07, -79.79 3.15" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1242.333333333333 488.429292929293) rotate(0 -40.5 2)"><path d="M-55.96 10.69 C-62.66 6.49, -70.99 7.21, -79.79 3.15 M-55.96 10.69 C-62.69 9.23, -68.65 7.53, -79.79 3.15" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(1247.333333333333 477.429292929293) rotate(0 129.68988037109375 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">SaveButton.cpp (QButton)</text></g><g stroke-linecap="round" transform="translate(1005.333333333333 484.429292929293) rotate(0 13.5 17.5)"><path d="M6.75 0 C9.92 -0.2, 16.31 1.38, 20.25 0 M6.75 0 C11.62 -0.38, 16.32 -0.58, 20.25 0 M20.25 0 C26.35 -1.97, 28.5 1.66, 27 6.75 M20.25 0 C24.01 -1.02, 27.24 2.84, 27 6.75 M27 6.75 C28.85 14.28, 28.08 22.09, 27 28.25 M27 6.75 C26.92 14.38, 27.65 22.43, 27 28.25 M27 28.25 C26.26 31.42, 22.96 35.3, 20.25 35 M27 28.25 C29.18 33.03, 25.2 33.24, 20.25 35 M20.25 35 C15.67 35.81, 12.98 35.93, 6.75 35 M20.25 35 C16.03 34.72, 10.87 34.5, 6.75 35 M6.75 35 C2.9 34.03, -0.39 33.16, 0 28.25 M6.75 35 C0.73 33.52, -2.27 30.99, 0 28.25 M0 28.25 C1.12 23.57, 1.49 15.7, 0 6.75 M0 28.25 C0.53 21.91, 0.3 15.73, 0 6.75 M0 6.75 C0.21 2.02, 1.34 -0.13, 6.75 0 M0 6.75 C-0.3 1.59, 1.63 1.72, 6.75 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1012.333333333333 489.429292929293) rotate(0 6.5 12.5)"><text x="6.5" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="middle" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">+</text></g><g stroke-linecap="round" transform="translate(912.333333333333 484.429292929293) rotate(0 40.5 17.5)"><path d="M8.75 0 C22.56 0.4, 37.31 -1.91, 72.25 0 M8.75 0 C23.05 -1.57, 38.12 0.11, 72.25 0 M72.25 0 C79.86 -0.3, 79.84 2.62, 81 8.75 M72.25 0 C78.7 -1.52, 83.27 4.93, 81 8.75 M81 8.75 C80.09 13.85, 80.67 21.49, 81 26.25 M81 8.75 C81.41 11.99, 80.31 16.06, 81 26.25 M81 26.25 C80.07 33.14, 79.58 34.9, 72.25 35 M81 26.25 C80.75 30.39, 78.08 34.73, 72.25 35 M72.25 35 C51.55 36.58, 32.98 33.29, 8.75 35 M72.25 35 C48.97 35.89, 24.15 35.79, 8.75 35 M8.75 35 C4.36 35.12, -0.4 31.08, 0 26.25 M8.75 35 C3.76 33.6, 1.1 34.33, 0 26.25 M0 26.25 C-1.35 23.1, 1.08 17.8, 0 8.75 M0 26.25 C0.84 21.29, 0.31 17.23, 0 8.75 M0 8.75 C-1.1 1.96, 3.44 -0.83, 8.75 0 M0 8.75 C-0.18 4.03, 2.99 -1.76, 8.75 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(926.8633397420244 489.429292929293) rotate(0 25.969993591308594 12.5)"><text x="25.969993591308594" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="middle" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">100%</text></g><g stroke-linecap="round" transform="translate(872.333333333333 483.429292929293) rotate(0 14.5 17.5)"><path d="M7.25 0 C10.22 0.81, 16.13 0.62, 21.75 0 M7.25 0 C10.45 0.04, 13.83 -0.2, 21.75 0 M21.75 0 C28.53 -1.66, 30.01 3.94, 29 7.25 M21.75 0 C25.25 -2.12, 27.32 2.65, 29 7.25 M29 7.25 C27.46 15.36, 29.95 22.12, 29 27.75 M29 7.25 C29.49 11.1, 29 15.36, 29 27.75 M29 27.75 C30.06 31.65, 24.8 35.36, 21.75 35 M29 27.75 C30.26 30.8, 26.27 32.76, 21.75 35 M21.75 35 C15.99 33.78, 11.09 33.83, 7.25 35 M21.75 35 C15.58 34.65, 9.83 34.46, 7.25 35 M7.25 35 C3.59 36.96, -1.4 33.4, 0 27.75 M7.25 35 C4.66 34.8, 1.38 33.03, 0 27.75 M0 27.75 C-1.77 20.42, 0.62 11.76, 0 7.25 M0 27.75 C-0.43 21.36, -0.19 15.55, 0 7.25 M0 7.25 C0.64 1.25, 0.77 1.31, 7.25 0 M0 7.25 C1.24 3.09, 4.53 0.82, 7.25 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(882.723340352376 488.429292929293) rotate(0 4.109992980957031 12.5)"><text x="4.109992980957031" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="middle" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">-</text></g><g stroke-linecap="round"><g transform="translate(1025.333333333333 418.429292929293) rotate(0 0.5 33.5)"><path d="M-0.62 -0.01 C-0.55 11.31, 0.02 56.24, 0.23 67.4 M1.26 -1.07 C1.73 9.93, 2.79 53.94, 2.54 65.49" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1025.333333333333 418.429292929293) rotate(0 0.5 33.5)"><path d="M-6.11 42.04 C-3.77 47.5, -0.6 54.94, 2.54 65.49 M-6.11 42.04 C-2.46 49.71, -1.44 56.21, 2.54 65.49" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1025.333333333333 418.429292929293) rotate(0 0.5 33.5)"><path d="M10.99 41.96 C8.45 47.36, 6.73 54.82, 2.54 65.49 M10.99 41.96 C9.59 49.67, 5.56 56.2, 2.54 65.49" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g stroke-linecap="round"><g transform="translate(948.333333333333 390.429292929293) rotate(0 -1.5 45)"><path d="M0.31 -0.19 C-0.53 14.85, -3.52 75.53, -3.92 90.75 M-0.99 -1.34 C-1.55 13.32, -1.46 73.9, -1.7 89.03" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(948.333333333333 390.429292929293) rotate(0 -1.5 45)"><path d="M-10.09 65.48 C-7.04 73.14, -2.17 85.36, -1.7 89.03 M-10.09 65.48 C-5.72 74.54, -2.43 83.73, -1.7 89.03" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(948.333333333333 390.429292929293) rotate(0 -1.5 45)"><path d="M7.01 65.59 C3.37 73.25, 1.54 85.43, -1.7 89.03 M7.01 65.59 C4.61 74.74, 1.14 83.9, -1.7 89.03" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g stroke-linecap="round"><g transform="translate(857.333333333333 427.429292929293) rotate(0 12.5 27)"><path d="M-0.25 -0.42 C3.93 8.8, 21.72 45.57, 25.74 54.77 M1.81 -1.68 C5.85 7.24, 21.12 43.96, 25.18 53.04" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(857.333333333333 427.429292929293) rotate(0 12.5 27)"><path d="M8.05 34.83 C13.31 42.52, 21.32 45.8, 25.18 53.04 M8.05 34.83 C13.65 41.12, 20.02 48.33, 25.18 53.04" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(857.333333333333 427.429292929293) rotate(0 12.5 27)"><path d="M23.77 28.08 C23.46 38.12, 25.93 43.77, 25.18 53.04 M23.77 28.08 C23.58 36.73, 24.22 46.39, 25.18 53.04" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(975.333333333333 397.429292929293) rotate(0 142.2398681640625 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">ZoomInButton.cpp (QButton)</text></g><g transform="translate(919.333333333333 368.429292929293) rotate(0 154.099853515625 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">ZoomInfoBUtton.cpp (QButton)</text></g><g transform="translate(739.333333333333 400.429292929293) rotate(0 98.07991027832031 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">ZoomOutBUtton.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">   (QButton)</text></g><g stroke-linecap="round" transform="translate(908.333333333333 528.4292929292931) rotate(0 132.5 282.5)"><path d="M32 0 C107.68 -0.2, 181.93 -0.74, 233 0 M32 0 C84.58 -0.32, 139.55 0.62, 233 0 M233 0 C254.72 0.92, 264.11 9.95, 265 32 M233 0 C252.46 0, 264.98 12.59, 265 32 M265 32 C263.46 146.81, 263.79 261.73, 265 533 M265 32 C264.71 216.17, 264.44 399.83, 265 533 M265 533 C264.79 556.25, 253.75 564.54, 233 565 M265 533 C263.43 553.47, 254.63 565.31, 233 565 M233 565 C181.87 565.95, 131.39 567.04, 32 565 M233 565 C163.75 564.45, 93.71 565.49, 32 565 M32 565 C11.87 566.97, 1.46 553.94, 0 533 M32 565 C11.74 566.93, 0.6 554.32, 0 533 M0 533 C0.22 423.53, -0.28 314.91, 0 32 M0 533 C0.18 386.7, 0.13 240.44, 0 32 M0 32 C1.34 10.17, 11.54 1.36, 32 0 M0 32 C1.77 12.9, 12.25 -0.5, 32 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(1223.333333333333 582.4292929292931) rotate(0 -23 -1.4999999999999858)"><path d="M-0.37 -0.23 C-8.08 -0.87, -38.83 -2.82, -46.38 -3.35 M0.44 -0.83 C-7.08 -1.44, -37.63 -2.46, -45.34 -2.83" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1223.333333333333 582.4292929292931) rotate(0 -23 -1.4999999999999858)"><path d="M-23.38 -9.83 C-29.77 -8.69, -35.99 -5.47, -45.34 -2.83 M-23.38 -9.83 C-28.55 -8.18, -32.93 -6.81, -45.34 -2.83" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1223.333333333333 582.4292929292931) rotate(0 -23 -1.4999999999999858)"><path d="M-24.02 5.92 C-30.3 2.77, -36.34 1.69, -45.34 -2.83 M-24.02 5.92 C-29.02 4.08, -33.27 1.95, -45.34 -2.83" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(1225.333333333333 568.4292929292931) rotate(0 77.17992401123047 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">TileSelector.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QScrollArea)</text></g><g stroke-linecap="round" transform="translate(180.33333333333303 533.4292929292931) rotate(0 363 279.5)"><path d="M32 0 C215.92 1.83, 398.86 2.46, 694 0 M32 0 C180.91 0.52, 329.24 0.39, 694 0 M694 0 C714.71 1.49, 727.21 9.49, 726 32 M694 0 C713.4 -1.3, 728.05 11.18, 726 32 M726 32 C723.76 180.22, 724.95 328.51, 726 527 M726 32 C725.6 187.45, 725.35 343.49, 726 527 M726 527 C727.77 546.98, 713.79 560.64, 694 559 M726 527 C724.33 547.44, 716.28 559.42, 694 559 M694 559 C523.33 555.73, 351.72 556.14, 32 559 M694 559 C519.52 556.36, 345.02 556.09, 32 559 M32 559 C8.95 560.86, 1.46 549.67, 0 527 M32 559 C8.93 559.29, 2.04 546.92, 0 527 M0 527 C-1.75 411.71, -0.93 296.78, 0 32 M0 527 C-1.1 389.49, -1.21 251.32, 0 32 M0 32 C-0.11 9.35, 9.88 0.55, 32 0 M0 32 C0.53 12.21, 12.51 -0.56, 32 0" stroke="#e03131" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(512.333333333333 1130.429292929293) rotate(0 0 -16.5)"><path d="M-0.52 -0.22 C-0.41 -5.75, 0.34 -27.1, 0.47 -32.65 M0.22 -0.81 C0.31 -6.27, 0.31 -28.04, 0.28 -33.44" stroke="#e03131" stroke-width="1" fill="none"></path></g><g transform="translate(512.333333333333 1130.429292929293) rotate(0 0 -16.5)"><path d="M5.96 -17.94 C4.03 -21.41, 3.36 -25.88, 0.28 -33.44 M5.96 -17.94 C4.57 -20.88, 3.41 -24.45, 0.28 -33.44" stroke="#e03131" stroke-width="1" fill="none"></path></g><g transform="translate(512.333333333333 1130.429292929293) rotate(0 0 -16.5)"><path d="M-5.33 -17.92 C-4.24 -21.34, -1.87 -25.81, 0.28 -33.44 M-5.33 -17.92 C-4.39 -20.85, -3.22 -24.43, 0.28 -33.44" stroke="#e03131" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(454.33333333333303 1133.429292929293) rotate(0 74.98992156982422 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#e03131" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">LevelView.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#e03131" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QGraphicsView)</text></g><g stroke-linecap="round" transform="translate(315.33333333333303 578.4292929292931) rotate(0 241 228.5)"><path d="M32 0 C146.33 -1.42, 257.76 -0.74, 450 0 M32 0 C115.45 1.81, 200.12 1.28, 450 0 M450 0 C471.46 -0.74, 482.45 8.99, 482 32 M450 0 C471.62 -1.64, 480.4 12.52, 482 32 M482 32 C480.83 137.55, 482.65 241.93, 482 425 M482 32 C481.31 143.38, 481.08 253.68, 482 425 M482 425 C483.61 444.62, 472.21 457.89, 450 457 M482 425 C483.83 445.93, 470.94 456.08, 450 457 M450 457 C293.51 457.25, 135.32 457.52, 32 457 M450 457 C297.48 456.29, 143.84 456.54, 32 457 M32 457 C11.7 455.78, 1 448.29, 0 425 M32 457 C9.59 455.68, 2.19 444.24, 0 425 M0 425 C0.5 336.06, 0.98 247.97, 0 32 M0 425 C-0.88 281.81, -0.96 139.85, 0 32 M0 32 C1.23 12.56, 12.45 -0.4, 32 0 M0 32 C-1.03 11.67, 9 1.82, 32 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(738.333333333333 1131.429292929293) rotate(0 -1 -48)"><path d="M-1.1 -1.19 C-1.57 -17.1, -1.85 -80.14, -2.02 -95.86 M0.52 0.8 C-0.18 -14.85, -2.4 -77.84, -2.98 -94.24" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(738.333333333333 1131.429292929293) rotate(0 -1 -48)"><path d="M6.4 -71.07 C1.06 -79.68, -0.15 -88.38, -2.98 -94.24 M6.4 -71.07 C3.17 -78.61, 0.8 -86.65, -2.98 -94.24" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(738.333333333333 1131.429292929293) rotate(0 -1 -48)"><path d="M-10.69 -70.46 C-9.77 -79.14, -4.72 -88.06, -2.98 -94.24 M-10.69 -70.46 C-8.09 -78.14, -4.63 -86.39, -2.98 -94.24" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(669.333333333333 1135.429292929293) rotate(0 82.77991485595703 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">LevelScene.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QGraphicsScene)</text></g><g stroke-linecap="round" transform="translate(320.33333333333303 588.4292929292931) rotate(0 21.5 18.5)"><path d="M9.25 0 C20.01 0.76, 26 0.03, 33.75 0 M9.25 0 C19.41 -0.24, 28.62 0.61, 33.75 0 M33.75 0 C40.46 1.11, 42.64 3.02, 43 9.25 M33.75 0 C37.82 1.09, 45.27 3.31, 43 9.25 M43 9.25 C43.43 14.75, 41.78 17.92, 43 27.75 M43 9.25 C42.23 14.12, 42.47 17.97, 43 27.75 M43 27.75 C42.57 33.29, 38.49 35.69, 33.75 37 M43 27.75 C42.31 36, 39.42 35.78, 33.75 37 M33.75 37 C27.37 37.9, 18.55 36.99, 9.25 37 M33.75 37 C27.4 37.24, 20.28 36.69, 9.25 37 M9.25 37 C3.16 35.98, -0.62 34.77, 0 27.75 M9.25 37 C4.45 38.28, 0.77 35.29, 0 27.75 M0 27.75 C-0.84 21.83, -1.11 18.45, 0 9.25 M0 27.75 C-0.9 22.6, -0.63 17.73, 0 9.25 M0 9.25 C1.28 2.3, 2.36 0.79, 9.25 0 M0 9.25 C-2.17 0.79, 1.37 -1.65, 9.25 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(366.33333333333303 590.4292929292931) rotate(0 19.5 17.5)"><path d="M8.75 0 C14.48 0.81, 22.09 1.13, 30.25 0 M8.75 0 C12.41 -0.36, 17.27 -0.4, 30.25 0 M30.25 0 C34.66 -1.31, 38.4 4.72, 39 8.75 M30.25 0 C35.58 -1.22, 38.69 2.57, 39 8.75 M39 8.75 C38.03 13.32, 38.56 17.7, 39 26.25 M39 8.75 C38.91 14.66, 39.09 20.93, 39 26.25 M39 26.25 C38.38 32.93, 37.27 36.11, 30.25 35 M39 26.25 C39.77 33.46, 35.99 33.98, 30.25 35 M30.25 35 C20.98 36.73, 13.64 35.46, 8.75 35 M30.25 35 C22.23 34.84, 16.11 34.56, 8.75 35 M8.75 35 C2.19 35.79, -1.89 30.09, 0 26.25 M8.75 35 C1.2 33.35, 2.23 34.3, 0 26.25 M0 26.25 C1.13 21.77, 0.87 18.25, 0 8.75 M0 26.25 C0.17 20.64, 0.41 15.47, 0 8.75 M0 8.75 C0.37 1, 0.95 -0.63, 8.75 0 M0 8.75 C-2.27 1.68, 4.22 0.85, 8.75 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(407.33333333333303 592.4292929292931) rotate(0 19 17.5)"><path d="M8.75 0 C12.21 -2.07, 17.95 -1.52, 29.25 0 M8.75 0 C16.34 -0.65, 25.62 -0.32, 29.25 0 M29.25 0 C35.97 -0.96, 38.17 2.3, 38 8.75 M29.25 0 C33.65 0.31, 37.44 3.84, 38 8.75 M38 8.75 C36.31 13.46, 36.3 18.34, 38 26.25 M38 8.75 C37.77 15.63, 37.75 20.41, 38 26.25 M38 26.25 C38.81 33.71, 34.44 36.29, 29.25 35 M38 26.25 C36.95 33.87, 35.7 34.47, 29.25 35 M29.25 35 C23.99 34.96, 19.58 35.62, 8.75 35 M29.25 35 C21.64 35.48, 13.28 35.95, 8.75 35 M8.75 35 C3.6 36.06, -0.03 32.15, 0 26.25 M8.75 35 C5.01 36.72, 1.66 32.54, 0 26.25 M0 26.25 C-0.4 20.69, -0.62 14.43, 0 8.75 M0 26.25 C0.97 20.51, -0.01 14.56, 0 8.75 M0 8.75 C-1.06 2.61, 1.97 -0.09, 8.75 0 M0 8.75 C0.27 2.26, 2.31 1.34, 8.75 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(443.33333333333303 593.4292929292931) rotate(0 23.5 17)"><path d="M8.5 0 C17.98 -0.54, 28.48 -0.79, 38.5 0 M8.5 0 C19.1 1.21, 28.52 0.08, 38.5 0 M38.5 0 C42.26 -1.06, 46.69 1.89, 47 8.5 M38.5 0 C44.07 0.27, 46.34 2.23, 47 8.5 M47 8.5 C46.21 15.46, 47.84 21.78, 47 25.5 M47 8.5 C47.86 14.93, 46.52 21.43, 47 25.5 M47 25.5 C45.53 32.33, 42.39 35.3, 38.5 34 M47 25.5 C46.76 33.3, 44.05 32.47, 38.5 34 M38.5 34 C26.79 33.78, 16.8 33.96, 8.5 34 M38.5 34 C27.54 33.62, 17.45 34.1, 8.5 34 M8.5 34 C2.5 34.19, -1.45 32.42, 0 25.5 M8.5 34 C0.87 34.71, -0.54 31.19, 0 25.5 M0 25.5 C-1.11 20.88, -0.96 15.77, 0 8.5 M0 25.5 C0.22 22.14, 0.65 18.26, 0 8.5 M0 8.5 C1.52 1.2, 3.35 -0.48, 8.5 0 M0 8.5 C0.5 1.77, 2.59 1.99, 8.5 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(90.33333333333303 598.4292929292931) rotate(0 114.5 3.5)"><path d="M-0.45 0.03 C37.84 1.39, 190.79 5.94, 229.13 7.13 M1.52 -1.01 C39.7 0.66, 190.32 7.14, 228.25 8.74" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(90.33333333333303 598.4292929292931) rotate(0 114.5 3.5)"><path d="M204.41 16.28 C210.51 14.68, 216.69 13.51, 228.25 8.74 M204.41 16.28 C211.84 13.8, 219.78 11.53, 228.25 8.74" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(90.33333333333303 598.4292929292931) rotate(0 114.5 3.5)"><path d="M205.14 -0.8 C210.91 1.89, 216.9 5.01, 228.25 8.74 M205.14 -0.8 C212.18 2.06, 219.89 5.13, 228.25 8.74" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(10.33333333333303 578.4292929292931) rotate(0 111.31987762451172 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">Tile.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(QGraphicsPixmapItem)</text></g><g stroke-linecap="round" transform="translate(922.4242424242425 541.7929292929294) rotate(0 39.545454545454504 38.18181818181817)"><path d="M19.09 0 C31.99 0.05, 47.15 -0.53, 60 0 M19.09 0 C29.75 0.09, 39.48 -0.85, 60 0 M60 0 C70.78 -0.88, 78.34 7.86, 79.09 19.09 M60 0 C74.4 -2.27, 77.32 8.05, 79.09 19.09 M79.09 19.09 C80.58 28.26, 77.27 36.91, 79.09 57.27 M79.09 19.09 C79.94 28.61, 79.51 37.47, 79.09 57.27 M79.09 57.27 C79.29 69.54, 73.18 75.68, 60 76.36 M79.09 57.27 C77.93 70.21, 73.15 75.2, 60 76.36 M60 76.36 C48.22 76.64, 36.6 74.93, 19.09 76.36 M60 76.36 C45.42 76.38, 28.85 75.34, 19.09 76.36 M19.09 76.36 C5.78 75.7, 1.48 71.62, 0 57.27 M19.09 76.36 C7.67 76.59, 1.84 68.94, 0 57.27 M0 57.27 C1.15 50.14, 0.65 40.5, 0 19.09 M0 57.27 C0.89 49.78, -0.19 41.24, 0 19.09 M0 19.09 C1.96 5.63, 7.56 -1.36, 19.09 0 M0 19.09 C0.71 8.1, 6.47 0.09, 19.09 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(1014.2424242424242 544.5202020202021) rotate(0 44.09090909090912 39.09090909090909)"><path d="M19.55 0 C31.27 1.47, 41.22 -0.04, 68.64 0 M19.55 0 C30.45 0.13, 39.41 -0.6, 68.64 0 M68.64 0 C83.62 -0.73, 89.38 5.16, 88.18 19.55 M68.64 0 C82.38 1.74, 88.28 6.61, 88.18 19.55 M88.18 19.55 C88.44 29.55, 88.97 39.15, 88.18 58.64 M88.18 19.55 C88.86 30.86, 87.55 41.71, 88.18 58.64 M88.18 58.64 C86.87 73.14, 81.14 78.81, 68.64 78.18 M88.18 58.64 C90.11 71.8, 83.64 77.52, 68.64 78.18 M68.64 78.18 C50.29 76.91, 30.26 79.58, 19.55 78.18 M68.64 78.18 C58.95 78.16, 48.2 78.52, 19.55 78.18 M19.55 78.18 C6.42 77.91, -1.93 73.64, 0 58.64 M19.55 78.18 C5.16 76.73, 1.25 73.78, 0 58.64 M0 58.64 C-0.15 44.9, -1.77 29.35, 0 19.55 M0 58.64 C-0.53 47.68, -0.01 39.17, 0 19.55 M0 19.55 C0.14 6.1, 5.94 -0.56, 19.55 0 M0 19.55 C1.96 5.38, 6.93 1.77, 19.55 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(931.5151515151517 629.0656565656567) rotate(0 37.727272727272634 46.81818181818181)"><path d="M18.86 0 C28.49 -1.64, 41.56 1.46, 56.59 0 M18.86 0 C32.64 0.5, 45.79 -0.05, 56.59 0 M56.59 0 C68.38 1.18, 73.81 5.68, 75.45 18.86 M56.59 0 C67.39 0.5, 77.53 6.45, 75.45 18.86 M75.45 18.86 C77 33.49, 75.66 51.63, 75.45 74.77 M75.45 18.86 C75.63 37.14, 76.59 53.14, 75.45 74.77 M75.45 74.77 C75.74 89.12, 67.65 92, 56.59 93.64 M75.45 74.77 C74.97 87.93, 70.99 94.76, 56.59 93.64 M56.59 93.64 C46.03 93.4, 29.78 92.11, 18.86 93.64 M56.59 93.64 C43.36 94.39, 30.19 93.63, 18.86 93.64 M18.86 93.64 C4.94 93.41, 1.49 86.93, 0 74.77 M18.86 93.64 C7.83 93.32, -1.17 87.17, 0 74.77 M0 74.77 C2.1 57.55, 0.34 38.86, 0 18.86 M0 74.77 C-1.16 57.05, 0.43 41.23, 0 18.86 M0 18.86 C1.7 5.85, 5.21 0.68, 18.86 0 M0 18.86 C-1.03 6.63, 4.97 1, 18.86 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round" transform="translate(1023.3333333333335 634.5202020202021) rotate(0 54.545454545454504 50)"><path d="M25 0 C38.24 -0.34, 52.52 -0.4, 84.09 0 M25 0 C43.22 -0.14, 60.61 -0.07, 84.09 0 M84.09 0 C99.74 -0.15, 109.55 6.65, 109.09 25 M84.09 0 C101.51 1.87, 110.05 8.18, 109.09 25 M109.09 25 C111.11 39.03, 107.98 57.73, 109.09 75 M109.09 25 C108.98 44.18, 109.07 62.82, 109.09 75 M109.09 75 C107.94 92.54, 102.02 101.39, 84.09 100 M109.09 75 C110.7 92.61, 103 99.39, 84.09 100 M84.09 100 C71.63 101.14, 57.62 98.14, 25 100 M84.09 100 C70.64 99.85, 58.84 100.65, 25 100 M25 100 C6.4 99.65, 1.6 93.59, 0 75 M25 100 C6.74 101.89, -2.03 93.21, 0 75 M0 75 C-0.09 58.47, 0.35 46.96, 0 25 M0 75 C-0.44 56.37, 0.39 39.04, 0 25 M0 25 C1.64 6.41, 7.17 1.87, 25 0 M0 25 C-0.39 7.74, 6.9 1.81, 25 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(1222.4242424242425 672.7020202020203) rotate(0 -43.18181818181813 0.45454545454543904)"><path d="M-0.83 0.99 C-15.56 1.08, -73.16 1.91, -87.42 1.72 M0.94 0.46 C-13.52 0.72, -70.58 0, -85.27 0.02" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1222.4242424242425 672.7020202020203) rotate(0 -43.18181818181813 0.45454545454543904)"><path d="M-61.72 -8.39 C-68.95 -7.12, -78.2 -2.25, -85.27 0.02 M-61.72 -8.39 C-67.58 -6.74, -70.89 -4.31, -85.27 0.02" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1222.4242424242425 672.7020202020203) rotate(0 -43.18181818181813 0.45454545454543904)"><path d="M-61.83 8.71 C-69.18 3.48, -78.39 1.85, -85.27 0.02 M-61.83 8.71 C-67.58 6.77, -70.87 5.62, -85.27 0.02" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(1226.9696969696972 658.1565656565658) rotate(0 125.56987762451172 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">TileButton.cpp (QButton)</text></g><g transform="translate(1318.8888888888887 918.6111111111111) rotate(0 53.07018280029297 17.5)"><text x="0" y="24.668" font-family="Virgil, Segoe UI Emoji" font-size="28px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">main.cpp</text></g><g transform="translate(1284.4444444444448 785.8333333333335) rotate(0 139.84982299804688 25)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">SpriteProvider.cpp</text><text x="0" y="42.62" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">(stores all QPixmap Sprites)</text></g><g stroke-linecap="round"><g transform="translate(1268.888888888889 792.5000000000001) rotate(0 -78.8888888888888 -39.44444444444446)"><path d="M-0.72 1.11 C-27.09 -11.74, -131.06 -65.01, -157.21 -78.23 M1.11 0.65 C-25.46 -12.45, -131.29 -66.53, -157.86 -80.01" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1268.888888888889 792.5000000000001) rotate(0 -78.8888888888888 -39.44444444444446)"><path d="M-133.05 -76.97 C-140.74 -77.35, -151.08 -79.2, -157.86 -80.01 M-133.05 -76.97 C-142.62 -78.36, -149.77 -80.05, -157.86 -80.01" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1268.888888888889 792.5000000000001) rotate(0 -78.8888888888888 -39.44444444444446)"><path d="M-140.81 -61.73 C-145.36 -67.94, -152.71 -75.68, -157.86 -80.01 M-140.81 -61.73 C-147.57 -68.47, -151.97 -75.57, -157.86 -80.01" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(1183.3333333333335 726.9444444444446) rotate(0 112.28987121582031 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">QPixmap get_sprite(id)</text></g><g transform="translate(933.3333333333333 818.0555555555557) rotate(0 112.28987121582031 12.5)"><text x="0" y="17.619999999999997" font-family="Virgil, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">QPixmap get_sprite(id)</text></g><g stroke-linecap="round"><g transform="translate(1272.2222222222224 836.784364824992) rotate(0 -393.33333333333337 -97.142182412496)"><path d="M0.45 0.38 C-130.53 -32.13, -655.33 -161.77, -786.53 -194.17 M-0.77 -0.46 C-131.85 -32.84, -656.28 -160.56, -787.41 -192.57" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1272.2222222222224 836.784364824992) rotate(0 -393.33333333333337 -97.142182412496)"><path d="M-762.56 -195.31 C-768.09 -194.31, -774.72 -193.98, -787.41 -192.57 M-762.56 -195.31 C-769.74 -193.76, -777.78 -192.73, -787.41 -192.57" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1272.2222222222224 836.784364824992) rotate(0 -393.33333333333337 -97.142182412496)"><path d="M-766.62 -178.69 C-771.26 -181.85, -776.88 -185.66, -787.41 -192.57 M-766.62 -178.69 C-772.53 -182.55, -779.25 -186.94, -787.41 -192.57" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g stroke-linecap="round"><g transform="translate(1034.4444444444446 784.7222222222223) rotate(0 1.6666666666667425 15.555555555555543)"><path d="M0.18 0.32 C0.72 5.52, 2.69 26.35, 3.2 31.54 M-0.38 0.01 C0.08 5.03, 2.16 25.7, 2.7 30.79" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g stroke-linecap="round"><g transform="translate(1351.1111111111113 908.0555555555557) rotate(0 10.201238247079914 -28.333333333333258)"><path d="M-0.46 0.92 C2.78 -8.25, 16.75 -46.17, 20.2 -55.79 M1.5 0.36 C4.49 -9.08, 16.16 -48.13, 19.14 -57.45" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1351.1111111111113 908.0555555555557) rotate(0 10.201238247079914 -28.333333333333258)"><path d="M20.4 -32.48 C21.63 -41.95, 21.1 -51, 19.14 -57.45 M20.4 -32.48 C20.49 -39.78, 19.35 -46.28, 19.14 -57.45" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1351.1111111111113 908.0555555555557) rotate(0 10.201238247079914 -28.333333333333258)"><path d="M4.06 -37.51 C11.24 -45.08, 16.68 -52.29, 19.14 -57.45 M4.06 -37.51 C8.96 -43.4, 12.59 -48.42, 19.14 -57.45" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(1361.1111111111109 878.1000000000004) rotate(0 158.83984375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">initialize (load hdf5 spritesheet)</text></g><g stroke-linecap="round"><g transform="translate(1305.5555555555557 936.9444444444446) rotate(0 -63.33333333333337 -0.5555555555555429)"><path d="M-0.43 0.11 C-21.48 -0.3, -105.83 -1.88, -126.74 -2.19 M1.55 -0.87 C-19.63 -1.19, -106.43 -1.24, -127.72 -1.22" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1305.5555555555557 936.9444444444446) rotate(0 -63.33333333333337 -0.5555555555555429)"><path d="M-104.23 -9.77 C-110.24 -7.71, -118.44 -3.97, -127.72 -1.22 M-104.23 -9.77 C-109.28 -8.07, -116.44 -5.49, -127.72 -1.22" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(1305.5555555555557 936.9444444444446) rotate(0 -63.33333333333337 -0.5555555555555429)"><path d="M-104.23 7.33 C-110.28 4.87, -118.48 4.08, -127.72 -1.22 M-104.23 7.33 C-109.11 4.8, -116.27 3.14, -127.72 -1.22" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(1203.3333333333335 930.2777777777778) rotate(0 55.729949951171875 25)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">construct</text><text x="0" y="42.62" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">MainWindow</text></g><g transform="translate(542.2222222222224 121.38888888888903) rotate(0 113.79843139648438 17.5)"><text x="0" y="24.668" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="28px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">EventHandler.cpp</text></g><g transform="translate(511.1111111111113 154.16666666666674) rotate(0 155.94985961914062 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#f08c00" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onLevelNameUpdated(new_name)</text></g><g transform="translate(834.4444444444443 1134.1666666666667) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#f08c00" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(560 378.61111111111126) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#f08c00" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(835.5555555555554 1156.388888888889) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1971c2" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(835.5555555555554 1179.7222222222222) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#2f9e44" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(835.5555555555554 1199.7222222222222) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#e03131" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(546.8888888888891 185.5000000000001) rotate(0 120.02986907958984 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#2f9e44" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onLevelWriteRequested()</text></g><g transform="translate(564.4444444444448 209.16666666666686) rotate(0 102.21990203857422 37.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1971c2" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onTileEntered(index)</text><text x="0" y="42.62" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1971c2" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onTileExited(index)</text><text x="0" y="67.62" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1971c2" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onTileClicked(index)</text></g><g stroke-linecap="round" transform="translate(467.77777777777806 95.83333333333348) rotate(0 190 127.2222222222222)"><path d="M32 0 C99.31 1.79, 168.77 1.21, 348 0 M32 0 C134.98 1.12, 238.33 0.36, 348 0 M348 0 C368.49 1.03, 378.15 12.6, 380 32 M348 0 C367.35 0.61, 377.88 9.94, 380 32 M380 32 C380.1 84.74, 379.31 141.3, 380 222.44 M380 32 C379.97 96.79, 379.78 163.12, 380 222.44 M380 222.44 C379.4 245.48, 370.62 255.32, 348 254.44 M380 222.44 C380.23 242.57, 371.38 252.49, 348 254.44 M348 254.44 C272.94 254.7, 197.6 254.59, 32 254.44 M348 254.44 C245.83 254.63, 142.8 255.15, 32 254.44 M32 254.44 C10.8 252.83, -1.78 243.8, 0 222.44 M32 254.44 C12.95 253.63, 0.02 245.45, 0 222.44 M0 222.44 C-2.03 149.77, -3.34 73.88, 0 32 M0 222.44 C-0.58 178.42, 0.62 131.73, 0 32 M0 32 C-1.19 9.19, 11.9 -1.93, 32 0 M0 32 C0.07 9.73, 11.54 -1.03, 32 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(544.4444444444446 281.38888888888897) rotate(0 118.32988739013672 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#e03131" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onNewTileIdSelected(id)</text></g><g transform="translate(572.2222222222222 305.83333333333354) rotate(0 83.0199203491211 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onZoomed(delta)</text></g><g transform="translate(186.66666666666674 321.38888888888897) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#f08c00" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(1274.4444444444446 680.2777777777778) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#e03131" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(10 552.5000000000001) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1971c2" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(1306.6666666666665 499.16666666666674) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#2f9e44" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(786.6666666666665 381.38888888888897) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(1048.8888888888887 418.05555555555566) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(462.2222222222224 1178.0555555555557) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(962.2222222222224 342.50000000000017) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g><g transform="translate(532.2222222222224 55.83333333333326) rotate(0 133.99624633789062 20)"><text x="0" y="14.096" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="16px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">connects emitters and overwriters</text><text x="0" y="34.096000000000004" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="16px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">makes interaction possible</text></g><g transform="translate(20.000000000000114 191.38888888888897) rotate(0 224.7923583984375 40)"><text x="0" y="14.096" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="16px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">Legende:</text><text x="0" y="34.096000000000004" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="16px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits] -&gt; dispatches event handler event method</text><text x="0" y="54.096000000000004" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="16px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites] -&gt; inherits from EventHandler and</text><text x="0" y="74.096" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="16px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">                    overwrites event method</text></g><g transform="translate(40.00000000000023 10) rotate(0 184.9500732421875 67.5)"><text x="0" y="31.716" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="36px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">Formless </text><text x="0" y="76.71600000000001" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="36px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">System Architecture </text><text x="0" y="121.71600000000001" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="36px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">Diagramm</text></g><g stroke-linecap="round" transform="translate(804.1199645996094 484.888888888889) rotate(0 15 16.5)"><path d="M7.5 0 C13.59 -0.73, 19.01 -0.13, 22.5 0 M7.5 0 C12.35 -0.82, 18.94 0.2, 22.5 0 M22.5 0 C27.45 -1.05, 29.87 1.93, 30 7.5 M22.5 0 C25.2 -0.19, 29.33 4.52, 30 7.5 M30 7.5 C29.75 11.42, 31.77 18.93, 30 25.5 M30 7.5 C29.67 13.07, 29.45 18.9, 30 25.5 M30 25.5 C30.01 31.74, 28.25 32.79, 22.5 33 M30 25.5 C32.24 30.97, 25.76 31.57, 22.5 33 M22.5 33 C16.01 32.35, 11.01 33.16, 7.5 33 M22.5 33 C17.4 32.88, 13.78 32.34, 7.5 33 M7.5 33 C3.16 32.07, 1.38 32.33, 0 25.5 M7.5 33 C2.97 32.81, -0.97 28.24, 0 25.5 M0 25.5 C-0.1 18.53, 1.65 10.85, 0 7.5 M0 25.5 C-0.34 20.98, -0.33 16.16, 0 7.5 M0 7.5 C-1.57 1.02, 1.65 -0.36, 7.5 0 M0 7.5 C-0.15 2.43, 4.01 1.09, 7.5 0" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g stroke-linecap="round"><g transform="translate(810.1199645996094 505.888888888889) rotate(0 5 5.5)"><path d="M0.25 -0.27 C2.07 1.62, 8.82 8.93, 10.39 10.82 M-0.28 0.77 C1.54 2.79, 8.58 9.61, 10.17 11.42" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g stroke-linecap="round"><g transform="translate(820.1199645996094 515.888888888889) rotate(0 4 -11)"><path d="M0.29 0.26 C1.57 -3.43, 6.84 -18.05, 8.16 -21.79 M-0.23 -0.09 C0.95 -3.97, 6.44 -19.05, 7.81 -22.65" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g stroke-linecap="round"><g transform="translate(902.1199645996094 325.888888888889) rotate(0 -31 83)"><path d="M0.81 -1.02 C-9.51 26.85, -51.6 139.17, -62 166.93 M-0.23 1.06 C-10.7 28.63, -52.63 137.7, -62.95 165.3" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(902.1199645996094 325.888888888889) rotate(0 -31 83)"><path d="M-62.6 140.31 C-64.45 147.65, -61.31 155.63, -62.95 165.3 M-62.6 140.31 C-62.02 147.05, -62.71 154.43, -62.95 165.3" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g><g transform="translate(902.1199645996094 325.888888888889) rotate(0 -31 83)"><path d="M-46.61 146.38 C-53.15 152.05, -54.7 158.24, -62.95 165.3 M-46.61 146.38 C-50.31 151.37, -55.24 157.14, -62.95 165.3" stroke="#1e1e1e" stroke-width="1" fill="none"></path></g></g><mask></mask><g transform="translate(901.1199645996094 291.888888888889) rotate(0 210.4097900390625 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#1e1e1e" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">AdvancedPlacementSwitch.cpp (QCheckBox)</text></g><g transform="translate(515.1199645996094 326.888888888889) rotate(0 151.55984497070312 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#9c36b5" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">onAdvancedPlacementToggled()</text></g><g transform="translate(1021.5601196289062 273.388888888889) rotate(0 35.119964599609375 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#9c36b5" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[emits]</text></g><g transform="translate(833 1113.3888888888891) rotate(0 60.47992706298828 12.5)"><text x="0" y="17.619999999999997" font-family="Excalifont, Xiaolai, Segoe UI Emoji" font-size="20px" fill="#9c36b5" text-anchor="start" style="white-space: pre;" direction="ltr" dominant-baseline="alphabetic">[overwrites]</text></g></svg>
\ No newline at end of file
diff --git a/src/editor/EventHandler.hpp b/src/editor/EventHandler.hpp
index e1fbe67..995f791 100644
--- a/src/editor/EventHandler.hpp
+++ b/src/editor/EventHandler.hpp
@@ -94,7 +94,7 @@ public:
 
     /**
      * Overwrite this event method to handle the change of tile placement method due
-     * to the user selecting automatic tile placement assisstance.
+     * to the user toggling advanced palacement on or off.
      */
     virtual void onAdvancedPlacementToggled(){};
 
-- 
GitLab


From d1e592634dcb56e91a24dfb86e2cbc2857bdfed2 Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Sun, 9 Feb 2025 21:42:05 +0100
Subject: [PATCH 18/26] repalced width/height with m_width/m_height when
 reading hdf5 file

---
 src/game/level/Level.cpp | 9 +++------
 1 file changed, 3 insertions(+), 6 deletions(-)

diff --git a/src/game/level/Level.cpp b/src/game/level/Level.cpp
index 1ced0bc..5cd393d 100644
--- a/src/game/level/Level.cpp
+++ b/src/game/level/Level.cpp
@@ -38,14 +38,11 @@ Level::Level(const std::string& path, Engine& engine)
     HighFive::File file(path, HighFive::File::ReadOnly);
     HighFive::DataSet tilesarray_set = file.getDataSet("tilesarray");
 
-    int width;
-    int height;
-    std::string name;
     std::vector<uint8_t> level_tilesarray;
 
-    tilesarray_set.getAttribute("width").read(width);
-    tilesarray_set.getAttribute("height").read(height);
-    tilesarray_set.getAttribute("name").read(name);
+    tilesarray_set.getAttribute("width").read(m_width);
+    tilesarray_set.getAttribute("height").read(m_height);
+    tilesarray_set.getAttribute("name").read(m_name);
     tilesarray_set.read(level_tilesarray); 
 
     // if level is smaler than 20x20 surround with water tiles
-- 
GitLab


From 6b01531c3abda6e4ae7a13d8ada4c40c8994b3c5 Mon Sep 17 00:00:00 2001
From: Nils <nils-jonathan.eckardt@informatik.hs-fulda.de>
Date: Sun, 9 Feb 2025 23:44:03 +0100
Subject: [PATCH 19/26] Kommentare, Symmetrie Implementiert

---
 src/editor/AdvancedPlacementSwitch.cpp | 11 ++++-
 src/editor/AdvancedPlacementSwitch.hpp |  8 +++-
 src/editor/EventHandler.hpp            |  8 +++-
 src/editor/LevelScene.cpp              | 60 ++++++++++++++------------
 src/editor/LevelScene.hpp              | 49 +++++++++++++++++++--
 src/editor/TileButton.hpp              | 18 +++++++-
 src/editor/TileSelector.cpp            | 20 ++++-----
 src/editor/TileSelector.hpp            | 59 ++++++++++++++++++++++---
 src/editor/TopBar.cpp                  |  6 ++-
 9 files changed, 185 insertions(+), 54 deletions(-)

diff --git a/src/editor/AdvancedPlacementSwitch.cpp b/src/editor/AdvancedPlacementSwitch.cpp
index 0572c37..139a40b 100644
--- a/src/editor/AdvancedPlacementSwitch.cpp
+++ b/src/editor/AdvancedPlacementSwitch.cpp
@@ -11,10 +11,13 @@
 #include <QMessageBox>
 #include <QEvent>
 
+#include <iostream>
+
 namespace editor
 {
 
-AdvancedPlacementSwitch::AdvancedPlacementSwitch(const QString text, QWidget* parent) : QCheckBox(text,parent)
+AdvancedPlacementSwitch::AdvancedPlacementSwitch(const QString text, const bool doesPlacement, QWidget* parent) : QCheckBox(text,parent), 
+isPlacement(doesPlacement)
 {
     setChecked(false);
 }
@@ -22,7 +25,11 @@ AdvancedPlacementSwitch::AdvancedPlacementSwitch(const QString text, QWidget* pa
 void AdvancedPlacementSwitch::mousePressEvent(QMouseEvent *event)
 {
     QCheckBox::mousePressEvent(event);
-    EventHandler::send([](EventHandler* e) { e->onAdvancedPlacementToggled(); });
+    if(isPlacement){
+        EventHandler::send([](EventHandler* e) { e->onAdvancedPlacementToggled(); });
+    } else {
+        EventHandler::send([](EventHandler* e) { e->onSymmetryToggled(); });
+    }
 }
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/AdvancedPlacementSwitch.hpp b/src/editor/AdvancedPlacementSwitch.hpp
index 214e54c..98b6d9a 100644
--- a/src/editor/AdvancedPlacementSwitch.hpp
+++ b/src/editor/AdvancedPlacementSwitch.hpp
@@ -24,9 +24,10 @@ public:
     /**
      * Creates an AdvancedPlacementSwitch as QCheckBox using the provided text and parent.
      * @param text The description to display next to the CheckBox.
+     * @param doesPlacement Which of the 2 checkboxes this one is: symetry or placement
      * @param parent The parent for this widget.
      */
-    AdvancedPlacementSwitch(const QString text, QWidget *parent = nullptr);
+    AdvancedPlacementSwitch(const QString text, bool doesPlacement, QWidget *parent = nullptr);
 protected:
     /**
      * Receives a QMouseEvent when the QCheckBox is pressed and subsequently emits
@@ -34,6 +35,11 @@ protected:
      * @param event The QMouseEvent for the CheckBox Pressing.
      */
     void mousePressEvent(QMouseEvent *event) override;
+private:
+    /**
+     * Set at creation, controlls if the switch is used for Placement or Symmetry
+     */
+    bool isPlacement;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/EventHandler.hpp b/src/editor/EventHandler.hpp
index 995f791..1e23baa 100644
--- a/src/editor/EventHandler.hpp
+++ b/src/editor/EventHandler.hpp
@@ -3,7 +3,7 @@
 *
 * @date 29.01.2025
 * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-* @author Nils Jonathan Friedrich Eckardt onAdvancedPlaement added
+* @author Nils Jonathan Friedrich Eckardt onAdvancedPlaement, onSymmetryToggled added
 */
 
 #pragma once
@@ -98,6 +98,12 @@ public:
      */
     virtual void onAdvancedPlacementToggled(){};
 
+    /**
+     * Overwrite this event method to handle the change of symmetric tile placement
+     * due to the user toggling map symmetry on or off.
+     */
+    virtual void onSymmetryToggled(){};
+
     /**
      * Overwrite this event method to handle the dispatch of a new delta due to 
      * the user pressing the zoom in or zoom out button.
diff --git a/src/editor/LevelScene.cpp b/src/editor/LevelScene.cpp
index 30ee581..9a2e1df 100644
--- a/src/editor/LevelScene.cpp
+++ b/src/editor/LevelScene.cpp
@@ -3,7 +3,7 @@
 *
 * @date 28.01.2025
 * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-* @author Nils Jonathan Friedrich Eckardt implemented advanced placement
+* @author Nils Jonathan Friedrich Eckardt implemented symmetry, advanced placement
 *         (onTileClicked, setTile, placeCliff, placeRoad, calcDir)
 */
 
@@ -32,7 +32,8 @@ LevelScene::LevelScene(
     const std::string& name, int width, int height, std::vector<uint8_t> tile_ids,
     const std::string& file_path, QWidget* parent)
     : QGraphicsScene(parent), m_name(name), m_width(width), m_height(height), m_tile_ids(tile_ids),
-      m_file_path(file_path), m_selected_tile_id(2), m_advanced_tile_placement(false)
+      m_file_path(file_path), m_selected_tile_id(2), m_advanced_tile_placement(false),
+      m_symmetric_tile_placement(false)
 {
     setSceneRect(0, 0, m_width * 16, m_height * 16); // set dimensions of the QGraphicsScene
 
@@ -246,40 +247,40 @@ void LevelScene::setTile(int index, uint8_t id)
     if (m_tile_ids[index] > 0)
     {
         m_tile_occupants[index] = occupy_tile(index, id);
-    }
-
-    /* gespiegeltes Setzen 
-    index = m_width * m_height - 1 -index;
-    int swapID[22] ={11,10,9,8,12,16,15,14,13,17,19,18,21,20,25,24,23,22,29,28,27,26};
-    if(id > 7 && id < 30) id = swapID[ id-8 ];
-
-    m_tile_ids[index]=id;
-    if (m_tile_occupants[index] != nullptr)
-    {
-        removeItem(m_tile_occupants[index]);
-        delete m_tile_occupants[index];
-        m_tile_occupants[index] = nullptr;
-    }
-    if (m_tile_ids[index] > 0)
-    {
-        m_tile_occupants[index] = occupy_tile(index, id);
-    }
-    */
+    } 
 }
 
 void LevelScene::onTileClicked(int index)
 {
 	if (is_border(index) && !is_water_tile(m_selected_tile_id)) {
-		return;
+		return;                             //no Placement allowed
 	}
-	
-	if (!m_advanced_tile_placement) {
-    	m_tile_ids[index] = m_selected_tile_id;
-		return;
+
+    m_tile_ids[index]=m_selected_tile_id;   //normal Placement
+
+	if (m_advanced_tile_placement) {
+        placeAdvancedTiles(index);          //advanced Placement
 	}
 
+    if(!m_symmetric_tile_placement) return;
+
+    uint8_t id = m_selected_tile_id;
+    index = m_width * m_height - 1 -index;
+    int swapID[22] ={11,10,9,8,12,16,15,14,13,17,19,18,21,20,25,24,23,22,29,28,27,26};
+    if(id > 7 && id < 30) id = swapID[ id-8 ];
+    if(id > 49 && id < 55) id += 5;  
+    else if(id > 54 && id < 60) id -= 5;  
 
-	if(m_selected_tile_id > 5 && m_selected_tile_id < 17){	//Straße plaziert
+    setTile(index,m_selected_tile_id);  //symmetric Placement
+
+    if (m_advanced_tile_placement) {
+        placeAdvancedTiles(index);      //symmetric advanced Placement
+    }
+}
+
+void LevelScene::placeAdvancedTiles(int index)
+{
+    if(m_selected_tile_id > 5 && m_selected_tile_id < 17){	//Straße plaziert
 		placeRoad(index, true);
 		return;
 	}
@@ -310,6 +311,11 @@ void LevelScene::onAdvancedPlacementToggled()
     m_advanced_tile_placement = !m_advanced_tile_placement;
 }
 
+void LevelScene::onSymmetryToggled()
+{
+    m_symmetric_tile_placement = !m_symmetric_tile_placement;
+}
+
 QGraphicsPixmapItem* LevelScene::occupy_tile(int index, uint8_t tile_id)
 {
     int                  x = (index % m_width) * 16;
diff --git a/src/editor/LevelScene.hpp b/src/editor/LevelScene.hpp
index d015768..f23511c 100644
--- a/src/editor/LevelScene.hpp
+++ b/src/editor/LevelScene.hpp
@@ -3,8 +3,8 @@
 *
 * @date 28.01.2025
 * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-* @author Nils Jonathan Friedrich Eckardt implementing advanced placement
-*         (onTileClicked, setTile, placeCliff, placeRoad, calcDir)
+* @author Nils Jonathan Friedrich Eckardt implementing symmetry, advanced placement
+*         (and onTileClicked, setTile, placeCliff, placeRoad, calcDir)
 */
 
 #pragma once
@@ -150,8 +150,27 @@ private:
      */
     void onTileExited(int index) override;
 
+    /**
+     * Evaluates how to procede once a tile has been placed by clicking on it.
+     * On the border only water tiles can be placed.
+     * If the option for advanced tile placement is checked, it will be executed from here.
+     * If the option for symmetric tile placement is checked, it will also be executed from here.
+     * When a red building is selected, symmetric tile placement will turn the mirrored building
+     * into a blue one and vice versa.
+     * @param index The index of the placed tile. Used to calculate both the previous id
+     * and the position on the map.
+     */
     void onTileClicked(int index) override;
 
+    /**
+     * Evaluates what tile has been placed, then calls the corresponding function.
+     * When this function is called advanced placement of tiles is enabled.
+     * If any street tile except bridges were placed placeRoad is called.
+     * If any Water or Land tiles are placed placeCliff is called.
+     * If any building is placed setTile is called.
+     */
+    void placeAdvancedTiles(int index);
+
     /**
      * Saves the newly selected tile_id inside LevelScene.
      * The onNewTileIdSelected event method is emitted by the TileButton which
@@ -161,11 +180,30 @@ private:
     void onNewTileIdSelected(uint8_t tile_id) override;
 
     /**
-     * Toggles LevelScene's internal m_advanced_placement member.
+     * Toggles LevelScene's internal m_advanced_tile_placement member.
      * This event method is emitted by the Advanced Placement CheckBox in the TopBar.
      */
     void onAdvancedPlacementToggled() override;
+    /**
+     * Toggles LevelScene's internal m_symmetric_tile_placement member.
+     * This event method is emitted by the Advanced Placement CheckBox in the TopBar.
+     */
+    void onSymmetryToggled() override;
+    /**
+     * This places a tile on the map.
+     * @param index Position on the map where the Tile is placed.
+     * @param id Id of the placed tile.
+     */
     void setTile(int index, uint8_t id);
+    /**
+     * A function of advanced placement used to determain whether the 8 surrounding tiles
+     * change when any land or water is placed. In this case it automaticly calculates the
+     * correct shape of the new cliffs and places them.
+     * @param placedLand If Land was placed - not water. Needed to evaluate if land should
+     * be added or removed around the placed tile.
+     * @param index Index of the tile water or land is placed on. The placed cliffs are the
+     * surrounding 8 tiles.
+     */
     void placeCliff(bool placedLand, int index);
     void placeRoad(int index, bool updateFlag);
     int calcDir(int i, int index);
@@ -215,6 +253,11 @@ private:
      */
     bool m_advanced_tile_placement;
 
+    /**
+     * Activates/deactivates adavanced placement.
+     */
+    bool m_symmetric_tile_placement;
+
     /**
      * Holds pointers to all of the QGraphicsPixmapItems of the top layer. 
      * It holds nullptrs in places at which just the bottom layer is present.
diff --git a/src/editor/TileButton.hpp b/src/editor/TileButton.hpp
index 6260cf0..1805e3c 100644
--- a/src/editor/TileButton.hpp
+++ b/src/editor/TileButton.hpp
@@ -12,13 +12,29 @@
 
 namespace editor
 {
-
+/**
+ * TileButtons are the Selection Buttons within the TileSelector.
+ * They listen for a mouse press and emit the onNewTileSelected event methode
+ * and transmits with it the selected id of the selected tile.
+ */
 class TileButton : public QPushButton {
 public:
+/**
+ * Creates a TileButton with the texture of a tile and the provided parent.
+ * @param id The id of the tile on this button.
+ * @param parent The parent to set for this button.
+ */
     TileButton(const uint8_t id, QWidget *parent = nullptr);
 protected:
+/**
+ * When a mouse press event is received,
+ * it emits the onNewTileIdSelected event with its tile's id.
+ */
     void mousePressEvent(QMouseEvent* event) override;
 private:
+/**
+ * The id of this button.
+ */
     uint8_t m_id;
 };
 
diff --git a/src/editor/TileSelector.cpp b/src/editor/TileSelector.cpp
index 1a0877e..e4e907f 100644
--- a/src/editor/TileSelector.cpp
+++ b/src/editor/TileSelector.cpp
@@ -63,11 +63,13 @@ QLabel* TileSelector::createNewLabel(QWidget* parent, const char* text)
     return label;
 }
 
-template <typename T>
-void TileSelector::sectionLayout(QGridLayout*& layout, int usedIdCounter, QWidget* parent, T id)
+template <typename... T>
+QGridLayout* TileSelector::creatSectionLayout(QWidget* parent, T... ids)
 {
-    TileButton* button = new TileButton(id, parent);
-    layout->addWidget(button, usedIdCounter / 3, usedIdCounter % 3);
+    QGridLayout* layout = new QGridLayout();
+    int          usedIdCounter = 0;
+    sectionLayout(layout, usedIdCounter, parent, ids...);
+    return layout;
 }
 
 template <typename T, typename... Rest>
@@ -80,13 +82,11 @@ void TileSelector::sectionLayout(
     sectionLayout(layout, usedIdCounter, parent, ids...);
 }
 
-template <typename... T>
-QGridLayout* TileSelector::creatSectionLayout(QWidget* parent, T... ids)
+template <typename T>
+void TileSelector::sectionLayout(QGridLayout*& layout, int usedIdCounter, QWidget* parent, T id)
 {
-    QGridLayout* layout = new QGridLayout();
-    int          usedIdCounter = 0;
-    sectionLayout(layout, usedIdCounter, parent, ids...);
-    return layout;
+    TileButton* button = new TileButton(id, parent);
+    layout->addWidget(button, usedIdCounter / 3, usedIdCounter % 3);
 }
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/TileSelector.hpp b/src/editor/TileSelector.hpp
index 2b0ebd8..25bdd2e 100644
--- a/src/editor/TileSelector.hpp
+++ b/src/editor/TileSelector.hpp
@@ -17,20 +17,65 @@
 
 namespace editor
 {
-
+/**
+ * The TileSelector is part of the MainWindow.
+ * It displays the tiles that can be selected within categories, to be placed on the
+ * map of the LevelScene.
+ */
 class TileSelector : public QScrollArea {
 public:
+/**
+ * Creates the TileSelector with the provided parent.
+ * The appearance of the selector is hardcoded by the arguments it provides its functions.
+ * There should not be created more then one of these at a time.
+ * @param parent The parent to set for the TileSelector
+ */
     TileSelector(QWidget *parent = nullptr);
-    
 private:
+/**
+ * Creates a label of a category to be displayed.
+ * @param parent The parent to set for the QLabel.
+ * @param text The text of the label.
+ */
     QLabel *createNewLabel(QWidget* parent, const char *text);
-
-    template<typename T>
-    void sectionLayout(QGridLayout*& layout, int usedIdCounter, QWidget* parent, T id);
-    template<typename T, typename... Rest>
-    void sectionLayout(QGridLayout*& layout, int usedIdCounter, QWidget* parent, T id, Rest...ids);
+/**
+ * Creates a section of the TileSelector.
+ * Before this there should always be a category label be created.
+ * The section contains TileButtons listed in the same order, that the ids for them
+ * are provided. After 3 buttons the next line is used. Reordering the TileButtons
+ * can simply be done by changing the order in which their ids are provided.
+ * @param parent The parent to set for this QGridLayout.
+ * @param ids A list of the ids for which TileButtons will be created.
+ */
     template<typename... T>
     QGridLayout* creatSectionLayout(QWidget* parent, T... ids);
+/**
+ * A recursive helper function for createSectionLayout.
+ * Each time it is called it adds a TileButton for the first of the provided ids to the
+ * QGridLayout. The id then is discarded and this function is called again with the
+ * remaining ids. 
+ * @param layout A link to the QGridLayout the TileButtons are added to.
+ * @param usedIdCounter Contains what the number of the current used id is. Needed to
+ * add the TileButton to the correct position of the grid.
+ * @param parent The parent the TileButtons will be set to.
+ * @param id The current id a TileButton will be created for.
+ * @param ids The remaining ids for which a TileButton will be created in a future
+ * function call.
+ */
+    template<typename T, typename... Rest>
+    void sectionLayout(QGridLayout*& layout, int usedIdCounter, QWidget* parent, T id, Rest...ids);
+/**
+ * The end of the recursive helper function sectionLayout.
+ * When this is called no more but 1 id is remaining for which a TileButton will be created.
+ * @param layout A link to the QGridLayout the TileButtons are added to.
+ * @param usedIdCounter Contains what the number of the current used id is. Needed to
+ * add the TileButton to the correct position of the grid.
+ * @param parent The parent the TileButtons will be set to.
+ * @param id The current id a TileButton will be created for.
+ */
+    template<typename T>
+    void sectionLayout(QGridLayout*& layout, int usedIdCounter, QWidget* parent, T id);
+    
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/TopBar.cpp b/src/editor/TopBar.cpp
index 04c6800..e63fc7a 100644
--- a/src/editor/TopBar.cpp
+++ b/src/editor/TopBar.cpp
@@ -41,8 +41,10 @@ TopBar::TopBar(const std::string& level_name, QWidget* parent) : QToolBar(parent
     QPushButton* zoom_in = new ZoomInButton(right_container);
     QPushButton* zoom_out = new ZoomOutButton(right_container);
     QPushButton* zoom_info = new ZoomInfo(right_container);
-    AdvancedPlacementSwitch* checkedBox = new AdvancedPlacementSwitch("Kacheln automatisch setzen", container);
-    left_layout->addWidget(checkedBox);
+    AdvancedPlacementSwitch* symmetryBox = new AdvancedPlacementSwitch("symmetrisches Bearbeiten", false, container);
+    left_layout->addWidget(symmetryBox);    //diese Reihenfolge vermeidet einen Bug, bei dem False zu true wird
+    AdvancedPlacementSwitch* placementBox = new AdvancedPlacementSwitch("Kacheln automatisch setzen", true, container);
+    left_layout->addWidget(placementBox);
     right_layout->addStretch();
     right_layout->addWidget(zoom_out);
     right_layout->addWidget(zoom_info);
-- 
GitLab


From c56aa68aef1d4d82ebf843cd142472e657131bc4 Mon Sep 17 00:00:00 2001
From: Nils <nils-jonathan.eckardt@informatik.hs-fulda.de>
Date: Mon, 10 Feb 2025 01:21:54 +0100
Subject: [PATCH 20/26] added Last comments

---
 src/editor/LevelScene.cpp | 94 ++++++++++++++++++++++++++-------------
 src/editor/LevelScene.hpp | 30 +++++++++++--
 2 files changed, 91 insertions(+), 33 deletions(-)

diff --git a/src/editor/LevelScene.cpp b/src/editor/LevelScene.cpp
index 9a2e1df..2102594 100644
--- a/src/editor/LevelScene.cpp
+++ b/src/editor/LevelScene.cpp
@@ -334,7 +334,33 @@ void LevelScene::placeCliff(bool placedLand, int index){
 
 	int16_t surroundingIDs[8] = {-2,-2,-2,-2,-2,-2,-2,-2};	//-2 = uninitialisiert, -1 = kartenrand
 	bool marchingSquares[8][4] = {false};
-	
+
+    /*
+        FUNKTIONSWEISE:
+        1. Laden der umliegenden 8 tile IDs
+        Hierfür wird zuerst geprüft, ob diese sich im Kartenrand befinden. In diesem fall
+        werden sie auf -1 gesetzt (daher int16_t nicht uint8_t). Anschließend werden die IDs
+        der tiles geladen.
+        2. Die geladenen Ids müssen gefiltert werden. Nicht alle IDs sind direkt verwendbar.
+        Riffe, Wälder und Gebirge werden als Land oder Wasser angesehen. Straßen und Gebäude
+        werden als Land behandelt. (dies kann einfach geändert werden, indem man diese auf -1
+        setzt). 
+        3. Die IDs werden remapped. Die Tiles haben die IDs 1,18-29. Um sie sich nutzbar machen
+        zu können müssen diese in 0-15 gemapped werden. Auf diese Weise kann aus einer ID ein 
+        tile und umgekehrt berechnet werden.
+        4. Berechnung der neuen IDs Der Ansatz der Berechnung ist vom Marching Cubes Algorithmus
+        (hier 2D als Marching Squares) abgeleitet. Darin ist jede Ecke eines Tiles entweder Innen
+        oder Außen, hier: Land (true) oder Wasser (false). Nun wird das Land/Wasser an den Ecken
+        hinzugefügt.
+        5. Aus den Berechneten Marching Squares werden nun die neuen IDs berechnet. Die Reihenfolge
+        der Ecken: TopLeft, TopRight, BottomRight, BottomLeft
+        6. Remappe die IDs zurück zu setzbaren IDs für die Karte. 0-15 werden zu 1,18-29 gemapped.
+        Für den Edgecase TopLeft, BottomRight existiert keine Textur. Stattdessen wir eine einzelne
+        TopLeft Ecke verwendet.
+        7.Setzen der neu berechneten Files. Wichtig hier ist, dass Riffe, die nicht verändert
+        wurden auch nicht verändert werden.
+    */
+
 	//Überprüfe Kartenränder, setze diese auf -1
 	if(index < m_width){					//oberer Kartenrand
 		surroundingIDs[7] = -1;
@@ -359,21 +385,16 @@ void LevelScene::placeCliff(bool placedLand, int index){
 
 	//Erhalte IDs von den umliegenden 8 Feldern, die kein Kartenrand sind
 	//startet in der mitte Oben, gehe im Uhrzeigersinn
-	if(surroundingIDs[0] == -2) surroundingIDs[0] = (int16_t) m_tile_ids[index - m_width];
-	if(surroundingIDs[1] == -2) surroundingIDs[1] = (int16_t) m_tile_ids[index - m_width + 1];
-	if(surroundingIDs[2] == -2) surroundingIDs[2] = (int16_t) m_tile_ids[index + 1];
-	if(surroundingIDs[3] == -2) surroundingIDs[3] = (int16_t) m_tile_ids[index + m_width + 1];
-	if(surroundingIDs[4] == -2) surroundingIDs[4] = (int16_t) m_tile_ids[index + m_width];
-	if(surroundingIDs[5] == -2) surroundingIDs[5] = (int16_t) m_tile_ids[index + m_width - 1];
-	if(surroundingIDs[6] == -2) surroundingIDs[6] = (int16_t) m_tile_ids[index - 1];
-	if(surroundingIDs[7] == -2) surroundingIDs[7] = (int16_t) m_tile_ids[index - m_width - 1];
+    for(int i=0;i<8;i++){
+	    if(surroundingIDs[i] == -2) surroundingIDs[i] = (int16_t) m_tile_ids[calcDir(i, index)];
+    }
 
 	//Ids können nicht lesbare Tiles enthalten, diese Herausfiltern
-	for(int i = 0; i < 8; i++){
+	for(int i = 0; i < 8; i++){                            //1 = Wasser, 0 = Land, -1 = unverändert
 		if(surroundingIDs[i] == 17)                          surroundingIDs[i] = 1;		//Riff als Wasser angesehen
 		if(surroundingIDs[i] == 2 || surroundingIDs[i] == 3) surroundingIDs[i] = 0;		//Wald, Gebirge als Land angesehen
-		if(surroundingIDs[i] > 3 && surroundingIDs[i] < 17)  surroundingIDs[i] = -1;	//Straßen werden nicht verändert
-		if(surroundingIDs[i] > 29)                           surroundingIDs[i] = 0;	//Gebäude werden als Land angesehen
+		if(surroundingIDs[i] > 3 && surroundingIDs[i] < 17)  surroundingIDs[i] = 0;     //Straßen werden als Land angesehen
+		if(surroundingIDs[i] > 29)                           surroundingIDs[i] = 0;	    //Gebäude werden als Land angesehen
 	}
 
 	//ID remapping um damit arbeiten zu können
@@ -445,13 +466,28 @@ void LevelScene::placeCliff(bool placedLand, int index){
 }
 
 void LevelScene::placeRoad(int index, bool updateFlag){
-	const int16_t IdToSum[] = {5,10,13,14,11,7,15,6,3,12,9};
+	//const int16_t IdToSum[] = {5,10,13,14,11,7,15,6,3,12,9};
 	const uint8_t SumToId[] = {6,6,7,14,6,6,13,11,7,16,7,10,15,8,9,12};
 	
 	bool tileDirections[] = {false,false,false,false};
 	int16_t surroundingIDs[] = {-1,-1,-1,-1};		//-1 = kartenrand oder keine strasse
 	uint8_t placedID = 0;
 	
+    /*
+        FUNKTIONSWEISE:
+        1. Laden der umliegenden 4 tile IDs falls diese nicht im Kartenrand stecken.
+        2. Die geladenen Ids müssen gefiltert werden. Tiles, die nicht Straßen sind, oder
+        Brücken sind werden nicht behandelt.
+        3. Berechnung in welchen Richtungen sich Straßen befinden.
+        4. Aus den berechneten Richtungen wird nun eine neue ID gebildet. Reihenfolge der
+        Richtungen: Up, Right, Down, Left
+        5. Die Berechnete ID wird zu einer verwendbaren ID gemapped. 0-15 werden zu 6-16 gemapped.
+        Straßen, die in weniger als 2 Richtungen zeigen gibt es nicht. Die Textur der Kreuzung,
+        die in alle 4 Richtungen zeigt ist falsch und zeigt nicht nach unten.
+        6. Setzen des neu berechneten Tiles. Im Anschluss wird die selbe Funktion für die
+        umliegenden 4 Tiles aufgerufen, falls diese Straßen beinhalten. 
+    */
+
 	//Erhalte IDs der umliegenden Felder - im Uhrzeigersinn, start: oben
 	//Vorgehen: überprüfe, ob die obere Zelle im Kartenrand ist. Wenn nicht erhalte index der oberen Zelle
 	if(!(index < m_width))                surroundingIDs[0] = (int16_t) m_tile_ids[index - m_width];
@@ -459,13 +495,9 @@ void LevelScene::placeRoad(int index, bool updateFlag){
 	if(!(index > m_width * (m_height-1))) surroundingIDs[2] = (int16_t) m_tile_ids[index + m_width];
 	if(!(index % m_width == 0))           surroundingIDs[3] = (int16_t) m_tile_ids[index - 1];
 	
-	//Umformen der IDs oder ID ist keine Straße
+	//Filtern der IDs, die keine Straßen sind
 	for(int i = 0; i < 4; i++){
-		if(surroundingIDs[i] < 6 || surroundingIDs[i] > 16){
-			surroundingIDs[i] = -1;			//ID ist keine Strasse
-		} else {
-			surroundingIDs[i] = IdToSum[ surroundingIDs[i] - 6];	//id remapping
-		}
+		if(surroundingIDs[i] < 4 || surroundingIDs[i] > 16) surroundingIDs[i] = -1;
 	}
 
 	//Berechne in welche Richtungen das neue Tile Zeigt
@@ -494,21 +526,23 @@ void LevelScene::placeRoad(int index, bool updateFlag){
 }
 
 int LevelScene::calcDir(int i, int index){
-    if(i==0) return (index - m_width);
-    if(i==1) return (index - m_width + 1);
-    if(i==2) return (index + 1);
-    if(i==3) return (index + m_width + 1);
-    if(i==4) return (index + m_width);
-    if(i==5) return (index + m_width - 1);
-    if(i==6) return (index - 1);
-    if(i==7) return (index - m_width - 1);
+    switch(i){
+        case(0): return (index - m_width);
+        case(1): return (index - m_width + 1);
+        case(2): return (index + 1);
+        case(3): return (index + m_width + 1);
+        case(4): return (index + m_width);
+        case(5): return (index + m_width - 1);
+        case(6): return (index - 1);
+        case(7): return (index - m_width - 1);
+    }
     throw std::invalid_argument("i has to be 0 <= i <= 7");
 }
 
 bool LevelScene::isntIdentical(int16_t id, int index){
-    bool flag  = (!(id == -1 ||               //kartenrand
-    (id == 0 && m_tile_ids[index]==2) ||   //wald
-    (id == 0 && m_tile_ids[index]==3) ||   //gebirge
+    bool flag  = (!(id == -1 ||             //kartenrand
+    (id == 0 && m_tile_ids[index]==2) ||    //wald
+    (id == 0 && m_tile_ids[index]==3) ||    //gebirge
     (id == 1 && m_tile_ids[index]==17)) );  //riff
     return flag;
 }
diff --git a/src/editor/LevelScene.hpp b/src/editor/LevelScene.hpp
index f23511c..9fe6007 100644
--- a/src/editor/LevelScene.hpp
+++ b/src/editor/LevelScene.hpp
@@ -118,8 +118,6 @@ private:
      */
     bool is_water_tile(uint8_t id);
 
-    bool isntIdentical(int16_t id, int index);
-
     /**
      * Updates the level name stored in LevelScene to new_name.
      * The onLevelNameUpdated event method is emitted by the LevelNameEdit Widget.
@@ -201,12 +199,38 @@ private:
      * correct shape of the new cliffs and places them.
      * @param placedLand If Land was placed - not water. Needed to evaluate if land should
      * be added or removed around the placed tile.
-     * @param index Index of the tile water or land is placed on. The placed cliffs are the
+     * @param index Position of the tile water or land is placed on. The placed cliffs are the
      * surrounding 8 tiles.
      */
     void placeCliff(bool placedLand, int index);
+    /**
+     * A recursive function of advanced placement used to adjust the roads around the placed one.
+     * The surrounding roads above, bellow, to the left and right are detected and used to
+     * calculate the shape the newly placed road should have. After that the function is again
+     * called for those up to 4 roads around.
+     * @param index The position of the newly placed road.
+     * @param updateFlag Used in the recursion. When true it calls itself on the 4 surrounding
+     * tiles. When false the recursion ends and it doesnt call itself again. 
+     */
     void placeRoad(int index, bool updateFlag);
+    /**
+     * A technical helper function for placeCliff. When calculating the Direction of the
+     * surrounding 8 tiles different calculations have to be done due to the map being
+     * represented as a 1D array rather then a 2D one. As a result it would not be easily
+     * possible to iterate through index of the 8 surrounding tiles, starting with the one
+     * above, then turning clockwise. This function is used for this to prevent code duplication.
+     */
     int calcDir(int i, int index);
+    /**
+     * A technical helper function for placeCliff. When evaluating whether land or water has
+     * been placed trees and mountains are treated as terrain, while reefs are treated as water.
+     * However once the placement of new cliffs has been determained reefs should not be replaced
+     * by water when there should not be made any change to the cell. This function fixes a bug
+     * where this would happen.
+     * @param id The id of a tile, this bug could trigger on.
+     * @param index The position the old tile is sitting on, possibly to be replaced by a new one.
+     */
+    bool isntIdentical(int16_t id, int index);
 
     /**
      * Places a new QGraphicsPixmapItem using the given tile_id at the given index.
-- 
GitLab


From f791e3a0f70b1a652df940a6bd577e67bb564b1d Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Mon, 10 Feb 2025 01:55:05 +0100
Subject: [PATCH 21/26] style guide changes

---
 src/editor/LevelNameEdit.hpp  |   4 +-
 src/editor/LevelScene.cpp     | 424 +++++++++++-----------------------
 src/editor/LevelScene.hpp     |  56 ++---
 src/editor/SpriteProvider.cpp |  10 +-
 src/editor/TopBar.cpp         |  27 ++-
 src/editor/TopBar.hpp         |   8 +-
 src/editor/main.cpp           |  36 +--
 src/game/level/Level.cpp      |  12 +-
 8 files changed, 217 insertions(+), 360 deletions(-)

diff --git a/src/editor/LevelNameEdit.hpp b/src/editor/LevelNameEdit.hpp
index 3edf824..28b29cf 100644
--- a/src/editor/LevelNameEdit.hpp
+++ b/src/editor/LevelNameEdit.hpp
@@ -21,10 +21,10 @@ public:
     /**
      * Creates a LevelNameEdit Widget prefilling the provided level_name.
      * The parent of the LevelNameEdit Widget is set to the provided parent.
-     * @param level_name The initial name of the level.
+     * @param levelName The initial name of the level.
      * @param parent The Widget that should be set as the parent of this Widget.
      */
-    LevelNameEdit(const std::string& level_name, QWidget* parent = nullptr);
+    LevelNameEdit(const std::string& levelName, QWidget* parent = nullptr);
 
 protected:
     /**
diff --git a/src/editor/LevelScene.cpp b/src/editor/LevelScene.cpp
index 5332f4e..70081ac 100644
--- a/src/editor/LevelScene.cpp
+++ b/src/editor/LevelScene.cpp
@@ -31,17 +31,17 @@ namespace editor
 LevelScene::LevelScene(
     const std::string& name, int width, int height, std::vector<uint8_t> tile_ids,
     const std::string& file_path, QWidget* parent)
-    : QGraphicsScene(parent), m_name(name), m_width(width), m_height(height), m_tile_ids(tile_ids),
-      m_file_path(file_path), m_selected_tile_id(2), m_advanced_tile_placement(false),
-      m_symmetric_tile_placement(false)
+    : QGraphicsScene(parent), m_name(name), m_width(width), m_height(height), m_tileIds(tile_ids),
+      m_filePath(file_path), m_selectedTileId(2), m_advancedTilePlacement(false),
+      m_symmetricTilePlacement(false)
 {
     setSceneRect(0, 0, m_width * 16, m_height * 16); // set dimensions of the QGraphicsScene
 
     // iterate over all of the level map's tile id and build the two layers 
     // bottom layer (static) -> Tile classes (QGraphicsPixmapItem descendants)
     // top layer (dynamic) -> direct QGraphicsPixmapItems (also stored in m_tile_occupants)
-    m_tile_occupants = {}; // holds QGraphicsPixmapItems of top layer (nullptr if top pximap item not needed)
-    m_tile_occupants.reserve(tile_ids.size()); // size will be same as tile ids array at the end
+    m_tileOccupants = {}; // holds QGraphicsPixmapItems of top layer (nullptr if top pximap item not needed)
+    m_tileOccupants.reserve(tile_ids.size()); // size will be same as tile ids array at the end
     for (size_t index = 0; index < tile_ids.size(); index++)
     {
         int   x = (index % m_width) * 16;
@@ -55,12 +55,12 @@ LevelScene::LevelScene(
             // if index is not on border and tile id is not grass the top layer is needed
             // the top QGraphicsPixmapItem also needs to be stored to be able to switch
             // it out for a different one later
-            m_tile_occupants.push_back(occupy_tile(index, tile_ids[index]));
+            m_tileOccupants.push_back(occupyTile(index, tile_ids[index]));
         }
         else
         {
             // top layer not needed
-            m_tile_occupants.push_back(nullptr);
+            m_tileOccupants.push_back(nullptr);
         }
     }
 }
@@ -71,12 +71,11 @@ LevelScene* LevelScene::empty(const std::string& name, int width, int height, QW
     tile_ids.reserve(width*height);
 
     // create top row with cliffs
-    tileIds.push_back(22); // cliff corner top left
-    for (int i = 0; i < width - 2; i++)
-    {
-        tileIds.push_back(19); // cliff bottom
+    tile_ids.push_back(22); // cliff corner top left 
+    for (int i = 0; i < width - 2; i++) {
+        tile_ids.push_back(19); // cliff bottom
     }
-    tileIds.push_back(23); // cliff corner top right
+    tile_ids.push_back(23); // cliff corner top right 
 
     // create main rows with cliff at start and end grass in the middle
     for (int i = 0; i < height - 2; i++) {
@@ -84,21 +83,20 @@ LevelScene* LevelScene::empty(const std::string& name, int width, int height, QW
         for (int j = 0; j < width - 2; j++) {
             tile_ids.push_back(0); // pleins
         }
-        tileIds.push_back(20); // cliff left
+        tile_ids.push_back(20); // cliff left
     }
 
     // create bottom row with cliffs
-    tileIds.push_back(24); // cliff corner bottom left
-    for (int i = 0; i < width - 2; i++)
-    {
-        tileIds.push_back(18); // cliff top
+    tile_ids.push_back(24); // cliff corner bottom left 
+    for (int i = 0; i < width - 2; i++) {
+        tile_ids.push_back(18); // cliff top
     }
-    tileIds.push_back(25); // cliff corner bottom right
+    tile_ids.push_back(25); // cliff corner bottom right 
 
     return new LevelScene(name, width, height, tile_ids, "", parent);
 }
 
-LevelScene* LevelScene::fromFile(const std::string& filePath, QWidget* parent)
+LevelScene* LevelScene::fromFile(const std::string& file_path, QWidget* parent)
 {
     HighFive::File file(file_path, HighFive::File::ReadOnly);
     HighFive::DataSet tilesarray_set = file.getDataSet("tilesarray");
@@ -113,7 +111,7 @@ LevelScene* LevelScene::fromFile(const std::string& filePath, QWidget* parent)
     tilesarray_set.getAttribute("name").read(name);
     tilesarray_set.read(level_tilesarray);
 
-    return new LevelScene(name, width, height, levelTilesarray, filePath, parent);
+    return new LevelScene(name, width, height, level_tilesarray, file_path, parent);
 }
 
 std::string LevelScene::getName()
@@ -133,13 +131,15 @@ int LevelScene::getHeight()
 
 bool LevelScene::isBorder(int index)
 {
-    return (index / m_width) == 0 || (index / m_width) == (m_height - 1) ||
-           (index % m_width) == 0 || (index % m_width) == (m_width - 1);
+    return (index / m_width) == 0 
+    || (index / m_width) == (m_height -1)
+    || (index % m_width) == 0 
+    || (index % m_width) == (m_width - 1);
 }
 
 bool LevelScene::isWaterTile(uint8_t id)
 {
-    if (id == 1)
+    if (id == 1) 
     {
         return true;
     }
@@ -150,14 +150,14 @@ bool LevelScene::isWaterTile(uint8_t id)
     return false;
 }
 
-void LevelScene::onLevelNameUpdated(std::string newName)
+void LevelScene::onLevelNameUpdated(std::string new_name)
 {
-    m_name = newName;
+    m_name = new_name;
 }
 
 void LevelScene::onLevelWriteRequested()
 {
-    if (m_file_path.empty()) {
+    if (m_filePath.empty()) {
         // create a nice file name from the levelname
         // it will be displayed in the file save dialog
         std::string filepath = m_name;
@@ -166,18 +166,18 @@ void LevelScene::onLevelWriteRequested()
         filepath = "/" + filepath + ".h5";
 
         // get path at which the level should be written to
-        m_file_path = QFileDialog::getSaveFileName(
+        m_filePath = QFileDialog::getSaveFileName(
             (QWidget*) parent(), "Level Speichern", QDir::currentPath() + QString(filepath.c_str()), "HDF5 Files (*.h5 *.hdf5)").toStdString();
     }
-    if (m_file_path.empty()) {
+    if (m_filePath.empty()) {
         return; // if still empty dialog was canceled
     }
 
     // write level to hdf5 file
     try {
-        HighFive::File file(m_file_path, HighFive::File::Overwrite);
-        HighFive::DataSet tilesarray_set = file.createDataSet<std::vector<uint8_t>>("tilesarray", m_tile_ids);
-        tilesarray_set.write(m_tile_ids);
+        HighFive::File file(m_filePath, HighFive::File::Overwrite);
+        HighFive::DataSet tilesarray_set = file.createDataSet<std::vector<uint8_t>>("tilesarray", m_tileIds);
+        tilesarray_set.write(m_tileIds);
         tilesarray_set.createAttribute<int>("width", m_width).write(m_width);
         tilesarray_set.createAttribute<int>("height", m_height).write(m_height);
         tilesarray_set.createAttribute<std::string>("name", m_name).write(m_name);
@@ -190,102 +190,102 @@ void LevelScene::onLevelWriteRequested()
 
 void LevelScene::onTileEntered(int index)
 {
-    if (m_selected_tile_id == m_tile_ids[index])
+    if (m_selectedTileId == m_tileIds[index])
     {
         return;
     }
-    if (isBorder(index) && !isWaterTile(m_selected_tile_id))
+    if (isBorder(index) && !isWaterTile(m_selectedTileId))
     {
         // only water tiles can be set on the border
         return;
     }
-    if (m_tile_occupants[index] != nullptr)
+    if (m_tileOccupants[index] != nullptr)
     {
-        removeItem(m_tile_occupants[index]);
-        delete m_tile_occupants[index];
-        m_tile_occupants[index] = nullptr;
+        removeItem(m_tileOccupants[index]);
+        delete m_tileOccupants[index];
+        m_tileOccupants[index] = nullptr;
     }
-    if ((!is_border(index) && m_selected_tile_id > 0) || is_border(index))
+    if ((!isBorder(index) && m_selectedTileId > 0) || isBorder(index))
     {
-        m_tile_occupants[index] = occupyTile(index, m_selected_tile_id);
+        m_tileOccupants[index] = occupyTile(index, m_selectedTileId);
     }
 }
 
 void LevelScene::onTileExited(int index)
 {
-    if (m_selected_tile_id == m_tile_ids[index])
+    if (m_selectedTileId == m_tileIds[index])
     {
         return;
     }
-    if (m_tile_occupants[index] != nullptr)
+    if (m_tileOccupants[index] != nullptr)
     {
-        removeItem(m_tile_occupants[index]);
+        removeItem(m_tileOccupants[index]);
         // Interestingly QGraphicsScene does take ownership of the QGraphicsPixmapItems that
         // are added to it, but inside removeItem it gives that ownership back without destroying it.
         // I first assumed that removeItem would also destroy the Pixmap Items, but valgrind taught me 
         // otherwise. :)
         // So therefore we delete it explicitly. That is probably the only place in the entire application
         // where we explicitly free memory.
-        delete m_tile_occupants[index];
-        m_tile_occupants[index] = nullptr;
+        delete m_tileOccupants[index];
+        m_tileOccupants[index] = nullptr;
     }
-    if (m_tile_ids[index] > 0)
+    if (m_tileIds[index] > 0)
     {
-        m_tile_occupants[index] = occupyTile(index, m_tile_ids[index]);
+        m_tileOccupants[index] = occupyTile(index, m_tileIds[index]);
     }
 }
 
 void LevelScene::setTile(int index, uint8_t id)
 {
-    m_tile_ids[index] = id;
-    if (m_tile_occupants[index] != nullptr)
+    m_tileIds[index]=id;
+    if (m_tileOccupants[index] != nullptr)
     {
-        removeItem(m_tile_occupants[index]);
-        delete m_tile_occupants[index];
-        m_tile_occupants[index] = nullptr;
+        removeItem(m_tileOccupants[index]);
+        delete m_tileOccupants[index];
+        m_tileOccupants[index] = nullptr;
     }
-    if (m_tile_ids[index] > 0)
+    if (m_tileIds[index] > 0)
     {
-        m_tile_occupants[index] = occupy_tile(index, id);
+        m_tileOccupants[index] = occupyTile(index, id);
     } 
 }
 
 void LevelScene::onTileClicked(int index)
 {
-	if (is_border(index) && !is_water_tile(m_selected_tile_id)) {
+	if (isBorder(index) && !isWaterTile(m_selectedTileId)) {
 		return;                             //no Placement allowed
 	}
 
-    m_tile_ids[index]=m_selected_tile_id;   //normal Placement
+    m_tileIds[index]=m_selectedTileId;   //normal Placement
 
-	if (m_advanced_tile_placement) {
+	if (m_advancedTilePlacement) {
         placeAdvancedTiles(index);          //advanced Placement
 	}
 
-    if(!m_symmetric_tile_placement) return;
+    if(!m_symmetricTilePlacement) return;
 
-    uint8_t id = m_selected_tile_id;
+    uint8_t id = m_selectedTileId;
     index = m_width * m_height - 1 -index;
     int swapID[22] ={11,10,9,8,12,16,15,14,13,17,19,18,21,20,25,24,23,22,29,28,27,26};
     if(id > 7 && id < 30) id = swapID[ id-8 ];
     if(id > 49 && id < 55) id += 5;  
     else if(id > 54 && id < 60) id -= 5;  
 
-    setTile(index,m_selected_tile_id);  //symmetric Placement
+    setTile(index,m_selectedTileId);  //symmetric Placement
 
-    if (m_advanced_tile_placement) {
+    if (m_advancedTilePlacement) {
         placeAdvancedTiles(index);      //symmetric advanced Placement
     }
 }
 
 void LevelScene::placeAdvancedTiles(int index)
 {
-    if(m_selected_tile_id > 5 && m_selected_tile_id < 17){	//Straße plaziert
+    if(m_selectedTileId > 5 && m_selectedTileId < 17){	//Straße plaziert
 		placeRoad(index, true);
 		return;
 	}
-	if((m_selected_tile_id > 16 && m_selected_tile_id < 30) || m_selected_tile_id == 1){	//Wasser plaziert
-		if(m_selected_tile_id == 17){
+	if((m_selectedTileId > 16 && m_selectedTileId < 30) || m_selectedTileId == 1){	//Wasser plaziert
+		if(m_selectedTileId == 17){
 			setTile(index,17);
 		} else {
 			setTile(index,1);
@@ -293,34 +293,34 @@ void LevelScene::placeAdvancedTiles(int index)
 		placeCliff(false, index);
 		return;
 	}
-	if(m_selected_tile_id == 0 || m_selected_tile_id == 2 || m_selected_tile_id == 3){	//Land plaziert
-		setTile(index,m_selected_tile_id);
+	if(m_selectedTileId == 0 || m_selectedTileId == 2 || m_selectedTileId == 3){	//Land plaziert
+		setTile(index,m_selectedTileId);
 		placeCliff(true, index);
 		return;
 	}
-    setTile(index, m_selected_tile_id);     //Gebäude plaziert
+    setTile(index, m_selectedTileId);     //Gebäude plaziert
 }
 
-void LevelScene::onNewTileIdSelected(uint8_t tileId)
+void LevelScene::onNewTileIdSelected(uint8_t tile_id)
 {
-    m_selected_tile_id = tileId;
+    m_selectedTileId = tile_id;
 }
 
 void LevelScene::onAdvancedPlacementToggled()
 {
-    m_advanced_tile_placement = !m_advanced_tile_placement;
+    m_advancedTilePlacement = !m_advancedTilePlacement;
 }
 
 void LevelScene::onSymmetryToggled()
 {
-    m_symmetric_tile_placement = !m_symmetric_tile_placement;
+    m_symmetricTilePlacement = !m_symmetricTilePlacement;
 }
 
-QGraphicsPixmapItem* LevelScene::occupy_tile(int index, uint8_t tile_id)
+QGraphicsPixmapItem* LevelScene::occupyTile(int index, uint8_t tile_id)
 {
     int                  x = (index % m_width) * 16;
     int                  y = (index / m_width) * 16;
-    QPixmap              tile_occupant = SpriteProvider::get_sprite(tile_id);
+    QPixmap              tile_occupant = SpriteProvider::getSprite(tile_id);
     QGraphicsPixmapItem* tile_occupant_item = addPixmap(tile_occupant);
     bool is_building_tile = tile_id >= 50;
     tile_occupant_item->setZValue(is_building_tile ? 2 + index : 1);
@@ -359,14 +359,14 @@ void LevelScene::placeCliff(bool placedLand, int index){
 
 	//Erhalte IDs von den umliegenden 8 Feldern, die kein Kartenrand sind
 	//startet in der mitte Oben, gehe im Uhrzeigersinn
-	if(surroundingIDs[0] == -2) surroundingIDs[0] = (int16_t) m_tile_ids[index - m_width];
-	if(surroundingIDs[1] == -2) surroundingIDs[1] = (int16_t) m_tile_ids[index - m_width + 1];
-	if(surroundingIDs[2] == -2) surroundingIDs[2] = (int16_t) m_tile_ids[index + 1];
-	if(surroundingIDs[3] == -2) surroundingIDs[3] = (int16_t) m_tile_ids[index + m_width + 1];
-	if(surroundingIDs[4] == -2) surroundingIDs[4] = (int16_t) m_tile_ids[index + m_width];
-	if(surroundingIDs[5] == -2) surroundingIDs[5] = (int16_t) m_tile_ids[index + m_width - 1];
-	if(surroundingIDs[6] == -2) surroundingIDs[6] = (int16_t) m_tile_ids[index - 1];
-	if(surroundingIDs[7] == -2) surroundingIDs[7] = (int16_t) m_tile_ids[index - m_width - 1];
+	if(surroundingIDs[0] == -2) surroundingIDs[0] = (int16_t) m_tileIds[index - m_width];
+	if(surroundingIDs[1] == -2) surroundingIDs[1] = (int16_t) m_tileIds[index - m_width + 1];
+	if(surroundingIDs[2] == -2) surroundingIDs[2] = (int16_t) m_tileIds[index + 1];
+	if(surroundingIDs[3] == -2) surroundingIDs[3] = (int16_t) m_tileIds[index + m_width + 1];
+	if(surroundingIDs[4] == -2) surroundingIDs[4] = (int16_t) m_tileIds[index + m_width];
+	if(surroundingIDs[5] == -2) surroundingIDs[5] = (int16_t) m_tileIds[index + m_width - 1];
+	if(surroundingIDs[6] == -2) surroundingIDs[6] = (int16_t) m_tileIds[index - 1];
+	if(surroundingIDs[7] == -2) surroundingIDs[7] = (int16_t) m_tileIds[index - m_width - 1];
 
 	//Ids können nicht lesbare Tiles enthalten, diese Herausfiltern
 	for(int i = 0; i < 8; i++){
@@ -431,206 +431,66 @@ void LevelScene::placeCliff(bool placedLand, int index){
     		if(marchingSquares[i][3]) surroundingIDs[i] += 1;
         }
     }
-
-    // ID remapping um damit arbeiten zu können
-    for (short& surroundingID : surroundingIDs)
-    {
-        if (surroundingID == -1)
-        {
-        }
-        else if (surroundingID == 0)
-        {
-            surroundingID = 15;
-        }
-        else if (surroundingID == 1)
-        {
-            surroundingID = 0;
-        }
-        else
-        {
-            surroundingID = IdToSum[surroundingID - 18];
-        }
-    }
-
-    // Berechne Marching Squares aus der remapped Id
-    for (int i = 0; i < 8; i++)
-    {
-        if (surroundingIDs[i] / 8 == 1)
-        {
-            marchingSquares[i][0] = true; // top left
-            surroundingIDs[i] -= 8;
-        }
-        if (surroundingIDs[i] / 4 == 1)
-        {
-            marchingSquares[i][1] = true; // top right
-            surroundingIDs[i] -= 4;
-        }
-        if (surroundingIDs[i] / 2 == 1)
-        {
-            marchingSquares[i][2] = true; // bottom right
-            surroundingIDs[i] -= 2;
-        }
-        if (surroundingIDs[i] == 1)
-        {
-            marchingSquares[i][3] = true; // bottom left
-        }
-    }
-
-    // Einfügen/Abziehen des Landes
-    marchingSquares[0][2] = placedLand; // oben
-    marchingSquares[0][3] = placedLand;
-    marchingSquares[1][3] = placedLand; // oben rechts
-    marchingSquares[2][3] = placedLand; // rechts
-    marchingSquares[2][0] = placedLand;
-    marchingSquares[3][0] = placedLand; // untern rechts
-    marchingSquares[4][0] = placedLand; // unten
-    marchingSquares[4][1] = placedLand;
-    marchingSquares[5][1] = placedLand; // unten links
-    marchingSquares[6][1] = placedLand; // links
-    marchingSquares[6][2] = placedLand;
-    marchingSquares[7][2] = placedLand; // oben links
-
-    // Berechne remapped ID aus Marching Squares
-    for (int i = 0; i < 8; i++)
-    {
-        if (surroundingIDs[i] > -1)
-        {
-            surroundingIDs[i] = 0;
-            if (marchingSquares[i][0])
-            {
-                surroundingIDs[i] += 8;
-            }
-            if (marchingSquares[i][1])
-            {
-                surroundingIDs[i] += 4;
-            }
-            if (marchingSquares[i][2])
-            {
-                surroundingIDs[i] += 2;
-            }
-            if (marchingSquares[i][3])
-            {
-                surroundingIDs[i] += 1;
-            }
-        }
-    }
-
-    // Remappe ID für setzbare Tiles
-    for (int i = 0; i < 8; i++)
-    {
-        if (surroundingIDs[i] > -1)
-        {
-            surroundingIDs[i] = SumToId[surroundingIDs[i]];
-        }
-    }
-
-    // Plaziere Tiles
-    for (int i = 0; i < 8; i++)
-    {
-        if (isntIdentical(surroundingIDs[i], calcDir(i, index)))
-        {
-            setTile(calcDir(i, index), (uint8_t)surroundingIDs[i]);
-        }
+	
+	//Remappe ID für setzbare Tiles
+	for(int i = 0; i < 8; i++){
+		if(surroundingIDs[i] > -1) surroundingIDs[i] = SumToId[ surroundingIDs[i] ];
+	}
+	
+	//Plaziere Tiles
+    for(int i = 0; i < 8; i++){
+	    if(isntIdentical(surroundingIDs[i], calcDir(i, index)))
+            setTile( calcDir(i, index),(uint8_t)surroundingIDs[i] );
     }
 }
 
-void LevelScene::placeRoad(int index, bool updateFlag)
-{
-    const int16_t IdToSum[] = {5, 10, 13, 14, 11, 7, 15, 6, 3, 12, 9};
-    const uint8_t SumToId[] = {6, 6, 7, 14, 6, 6, 13, 11, 7, 16, 7, 10, 15, 8, 9, 12};
-
-    bool    tileDirections[] = {false, false, false, false};
-    int16_t surroundingIDs[] = {-1, -1, -1, -1}; //-1 = kartenrand oder keine strasse
-    uint8_t placedID = 0;
-
-    // Erhalte IDs der umliegenden Felder - im Uhrzeigersinn, start: oben
-    // Vorgehen: überprüfe, ob die obere Zelle im Kartenrand ist. Wenn nicht erhalte index der
-    // oberen Zelle
-    if (!(index < m_width))
-    {
-        surroundingIDs[0] = (int16_t)m_tile_ids[index - m_width];
-    }
-    if (!((index + 1) % m_width == 0))
-    {
-        surroundingIDs[1] = (int16_t)m_tile_ids[index + 1];
-    }
-    if (!(index > m_width * (m_height - 1)))
-    {
-        surroundingIDs[2] = (int16_t)m_tile_ids[index + m_width];
-    }
-    if (!(index % m_width == 0))
-    {
-        surroundingIDs[3] = (int16_t)m_tile_ids[index - 1];
-    }
-
-    // Umformen der IDs oder ID ist keine Straße
-    for (int i = 0; i < 4; i++)
-    {
-        if (surroundingIDs[i] < 6 || surroundingIDs[i] > 16)
-        {
-            surroundingIDs[i] = -1; // ID ist keine Strasse
-        }
-        else
-        {
-            surroundingIDs[i] = IdToSum[surroundingIDs[i] - 6]; // id remapping
-        }
-    }
-
-    // Berechne in welche Richtungen das neue Tile Zeigt
-    for (int i = 0; i < 4; i++)
-    {
-        if (surroundingIDs[i] > -1)
-        {
-            tileDirections[i] = true;
-        }
-    }
-
-    // Berechne die Remapped ID
-    placedID = 0;
-    if (tileDirections[0])
-    {
-        placedID += 8;
-    }
-    if (tileDirections[1])
-    {
-        placedID += 4;
-    }
-    if (tileDirections[2])
-    {
-        placedID += 2;
-    }
-    if (tileDirections[3])
-    {
-        placedID += 1;
-    }
-
-    if (placedID == 0)
-    {
-        updateFlag = false; // Umliegende Tiles müssen nicht geupdated werden, da keine Strassen
-    }
-    placedID = SumToId[placedID]; // Berechnete Summe in Valide ID umformen
-    setTile(index, placedID);     // Tile setzen
+void LevelScene::placeRoad(int index, bool updateFlag){
+	const int16_t IdToSum[] = {5,10,13,14,11,7,15,6,3,12,9};
+	const uint8_t SumToId[] = {6,6,7,14,6,6,13,11,7,16,7,10,15,8,9,12};
+	
+	bool tileDirections[] = {false,false,false,false};
+	int16_t surroundingIDs[] = {-1,-1,-1,-1};		//-1 = kartenrand oder keine strasse
+	uint8_t placedID = 0;
+	
+	//Erhalte IDs der umliegenden Felder - im Uhrzeigersinn, start: oben
+	//Vorgehen: überprüfe, ob die obere Zelle im Kartenrand ist. Wenn nicht erhalte index der oberen Zelle
+	if(!(index < m_width))                surroundingIDs[0] = (int16_t) m_tileIds[index - m_width];
+	if(!((index + 1) % m_width == 0))     surroundingIDs[1] = (int16_t) m_tileIds[index + 1];
+	if(!(index > m_width * (m_height-1))) surroundingIDs[2] = (int16_t) m_tileIds[index + m_width];
+	if(!(index % m_width == 0))           surroundingIDs[3] = (int16_t) m_tileIds[index - 1];
+	
+	//Umformen der IDs oder ID ist keine Straße
+	for(int i = 0; i < 4; i++){
+		if(surroundingIDs[i] < 6 || surroundingIDs[i] > 16){
+			surroundingIDs[i] = -1;			//ID ist keine Strasse
+		} else {
+			surroundingIDs[i] = IdToSum[ surroundingIDs[i] - 6];	//id remapping
+		}
+	}
 
-    // Update umliegende Tiles
-    if (updateFlag)
-    {
-        if (tileDirections[0])
-        {
-            placeRoad((index - m_width), false); // update oben
-        }
-        if (tileDirections[1])
-        {
-            placeRoad((index + 1), false); // update rechts
-        }
-        if (tileDirections[2])
-        {
-            placeRoad((index + m_width), false); // update unten
-        }
-        if (tileDirections[3])
-        {
-            placeRoad((index - 1), false); // update links
-        }
-    }
+	//Berechne in welche Richtungen das neue Tile Zeigt
+	for(int i = 0; i < 4; i++){
+		if(surroundingIDs[i] > -1) tileDirections[i] = true;
+	}
+	
+	//Berechne die Remapped ID
+	placedID = 0;
+	if(tileDirections[0]) placedID += 8;
+	if(tileDirections[1]) placedID += 4;
+	if(tileDirections[2]) placedID += 2;
+	if(tileDirections[3]) placedID += 1;
+	
+	if(placedID == 0) updateFlag = false; 	//Umliegende Tiles müssen nicht geupdated werden, da keine Strassen
+	placedID = SumToId[placedID];			//Berechnete Summe in Valide ID umformen
+	setTile(index, placedID);	            //Tile setzen
+	
+	//Update umliegende Tiles
+	if(updateFlag){	
+		if(tileDirections[0]) placeRoad((index - m_width), false);	//update oben
+		if(tileDirections[1]) placeRoad((index + 1),       false);	//update rechts
+		if(tileDirections[2]) placeRoad((index + m_width), false);	//update unten
+		if(tileDirections[3]) placeRoad((index - 1),       false);	//update links
+	}
 }
 
 int LevelScene::calcDir(int i, int index){
@@ -645,13 +505,11 @@ int LevelScene::calcDir(int i, int index){
     throw std::invalid_argument("i has to be 0 <= i <= 7");
 }
 
-bool LevelScene::isntIdentical(int16_t id, int index)
-{
-    bool flag =
-        (id != -1 &&                            // kartenrand
-         (id != 0 || m_tile_ids[index] != 2) && // wald
-         (id != 0 || m_tile_ids[index] != 3) && // gebirge
-         (id != 1 || m_tile_ids[index] != 17)); // riff
+bool LevelScene::isntIdentical(int16_t id, int index){
+    bool flag  = (!(id == -1 ||               //kartenrand
+    (id == 0 && m_tileIds[index]==2) ||   //wald
+    (id == 0 && m_tileIds[index]==3) ||   //gebirge
+    (id == 1 && m_tileIds[index]==17)) );  //riff
     return flag;
 }
 
diff --git a/src/editor/LevelScene.hpp b/src/editor/LevelScene.hpp
index 81d2047..dafb2aa 100644
--- a/src/editor/LevelScene.hpp
+++ b/src/editor/LevelScene.hpp
@@ -50,7 +50,7 @@ namespace editor
  * The bottom layer always gets a z value of 0.
  * For non grass tile ids, QGraphicsPixmapItems are created on the second layer with a z value of 1
  * for terrain tiles and 2 + index for building tiles.
- * These Items are also saved in m_tile_occupants. The second layer is dynamic, by keeping pointers
+ * These Items are also saved in m_tileOccupants. The second layer is dynamic, by keeping pointers
  * to its Pixmap Items we can remove them and switch them around.
  */
 class LevelScene : public QGraphicsScene, public EventHandler {
@@ -62,11 +62,11 @@ public:
      * @param name The name of the level.
      * @param width The width of the level. Unit: number of tiles
      * @param height The height of the level. Unit: number of tiles
-     * @param tile_ids A vector of tile ids that define the level map.
-     * @param file_path The path to the file from which the level was loaded, empty string if level was just created.
+     * @param tileIds A vector of tile ids that define the level map.
+     * @param filePath The path to the file from which the level was loaded, empty string if level was just created.
      * @param parent The parent to set for the LevelScene.
      */
-    LevelScene(const std::string& name, int width, int height, std::vector<uint8_t> tile_ids, const std::string& file_path, QWidget *parent = nullptr);
+    LevelScene(const std::string& name, int width, int height, std::vector<uint8_t> tileIds, const std::string& filePath, QWidget *parent = nullptr);
 
     /**
      * Uses the LevelScene constructor internally to create an empty LevelScene (only grass, water cliffs on the borders).
@@ -80,11 +80,11 @@ public:
 
     /**
      * Uses the LevelScene constructor internally to create a LevelScene from an hdf5 file.
-     * @param file_path The path to the hdf5 file from which the LevelScene should be loaded.
+     * @param filePath The path to the hdf5 file from which the LevelScene should be loaded.
      * @param parent The parent to set for the newly created LevelScene.
      * @return A LevelScene that was loaded from a file.
      */
-    static LevelScene* fromFile(const std::string& file_path, QWidget *parent = nullptr);
+    static LevelScene* fromFile(const std::string& filePath, QWidget *parent = nullptr);
 
     /**
      * Gets the name of the level.
@@ -110,23 +110,23 @@ private:
      * @param index The position of an individual tile if you linearized the level map.
      * @return True or False if the given index corresponds to a border tile.
      */
-    bool is_border(int index);
+    bool isBorder(int index);
 
     /**
      * Checks if the tile id corresponds to a water tile.
      * @param id The tile id to check.
      * @return True or false if the given tile id corresponds to a water tile.
      */
-    bool is_water_tile(uint8_t id);
+    bool isWaterTile(uint8_t id);
 
     bool isntIdentical(int16_t id, int index);
 
     /**
-     * Updates the level name stored in LevelScene to new_name.
+     * Updates the level name stored in LevelScene to newName.
      * The onLevelNameUpdated event method is emitted by the LevelNameEdit Widget.
-     * @param new_name The new name of the level.
+     * @param newName The new name of the level.
      */
-    void onLevelNameUpdated(std::string new_name) override;
+    void onLevelNameUpdated(std::string newName) override;
 
     /**
      * Writes the level to the file from which it was loaded initially. 
@@ -137,14 +137,14 @@ private:
     void onLevelWriteRequested() override;
 
     /**
-     * Renders the currently selcted tile (m_selected_tile_id) on the provided index.
+     * Renders the currently selcted tile (m_selectedTileId) on the provided index.
      * The onTileEntered event method is emitted by the Tile object.
      * @param index The position of an individual tile if you were to linearized the level map.
      */
     void onTileEntered(int index) override;  
 
     /**
-     * Renders the old tile id from m_tile_ids at index again if the selected tile id was
+     * Renders the old tile id from m_tileIds at index again if the selected tile id was
      * not set onto that tile.
      * The onTileExited event method is emitted by the Tile object.
      * @param index The position of an individual tile if you were to linearized the level map.
@@ -173,20 +173,20 @@ private:
     void placeAdvancedTiles(int index);
 
     /**
-     * Saves the newly selected tile_id inside LevelScene.
+     * Saves the newly selected tileId inside LevelScene.
      * The onNewTileIdSelected event method is emitted by the TileButton which
      * is part of the TileSelector on the right of the level editor.
-     * @param tile_id The newly selected tile id.
+     * @param tileId The newly selected tile id.
      */
-    void onNewTileIdSelected(uint8_t tile_id) override;
+    void onNewTileIdSelected(uint8_t tileId) override;
 
     /**
-     * Toggles LevelScene's internal m_advanced_tile_placement member.
+     * Toggles LevelScene's internal m_advancedTilePlacement member.
      * This event method is emitted by the Advanced Placement CheckBox in the TopBar.
      */
     void onAdvancedPlacementToggled() override;
     /**
-     * Toggles LevelScene's internal m_symmetric_tile_placement member.
+     * Toggles LevelScene's internal m_symmetricTilePlacement member.
      * This event method is emitted by the Advanced Placement CheckBox in the TopBar.
      */
     void onSymmetryToggled() override;
@@ -210,13 +210,13 @@ private:
     int calcDir(int i, int index);
 
     /**
-     * Places a new QGraphicsPixmapItem using the given tile_id at the given index.
+     * Places a new QGraphicsPixmapItem using the given tileId at the given index.
      * It correclty sets its position and z value (1 -> terrain tile, 2 + index -> building tile)
      * @param index The position of an individual tile if you were to linearized the level map.
-     * @param tile_id The id that corresponds to a type of tile to use.
+     * @param tileId The id that corresponds to a type of tile to use.
      * @return A pointer to the QGraphicsPixmapItem, that was added to the level scene.
      */
-    QGraphicsPixmapItem* occupy_tile(int index, uint8_t tile_id);
+    QGraphicsPixmapItem* occupyTile(int index, uint8_t tileId);
 
     /**
      * The name of the level.
@@ -236,35 +236,35 @@ private:
     /**
      * The tile id of every tile. (linearized representation)
      */
-    std::vector<uint8_t> m_tile_ids;
+    std::vector<uint8_t> m_tileIds;
 
     /**
      * The path from which the LevelScene was loaded (empty if created from scratch).
      */
-    std::string m_file_path;
+    std::string m_filePath;
 
     /**
      * The currently selected tile id. Tells the LevelScene which tiles need to be set
      * if a tile is clicked.
      */
-    uint8_t m_selected_tile_id;
+    uint8_t m_selectedTileId;
 
     /**
      * Activates/deactivates adavanced placement.
      */
-    bool m_advanced_tile_placement;
+    bool m_advancedTilePlacement;
 
     /**
      * Activates/deactivates adavanced placement.
      */
-    bool m_symmetric_tile_placement;
+    bool m_symmetricTilePlacement;
 
     /**
      * Holds pointers to all of the QGraphicsPixmapItems of the top layer. 
      * It holds nullptrs in places at which just the bottom layer is present.
-     * The length of m_tile_occupants is the same as m_tile_ids.
+     * The length of m_tileOccupants is the same as m_tileIds.
      */
-    std::vector<QGraphicsPixmapItem*> m_tile_occupants;
+    std::vector<QGraphicsPixmapItem*> m_tileOccupants;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/SpriteProvider.cpp b/src/editor/SpriteProvider.cpp
index 0287a32..b70cd56 100644
--- a/src/editor/SpriteProvider.cpp
+++ b/src/editor/SpriteProvider.cpp
@@ -41,7 +41,7 @@ void SpriteProvider::initialize(const std::string& path)
  * They are necessary to create the correct path to 
  * the hdf5 dataset that contains the pixels for a given terrain tile.
  */
-const std::vector<std::string> tile_names({"plain",
+const std::vector<std::string> tileNames({"plain",
                                   "water",
                                   "forest",
                                   "mountain",
@@ -77,22 +77,22 @@ const std::vector<std::string> tile_names({"plain",
  * The names can be used to create the path to the hdf5 dataset
  * containing the buildings for a given faction.
  */
-const std::vector<std::string> faction_names(
+const std::vector<std::string> factionNames(
       {"red", "blue", "green", "yellow", "purple", "neutral"});
 
     HighFive::File file(path, HighFive::File::ReadOnly);
     sprites.reserve(60); // we now that we will load 60 sprites
 
     // load terrains
-    for (size_t i = 0; i < TILE_NAMES.size(); i++)
+    for (size_t i = 0; i < tileNames.size(); i++)
     { // size_t?
         std::vector<std::vector<std::vector<uint32_t>>> pixels;
-        file.getDataSet("tiles/" + TILE_NAMES[i]).read(pixels);
+        file.getDataSet("tiles/" + tileNames[i]).read(pixels);
         sprites.push_back(SpriteProvider::loadPixmap(pixels, 0));
     }
 
     // load buildings
-    for (const std::string& factionName : FACTION_NAMES)
+    for (const std::string& factionName : factionNames)
     {
         std::vector<std::vector<std::vector<uint32_t>>> pixels;
         file.getDataSet("buildings/" + factionName).read(pixels);
diff --git a/src/editor/TopBar.cpp b/src/editor/TopBar.cpp
index 018da14..cae08c0 100644
--- a/src/editor/TopBar.cpp
+++ b/src/editor/TopBar.cpp
@@ -12,7 +12,6 @@
 #include <QLabel>
 #include <QSize>
 
-#include "AutomateButton.hpp"
 #include "LevelNameEdit.hpp"
 #include "SaveButton.hpp"
 #include "ZoomInButton.hpp"
@@ -38,21 +37,21 @@ TopBar::TopBar(const std::string& levelName, QWidget* parent) : QToolBar(parent)
     leftLayout->addWidget(textField);
     leftLayout->addStretch();
 
-    QPushButton* save_button = new SaveButton("Speichern", right_container);
-    QPushButton* zoom_in = new ZoomInButton(right_container);
-    QPushButton* zoom_out = new ZoomOutButton(right_container);
-    QPushButton* zoom_info = new ZoomInfo(right_container);
+    QPushButton* saveButton = new SaveButton("Speichern", rightContainer);
+    QPushButton* zoomIn = new ZoomInButton(rightContainer);
+    QPushButton* zoomOut = new ZoomOutButton(rightContainer);
+    QPushButton* zoomInfo = new ZoomInfo(rightContainer);
     AdvancedPlacementSwitch* symmetryBox = new AdvancedPlacementSwitch("symmetrisches Bearbeiten", false, container);
-    left_layout->addWidget(symmetryBox);    //diese Reihenfolge vermeidet einen Bug, bei dem False zu true wird
+    leftLayout->addWidget(symmetryBox);    //diese Reihenfolge vermeidet einen Bug, bei dem False zu true wird
     AdvancedPlacementSwitch* placementBox = new AdvancedPlacementSwitch("Kacheln automatisch setzen", true, container);
-    left_layout->addWidget(placementBox);
-    right_layout->addStretch();
-    right_layout->addWidget(zoom_out);
-    right_layout->addWidget(zoom_info);
-    right_layout->addWidget(zoom_in);
-    right_layout->addStretch();
-    right_layout->addWidget(save_button);
-    right_layout->addStretch();
+    leftLayout->addWidget(placementBox);
+    rightLayout->addStretch();
+    rightLayout->addWidget(zoomOut);
+    rightLayout->addWidget(zoomInfo);
+    rightLayout->addWidget(zoomIn);
+    rightLayout->addStretch();
+    rightLayout->addWidget(saveButton);
+    rightLayout->addStretch();
 
     rightContainer->setFixedWidth(300);
     mainLayout->addWidget(leftContainer, 1);
diff --git a/src/editor/TopBar.hpp b/src/editor/TopBar.hpp
index 51a2a8b..26037ef 100644
--- a/src/editor/TopBar.hpp
+++ b/src/editor/TopBar.hpp
@@ -25,13 +25,13 @@ namespace editor
 class TopBar : public QToolBar {
 public: 
     /**
-     * Creates a TopBar with the provided level_name and parent.
-     * The level_name is needed to prefill the LineEdit in the TopBar with
+     * Creates a TopBar with the provided levelName and parent.
+     * The levelName is needed to prefill the LineEdit in the TopBar with
      * the current level name.
-     * @param level_name The current name of the level.
+     * @param levelName The current name of the level.
      * @param parent The parent to set for the TopBar.
      */
-    TopBar(const std::string& level_name, QWidget *parent = nullptr);
+    TopBar(const std::string& levelName, QWidget *parent = nullptr);
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/main.cpp b/src/editor/main.cpp
index f558cb4..f136dbe 100644
--- a/src/editor/main.cpp
+++ b/src/editor/main.cpp
@@ -35,7 +35,7 @@ using namespace editor;
 struct LevelOptions {
     int width;
     int height;
-    std::string level_filepath;
+    std::string levelFilepath;
 };
 
 /**
@@ -63,7 +63,7 @@ std::optional<LevelOptions> loadLevelOptions(int argc, char* argv[]) {
     QCommandLineParser parser;
 
     // application description with examples for help output of ./editor --help
-    std::string top_section = R"(QT Level Editor for creating/editing Maps of Advanced Wars.
+    std::string topSection = R"(QT Level Editor for creating/editing Maps of Advanced Wars.
 
 Examples:
   ./editor                         Create new level map (default 20x20).
@@ -72,7 +72,7 @@ Examples:
 
     parser.addVersionOption();
     parser.addHelpOption();
-    parser.setApplicationDescription(top_section.c_str());
+    parser.setApplicationDescription(topSection.c_str());
     parser.addOption(QCommandLineOption("width", "The width of the new level map (default 20, minimum: 3).", "number-of-tiles", "20"));
     parser.addOption(QCommandLineOption("height", "The height of the new level map (default 20, minimum: 3).", "number-of-tiles", "20"));
     parser.addOption(QCommandLineOption("edit", "The path to the HDF5 level map file that you want to edit. If edit is not set, a new level map is created.", "filepath"));
@@ -88,22 +88,22 @@ Examples:
 
     // make sure that provided with, height and level file path are valid
     // if yes add them to the level options struct
-    bool width_ok;
-    bool height_ok;
+    bool widthOk;
+    bool heightOk;
     LevelOptions options;
-    options.width = parser.value("width").toUInt(&width_ok);
-    options.height = parser.value("height").toUInt(&height_ok);
-    if (!width_ok || options.width < 3) {
+    options.width = parser.value("width").toUInt(&widthOk);
+    options.height = parser.value("height").toUInt(&heightOk);
+    if (!widthOk || options.width < 3) {
         std::cerr << "You provided an invalid level width: '" << parser.value("width").toStdString() << "'\nThe level width has to be a valid number >= 3." << std::endl;
         return std::nullopt;
     }
-    if (!height_ok || options.height < 3) {
+    if (!heightOk || options.height < 3) {
         std::cerr << "You provided an invalid level height: '" << parser.value("height").toStdString() << "'\nThe level height has to be a valid number >= 3." << std::endl;
         return std::nullopt;
     }
-    options.level_filepath = parser.value("edit").toStdString();
-    if (!options.level_filepath.empty() && !std::filesystem::exists(options.level_filepath)) {
-        std::cerr << "The level map file path: '" << options.level_filepath <<"' does not exist." << std::endl;
+    options.levelFilepath = parser.value("edit").toStdString();
+    if (!options.levelFilepath.empty() && !std::filesystem::exists(options.levelFilepath)) {
+        std::cerr << "The level map file path: '" << options.levelFilepath <<"' does not exist." << std::endl;
         return std::nullopt;
     }
 
@@ -113,8 +113,8 @@ Examples:
 
 int main(int argc, char* argv[])
 {
-    std::optional<LevelOptions> level_options = loadLevelOptions(argc, argv);
-    if (!level_options.has_value()) {
+    std::optional<LevelOptions> levelOptions = loadLevelOptions(argc, argv);
+    if (!levelOptions.has_value()) {
         return 1;
     }
 
@@ -135,17 +135,17 @@ int main(int argc, char* argv[])
 
     // initialize LevelScene
     LevelScene* level;
-    if (!level_options.value().level_filepath.empty()) {
+    if (!levelOptions.value().levelFilepath.empty()) {
         try {
-            level = LevelScene::fromFile(level_options.value().level_filepath);
+            level = LevelScene::fromFile(levelOptions.value().levelFilepath);
         }
         catch (const HighFive::Exception&) {
-            std::cerr << "Loading an existing level map from '" << level_options.value().level_filepath << "' failed.\nPlease make sure that the hdf5 level file is not corrupted." << std::endl;
+            std::cerr << "Loading an existing level map from '" << levelOptions.value().levelFilepath << "' failed.\nPlease make sure that the hdf5 level file is not corrupted." << std::endl;
             return 1;
         }
     }
     else {
-        level = LevelScene::empty("My Level", level_options.value().width, level_options.value().height);
+        level = LevelScene::empty("My Level", levelOptions.value().width, levelOptions.value().height);
     }
 
     // We create the MainWindow on the Stack. Thus it will be destructed 
diff --git a/src/game/level/Level.cpp b/src/game/level/Level.cpp
index 0b0741a..f84f3a0 100644
--- a/src/game/level/Level.cpp
+++ b/src/game/level/Level.cpp
@@ -44,14 +44,14 @@ Level::Level(const std::string& path, Engine& engine)
     m_physicsEngine = std::make_unique<PhysicsEngine>();
     m_combatEngine = std::make_unique<CombatEngine>();
     HighFive::File file(path, HighFive::File::ReadOnly);
-    HighFive::DataSet tilesarray_set = file.getDataSet("tilesarray");
+    HighFive::DataSet tilesarraySet = file.getDataSet("tilesarray");
 
-    std::vector<uint8_t> level_tilesarray;
+    std::vector<uint8_t> levelTilesarray;
 
-    tilesarray_set.getAttribute("width").read(m_width);
-    tilesarray_set.getAttribute("height").read(m_height);
-    tilesarray_set.getAttribute("name").read(m_name);
-    tilesarray_set.read(level_tilesarray); 
+    tilesarraySet.getAttribute("width").read(m_width);
+    tilesarraySet.getAttribute("height").read(m_height);
+    tilesarraySet.getAttribute("name").read(m_name);
+    tilesarraySet.read(levelTilesarray); 
 
     // if level is smaler than 20x20 surround with water tiles
     if (m_width < 20 || m_height < 20)
-- 
GitLab


From e69d91aafe896f5f593bb03e1e39691b02d537e0 Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Mon, 10 Feb 2025 02:01:06 +0100
Subject: [PATCH 22/26] fixed minor mistake

---
 src/editor/LevelScene.cpp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/src/editor/LevelScene.cpp b/src/editor/LevelScene.cpp
index d8ea2b3..196ff93 100644
--- a/src/editor/LevelScene.cpp
+++ b/src/editor/LevelScene.cpp
@@ -386,7 +386,7 @@ void LevelScene::placeCliff(bool placedLand, int index){
 	//Erhalte IDs von den umliegenden 8 Feldern, die kein Kartenrand sind
 	//startet in der mitte Oben, gehe im Uhrzeigersinn
     for(int i=0;i<8;i++){
-	    if(surroundingIDs[i] == -2) surroundingIDs[i] = (int16_t) m_tile_ids[calcDir(i, index)];
+	    if(surroundingIDs[i] == -2) surroundingIDs[i] = (int16_t) m_tileIds[calcDir(i, index)];
     }
 
 	//Ids können nicht lesbare Tiles enthalten, diese Herausfiltern
-- 
GitLab


From 655059b24d495cea20c5507859767a1a804cb2ae Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Mon, 10 Feb 2025 02:04:54 +0100
Subject: [PATCH 23/26] removed old outaded doku

---
 level-spezifikation.md | 36 ------------------------------------
 1 file changed, 36 deletions(-)
 delete mode 100644 level-spezifikation.md

diff --git a/level-spezifikation.md b/level-spezifikation.md
deleted file mode 100644
index 1f087e5..0000000
--- a/level-spezifikation.md
+++ /dev/null
@@ -1,36 +0,0 @@
-# Levelspezifikation
-
-Das Level wird ueber 2 Datasets in der HDF5-Datei repraesentiert.  
-Ein Dataset in XML Format, das die Level Metadaten (Breite, Hoehe, Dataset ID Tiles Array) angibt.  
-Ein weiters Dataset, das letztlich ein array<uint8_t> ist, welches die Levelmap ueber ein Array von Tile IDs definiert.
-
-## 1. XML Dataset mit Level Metadaten
-```xml
-<?xml version="1.0" encoding="ASCII"?>
-<level>
-    <width>20</width> <!-- Breite des Levels -->
-    <height>20</height> <!-- Hoehe des Levels -->
-    <name>Geiles Level<name><!-- Name des Levels -->
-</level>
-```
-
-## 2. Tiles Array
-Das Tiles Array wird als array<uint8_t> in einem Dataset in der HDF5-Datei gespeichert.  
-Die Laenge des Arrays ist Breite X Hoehe (kann man aus XML Leveldefinition entnehmen).  
-Aus den einzelnen Werte in dem Array lassen sich die IDs der entsprechenden Gebaudes/Terrains ableiten.  
-0 - 29 sind Terrain IDs => Zuordnung siehe entsprechendes Enum in Tile.hpp  
-30-49 sind undefiniert  
-50-79  sind Gebaeude IDs:  
-50 => Faction ID 0, Gebaeude ID 0  
-51 => Faction ID 0, Gebaeude ID 1  
-...  
-55 => Faction ID 1, Gebaeude ID 0  
-56 => Faction ID 1, Gebaeude ID 1  
-57 => Faction ID 1, Gebaeude ID 2  
-...  
-Allgemein:  
-Sei t ein Wert im Tiles Array, dann gillt  
-falls t < 30: Terrain ID = t  
-falls t >= 50: Faction ID = (t - 50) / 5   Gebaeude ID = (t - 50) % 5  
-t wird ermittelt mit entweder t = Terrain ID fuer Terrains  
-oder t = 50 + 5*Faction Id + Gebaeude ID fuer Gebaeude
\ No newline at end of file
-- 
GitLab


From a88136c006d79642a7f4603808676b53324fc2cf Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Mon, 10 Feb 2025 02:19:55 +0100
Subject: [PATCH 24/26] formatted level editor

---
 src/editor/AdvancedPlacementSwitch.cpp |  28 +-
 src/editor/AdvancedPlacementSwitch.hpp |  59 +--
 src/editor/EventHandler.cpp            |  10 +-
 src/editor/EventHandler.hpp            |  54 +--
 src/editor/LevelNameEdit.cpp           |  10 +-
 src/editor/LevelNameEdit.hpp           |  43 +-
 src/editor/LevelScene.cpp              | 599 ++++++++++++++-----------
 src/editor/LevelScene.hpp              | 465 +++++++++----------
 src/editor/MainWindow.hpp              |  45 +-
 src/editor/SaveButton.cpp              |   2 +-
 src/editor/SaveButton.hpp              |  47 +-
 src/editor/SpriteProvider.cpp          |  83 ++--
 src/editor/Tile.hpp                    |  81 ++--
 src/editor/TileButton.cpp              |  12 +-
 src/editor/TileButton.hpp              |  53 +--
 src/editor/TileSelector.hpp            | 122 ++---
 src/editor/TopBar.cpp                  |  19 +-
 src/editor/TopBar.hpp                  |  21 +-
 src/editor/ZoomInButton.hpp            |  37 +-
 src/editor/ZoomInfo.hpp                |  20 +-
 src/editor/ZoomOutButton.hpp           |  37 +-
 src/editor/main.cpp                    | 107 +++--
 src/game/level/Level.cpp               |   4 +-
 23 files changed, 1058 insertions(+), 900 deletions(-)

diff --git a/src/editor/AdvancedPlacementSwitch.cpp b/src/editor/AdvancedPlacementSwitch.cpp
index 139a40b..080c9ae 100644
--- a/src/editor/AdvancedPlacementSwitch.cpp
+++ b/src/editor/AdvancedPlacementSwitch.cpp
@@ -1,33 +1,37 @@
 /**
-* AdvancedPlacementSwitch.cpp
-*
-* @date 06.02.2025
-* @author Nils Jonathan Friedrich Eckardt implementation
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) small changes
-*/
+ * AdvancedPlacementSwitch.cpp
+ *
+ * @date 06.02.2025
+ * @author Nils Jonathan Friedrich Eckardt implementation
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) small changes
+ */
 
 #include "AdvancedPlacementSwitch.hpp"
 #include "EventHandler.hpp"
-#include <QMessageBox>
 #include <QEvent>
+#include <QMessageBox>
 
 #include <iostream>
 
 namespace editor
 {
 
-AdvancedPlacementSwitch::AdvancedPlacementSwitch(const QString text, const bool doesPlacement, QWidget* parent) : QCheckBox(text,parent), 
-isPlacement(doesPlacement)
+AdvancedPlacementSwitch::AdvancedPlacementSwitch(
+    const QString text, const bool doesPlacement, QWidget* parent)
+    : QCheckBox(text, parent), isPlacement(doesPlacement)
 {
     setChecked(false);
 }
 
-void AdvancedPlacementSwitch::mousePressEvent(QMouseEvent *event)
+void AdvancedPlacementSwitch::mousePressEvent(QMouseEvent* event)
 {
     QCheckBox::mousePressEvent(event);
-    if(isPlacement){
+    if (isPlacement)
+    {
         EventHandler::send([](EventHandler* e) { e->onAdvancedPlacementToggled(); });
-    } else {
+    }
+    else
+    {
         EventHandler::send([](EventHandler* e) { e->onSymmetryToggled(); });
     }
 }
diff --git a/src/editor/AdvancedPlacementSwitch.hpp b/src/editor/AdvancedPlacementSwitch.hpp
index 98b6d9a..6340927 100644
--- a/src/editor/AdvancedPlacementSwitch.hpp
+++ b/src/editor/AdvancedPlacementSwitch.hpp
@@ -1,16 +1,16 @@
 /**
-* AdvancedPlacementSwitch.hpp
-*
-* @date 06.02.2025
-* @author Nils Jonathan Friedrich Eckardt implementation
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) small changes, doc comments
-*/
+ * AdvancedPlacementSwitch.hpp
+ *
+ * @date 06.02.2025
+ * @author Nils Jonathan Friedrich Eckardt implementation
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) small changes, doc comments
+ */
 
 #pragma once
 
 #include <QCheckBox>
-#include <QString>
 #include <QEvent>
+#include <QString>
 
 namespace editor
 {
@@ -19,27 +19,30 @@ namespace editor
  * The AdvancedPlacementSwitch is displayed in the TopBar and allows the user to switch between
  * regular tile placement and advanced tile placement.
  */
-class AdvancedPlacementSwitch : public QCheckBox {
-public:
-    /**
-     * Creates an AdvancedPlacementSwitch as QCheckBox using the provided text and parent.
-     * @param text The description to display next to the CheckBox.
-     * @param doesPlacement Which of the 2 checkboxes this one is: symetry or placement
-     * @param parent The parent for this widget.
-     */
-    AdvancedPlacementSwitch(const QString text, bool doesPlacement, QWidget *parent = nullptr);
-protected:
-    /**
-     * Receives a QMouseEvent when the QCheckBox is pressed and subsequently emits
-     * the onAdvancedPlacementToggled event method.
-     * @param event The QMouseEvent for the CheckBox Pressing.
-     */
-    void mousePressEvent(QMouseEvent *event) override;
-private:
-    /**
-     * Set at creation, controlls if the switch is used for Placement or Symmetry
-     */
-    bool isPlacement;
+class AdvancedPlacementSwitch : public QCheckBox
+{
+    public:
+        /**
+         * Creates an AdvancedPlacementSwitch as QCheckBox using the provided text and parent.
+         * @param text The description to display next to the CheckBox.
+         * @param doesPlacement Which of the 2 checkboxes this one is: symetry or placement
+         * @param parent The parent for this widget.
+         */
+        AdvancedPlacementSwitch(const QString text, bool doesPlacement, QWidget* parent = nullptr);
+
+    protected:
+        /**
+         * Receives a QMouseEvent when the QCheckBox is pressed and subsequently emits
+         * the onAdvancedPlacementToggled event method.
+         * @param event The QMouseEvent for the CheckBox Pressing.
+         */
+        void mousePressEvent(QMouseEvent* event) override;
+
+    private:
+        /**
+         * Set at creation, controlls if the switch is used for Placement or Symmetry
+         */
+        bool isPlacement;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/EventHandler.cpp b/src/editor/EventHandler.cpp
index ca80bad..0f77e6c 100644
--- a/src/editor/EventHandler.cpp
+++ b/src/editor/EventHandler.cpp
@@ -1,9 +1,9 @@
 /**
-* EventHandler.cpp
-*
-* @date 29.01.2025
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-*/
+ * EventHandler.cpp
+ *
+ * @date 29.01.2025
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
+ */
 
 #include "EventHandler.hpp"
 
diff --git a/src/editor/EventHandler.hpp b/src/editor/EventHandler.hpp
index 54a330c..a95b39e 100644
--- a/src/editor/EventHandler.hpp
+++ b/src/editor/EventHandler.hpp
@@ -1,10 +1,10 @@
 /**
-* EventHandler.hpp
-*
-* @date 29.01.2025
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-* @author Nils Jonathan Friedrich Eckardt onAdvancedPlaement, onSymmetryToggled added
-*/
+ * EventHandler.hpp
+ *
+ * @date 29.01.2025
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
+ * @author Nils Jonathan Friedrich Eckardt onAdvancedPlaement, onSymmetryToggled added
+ */
 
 #pragma once
 
@@ -60,51 +60,51 @@ class EventHandler
          */
         virtual void onLevelNameUpdated(std::string /*newName*/){};
 
-    /**
-     * Overwrite this event method to handle the dispatch of a request to write 
-     * the level to disk by the save button.
-     */
-    virtual void onLevelWriteRequested(){};
+        /**
+         * Overwrite this event method to handle the dispatch of a request to write
+         * the level to disk by the save button.
+         */
+        virtual void onLevelWriteRequested(){};
 
         /**
          * Overwrite this event method to handle the dispatch of a new tile index due
          * to the mouse entering its boundaries.
          * @param index The index of the entered tile.
          */
-        virtual void onTileEntered(int /*index*/) {};
+        virtual void onTileEntered(int /*index*/){};
 
         /**
          * Overwrite this event method to handle the dispatch of a new tile index due
          * to the mouse leaving its boundaries.
          * @param index The index of the exited tile.
          */
-        virtual void onTileExited(int /*index*/) {};
+        virtual void onTileExited(int /*index*/){};
 
         /**
          * Overwrite this event method to handle the dispatch of a new tile index due
          * to the user clicking it.
          * @param index The index of the clicked tile.
          */
-        virtual void onTileClicked(int /*index*/) {};
+        virtual void onTileClicked(int /*index*/){};
 
         /**
          * Overwrite this event method to handle the dispatch of a new tile_id due to
          * the user selecting a different tile type in the TileSelector on the right.
          * @param tile_id Id of the tile to use when an existing tile is clicked on the levelmap.
          */
-        virtual void onNewTileIdSelected(uint8_t /*tileId*/) {};
-
-    /**
-     * Overwrite this event method to handle the change of tile placement method due
-     * to the user toggling advanced palacement on or off.
-     */
-    virtual void onAdvancedPlacementToggled(){};
-
-    /**
-     * Overwrite this event method to handle the change of symmetric tile placement
-     * due to the user toggling map symmetry on or off.
-     */
-    virtual void onSymmetryToggled(){};
+        virtual void onNewTileIdSelected(uint8_t /*tileId*/){};
+
+        /**
+         * Overwrite this event method to handle the change of tile placement method due
+         * to the user toggling advanced palacement on or off.
+         */
+        virtual void onAdvancedPlacementToggled(){};
+
+        /**
+         * Overwrite this event method to handle the change of symmetric tile placement
+         * due to the user toggling map symmetry on or off.
+         */
+        virtual void onSymmetryToggled(){};
 
         /**
          * Overwrite this event method to handle the dispatch of a new delta due to
diff --git a/src/editor/LevelNameEdit.cpp b/src/editor/LevelNameEdit.cpp
index fa9c263..25571a7 100644
--- a/src/editor/LevelNameEdit.cpp
+++ b/src/editor/LevelNameEdit.cpp
@@ -1,9 +1,9 @@
 /**
-* LevelNameEdit.cpp
-*
-* @date 29.01.2025
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-*/
+ * LevelNameEdit.cpp
+ *
+ * @date 29.01.2025
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
+ */
 
 #include "LevelNameEdit.hpp"
 
diff --git a/src/editor/LevelNameEdit.hpp b/src/editor/LevelNameEdit.hpp
index 28b29cf..0758f9b 100644
--- a/src/editor/LevelNameEdit.hpp
+++ b/src/editor/LevelNameEdit.hpp
@@ -1,9 +1,9 @@
 /**
-* LevelNameEdit.hpp
-*
-* @date 29.01.2025
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-*/
+ * LevelNameEdit.hpp
+ *
+ * @date 29.01.2025
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
+ */
 
 #pragma once
 
@@ -16,23 +16,24 @@ namespace editor
  * The LevelNameEdit Widget is displayed on the left of the TopBar.
  * It allows the user to set a custom level name.
  */
-class LevelNameEdit : public QLineEdit {
-public:
-    /**
-     * Creates a LevelNameEdit Widget prefilling the provided level_name.
-     * The parent of the LevelNameEdit Widget is set to the provided parent.
-     * @param levelName The initial name of the level.
-     * @param parent The Widget that should be set as the parent of this Widget.
-     */
-    LevelNameEdit(const std::string& levelName, QWidget* parent = nullptr);
+class LevelNameEdit : public QLineEdit
+{
+    public:
+        /**
+         * Creates a LevelNameEdit Widget prefilling the provided level_name.
+         * The parent of the LevelNameEdit Widget is set to the provided parent.
+         * @param levelName The initial name of the level.
+         * @param parent The Widget that should be set as the parent of this Widget.
+         */
+        LevelNameEdit(const std::string& levelName, QWidget* parent = nullptr);
 
-protected:
-    /**
-     * Receives a QKeyEvent when the user presses a key to change the content of the QLineEdit.
-     * The onLevelNameUpdated event method is subsequently emitted. 
-     * @param event The QKeyEvent for the Key Press.
-     */
-    void keyPressEvent(QKeyEvent* event) override;
+    protected:
+        /**
+         * Receives a QKeyEvent when the user presses a key to change the content of the QLineEdit.
+         * The onLevelNameUpdated event method is subsequently emitted.
+         * @param event The QKeyEvent for the Key Press.
+         */
+        void keyPressEvent(QKeyEvent* event) override;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/LevelScene.cpp b/src/editor/LevelScene.cpp
index 196ff93..a066f28 100644
--- a/src/editor/LevelScene.cpp
+++ b/src/editor/LevelScene.cpp
@@ -1,29 +1,29 @@
 /**
-* LevelScene.cpp
-*
-* @date 28.01.2025
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-* @author Nils Jonathan Friedrich Eckardt implemented symmetry, advanced placement
-*         (onTileClicked, setTile, placeCliff, placeRoad, calcDir)
-*/
+ * LevelScene.cpp
+ *
+ * @date 28.01.2025
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
+ * @author Nils Jonathan Friedrich Eckardt implemented symmetry, advanced placement
+ *         (onTileClicked, setTile, placeCliff, placeRoad, calcDir)
+ */
 
 #include "LevelScene.hpp"
 
-#include <string>
-#include <algorithm>
-#include <iostream>
+#include <QFileDialog>
 #include <QGraphicsPixmapItem>
+#include <QMessageBox>
 #include <QPixmap>
 #include <QPoint>
-#include <QMessageBox>
-#include <QFileDialog>
+#include <algorithm>
 #include <boost/property_tree/ptree.hpp>
 #include <boost/property_tree/xml_parser.hpp>
+#include <iostream>
 #include <stdexcept>
+#include <string>
 
-#include "highfive/H5File.hpp"
 #include "SpriteProvider.hpp"
 #include "Tile.hpp"
+#include "highfive/H5File.hpp"
 
 namespace editor
 {
@@ -37,10 +37,11 @@ LevelScene::LevelScene(
 {
     setSceneRect(0, 0, m_width * 16, m_height * 16); // set dimensions of the QGraphicsScene
 
-    // iterate over all of the level map's tile id and build the two layers 
+    // iterate over all of the level map's tile id and build the two layers
     // bottom layer (static) -> Tile classes (QGraphicsPixmapItem descendants)
     // top layer (dynamic) -> direct QGraphicsPixmapItems (also stored in m_tile_occupants)
-    m_tileOccupants = {}; // holds QGraphicsPixmapItems of top layer (nullptr if top pximap item not needed)
+    m_tileOccupants =
+        {}; // holds QGraphicsPixmapItems of top layer (nullptr if top pximap item not needed)
     m_tileOccupants.reserve(tile_ids.size()); // size will be same as tile ids array at the end
     for (size_t index = 0; index < tile_ids.size(); index++)
     {
@@ -68,42 +69,46 @@ LevelScene::LevelScene(
 LevelScene* LevelScene::empty(const std::string& name, int width, int height, QWidget* parent)
 {
     std::vector<uint8_t> tile_ids;
-    tile_ids.reserve(width*height);
+    tile_ids.reserve(width * height);
 
     // create top row with cliffs
-    tile_ids.push_back(22); // cliff corner top left 
-    for (int i = 0; i < width - 2; i++) {
+    tile_ids.push_back(22); // cliff corner top left
+    for (int i = 0; i < width - 2; i++)
+    {
         tile_ids.push_back(19); // cliff bottom
     }
-    tile_ids.push_back(23); // cliff corner top right 
+    tile_ids.push_back(23); // cliff corner top right
 
     // create main rows with cliff at start and end grass in the middle
-    for (int i = 0; i < height - 2; i++) {
+    for (int i = 0; i < height - 2; i++)
+    {
         tile_ids.push_back(21); // cliff right
-        for (int j = 0; j < width - 2; j++) {
+        for (int j = 0; j < width - 2; j++)
+        {
             tile_ids.push_back(0); // pleins
         }
         tile_ids.push_back(20); // cliff left
     }
 
     // create bottom row with cliffs
-    tile_ids.push_back(24); // cliff corner bottom left 
-    for (int i = 0; i < width - 2; i++) {
+    tile_ids.push_back(24); // cliff corner bottom left
+    for (int i = 0; i < width - 2; i++)
+    {
         tile_ids.push_back(18); // cliff top
     }
-    tile_ids.push_back(25); // cliff corner bottom right 
+    tile_ids.push_back(25); // cliff corner bottom right
 
     return new LevelScene(name, width, height, tile_ids, "", parent);
 }
 
 LevelScene* LevelScene::fromFile(const std::string& file_path, QWidget* parent)
 {
-    HighFive::File file(file_path, HighFive::File::ReadOnly);
+    HighFive::File    file(file_path, HighFive::File::ReadOnly);
     HighFive::DataSet tilesarray_set = file.getDataSet("tilesarray");
 
-    int width;
-    int height;
-    std::string name;
+    int                  width;
+    int                  height;
+    std::string          name;
     std::vector<uint8_t> level_tilesarray;
 
     tilesarray_set.getAttribute("width").read(width);
@@ -131,15 +136,13 @@ int LevelScene::getHeight()
 
 bool LevelScene::isBorder(int index)
 {
-    return (index / m_width) == 0 
-    || (index / m_width) == (m_height -1)
-    || (index % m_width) == 0 
-    || (index % m_width) == (m_width - 1);
+    return (index / m_width) == 0 || (index / m_width) == (m_height - 1) ||
+           (index % m_width) == 0 || (index % m_width) == (m_width - 1);
 }
 
 bool LevelScene::isWaterTile(uint8_t id)
 {
-    if (id == 1) 
+    if (id == 1)
     {
         return true;
     }
@@ -157,7 +160,8 @@ void LevelScene::onLevelNameUpdated(std::string new_name)
 
 void LevelScene::onLevelWriteRequested()
 {
-    if (m_filePath.empty()) {
+    if (m_filePath.empty())
+    {
         // create a nice file name from the levelname
         // it will be displayed in the file save dialog
         std::string filepath = m_name;
@@ -166,24 +170,35 @@ void LevelScene::onLevelWriteRequested()
         filepath = "/" + filepath + ".h5";
 
         // get path at which the level should be written to
-        m_filePath = QFileDialog::getSaveFileName(
-            (QWidget*) parent(), "Level Speichern", QDir::currentPath() + QString(filepath.c_str()), "HDF5 Files (*.h5 *.hdf5)").toStdString();
+        m_filePath =
+            QFileDialog::getSaveFileName(
+                (QWidget*)parent(), "Level Speichern",
+                QDir::currentPath() + QString(filepath.c_str()), "HDF5 Files (*.h5 *.hdf5)")
+                .toStdString();
     }
-    if (m_filePath.empty()) {
+    if (m_filePath.empty())
+    {
         return; // if still empty dialog was canceled
     }
 
     // write level to hdf5 file
-    try {
-        HighFive::File file(m_filePath, HighFive::File::Overwrite);
-        HighFive::DataSet tilesarray_set = file.createDataSet<std::vector<uint8_t>>("tilesarray", m_tileIds);
+    try
+    {
+        HighFive::File    file(m_filePath, HighFive::File::Overwrite);
+        HighFive::DataSet tilesarray_set =
+            file.createDataSet<std::vector<uint8_t>>("tilesarray", m_tileIds);
         tilesarray_set.write(m_tileIds);
         tilesarray_set.createAttribute<int>("width", m_width).write(m_width);
         tilesarray_set.createAttribute<int>("height", m_height).write(m_height);
         tilesarray_set.createAttribute<std::string>("name", m_name).write(m_name);
-        QMessageBox::information((QWidget*) parent(), "Saved", "Level map saved successfully.");
-    } catch (const HighFive::Exception& e) {
-        QMessageBox::critical((QWidget*) parent(), "Save failed", "Saving the level map failed.\nPlease make sure that you have write permissions for the selected path.");
+        QMessageBox::information((QWidget*)parent(), "Saved", "Level map saved successfully.");
+    }
+    catch (const HighFive::Exception& e)
+    {
+        QMessageBox::critical(
+            (QWidget*)parent(), "Save failed",
+            "Saving the level map failed.\nPlease make sure that you have write permissions for "
+            "the selected path.");
         throw e;
     }
 }
@@ -221,11 +236,10 @@ void LevelScene::onTileExited(int index)
     {
         removeItem(m_tileOccupants[index]);
         // Interestingly QGraphicsScene does take ownership of the QGraphicsPixmapItems that
-        // are added to it, but inside removeItem it gives that ownership back without destroying it.
-        // I first assumed that removeItem would also destroy the Pixmap Items, but valgrind taught me 
-        // otherwise. :)
-        // So therefore we delete it explicitly. That is probably the only place in the entire application
-        // where we explicitly free memory.
+        // are added to it, but inside removeItem it gives that ownership back without destroying
+        // it. I first assumed that removeItem would also destroy the Pixmap Items, but valgrind
+        // taught me otherwise. :) So therefore we delete it explicitly. That is probably the only
+        // place in the entire application where we explicitly free memory.
         delete m_tileOccupants[index];
         m_tileOccupants[index] = nullptr;
     }
@@ -237,7 +251,7 @@ void LevelScene::onTileExited(int index)
 
 void LevelScene::setTile(int index, uint8_t id)
 {
-    m_tileIds[index]=id;
+    m_tileIds[index] = id;
     if (m_tileOccupants[index] != nullptr)
     {
         removeItem(m_tileOccupants[index]);
@@ -247,58 +261,72 @@ void LevelScene::setTile(int index, uint8_t id)
     if (m_tileIds[index] > 0)
     {
         m_tileOccupants[index] = occupyTile(index, id);
-    } 
+    }
 }
 
 void LevelScene::onTileClicked(int index)
 {
-	if (isBorder(index) && !isWaterTile(m_selectedTileId)) {
-		return;                             //no Placement allowed
-	}
+    if (isBorder(index) && !isWaterTile(m_selectedTileId))
+    {
+        return; // no Placement allowed
+    }
 
-    m_tileIds[index]=m_selectedTileId;   //normal Placement
+    m_tileIds[index] = m_selectedTileId; // normal Placement
 
-	if (m_advancedTilePlacement) {
-        placeAdvancedTiles(index);          //advanced Placement
-	}
+    if (m_advancedTilePlacement)
+    {
+        placeAdvancedTiles(index); // advanced Placement
+    }
 
-    if(!m_symmetricTilePlacement) return;
+    if (!m_symmetricTilePlacement)
+        return;
 
     uint8_t id = m_selectedTileId;
-    index = m_width * m_height - 1 -index;
-    int swapID[22] ={11,10,9,8,12,16,15,14,13,17,19,18,21,20,25,24,23,22,29,28,27,26};
-    if(id > 7 && id < 30) id = swapID[ id-8 ];
-    if(id > 49 && id < 55) id += 5;  
-    else if(id > 54 && id < 60) id -= 5;  
-
-    setTile(index,m_selectedTileId);  //symmetric Placement
-
-    if (m_advancedTilePlacement) {
-        placeAdvancedTiles(index);      //symmetric advanced Placement
+    index = m_width * m_height - 1 - index;
+    int swapID[22] = {11, 10, 9,  8,  12, 16, 15, 14, 13, 17, 19,
+                      18, 21, 20, 25, 24, 23, 22, 29, 28, 27, 26};
+    if (id > 7 && id < 30)
+        id = swapID[id - 8];
+    if (id > 49 && id < 55)
+        id += 5;
+    else if (id > 54 && id < 60)
+        id -= 5;
+
+    setTile(index, m_selectedTileId); // symmetric Placement
+
+    if (m_advancedTilePlacement)
+    {
+        placeAdvancedTiles(index); // symmetric advanced Placement
     }
 }
 
 void LevelScene::placeAdvancedTiles(int index)
 {
-    if(m_selectedTileId > 5 && m_selectedTileId < 17){	//Straße plaziert
-		placeRoad(index, true);
-		return;
-	}
-	if((m_selectedTileId > 16 && m_selectedTileId < 30) || m_selectedTileId == 1){	//Wasser plaziert
-		if(m_selectedTileId == 17){
-			setTile(index,17);
-		} else {
-			setTile(index,1);
-		}
-		placeCliff(false, index);
-		return;
-	}
-	if(m_selectedTileId == 0 || m_selectedTileId == 2 || m_selectedTileId == 3){	//Land plaziert
-		setTile(index,m_selectedTileId);
-		placeCliff(true, index);
-		return;
-	}
-    setTile(index, m_selectedTileId);     //Gebäude plaziert
+    if (m_selectedTileId > 5 && m_selectedTileId < 17)
+    { // Straße plaziert
+        placeRoad(index, true);
+        return;
+    }
+    if ((m_selectedTileId > 16 && m_selectedTileId < 30) || m_selectedTileId == 1)
+    { // Wasser plaziert
+        if (m_selectedTileId == 17)
+        {
+            setTile(index, 17);
+        }
+        else
+        {
+            setTile(index, 1);
+        }
+        placeCliff(false, index);
+        return;
+    }
+    if (m_selectedTileId == 0 || m_selectedTileId == 2 || m_selectedTileId == 3)
+    { // Land plaziert
+        setTile(index, m_selectedTileId);
+        placeCliff(true, index);
+        return;
+    }
+    setTile(index, m_selectedTileId); // Gebäude plaziert
 }
 
 void LevelScene::onNewTileIdSelected(uint8_t tile_id)
@@ -322,18 +350,20 @@ QGraphicsPixmapItem* LevelScene::occupyTile(int index, uint8_t tile_id)
     int                  y = (index / m_width) * 16;
     QPixmap              tile_occupant = SpriteProvider::getSprite(tile_id);
     QGraphicsPixmapItem* tile_occupant_item = addPixmap(tile_occupant);
-    bool is_building_tile = tile_id >= 50;
+    bool                 is_building_tile = tile_id >= 50;
     tile_occupant_item->setZValue(is_building_tile ? 2 + index : 1);
     tile_occupant_item->setPos(x, is_building_tile ? y - 16 : y);
     return tile_occupant_item;
 }
 
-void LevelScene::placeCliff(bool placedLand, int index){
-	const int16_t IdToSum[12] = {12,3,9,6,2,1,4,8,13,14,11,7};
-	const int16_t SumToId[16] = {1,23,22,19,24,24,21,29,25,20,25,28,18,26,27,0};
+void LevelScene::placeCliff(bool placedLand, int index)
+{
+    const int16_t IdToSum[12] = {12, 3, 9, 6, 2, 1, 4, 8, 13, 14, 11, 7};
+    const int16_t SumToId[16] = {1, 23, 22, 19, 24, 24, 21, 29, 25, 20, 25, 28, 18, 26, 27, 0};
 
-	int16_t surroundingIDs[8] = {-2,-2,-2,-2,-2,-2,-2,-2};	//-2 = uninitialisiert, -1 = kartenrand
-	bool marchingSquares[8][4] = {false};
+    int16_t surroundingIDs[8] = {-2, -2, -2, -2,
+                                 -2, -2, -2, -2}; //-2 = uninitialisiert, -1 = kartenrand
+    bool    marchingSquares[8][4] = {false};
 
     /*
         FUNKTIONSWEISE:
@@ -344,9 +374,9 @@ void LevelScene::placeCliff(bool placedLand, int index){
         2. Die geladenen Ids müssen gefiltert werden. Nicht alle IDs sind direkt verwendbar.
         Riffe, Wälder und Gebirge werden als Land oder Wasser angesehen. Straßen und Gebäude
         werden als Land behandelt. (dies kann einfach geändert werden, indem man diese auf -1
-        setzt). 
+        setzt).
         3. Die IDs werden remapped. Die Tiles haben die IDs 1,18-29. Um sie sich nutzbar machen
-        zu können müssen diese in 0-15 gemapped werden. Auf diese Weise kann aus einer ID ein 
+        zu können müssen diese in 0-15 gemapped werden. Auf diese Weise kann aus einer ID ein
         tile und umgekehrt berechnet werden.
         4. Berechnung der neuen IDs Der Ansatz der Berechnung ist vom Marching Cubes Algorithmus
         (hier 2D als Marching Squares) abgeleitet. Darin ist jede Ecke eines Tiles entweder Innen
@@ -361,118 +391,152 @@ void LevelScene::placeCliff(bool placedLand, int index){
         wurden auch nicht verändert werden.
     */
 
-	//Überprüfe Kartenränder, setze diese auf -1
-	if(index < m_width){					//oberer Kartenrand
-		surroundingIDs[7] = -1;
-		surroundingIDs[0] = -1;
-		surroundingIDs[1] = -1;
-	}
-	if((index + 1) % m_width == 0){			//rechter Kartenrand
-		surroundingIDs[1] = -1;
-		surroundingIDs[2] = -1;
-		surroundingIDs[3] = -1;
-	}
-	if(index >= m_width * (m_height - 1)){	//unterer Kartenrand
-		surroundingIDs[3] = -1;
-		surroundingIDs[4] = -1;
-		surroundingIDs[5] = -1;
-	}
-	if(index % m_width == 0){				//linker Kartenrand
-		surroundingIDs[5] = -1;
-		surroundingIDs[6] = -1;
-		surroundingIDs[7] = -1;
-	}
-
-	//Erhalte IDs von den umliegenden 8 Feldern, die kein Kartenrand sind
-	//startet in der mitte Oben, gehe im Uhrzeigersinn
-    for(int i=0;i<8;i++){
-	    if(surroundingIDs[i] == -2) surroundingIDs[i] = (int16_t) m_tileIds[calcDir(i, index)];
-    }
-
-	//Ids können nicht lesbare Tiles enthalten, diese Herausfiltern
-	for(int i = 0; i < 8; i++){                            //1 = Wasser, 0 = Land, -1 = unverändert
-		if(surroundingIDs[i] == 17)                          surroundingIDs[i] = 1;		//Riff als Wasser angesehen
-		if(surroundingIDs[i] == 2 || surroundingIDs[i] == 3) surroundingIDs[i] = 0;		//Wald, Gebirge als Land angesehen
-		if(surroundingIDs[i] > 3 && surroundingIDs[i] < 17)  surroundingIDs[i] = 0;     //Straßen werden als Land angesehen
-		if(surroundingIDs[i] > 29)                           surroundingIDs[i] = 0;	    //Gebäude werden als Land angesehen
-	}
-
-	//ID remapping um damit arbeiten zu können
-	for(int i = 0; i < 8; i++){
-        if(surroundingIDs[i] == -1){
-        } else if(surroundingIDs[i] == 0){
-			surroundingIDs[i] = 15;
-		} else if(surroundingIDs[i] == 1){
-			surroundingIDs[i] = 0;
-		} else{
-			surroundingIDs[i]= IdToSum[surroundingIDs[i] - 18];
-		}
-	}
-	
-	//Berechne Marching Squares aus der remapped Id
-	for(int i = 0; i < 8; i++){
-		if(surroundingIDs[i] / 8 == 1){
-			marchingSquares[i][0] = true;	//top left
-			surroundingIDs[i] -= 8;
-		}
-		if(surroundingIDs[i] / 4 == 1){
-			marchingSquares[i][1] = true;	//top right
-			surroundingIDs[i] -= 4;
-		}
-		if(surroundingIDs[i] / 2 == 1){
-			marchingSquares[i][2] = true;	//bottom right
-			surroundingIDs[i] -= 2;
-		}
-		if(surroundingIDs[i] == 1){
-			marchingSquares[i][3] = true;	//bottom left
-		}
-	}
-	
-	//Einfügen/Abziehen des Landes
-	marchingSquares[0][2] = placedLand;	//oben
-	marchingSquares[0][3] = placedLand;
-	marchingSquares[1][3] = placedLand;	//oben rechts
-	marchingSquares[2][3] = placedLand;	//rechts
-	marchingSquares[2][0] = placedLand;
-	marchingSquares[3][0] = placedLand;	//untern rechts
-	marchingSquares[4][0] = placedLand;	//unten
-	marchingSquares[4][1] = placedLand;
-	marchingSquares[5][1] = placedLand;	//unten links
-	marchingSquares[6][1] = placedLand;	//links
-	marchingSquares[6][2] = placedLand;
-	marchingSquares[7][2] = placedLand;	//oben links
-	
-	//Berechne remapped ID aus Marching Squares
-	for(int i = 0; i < 8; i++){
-		if(surroundingIDs[i] > -1){
+    //Überprüfe Kartenränder, setze diese auf -1
+    if (index < m_width)
+    { // oberer Kartenrand
+        surroundingIDs[7] = -1;
+        surroundingIDs[0] = -1;
+        surroundingIDs[1] = -1;
+    }
+    if ((index + 1) % m_width == 0)
+    { // rechter Kartenrand
+        surroundingIDs[1] = -1;
+        surroundingIDs[2] = -1;
+        surroundingIDs[3] = -1;
+    }
+    if (index >= m_width * (m_height - 1))
+    { // unterer Kartenrand
+        surroundingIDs[3] = -1;
+        surroundingIDs[4] = -1;
+        surroundingIDs[5] = -1;
+    }
+    if (index % m_width == 0)
+    { // linker Kartenrand
+        surroundingIDs[5] = -1;
+        surroundingIDs[6] = -1;
+        surroundingIDs[7] = -1;
+    }
+
+    // Erhalte IDs von den umliegenden 8 Feldern, die kein Kartenrand sind
+    // startet in der mitte Oben, gehe im Uhrzeigersinn
+    for (int i = 0; i < 8; i++)
+    {
+        if (surroundingIDs[i] == -2)
+            surroundingIDs[i] = (int16_t)m_tileIds[calcDir(i, index)];
+    }
+
+    // Ids können nicht lesbare Tiles enthalten, diese Herausfiltern
+    for (int i = 0; i < 8; i++)
+    { // 1 = Wasser, 0 = Land, -1 = unverändert
+        if (surroundingIDs[i] == 17)
+            surroundingIDs[i] = 1; // Riff als Wasser angesehen
+        if (surroundingIDs[i] == 2 || surroundingIDs[i] == 3)
+            surroundingIDs[i] = 0; // Wald, Gebirge als Land angesehen
+        if (surroundingIDs[i] > 3 && surroundingIDs[i] < 17)
+            surroundingIDs[i] = 0; // Straßen werden als Land angesehen
+        if (surroundingIDs[i] > 29)
+            surroundingIDs[i] = 0; // Gebäude werden als Land angesehen
+    }
+
+    // ID remapping um damit arbeiten zu können
+    for (int i = 0; i < 8; i++)
+    {
+        if (surroundingIDs[i] == -1)
+        {
+        }
+        else if (surroundingIDs[i] == 0)
+        {
+            surroundingIDs[i] = 15;
+        }
+        else if (surroundingIDs[i] == 1)
+        {
             surroundingIDs[i] = 0;
-		    if(marchingSquares[i][0]) surroundingIDs[i] += 8;
-	    	if(marchingSquares[i][1]) surroundingIDs[i] += 4;
-		    if(marchingSquares[i][2]) surroundingIDs[i] += 2;
-    		if(marchingSquares[i][3]) surroundingIDs[i] += 1;
+        }
+        else
+        {
+            surroundingIDs[i] = IdToSum[surroundingIDs[i] - 18];
         }
     }
-	
-	//Remappe ID für setzbare Tiles
-	for(int i = 0; i < 8; i++){
-		if(surroundingIDs[i] > -1) surroundingIDs[i] = SumToId[ surroundingIDs[i] ];
-	}
-	
-	//Plaziere Tiles
-    for(int i = 0; i < 8; i++){
-	    if(isntIdentical(surroundingIDs[i], calcDir(i, index)))
-            setTile( calcDir(i, index),(uint8_t)surroundingIDs[i] );
+
+    // Berechne Marching Squares aus der remapped Id
+    for (int i = 0; i < 8; i++)
+    {
+        if (surroundingIDs[i] / 8 == 1)
+        {
+            marchingSquares[i][0] = true; // top left
+            surroundingIDs[i] -= 8;
+        }
+        if (surroundingIDs[i] / 4 == 1)
+        {
+            marchingSquares[i][1] = true; // top right
+            surroundingIDs[i] -= 4;
+        }
+        if (surroundingIDs[i] / 2 == 1)
+        {
+            marchingSquares[i][2] = true; // bottom right
+            surroundingIDs[i] -= 2;
+        }
+        if (surroundingIDs[i] == 1)
+        {
+            marchingSquares[i][3] = true; // bottom left
+        }
+    }
+
+    // Einfügen/Abziehen des Landes
+    marchingSquares[0][2] = placedLand; // oben
+    marchingSquares[0][3] = placedLand;
+    marchingSquares[1][3] = placedLand; // oben rechts
+    marchingSquares[2][3] = placedLand; // rechts
+    marchingSquares[2][0] = placedLand;
+    marchingSquares[3][0] = placedLand; // untern rechts
+    marchingSquares[4][0] = placedLand; // unten
+    marchingSquares[4][1] = placedLand;
+    marchingSquares[5][1] = placedLand; // unten links
+    marchingSquares[6][1] = placedLand; // links
+    marchingSquares[6][2] = placedLand;
+    marchingSquares[7][2] = placedLand; // oben links
+
+    // Berechne remapped ID aus Marching Squares
+    for (int i = 0; i < 8; i++)
+    {
+        if (surroundingIDs[i] > -1)
+        {
+            surroundingIDs[i] = 0;
+            if (marchingSquares[i][0])
+                surroundingIDs[i] += 8;
+            if (marchingSquares[i][1])
+                surroundingIDs[i] += 4;
+            if (marchingSquares[i][2])
+                surroundingIDs[i] += 2;
+            if (marchingSquares[i][3])
+                surroundingIDs[i] += 1;
+        }
+    }
+
+    // Remappe ID für setzbare Tiles
+    for (int i = 0; i < 8; i++)
+    {
+        if (surroundingIDs[i] > -1)
+            surroundingIDs[i] = SumToId[surroundingIDs[i]];
+    }
+
+    // Plaziere Tiles
+    for (int i = 0; i < 8; i++)
+    {
+        if (isntIdentical(surroundingIDs[i], calcDir(i, index)))
+            setTile(calcDir(i, index), (uint8_t)surroundingIDs[i]);
     }
 }
 
-void LevelScene::placeRoad(int index, bool updateFlag){
-	//const int16_t IdToSum[] = {5,10,13,14,11,7,15,6,3,12,9};
-	const uint8_t SumToId[] = {6,6,7,14,6,6,13,11,7,16,7,10,15,8,9,12};
-	
-	bool tileDirections[] = {false,false,false,false};
-	int16_t surroundingIDs[] = {-1,-1,-1,-1};		//-1 = kartenrand oder keine strasse
-	uint8_t placedID = 0;
-	
+void LevelScene::placeRoad(int index, bool updateFlag)
+{
+    // const int16_t IdToSum[] = {5,10,13,14,11,7,15,6,3,12,9};
+    const uint8_t SumToId[] = {6, 6, 7, 14, 6, 6, 13, 11, 7, 16, 7, 10, 15, 8, 9, 12};
+
+    bool    tileDirections[] = {false, false, false, false};
+    int16_t surroundingIDs[] = {-1, -1, -1, -1}; //-1 = kartenrand oder keine strasse
+    uint8_t placedID = 0;
+
     /*
         FUNKTIONSWEISE:
         1. Laden der umliegenden 4 tile IDs falls diese nicht im Kartenrand stecken.
@@ -485,65 +549,96 @@ void LevelScene::placeRoad(int index, bool updateFlag){
         Straßen, die in weniger als 2 Richtungen zeigen gibt es nicht. Die Textur der Kreuzung,
         die in alle 4 Richtungen zeigt ist falsch und zeigt nicht nach unten.
         6. Setzen des neu berechneten Tiles. Im Anschluss wird die selbe Funktion für die
-        umliegenden 4 Tiles aufgerufen, falls diese Straßen beinhalten. 
+        umliegenden 4 Tiles aufgerufen, falls diese Straßen beinhalten.
     */
 
-	//Erhalte IDs der umliegenden Felder - im Uhrzeigersinn, start: oben
-	//Vorgehen: überprüfe, ob die obere Zelle im Kartenrand ist. Wenn nicht erhalte index der oberen Zelle
-	if(!(index < m_width))                surroundingIDs[0] = (int16_t) m_tileIds[index - m_width];
-	if(!((index + 1) % m_width == 0))     surroundingIDs[1] = (int16_t) m_tileIds[index + 1];
-	if(!(index > m_width * (m_height-1))) surroundingIDs[2] = (int16_t) m_tileIds[index + m_width];
-	if(!(index % m_width == 0))           surroundingIDs[3] = (int16_t) m_tileIds[index - 1];
-	
-	//Filtern der IDs, die keine Straßen sind
-	for(int i = 0; i < 4; i++){
-		if(surroundingIDs[i] < 4 || surroundingIDs[i] > 16) surroundingIDs[i] = -1;
-	}
-
-	//Berechne in welche Richtungen das neue Tile Zeigt
-	for(int i = 0; i < 4; i++){
-		if(surroundingIDs[i] > -1) tileDirections[i] = true;
-	}
-	
-	//Berechne die Remapped ID
-	placedID = 0;
-	if(tileDirections[0]) placedID += 8;
-	if(tileDirections[1]) placedID += 4;
-	if(tileDirections[2]) placedID += 2;
-	if(tileDirections[3]) placedID += 1;
-	
-	if(placedID == 0) updateFlag = false; 	//Umliegende Tiles müssen nicht geupdated werden, da keine Strassen
-	placedID = SumToId[placedID];			//Berechnete Summe in Valide ID umformen
-	setTile(index, placedID);	            //Tile setzen
-	
-	//Update umliegende Tiles
-	if(updateFlag){	
-		if(tileDirections[0]) placeRoad((index - m_width), false);	//update oben
-		if(tileDirections[1]) placeRoad((index + 1),       false);	//update rechts
-		if(tileDirections[2]) placeRoad((index + m_width), false);	//update unten
-		if(tileDirections[3]) placeRoad((index - 1),       false);	//update links
-	}
+    // Erhalte IDs der umliegenden Felder - im Uhrzeigersinn, start: oben
+    // Vorgehen: überprüfe, ob die obere Zelle im Kartenrand ist. Wenn nicht erhalte index der
+    // oberen Zelle
+    if (!(index < m_width))
+        surroundingIDs[0] = (int16_t)m_tileIds[index - m_width];
+    if (!((index + 1) % m_width == 0))
+        surroundingIDs[1] = (int16_t)m_tileIds[index + 1];
+    if (!(index > m_width * (m_height - 1)))
+        surroundingIDs[2] = (int16_t)m_tileIds[index + m_width];
+    if (!(index % m_width == 0))
+        surroundingIDs[3] = (int16_t)m_tileIds[index - 1];
+
+    // Filtern der IDs, die keine Straßen sind
+    for (int i = 0; i < 4; i++)
+    {
+        if (surroundingIDs[i] < 4 || surroundingIDs[i] > 16)
+            surroundingIDs[i] = -1;
+    }
+
+    // Berechne in welche Richtungen das neue Tile Zeigt
+    for (int i = 0; i < 4; i++)
+    {
+        if (surroundingIDs[i] > -1)
+            tileDirections[i] = true;
+    }
+
+    // Berechne die Remapped ID
+    placedID = 0;
+    if (tileDirections[0])
+        placedID += 8;
+    if (tileDirections[1])
+        placedID += 4;
+    if (tileDirections[2])
+        placedID += 2;
+    if (tileDirections[3])
+        placedID += 1;
+
+    if (placedID == 0)
+        updateFlag = false; // Umliegende Tiles müssen nicht geupdated werden, da keine Strassen
+    placedID = SumToId[placedID]; // Berechnete Summe in Valide ID umformen
+    setTile(index, placedID);     // Tile setzen
+
+    // Update umliegende Tiles
+    if (updateFlag)
+    {
+        if (tileDirections[0])
+            placeRoad((index - m_width), false); // update oben
+        if (tileDirections[1])
+            placeRoad((index + 1), false); // update rechts
+        if (tileDirections[2])
+            placeRoad((index + m_width), false); // update unten
+        if (tileDirections[3])
+            placeRoad((index - 1), false); // update links
+    }
 }
 
-int LevelScene::calcDir(int i, int index){
-    switch(i){
-        case(0): return (index - m_width);
-        case(1): return (index - m_width + 1);
-        case(2): return (index + 1);
-        case(3): return (index + m_width + 1);
-        case(4): return (index + m_width);
-        case(5): return (index + m_width - 1);
-        case(6): return (index - 1);
-        case(7): return (index - m_width - 1);
+int LevelScene::calcDir(int i, int index)
+{
+    switch (i)
+    {
+    case (0):
+        return (index - m_width);
+    case (1):
+        return (index - m_width + 1);
+    case (2):
+        return (index + 1);
+    case (3):
+        return (index + m_width + 1);
+    case (4):
+        return (index + m_width);
+    case (5):
+        return (index + m_width - 1);
+    case (6):
+        return (index - 1);
+    case (7):
+        return (index - m_width - 1);
     }
     throw std::invalid_argument("i has to be 0 <= i <= 7");
 }
 
-bool LevelScene::isntIdentical(int16_t id, int index){
-    bool flag  = (!(id == -1 ||               //kartenrand
-    (id == 0 && m_tileIds[index]==2) ||   //wald
-    (id == 0 && m_tileIds[index]==3) ||   //gebirge
-    (id == 1 && m_tileIds[index]==17)) );  //riff
+bool LevelScene::isntIdentical(int16_t id, int index)
+{
+    bool flag =
+        (!(id == -1 ||                            // kartenrand
+           (id == 0 && m_tileIds[index] == 2) ||  // wald
+           (id == 0 && m_tileIds[index] == 3) ||  // gebirge
+           (id == 1 && m_tileIds[index] == 17))); // riff
     return flag;
 }
 
diff --git a/src/editor/LevelScene.hpp b/src/editor/LevelScene.hpp
index 8e79abe..a466a9d 100644
--- a/src/editor/LevelScene.hpp
+++ b/src/editor/LevelScene.hpp
@@ -1,17 +1,17 @@
 /**
-* LevelScene.hpp
-*
-* @date 28.01.2025
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-* @author Nils Jonathan Friedrich Eckardt implementing symmetry, advanced placement
-*         (and onTileClicked, setTile, placeCliff, placeRoad, calcDir)
-*/
+ * LevelScene.hpp
+ *
+ * @date 28.01.2025
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
+ * @author Nils Jonathan Friedrich Eckardt implementing symmetry, advanced placement
+ *         (and onTileClicked, setTile, placeCliff, placeRoad, calcDir)
+ */
 
 #pragma once
 
+#include <QGraphicsPixmapItem>
 #include <QGraphicsRectItem>
 #include <QGraphicsScene>
-#include <QGraphicsPixmapItem>
 
 #include "EventHandler.hpp"
 
@@ -19,17 +19,17 @@ namespace editor
 {
 
 /**
- * The LevelScene is a Container for all of the individual tiles (QGraphicsPixmapItems) 
+ * The LevelScene is a Container for all of the individual tiles (QGraphicsPixmapItems)
  * of the level map.
  * LevelScene is responsible for rendering/updating the map on user actions.
- * It also privdes the static factory methods empty, fromFile for creating empty level maps, 
+ * It also privdes the static factory methods empty, fromFile for creating empty level maps,
  * laoding a level map from a hdf5 file.
- * 
+ *
  * LevelScene inherits from EventHandler overwriting many event methods:
- * - onLevelNameUpdated 
+ * - onLevelNameUpdated
  *   To keep the current level name for when the level map should be saved.
- * - onLevelWriteRequested 
- *   To write the level map to a hdf5 file when the save button is pressed. 
+ * - onLevelWriteRequested
+ *   To write the level map to a hdf5 file when the save button is pressed.
  * - onTileEntered
  *   To render the currently selected tile from the tile selector on the entered tile.
  * - onTileExited
@@ -40,12 +40,12 @@ namespace editor
  *   To update the currently selected tile id.
  * - onAdvancedPlacmentToggled
  *   To toggle advanced placement on or off.
- * 
+ *
  * How does the rendering work?
- * LevelScene implements a two layer approach. 
+ * LevelScene implements a two layer approach.
  * The bottom layer is static. It is created out of Tile (Tile.cpp) objects. These Tile objects
  * inherit from QGraphicsPixmapItems to override onmouse enter, exit and press.
- * LevelScene receives those events in onTileEntered, onTileExited, onTileClicked. 
+ * LevelScene receives those events in onTileEntered, onTileExited, onTileClicked.
  * The bottom layer is only grass and water cliffs on the borders.
  * The bottom layer always gets a z value of 0.
  * For non grass tile ids, QGraphicsPixmapItems are created on the second layer with a z value of 1
@@ -53,242 +53,251 @@ namespace editor
  * These Items are also saved in m_tileOccupants. The second layer is dynamic, by keeping pointers
  * to its Pixmap Items we can remove them and switch them around.
  */
-class LevelScene : public QGraphicsScene, public EventHandler {
-public:
-    /**
-     * It builds a LevelScene from the provided vector of tile ids and width and height.
-     * It creates the bottom layer of Tile objects and builds a second layer of QGraphicsPixmapItems on top,
-     * if the tile id is > 0 and the tile is not on the border.
-     * @param name The name of the level.
-     * @param width The width of the level. Unit: number of tiles
-     * @param height The height of the level. Unit: number of tiles
-     * @param tileIds A vector of tile ids that define the level map.
-     * @param filePath The path to the file from which the level was loaded, empty string if level was just created.
-     * @param parent The parent to set for the LevelScene.
-     */
-    LevelScene(const std::string& name, int width, int height, std::vector<uint8_t> tileIds, const std::string& filePath, QWidget *parent = nullptr);
+class LevelScene : public QGraphicsScene, public EventHandler
+{
+    public:
+        /**
+         * It builds a LevelScene from the provided vector of tile ids and width and height.
+         * It creates the bottom layer of Tile objects and builds a second layer of
+         * QGraphicsPixmapItems on top, if the tile id is > 0 and the tile is not on the border.
+         * @param name The name of the level.
+         * @param width The width of the level. Unit: number of tiles
+         * @param height The height of the level. Unit: number of tiles
+         * @param tileIds A vector of tile ids that define the level map.
+         * @param filePath The path to the file from which the level was loaded, empty string if
+         * level was just created.
+         * @param parent The parent to set for the LevelScene.
+         */
+        LevelScene(
+            const std::string& name, int width, int height, std::vector<uint8_t> tileIds,
+            const std::string& filePath, QWidget* parent = nullptr);
 
-    /**
-     * Uses the LevelScene constructor internally to create an empty LevelScene (only grass, water cliffs on the borders).
-     * @param name The name of the new level.
-     * @param width The width of the new level. Unit: number of tiles
-     * @param height The height of the new level. Unit: number of tiles
-     * @param parent The parent to set for the newly created LevelScene.
-     * @return An empty LevelScene.
-     */
-    static LevelScene* empty(const std::string& name, int width, int height, QWidget *parent = nullptr);
+        /**
+         * Uses the LevelScene constructor internally to create an empty LevelScene (only grass,
+         * water cliffs on the borders).
+         * @param name The name of the new level.
+         * @param width The width of the new level. Unit: number of tiles
+         * @param height The height of the new level. Unit: number of tiles
+         * @param parent The parent to set for the newly created LevelScene.
+         * @return An empty LevelScene.
+         */
+        static LevelScene*
+        empty(const std::string& name, int width, int height, QWidget* parent = nullptr);
 
-    /**
-     * Uses the LevelScene constructor internally to create a LevelScene from an hdf5 file.
-     * @param filePath The path to the hdf5 file from which the LevelScene should be loaded.
-     * @param parent The parent to set for the newly created LevelScene.
-     * @return A LevelScene that was loaded from a file.
-     */
-    static LevelScene* fromFile(const std::string& filePath, QWidget *parent = nullptr);
+        /**
+         * Uses the LevelScene constructor internally to create a LevelScene from an hdf5 file.
+         * @param filePath The path to the hdf5 file from which the LevelScene should be loaded.
+         * @param parent The parent to set for the newly created LevelScene.
+         * @return A LevelScene that was loaded from a file.
+         */
+        static LevelScene* fromFile(const std::string& filePath, QWidget* parent = nullptr);
 
-    /**
-     * Gets the name of the level.
-     * @return The current name of the level.
-     */
-    std::string getName();
+        /**
+         * Gets the name of the level.
+         * @return The current name of the level.
+         */
+        std::string getName();
 
-    /**
-     * Gets the width of the level.
-     * @return The width of the level. Unit: number of tiles.
-     */
-    int getWidth();
+        /**
+         * Gets the width of the level.
+         * @return The width of the level. Unit: number of tiles.
+         */
+        int getWidth();
 
-    /**
-     * Gets the height of the level.
-     * @return The height of the level. Unit: number of tiles.
-     */
-    int getHeight();
+        /**
+         * Gets the height of the level.
+         * @return The height of the level. Unit: number of tiles.
+         */
+        int getHeight();
 
-private:
-    /**
-     * Checks if the given index corresponds to a border tile.
-     * @param index The position of an individual tile if you linearized the level map.
-     * @return True or False if the given index corresponds to a border tile.
-     */
-    bool isBorder(int index);
+    private:
+        /**
+         * Checks if the given index corresponds to a border tile.
+         * @param index The position of an individual tile if you linearized the level map.
+         * @return True or False if the given index corresponds to a border tile.
+         */
+        bool isBorder(int index);
 
-    /**
-     * Checks if the tile id corresponds to a water tile.
-     * @param id The tile id to check.
-     * @return True or false if the given tile id corresponds to a water tile.
-     */
-    bool isWaterTile(uint8_t id);
+        /**
+         * Checks if the tile id corresponds to a water tile.
+         * @param id The tile id to check.
+         * @return True or false if the given tile id corresponds to a water tile.
+         */
+        bool isWaterTile(uint8_t id);
 
-    /**
-     * Updates the level name stored in LevelScene to newName.
-     * The onLevelNameUpdated event method is emitted by the LevelNameEdit Widget.
-     * @param newName The new name of the level.
-     */
-    void onLevelNameUpdated(std::string newName) override;
+        /**
+         * Updates the level name stored in LevelScene to newName.
+         * The onLevelNameUpdated event method is emitted by the LevelNameEdit Widget.
+         * @param newName The new name of the level.
+         */
+        void onLevelNameUpdated(std::string newName) override;
 
-    /**
-     * Writes the level to the file from which it was loaded initially. 
-     * If it was created from scratch, a path to the desired location is 
-     * obtained from the QT file save dialog.
-     * The onLevelWriteRequested event method is emitted by the SaveButton.
-     */
-    void onLevelWriteRequested() override;
+        /**
+         * Writes the level to the file from which it was loaded initially.
+         * If it was created from scratch, a path to the desired location is
+         * obtained from the QT file save dialog.
+         * The onLevelWriteRequested event method is emitted by the SaveButton.
+         */
+        void onLevelWriteRequested() override;
 
-    /**
-     * Renders the currently selcted tile (m_selectedTileId) on the provided index.
-     * The onTileEntered event method is emitted by the Tile object.
-     * @param index The position of an individual tile if you were to linearized the level map.
-     */
-    void onTileEntered(int index) override;  
+        /**
+         * Renders the currently selcted tile (m_selectedTileId) on the provided index.
+         * The onTileEntered event method is emitted by the Tile object.
+         * @param index The position of an individual tile if you were to linearized the level map.
+         */
+        void onTileEntered(int index) override;
 
-    /**
-     * Renders the old tile id from m_tileIds at index again if the selected tile id was
-     * not set onto that tile.
-     * The onTileExited event method is emitted by the Tile object.
-     * @param index The position of an individual tile if you were to linearized the level map.
-     */
-    void onTileExited(int index) override;
+        /**
+         * Renders the old tile id from m_tileIds at index again if the selected tile id was
+         * not set onto that tile.
+         * The onTileExited event method is emitted by the Tile object.
+         * @param index The position of an individual tile if you were to linearized the level map.
+         */
+        void onTileExited(int index) override;
 
-    /**
-     * Evaluates how to procede once a tile has been placed by clicking on it.
-     * On the border only water tiles can be placed.
-     * If the option for advanced tile placement is checked, it will be executed from here.
-     * If the option for symmetric tile placement is checked, it will also be executed from here.
-     * When a red building is selected, symmetric tile placement will turn the mirrored building
-     * into a blue one and vice versa.
-     * @param index The index of the placed tile. Used to calculate both the previous id
-     * and the position on the map.
-     */
-    void onTileClicked(int index) override;
+        /**
+         * Evaluates how to procede once a tile has been placed by clicking on it.
+         * On the border only water tiles can be placed.
+         * If the option for advanced tile placement is checked, it will be executed from here.
+         * If the option for symmetric tile placement is checked, it will also be executed from
+         * here. When a red building is selected, symmetric tile placement will turn the mirrored
+         * building into a blue one and vice versa.
+         * @param index The index of the placed tile. Used to calculate both the previous id
+         * and the position on the map.
+         */
+        void onTileClicked(int index) override;
 
-    /**
-     * Evaluates what tile has been placed, then calls the corresponding function.
-     * When this function is called advanced placement of tiles is enabled.
-     * If any street tile except bridges were placed placeRoad is called.
-     * If any Water or Land tiles are placed placeCliff is called.
-     * If any building is placed setTile is called.
-     */
-    void placeAdvancedTiles(int index);
+        /**
+         * Evaluates what tile has been placed, then calls the corresponding function.
+         * When this function is called advanced placement of tiles is enabled.
+         * If any street tile except bridges were placed placeRoad is called.
+         * If any Water or Land tiles are placed placeCliff is called.
+         * If any building is placed setTile is called.
+         */
+        void placeAdvancedTiles(int index);
 
-    /**
-     * Saves the newly selected tileId inside LevelScene.
-     * The onNewTileIdSelected event method is emitted by the TileButton which
-     * is part of the TileSelector on the right of the level editor.
-     * @param tileId The newly selected tile id.
-     */
-    void onNewTileIdSelected(uint8_t tileId) override;
+        /**
+         * Saves the newly selected tileId inside LevelScene.
+         * The onNewTileIdSelected event method is emitted by the TileButton which
+         * is part of the TileSelector on the right of the level editor.
+         * @param tileId The newly selected tile id.
+         */
+        void onNewTileIdSelected(uint8_t tileId) override;
 
-    /**
-     * Toggles LevelScene's internal m_advancedTilePlacement member.
-     * This event method is emitted by the Advanced Placement CheckBox in the TopBar.
-     */
-    void onAdvancedPlacementToggled() override;
-    /**
-     * Toggles LevelScene's internal m_symmetricTilePlacement member.
-     * This event method is emitted by the Advanced Placement CheckBox in the TopBar.
-     */
-    void onSymmetryToggled() override;
-    /**
-     * This places a tile on the map.
-     * @param index Position on the map where the Tile is placed.
-     * @param id Id of the placed tile.
-     */
-    void setTile(int index, uint8_t id);
-    /**
-     * A function of advanced placement used to determain whether the 8 surrounding tiles
-     * change when any land or water is placed. In this case it automaticly calculates the
-     * correct shape of the new cliffs and places them.
-     * @param placedLand If Land was placed - not water. Needed to evaluate if land should
-     * be added or removed around the placed tile.
-     * @param index Position of the tile water or land is placed on. The placed cliffs are the
-     * surrounding 8 tiles.
-     */
-    void placeCliff(bool placedLand, int index);
-    /**
-     * A recursive function of advanced placement used to adjust the roads around the placed one.
-     * The surrounding roads above, bellow, to the left and right are detected and used to
-     * calculate the shape the newly placed road should have. After that the function is again
-     * called for those up to 4 roads around.
-     * @param index The position of the newly placed road.
-     * @param updateFlag Used in the recursion. When true it calls itself on the 4 surrounding
-     * tiles. When false the recursion ends and it doesnt call itself again. 
-     */
-    void placeRoad(int index, bool updateFlag);
-    /**
-     * A technical helper function for placeCliff. When calculating the Direction of the
-     * surrounding 8 tiles different calculations have to be done due to the map being
-     * represented as a 1D array rather then a 2D one. As a result it would not be easily
-     * possible to iterate through index of the 8 surrounding tiles, starting with the one
-     * above, then turning clockwise. This function is used for this to prevent code duplication.
-     */
-    int calcDir(int i, int index);
-    /**
-     * A technical helper function for placeCliff. When evaluating whether land or water has
-     * been placed trees and mountains are treated as terrain, while reefs are treated as water.
-     * However once the placement of new cliffs has been determained reefs should not be replaced
-     * by water when there should not be made any change to the cell. This function fixes a bug
-     * where this would happen.
-     * @param id The id of a tile, this bug could trigger on.
-     * @param index The position the old tile is sitting on, possibly to be replaced by a new one.
-     */
-    bool isntIdentical(int16_t id, int index);
+        /**
+         * Toggles LevelScene's internal m_advancedTilePlacement member.
+         * This event method is emitted by the Advanced Placement CheckBox in the TopBar.
+         */
+        void onAdvancedPlacementToggled() override;
+        /**
+         * Toggles LevelScene's internal m_symmetricTilePlacement member.
+         * This event method is emitted by the Advanced Placement CheckBox in the TopBar.
+         */
+        void onSymmetryToggled() override;
+        /**
+         * This places a tile on the map.
+         * @param index Position on the map where the Tile is placed.
+         * @param id Id of the placed tile.
+         */
+        void setTile(int index, uint8_t id);
+        /**
+         * A function of advanced placement used to determain whether the 8 surrounding tiles
+         * change when any land or water is placed. In this case it automaticly calculates the
+         * correct shape of the new cliffs and places them.
+         * @param placedLand If Land was placed - not water. Needed to evaluate if land should
+         * be added or removed around the placed tile.
+         * @param index Position of the tile water or land is placed on. The placed cliffs are the
+         * surrounding 8 tiles.
+         */
+        void placeCliff(bool placedLand, int index);
+        /**
+         * A recursive function of advanced placement used to adjust the roads around the placed
+         * one. The surrounding roads above, bellow, to the left and right are detected and used to
+         * calculate the shape the newly placed road should have. After that the function is again
+         * called for those up to 4 roads around.
+         * @param index The position of the newly placed road.
+         * @param updateFlag Used in the recursion. When true it calls itself on the 4 surrounding
+         * tiles. When false the recursion ends and it doesnt call itself again.
+         */
+        void placeRoad(int index, bool updateFlag);
+        /**
+         * A technical helper function for placeCliff. When calculating the Direction of the
+         * surrounding 8 tiles different calculations have to be done due to the map being
+         * represented as a 1D array rather then a 2D one. As a result it would not be easily
+         * possible to iterate through index of the 8 surrounding tiles, starting with the one
+         * above, then turning clockwise. This function is used for this to prevent code
+         * duplication.
+         */
+        int calcDir(int i, int index);
+        /**
+         * A technical helper function for placeCliff. When evaluating whether land or water has
+         * been placed trees and mountains are treated as terrain, while reefs are treated as water.
+         * However once the placement of new cliffs has been determained reefs should not be
+         * replaced by water when there should not be made any change to the cell. This function
+         * fixes a bug where this would happen.
+         * @param id The id of a tile, this bug could trigger on.
+         * @param index The position the old tile is sitting on, possibly to be replaced by a new
+         * one.
+         */
+        bool isntIdentical(int16_t id, int index);
 
-    /**
-     * Places a new QGraphicsPixmapItem using the given tileId at the given index.
-     * It correclty sets its position and z value (1 -> terrain tile, 2 + index -> building tile)
-     * @param index The position of an individual tile if you were to linearized the level map.
-     * @param tileId The id that corresponds to a type of tile to use.
-     * @return A pointer to the QGraphicsPixmapItem, that was added to the level scene.
-     */
-    QGraphicsPixmapItem* occupyTile(int index, uint8_t tileId);
+        /**
+         * Places a new QGraphicsPixmapItem using the given tileId at the given index.
+         * It correclty sets its position and z value (1 -> terrain tile, 2 + index -> building
+         * tile)
+         * @param index The position of an individual tile if you were to linearized the level map.
+         * @param tileId The id that corresponds to a type of tile to use.
+         * @return A pointer to the QGraphicsPixmapItem, that was added to the level scene.
+         */
+        QGraphicsPixmapItem* occupyTile(int index, uint8_t tileId);
 
-    /**
-     * The name of the level.
-     */
-    std::string m_name;
+        /**
+         * The name of the level.
+         */
+        std::string m_name;
 
-    /**
-     * The width of the level. Unit: number of tiles.
-     */
-    int m_width;
+        /**
+         * The width of the level. Unit: number of tiles.
+         */
+        int m_width;
 
-    /**
-     * The height of the level. Unit: number of tiles.
-     */
-    int m_height;
+        /**
+         * The height of the level. Unit: number of tiles.
+         */
+        int m_height;
 
-    /**
-     * The tile id of every tile. (linearized representation)
-     */
-    std::vector<uint8_t> m_tileIds;
+        /**
+         * The tile id of every tile. (linearized representation)
+         */
+        std::vector<uint8_t> m_tileIds;
 
-    /**
-     * The path from which the LevelScene was loaded (empty if created from scratch).
-     */
-    std::string m_filePath;
+        /**
+         * The path from which the LevelScene was loaded (empty if created from scratch).
+         */
+        std::string m_filePath;
 
-    /**
-     * The currently selected tile id. Tells the LevelScene which tiles need to be set
-     * if a tile is clicked.
-     */
-    uint8_t m_selectedTileId;
+        /**
+         * The currently selected tile id. Tells the LevelScene which tiles need to be set
+         * if a tile is clicked.
+         */
+        uint8_t m_selectedTileId;
 
-    /**
-     * Activates/deactivates adavanced placement.
-     */
-    bool m_advancedTilePlacement;
+        /**
+         * Activates/deactivates adavanced placement.
+         */
+        bool m_advancedTilePlacement;
 
-    /**
-     * Activates/deactivates adavanced placement.
-     */
-    bool m_symmetricTilePlacement;
+        /**
+         * Activates/deactivates adavanced placement.
+         */
+        bool m_symmetricTilePlacement;
 
-    /**
-     * Holds pointers to all of the QGraphicsPixmapItems of the top layer. 
-     * It holds nullptrs in places at which just the bottom layer is present.
-     * The length of m_tileOccupants is the same as m_tileIds.
-     */
-    std::vector<QGraphicsPixmapItem*> m_tileOccupants;
+        /**
+         * Holds pointers to all of the QGraphicsPixmapItems of the top layer.
+         * It holds nullptrs in places at which just the bottom layer is present.
+         * The length of m_tileOccupants is the same as m_tileIds.
+         */
+        std::vector<QGraphicsPixmapItem*> m_tileOccupants;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/MainWindow.hpp b/src/editor/MainWindow.hpp
index 65057c0..f4cf77b 100644
--- a/src/editor/MainWindow.hpp
+++ b/src/editor/MainWindow.hpp
@@ -16,8 +16,8 @@ namespace editor
 {
 
 /**
- * MainWindow is the top level Widget of the LevelEditor. 
- * All other Widgets are children of MainWindow. 
+ * MainWindow is the top level Widget of the LevelEditor.
+ * All other Widgets are children of MainWindow.
  * MainWindow is instantiated on the stack in main.cpp.
  * Thus, MainWindow is freed automatically at application exit together
  * with all of the other widgets (descendants), because of the way memory management works in QT.
@@ -27,32 +27,31 @@ namespace editor
 class MainWindow : public QMainWindow, public EventHandler
 {
     public:
-    /**
-     * Creates a MainWindow from the given LevelScene and parent.
-     * @param level The LevelScene of the level that should be edited.
-     * @param parent The parent widget for the MainWindow.
-     */
+        /**
+         * Creates a MainWindow from the given LevelScene and parent.
+         * @param level The LevelScene of the level that should be edited.
+         * @param parent The parent widget for the MainWindow.
+         */
         MainWindow(LevelScene* level, QWidget* parent = nullptr);
 
-
     private:
-    /**
-     * Updates the Window Title with the new_name.
-     * @param new_name The new level name.
-     */
+        /**
+         * Updates the Window Title with the new_name.
+         * @param new_name The new level name.
+         */
         void onLevelNameUpdated(std::string newName) override;
 
-    /**
-     * The widht of the level that is being edited.
-     * Unit: number of tiles.
-     */
-        int  m_levelWidth;
-
-    /**
-     * The height of the level that is being edited.
-     * Unit: number of tiles.
-     */ 
-        int  m_levelHeight;
+        /**
+         * The widht of the level that is being edited.
+         * Unit: number of tiles.
+         */
+        int m_levelWidth;
+
+        /**
+         * The height of the level that is being edited.
+         * Unit: number of tiles.
+         */
+        int m_levelHeight;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/SaveButton.cpp b/src/editor/SaveButton.cpp
index a7aaa81..6c96287 100644
--- a/src/editor/SaveButton.cpp
+++ b/src/editor/SaveButton.cpp
@@ -21,7 +21,7 @@ SaveButton::SaveButton(const std::string& title, QWidget* parent)
 
 void SaveButton::mousePressEvent(QMouseEvent*)
 {
-    EventHandler::send([](EventHandler* e) { e->onLevelWriteRequested();});
+    EventHandler::send([](EventHandler* e) { e->onLevelWriteRequested(); });
 }
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/SaveButton.hpp b/src/editor/SaveButton.hpp
index bb16b5e..98993a3 100644
--- a/src/editor/SaveButton.hpp
+++ b/src/editor/SaveButton.hpp
@@ -1,9 +1,9 @@
 /**
-* SaveButton.cpp
-*
-* @date 29.01.2025
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-*/
+ * SaveButton.cpp
+ *
+ * @date 29.01.2025
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
+ */
 
 #pragma once
 
@@ -13,28 +13,29 @@ namespace editor
 {
 
 /**
- * The Save Button is displayed on the top right in the TopBar. 
- * Clicking it opens the file save dialog. 
- * It is not responsible for writing the level itself. 
+ * The Save Button is displayed on the top right in the TopBar.
+ * Clicking it opens the file save dialog.
+ * It is not responsible for writing the level itself.
  * Instead it collects the desired file path from the file save dialog and
  * emits the onLevelWriteRequested event method which is overwritten by the LevelScene.
  */
-class SaveButton : public QPushButton {
-public:
-    /**
-     * Creates a SaveButton with the given title and parent.
-     * @param title The title to display inside the SaveButton.
-     * @param parent The parent that should be set for the SaveButton.
-     */
-    SaveButton(const std::string& title, QWidget *parent = nullptr);
+class SaveButton : public QPushButton
+{
+    public:
+        /**
+         * Creates a SaveButton with the given title and parent.
+         * @param title The title to display inside the SaveButton.
+         * @param parent The parent that should be set for the SaveButton.
+         */
+        SaveButton(const std::string& title, QWidget* parent = nullptr);
 
-protected:
-    /**
-     * When a mouse press event is received,
-     * it emits the onLevelWriteRequested event method. 
-     * onLevelWriteRequested is overwritten by LevelScene.
-     */
-    void mousePressEvent(QMouseEvent*) override;
+    protected:
+        /**
+         * When a mouse press event is received,
+         * it emits the onLevelWriteRequested event method.
+         * onLevelWriteRequested is overwritten by LevelScene.
+         */
+        void mousePressEvent(QMouseEvent*) override;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/SpriteProvider.cpp b/src/editor/SpriteProvider.cpp
index b70cd56..f00416f 100644
--- a/src/editor/SpriteProvider.cpp
+++ b/src/editor/SpriteProvider.cpp
@@ -36,49 +36,50 @@ void SpriteProvider::initialize(const std::string& path)
         return;
     }
 
-/**
- * Provides all terrain tile names.
- * They are necessary to create the correct path to 
- * the hdf5 dataset that contains the pixels for a given terrain tile.
- */
-const std::vector<std::string> tileNames({"plain",
-                                  "water",
-                                  "forest",
-                                  "mountain",
-                                  "bridge_horizontal",
-                                  "bridge_vertical",
-                                  "street_horizontal",
-                                  "street_vertical",
-                                  "street_crossing",
-                                  "street_junction_right",
-                                  "street_junction_left",
-                                  "street_junction_down",
-                                  "street_junction_up",
-                                  "street_corner_top_left",
-                                  "street_corner_top_right",
-                                  "street_corner_bottom_left",
-                                  "street_corner_bottom_right",
-                                  "riff",
-                                  "cliff_top",
-                                  "cliff_bottom",
-                                  "cliff_left",
-                                  "cliff_right",
-                                  "cliff_corner_top_left",
-                                  "cliff_corner_top_right",
-                                  "cliff_corner_bottom_left",
-                                  "cliff_corner_bottom_right",
-                                  "cliff_inverse_corner_top_left",
-                                  "cliff_inverse_corner_top_right",
-                                  "cliff_inverse_corner_bottom_left",
-                                  "cliff_inverse_corner_bottom_right"});
+    /**
+     * Provides all terrain tile names.
+     * They are necessary to create the correct path to
+     * the hdf5 dataset that contains the pixels for a given terrain tile.
+     */
+    const std::vector<std::string> tileNames(
+        {"plain",
+         "water",
+         "forest",
+         "mountain",
+         "bridge_horizontal",
+         "bridge_vertical",
+         "street_horizontal",
+         "street_vertical",
+         "street_crossing",
+         "street_junction_right",
+         "street_junction_left",
+         "street_junction_down",
+         "street_junction_up",
+         "street_corner_top_left",
+         "street_corner_top_right",
+         "street_corner_bottom_left",
+         "street_corner_bottom_right",
+         "riff",
+         "cliff_top",
+         "cliff_bottom",
+         "cliff_left",
+         "cliff_right",
+         "cliff_corner_top_left",
+         "cliff_corner_top_right",
+         "cliff_corner_bottom_left",
+         "cliff_corner_bottom_right",
+         "cliff_inverse_corner_top_left",
+         "cliff_inverse_corner_top_right",
+         "cliff_inverse_corner_bottom_left",
+         "cliff_inverse_corner_bottom_right"});
 
     /**
- * Provides the names for all factions in the game.
- * The names can be used to create the path to the hdf5 dataset
- * containing the buildings for a given faction.
- */
-const std::vector<std::string> factionNames(
-      {"red", "blue", "green", "yellow", "purple", "neutral"});
+     * Provides the names for all factions in the game.
+     * The names can be used to create the path to the hdf5 dataset
+     * containing the buildings for a given faction.
+     */
+    const std::vector<std::string> factionNames(
+        {"red", "blue", "green", "yellow", "purple", "neutral"});
 
     HighFive::File file(path, HighFive::File::ReadOnly);
     sprites.reserve(60); // we now that we will load 60 sprites
diff --git a/src/editor/Tile.hpp b/src/editor/Tile.hpp
index b978d12..c108f96 100644
--- a/src/editor/Tile.hpp
+++ b/src/editor/Tile.hpp
@@ -1,9 +1,9 @@
 /**
-* Tile.hpp
-*
-* @date 27.01.2025
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-*/
+ * Tile.hpp
+ *
+ * @date 27.01.2025
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
+ */
 
 #pragma once
 
@@ -21,41 +21,42 @@ namespace editor
  * Every Tile is instantiated with its index so that it can send that index to the LevelScene
  * in case it registers a hover/enter/press event.
  */
-class Tile : public QGraphicsPixmapItem {
-public:
-    /**
-     * Creates a Tile instance for the given index with the given tile id.
-     * @param index The index of the tile if you were to linearize the level map.
-     * @param id The tile id, e.g. 0 -> grass, 1-> water, ...
-     */
-    Tile(int index, uint8_t id);
-
-private:
-    /**
-     * When a hover enter event is received it
-     * emits the onTileEntered event method with the tile's index.
-     * The LevelScene overwrites the onTileEntered event method.
-     */
-    void hoverEnterEvent(QGraphicsSceneHoverEvent*) override;
-
-    /**
-     * When a hover leave event is received it
-     * emits the onTileExited event method with the tile's index.
-     * The LevelScene overwrites the onTileExited event method.
-     */
-    void hoverLeaveEvent(QGraphicsSceneHoverEvent*) override;
-
-    /**
-     * When a mouse press event is received it
-     * emits the onTileClicked event method with the tile's index.
-     * The LevelScene overwrites the onTileClicked event method.
-     */
-    void mousePressEvent(QGraphicsSceneMouseEvent*) override;
-
-    /**
-     * The index of the tile if you were to linearize the level map.
-     */
-    int m_index;
+class Tile : public QGraphicsPixmapItem
+{
+    public:
+        /**
+         * Creates a Tile instance for the given index with the given tile id.
+         * @param index The index of the tile if you were to linearize the level map.
+         * @param id The tile id, e.g. 0 -> grass, 1-> water, ...
+         */
+        Tile(int index, uint8_t id);
+
+    private:
+        /**
+         * When a hover enter event is received it
+         * emits the onTileEntered event method with the tile's index.
+         * The LevelScene overwrites the onTileEntered event method.
+         */
+        void hoverEnterEvent(QGraphicsSceneHoverEvent*) override;
+
+        /**
+         * When a hover leave event is received it
+         * emits the onTileExited event method with the tile's index.
+         * The LevelScene overwrites the onTileExited event method.
+         */
+        void hoverLeaveEvent(QGraphicsSceneHoverEvent*) override;
+
+        /**
+         * When a mouse press event is received it
+         * emits the onTileClicked event method with the tile's index.
+         * The LevelScene overwrites the onTileClicked event method.
+         */
+        void mousePressEvent(QGraphicsSceneMouseEvent*) override;
+
+        /**
+         * The index of the tile if you were to linearize the level map.
+         */
+        int m_index;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/TileButton.cpp b/src/editor/TileButton.cpp
index a617423..7ff5e34 100644
--- a/src/editor/TileButton.cpp
+++ b/src/editor/TileButton.cpp
@@ -1,10 +1,10 @@
 /**
-* TileButton.cpp
-*
-* @date 29.01.2025
-* @author Nils Jonathan Friedrich Eckardt implementation
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) minor changes
-*/
+ * TileButton.cpp
+ *
+ * @date 29.01.2025
+ * @author Nils Jonathan Friedrich Eckardt implementation
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) minor changes
+ */
 
 #include "TileButton.hpp"
 
diff --git a/src/editor/TileButton.hpp b/src/editor/TileButton.hpp
index 1805e3c..488db9b 100644
--- a/src/editor/TileButton.hpp
+++ b/src/editor/TileButton.hpp
@@ -1,10 +1,10 @@
 /**
-* TileButton.hpp
-*
-* @date 29.01.2025
-* @author Nils Jonathan Friedrich Eckardt implementation
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) minor changes
-*/
+ * TileButton.hpp
+ *
+ * @date 29.01.2025
+ * @author Nils Jonathan Friedrich Eckardt implementation
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) minor changes
+ */
 
 #pragma once
 
@@ -17,25 +17,28 @@ namespace editor
  * They listen for a mouse press and emit the onNewTileSelected event methode
  * and transmits with it the selected id of the selected tile.
  */
-class TileButton : public QPushButton {
-public:
-/**
- * Creates a TileButton with the texture of a tile and the provided parent.
- * @param id The id of the tile on this button.
- * @param parent The parent to set for this button.
- */
-    TileButton(const uint8_t id, QWidget *parent = nullptr);
-protected:
-/**
- * When a mouse press event is received,
- * it emits the onNewTileIdSelected event with its tile's id.
- */
-    void mousePressEvent(QMouseEvent* event) override;
-private:
-/**
- * The id of this button.
- */
-    uint8_t m_id;
+class TileButton : public QPushButton
+{
+    public:
+        /**
+         * Creates a TileButton with the texture of a tile and the provided parent.
+         * @param id The id of the tile on this button.
+         * @param parent The parent to set for this button.
+         */
+        TileButton(const uint8_t id, QWidget* parent = nullptr);
+
+    protected:
+        /**
+         * When a mouse press event is received,
+         * it emits the onNewTileIdSelected event with its tile's id.
+         */
+        void mousePressEvent(QMouseEvent* event) override;
+
+    private:
+        /**
+         * The id of this button.
+         */
+        uint8_t m_id;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/TileSelector.hpp b/src/editor/TileSelector.hpp
index bcb7500..372c512 100644
--- a/src/editor/TileSelector.hpp
+++ b/src/editor/TileSelector.hpp
@@ -1,10 +1,10 @@
 /**
-* TileSelector.cpp
-*
-* @date 28.01.2025
-* @author Nils Jonathan Friedrich Eckardt implementation
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) skeleton
-*/
+ * TileSelector.cpp
+ *
+ * @date 28.01.2025
+ * @author Nils Jonathan Friedrich Eckardt implementation
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de) skeleton
+ */
 
 #pragma once
 
@@ -20,60 +20,62 @@ namespace editor
  * It displays the tiles that can be selected within categories, to be placed on the
  * map of the LevelScene.
  */
-class TileSelector : public QScrollArea {
-public:
-/**
- * Creates the TileSelector with the provided parent.
- * The appearance of the selector is hardcoded by the arguments it provides its functions.
- * There should not be created more then one of these at a time.
- * @param parent The parent to set for the TileSelector
- */
-    TileSelector(QWidget *parent = nullptr);
-private:
-/**
- * Creates a label of a category to be displayed.
- * @param parent The parent to set for the QLabel.
- * @param text The text of the label.
- */
-    QLabel *createNewLabel(QWidget* parent, const char *text);
-/**
- * Creates a section of the TileSelector.
- * Before this there should always be a category label be created.
- * The section contains TileButtons listed in the same order, that the ids for them
- * are provided. After 3 buttons the next line is used. Reordering the TileButtons
- * can simply be done by changing the order in which their ids are provided.
- * @param parent The parent to set for this QGridLayout.
- * @param ids A list of the ids for which TileButtons will be created.
- */
-    template<typename... T>
-    QGridLayout* creatSectionLayout(QWidget* parent, T... ids);
-/**
- * A recursive helper function for createSectionLayout.
- * Each time it is called it adds a TileButton for the first of the provided ids to the
- * QGridLayout. The id then is discarded and this function is called again with the
- * remaining ids. 
- * @param layout A link to the QGridLayout the TileButtons are added to.
- * @param usedIdCounter Contains what the number of the current used id is. Needed to
- * add the TileButton to the correct position of the grid.
- * @param parent The parent the TileButtons will be set to.
- * @param id The current id a TileButton will be created for.
- * @param ids The remaining ids for which a TileButton will be created in a future
- * function call.
- */
-    template<typename T, typename... Rest>
-    void sectionLayout(QGridLayout*& layout, int usedIdCounter, QWidget* parent, T id, Rest...ids);
-/**
- * The end of the recursive helper function sectionLayout.
- * When this is called no more but 1 id is remaining for which a TileButton will be created.
- * @param layout A link to the QGridLayout the TileButtons are added to.
- * @param usedIdCounter Contains what the number of the current used id is. Needed to
- * add the TileButton to the correct position of the grid.
- * @param parent The parent the TileButtons will be set to.
- * @param id The current id a TileButton will be created for.
- */
-    template<typename T>
-    void sectionLayout(QGridLayout*& layout, int usedIdCounter, QWidget* parent, T id);
-    
+class TileSelector : public QScrollArea
+{
+    public:
+        /**
+         * Creates the TileSelector with the provided parent.
+         * The appearance of the selector is hardcoded by the arguments it provides its functions.
+         * There should not be created more then one of these at a time.
+         * @param parent The parent to set for the TileSelector
+         */
+        TileSelector(QWidget* parent = nullptr);
+
+    private:
+        /**
+         * Creates a label of a category to be displayed.
+         * @param parent The parent to set for the QLabel.
+         * @param text The text of the label.
+         */
+        QLabel* createNewLabel(QWidget* parent, const char* text);
+        /**
+         * Creates a section of the TileSelector.
+         * Before this there should always be a category label be created.
+         * The section contains TileButtons listed in the same order, that the ids for them
+         * are provided. After 3 buttons the next line is used. Reordering the TileButtons
+         * can simply be done by changing the order in which their ids are provided.
+         * @param parent The parent to set for this QGridLayout.
+         * @param ids A list of the ids for which TileButtons will be created.
+         */
+        template <typename... T>
+        QGridLayout* creatSectionLayout(QWidget* parent, T... ids);
+        /**
+         * A recursive helper function for createSectionLayout.
+         * Each time it is called it adds a TileButton for the first of the provided ids to the
+         * QGridLayout. The id then is discarded and this function is called again with the
+         * remaining ids.
+         * @param layout A link to the QGridLayout the TileButtons are added to.
+         * @param usedIdCounter Contains what the number of the current used id is. Needed to
+         * add the TileButton to the correct position of the grid.
+         * @param parent The parent the TileButtons will be set to.
+         * @param id The current id a TileButton will be created for.
+         * @param ids The remaining ids for which a TileButton will be created in a future
+         * function call.
+         */
+        template <typename T, typename... Rest>
+        void
+        sectionLayout(QGridLayout*& layout, int usedIdCounter, QWidget* parent, T id, Rest... ids);
+        /**
+         * The end of the recursive helper function sectionLayout.
+         * When this is called no more but 1 id is remaining for which a TileButton will be created.
+         * @param layout A link to the QGridLayout the TileButtons are added to.
+         * @param usedIdCounter Contains what the number of the current used id is. Needed to
+         * add the TileButton to the correct position of the grid.
+         * @param parent The parent the TileButtons will be set to.
+         * @param id The current id a TileButton will be created for.
+         */
+        template <typename T>
+        void sectionLayout(QGridLayout*& layout, int usedIdCounter, QWidget* parent, T id);
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/TopBar.cpp b/src/editor/TopBar.cpp
index cae08c0..41a20d5 100644
--- a/src/editor/TopBar.cpp
+++ b/src/editor/TopBar.cpp
@@ -12,12 +12,12 @@
 #include <QLabel>
 #include <QSize>
 
+#include "AdvancedPlacementSwitch.hpp"
 #include "LevelNameEdit.hpp"
 #include "SaveButton.hpp"
 #include "ZoomInButton.hpp"
 #include "ZoomInfo.hpp"
 #include "ZoomOutButton.hpp"
-#include "AdvancedPlacementSwitch.hpp"
 
 namespace editor
 {
@@ -37,13 +37,16 @@ TopBar::TopBar(const std::string& levelName, QWidget* parent) : QToolBar(parent)
     leftLayout->addWidget(textField);
     leftLayout->addStretch();
 
-    QPushButton* saveButton = new SaveButton("Speichern", rightContainer);
-    QPushButton* zoomIn = new ZoomInButton(rightContainer);
-    QPushButton* zoomOut = new ZoomOutButton(rightContainer);
-    QPushButton* zoomInfo = new ZoomInfo(rightContainer);
-    AdvancedPlacementSwitch* symmetryBox = new AdvancedPlacementSwitch("symmetrisches Bearbeiten", false, container);
-    leftLayout->addWidget(symmetryBox);    //diese Reihenfolge vermeidet einen Bug, bei dem False zu true wird
-    AdvancedPlacementSwitch* placementBox = new AdvancedPlacementSwitch("Kacheln automatisch setzen", true, container);
+    QPushButton*             saveButton = new SaveButton("Speichern", rightContainer);
+    QPushButton*             zoomIn = new ZoomInButton(rightContainer);
+    QPushButton*             zoomOut = new ZoomOutButton(rightContainer);
+    QPushButton*             zoomInfo = new ZoomInfo(rightContainer);
+    AdvancedPlacementSwitch* symmetryBox =
+        new AdvancedPlacementSwitch("symmetrisches Bearbeiten", false, container);
+    leftLayout->addWidget(
+        symmetryBox); // diese Reihenfolge vermeidet einen Bug, bei dem False zu true wird
+    AdvancedPlacementSwitch* placementBox =
+        new AdvancedPlacementSwitch("Kacheln automatisch setzen", true, container);
     leftLayout->addWidget(placementBox);
     rightLayout->addStretch();
     rightLayout->addWidget(zoomOut);
diff --git a/src/editor/TopBar.hpp b/src/editor/TopBar.hpp
index 26037ef..4852077 100644
--- a/src/editor/TopBar.hpp
+++ b/src/editor/TopBar.hpp
@@ -22,16 +22,17 @@ namespace editor
  * - SaveButon
  * TopBar inherits from QToolBar to ensure the QT look and fell.
  */
-class TopBar : public QToolBar {
-public: 
-    /**
-     * Creates a TopBar with the provided levelName and parent.
-     * The levelName is needed to prefill the LineEdit in the TopBar with
-     * the current level name.
-     * @param levelName The current name of the level.
-     * @param parent The parent to set for the TopBar.
-     */
-    TopBar(const std::string& levelName, QWidget *parent = nullptr);
+class TopBar : public QToolBar
+{
+    public:
+        /**
+         * Creates a TopBar with the provided levelName and parent.
+         * The levelName is needed to prefill the LineEdit in the TopBar with
+         * the current level name.
+         * @param levelName The current name of the level.
+         * @param parent The parent to set for the TopBar.
+         */
+        TopBar(const std::string& levelName, QWidget* parent = nullptr);
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/ZoomInButton.hpp b/src/editor/ZoomInButton.hpp
index 4faef07..daba616 100644
--- a/src/editor/ZoomInButton.hpp
+++ b/src/editor/ZoomInButton.hpp
@@ -1,9 +1,9 @@
 /**
-* ZoomInButton.hpp
-*
-* @date 02.02.2025
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-*/
+ * ZoomInButton.hpp
+ *
+ * @date 02.02.2025
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
+ */
 
 #pragma once
 
@@ -17,20 +17,21 @@ namespace editor
  * It listens to mouse presses and emits the onZoomed event method
  * with a delta of 0.25 in case of a mouse press.
  */
-class ZoomInButton : public QPushButton {
-public:
-    /**
-     * Creates a ZoomInButton with the provided parent.
-     * @param parent The parent to set for the ZoomInButton.
-     */
-    ZoomInButton(QWidget* parent = nullptr);
+class ZoomInButton : public QPushButton
+{
+    public:
+        /**
+         * Creates a ZoomInButton with the provided parent.
+         * @param parent The parent to set for the ZoomInButton.
+         */
+        ZoomInButton(QWidget* parent = nullptr);
 
-private:
-    /**
-     * When a mouse press event is received,
-     * it emits the onZoomed event method with a delta of 0.25.
-     */
-    void mousePressEvent(QMouseEvent*) override;
+    private:
+        /**
+         * When a mouse press event is received,
+         * it emits the onZoomed event method with a delta of 0.25.
+         */
+        void mousePressEvent(QMouseEvent*) override;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/ZoomInfo.hpp b/src/editor/ZoomInfo.hpp
index 4ea2511..edf4412 100644
--- a/src/editor/ZoomInfo.hpp
+++ b/src/editor/ZoomInfo.hpp
@@ -15,9 +15,9 @@ namespace editor
 {
 
 /**
- * ZoomInfo inherits from QPushButton, but doesn't actually act as a button. 
+ * ZoomInfo inherits from QPushButton, but doesn't actually act as a button.
  * It just displays the current zoom percentage.
- * To update the text that is displayed in case of a zoom change, it 
+ * To update the text that is displayed in case of a zoom change, it
  * inherits from EventHandler and overwrites the onZoomed event method.
  */
 class ZoomInfo : public QPushButton, public EventHandler
@@ -26,16 +26,16 @@ class ZoomInfo : public QPushButton, public EventHandler
         ZoomInfo(QWidget* parent = nullptr);
 
     private:
-    /**
-     * The percentage by which the LevelMap is zoomed in/out at the moment.
-     */
+        /**
+         * The percentage by which the LevelMap is zoomed in/out at the moment.
+         */
         double m_currentScale;
 
-    /**
-     * Updates the zoom info text to correctly display the updated zoom percentage.
-     * @param delta The percentage to add/subtract to the current zoom percentage.
-     */
-        void   onZoomed(double delta) override;
+        /**
+         * Updates the zoom info text to correctly display the updated zoom percentage.
+         * @param delta The percentage to add/subtract to the current zoom percentage.
+         */
+        void onZoomed(double delta) override;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/ZoomOutButton.hpp b/src/editor/ZoomOutButton.hpp
index 00969ea..886fb1b 100644
--- a/src/editor/ZoomOutButton.hpp
+++ b/src/editor/ZoomOutButton.hpp
@@ -1,9 +1,9 @@
 /**
-* ZoomOutButton.hpp
-*
-* @date 02.02.2025
-* @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
-*/
+ * ZoomOutButton.hpp
+ *
+ * @date 02.02.2025
+ * @author Jonathan Dueck (jonathan.dueck@informatik.hs-fulda.de)
+ */
 
 #pragma once
 
@@ -17,20 +17,21 @@ namespace editor
  * It listens to mouse presses and emits the onZoomed event method
  * with a delta of -0.25 in case of a mouse press.
  */
-class ZoomOutButton : public QPushButton {
-public:
-    /**
-    * Creates a ZoomInButton with the provided parent.
-    * @param parent The parent to set for the ZoomInButton.
-    */
-    ZoomOutButton(QWidget* parent = nullptr);
+class ZoomOutButton : public QPushButton
+{
+    public:
+        /**
+         * Creates a ZoomInButton with the provided parent.
+         * @param parent The parent to set for the ZoomInButton.
+         */
+        ZoomOutButton(QWidget* parent = nullptr);
 
-private:
-    /**
-     * When a mouse press event is received,
-     * it emits the onZoomed event method with a delta of 0.25.
-     */
-    void mousePressEvent(QMouseEvent*) override;
+    private:
+        /**
+         * When a mouse press event is received,
+         * it emits the onZoomed event method with a delta of 0.25.
+         */
+        void mousePressEvent(QMouseEvent*) override;
 };
 
 } // namespace editor
\ No newline at end of file
diff --git a/src/editor/main.cpp b/src/editor/main.cpp
index f136dbe..adc6ab4 100644
--- a/src/editor/main.cpp
+++ b/src/editor/main.cpp
@@ -9,10 +9,10 @@
 #include <QCommandLineParser>
 #include <filesystem>
 
-#include "highfive/H5File.hpp"
 #include "LevelScene.hpp"
 #include "MainWindow.hpp"
 #include "SpriteProvider.hpp"
+#include "highfive/H5File.hpp"
 
 using namespace editor;
 
@@ -32,15 +32,16 @@ using namespace editor;
  * They are constructed from the provided command line options
  * in the loadLevelOptions function.
  */
-struct LevelOptions {
-    int width;
-    int height;
-    std::string levelFilepath;
+struct LevelOptions
+{
+        int         width;
+        int         height;
+        std::string levelFilepath;
 };
 
 /**
- * loadLevelOptions implements a full fledged command line application for retrieving the 
- * level options. 
+ * loadLevelOptions implements a full fledged command line application for retrieving the
+ * level options.
  * For that purpose it creates a QCoreApplication and QCommandLineParser object.
  * QCoreApplication is just used for loading the level options.
  * It is destroyed at function exit.
@@ -50,14 +51,15 @@ struct LevelOptions {
  * All of these arguments have default values: width/height: 20, level h5 file path: ''
  * @param argc The number of command line arguments provided by the user.
  * @param argv All of the command line arguments provided by the user.
- * @returns If the user provided options are valid, they will be returned inside an optional, 
+ * @returns If the user provided options are valid, they will be returned inside an optional,
  *          else an empty optional will be returned.
  */
-std::optional<LevelOptions> loadLevelOptions(int argc, char* argv[]) {
+std::optional<LevelOptions> loadLevelOptions(int argc, char* argv[])
+{
     // Sperately from the QApplication we use for the Level Editor UI, we use QCoreApplication for
     // the command line application for launching the editor.
-    // The reason is that using QApplication is very slow, because it has to initialize all of the internal UI stuff.
-    // That is not what you want if only a simple ./editor --help was executed.
+    // The reason is that using QApplication is very slow, because it has to initialize all of the
+    // internal UI stuff. That is not what you want if only a simple ./editor --help was executed.
     QCoreApplication app(argc, argv);
     QCoreApplication::setApplicationVersion("1.0.0");
     QCommandLineParser parser;
@@ -73,14 +75,23 @@ Examples:
     parser.addVersionOption();
     parser.addHelpOption();
     parser.setApplicationDescription(topSection.c_str());
-    parser.addOption(QCommandLineOption("width", "The width of the new level map (default 20, minimum: 3).", "number-of-tiles", "20"));
-    parser.addOption(QCommandLineOption("height", "The height of the new level map (default 20, minimum: 3).", "number-of-tiles", "20"));
-    parser.addOption(QCommandLineOption("edit", "The path to the HDF5 level map file that you want to edit. If edit is not set, a new level map is created.", "filepath"));
+    parser.addOption(QCommandLineOption(
+        "width", "The width of the new level map (default 20, minimum: 3).", "number-of-tiles",
+        "20"));
+    parser.addOption(QCommandLineOption(
+        "height", "The height of the new level map (default 20, minimum: 3).", "number-of-tiles",
+        "20"));
+    parser.addOption(QCommandLineOption(
+        "edit",
+        "The path to the HDF5 level map file that you want to edit. If edit is not set, a new "
+        "level map is created.",
+        "filepath"));
     parser.process(app);
 
     // QT Parser does not exit when unexpected positional arguments are provided,
     // so have to do it by hand. 0 positional arguments are expected.
-    if (parser.positionalArguments().size() > 0) {
+    if (parser.positionalArguments().size() > 0)
+    {
         std::cerr << "Command not recognized.\n" << std::endl;
         parser.showHelp(1); // shows the help info and quits the application with exit code 1
         return std::nullopt;
@@ -88,33 +99,40 @@ Examples:
 
     // make sure that provided with, height and level file path are valid
     // if yes add them to the level options struct
-    bool widthOk;
-    bool heightOk;
+    bool         widthOk;
+    bool         heightOk;
     LevelOptions options;
     options.width = parser.value("width").toUInt(&widthOk);
     options.height = parser.value("height").toUInt(&heightOk);
-    if (!widthOk || options.width < 3) {
-        std::cerr << "You provided an invalid level width: '" << parser.value("width").toStdString() << "'\nThe level width has to be a valid number >= 3." << std::endl;
+    if (!widthOk || options.width < 3)
+    {
+        std::cerr << "You provided an invalid level width: '" << parser.value("width").toStdString()
+                  << "'\nThe level width has to be a valid number >= 3." << std::endl;
         return std::nullopt;
     }
-    if (!heightOk || options.height < 3) {
-        std::cerr << "You provided an invalid level height: '" << parser.value("height").toStdString() << "'\nThe level height has to be a valid number >= 3." << std::endl;
+    if (!heightOk || options.height < 3)
+    {
+        std::cerr << "You provided an invalid level height: '"
+                  << parser.value("height").toStdString()
+                  << "'\nThe level height has to be a valid number >= 3." << std::endl;
         return std::nullopt;
     }
     options.levelFilepath = parser.value("edit").toStdString();
-    if (!options.levelFilepath.empty() && !std::filesystem::exists(options.levelFilepath)) {
-        std::cerr << "The level map file path: '" << options.levelFilepath <<"' does not exist." << std::endl;
+    if (!options.levelFilepath.empty() && !std::filesystem::exists(options.levelFilepath))
+    {
+        std::cerr << "The level map file path: '" << options.levelFilepath << "' does not exist."
+                  << std::endl;
         return std::nullopt;
     }
 
     return options;
 }
 
-
 int main(int argc, char* argv[])
 {
     std::optional<LevelOptions> levelOptions = loadLevelOptions(argc, argv);
-    if (!levelOptions.has_value()) {
+    if (!levelOptions.has_value())
+    {
         return 1;
     }
 
@@ -122,33 +140,48 @@ int main(int argc, char* argv[])
 
     // SpriteProvider is initialized once and can then be used from anywhere in the application
     // to get the QGraphicsPixmap for a specific tile.
-    if (!std::filesystem::exists("../res/spritesheet.h5")) {
-        std::cerr << "The spritesheet was not found.\nIt was expected in: ../res/spritesheet.h5" << std::endl;
+    if (!std::filesystem::exists("../res/spritesheet.h5"))
+    {
+        std::cerr << "The spritesheet was not found.\nIt was expected in: ../res/spritesheet.h5"
+                  << std::endl;
         return 1;
     }
-    try {
+    try
+    {
         SpriteProvider::initialize("../res/spritesheet.h5");
-    } catch (const HighFive::Exception&) {
-        std::cerr << "Loading the spritesheet failed.\nPlease make sure that it is not corrupted.\nIt was loaded from: ../res/spritesheet.h5" << std::endl;
+    }
+    catch (const HighFive::Exception&)
+    {
+        std::cerr << "Loading the spritesheet failed.\nPlease make sure that it is not "
+                     "corrupted.\nIt was loaded from: ../res/spritesheet.h5"
+                  << std::endl;
         return 1;
     }
 
     // initialize LevelScene
     LevelScene* level;
-    if (!levelOptions.value().levelFilepath.empty()) {
-        try {
+    if (!levelOptions.value().levelFilepath.empty())
+    {
+        try
+        {
             level = LevelScene::fromFile(levelOptions.value().levelFilepath);
         }
-        catch (const HighFive::Exception&) {
-            std::cerr << "Loading an existing level map from '" << levelOptions.value().levelFilepath << "' failed.\nPlease make sure that the hdf5 level file is not corrupted." << std::endl;
+        catch (const HighFive::Exception&)
+        {
+            std::cerr << "Loading an existing level map from '"
+                      << levelOptions.value().levelFilepath
+                      << "' failed.\nPlease make sure that the hdf5 level file is not corrupted."
+                      << std::endl;
             return 1;
         }
     }
-    else {
-        level = LevelScene::empty("My Level", levelOptions.value().width, levelOptions.value().height);
+    else
+    {
+        level =
+            LevelScene::empty("My Level", levelOptions.value().width, levelOptions.value().height);
     }
 
-    // We create the MainWindow on the Stack. Thus it will be destructed 
+    // We create the MainWindow on the Stack. Thus it will be destructed
     // automatically at exit. The way memory management works in QT is that
     // you can set a parent on every Widget class you create. If the parent gets
     // destroyed all its children are destroyed as well. It is acutally save in both
diff --git a/src/game/level/Level.cpp b/src/game/level/Level.cpp
index aa61098..4f3ef41 100644
--- a/src/game/level/Level.cpp
+++ b/src/game/level/Level.cpp
@@ -43,7 +43,7 @@ Level::Level(const std::string& path, Engine& engine)
 
     m_physicsEngine = std::make_unique<PhysicsEngine>();
     m_combatEngine = std::make_unique<CombatEngine>();
-    HighFive::File file(path, HighFive::File::ReadOnly);
+    HighFive::File    file(path, HighFive::File::ReadOnly);
     HighFive::DataSet tilesarraySet = file.getDataSet("tilesarray");
 
     std::vector<uint8_t> levelTilesarray;
@@ -51,7 +51,7 @@ Level::Level(const std::string& path, Engine& engine)
     tilesarraySet.getAttribute("width").read(m_width);
     tilesarraySet.getAttribute("height").read(m_height);
     tilesarraySet.getAttribute("name").read(m_name);
-    tilesarraySet.read(levelTilesarray); 
+    tilesarraySet.read(levelTilesarray);
 
     // if level is smaler than 20x20 surround with water tiles
     if (m_width < 20 || m_height < 20)
-- 
GitLab


From d79d15403caa5fdbb039804439677dc95ef673c1 Mon Sep 17 00:00:00 2001
From: Frederik <frederik@prasch.de>
Date: Mon, 10 Feb 2025 02:27:49 +0100
Subject: [PATCH 25/26] Fix CmakeLists

---
 CMakeLists.txt | 1 +
 1 file changed, 1 insertion(+)

diff --git a/CMakeLists.txt b/CMakeLists.txt
index 1ed2fab..77d7e8e 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -127,6 +127,7 @@ else()
     include_directories(${SDL2_IMG_INCLUDE_DIR})
     include_directories(${SDL2_TTF_INCLUDE_DIR})
     include_directories(${HDF5_INCLUDE_DIRS})
+    target_include_directories(advanced_wars PRIVATE ${highfive_SOURCE_DIR}/include)
 
     target_link_libraries(advanced_wars
         ${HDF5_LIBRARIES}
-- 
GitLab


From 3f26bfd1b9249dd05f82f2f48f680557c948f410 Mon Sep 17 00:00:00 2001
From: TheUltimateOptimist <digitalConfidence@web.de>
Date: Mon, 10 Feb 2025 02:39:14 +0100
Subject: [PATCH 26/26] fixed level maps for compatibality with new format

---
 res/level.h5            | Bin 6310 -> 6310 bytes
 res/map_split_island.h5 | Bin 6560 -> 6560 bytes
 2 files changed, 0 insertions(+), 0 deletions(-)

diff --git a/res/level.h5 b/res/level.h5
index aa5ba5b60aae9dc4927a4e818e5bb480796ee5a0..121e122f46d9b6010fe278739e02a9f570b29214 100644
GIT binary patch
delta 373
zcmZ2xxXf_F4kkqo1_(I81fgN129zN%`6iQlJr6?wn9s<-&cMT<!H|)fnVwO?z#zcE
zz`z2QQ2>*SOpFj3OfoP)c$hR7RGx>y1I%J%U}fN7&|t_*%uNLe2s1D+ure?(K+RLb
zX%Nf;$DD$U#EBcTCmXP^F*0tBXOU!_ctC@hk%4P+HEU!2)QFYo2tTla{ZO8nQj)<y
jz90BO4h89F5CF3jn86go3J3+3figGlY-QZUu}lB}B~BjJ

delta 206
zcmZ2xxXf_F4kkqn1_(I81fgMMZfZ$lN@7VO!{nPx?z)T&Yz&MbDKNpnz{tP>;z7h1
z7#NrtB*1J*Mn(pK$!l3<Ex}v{4h9LZI%b##1_3Z1MhGF9(`-E>oq?fa;>O;|1}tnm
pOi(EX1_kDc8|5}zut+d6GcvGEu4Zjyhp27XypiKC<0g(}0svN88rlE=

diff --git a/res/map_split_island.h5 b/res/map_split_island.h5
index cfaaa1b32769273462ff045ff0eb1834c2309b2f..6ea30413cd50fa6f858d35eb817f5b96ec27b503 100644
GIT binary patch
delta 379
zcmZ2ryuf(F4kkqo1_(I81fgN129zN%`6iQlJr6?wn9s<-&cMT<!H|)fnVwO?z#zcE
zz`z2QQ2>*SOpFj3OfoP)c$l;ZR32e2D+33E218zAZYoGhn1O+Tn}LA=YMu^GgJ2c}
z7vyA?coyd*=A}&Bm^#^jg^iJMb3BVA<HQ3R%!~|NldD-9>+8c;rXy@*1N)>rGo>Vh
ifpVV+FbIGg&Y-{yrWiIrD3Hl8*2bN!jGH(X2m$~Yf+1J{

delta 206
zcmZ2ryuf(F4kkqn1_(I81fgMMZfZ$lN@7VO!{nPx?z)T&Yz&MbDKNpnz{tP>;z7h1
z7#NrtB*1J*Mn(pK$!l3<Ex}v{4h9LZI%b##1_3Z1MhGF9Qx>%}oq?fa;>O;|1}tnm
pOi(EX1_kDc8|5}zut+d6GcvGEu4Zjyhp27Xe30WW<0g&;f&f`18yf%s

-- 
GitLab