summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLaG1924 <12997935+LaG1924@users.noreply.github.com>2018-02-25 13:05:18 +0100
committerGitHub <noreply@github.com>2018-02-25 13:05:18 +0100
commit55e432becc8c5a1b8dd6543cc0a26e0213aeb88f (patch)
treef5d7dea2c6dc5a3d2feb8f4c0413f83beef61793
parentRaycast debug render (diff)
parentmin/max functions (diff)
downloadAltCraft-55e432becc8c5a1b8dd6543cc0a26e0213aeb88f.tar
AltCraft-55e432becc8c5a1b8dd6543cc0a26e0213aeb88f.tar.gz
AltCraft-55e432becc8c5a1b8dd6543cc0a26e0213aeb88f.tar.bz2
AltCraft-55e432becc8c5a1b8dd6543cc0a26e0213aeb88f.tar.lz
AltCraft-55e432becc8c5a1b8dd6543cc0a26e0213aeb88f.tar.xz
AltCraft-55e432becc8c5a1b8dd6543cc0a26e0213aeb88f.tar.zst
AltCraft-55e432becc8c5a1b8dd6543cc0a26e0213aeb88f.zip
-rw-r--r--src/AssetManager.cpp294
-rw-r--r--src/AssetManager.hpp19
-rw-r--r--src/Block.cpp4
-rw-r--r--src/Block.hpp25
-rw-r--r--src/Entity.cpp128
-rw-r--r--src/Event.cpp1
-rw-r--r--src/Event.hpp3
-rw-r--r--src/Frustum.cpp2
-rw-r--r--src/GameState.cpp205
-rw-r--r--src/GameState.hpp65
-rw-r--r--src/GlobalState.cpp88
-rw-r--r--src/Packet.hpp910
-rw-r--r--src/Render.cpp600
-rw-r--r--src/RendererSection.cpp6
-rw-r--r--src/RendererWorld.cpp16
-rw-r--r--src/Utility.cpp83
-rw-r--r--src/Utility.hpp56
-rw-r--r--src/Vector.hpp210
-rw-r--r--src/World.cpp67
-rw-r--r--src/main.cpp2
20 files changed, 1549 insertions, 1235 deletions
diff --git a/src/AssetManager.cpp b/src/AssetManager.cpp
index 0507bc1..0561992 100644
--- a/src/AssetManager.cpp
+++ b/src/AssetManager.cpp
@@ -19,184 +19,183 @@ const std::string pathToTextureIndex = "./textures.json";
const fs::path pathToModels = "./assets/minecraft/models/";
AssetManager::AssetManager() {
- LoadIds();
- LoadTextureResources();
+ LoadIds();
+ LoadTextureResources();
LoadBlockModels();
}
void AssetManager::LoadIds() {
- std::ifstream in(pathToAssetsList);
- nlohmann::json index;
- in >> index;
- for (auto &it:index) {
- unsigned short id = it["type"].get<int>();
- unsigned char state = it["meta"].get<int>();
- std::string blockName = it["text_type"].get<std::string>();
+ std::ifstream in(pathToAssetsList);
+ nlohmann::json index;
+ in >> index;
+ for (auto &it:index) {
+ unsigned short id = it["type"].get<int>();
+ unsigned char state = it["meta"].get<int>();
+ std::string blockName = it["text_type"].get<std::string>();
assetIds[blockName] = BlockId{ id, state };
- }
- LOG(INFO) << "Loaded " << assetIds.size() << " ids";
+ }
+ LOG(INFO) << "Loaded " << assetIds.size() << " ids";
}
AssetManager::~AssetManager() {
- delete textureAtlas;
+ delete textureAtlas;
}
//TODO: This function must be replaced with runtime texture atlas generating
void AssetManager::LoadTextureResources() {
- std::ifstream in(pathToTextureIndex);
- nlohmann::json index;
- in >> index;
- std::string filename = index["meta"]["image"].get<std::string>();
- float textureWidth = index["meta"]["size"]["w"].get<int>();
- float textureHeight = index["meta"]["size"]["h"].get<int>();
+ std::ifstream in(pathToTextureIndex);
+ nlohmann::json index;
+ in >> index;
+ std::string filename = index["meta"]["image"].get<std::string>();
+ float textureWidth = index["meta"]["size"]["w"].get<int>();
+ float textureHeight = index["meta"]["size"]["h"].get<int>();
size_t sizeName = 0,sizeTexture = 0;
- for (auto &it:index["frames"]) {
- auto frame = it["frame"];
- TextureCoordinates coord;
- coord.x = frame["x"].get<int>() / textureWidth;
- coord.y = frame["y"].get<int>() / textureHeight;
- coord.w = frame["w"].get<int>() / textureWidth;
- coord.h = frame["h"].get<int>() / textureHeight;
- std::string assetName = it["filename"].get<std::string>();
- assetName.insert(0, "minecraft/textures/");
- assetName.erase(assetName.length() - 4);
+ for (auto &it:index["frames"]) {
+ auto frame = it["frame"];
+ TextureCoordinates coord;
+ coord.x = frame["x"].get<int>() / textureWidth;
+ coord.y = frame["y"].get<int>() / textureHeight;
+ coord.w = frame["w"].get<int>() / textureWidth;
+ coord.h = frame["h"].get<int>() / textureHeight;
+ std::string assetName = it["filename"].get<std::string>();
+ assetName.insert(0, "minecraft/textures/");
+ assetName.erase(assetName.length() - 4);
assetName.shrink_to_fit();
sizeName += sizeof(assetName) + assetName.capacity();
sizeTexture += sizeof(coord);
- assetTextures[assetName] = coord;
- }
- textureAtlas = new Texture(filename);
- LOG(INFO) << "Texture atlas id is " << textureAtlas->texture;
+ assetTextures[assetName] = coord;
+ }
+ textureAtlas = new Texture(filename);
+ LOG(INFO) << "Texture atlas id is " << textureAtlas->texture;
}
TextureCoordinates AssetManager::GetTextureByAssetName(std::string AssetName) {
- if (assetTextures.find(AssetName) != assetTextures.end())
- return assetTextures[AssetName];
- else
- return TextureCoordinates{-1, -1, -1, -1};
+ if (assetTextures.find(AssetName) != assetTextures.end())
+ return assetTextures[AssetName];
+ else
+ return TextureCoordinates{-1, -1, -1, -1};
}
std::string AssetManager::GetTextureAssetNameByBlockId(BlockTextureId block) {
- //Block sides: 0 - bottom, 1 - top, 2 - north, 3 - south, 4 - west, 5 - east 6 - every side
- const std::map<BlockTextureId, std::string> lookupTable = {
- {BlockTextureId(0, 0), "minecraft/textures/blocks/air"},
- {BlockTextureId(1, 0), "minecraft/textures/blocks/stone"},
- {BlockTextureId(1, 1), "minecraft/textures/blocks/stone_granite"},
-
- {BlockTextureId(2, 0, 0), "minecraft/textures/blocks/dirt"},
- {BlockTextureId(2, 0, 1), "minecraft/textures/blocks/grass_top"},
- {BlockTextureId(2, 0, 2), "minecraft/textures/blocks/grass_side"},
- {BlockTextureId(2, 0, 3), "minecraft/textures/blocks/grass_side"},
- {BlockTextureId(2, 0, 4), "minecraft/textures/blocks/grass_side"},
- {BlockTextureId(2, 0, 5), "minecraft/textures/blocks/grass_side"},
-
- {BlockTextureId(3, 0), "minecraft/textures/blocks/dirt"},
- {BlockTextureId(4, 0), "minecraft/textures/blocks/cobblestone"},
- {BlockTextureId(5, 0), "minecraft/textures/blocks/planks"},
-
- {BlockTextureId(7, 0), "minecraft/textures/blocks/bedrock"},
-
- {BlockTextureId(17, 0, 0), "minecraft/textures/blocks/log_oak_top"},
- {BlockTextureId(17, 0, 1), "minecraft/textures/blocks/log_oak_top"},
- {BlockTextureId(17, 0, 2), "minecraft/textures/blocks/log_oak"},
- {BlockTextureId(17, 0, 3), "minecraft/textures/blocks/log_oak"},
- {BlockTextureId(17, 0, 4), "minecraft/textures/blocks/log_oak"},
- {BlockTextureId(17, 0, 5), "minecraft/textures/blocks/log_oak"},
-
- {BlockTextureId(17, 1, 0), "minecraft/textures/blocks/log_spruce_top"},
- {BlockTextureId(17, 1, 1), "minecraft/textures/blocks/log_spruce_top"},
- {BlockTextureId(17, 1, 2), "minecraft/textures/blocks/log_spruce"},
- {BlockTextureId(17, 1, 3), "minecraft/textures/blocks/log_spruce"},
- {BlockTextureId(17, 1, 4), "minecraft/textures/blocks/log_spruce"},
- {BlockTextureId(17, 1, 5), "minecraft/textures/blocks/log_spruce"},
-
- {BlockTextureId(17, 2, 0), "minecraft/textures/blocks/log_birch_top"},
- {BlockTextureId(17, 2, 1), "minecraft/textures/blocks/log_birch_top"},
- {BlockTextureId(17, 2, 2), "minecraft/textures/blocks/log_birch"},
- {BlockTextureId(17, 2, 3), "minecraft/textures/blocks/log_birch"},
- {BlockTextureId(17, 2, 4), "minecraft/textures/blocks/log_birch"},
- {BlockTextureId(17, 2, 5), "minecraft/textures/blocks/log_birch"},
-
- {BlockTextureId(17, 3, 0), "minecraft/textures/blocks/log_jungle_top"},
- {BlockTextureId(17, 3, 1), "minecraft/textures/blocks/log_jungle_top"},
- {BlockTextureId(17, 3, 2), "minecraft/textures/blocks/log_jungle"},
- {BlockTextureId(17, 3, 3), "minecraft/textures/blocks/log_jungle"},
- {BlockTextureId(17, 3, 4), "minecraft/textures/blocks/log_jungle"},
- {BlockTextureId(17, 3, 5), "minecraft/textures/blocks/log_jungle"},
-
- {BlockTextureId(18, 0), "minecraft/textures/blocks/leaves_oak"},
- {BlockTextureId(18, 1), "minecraft/textures/blocks/leaves_spruce"},
- {BlockTextureId(18, 2), "minecraft/textures/blocks/leaves_birch"},
- {BlockTextureId(18, 3), "minecraft/textures/blocks/leaves_jungle"},
-
- {BlockTextureId(61, 0, 0), "minecraft/textures/blocks/furnace_side"},
- {BlockTextureId(61, 0, 1), "minecraft/textures/blocks/furnace_top"},
- {BlockTextureId(61, 0, 2), "minecraft/textures/blocks/furnace_front_off"},
- {BlockTextureId(61, 0, 3), "minecraft/textures/blocks/furnace_side"},
- {BlockTextureId(61, 0, 4), "minecraft/textures/blocks/furnace_side"},
- {BlockTextureId(61, 0, 5), "minecraft/textures/blocks/furnace_side"},
-
- {BlockTextureId(62, 0, 0), "minecraft/textures/blocks/furnace_side"},
- {BlockTextureId(62, 0, 1), "minecraft/textures/blocks/furnace_top"},
- {BlockTextureId(62, 0, 2), "minecraft/textures/blocks/furnace_front_on"},
- {BlockTextureId(62, 0, 3), "minecraft/textures/blocks/furnace_side"},
- {BlockTextureId(62, 0, 4), "minecraft/textures/blocks/furnace_side"},
- {BlockTextureId(62, 0, 5), "minecraft/textures/blocks/furnace_side"},
-
-
- {BlockTextureId(31, 0), "minecraft/textures/blocks/deadbush"},
- {BlockTextureId(31, 1), "minecraft/textures/blocks/tallgrass"},
- {BlockTextureId(31, 2), "minecraft/textures/blocks/fern"},
- };
- auto ret = lookupTable.find(block);
- if (ret == lookupTable.end())
- return "";
- else
- return ret->second;
+ //Block sides: 0 - bottom, 1 - top, 2 - north, 3 - south, 4 - west, 5 - east 6 - every side
+ const std::map<BlockTextureId, std::string> lookupTable = {
+ {BlockTextureId(0, 0), "minecraft/textures/blocks/air"},
+ {BlockTextureId(1, 0), "minecraft/textures/blocks/stone"},
+ {BlockTextureId(1, 1), "minecraft/textures/blocks/stone_granite"},
+
+ {BlockTextureId(2, 0, 0), "minecraft/textures/blocks/dirt"},
+ {BlockTextureId(2, 0, 1), "minecraft/textures/blocks/grass_top"},
+ {BlockTextureId(2, 0, 2), "minecraft/textures/blocks/grass_side"},
+ {BlockTextureId(2, 0, 3), "minecraft/textures/blocks/grass_side"},
+ {BlockTextureId(2, 0, 4), "minecraft/textures/blocks/grass_side"},
+ {BlockTextureId(2, 0, 5), "minecraft/textures/blocks/grass_side"},
+
+ {BlockTextureId(3, 0), "minecraft/textures/blocks/dirt"},
+ {BlockTextureId(4, 0), "minecraft/textures/blocks/cobblestone"},
+ {BlockTextureId(5, 0), "minecraft/textures/blocks/planks"},
+
+ {BlockTextureId(7, 0), "minecraft/textures/blocks/bedrock"},
+
+ {BlockTextureId(17, 0, 0), "minecraft/textures/blocks/log_oak_top"},
+ {BlockTextureId(17, 0, 1), "minecraft/textures/blocks/log_oak_top"},
+ {BlockTextureId(17, 0, 2), "minecraft/textures/blocks/log_oak"},
+ {BlockTextureId(17, 0, 3), "minecraft/textures/blocks/log_oak"},
+ {BlockTextureId(17, 0, 4), "minecraft/textures/blocks/log_oak"},
+ {BlockTextureId(17, 0, 5), "minecraft/textures/blocks/log_oak"},
+
+ {BlockTextureId(17, 1, 0), "minecraft/textures/blocks/log_spruce_top"},
+ {BlockTextureId(17, 1, 1), "minecraft/textures/blocks/log_spruce_top"},
+ {BlockTextureId(17, 1, 2), "minecraft/textures/blocks/log_spruce"},
+ {BlockTextureId(17, 1, 3), "minecraft/textures/blocks/log_spruce"},
+ {BlockTextureId(17, 1, 4), "minecraft/textures/blocks/log_spruce"},
+ {BlockTextureId(17, 1, 5), "minecraft/textures/blocks/log_spruce"},
+
+ {BlockTextureId(17, 2, 0), "minecraft/textures/blocks/log_birch_top"},
+ {BlockTextureId(17, 2, 1), "minecraft/textures/blocks/log_birch_top"},
+ {BlockTextureId(17, 2, 2), "minecraft/textures/blocks/log_birch"},
+ {BlockTextureId(17, 2, 3), "minecraft/textures/blocks/log_birch"},
+ {BlockTextureId(17, 2, 4), "minecraft/textures/blocks/log_birch"},
+ {BlockTextureId(17, 2, 5), "minecraft/textures/blocks/log_birch"},
+
+ {BlockTextureId(17, 3, 0), "minecraft/textures/blocks/log_jungle_top"},
+ {BlockTextureId(17, 3, 1), "minecraft/textures/blocks/log_jungle_top"},
+ {BlockTextureId(17, 3, 2), "minecraft/textures/blocks/log_jungle"},
+ {BlockTextureId(17, 3, 3), "minecraft/textures/blocks/log_jungle"},
+ {BlockTextureId(17, 3, 4), "minecraft/textures/blocks/log_jungle"},
+ {BlockTextureId(17, 3, 5), "minecraft/textures/blocks/log_jungle"},
+
+ {BlockTextureId(18, 0), "minecraft/textures/blocks/leaves_oak"},
+ {BlockTextureId(18, 1), "minecraft/textures/blocks/leaves_spruce"},
+ {BlockTextureId(18, 2), "minecraft/textures/blocks/leaves_birch"},
+ {BlockTextureId(18, 3), "minecraft/textures/blocks/leaves_jungle"},
+
+ {BlockTextureId(61, 0, 0), "minecraft/textures/blocks/furnace_side"},
+ {BlockTextureId(61, 0, 1), "minecraft/textures/blocks/furnace_top"},
+ {BlockTextureId(61, 0, 2), "minecraft/textures/blocks/furnace_front_off"},
+ {BlockTextureId(61, 0, 3), "minecraft/textures/blocks/furnace_side"},
+ {BlockTextureId(61, 0, 4), "minecraft/textures/blocks/furnace_side"},
+ {BlockTextureId(61, 0, 5), "minecraft/textures/blocks/furnace_side"},
+
+ {BlockTextureId(62, 0, 0), "minecraft/textures/blocks/furnace_side"},
+ {BlockTextureId(62, 0, 1), "minecraft/textures/blocks/furnace_top"},
+ {BlockTextureId(62, 0, 2), "minecraft/textures/blocks/furnace_front_on"},
+ {BlockTextureId(62, 0, 3), "minecraft/textures/blocks/furnace_side"},
+ {BlockTextureId(62, 0, 4), "minecraft/textures/blocks/furnace_side"},
+ {BlockTextureId(62, 0, 5), "minecraft/textures/blocks/furnace_side"},
+
+
+ {BlockTextureId(31, 0), "minecraft/textures/blocks/deadbush"},
+ {BlockTextureId(31, 1), "minecraft/textures/blocks/tallgrass"},
+ {BlockTextureId(31, 2), "minecraft/textures/blocks/fern"},
+ };
+
+ auto ret = lookupTable.find(block);
+ return (ret == lookupTable.end()) ? "" : ret->second;
}
GLuint AssetManager::GetTextureAtlas() {
- return textureAtlas->texture;
+ return textureAtlas->texture;
}
TextureCoordinates AssetManager::GetTextureByBlock(BlockTextureId block) {
- std::string assetName = this->GetTextureAssetNameByBlockId(block);
- return this->GetTextureByAssetName(assetName);
+ std::string assetName = this->GetTextureAssetNameByBlockId(block);
+ return this->GetTextureByAssetName(assetName);
}
const std::map<BlockTextureId, glm::vec4> &AssetManager::GetTextureAtlasIndexes() {
- if (!textureAtlasIndexes.empty())
- return textureAtlasIndexes;
-
- LOG(INFO) << "Initializing texture atlas...";
- for (int id = 1; id < 128; id++) {
- for (int state = 0; state < 16; state++) {
- BlockTextureId blockTextureId(id, state, 6);
- if (!this->GetTextureByBlock(blockTextureId) &&
- !this->GetTextureByBlock(BlockTextureId(id, state, 0))) {
- continue;
- }
- if (this->GetTextureByBlock(blockTextureId)) {
- for (int i = 0; i < 6; i++) {
- TextureCoordinates tc = this->GetTextureByBlock(BlockTextureId(id, state, 6));
- textureAtlasIndexes[BlockTextureId(id, state, i)] = glm::vec4(tc.x, tc.y, tc.w, tc.h);
- }
- } else {
- for (int i = 0; i < 6; i++) {
- TextureCoordinates tc = this->GetTextureByBlock(BlockTextureId(id, state, i));
- textureAtlasIndexes[BlockTextureId(id, state, i)] = glm::vec4(tc.x, tc.y, tc.w, tc.h);
- }
- }
- }
- }
- LOG(INFO) << "Created " << textureAtlasIndexes.size() << " texture indexes";
-
- return textureAtlasIndexes;
+ if (!textureAtlasIndexes.empty())
+ return textureAtlasIndexes;
+
+ LOG(INFO) << "Initializing texture atlas...";
+ for (int id = 1; id < 128; id++) {
+ for (int state = 0; state < 16; state++) {
+ BlockTextureId blockTextureId(id, state, 6);
+ if (!this->GetTextureByBlock(blockTextureId) &&
+ !this->GetTextureByBlock(BlockTextureId(id, state, 0))) {
+ continue;
+ }
+
+ if (this->GetTextureByBlock(blockTextureId)) {
+ for (int i = 0; i < 6; i++) {
+ TextureCoordinates tc = this->GetTextureByBlock(BlockTextureId(id, state, 6));
+ textureAtlasIndexes[BlockTextureId(id, state, i)] = glm::vec4(tc.x, tc.y, tc.w, tc.h);
+ }
+ } else {
+ for (int i = 0; i < 6; i++) {
+ TextureCoordinates tc = this->GetTextureByBlock(BlockTextureId(id, state, i));
+ textureAtlasIndexes[BlockTextureId(id, state, i)] = glm::vec4(tc.x, tc.y, tc.w, tc.h);
+ }
+ }
+ }
+ }
+ LOG(INFO) << "Created " << textureAtlasIndexes.size() << " texture indexes";
+
+ return textureAtlasIndexes;
}
AssetManager &AssetManager::Instance() {
- static AssetManager assetManager;
- return assetManager;
+ static AssetManager assetManager;
+ return assetManager;
}
const BlockModel *AssetManager::GetBlockModelByBlockId(BlockId block) {
@@ -233,14 +232,10 @@ const BlockModel *AssetManager::GetBlockModelByBlockId(BlockId block) {
std::string blockName = blockIdToBlockName[block];
auto modelIt = models.find(blockName);
- if (modelIt == models.end())
- return nullptr;
-
- return &modelIt->second;
+ return (modelIt == models.end()) ? nullptr : &modelIt->second;
}
void AssetManager::LoadBlockModels() {
-
std::function<void(std::string)> parseModel = [&](std::string ModelName) {
if (models.find(ModelName) != models.end())
return;
@@ -377,7 +372,6 @@ void AssetManager::LoadBlockModels() {
continue;
std::string modelName = dirEntry.path().stem().generic_string();
-
parseModel("block/" + modelName);
}
}
diff --git a/src/AssetManager.hpp b/src/AssetManager.hpp
index 1169b7d..b828ee1 100644
--- a/src/AssetManager.hpp
+++ b/src/AssetManager.hpp
@@ -13,7 +13,8 @@
class Texture;
struct TextureCoordinates {
- TextureCoordinates(float x = -1, float y = -1, float w = -1, float h = -1) : x(x), y(y), w(w), h(h) {}
+ TextureCoordinates(float x = -1, float y = -1, float w = -1, float h = -1)
+ : x(x), y(y), w(w), h(h) {}
bool operator==(const TextureCoordinates &rhs) const {
return x == rhs.x &&
@@ -35,11 +36,12 @@ struct TextureCoordinates {
struct BlockTextureId {
//Block sides: 0 - bottom, 1 - top, 2 - north, 3 - south, 4 - west, 5 - east 6 - every side
- BlockTextureId(int id = 0, int state = 0, int side = 6) : id(id), state(state), side(side) {}
+ BlockTextureId(int id = 0, int state = 0, int side = 6)
+ : id(id), state(state), side(side) {}
- int id:9;
- int state:4;
- int side:3;
+ int id : 9;
+ int state : 4;
+ int side : 3;
bool operator<(const BlockTextureId &rhs) const {
@@ -59,7 +61,7 @@ struct BlockModel {
bool IsBlock = false;
std::string BlockName;
- bool AmbientOcclusion=true;
+ bool AmbientOcclusion = true;
enum DisplayVariants {
thirdperson_righthand,
@@ -72,6 +74,7 @@ struct BlockModel {
fixed,
DisplayVariantsCount,
};
+
struct DisplayData {
Vector rotation;
Vector translation;
@@ -105,6 +108,7 @@ struct BlockModel {
east,
none,
};
+
struct FaceData {
struct Uv {
int x1, y1, x2, y2;
@@ -122,7 +126,8 @@ struct BlockModel {
std::vector<ElementData> Elements;
};
-inline bool operator==(const BlockModel::ElementData::FaceData::Uv &lhs, const BlockModel::ElementData::FaceData::Uv &rhs) {
+inline bool operator==(const BlockModel::ElementData::FaceData::Uv &lhs,
+ const BlockModel::ElementData::FaceData::Uv &rhs) {
return lhs.x1 == rhs.x1 && lhs.y1 == rhs.y1 && lhs.x2 == rhs.x2 && lhs.y2 == rhs.y2;
}
diff --git a/src/Block.cpp b/src/Block.cpp
index 667670d..303909b 100644
--- a/src/Block.cpp
+++ b/src/Block.cpp
@@ -2,7 +2,9 @@
Block::~Block() {}
-Block::Block(unsigned short id, unsigned char state, unsigned char light, unsigned char sky) : id(id), state(state), light(light), sky (sky) {}
+Block::Block(unsigned short id, unsigned char state,
+ unsigned char light, unsigned char sky)
+ : id(id), state(state), light(light), sky (sky) {}
Block::Block() : id(0), state(0), light(0), sky(0) {}
diff --git a/src/Block.hpp b/src/Block.hpp
index 12d2907..cd01f9a 100644
--- a/src/Block.hpp
+++ b/src/Block.hpp
@@ -3,14 +3,13 @@
#include <functional>
struct Block {
- Block();
+ Block();
+ Block(unsigned short id, unsigned char state,
+ unsigned char light, unsigned char sky);
+ ~Block();
- Block(unsigned short id, unsigned char state, unsigned char light, unsigned char sky);
-
- ~Block();
-
- unsigned short id : 13;
- unsigned char state : 4;
+ unsigned short id : 13;
+ unsigned char state : 4;
unsigned char light : 4;
unsigned char sky : 4;
};
@@ -20,6 +19,15 @@ struct BlockId {
unsigned char state : 4;
};
+enum BlockFacing {
+ Bottom = 0,
+ Top,
+ North,
+ South,
+ West,
+ East
+};
+
bool operator==(const BlockId& lhs, const BlockId &rhs);
bool operator<(const BlockId& lhs, const BlockId &rhs);
@@ -27,8 +35,7 @@ bool operator<(const BlockId& lhs, const BlockId &rhs);
namespace std {
template <>
struct hash<BlockId> {
- std::size_t operator()(const BlockId& k) const
- {
+ std::size_t operator()(const BlockId& k) const {
size_t id = std::hash<unsigned short>()(k.id);
size_t state = std::hash<unsigned char>()(k.state);
diff --git a/src/Entity.cpp b/src/Entity.cpp
index d91e78d..a3a9527 100644
--- a/src/Entity.cpp
+++ b/src/Entity.cpp
@@ -1,14 +1,12 @@
#include "Entity.hpp"
-VectorF Entity::DecodeVelocity(short x, short y, short z)
-{
+VectorF Entity::DecodeVelocity(short x, short y, short z) {
const float ticksPerSecond = 20;
const double velMod = 1 / 8000.0;
return VectorF(x * velMod * ticksPerSecond, y*velMod*ticksPerSecond, z*velMod*ticksPerSecond);
}
-VectorF Entity::DecodeDeltaPos(short deltaX, short deltaY, short deltaZ)
-{
+VectorF Entity::DecodeDeltaPos(short deltaX, short deltaY, short deltaZ) {
const double posMod = 4096.0;
return VectorF(deltaX / posMod, deltaY / posMod, deltaZ / posMod);
}
@@ -29,75 +27,73 @@ double Entity::EncodePitch(double pitch) {
return -pitch;
}
-Entity CreateObject(ObjectType type)
-{
+Entity CreateObject(ObjectType type) {
Entity entity;
entity.type = EntityType::Object;
switch (type) {
- case ObjectType::Boat:
- break;
- case ObjectType::ItemStack:
- entity.width = 0.25;
- entity.height = 0.25;
- break;
- case ObjectType::AreaEffectCloud:
- break;
- case ObjectType::Minecart:
- break;
- case ObjectType::ActivatedTNT:
- break;
- case ObjectType::EnderCrystal:
- break;
- case ObjectType::TippedArrow:
- break;
- case ObjectType::Snowball:
- break;
- case ObjectType::Egg:
- break;
- case ObjectType::FireBall:
- break;
- case ObjectType::FireCharge:
- break;
- case ObjectType::ThrownEnderpearl:
- break;
- case ObjectType::WitherSkull:
- break;
- case ObjectType::ShulkerBullet:
- break;
- case ObjectType::LlamaSpit:
- break;
- case ObjectType::FallingObjects:
- break;
- case ObjectType::Itemframes:
- break;
- case ObjectType::EyeOfEnder:
- break;
- case ObjectType::ThrownPotion:
- break;
- case ObjectType::ThrownExpBottle:
- break;
- case ObjectType::FireworkRocket:
- break;
- case ObjectType::LeashKnot:
- break;
- case ObjectType::ArmorStand:
- break;
- case ObjectType::EvocationFangs:
- break;
- case ObjectType::FishingHook:
- break;
- case ObjectType::SpectralArrow:
- break;
- case ObjectType::DragonFireball:
- break;
- default:
- break;
+ case ObjectType::Boat:
+ break;
+ case ObjectType::ItemStack:
+ entity.width = 0.25;
+ entity.height = 0.25;
+ break;
+ case ObjectType::AreaEffectCloud:
+ break;
+ case ObjectType::Minecart:
+ break;
+ case ObjectType::ActivatedTNT:
+ break;
+ case ObjectType::EnderCrystal:
+ break;
+ case ObjectType::TippedArrow:
+ break;
+ case ObjectType::Snowball:
+ break;
+ case ObjectType::Egg:
+ break;
+ case ObjectType::FireBall:
+ break;
+ case ObjectType::FireCharge:
+ break;
+ case ObjectType::ThrownEnderpearl:
+ break;
+ case ObjectType::WitherSkull:
+ break;
+ case ObjectType::ShulkerBullet:
+ break;
+ case ObjectType::LlamaSpit:
+ break;
+ case ObjectType::FallingObjects:
+ break;
+ case ObjectType::Itemframes:
+ break;
+ case ObjectType::EyeOfEnder:
+ break;
+ case ObjectType::ThrownPotion:
+ break;
+ case ObjectType::ThrownExpBottle:
+ break;
+ case ObjectType::FireworkRocket:
+ break;
+ case ObjectType::LeashKnot:
+ break;
+ case ObjectType::ArmorStand:
+ break;
+ case ObjectType::EvocationFangs:
+ break;
+ case ObjectType::FishingHook:
+ break;
+ case ObjectType::SpectralArrow:
+ break;
+ case ObjectType::DragonFireball:
+ break;
+ default:
+ break;
}
return entity;
}
-Entity CreateMob(MobType type)
-{
+Entity CreateMob(MobType type) {
Entity entity;
entity.type = EntityType::Mob;
return entity;
diff --git a/src/Event.cpp b/src/Event.cpp
index 08c9ee7..5c126bb 100644
--- a/src/Event.cpp
+++ b/src/Event.cpp
@@ -57,6 +57,7 @@ void EventListener::PollEvents() {
std::lock_guard<std::recursive_mutex> rawLock (rawEventsMutex);
if (rawEvents.empty())
return;
+
std::lock_guard<std::recursive_mutex> eventsLock (eventsMutex);
std::lock_guard<std::recursive_mutex> handlersLock (handlersMutex);
while (!rawEvents.empty()) {
diff --git a/src/Event.hpp b/src/Event.hpp
index 4cdcdc3..4e04a5a 100644
--- a/src/Event.hpp
+++ b/src/Event.hpp
@@ -55,7 +55,7 @@ public:
template<typename T>
const T& get() const {
if (typeid(T) != data->Type())
- throw std::runtime_error(std::string("Type ") + typeid(T).name() + " encountered but " + data->Type().name() + " expected");
+ throw std::runtime_error(std::string("Type ") + typeid(T).name() +" encountered but " + data->Type().name() + " expected");
return static_cast<EventData<T>*>(data.get())->data;
}
};
@@ -69,6 +69,7 @@ class EventListener {
std::recursive_mutex eventsMutex;
std::queue<Event> rawEvents;
std::recursive_mutex rawEventsMutex;
+
public:
EventListener();
diff --git a/src/Frustum.cpp b/src/Frustum.cpp
index dbad920..e928e6b 100644
--- a/src/Frustum.cpp
+++ b/src/Frustum.cpp
@@ -3,7 +3,7 @@
#include <glm/gtc/type_ptr.hpp>
void Frustum::NormalizePlane(FrustumSide side) {
- float magnitude = (float)sqrt(frustum[side][A] * frustum[side][A] + frustum[side][B] * frustum[side][B] + frustum[side][C] * frustum[side][C]);
+ float magnitude = (float) sqrt(frustum[side][A] * frustum[side][A] + frustum[side][B] * frustum[side][B] + frustum[side][C] * frustum[side][C]);
frustum[side][A] /= magnitude;
frustum[side][B] /= magnitude;
diff --git a/src/GameState.cpp b/src/GameState.cpp
index 28e8007..6c2ad42 100644
--- a/src/GameState.cpp
+++ b/src/GameState.cpp
@@ -7,24 +7,30 @@
#include "Packet.hpp"
void GameState::Update(float deltaTime) {
- if (g_IsGameStarted) {
- std::chrono::steady_clock clock;
- static auto timeOfPreviousSendedPacket(clock.now());
+ if (g_IsGameStarted) {
+ std::chrono::steady_clock clock;
+ static auto timeOfPreviousSendedPacket(clock.now());
auto delta = clock.now() - timeOfPreviousSendedPacket;
- using namespace std::chrono_literals;
+ using namespace std::chrono_literals;
if (delta >= 50ms) {
- auto packetToSend = std::make_shared<PacketPlayerPositionAndLookSB>(player->pos.x, player->pos.y, player->pos.z, player->yaw, player->pitch, player->onGround);
+ auto packetToSend = std::make_shared<PacketPlayerPositionAndLookSB>(
+ player->pos.x, player->pos.y, player->pos.z,
+ player->yaw, player->pitch, player->onGround);
+
auto packet = std::static_pointer_cast<Packet>(packetToSend);
- PUSH_EVENT("SendPacket",packet);
+ PUSH_EVENT("SendPacket", packet);
timeOfPreviousSendedPacket = clock.now();
}
bool prevOnGround = player->onGround;
world.UpdatePhysics(deltaTime);
if (player->onGround != prevOnGround) {
- auto updatePacket = std::make_shared<PacketPlayerPosition>(player->pos.x, player->pos.y, player->pos.z, player->onGround);
+ auto updatePacket = std::make_shared<PacketPlayerPosition>(
+ player->pos.x, player->pos.y,
+ player->pos.z, player->onGround);
+
auto packet = std::static_pointer_cast<Packet>(updatePacket);
- PUSH_EVENT("SendPacket",packet);
+ PUSH_EVENT("SendPacket", packet);
}
@@ -37,15 +43,26 @@ void GameState::Update(float deltaTime) {
direction.z = sin(glm::radians(playerYaw)) * cos(glm::radians(playerPitch));
RaycastResult raycast = world.Raycast(player->pos + player->EyeOffset, direction);
- selectedBlock = raycast.isHit ? raycast.hitBlock : Vector(0,0,0);
- distanceToSelectedBlock = raycast.isHit ? (player->pos - raycast.hitPos).GetLength() : 0.0f;
+ if (raycast.isHit != isBlockSelected || ((raycast.isHit == true && isBlockSelected == true) &&
+ selectedBlock != raycast.hitBlock)) {
+ PUSH_EVENT("SelectedBlockChanged", 0);
+ }
+
+ if (raycast.isHit) {
+ selectedBlock = raycast.hitBlock;
+ distanceToSelectedBlock = (player->pos - raycast.hitPos).GetLength();
+ } else {
+ selectedBlock = Vector(0, 0, 0);
+ distanceToSelectedBlock = 0.0f;
+ }
+
+ isBlockSelected = raycast.isHit;
raycastHit = raycast.hitPos;
- }
+ }
}
-void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
-{
- switch ((PacketNamePlayCB)ptr->GetPacketId()) {
+void GameState::UpdatePacket(std::shared_ptr<Packet> ptr) {
+ switch ((PacketNamePlayCB) ptr->GetPacketId()) {
case SpawnObject: {
auto packet = std::static_pointer_cast<PacketSpawnObject>(ptr);
Entity entity = CreateObject(static_cast<ObjectType>(packet->Type));
@@ -60,10 +77,13 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
PUSH_EVENT("EntityChanged", entity.entityId);
break;
}
+
case SpawnExperienceOrb:
break;
+
case SpawnGlobalEntity:
break;
+
case SpawnMob: {
auto packet = std::static_pointer_cast<PacketSpawnMob>(ptr);
Entity entity;
@@ -78,8 +98,10 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
PUSH_EVENT("EntityChanged", entity.entityId);
break;
}
+
case SpawnPainting:
break;
+
case SpawnPlayer: {
auto packet = std::static_pointer_cast<PacketSpawnPlayer>(ptr);
Entity entity;
@@ -105,28 +127,33 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
break;
case BlockAction:
break;
+
case BlockChange: {
auto packet = std::static_pointer_cast<PacketBlockChange>(ptr);
world.ParseChunkData(packet);
break;
}
+
case BossBar:
break;
case ServerDifficulty:
break;
case TabCompleteCB:
break;
+
case ChatMessageCB: {
auto packet = std::static_pointer_cast<PacketChatMessageCB>(ptr);
LOG(INFO) << "Message (" << int(packet->Position) << "): " << packet->JsonData.text;
PUSH_EVENT("ChatMessageReceived", std::make_tuple(packet->JsonData, packet->Position));
break;
}
+
case MultiBlockChange: {
auto packet = std::static_pointer_cast<PacketMultiBlockChange>(ptr);
world.ParseChunkData(packet);
break;
}
+
case ConfirmTransactionCB: {
auto packet = std::static_pointer_cast<PacketConfirmTransactionCB>(ptr);
if (packet->WindowId == 0) {
@@ -138,14 +165,17 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
}
break;
}
+
case CloseWindowCB:
break;
+
case OpenWindow: {
auto packet = std::static_pointer_cast<PacketOpenWindow>(ptr);
LOG(INFO) << "Open new window " << packet->WindowTitle << ": " << packet->WindowId;
break;
}
+
case WindowItems: {
auto packet = std::static_pointer_cast<PacketWindowItems>(ptr);
if (packet->WindowId == 0) {
@@ -154,8 +184,10 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
}
break;
}
+
case WindowProperty:
break;
+
case SetSlot: {
auto packet = std::static_pointer_cast<PacketSetSlot>(ptr);
if (packet->WindowId == 0) {
@@ -163,41 +195,51 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
}
break;
}
+
case SetCooldown:
break;
case PluginMessageCB:
break;
case NamedSoundEffect:
break;
+
case DisconnectPlay: {
auto packet = std::static_pointer_cast<PacketDisconnectPlay>(ptr);
LOG(INFO) << "Disconnect reason: " << packet->Reason;
PUSH_EVENT("Disconnected", packet->Reason);
break;
}
+
case EntityStatus:
break;
case Explosion:
break;
+
case UnloadChunk: {
auto packet = std::static_pointer_cast<PacketUnloadChunk>(ptr);
world.ParseChunkData(packet);
break;
}
+
case ChangeGameState:
break;
- case KeepAliveCB:
+
+ case KeepAliveCB: {
LOG(WARNING) << "Receive KeepAlive packet in GameState handler";
break;
+ }
+
case ChunkData: {
auto packet = std::static_pointer_cast<PacketChunkData>(ptr);
world.ParseChunkData(packet);
break;
}
+
case Effect:
break;
case Particle:
break;
+
case JoinGame: {
auto packet = std::static_pointer_cast<PacketJoinGame>(ptr);
Entity entity;
@@ -219,8 +261,10 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
PUSH_EVENT("PlayerConnected", 0);
break;
}
+
case Map:
break;
+
case EntityRelativeMove: {
auto packet = std::static_pointer_cast<PacketEntityRelativeMove>(ptr);
Entity &entity = world.GetEntity(packet->EntityId);
@@ -229,6 +273,7 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
LOG(INFO) << "M: " << packet->EntityId;
break;
}
+
case EntityLookAndRelativeMove: {
auto packet = std::static_pointer_cast<PacketEntityLookAndRelativeMove>(ptr);
Entity &entity = world.GetEntity(packet->EntityId);
@@ -237,6 +282,7 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
entity.yaw = packet->Yaw / 256.0;
break;
}
+
case EntityLook: {
auto packet = std::static_pointer_cast<PacketEntityLook>(ptr);
Entity &entity = world.GetEntity(packet->EntityId);
@@ -245,6 +291,7 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
//LOG(INFO) << "L: " << packet->EntityId;
break;
}
+
case EntityCB:
break;
case VehicleMove:
@@ -257,13 +304,14 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
break;
case PlayerListItem:
break;
+
case PlayerPositionAndLookCB: {
auto packet = std::static_pointer_cast<PacketPlayerPositionAndLookCB>(ptr);
if ((packet->Flags & 0x10) != 0) {
player->pitch += packet->Pitch;
} else {
player->pitch = packet->Pitch;
- };
+ }
if ((packet->Flags & 0x08) != 0) {
player->yaw += packet->Yaw;
@@ -306,10 +354,12 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
PUSH_EVENT("SendPacket",std::static_pointer_cast<Packet>(packetPerformRespawn));
break;
}
+
case UseBed:
break;
case UnlockRecipes:
break;
+
case DestroyEntities: {
auto packet = std::static_pointer_cast<PacketDestroyEntities>(ptr);
for (unsigned int entityId : packet->EntityIds) {
@@ -317,6 +367,7 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
}
break;
}
+
case RemoveEntityEffect:
break;
case ResourcePackSend:
@@ -339,16 +390,19 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
break;
case AttachEntity:
break;
+
case EntityVelocity: {
auto packet = std::static_pointer_cast<PacketEntityVelocity>(ptr);
Entity &entity = world.GetEntity(packet->EntityId);
entity.vel = Entity::DecodeVelocity(packet->VelocityX, packet->VelocityY, packet->VelocityZ);
break;
}
+
case EntityEquipment:
break;
case SetExperience:
break;
+
case UpdateHealth: {
auto packet = std::static_pointer_cast<PacketUpdateHealth>(ptr);
g_PlayerHealth = packet->Health;
@@ -359,6 +413,7 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
}
break;
}
+
case ScoreboardObjective:
break;
case SetPassengers:
@@ -367,6 +422,7 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
break;
case UpdateScore:
break;
+
case SpawnPosition: {
auto packet = std::static_pointer_cast<PacketSpawnPosition>(ptr);
g_SpawnPosition = packet->Location;
@@ -374,12 +430,14 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
<< g_SpawnPosition.z;
break;
}
+
case TimeUpdate: {
auto packet = std::static_pointer_cast<PacketTimeUpdate>(ptr);
WorldAge = packet->WorldAge;
TimeOfDay = packet->TimeOfDay;
break;
}
+
case Title:
break;
case SoundEffect:
@@ -388,6 +446,7 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
break;
case CollectItem:
break;
+
case EntityTeleport: {
auto packet = std::static_pointer_cast<PacketEntityTeleport>(ptr);
Entity &entity = world.GetEntity(packet->EntityId);
@@ -396,6 +455,7 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
entity.yaw = packet->Yaw / 256.0;
break;
}
+
case Advancements:
break;
case EntityProperties:
@@ -403,6 +463,7 @@ void GameState::UpdatePacket(std::shared_ptr<Packet> ptr)
case EntityEffect:
break;
}
+
while (!playerInventory.pendingTransactions.empty()) {
auto packet = std::make_shared<PacketClickWindow>(playerInventory.pendingTransactions.front());
playerInventory.pendingTransactions.pop();
@@ -431,25 +492,33 @@ void GameState::HandleMovement(GameState::Direction direction, float deltaTime)
glm::vec3 vel = player->vel.glm();
switch (direction) {
- case FORWARD:
- vel += front * velocity;
- break;
- case BACKWARD:
- vel -= front * velocity;
- break;
- case RIGHT:
- vel += right * velocity;
- break;
- case LEFT:
- vel -= right * velocity;
- break;
- case JUMP:
- if (player->onGround) {
- vel.y += 10;
- player->onGround = false;
- }
- break;
- }
+ case FORWARD: {
+ vel += front * velocity;
+ break;
+ }
+
+ case BACKWARD: {
+ vel -= front * velocity;
+ break;
+ }
+
+ case RIGHT: {
+ vel += right * velocity;
+ break;
+ }
+
+ case LEFT: {
+ vel -= right * velocity;
+ break;
+ }
+
+ case JUMP:
+ if (player->onGround) {
+ vel.y += 10;
+ player->onGround = false;
+ }
+ break;
+ }
player->vel = VectorF(vel.x, vel.y, vel.z);
}
@@ -485,15 +554,75 @@ glm::mat4 GameState::GetViewMatrix() {
return glm::lookAt(eyePos, eyePos + front, up);
}
+// TODO: it should actually be something like this:
+// function start_digging():
+// send_packet(packet_type=start_digging_packet)
+// delay(time=selected_block_dig_time, action=finish_digging)
void GameState::StartDigging() {
+ if (!isBlockSelected)
+ return;
+
auto packetStart = std::make_shared<PacketPlayerDigging>(0,selectedBlock,1);
- auto packetStop = std::make_shared<PacketPlayerDigging>(2,selectedBlock,1);
auto packet = std::static_pointer_cast<Packet>(packetStart);
PUSH_EVENT("SendPacket",packet);
- packet = std::static_pointer_cast<Packet>(packetStop);
+
+ FinishDigging();
+}
+
+void GameState::FinishDigging() {
+ auto packetFinish = std::make_shared<PacketPlayerDigging>(2,selectedBlock,1);
+ auto packet = std::static_pointer_cast<Packet>(packetFinish);
PUSH_EVENT("SendPacket",packet);
}
-void GameState::StopDigging() {
+// TODO: it should actually be something like this:
+// function cancel_digging():
+// if finish_digging is in delayed_actions:
+// send_packet(packet_type=start_digging_packet)
+// remove_delayed_action(finish_digging)
+void GameState::CancelDigging() {
+ auto packetCancel = std::make_shared<PacketPlayerDigging>(1,selectedBlock,1);
+ auto packet = std::static_pointer_cast<Packet>(packetCancel);
+ PUSH_EVENT("SendPacket", packet);
+}
+
+BlockFacing detectHitFace(VectorF raycastHit, Vector selectedBlock) {
+ auto vec = VectorF(selectedBlock.x + .5, selectedBlock.y + .5, selectedBlock.z +.5) - raycastHit;
+
+ // TODO: move these vectors to Vector.hpp
+ static const auto vecUp = VectorF(0, 1, 0);
+ static const auto vecRight = VectorF(1, 0, 0);
+ static const auto vecForward = VectorF(0, 0, -1);
+ const double up = vec.cosBetween(vecUp);
+ const double down = -up;
+ const double right = vec.cosBetween(vecRight);
+ const double left = -right;
+ const double forward = vec.cosBetween(vecForward);
+ const double backward = -forward;
+
+ const double min_cos = _min(up, down, right, left, forward, backward);
+ if (min_cos == down)
+ return BlockFacing::Bottom;
+ else if (min_cos == up)
+ return BlockFacing::Top;
+ else if (min_cos == forward)
+ return BlockFacing::North;
+ else if (min_cos == backward)
+ return BlockFacing::South;
+ else if (min_cos == left)
+ return BlockFacing::West;
+ else return BlockFacing::East;
}
+
+void GameState::PlaceBlock() {
+ if (!isBlockSelected)
+ return;
+
+ BlockFacing face = detectHitFace(raycastHit, selectedBlock);
+ auto packetPlace = std::make_shared<PacketPlayerBlockPlacement>(
+ selectedBlock, (unsigned char) face, 0, 0, 0, 0);
+
+ auto packet = std::static_pointer_cast<Packet>(packetPlace);
+ PUSH_EVENT("SendPacket", packet);
+} \ No newline at end of file
diff --git a/src/GameState.hpp b/src/GameState.hpp
index fac9923..81ab3dc 100644
--- a/src/GameState.hpp
+++ b/src/GameState.hpp
@@ -20,40 +20,42 @@ public:
~GameState() = default;
- void Update(float deltaTime);
+ void Update(float deltaTime);
void UpdatePacket(std::shared_ptr<Packet> ptr);
- enum Direction {
- FORWARD, BACKWARD, LEFT, RIGHT, JUMP
- };
- void StartDigging();
- void StopDigging();
- void HandleMovement(GameState::Direction direction, float deltaTime);
- void HandleRotation(double yaw, double pitch);
- glm::mat4 GetViewMatrix();
+ enum Direction {
+ FORWARD, BACKWARD, LEFT, RIGHT, JUMP
+ };
+ void StartDigging();
+ void FinishDigging();
+ void CancelDigging();
+ void PlaceBlock();
+ void HandleMovement(GameState::Direction direction, float deltaTime);
+ void HandleRotation(double yaw, double pitch);
+ glm::mat4 GetViewMatrix();
Entity* player;
- World world;
+ World world;
- std::string g_PlayerUuid = "";
- std::string g_PlayerName = "";
- bool g_IsGameStarted = false;
- int g_PlayerEid = 0;
- int g_Gamemode = 0;
- int g_Dimension = 0;
- unsigned char g_Difficulty = 0;
- unsigned char g_MaxPlayers = 0;
- std::string g_LevelType = "";
- bool g_ReducedDebugInfo = false;
- Vector g_SpawnPosition;
- bool g_PlayerInvulnerable = false;
- bool g_PlayerFlying = false;
- bool g_PlayerAllowFlying = false;
- bool g_PlayerCreativeMode = false;
- float g_PlayerFlyingSpeed = 0;
- float g_PlayerFovModifier = 0;
- float g_PlayerHealth = 0;
+ std::string g_PlayerUuid = "";
+ std::string g_PlayerName = "";
+ bool g_IsGameStarted = false;
+ int g_PlayerEid = 0;
+ int g_Gamemode = 0;
+ int g_Dimension = 0;
+ unsigned char g_Difficulty = 0;
+ unsigned char g_MaxPlayers = 0;
+ std::string g_LevelType = "";
+ bool g_ReducedDebugInfo = false;
+ Vector g_SpawnPosition;
+ bool g_PlayerInvulnerable = false;
+ bool g_PlayerFlying = false;
+ bool g_PlayerAllowFlying = false;
+ bool g_PlayerCreativeMode = false;
+ float g_PlayerFlyingSpeed = 0;
+ float g_PlayerFovModifier = 0;
+ float g_PlayerHealth = 0;
long long WorldAge = 0;
long long TimeOfDay = 0;
@@ -61,7 +63,8 @@ public:
Window playerInventory;
std::vector<Window> openedWindows;
- Vector selectedBlock;
- float distanceToSelectedBlock;
- VectorF raycastHit;
+ bool isBlockSelected;
+ Vector selectedBlock;
+ float distanceToSelectedBlock;
+ VectorF raycastHit;
};
diff --git a/src/GlobalState.cpp b/src/GlobalState.cpp
index ce8cb05..8d75bac 100644
--- a/src/GlobalState.cpp
+++ b/src/GlobalState.cpp
@@ -42,9 +42,10 @@ void InitEvents() {
isPhysRunning = true;
threadPhys = std::thread(&PhysExec);
try {
- nc = std::make_unique<NetworkClient>(std::get<0>(data), std::get<1>(data), std::get<2>(data));
- }
- catch (std::exception &e) {
+ nc = std::make_unique<NetworkClient>(std::get<0>(data),
+ std::get<1>(data),
+ std::get<2>(data));
+ } catch (std::exception &e) {
LOG(WARNING) << "Connection failed";
PUSH_EVENT("ConnectionFailed", std::string(e.what()));
isPhysRunning = false;
@@ -98,47 +99,47 @@ void PhysExec() {
if (!gs)
return;
switch (eventData.get<SDL_Scancode>()) {
- case SDL_SCANCODE_W:
- isMoving[GameState::FORWARD] = true;
- break;
- case SDL_SCANCODE_A:
- isMoving[GameState::LEFT] = true;
- break;
- case SDL_SCANCODE_S:
- isMoving[GameState::BACKWARD] = true;
- break;
- case SDL_SCANCODE_D:
- isMoving[GameState::RIGHT] = true;
- break;
- case SDL_SCANCODE_SPACE:
- isMoving[GameState::JUMP] = true;
- break;
- default:
- break;
- }
+ case SDL_SCANCODE_W:
+ isMoving[GameState::FORWARD] = true;
+ break;
+ case SDL_SCANCODE_A:
+ isMoving[GameState::LEFT] = true;
+ break;
+ case SDL_SCANCODE_S:
+ isMoving[GameState::BACKWARD] = true;
+ break;
+ case SDL_SCANCODE_D:
+ isMoving[GameState::RIGHT] = true;
+ break;
+ case SDL_SCANCODE_SPACE:
+ isMoving[GameState::JUMP] = true;
+ break;
+ default:
+ break;
+ }
});
listener.RegisterHandler("KeyReleased", [](const Event& eventData) {
if (!gs)
return;
switch (eventData.get<SDL_Scancode>()) {
- case SDL_SCANCODE_W:
- isMoving[GameState::FORWARD] = false;
- break;
- case SDL_SCANCODE_A:
- isMoving[GameState::LEFT] = false;
- break;
- case SDL_SCANCODE_S:
- isMoving[GameState::BACKWARD] = false;
- break;
- case SDL_SCANCODE_D:
- isMoving[GameState::RIGHT] = false;
- break;
- case SDL_SCANCODE_SPACE:
- isMoving[GameState::JUMP] = false;
- break;
- default:
- break;
+ case SDL_SCANCODE_W:
+ isMoving[GameState::FORWARD] = false;
+ break;
+ case SDL_SCANCODE_A:
+ isMoving[GameState::LEFT] = false;
+ break;
+ case SDL_SCANCODE_S:
+ isMoving[GameState::BACKWARD] = false;
+ break;
+ case SDL_SCANCODE_D:
+ isMoving[GameState::RIGHT] = false;
+ break;
+ case SDL_SCANCODE_SPACE:
+ isMoving[GameState::JUMP] = false;
+ break;
+ default:
+ break;
}
});
@@ -159,7 +160,16 @@ void PhysExec() {
});
listener.RegisterHandler("LmbReleased",[](const Event& eventData) {
- gs->StopDigging();
+ gs->CancelDigging();
+ });
+
+ listener.RegisterHandler("RmbPressed", [](const Event& eventData) {
+ gs->PlaceBlock();
+ });
+
+ listener.RegisterHandler("SelectedBlockChanged", [](const Event& eventData) {
+ //TODO:
+ //gs->CancelDigging();
});
LoopExecutionTimeController timer(std::chrono::milliseconds(8));
diff --git a/src/Packet.hpp b/src/Packet.hpp
index 1920ea6..7b18ce1 100644
--- a/src/Packet.hpp
+++ b/src/Packet.hpp
@@ -3,520 +3,520 @@
#include "Stream.hpp"
enum PacketNameLoginSB {
- LoginStart = 0x00,
- EncryptionResponse = 0x01,
+ LoginStart = 0x00,
+ EncryptionResponse = 0x01,
};
enum PacketNamePlaySB {
- TeleportConfirm = 0x00,
- TabCompleteSB,
- ChatMessageSB,
- ClientStatus,
- ClientSettings,
- ConfirmTransactionSB,
- EnchantItem,
- ClickWindow,
- CloseWindowSB,
- PluginMessageSB,
- UseEntity,
- KeepAliveSB,
- Player,
- PlayerPosition,
- PlayerPositionAndLookSB,
- PlayerLook,
- VehicleMoveSB,
- SteerBoat,
+ TeleportConfirm = 0x00,
+ TabCompleteSB,
+ ChatMessageSB,
+ ClientStatus,
+ ClientSettings,
+ ConfirmTransactionSB,
+ EnchantItem,
+ ClickWindow,
+ CloseWindowSB,
+ PluginMessageSB,
+ UseEntity,
+ KeepAliveSB,
+ Player,
+ PlayerPosition,
+ PlayerPositionAndLookSB,
+ PlayerLook,
+ VehicleMoveSB,
+ SteerBoat,
CraftRecipeRequest,
- PlayerAbilitiesSB,
- PlayerDigging,
- EntityAction,
- SteerVehicle,
- CraftingBookData,
- ResourcePackStatus,
- AdvancementTab,
- HeldItemChangeSB,
- CreativeInventoryAction,
- UpdateSign,
- AnimationSB,
- Spectate,
- PlayerBlockPlacement,
- UseItem,
+ PlayerAbilitiesSB,
+ PlayerDigging,
+ EntityAction,
+ SteerVehicle,
+ CraftingBookData,
+ ResourcePackStatus,
+ AdvancementTab,
+ HeldItemChangeSB,
+ CreativeInventoryAction,
+ UpdateSign,
+ AnimationSB,
+ Spectate,
+ PlayerBlockPlacement,
+ UseItem,
};
enum PacketNameHandshakingCB {
- Handshake = 0x00,
+ Handshake = 0x00,
};
enum PacketNameLoginCB {
- Disconnect = 0x00,
- EncryptionRequest = 0x01,
- LoginSuccess = 0x02,
- SetCompression = 0x03,
+ Disconnect = 0x00,
+ EncryptionRequest = 0x01,
+ LoginSuccess = 0x02,
+ SetCompression = 0x03,
};
enum PacketNamePlayCB {
- SpawnObject = 0x00,
- SpawnExperienceOrb,
- SpawnGlobalEntity,
- SpawnMob,
- SpawnPainting,
- SpawnPlayer,
- AnimationCB,
- Statistics,
- BlockBreakAnimation,
- UpdateBlockEntity,
- BlockAction,
- BlockChange,
- BossBar,
- ServerDifficulty,
- TabCompleteCB,
- ChatMessageCB,
- MultiBlockChange,
- ConfirmTransactionCB,
- CloseWindowCB,
- OpenWindow,
- WindowItems,
- WindowProperty,
- SetSlot,
- SetCooldown,
- PluginMessageCB,
- NamedSoundEffect,
- DisconnectPlay,
- EntityStatus,
- Explosion,
- UnloadChunk,
- ChangeGameState,
- KeepAliveCB,
- ChunkData,
- Effect,
- Particle,
- JoinGame,
- Map,
- EntityRelativeMove,
- EntityLookAndRelativeMove,
- EntityLook,
- EntityCB,
- VehicleMove,
- OpenSignEditor,
+ SpawnObject = 0x00,
+ SpawnExperienceOrb,
+ SpawnGlobalEntity,
+ SpawnMob,
+ SpawnPainting,
+ SpawnPlayer,
+ AnimationCB,
+ Statistics,
+ BlockBreakAnimation,
+ UpdateBlockEntity,
+ BlockAction,
+ BlockChange,
+ BossBar,
+ ServerDifficulty,
+ TabCompleteCB,
+ ChatMessageCB,
+ MultiBlockChange,
+ ConfirmTransactionCB,
+ CloseWindowCB,
+ OpenWindow,
+ WindowItems,
+ WindowProperty,
+ SetSlot,
+ SetCooldown,
+ PluginMessageCB,
+ NamedSoundEffect,
+ DisconnectPlay,
+ EntityStatus,
+ Explosion,
+ UnloadChunk,
+ ChangeGameState,
+ KeepAliveCB,
+ ChunkData,
+ Effect,
+ Particle,
+ JoinGame,
+ Map,
+ EntityRelativeMove,
+ EntityLookAndRelativeMove,
+ EntityLook,
+ EntityCB,
+ VehicleMove,
+ OpenSignEditor,
CraftRecipeResponse,
- PlayerAbilitiesCB,
- CombatEvent,
- PlayerListItem,
- PlayerPositionAndLookCB,
- UseBed,
- UnlockRecipes,
- DestroyEntities,
- RemoveEntityEffect,
- ResourcePackSend,
- Respawn,
- EntityHeadLook,
- SelectAdvancementTab,
- WorldBorder,
- Camera,
- HeldItemChangeCB,
- DisplayScoreboard,
- EntityMetadata,
- AttachEntity,
- EntityVelocity,
- EntityEquipment,
- SetExperience,
- UpdateHealth,
- ScoreboardObjective,
- SetPassengers,
- Teams,
- UpdateScore,
- SpawnPosition,
- TimeUpdate,
- Title,
- SoundEffect,
- PlayerListHeaderAndFooter,
- CollectItem,
- EntityTeleport,
- Advancements,
- EntityProperties,
- EntityEffect,
+ PlayerAbilitiesCB,
+ CombatEvent,
+ PlayerListItem,
+ PlayerPositionAndLookCB,
+ UseBed,
+ UnlockRecipes,
+ DestroyEntities,
+ RemoveEntityEffect,
+ ResourcePackSend,
+ Respawn,
+ EntityHeadLook,
+ SelectAdvancementTab,
+ WorldBorder,
+ Camera,
+ HeldItemChangeCB,
+ DisplayScoreboard,
+ EntityMetadata,
+ AttachEntity,
+ EntityVelocity,
+ EntityEquipment,
+ SetExperience,
+ UpdateHealth,
+ ScoreboardObjective,
+ SetPassengers,
+ Teams,
+ UpdateScore,
+ SpawnPosition,
+ TimeUpdate,
+ Title,
+ SoundEffect,
+ PlayerListHeaderAndFooter,
+ CollectItem,
+ EntityTeleport,
+ Advancements,
+ EntityProperties,
+ EntityEffect,
};
struct Packet {
- virtual ~Packet() = default;
- virtual void ToStream(StreamOutput *stream) = 0;
- virtual void FromStream(StreamInput *stream) = 0;
- virtual int GetPacketId() = 0;
+ virtual ~Packet() = default;
+ virtual void ToStream(StreamOutput *stream) = 0;
+ virtual void FromStream(StreamInput *stream) = 0;
+ virtual int GetPacketId() = 0;
};
struct PacketHandshake : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteVarInt(protocolVersion);
- stream->WriteString(serverAddress);
- stream->WriteUShort(serverPort);
- stream->WriteVarInt(nextState);
- }
-
- void FromStream(StreamInput *stream) override {
- protocolVersion = stream->ReadVarInt();
- serverAddress = stream->ReadString();
- serverPort = stream->ReadUShort();
- nextState = stream->ReadVarInt();
- }
-
- int GetPacketId() override {
- return PacketNameHandshakingCB::Handshake;
- }
-
- int protocolVersion;
- std::string serverAddress;
- unsigned short serverPort;
- int nextState;
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteVarInt(protocolVersion);
+ stream->WriteString(serverAddress);
+ stream->WriteUShort(serverPort);
+ stream->WriteVarInt(nextState);
+ }
+
+ void FromStream(StreamInput *stream) override {
+ protocolVersion = stream->ReadVarInt();
+ serverAddress = stream->ReadString();
+ serverPort = stream->ReadUShort();
+ nextState = stream->ReadVarInt();
+ }
+
+ int GetPacketId() override {
+ return PacketNameHandshakingCB::Handshake;
+ }
+
+ int protocolVersion;
+ std::string serverAddress;
+ unsigned short serverPort;
+ int nextState;
};
struct PacketLoginStart : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteString(Username);
- }
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteString(Username);
+ }
- void FromStream(StreamInput *stream) override {
- Username = stream->ReadString();
- }
+ void FromStream(StreamInput *stream) override {
+ Username = stream->ReadString();
+ }
- int GetPacketId() override {
- return PacketNameLoginSB::LoginStart;
- }
+ int GetPacketId() override {
+ return PacketNameLoginSB::LoginStart;
+ }
- std::string Username;
+ std::string Username;
};
struct PacketLoginSuccess : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteString(Uuid);
- stream->WriteString(Username);
- }
-
- void FromStream(StreamInput *stream) override {
- Uuid = stream->ReadString();
- Username = stream->ReadString();
- }
-
- int GetPacketId() override {
- return PacketNameLoginCB::LoginSuccess;
- }
-
- std::string Uuid;
- std::string Username;
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteString(Uuid);
+ stream->WriteString(Username);
+ }
+
+ void FromStream(StreamInput *stream) override {
+ Uuid = stream->ReadString();
+ Username = stream->ReadString();
+ }
+
+ int GetPacketId() override {
+ return PacketNameLoginCB::LoginSuccess;
+ }
+
+ std::string Uuid;
+ std::string Username;
};
struct PacketJoinGame : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteInt(EntityId);
- stream->WriteUByte(Gamemode);
- stream->WriteInt(Dimension);
- stream->WriteUByte(Difficulty);
- stream->WriteUByte(MaxPlayers);
- stream->WriteString(LevelType);
- stream->WriteBool(ReducedDebugInfo);
- }
-
- void FromStream(StreamInput *stream) override {
- EntityId = stream->ReadInt();
- Gamemode = stream->ReadUByte();
- Dimension = stream->ReadInt();
- Difficulty = stream->ReadUByte();
- MaxPlayers = stream->ReadUByte();
- LevelType = stream->ReadString();
- ReducedDebugInfo = stream->ReadBool();
- }
-
- int GetPacketId() override {
- return PacketNamePlayCB::JoinGame;
- }
-
- int EntityId;
- unsigned char Gamemode;
- int Dimension;
- unsigned char Difficulty;
- unsigned char MaxPlayers;
- std::string LevelType;
- bool ReducedDebugInfo;
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteInt(EntityId);
+ stream->WriteUByte(Gamemode);
+ stream->WriteInt(Dimension);
+ stream->WriteUByte(Difficulty);
+ stream->WriteUByte(MaxPlayers);
+ stream->WriteString(LevelType);
+ stream->WriteBool(ReducedDebugInfo);
+ }
+
+ void FromStream(StreamInput *stream) override {
+ EntityId = stream->ReadInt();
+ Gamemode = stream->ReadUByte();
+ Dimension = stream->ReadInt();
+ Difficulty = stream->ReadUByte();
+ MaxPlayers = stream->ReadUByte();
+ LevelType = stream->ReadString();
+ ReducedDebugInfo = stream->ReadBool();
+ }
+
+ int GetPacketId() override {
+ return PacketNamePlayCB::JoinGame;
+ }
+
+ int EntityId;
+ unsigned char Gamemode;
+ int Dimension;
+ unsigned char Difficulty;
+ unsigned char MaxPlayers;
+ std::string LevelType;
+ bool ReducedDebugInfo;
};
struct PacketDisconnectPlay : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteString(Reason); //TODO: Implement chat-wrapper
- }
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteString(Reason); //TODO: Implement chat-wrapper
+ }
- void FromStream(StreamInput *stream) override {
- Reason = stream->ReadChat().text;
- }
+ void FromStream(StreamInput *stream) override {
+ Reason = stream->ReadChat().text;
+ }
- int GetPacketId() override {
- return PacketNamePlayCB::DisconnectPlay;
- }
+ int GetPacketId() override {
+ return PacketNamePlayCB::DisconnectPlay;
+ }
- std::string Reason;
+ std::string Reason;
};
struct PacketSpawnPosition : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WritePosition(Location);
- }
+ void ToStream(StreamOutput *stream) override {
+ stream->WritePosition(Location);
+ }
- void FromStream(StreamInput *stream) override {
- Location = stream->ReadPosition();
- }
+ void FromStream(StreamInput *stream) override {
+ Location = stream->ReadPosition();
+ }
- int GetPacketId() override {
- return PacketNamePlayCB::SpawnPosition;
- }
+ int GetPacketId() override {
+ return PacketNamePlayCB::SpawnPosition;
+ }
- Vector Location;
+ Vector Location;
};
struct PacketKeepAliveCB : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteLong(KeepAliveId);
- }
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteLong(KeepAliveId);
+ }
- void FromStream(StreamInput *stream) override {
- KeepAliveId = stream->ReadLong();
- }
+ void FromStream(StreamInput *stream) override {
+ KeepAliveId = stream->ReadLong();
+ }
- int GetPacketId() override {
- return PacketNamePlayCB::KeepAliveCB;
- }
+ int GetPacketId() override {
+ return PacketNamePlayCB::KeepAliveCB;
+ }
- long long KeepAliveId;
+ long long KeepAliveId;
};
struct PacketKeepAliveSB : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteLong(KeepAliveId);
- }
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteLong(KeepAliveId);
+ }
- void FromStream(StreamInput *stream) override {
- KeepAliveId = stream->ReadLong();
- }
+ void FromStream(StreamInput *stream) override {
+ KeepAliveId = stream->ReadLong();
+ }
- int GetPacketId() override {
- return PacketNamePlaySB::KeepAliveSB;
- }
+ int GetPacketId() override {
+ return PacketNamePlaySB::KeepAliveSB;
+ }
- long long KeepAliveId;
+ long long KeepAliveId;
- PacketKeepAliveSB(int KeepAliveId) : KeepAliveId(KeepAliveId) {}
+ PacketKeepAliveSB(int KeepAliveId) : KeepAliveId(KeepAliveId) {}
};
struct PacketPlayerPositionAndLookCB : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteDouble(X);
- stream->WriteDouble(Y);
- stream->WriteDouble(Z);
- stream->WriteFloat(Yaw);
- stream->WriteFloat(Pitch);
- stream->WriteUByte(Flags);
- stream->WriteVarInt(TeleportId);
- }
-
- void FromStream(StreamInput *stream) override {
- X = stream->ReadDouble();
- Y = stream->ReadDouble();
- Z = stream->ReadDouble();
- Yaw = stream->ReadFloat();
- Pitch = stream->ReadFloat();
- Flags = stream->ReadUByte();
- TeleportId = stream->ReadVarInt();
- }
-
- int GetPacketId() override {
- return PacketNamePlayCB::PlayerPositionAndLookCB;
- }
-
- double X;
- double Y;
- double Z;
- float Yaw;
- float Pitch;
- unsigned char Flags;
- int TeleportId;
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteDouble(X);
+ stream->WriteDouble(Y);
+ stream->WriteDouble(Z);
+ stream->WriteFloat(Yaw);
+ stream->WriteFloat(Pitch);
+ stream->WriteUByte(Flags);
+ stream->WriteVarInt(TeleportId);
+ }
+
+ void FromStream(StreamInput *stream) override {
+ X = stream->ReadDouble();
+ Y = stream->ReadDouble();
+ Z = stream->ReadDouble();
+ Yaw = stream->ReadFloat();
+ Pitch = stream->ReadFloat();
+ Flags = stream->ReadUByte();
+ TeleportId = stream->ReadVarInt();
+ }
+
+ int GetPacketId() override {
+ return PacketNamePlayCB::PlayerPositionAndLookCB;
+ }
+
+ double X;
+ double Y;
+ double Z;
+ float Yaw;
+ float Pitch;
+ unsigned char Flags;
+ int TeleportId;
};
struct PacketTeleportConfirm : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteVarInt(TeleportId);
- }
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteVarInt(TeleportId);
+ }
- void FromStream(StreamInput *stream) override {
- TeleportId = stream->ReadVarInt();
- }
+ void FromStream(StreamInput *stream) override {
+ TeleportId = stream->ReadVarInt();
+ }
- int GetPacketId() override {
- return PacketNamePlaySB::TeleportConfirm;
- }
+ int GetPacketId() override {
+ return PacketNamePlaySB::TeleportConfirm;
+ }
- int TeleportId;
+ int TeleportId;
- PacketTeleportConfirm(int TeleportId) : TeleportId(TeleportId) {}
+ PacketTeleportConfirm(int TeleportId) : TeleportId(TeleportId) {}
};
struct PacketClientStatus : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteVarInt(ActionId);
- }
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteVarInt(ActionId);
+ }
- void FromStream(StreamInput *stream) override {
- ActionId = stream->ReadVarInt();
- }
+ void FromStream(StreamInput *stream) override {
+ ActionId = stream->ReadVarInt();
+ }
- int GetPacketId() override {
- return PacketNamePlaySB::ClientStatus;
- }
+ int GetPacketId() override {
+ return PacketNamePlaySB::ClientStatus;
+ }
- int ActionId;
+ int ActionId;
- PacketClientStatus(int ActionId) : ActionId(ActionId) {}
+ PacketClientStatus(int ActionId) : ActionId(ActionId) {}
};
struct PacketPlayerPositionAndLookSB : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteDouble(X);
- stream->WriteDouble(FeetY);
- stream->WriteDouble(Z);
- stream->WriteFloat(Yaw);
- stream->WriteFloat(Pitch);
- stream->WriteBool(OnGround);
- }
-
- void FromStream(StreamInput *stream) override {
- X = stream->ReadDouble();
- FeetY = stream->ReadDouble();
- Z = stream->ReadDouble();
- Yaw = stream->ReadFloat();
- Pitch = stream->ReadFloat();
- OnGround = stream->ReadBool();
- }
-
- int GetPacketId() override {
- return PacketNamePlaySB::PlayerPositionAndLookSB;
- }
-
-
- double X;
- double FeetY;
- double Z;
- float Yaw;
- float Pitch;
- bool OnGround;
-
- PacketPlayerPositionAndLookSB(double X, double FeetY, double Z,
- float Yaw, float Pitch, bool OnGround) : X(X), FeetY(FeetY), Z(Z), Yaw(Yaw),
- Pitch(Pitch), OnGround(OnGround) {}
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteDouble(X);
+ stream->WriteDouble(FeetY);
+ stream->WriteDouble(Z);
+ stream->WriteFloat(Yaw);
+ stream->WriteFloat(Pitch);
+ stream->WriteBool(OnGround);
+ }
+
+ void FromStream(StreamInput *stream) override {
+ X = stream->ReadDouble();
+ FeetY = stream->ReadDouble();
+ Z = stream->ReadDouble();
+ Yaw = stream->ReadFloat();
+ Pitch = stream->ReadFloat();
+ OnGround = stream->ReadBool();
+ }
+
+ int GetPacketId() override {
+ return PacketNamePlaySB::PlayerPositionAndLookSB;
+ }
+
+
+ double X;
+ double FeetY;
+ double Z;
+ float Yaw;
+ float Pitch;
+ bool OnGround;
+
+ PacketPlayerPositionAndLookSB(double X, double FeetY, double Z,
+ float Yaw, float Pitch, bool OnGround) : X(X), FeetY(FeetY), Z(Z), Yaw(Yaw),
+ Pitch(Pitch), OnGround(OnGround) {}
};
struct PacketChunkData : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteInt(ChunkX);
- stream->WriteInt(ChunkZ);
- stream->WriteBool(GroundUpContinuous);
- stream->WriteInt(PrimaryBitMask);
- stream->WriteVarInt(Data.size());
- stream->WriteByteArray(Data);
- stream->WriteVarInt(BlockEntities.size());
- //LOG(FATAL) << "Serializing unimplemented packet";
- }
-
- void FromStream(StreamInput *stream) override {
- ChunkX = stream->ReadInt();
- ChunkZ = stream->ReadInt();
- GroundUpContinuous = stream->ReadBool();
- PrimaryBitMask = stream->ReadVarInt();
- int Size = stream->ReadVarInt();
- Data = stream->ReadByteArray(Size);
- int NumberOfBlockEntities = stream->ReadVarInt(); //TODO: Need NBT
- for (int i = 0; i < NumberOfBlockEntities; i++) {
- //BlockEntities[i] = stream->ReadNbt();
- }
- }
-
- int GetPacketId() override {
- return PacketNamePlayCB::ChunkData;
- }
-
- int ChunkX;
- int ChunkZ;
- bool GroundUpContinuous;
- int PrimaryBitMask;
- //int Size;
- std::vector<unsigned char> Data;
- //int NumberOfBlockEntities;
- std::vector<int> BlockEntities; //TODO: Replace int with NbtTag and implement NbtTree
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteInt(ChunkX);
+ stream->WriteInt(ChunkZ);
+ stream->WriteBool(GroundUpContinuous);
+ stream->WriteInt(PrimaryBitMask);
+ stream->WriteVarInt(Data.size());
+ stream->WriteByteArray(Data);
+ stream->WriteVarInt(BlockEntities.size());
+ //LOG(FATAL) << "Serializing unimplemented packet";
+ }
+
+ void FromStream(StreamInput *stream) override {
+ ChunkX = stream->ReadInt();
+ ChunkZ = stream->ReadInt();
+ GroundUpContinuous = stream->ReadBool();
+ PrimaryBitMask = stream->ReadVarInt();
+ int Size = stream->ReadVarInt();
+ Data = stream->ReadByteArray(Size);
+ int NumberOfBlockEntities = stream->ReadVarInt(); //TODO: Need NBT
+ for (int i = 0; i < NumberOfBlockEntities; i++) {
+ //BlockEntities[i] = stream->ReadNbt();
+ }
+ }
+
+ int GetPacketId() override {
+ return PacketNamePlayCB::ChunkData;
+ }
+
+ int ChunkX;
+ int ChunkZ;
+ bool GroundUpContinuous;
+ int PrimaryBitMask;
+ //int Size;
+ std::vector<unsigned char> Data;
+ //int NumberOfBlockEntities;
+ std::vector<int> BlockEntities; //TODO: Replace int with NbtTag and implement NbtTree
};
struct PacketPlayerPosition : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteDouble(X);
- stream->WriteDouble(FeetY);
- stream->WriteDouble(Z);
- stream->WriteBool(OnGround);
- }
-
- void FromStream(StreamInput *stream) override {
- X = stream->ReadDouble();
- FeetY = stream->ReadDouble();
- Z = stream->ReadDouble();
- OnGround = stream->ReadBool();
- }
-
- int GetPacketId() override {
- return PacketNamePlaySB::PlayerPosition;
- }
-
- double X;
- double FeetY;
- double Z;
- bool OnGround;
-
- PacketPlayerPosition(double X, double Y, double Z, bool ground) : X(X), FeetY(Y), Z(Z), OnGround(ground) {}
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteDouble(X);
+ stream->WriteDouble(FeetY);
+ stream->WriteDouble(Z);
+ stream->WriteBool(OnGround);
+ }
+
+ void FromStream(StreamInput *stream) override {
+ X = stream->ReadDouble();
+ FeetY = stream->ReadDouble();
+ Z = stream->ReadDouble();
+ OnGround = stream->ReadBool();
+ }
+
+ int GetPacketId() override {
+ return PacketNamePlaySB::PlayerPosition;
+ }
+
+ double X;
+ double FeetY;
+ double Z;
+ bool OnGround;
+
+ PacketPlayerPosition(double X, double Y, double Z, bool ground) : X(X), FeetY(Y), Z(Z), OnGround(ground) {}
};
struct PacketPlayerLook : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteFloat(Yaw);
- stream->WriteFloat(Pitch);
- stream->WriteBool(OnGround);
- }
-
- void FromStream(StreamInput *stream) override {
- Yaw = stream->ReadFloat();
- Pitch = stream->ReadFloat();
- OnGround = stream->ReadBool();
- }
-
- int GetPacketId() override {
- return PacketNamePlaySB::PlayerLook;
- }
-
- float Yaw;
- float Pitch;
- bool OnGround;
-
- PacketPlayerLook(float Yaw, float Pitch, bool ground) : Yaw(Yaw), Pitch(Pitch), OnGround(ground) {}
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteFloat(Yaw);
+ stream->WriteFloat(Pitch);
+ stream->WriteBool(OnGround);
+ }
+
+ void FromStream(StreamInput *stream) override {
+ Yaw = stream->ReadFloat();
+ Pitch = stream->ReadFloat();
+ OnGround = stream->ReadBool();
+ }
+
+ int GetPacketId() override {
+ return PacketNamePlaySB::PlayerLook;
+ }
+
+ float Yaw;
+ float Pitch;
+ bool OnGround;
+
+ PacketPlayerLook(float Yaw, float Pitch, bool ground) : Yaw(Yaw), Pitch(Pitch), OnGround(ground) {}
};
struct PacketUpdateHealth : Packet {
- void ToStream(StreamOutput *stream) override {
- stream->WriteFloat(Health);
- stream->WriteVarInt(Food);
- stream->WriteFloat(FoodSaturation);
- }
-
- void FromStream(StreamInput *stream) override {
- Health = stream->ReadFloat();
- Food = stream->ReadVarInt();
- FoodSaturation = stream->ReadFloat();
- }
-
- int GetPacketId() override {
- return PacketNamePlayCB::UpdateHealth;
- }
-
- float Health;
- int Food;
- float FoodSaturation;
+ void ToStream(StreamOutput *stream) override {
+ stream->WriteFloat(Health);
+ stream->WriteVarInt(Food);
+ stream->WriteFloat(FoodSaturation);
+ }
+
+ void FromStream(StreamInput *stream) override {
+ Health = stream->ReadFloat();
+ Food = stream->ReadVarInt();
+ FoodSaturation = stream->ReadFloat();
+ }
+
+ int GetPacketId() override {
+ return PacketNamePlayCB::UpdateHealth;
+ }
+
+ float Health;
+ int Food;
+ float FoodSaturation;
};
struct PacketSpawnObject : Packet {
@@ -1095,23 +1095,55 @@ struct PacketChatMessageSB : Packet {
};
struct PacketPlayerDigging : Packet {
- void ToStream(StreamOutput *stream) override {
+ void ToStream(StreamOutput *stream) override {
stream->WriteVarInt(Status);
stream->WritePosition(Location);
stream->WriteByte(Face);
- }
+ }
- void FromStream(StreamInput *stream) override {
+ void FromStream(StreamInput *stream) override {
- }
+ }
- int GetPacketId() override {
- return PacketNamePlaySB::PlayerDigging;
- }
+ int GetPacketId() override {
+ return PacketNamePlaySB::PlayerDigging;
+ }
+
+ int Status;
+ Vector Location;
+ signed char Face;
+
+ PacketPlayerDigging(int status, const Vector& location, signed char face) : Status(status),Location(location),Face(face) {};
+};
+
+struct PacketPlayerBlockPlacement : Packet {
+ void ToStream(StreamOutput *stream) override {
+ stream->WritePosition(location);
+ stream->WriteByte(face);
+ stream->WriteByte(hand);
+ stream->WriteFloat(cursorPositionX);
+ stream->WriteFloat(cursorPositionY);
+ stream->WriteFloat(cursorPositionZ);
+ }
+
+ void FromStream(StreamInput *stream) override {
+
+ }
+
+ int GetPacketId() override {
+ return PacketNamePlaySB::PlayerBlockPlacement;
+ }
- int Status;
- Vector Location;
- signed char Face;
+ PacketPlayerBlockPlacement(
+ const Vector& location, signed char face, unsigned char hand,
+ float cursorPositionX, float cursorPositionY, float cursorPositionZ)
+ : location(location), face(face), hand(hand), cursorPositionX(cursorPositionX),
+ cursorPositionY(cursorPositionY), cursorPositionZ(cursorPositionZ) {};
- PacketPlayerDigging(int status, const Vector& location, signed char face) : Status(status),Location(location),Face(face) {};
+ Vector location;
+ signed char face;
+ unsigned char hand;
+ float cursorPositionX;
+ float cursorPositionY;
+ float cursorPositionZ;
}; \ No newline at end of file
diff --git a/src/Render.cpp b/src/Render.cpp
index 534782e..b5d24b6 100644
--- a/src/Render.cpp
+++ b/src/Render.cpp
@@ -13,7 +13,9 @@
#include "GameState.hpp"
#include "RendererWorld.hpp"
-Render::Render(unsigned int windowWidth, unsigned int windowHeight, std::string windowTitle) : timer(std::chrono::milliseconds(16)) {
+Render::Render(unsigned int windowWidth, unsigned int windowHeight,
+ std::string windowTitle)
+ : timer(std::chrono::milliseconds(16)) {
InitEvents();
InitSdl(windowWidth, windowHeight, windowTitle);
@@ -34,7 +36,7 @@ Render::~Render() {
}
void Render::InitSdl(unsigned int WinWidth, unsigned int WinHeight, std::string WinTitle) {
- LOG(INFO) << "Creating window: " << WinWidth << "x" << WinHeight << " \"" << WinTitle << "\"";
+ LOG(INFO) << "Creating window: " << WinWidth << "x" << WinHeight << " \"" << WinTitle << "\"";
if (SDL_Init(SDL_INIT_VIDEO) < 0)
throw std::runtime_error("SDL initalization failed: " + std::string(SDL_GetError()));
@@ -44,7 +46,10 @@ void Render::InitSdl(unsigned int WinWidth, unsigned int WinHeight, std::string
SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1);
SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 24);
- window = SDL_CreateWindow(WinTitle.c_str(), SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, WinWidth, WinHeight, SDL_WINDOW_OPENGL | SDL_WINDOW_RESIZABLE);
+ window = SDL_CreateWindow(
+ WinTitle.c_str(), SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED,
+ WinWidth, WinHeight, SDL_WINDOW_OPENGL | SDL_WINDOW_RESIZABLE);
+
if (!window)
throw std::runtime_error("Window creation failed: " + std::string(SDL_GetError()));
@@ -52,7 +57,7 @@ void Render::InitSdl(unsigned int WinWidth, unsigned int WinHeight, std::string
if (!glContext)
throw std::runtime_error("OpenGl context creation failed: " + std::string(SDL_GetError()));
- SetMouseCapture(false);
+ SetMouseCapture(false);
renderState.WindowWidth = WinWidth;
renderState.WindowHeight = WinHeight;
@@ -60,34 +65,34 @@ void Render::InitSdl(unsigned int WinWidth, unsigned int WinHeight, std::string
}
void Render::InitGlew() {
- LOG(INFO) << "Initializing GLEW";
- glewExperimental = GL_TRUE;
- GLenum glewStatus = glewInit();
- glCheckError();
- if (glewStatus != GLEW_OK) {
- LOG(FATAL) << "Failed to initialize GLEW: " << glewGetErrorString(glewStatus);
- }
+ LOG(INFO) << "Initializing GLEW";
+ glewExperimental = GL_TRUE;
+ GLenum glewStatus = glewInit();
+ glCheckError();
+ if (glewStatus != GLEW_OK) {
+ LOG(FATAL) << "Failed to initialize GLEW: " << glewGetErrorString(glewStatus);
+ }
int width, height;
SDL_GL_GetDrawableSize(window, &width, &height);
glViewport(0, 0, width, height);
glClearColor(0.8,0.8,0.8, 1.0f);
- glEnable(GL_DEPTH_TEST);
+ glEnable(GL_DEPTH_TEST);
- glEnable(GL_CULL_FACE);
- glCullFace(GL_BACK);
- glFrontFace(GL_CCW);
+ glEnable(GL_CULL_FACE);
+ glCullFace(GL_BACK);
+ glFrontFace(GL_CCW);
- glEnable(GL_BLEND);
- glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
- glCheckError();
+ glEnable(GL_BLEND);
+ glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
+ glCheckError();
if (glActiveTexture == nullptr) {
throw std::runtime_error("GLEW initialization failed with unknown reason");
}
}
void Render::PrepareToRendering() {
- //TextureAtlas texture
- glActiveTexture(GL_TEXTURE0);
+ //TextureAtlas texture
+ glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, AssetManager::Instance().GetTextureAtlas());
AssetManager::Instance().GetTextureAtlasIndexes();
@@ -103,13 +108,13 @@ void Render::UpdateKeyboard() {
for (auto key : toUpdate) {
bool isPressed = kbState[key];
if (!isKeyPressed[key] && isPressed) {
- PUSH_EVENT("KeyPressed", key);
+ PUSH_EVENT("KeyPressed", key);
}
if (isKeyPressed[key] && isPressed) {
//KeyHeld
}
if (isKeyPressed[key] && !isPressed) {
- PUSH_EVENT("KeyReleased", key);
+ PUSH_EVENT("KeyReleased", key);
}
isKeyPressed[key] = isPressed;
}
@@ -141,94 +146,127 @@ void Render::HandleEvents() {
ImGui_ImplSdlGL3_ProcessEvent(&event);
switch (event.type) {
- case SDL_QUIT:
- LOG(INFO) << "Received close event by window closing";
- PUSH_EVENT("Exit",0);
- break;
- case SDL_WINDOWEVENT: {
- switch (event.window.event) {
- case SDL_WINDOWEVENT_RESIZED: {
- int width, height;
- SDL_GL_GetDrawableSize(window, &width, &height);
- glViewport(0, 0, width, height);
- renderState.WindowWidth = width;
- renderState.WindowHeight = height;
- break;
- }
- case SDL_WINDOWEVENT_FOCUS_GAINED:
- HasFocus = true;
- break;
- case SDL_WINDOWEVENT_FOCUS_LOST:
- HasFocus = false;
- if (GlobalState::GetState() == State::Inventory || GlobalState::GetState() == State::Playing || GlobalState::GetState() == State::Chat)
- GlobalState::SetState(State::Paused);
+ case SDL_QUIT: {
+ LOG(INFO) << "Received close event by window closing";
+ PUSH_EVENT("Exit",0);
break;
}
- break;
- }
- case SDL_KEYDOWN:
- switch (event.key.keysym.scancode) {
- case SDL_SCANCODE_ESCAPE:
- switch (GlobalState::GetState()) {
- case State::Playing:
- GlobalState::SetState(State::Paused);
- break;
- case State::Inventory:
- GlobalState::SetState(State::Paused);
- break;
- case State::Paused:
- GlobalState::SetState(State::Playing);
- break;
- case State::MainMenu:
- LOG(INFO) << "Received close event by esc";
- PUSH_EVENT("Exit",0);
- break;
- }
- break;
- case SDL_SCANCODE_E:
- switch (GlobalState::GetState()) {
- case State::Playing:
- GlobalState::SetState(State::Inventory);
- break;
- case State::Inventory:
- GlobalState::SetState(State::Playing);
- break;
+
+ case SDL_WINDOWEVENT: {
+ switch (event.window.event) {
+ case SDL_WINDOWEVENT_RESIZED: {
+ int width, height;
+ SDL_GL_GetDrawableSize(window, &width, &height);
+ glViewport(0, 0, width, height);
+ renderState.WindowWidth = width;
+ renderState.WindowHeight = height;
+ break;
+ }
+
+ case SDL_WINDOWEVENT_FOCUS_GAINED:
+ HasFocus = true;
+ break;
+
+ case SDL_WINDOWEVENT_FOCUS_LOST: {
+ HasFocus = false;
+ auto state = GlobalState::GetState();
+ if (state == State::Inventory ||
+ state == State::Playing ||
+ state == State::Chat) {
+ GlobalState::SetState(State::Paused);
+ }
+ break;
+ }
+
}
break;
- case SDL_SCANCODE_T:
- if (!ImGui::GetIO().WantCaptureKeyboard)
- switch (GlobalState::GetState()) {
- case State::Playing:
- GlobalState::SetState(State::Chat);
- SetMouseCapture(false);
+ }
+
+ case SDL_KEYDOWN: {
+ switch (event.key.keysym.scancode) {
+ case SDL_SCANCODE_ESCAPE: {
+ auto state = GlobalState::GetState();
+ if (state == State::Playing) {
+ GlobalState::SetState(State::Paused);
+ } else if (state == State::Paused ||
+ state == State::Inventory ||
+ state == State::Chat) {
+ GlobalState::SetState(State::Playing);
+ } else if (state == State::MainMenu) {
+ LOG(INFO) << "Received close event by esc";
+ PUSH_EVENT("Exit", 0);
+ }
+
break;
- case State::Chat:
- GlobalState::SetState(State::Playing);
- SetMouseCapture(true);
+ }
+
+ case SDL_SCANCODE_E: {
+ auto state = GlobalState::GetState();
+ if (state == State::Playing) {
+ GlobalState::SetState(State::Inventory);
+ } else if (state == State::Inventory) {
+ GlobalState::SetState(State::Playing);
+ }
+
break;
}
+
+ case SDL_SCANCODE_SLASH:
+ case SDL_SCANCODE_T: {
+ if (!ImGui::GetIO().WantCaptureKeyboard) {
+ auto state = GlobalState::GetState();
+ if (state == State::Playing) {
+ GlobalState::SetState(State::Chat);
+ } else if (state == State::Chat) {
+ GlobalState::SetState(State::Playing);
+ }
+ }
+
+ break;
+ }
+
+ default:
+ break;
+ }
+
break;
}
- break;
- case SDL_MOUSEMOTION:
- if (isMouseCaptured) {
- double deltaX = event.motion.xrel;
- double deltaY = event.motion.yrel;
- deltaX *= sensetivity;
- deltaY *= sensetivity * -1;
- PUSH_EVENT("MouseMove", std::make_tuple(deltaX, deltaY));
+
+ case SDL_MOUSEMOTION: {
+ if (isMouseCaptured) {
+ double deltaX = event.motion.xrel;
+ double deltaY = event.motion.yrel;
+ deltaX *= sensetivity;
+ deltaY *= sensetivity * -1;
+ PUSH_EVENT("MouseMove", std::make_tuple(deltaX, deltaY));
+ }
+
+ break;
}
+
+ case SDL_MOUSEBUTTONDOWN: {
+ if (isMouseCaptured && !ImGui::GetIO().WantCaptureMouse) {
+ if (event.button.button == SDL_BUTTON_LEFT)
+ PUSH_EVENT("LmbPressed", 0);
+ else if (event.button.button == SDL_BUTTON_RIGHT)
+ PUSH_EVENT("RmbPressed", 0);
+ }
+
break;
- case SDL_MOUSEBUTTONDOWN:
- if (event.button.button == SDL_BUTTON_LEFT && !ImGui::GetIO().WantCaptureMouse)
- PUSH_EVENT("LmbPressed",0);
+ }
+
+ case SDL_MOUSEBUTTONUP: {
+ if (isMouseCaptured && !ImGui::GetIO().WantCaptureMouse) {
+ if (event.button.button == SDL_BUTTON_LEFT)
+ PUSH_EVENT("LmbReleased", 0);
+ else if (event.button.button == SDL_BUTTON_RIGHT)
+ PUSH_EVENT("RmbReleased", 0);
+ }
break;
- case SDL_MOUSEBUTTONUP:
- if (event.button.button == SDL_BUTTON_LEFT && !ImGui::GetIO().WantCaptureMouse)
- PUSH_EVENT("LmbReleased",0);
+ }
+
+ default:
break;
- default:
- break;
}
}
}
@@ -254,7 +292,6 @@ void Render::SetMouseCapture(bool IsCaptured) {
}
void Render::Update() {
-
HandleEvents();
if (HasFocus && GlobalState::GetState() == State::Playing) UpdateKeyboard();
if (isMouseCaptured) HandleMouseCapture();
@@ -272,7 +309,12 @@ void Render::RenderGui() {
auto& io = ImGui::GetIO();
io.MousePos = ImVec2(-FLT_MAX, -FLT_MAX);
}
- const ImGuiWindowFlags windowFlags = ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoMove | ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoSavedSettings;
+
+ const ImGuiWindowFlags windowFlags = ImGuiWindowFlags_NoTitleBar |
+ ImGuiWindowFlags_NoResize |
+ ImGuiWindowFlags_NoMove |
+ ImGuiWindowFlags_AlwaysAutoResize|
+ ImGuiWindowFlags_NoSavedSettings;
//ImGui::ShowTestWindow();
@@ -285,203 +327,235 @@ void Render::RenderGui() {
float gameTime = DebugInfo::gameThreadTime / 100.0f;
if (world) {
ImGui::Text("TPS: %.1f (%.2fms)", 1000.0f / gameTime, gameTime);
- ImGui::Text("Sections loaded: %d", (int)DebugInfo::totalSections);
- ImGui::Text("SectionsRenderer: %d (%d)", (int)DebugInfo::renderSections, (int)DebugInfo::readyRenderer);
- ImGui::Text("Culled sections: %d", (int)DebugInfo::renderSections - world->culledSections);
- ImGui::Text("Player pos: %.1f %.1f %.1f OnGround=%d", world->GameStatePtr()->player->pos.x, world->GameStatePtr()->player->pos.y, world->GameStatePtr()->player->pos.z, world->GameStatePtr()->player->onGround);
- ImGui::Text("Player vel: %.1f %.1f %.1f", world->GameStatePtr()->player->vel.x, world->GameStatePtr()->player->vel.y, world->GameStatePtr()->player->vel.z);
- ImGui::Text("Player health: %.1f/%.1f", world->GameStatePtr()->g_PlayerHealth, 20.0f);
- ImGui::Text("Selected block: %d %d %d : %.1f",world->GameStatePtr()->selectedBlock.x,world->GameStatePtr()->selectedBlock.y,world->GameStatePtr()->selectedBlock.z,world->GameStatePtr()->distanceToSelectedBlock);
+ ImGui::Text("Sections loaded: %d", (int) DebugInfo::totalSections);
+ ImGui::Text(
+ "SectionsRenderer: %d (%d)",
+ (int) DebugInfo::renderSections,(int) DebugInfo::readyRenderer);
+
+ ImGui::Text(
+ "Culled sections: %d",
+ (int) DebugInfo::renderSections - world->culledSections);
+
+ ImGui::Text(
+ "Player pos: %.1f %.1f %.1f OnGround=%d",
+ world->GameStatePtr()->player->pos.x,
+ world->GameStatePtr()->player->pos.y,
+ world->GameStatePtr()->player->pos.z,
+ world->GameStatePtr()->player->onGround);
+
+ ImGui::Text(
+ "Player vel: %.1f %.1f %.1f",
+ world->GameStatePtr()->player->vel.x,
+ world->GameStatePtr()->player->vel.y,
+ world->GameStatePtr()->player->vel.z);
+
+ ImGui::Text(
+ "Player health: %.1f/%.1f",
+ world->GameStatePtr()->g_PlayerHealth, 20.0f);
+
+ ImGui::Text(
+ "Selected block: %d %d %d : %.1f",
+ world->GameStatePtr()->selectedBlock.x,
+ world->GameStatePtr()->selectedBlock.y,
+ world->GameStatePtr()->selectedBlock.z,
+ world->GameStatePtr()->distanceToSelectedBlock);
}
ImGui::End();
switch (GlobalState::GetState()) {
- case State::MainMenu: {
- ImGui::SetNextWindowPosCenter();
- ImGui::Begin("Menu", 0, windowFlags);
- static char buff[512] = "127.0.0.1";
- static int port = 25565;
- static char buffName[512] = "HelloOne";
- if (ImGui::Button("Connect")) {
- PUSH_EVENT("ConnectToServer", std::make_tuple(std::string(buff), (unsigned short)port, std::string(buffName)));
- }
- ImGui::InputText("Username", buffName, 512);
- ImGui::InputText("Address", buff, 512);
- ImGui::InputInt("Port", &port);
- ImGui::Separator();
- if (ImGui::Button("Exit"))
- PUSH_EVENT("Exit",0);
- ImGui::End();
- break;
- }
- case State::Loading:
- break;
- case State::Chat: {
- ImGui::SetNextWindowPosCenter();
- ImGui::Begin("Chat", 0, windowFlags);
- for (const auto& msg : chatMessages) {
- ImGui::PushStyleColor(ImGuiCol_Text, ImVec4(1,1,1,1));
- ImGui::TextWrapped("%s", msg.c_str());
- ImGui::PopStyleColor();
- }
- static char buff[256];
- ImGui::InputText("", buff, 256);
- ImGui::SameLine();
- if (ImGui::Button("Send")) {
- PUSH_EVENT("SendChatMessage", std::string(buff));
+ case State::MainMenu: {
+ ImGui::SetNextWindowPosCenter();
+ ImGui::Begin("Menu", 0, windowFlags);
+ static char buff[512] = "127.0.0.1";
+ static int port = 25565;
+ static char buffName[512] = "HelloOne";
+ if (ImGui::Button("Connect")) {
+ PUSH_EVENT("ConnectToServer", std::make_tuple(std::string(buff),
+ (unsigned short) port, std::string(buffName)));
+ }
+ ImGui::InputText("Username", buffName, 512);
+ ImGui::InputText("Address", buff, 512);
+ ImGui::InputInt("Port", &port);
+ ImGui::Separator();
+ if (ImGui::Button("Exit"))
+ PUSH_EVENT("Exit",0);
+ ImGui::End();
+ break;
}
- ImGui::End();
- break;
- }
- case State::Inventory: {
- auto renderSlot = [](const SlotDataType &slot, int i) -> bool {
- return ImGui::Button(((slot.BlockId == -1 ? " ##" :
- AssetManager::Instance().GetAssetNameByBlockId(BlockId{ (unsigned short)slot.BlockId,0 }) + " x" + std::to_string(slot.ItemCount) + "##")
- + std::to_string(i)).c_str());
- };
- ImGui::SetNextWindowPosCenter();
- ImGui::Begin("Inventory", 0, windowFlags);
- Window& inventory = world->GameStatePtr()->playerInventory;
- //Hand and drop slots
- if (renderSlot(inventory.handSlot, -1)) {
- }
- ImGui::SameLine();
- if (ImGui::Button("Drop")) {
- inventory.MakeClick(-1, true, true);
- }
- ImGui::SameLine();
- ImGui::Text("Hand slot and drop mode");
- ImGui::Separator();
- //Crafting
- if (renderSlot(inventory.slots[1], 1)) {
- inventory.MakeClick(1, true);
- }
- ImGui::SameLine();
- if (renderSlot(inventory.slots[2], 2)) {
- inventory.MakeClick(2, true);
- }
- //Crafting result
- ImGui::SameLine();
- ImGui::Text("Result");
- ImGui::SameLine();
- if (renderSlot(inventory.slots[0], 0)) {
- inventory.MakeClick(0, true);
- }
- //Crafting second line
- if (renderSlot(inventory.slots[3], 3)) {
- inventory.MakeClick(3, true);
- }
- ImGui::SameLine();
- if (renderSlot(inventory.slots[4], 4)) {
- inventory.MakeClick(4, true);
- }
- ImGui::Separator();
- //Armor and offhand
- for (int i = 5; i < 8 + 1; i++) {
- if (renderSlot(inventory.slots[i], i)) {
- inventory.MakeClick(i, true);
+ case State::Loading:
+ break;
+
+ case State::Chat: {
+ ImGui::SetNextWindowPosCenter();
+ ImGui::Begin("Chat", 0, windowFlags);
+ for (const auto& msg : chatMessages) {
+ ImGui::PushStyleColor(ImGuiCol_Text, ImVec4(1,1,1,1));
+ ImGui::TextWrapped("%s", msg.c_str());
+ ImGui::PopStyleColor();
}
+ static char buff[256];
+ ImGui::InputText("", buff, 256);
ImGui::SameLine();
+ if (ImGui::Button("Send")) {
+ PUSH_EVENT("SendChatMessage", std::string(buff));
+ }
+ ImGui::End();
+ break;
}
- if (renderSlot(inventory.slots[45], 45)) {
- inventory.MakeClick(45, true);
- }
- ImGui::SameLine();
- ImGui::Text("Armor and offhand");
- ImGui::Separator();
- for (int i = 36; i < 44 + 1; i++) {
- if (renderSlot(inventory.slots[i], i)) {
- inventory.MakeClick(i, true);
+
+ case State::Inventory: {
+ auto renderSlot = [](const SlotDataType &slot, int i) -> bool {
+ return ImGui::Button(((slot.BlockId == -1 ? " ##" :
+ AssetManager::Instance().GetAssetNameByBlockId(BlockId{ (unsigned short)slot.BlockId,0 }) + " x" + std::to_string(slot.ItemCount) + "##")
+ + std::to_string(i)).c_str());
+ };
+ ImGui::SetNextWindowPosCenter();
+ ImGui::Begin("Inventory", 0, windowFlags);
+ Window& inventory = world->GameStatePtr()->playerInventory;
+ //Hand and drop slots
+ if (renderSlot(inventory.handSlot, -1)) {
+
}
ImGui::SameLine();
- }
- ImGui::Text("Hotbar");
- ImGui::Separator();
- ImGui::Text("Main inventory");
- for (int i = 9; i < 17 + 1; i++) {
- if (renderSlot(inventory.slots[i], i)) {
- inventory.MakeClick(i, true);
+ if (ImGui::Button("Drop")) {
+ inventory.MakeClick(-1, true, true);
}
ImGui::SameLine();
- }
- ImGui::Text("");
- for (int i = 18; i < 26 + 1; i++) {
- if (renderSlot(inventory.slots[i], i)) {
- inventory.MakeClick(i, true);
+ ImGui::Text("Hand slot and drop mode");
+ ImGui::Separator();
+ //Crafting
+ if (renderSlot(inventory.slots[1], 1)) {
+ inventory.MakeClick(1, true);
}
ImGui::SameLine();
- }
- ImGui::Text("");
- for (int i = 27; i < 35 + 1; i++) {
- if (renderSlot(inventory.slots[i], i)) {
- inventory.MakeClick(i, true);
+ if (renderSlot(inventory.slots[2], 2)) {
+ inventory.MakeClick(2, true);
}
+ //Crafting result
ImGui::SameLine();
- }
- ImGui::End();
+ ImGui::Text("Result");
+ ImGui::SameLine();
+ if (renderSlot(inventory.slots[0], 0)) {
+ inventory.MakeClick(0, true);
+ }
+ //Crafting second line
+ if (renderSlot(inventory.slots[3], 3)) {
+ inventory.MakeClick(3, true);
+ }
+ ImGui::SameLine();
+ if (renderSlot(inventory.slots[4], 4)) {
+ inventory.MakeClick(4, true);
+ }
+ ImGui::Separator();
+ //Armor and offhand
+ for (int i = 5; i < 8 + 1; i++) {
+ if (renderSlot(inventory.slots[i], i)) {
+ inventory.MakeClick(i, true);
+ }
+ ImGui::SameLine();
+ }
+ if (renderSlot(inventory.slots[45], 45)) {
+ inventory.MakeClick(45, true);
+ }
+ ImGui::SameLine();
+ ImGui::Text("Armor and offhand");
+ ImGui::Separator();
+ for (int i = 36; i < 44 + 1; i++) {
+ if (renderSlot(inventory.slots[i], i)) {
+ inventory.MakeClick(i, true);
+ }
+ ImGui::SameLine();
+ }
+ ImGui::Text("Hotbar");
+ ImGui::Separator();
+ ImGui::Text("Main inventory");
+ for (int i = 9; i < 17 + 1; i++) {
+ if (renderSlot(inventory.slots[i], i)) {
+ inventory.MakeClick(i, true);
+ }
+ ImGui::SameLine();
+ }
+ ImGui::Text("");
+ for (int i = 18; i < 26 + 1; i++) {
+ if (renderSlot(inventory.slots[i], i)) {
+ inventory.MakeClick(i, true);
+ }
+ ImGui::SameLine();
+ }
+ ImGui::Text("");
+ for (int i = 27; i < 35 + 1; i++) {
+ if (renderSlot(inventory.slots[i], i)) {
+ inventory.MakeClick(i, true);
+ }
+ ImGui::SameLine();
+ }
+ ImGui::End();
- break;
- }
- case State::Paused: {
- ImGui::SetNextWindowPosCenter();
- ImGui::Begin("Pause Menu", 0, windowFlags);
- if (ImGui::Button("Continue")) {
- GlobalState::SetState(State::Playing);
+ break;
}
- ImGui::Separator();
- static float distance = world->MaxRenderingDistance;
- ImGui::SliderFloat("Render distance", &distance, 1.0f, 16.0f);
- static float sense = sensetivity;
- ImGui::SliderFloat("Sensetivity", &sense, 0.01f, 1.0f);
+ case State::Paused: {
+ ImGui::SetNextWindowPosCenter();
+ ImGui::Begin("Pause Menu", 0, windowFlags);
+ if (ImGui::Button("Continue")) {
+ GlobalState::SetState(State::Playing);
+ }
+ ImGui::Separator();
+ static float distance = world->MaxRenderingDistance;
+ ImGui::SliderFloat("Render distance", &distance, 1.0f, 16.0f);
- static float targetFps = 60.0f;
- ImGui::SliderFloat("Target FPS", &targetFps, 1.0f, 300.0f);
+ static float sense = sensetivity;
+ ImGui::SliderFloat("Sensetivity", &sense, 0.01f, 1.0f);
- static bool wireframe = isWireframe;
+ static float targetFps = 60.0f;
+ ImGui::SliderFloat("Target FPS", &targetFps, 1.0f, 300.0f);
- ImGui::Checkbox("Wireframe", &wireframe);
+ static bool wireframe = isWireframe;
- static bool vsync = false;
+ ImGui::Checkbox("Wireframe", &wireframe);
- ImGui::Checkbox("VSync", &vsync);
+ static bool vsync = false;
- if (ImGui::Button("Apply settings")) {
- if (distance != world->MaxRenderingDistance) {
- world->MaxRenderingDistance = distance;
- PUSH_EVENT("UpdateSectionsRender", 0);
- }
+ ImGui::Checkbox("VSync", &vsync);
+
+ if (ImGui::Button("Apply settings")) {
+ if (distance != world->MaxRenderingDistance) {
+ world->MaxRenderingDistance = distance;
+ PUSH_EVENT("UpdateSectionsRender", 0);
+ }
- if (sense != sensetivity)
- sensetivity = sense;
+ if (sense != sensetivity)
+ sensetivity = sense;
- isWireframe = wireframe;
- timer.SetDelayLength(std::chrono::duration<double, std::milli>(1.0 / targetFps * 1000.0));
- if (vsync) {
- timer.SetDelayLength(std::chrono::milliseconds(0));
- SDL_GL_SetSwapInterval(1);
- } else
- SDL_GL_SetSwapInterval(0);
+ isWireframe = wireframe;
+ timer.SetDelayLength(std::chrono::duration<double, std::milli>(1.0 / targetFps * 1000.0));
+ if (vsync) {
+ timer.SetDelayLength(std::chrono::milliseconds(0));
+ SDL_GL_SetSwapInterval(1);
+ } else
+ SDL_GL_SetSwapInterval(0);
+ }
+ ImGui::Separator();
+
+ if (ImGui::Button("Disconnect")) {
+ PUSH_EVENT("Disconnect", std::string("Disconnected by user"));
+ }
+ ImGui::End();
+ break;
}
- ImGui::Separator();
- if (ImGui::Button("Disconnect")) {
- PUSH_EVENT("Disconnect", std::string("Disconnected by user"));
+ case State::InitialLoading:
+ break;
+
+ case State::Playing: {
+ ImGui::SetNextWindowPosCenter();
+ ImGui::Begin("",0,windowFlags);
+ ImGui::End();
+ break;
}
- ImGui::End();
- break;
- }
- case State::InitialLoading:
- break;
- case State::Playing: {
- ImGui::SetNextWindowPosCenter();
- ImGui::Begin("",0,windowFlags);
- ImGui::End();
- break;
- }
}
ImGui::Render();
diff --git a/src/RendererSection.cpp b/src/RendererSection.cpp
index 23b0a42..0311171 100644
--- a/src/RendererSection.cpp
+++ b/src/RendererSection.cpp
@@ -162,12 +162,10 @@ void RendererSection::Render(RenderState &renderState) {
glCheckError();
}
-Vector RendererSection::GetPosition()
-{
+Vector RendererSection::GetPosition() {
return sectionPos;
}
-size_t RendererSection::GetHash()
-{
+size_t RendererSection::GetHash() {
return hash;
} \ No newline at end of file
diff --git a/src/RendererWorld.cpp b/src/RendererWorld.cpp
index 8390de7..16f7950 100644
--- a/src/RendererWorld.cpp
+++ b/src/RendererWorld.cpp
@@ -60,8 +60,7 @@ void RendererWorld::WorkerFunction(size_t workerId) {
}
}
-void RendererWorld::UpdateAllSections(VectorF playerPos)
-{
+void RendererWorld::UpdateAllSections(VectorF playerPos) {
Vector playerChunk(std::floor(gs->player->pos.x / 16), 0, std::floor(gs->player->pos.z / 16));
std::vector<Vector> suitableChunks;
@@ -213,7 +212,7 @@ RendererWorld::~RendererWorld() {
faces += it.second.numOfFaces;
}
sectionsMutex.unlock();
- LOG(INFO) << "Total faces to render: "<<faces;
+ LOG(INFO) << "Total faces to render: " << faces;
isRunning = false;
for (int i = 0; i < numOfWorkers; i++)
workers[i].join();
@@ -227,7 +226,10 @@ RendererWorld::~RendererWorld() {
void RendererWorld::Render(RenderState & renderState) {
//Common
GLint projectionLoc, viewLoc, modelLoc, pvLoc, windowSizeLoc, colorLoc;
- glm::mat4 projection = glm::perspective(45.0f, (float)renderState.WindowWidth / (float)renderState.WindowHeight, 0.1f, 10000000.0f);
+ glm::mat4 projection = glm::perspective(
+ 45.0f, (float) renderState.WindowWidth / (float) renderState.WindowHeight,
+ 0.1f, 10000000.0f
+ );
glm::mat4 view = gs->GetViewMatrix();
glm::mat4 projView = projection * view;
@@ -328,7 +330,11 @@ void RendererWorld::Render(RenderState & renderState) {
}
}
- double lengthToSection = (gs->player->pos - VectorF(section.first.x*16,section.first.y*16,section.first.z*16)).GetLength();
+ double lengthToSection = (gs->player->pos -
+ VectorF(section.first.x*16,
+ section.first.y*16,
+ section.first.z*16)
+ ).GetLength();
if (!isVisible && lengthToSection > 30.0f) {
sectionsMutex.lock();
diff --git a/src/Utility.cpp b/src/Utility.cpp
index 0fb10cf..848ee02 100644
--- a/src/Utility.cpp
+++ b/src/Utility.cpp
@@ -5,40 +5,41 @@
#include <easylogging++.h>
GLenum glCheckError_(const char *file, int line) {
- GLenum errorCode;
- while ((errorCode = glGetError()) != GL_NO_ERROR) {
- std::string error;
- switch (errorCode) {
- case GL_INVALID_ENUM:
- error = "INVALID_ENUM";
- break;
- case GL_INVALID_VALUE:
- error = "INVALID_VALUE";
- break;
- case GL_INVALID_OPERATION:
- error = "INVALID_OPERATION";
- break;
- case GL_STACK_OVERFLOW:
- error = "STACK_OVERFLOW";
- break;
- case GL_STACK_UNDERFLOW:
- error = "STACK_UNDERFLOW";
- break;
- case GL_OUT_OF_MEMORY:
- error = "OUT_OF_MEMORY";
- break;
- case GL_INVALID_FRAMEBUFFER_OPERATION:
- error = "INVALID_FRAMEBUFFER_OPERATION";
- break;
- }
- static int t = 0;
- LOG(ERROR) << "OpenGL error: " << error << " at " << file << ":" << line;
- }
- return errorCode;
+ GLenum errorCode;
+ while ((errorCode = glGetError()) != GL_NO_ERROR) {
+ std::string error;
+ switch (errorCode) {
+ case GL_INVALID_ENUM:
+ error = "INVALID_ENUM";
+ break;
+ case GL_INVALID_VALUE:
+ error = "INVALID_VALUE";
+ break;
+ case GL_INVALID_OPERATION:
+ error = "INVALID_OPERATION";
+ break;
+ case GL_STACK_OVERFLOW:
+ error = "STACK_OVERFLOW";
+ break;
+ case GL_STACK_UNDERFLOW:
+ error = "STACK_UNDERFLOW";
+ break;
+ case GL_OUT_OF_MEMORY:
+ error = "OUT_OF_MEMORY";
+ break;
+ case GL_INVALID_FRAMEBUFFER_OPERATION:
+ error = "INVALID_FRAMEBUFFER_OPERATION";
+ break;
+ }
+ static int t = 0;
+ LOG(ERROR) << "OpenGL error: " << error << " at " << file << ":" << line;
+ }
+ return errorCode;
}
-LoopExecutionTimeController::LoopExecutionTimeController(duration delayLength) : delayLength(delayLength) {
- previousUpdate = clock::now();
+LoopExecutionTimeController::LoopExecutionTimeController(duration delayLength)
+ : delayLength(delayLength) {
+ previousUpdate = clock::now();
}
LoopExecutionTimeController::~LoopExecutionTimeController() {
@@ -46,16 +47,16 @@ LoopExecutionTimeController::~LoopExecutionTimeController() {
}
void LoopExecutionTimeController::SetDelayLength(duration length) {
- delayLength = length;
+ delayLength = length;
}
unsigned long long LoopExecutionTimeController::GetIterations() {
- return iterations;
+ return iterations;
}
void LoopExecutionTimeController::Update() {
- iterations++;
- auto timeToSleep = delayLength - GetDelta();
+ iterations++;
+ auto timeToSleep = delayLength - GetDelta();
if (timeToSleep.count() > 0)
std::this_thread::sleep_for(timeToSleep);
previousPreviousUpdate = previousUpdate;
@@ -68,8 +69,8 @@ double LoopExecutionTimeController::GetDeltaMs() {
}
LoopExecutionTimeController::duration LoopExecutionTimeController::GetDelta() {
- auto now = clock::now();
- return duration(now-previousUpdate);
+ auto now = clock::now();
+ return duration(now-previousUpdate);
}
double LoopExecutionTimeController::GetDeltaS() {
@@ -77,13 +78,11 @@ double LoopExecutionTimeController::GetDeltaS() {
return delta.count();
}
-double LoopExecutionTimeController::GetRealDeltaS()
-{
+double LoopExecutionTimeController::GetRealDeltaS() {
return std::chrono::duration<double,std::ratio<1,1>>(previousUpdate - previousPreviousUpdate).count();
}
-double LoopExecutionTimeController::RemainTimeMs()
-{
+double LoopExecutionTimeController::RemainTimeMs() {
auto remain = delayLength - GetDelta();
return remain.count();
}
diff --git a/src/Utility.hpp b/src/Utility.hpp
index e8c508d..9b90cb9 100644
--- a/src/Utility.hpp
+++ b/src/Utility.hpp
@@ -11,18 +11,38 @@ using Uuid = std::vector<unsigned char>;
template<class T>
void endswap(T *objp) {
- unsigned char *memp = reinterpret_cast<unsigned char *>(objp);
- std::reverse(memp, memp + sizeof(T));
+ unsigned char *memp = reinterpret_cast<unsigned char *>(objp);
+ std::reverse(memp, memp + sizeof(T));
}
template<class T>
void endswap(T &obj) {
- unsigned char *raw = reinterpret_cast<unsigned char *>(&obj);
- std::reverse(raw, raw + sizeof(T));
+ unsigned char *raw = reinterpret_cast<unsigned char *>(&obj);
+ std::reverse(raw, raw + sizeof(T));
+}
+
+template<typename T>
+T _min(T a, T b) {
+ return (a > b) ? b : a;
+}
+
+template<typename T, typename... Args>
+T _min(T a, T b, Args... args) {
+ return _min(a > b ? b : a, args...);
+}
+
+template<typename T>
+T _max(T a, T b) {
+ return (a > b) ? a : b;
+}
+
+template<typename T, typename... Args>
+T _max(T a, T b, Args... args) {
+ return _max(a > b ? a : b, args...);
}
inline void endswap(unsigned char *arr, size_t arrLen) {
- std::reverse(arr, arr + arrLen);
+ std::reverse(arr, arr + arrLen);
}
GLenum glCheckError_(const char *file, int line);
@@ -30,27 +50,27 @@ GLenum glCheckError_(const char *file, int line);
class LoopExecutionTimeController {
- using clock = std::chrono::steady_clock ;
- using timePoint = std::chrono::time_point<clock>;
- using duration = std::chrono::duration<double,std::milli>;
- timePoint previousUpdate;
+ using clock = std::chrono::steady_clock ;
+ using timePoint = std::chrono::time_point<clock>;
+ using duration = std::chrono::duration<double,std::milli>;
+ timePoint previousUpdate;
timePoint previousPreviousUpdate;
- duration delayLength;
- unsigned long long iterations=0;
+ duration delayLength;
+ unsigned long long iterations=0;
public:
- LoopExecutionTimeController(duration delayLength);
+ LoopExecutionTimeController(duration delayLength);
- ~LoopExecutionTimeController();
+ ~LoopExecutionTimeController();
- void SetDelayLength(duration length);
+ void SetDelayLength(duration length);
- unsigned long long GetIterations();
+ unsigned long long GetIterations();
- void Update();
+ void Update();
- double GetDeltaMs();
+ double GetDeltaMs();
- duration GetDelta();
+ duration GetDelta();
double GetDeltaS();
diff --git a/src/Vector.hpp b/src/Vector.hpp
index 5795db2..03b1ec4 100644
--- a/src/Vector.hpp
+++ b/src/Vector.hpp
@@ -7,108 +7,134 @@
template<class T>
struct Vector3 {
- T x, y, z;
+ T x, y, z;
- Vector3(T X = 0, T Y = 0, T Z = 0) : x(X), y(Y), z(Z) {}
+ Vector3(T X = 0, T Y = 0, T Z = 0) : x(X), y(Y), z(Z) {}
- Vector3(const Vector3 &rhs) : x(rhs.x), y(rhs.y), z(rhs.z) {}
+ Vector3(const Vector3 &rhs) : x(rhs.x), y(rhs.y), z(rhs.z) {}
- ~Vector3() = default;
+ ~Vector3() = default;
- double GetLength() const { return std::sqrt(std::pow(x, 2) + std::pow(y, 2) + std::pow(z, 2)); }
+ double GetLength() const { return std::sqrt(std::pow(x, 2) + std::pow(y, 2) + std::pow(z, 2)); }
- operator glm::vec3() const {
- return glm::vec3(x, y, z);
- }
+ operator glm::vec3() const {
+ return glm::vec3(x, y, z);
+ }
glm::vec3 glm() const {
return (glm::vec3)(*this);
}
- void swap(Vector3 &rhs) noexcept {
- std::swap(x, rhs.x);
- std::swap(y, rhs.y);
- std::swap(z, rhs.z);
- }
-
- Vector3 &operator=(Vector3 rhs) noexcept {
- rhs.swap(*this);
- return *this;
- }
-
- Vector3 operator*(T rhs) const {
- return Vector3<T>(
- x * rhs,
- y * rhs,
- z * rhs
- );
- }
-
- Vector3 operator/(T rhs) const {
- return Vector3<T>(
- x / rhs,
- y / rhs,
- z / rhs
- );
- }
-
- Vector3 operator+(const Vector3 &rhs) const {
- return Vector3<T>(
- x + rhs.x,
- y + rhs.y,
- z + rhs.z
- );
- }
-
- Vector3 operator-(const Vector3 &rhs) const {
- return Vector3<T>(
- x - rhs.x,
- y - rhs.y,
- z - rhs.z
- );
- }
-
- Vector3 operator*(const Vector3 &rhs) const {
- return Vector3<T>(
- x * rhs.x,
- y * rhs.y,
- z * rhs.z
- );
- }
-
- Vector3 operator/(const Vector3 &rhs) const {
- return Vector3<T>(
- x / rhs.x,
- y / rhs.y,
- z / rhs.z
- );
- }
-
- bool operator==(const Vector3 &rhs) const {
- return (x == rhs.x && y == rhs.y && z == rhs.z);
- }
-
- bool operator!=(const Vector3 &rhs) const {
- return !(*this == rhs);
- }
-
- bool operator<(const Vector3 &rhs) const {
- if (x < rhs.x)
- return true;
- if (rhs.x < x)
- return false;
- if (y < rhs.y)
- return true;
- if (rhs.y < y)
- return false;
- return z < rhs.z;
- }
-
-
- friend std::ostream &operator<<(std::ostream &os, const Vector3 &vector3) {
- os << vector3.x << ", " << vector3.y << ", " << vector3.z;
- return os;
- }
+ void swap(Vector3 &rhs) noexcept {
+ std::swap(x, rhs.x);
+ std::swap(y, rhs.y);
+ std::swap(z, rhs.z);
+ }
+
+ T dot(const Vector3 &rhs) const {
+ return x*rhs.x + y*rhs.y + z*rhs.z;
+ }
+
+ double cosBetween(const Vector3<T> &rhs) const {
+ return dot(rhs) / GetLength() / rhs.GetLength();
+ }
+
+ Vector3<double> normalize() {
+ auto length = GetLength();
+
+ return Vector3<double> (
+ x / length,
+ y / length,
+ z / length
+ );
+ }
+
+ Vector3 &operator=(Vector3 rhs) noexcept {
+ rhs.swap(*this);
+ return *this;
+ }
+
+ Vector3 operator*(T rhs) const {
+ return Vector3<T>(
+ x * rhs,
+ y * rhs,
+ z * rhs
+ );
+ }
+
+ Vector3 operator/(T rhs) const {
+ return Vector3<T>(
+ x / rhs,
+ y / rhs,
+ z / rhs
+ );
+ }
+
+ Vector3 operator+(const Vector3 &rhs) const {
+ return Vector3<T>(
+ x + rhs.x,
+ y + rhs.y,
+ z + rhs.z
+ );
+ }
+
+ Vector3 operator-(const Vector3 &rhs) const {
+ return Vector3<T>(
+ x - rhs.x,
+ y - rhs.y,
+ z - rhs.z
+ );
+ }
+
+ Vector3 operator-() const {
+ return Vector3<T> (
+ -x,
+ -y,
+ -z
+ );
+ }
+
+ Vector3 operator*(const Vector3 &rhs) const {
+ return Vector3<T>(
+ x * rhs.x,
+ y * rhs.y,
+ z * rhs.z
+ );
+ }
+
+ Vector3 operator/(const Vector3 &rhs) const {
+ return Vector3<T>(
+ x / rhs.x,
+ y / rhs.y,
+ z / rhs.z
+ );
+ }
+
+ bool operator==(const Vector3 &rhs) const {
+ return (x == rhs.x && y == rhs.y && z == rhs.z);
+ }
+
+ bool operator!=(const Vector3 &rhs) const {
+ return !(*this == rhs);
+ }
+
+ bool operator<(const Vector3 &rhs) const {
+ if (x < rhs.x)
+ return true;
+ if (rhs.x < x)
+ return false;
+ if (y < rhs.y)
+ return true;
+ if (rhs.y < y)
+ return false;
+ return z < rhs.z;
+ }
+
+
+ friend std::ostream &operator<<(std::ostream &os, const Vector3 &vector3) {
+ os << vector3.x << ", " << vector3.y << ", " << vector3.z;
+ return os;
+ }
};
using VectorF = Vector3<double>;
diff --git a/src/World.cpp b/src/World.cpp
index 4678964..59399f5 100644
--- a/src/World.cpp
+++ b/src/World.cpp
@@ -21,13 +21,13 @@ void World::ParseChunkData(std::shared_ptr<PacketChunkData> packet) {
if (!sections.insert(std::make_pair(chunkPosition, std::make_unique<Section>(section))).second) {
LOG(ERROR) << "New chunk not created " << chunkPosition << " potential memory leak";
}
+
UpdateSectionsList();
+ } else {
+ std::swap(*sections.at(chunkPosition).get(), section);
}
- else {
- using std::swap;
- swap(*sections.at(chunkPosition).get(), section);
- }
- PUSH_EVENT("ChunkChanged", chunkPosition);
+
+ PUSH_EVENT("ChunkChanged", chunkPosition);
}
}
}
@@ -53,7 +53,9 @@ Section World::ParseSection(StreamInput *data, Vector position) {
std::vector<long long> blockArray(blockData, blockData + dataArray.size() / sizeof(long long));
- return Section(position, bitsPerBlock, std::move(palette), std::move(blockArray), std::move(blockLight), std::move(skyLight));
+ return Section(
+ position, bitsPerBlock, std::move(palette),std::move(blockArray),
+ std::move(blockLight), std::move(skyLight));
}
World::~World() {
@@ -64,7 +66,8 @@ World::World() {
bool World::isPlayerCollides(double X, double Y, double Z) {
Vector PlayerChunk(floor(X / 16.0), floor(Y / 16.0), floor(Z / 16.0));
- if (sections.find(PlayerChunk) == sections.end() || sections.find(PlayerChunk - Vector(0, 1, 0)) == sections.end())
+ if (sections.find(PlayerChunk) == sections.end() ||
+ sections.find(PlayerChunk - Vector(0, 1, 0)) == sections.end())
return false;
std::vector<Vector> closestSectionsCoordinates = {
@@ -135,16 +138,17 @@ const Section &World::GetSection(Vector sectionPos) {
}
}
+// TODO: skip liquid blocks
RaycastResult World::Raycast(glm::vec3 position, glm::vec3 direction) {
const float maxLen = 5.0;
const float step = 0.01;
glm::vec3 pos;
- float len=0;
+ float len = 0;
Vector blockPos = Vector(position.x,position.y,position.z);
while (GetBlockId(blockPos) == BlockId{0, 0} && len <= maxLen) {
pos = position + direction * len;
len += step;
- blockPos = Vector(floor(pos.x),floor(pos.y),floor(pos.z));
+ blockPos = Vector(floor(pos.x), floor(pos.y), floor(pos.z));
}
RaycastResult result;
@@ -154,8 +158,7 @@ RaycastResult World::Raycast(glm::vec3 position, glm::vec3 direction) {
return result;
}
-void World::UpdatePhysics(float delta)
-{
+void World::UpdatePhysics(float delta) {
struct CollisionResult {
bool isCollide;
//Vector block;
@@ -164,7 +167,6 @@ void World::UpdatePhysics(float delta)
};
auto testCollision = [this](double width, double height, VectorF pos)->CollisionResult {
-
int blockXBegin = pos.x - width - 1.0;
int blockXEnd = pos.x + width + 0.5;
int blockYBegin = pos.y - 0.5;
@@ -211,6 +213,7 @@ void World::UpdatePhysics(float delta)
it.pos = newPos;
}
}
+
{ //Horizontal velocity
VectorF newPos = it.pos + VectorF(it.vel.x, 0, it.vel.z) * delta;
auto coll = testCollision(it.width, it.height, newPos);
@@ -231,8 +234,7 @@ void World::UpdatePhysics(float delta)
DebugInfo::totalSections = sections.size();
}
-Entity & World::GetEntity(unsigned int EntityId)
-{
+Entity& World::GetEntity(unsigned int EntityId){
entitiesMutex.lock();
for (auto& it : entities) {
if (it.entityId == EntityId) {
@@ -241,12 +243,12 @@ Entity & World::GetEntity(unsigned int EntityId)
}
}
entitiesMutex.unlock();
+
static Entity fallback;
return fallback;
}
-std::vector<unsigned int> World::GetEntitiesList()
-{
+std::vector<unsigned int> World::GetEntitiesList() {
entitiesMutex.lock();
std::vector<unsigned int> ret;
for (auto& it : entities) {
@@ -256,8 +258,7 @@ std::vector<unsigned int> World::GetEntitiesList()
return ret;
}
-void World::AddEntity(Entity entity)
-{
+void World::AddEntity(Entity entity) {
entitiesMutex.lock();
for (auto& it : entities) {
if (it.entityId == entity.entityId) {
@@ -270,8 +271,7 @@ void World::AddEntity(Entity entity)
entitiesMutex.unlock();
}
-void World::DeleteEntity(unsigned int EntityId)
-{
+void World::DeleteEntity(unsigned int EntityId) {
entitiesMutex.lock();
auto it = entities.begin();
for (; it != entities.end(); ++it) {
@@ -285,10 +285,16 @@ void World::DeleteEntity(unsigned int EntityId)
}
void World::ParseChunkData(std::shared_ptr<PacketBlockChange> packet) {
- SetBlockId(packet->Position, BlockId{(unsigned short) (packet->BlockId >> 4),(unsigned char) (packet->BlockId & 0xF) });
-
- Vector sectionPos(std::floor(packet->Position.x / 16.0), std::floor(packet->Position.y / 16.0), std::floor(packet->Position.z / 16.0));
- PUSH_EVENT("ChunkChanged", sectionPos);
+ SetBlockId(packet->Position,
+ BlockId {
+ (unsigned short) (packet->BlockId >> 4),
+ (unsigned char) (packet->BlockId & 0xF)
+ });
+
+ Vector sectionPos(std::floor(packet->Position.x / 16.0),
+ std::floor(packet->Position.y / 16.0),
+ std::floor(packet->Position.z / 16.0));
+ PUSH_EVENT("ChunkChanged", sectionPos);
}
void World::ParseChunkData(std::shared_ptr<PacketMultiBlockChange> packet) {
@@ -306,7 +312,7 @@ void World::ParseChunkData(std::shared_ptr<PacketMultiBlockChange> packet) {
}
for (auto& sectionPos : changedSections)
- PUSH_EVENT("ChunkChanged", sectionPos);
+ PUSH_EVENT("ChunkChanged", sectionPos);
}
void World::ParseChunkData(std::shared_ptr<PacketUnloadChunk> packet) {
@@ -316,7 +322,7 @@ void World::ParseChunkData(std::shared_ptr<PacketUnloadChunk> packet) {
toRemove.push_back(it);
}
for (auto& it : toRemove) {
- PUSH_EVENT("ChunkDeleted", it->first);
+ PUSH_EVENT("ChunkDeleted", it->first);
sections.erase(it);
}
UpdateSectionsList();
@@ -332,14 +338,19 @@ void World::UpdateSectionsList() {
}
BlockId World::GetBlockId(Vector pos) {
- Vector sectionPos(std::floor(pos.x / 16.0), std::floor(pos.y / 16.0), std::floor(pos.z / 16.0));
+ Vector sectionPos(std::floor(pos.x / 16.0),
+ std::floor(pos.y / 16.0),
+ std::floor(pos.z / 16.0));
Section* section = GetSectionPtr(sectionPos);
return !section ? BlockId{0, 0} : section->GetBlockId(pos - (sectionPos * 16));
}
void World::SetBlockId(Vector pos, BlockId block) {
- Vector sectionPos(std::floor(pos.x / 16.0), std::floor(pos.y / 16.0), std::floor(pos.z / 16.0));
+ Vector sectionPos(std::floor(pos.x / 16.0),
+ std::floor(pos.y / 16.0),
+ std::floor(pos.z / 16.0));
+
Section* section = GetSectionPtr(sectionPos);
section->SetBlockId(pos - (sectionPos * 16), block);
PUSH_EVENT("ChunkChanged",sectionPos);
diff --git a/src/main.cpp b/src/main.cpp
index eac2417..cb2daa8 100644
--- a/src/main.cpp
+++ b/src/main.cpp
@@ -47,7 +47,7 @@ int main(int argc, char** argv) {
LOG(ERROR) << e.what();
return -1;
}
-
+
GlobalState::Exec();
return 0;