Potato Engine
Loading...
Searching...
No Matches
PersistentLevel.cpp
Go to the documentation of this file.
1
2
3#include "Util/Vector2.hpp"
4#include "Archivable.hpp"
6#include "Debug/Debug.hpp"
7#include "Game/World.hpp"
8
9#include "fmt/core.h"
10#include "nlohmann/json.hpp"
11#include "PersistentLevel.hpp"
12
13using json = nlohmann::json;
14
15static json safeGetJson(const std::filesystem::path& path);
16
17PersistentLevel::PersistentLevel(const std::string& saveFileName) {
18
19 saveFileAbsPath = std::filesystem::current_path() / "Saves" / saveFileName;
20
21}
22
24 json Save = safeGetJson(saveFileAbsPath);
25 json StaticActors = Save["StaticActors"];
26
27 bool allSuccessful = true;
28
29 World* world = GameInstance::get()->GetWorld();
30 __ArchiveType& Archive = __Archive::_GetArchive();
31
32 LOG_DEFAULT(LogType::INFO, "Loading static actors from persistent level");
33
34 for (const auto& [ClassID, posList] : StaticActors.items()) {
35
36 auto it = Archive.find(ClassID);
37 // if ClassID not found in archive, continue to skip
38 if (it == Archive.end()) {
39 LOG_DEFAULT(LogType::WARNING, fmt::format("Unkown ClassID in factory: {} - skipped loading", ClassID));
40 continue;
41 }
42
43 auto constructor = it->second;
44 // if constsructor not found, continue to skip
45 if (constructor == nullptr) {
46 LOG_DEFAULT(LogType::WARNING, fmt::format("Bad function reference in archive for class: {} - skipped loading", ClassID));
47 continue;
48 }
49
50 LOG_DEFAULT(LogType::INFO, fmt::format("Loading static actors of class: {}", ClassID));
51
52 for (const auto& pos : posList) {
53
54 if (!pos.is_array() || pos.size() != 2) {
55 LOG_DEFAULT(LogType::WARNING, fmt::format("Invalid position data for class: {} - skipped loading", ClassID));
56 continue;
57 }
58
59 Vector2 Position;
60
61 try {
62
63 float x = pos[0].get<float>();
64 float y = pos[1].get<float>();
65 Position = Vector2(x,y);
66
67 } catch (const json::type_error& e) {
68
69 LOG_DEFAULT(LogType::WARNING, fmt::format("Failed to parse data for actor: {} - skipped loading", e.what()));
70 allSuccessful = false;
71
72 continue;
73 }
74
75 Archivable* obj = constructor();
76
77 // if returns nullptr, skip
78 if (obj == nullptr) {
79 LOG_DEFAULT(LogType::WARNING, fmt::format("Object could not be constructor for class: {} - skipped loading", ClassID));
80 allSuccessful = false;
81 continue;
82 }
83
84 if (Actor* addedActor = world->AddtoPool(dynamic_cast<Actor*>(obj))) {
85 addedActor->SetPosition(Position);
86 } else {
87 allSuccessful = false;
88 LOG_DEFAULT(LogType::WARNING, fmt::format( "Failed to load static actor when adding to actor pool: {} - skipped loading", ClassID ));
89 delete obj;
90 }
91 }
92
93 }
94
95
96 LOG_DEFAULT(LogType::INFO, fmt::format("Static actors loaded {}", allSuccessful ? "successfully" : "unsuccessfully"));
97 return allSuccessful;
98}
99
100int PersistentLevel::GetIntData( std::string key ) const {
101 json Save = safeGetJson(saveFileAbsPath);
102
103 return Save["Data"][key].get<int>();
104}
105float PersistentLevel::GetFloatData( std::string key ) const {
106 json Save = safeGetJson(saveFileAbsPath);
107
108 return Save["Data"][key].get<float>();
109}
110std::string PersistentLevel::GetStringData( std::string key ) const {
111 json Save = safeGetJson(saveFileAbsPath);
112
113 return Save["Data"][key].get<std::string>();
114}
115Vector2 PersistentLevel::GetVector2Data( std::string key ) const {
116 json Save = safeGetJson(saveFileAbsPath);
117
118 json vecJson = Save["Data"][key];
119 return Vector2(vecJson[0].get<float>(), vecJson[1].get<float>());
120}
121
122void PersistentLevel::WriteIntData( std::string key, int value ) {
123 json Save = safeGetJson(saveFileAbsPath);
124
125 Save["Data"][key] = value;
126}
127void PersistentLevel::WriteFloatData( std::string key, float value ) {
128 json Save = safeGetJson(saveFileAbsPath);
129
130 Save["Data"][key] = value;
131}
132void PersistentLevel::WriteStringData( std::string key, std::string value ) {
133 json Save = safeGetJson(saveFileAbsPath);
134
135 Save["Data"][key] = value;
136}
137void PersistentLevel::WriteVector2Data( std::string key, const Vector2& value ) {
138 json Save = safeGetJson(saveFileAbsPath);
139
140 Save["Data"][key] = { value.x, value.y };
141}
142
143static json safeGetJson(const std::filesystem::path& path) {
144 json parsed;
145
146 if (!std::filesystem::exists(path)) {
147 LOG_DEFAULT(LogType::ERROR, fmt::format("Save file not found at {}", path.c_str()));
148 return parsed;
149 }
150
151 std::ifstream file(path);
152
153 if (!file.is_open()) {
154 LOG_DEFAULT(LogType::ERROR, fmt::format("Could not open save file at {}", path.c_str()));
155 return parsed;
156 }
157
158 try {
159 parsed = json::parse(file);
160 } catch (const json::parse_error& e) {
161 LOG_DEFAULT(LogType::ERROR, fmt::format("Failed to parse save file at {}: {}", path.c_str(), e.what()));
162 }
163
164 return parsed;
165
166}
167
168
169
170
171
172
Logger LOG_DEFAULT
Default log object.
Definition Debug.cpp:9
Base actor class.
Definition Actor.hpp:14
Abstract factory class inherited by all classes that should be archived.
static GameInstance * get()
Gets singleton instance.
World * GetWorld() const
Gets world object.
Local level managing gameplay interactions.
Definition World.hpp:19
Actor * AddtoPool(Actor *actor)
Attempts to add external actor object to world managing system.
Definition World.cpp:37
PersistentLevel(const std::string &saveFileName)
Construct level object.
bool LoadStaticActors()
Loads all static actors into the world.
Standard 2-dimensional vector.
Definition Vector2.hpp:11
float x
X Component.
Definition Vector2.hpp:13
float y
Y Component.
Definition Vector2.hpp:15