diff --git a/SHADE_Engine/SHADE_Engine.vcxproj b/SHADE_Engine/SHADE_Engine.vcxproj
index 50bcc7eb..178b98f7 100644
--- a/SHADE_Engine/SHADE_Engine.vcxproj
+++ b/SHADE_Engine/SHADE_Engine.vcxproj
@@ -116,6 +116,7 @@
+
@@ -199,6 +200,7 @@
+
diff --git a/SHADE_Engine/SHADE_Engine.vcxproj.filters b/SHADE_Engine/SHADE_Engine.vcxproj.filters
index 7752c7fb..c28e339e 100644
--- a/SHADE_Engine/SHADE_Engine.vcxproj.filters
+++ b/SHADE_Engine/SHADE_Engine.vcxproj.filters
@@ -19,6 +19,9 @@
{B3E3FAFD-9FDD-2350-884A-BA6074E389BC}
+
+ {8A8E2B37-7646-6D84-DF4D-46E0CB240875}
+
{1653CE33-0220-293F-2B39-17E717655ECD}
@@ -156,6 +159,9 @@
Engine
+
+ Filesystem
+
Graphics\Buffers
@@ -407,6 +413,9 @@
Engine
+
+ Filesystem
+
Graphics\Buffers
diff --git a/SHADE_Engine/src/Filesystem/SHFileSystem.cpp b/SHADE_Engine/src/Filesystem/SHFileSystem.cpp
new file mode 100644
index 00000000..5663dadd
--- /dev/null
+++ b/SHADE_Engine/src/Filesystem/SHFileSystem.cpp
@@ -0,0 +1,135 @@
+#include "SHpch.h"
+#include "SHFileSystem.h"
+#include "fileapi.h"
+#include
+#include
+#include
+
+namespace SHADE
+{
+ char const FOLDER_MAX_COUNT {15};
+
+ std::unordered_map> SHFileSystem::folders;
+ FolderPointer SHFileSystem::root {nullptr};
+
+ SHFolder::SHFolder(FolderHandle id, FolderName name)
+ :id{ id }, name{ name }, subFolders(0), folded{ false }, path{""}
+ {
+ }
+
+ FolderLocation SHFileSystem::CreateNewFolderHere(FolderName name, FolderLocation here) noexcept
+ {
+ if (here == 0)
+ {
+ if (!folders.contains(0))
+ {
+ folders[0] = std::make_unique(0, "root");
+ }
+
+ auto const count = static_cast(folders[here]->subFolders.size());
+
+ assert(count < FOLDER_MAX_COUNT, "Max subfolders reached\n");
+
+ auto const location = static_cast(count);
+
+ CreateFolder(folders[0]->path, here, location, name);
+
+ return location;
+ }
+
+ assert(folders.contains(here), "Folder creation location does not exist/invalid\n");
+
+ auto const count = static_cast(folders[here]->subFolders.size());
+
+ FolderHandle location = here;
+ location <<= FOLDER_BIT_ALLOCATE;
+ location |= count;
+
+ assert(count < FOLDER_MAX_COUNT, "Max subfolders reached\n");
+ CreateFolder(folders[0]->path, here, location, name);
+
+ return location;
+ }
+
+ bool SHFileSystem::DeleteFolder(FolderPointer location) noexcept
+ {
+ assert(folders.contains(location->id), "Delete target does not exist/invalid.\n");
+
+ for (auto const& subFolder : folders[location->id]->subFolders)
+ {
+ DeleteFolder(subFolder);
+ }
+
+ RemoveDirectoryA(folders[location->id]->path.c_str());
+ return true;
+ }
+
+ void SHFileSystem::StartupFillDirectories(FolderPath path) noexcept
+ {
+ std::queue folderQueue;
+
+ folderQueue.push(RegisterFolder(path, 0, 0, "Root"));
+
+ while (!folderQueue.empty())
+ {
+ auto folder = folderQueue.front();
+ folderQueue.pop();
+ FolderCounter count = 0;
+
+ for (auto const& dirEntry : std::filesystem::directory_iterator(folder->path))
+ {
+ if (!dirEntry.is_directory())
+ {
+ continue;
+ }
+
+ FolderLocation location = folder->id;
+ location <<= FOLDER_BIT_ALLOCATE;
+ location |= ++count;
+
+ std::string name = dirEntry.path().string();
+ name = name.substr(name.find_last_of('/') + 1, name.length() - name.find_last_of('/'));
+
+ FolderPointer newFolder{ RegisterFolder(
+ dirEntry.path().string(),
+ folder->id,
+ location,
+ name)
+ };
+
+ folderQueue.push(newFolder);
+ folder->subFolders.push_back(newFolder);
+ }
+ }
+ }
+
+ FolderPointer SHFileSystem::CreateFolder(FolderPath path, FolderLocation parent, FolderHandle location, FolderName name) noexcept
+ {
+ assert(
+ CreateDirectoryA(path.c_str(), nullptr),
+ "Failed to create folder\n"
+ );
+
+ folders[location] = std::make_unique(location, name);
+ folders[location]->path = path;
+ folders[parent]->subFolders.push_back(folders[location].get());
+
+ return FolderMakeHelper(path, parent, location, name);
+ }
+
+ FolderPointer SHFileSystem::RegisterFolder(FolderPath path, FolderLocation parent, FolderHandle location,
+ FolderName name) noexcept
+ {
+ return FolderMakeHelper(path, parent, location, name);
+ }
+
+ FolderPointer SHFileSystem::FolderMakeHelper(FolderPath path, FolderLocation parent, FolderHandle location,
+ FolderName name) noexcept
+ {
+ folders[location] = std::make_unique(location, name);
+ folders[location]->path = path;
+ folders[parent]->subFolders.push_back(folders[location].get());
+
+ return folders[location].get();
+ }
+}
diff --git a/SHADE_Engine/src/Filesystem/SHFileSystem.h b/SHADE_Engine/src/Filesystem/SHFileSystem.h
new file mode 100644
index 00000000..9b8b94a2
--- /dev/null
+++ b/SHADE_Engine/src/Filesystem/SHFileSystem.h
@@ -0,0 +1,57 @@
+#pragma once
+
+#include
+#include
+#include
+#include
+
+namespace SHADE
+{
+ class SHFolder;
+
+ typedef unsigned char FolderCounter;
+ typedef unsigned char FileCounter;
+ typedef uint64_t FolderLocation;
+ typedef uint64_t FolderHandle;
+ typedef std::string FolderName;
+ typedef std::string FolderPath;
+ typedef SHFolder* FolderPointer;
+
+ constexpr char FOLDER_BIT_ALLOCATE{ 4 };
+ constexpr char FOLDER_MAX_DEPTH{ 16 };
+
+ class SHFolder
+ {
+ public:
+ SHFolder(FolderHandle id, FolderName name);
+
+ FolderHandle id;
+ FolderName name;
+ std::vector subFolders;
+
+ bool folded;
+
+ private:
+ FolderPath path;
+ friend class SHFileSystem;
+ };
+
+ class SHFileSystem
+ {
+ public:
+ static FolderLocation CreateNewFolderHere(FolderName name, FolderLocation here = 0) noexcept;
+
+ static bool DeleteFolder(FolderPointer location) noexcept;
+
+ static void StartupFillDirectories(FolderPath path) noexcept;
+
+ private:
+ static FolderPointer root;
+
+ static std::unordered_map> folders;
+
+ static FolderPointer CreateFolder(FolderPath path, FolderLocation parent, FolderHandle location, FolderName name) noexcept;
+ static FolderPointer RegisterFolder(FolderPath path, FolderLocation parent, FolderHandle location, FolderName name) noexcept;
+ static FolderPointer FolderMakeHelper(FolderPath path, FolderLocation parent, FolderHandle location, FolderName name) noexcept;
+ };
+}
\ No newline at end of file