From 51bcbfa03fc9797488e1169c99e731dd2d01967f Mon Sep 17 00:00:00 2001 From: Ben Date: Sat, 5 Sep 2020 21:10:18 +0100 Subject: [PATCH] COLLISIONS, i forgot to commit but i also did a lot of other shit --- TODO | 18 +- The Great Machine/Camera.cpp | 3 +- The Great Machine/Collisions.cpp | 54 +- The Great Machine/Collisions.hpp | 5 +- The Great Machine/Dungeon.cpp | 130 ++- The Great Machine/Dungeon.hpp | 4 +- The Great Machine/olcPixelGameEngine.hpp | 1352 +++++++++++----------- The Great Machine/res/torch.png | Bin 0 -> 81107 bytes res/torch.png | Bin 0 -> 81107 bytes 9 files changed, 847 insertions(+), 719 deletions(-) create mode 100644 The Great Machine/res/torch.png create mode 100644 res/torch.png diff --git a/TODO b/TODO index 8375f5a..ad047c8 100644 --- a/TODO +++ b/TODO @@ -1,7 +1,17 @@ [x] Dungeon generation [x] Tile movement / playable character -[-] Tile collisions -[ ] Lighting -[ ] Gameplay - [ ] Actually figure out Gameplay +[X] Tile collisions + +# Today + +[-] Lighting (and torches) +[ ] Lighting flicker (fire) +[ ] NO TIME raytraced lighting +[ ] Fix collision +[ ] Better player spritesheet +[ ] Animation system +[ ] Enemies / AI +[ ] Dungeon fixed entity spawning +[ ] Enemy AI +[ ] Gameplay diff --git a/The Great Machine/Camera.cpp b/The Great Machine/Camera.cpp index 34fd206..053a758 100644 --- a/The Great Machine/Camera.cpp +++ b/The Great Machine/Camera.cpp @@ -8,8 +8,7 @@ void Camera::Update(float fTime) { if (_Track == nullptr) return; - _DesiredCoords.x = _Track->Coords.x - (ViewPort.x / 2); - _DesiredCoords.y = _Track->Coords.y - (ViewPort.y / 2); + _DesiredCoords = _Track->Coords - (ViewPort / 2); float lerpX = std::lerp(Coords.x, _DesiredCoords.x, _SmoothSpeed); float lerpY = std::lerp(Coords.y, _DesiredCoords.y, _SmoothSpeed); diff --git a/The Great Machine/Collisions.cpp b/The Great Machine/Collisions.cpp index d5eaf7c..4b3229e 100644 --- a/The Great Machine/Collisions.cpp +++ b/The Great Machine/Collisions.cpp @@ -1,18 +1,64 @@ #include "Collisions.hpp" -#include "Camera.hpp" -#include "Things.hpp" #include "Logger.hpp" +#include "Things.hpp" +#include "Camera.hpp" +#include "Collisions.hpp" bool EntityCollide(Entity* entity, std::vector& nearby, int tileSize, CollisionInfo* info, olc::PixelGameEngine* engine) { if (!entity->HitBox) return false; + static Logger& _Logger = Logger::getInstance(); + + engine->SetDrawTarget(uint8_t(0)); + engine->Clear(olc::BLANK); + + float entityX = static_cast(entity->Coords.x - entity->TrackingCamera->Coords.x); + float entityY = static_cast(entity->Coords.y - entity->TrackingCamera->Coords.y); + float entityW = static_cast(tileSize / 3.0f) * 2.0f; + float entityH = static_cast(tileSize / 3.0f) * 2.0f; + + int entityLeft = static_cast(entityX); + int entityRight = static_cast(entityX + entityW); + int entityTop = static_cast(entityY); + int entityBottom = static_cast(entityY + entityH); + + //engine->DrawRect({(entity->HitBox->x + (int)entity->Coords.x) - (int)entity->TrackingCamera->Coords.x, (entity->HitBox->y + (int)entity->Coords.y) - (int)entity->TrackingCamera->Coords.y}, {entity->HitBox->w, entity->HitBox->h}, olc::RED); + for (auto tile : nearby) { - Logger::getInstance().Debug(tile->Coords.x, " ", tile->Coords.y); - engine->DrawRect({ static_cast((tile->Coords.x + tileSize) - entity->TrackingCamera->Coords.x), static_cast((tile->Coords.y + tileSize) - entity->TrackingCamera->Coords.y) }, {tileSize, tileSize}, olc::RED); + //engine->DrawRect({ static_cast(static_cast((tile->Coords.x * tileSize) - entity->TrackingCamera->Coords.x)), static_cast(static_cast((tile->Coords.y * tileSize) - entity->TrackingCamera->Coords.y)) }, {tileSize, tileSize}, olc::BLUE); + + // return if not collidable + if (!tile->IsSolid) continue; + + int tileLeft = static_cast(static_cast(tile->Coords.x * tileSize) - entity->TrackingCamera->Coords.x); + int tileRight = static_cast(static_cast(tile->Coords.x * tileSize) - entity->TrackingCamera->Coords.x) + tileSize; + int tileTop = static_cast(static_cast(tile->Coords.y * tileSize) - entity->TrackingCamera->Coords.y); + int tileBottom = static_cast(static_cast(tile->Coords.y * tileSize) - entity->TrackingCamera->Coords.y) + tileSize; + + // _Logger.Debug(entityLeft, " ", tileRight); + + bool xOverlaps = (entityLeft <= tileRight) && (entityRight >= tileLeft); + bool yOverlaps = (entityTop <= tileBottom) && (entityBottom >= tileTop); + + bool collision = xOverlaps && yOverlaps; + + //engine->FillRect({static_cast(static_cast((tile->Coords.x * tileSize) - entity->TrackingCamera->Coords.x)), static_cast(static_cast((tile->Coords.y * tileSize) - entity->TrackingCamera->Coords.y))}, {tileSize, tileSize}, collision ? olc::RED : olc::BLUE); + + if (!collision) continue; + + info->TileCollided = tile; + + //info->CollidingX = xOverlaps; + //info->CollidingY = yOverlaps; + + return true; + } + return false; + } diff --git a/The Great Machine/Collisions.hpp b/The Great Machine/Collisions.hpp index afdcc22..4889718 100644 --- a/The Great Machine/Collisions.hpp +++ b/The Great Machine/Collisions.hpp @@ -18,10 +18,13 @@ class Collider class CollisionInfo { public: - + Tile* TileCollided; + bool CollidingX; + bool CollidingY; }; bool EntityCollide(Entity* entity, std::vector& nearby, int tileSize, CollisionInfo* info, olc::PixelGameEngine* engine); #endif + diff --git a/The Great Machine/Dungeon.cpp b/The Great Machine/Dungeon.cpp index 08be288..b79025c 100644 --- a/The Great Machine/Dungeon.cpp +++ b/The Great Machine/Dungeon.cpp @@ -17,18 +17,14 @@ Dungeon::Dungeon() Player = new Playable(); - Player->Coords = { 0, 0 }; + Player->Coords = { 2, 2 }; Player->Type = EEntity::Type::Player; // Relative to player TL corner + // not really used ? lol Player->HitBox = new Collider{ 0, 0, static_cast((static_cast(TileSize) / 3.0f) * 2.0f), static_cast((static_cast(TileSize) / 3.0f) * 2.0f) } ; ActiveCamera->TrackEntity(Player); ActiveCamera->Update(0.0f); -} - -void Dungeon::Generate() -{ - srand(time(NULL)); TileSetDictionary = new TileDictionary(); TileSetDictionary->Register(); @@ -37,6 +33,15 @@ void Dungeon::Generate() TileSet->Load("res/dungeon_tileset.png"); _Logger.Debug("Texture Loaded: ", TileSet, " ", TileSet->Sprite()->width, " ", TileSet->Sprite()->height); + FireOverlay = new olc::Renderable(); + FireOverlay->Load("res/torch.png"); + +} + +void Dungeon::Generate() +{ + srand(time(NULL)); + DungeonWidth = 0; DungeonHeight = 0; @@ -58,7 +63,7 @@ void Dungeon::Generate() int directionChance = 5; int roomChance = 5; - int dungeonMinSize = 5000; + int dungeonMinSize = 3000; struct Agent { @@ -188,6 +193,8 @@ void Dungeon::SpawnEntity(Entity* entity) void Dungeon::Input(olc::PixelGameEngine* engine, float fTime) { + olc::vf2d oldCoords = Player->Coords; + if (engine->GetKey(olc::W).bHeld) Player->Coords.y -= static_cast(TileSize) * (fTime * Player->Speed); if (engine->GetKey(olc::A).bHeld) @@ -217,55 +224,95 @@ void Dungeon::Input(olc::PixelGameEngine* engine, float fTime) Player->Coords.y -= static_cast(TileSize) * (fTime * (Player->Speed / 3.0f)); Player->Coords.x += static_cast(TileSize) * (fTime * (Player->Speed / 3.0f)); } -} - -void Dungeon::Update(olc::PixelGameEngine* engine, float fTime) -{ // Map collisions - olc::vi2d currentTile = { static_cast(Player->Coords.x / TileSize), static_cast(Player->Coords.y / TileSize) }; static olc::vi2d lastTile; - auto IsMapMember = [&] (int x, int y) { - std::unordered_map::const_iterator found = DungeonTiles.find({x, y}); - if (found == DungeonTiles.end()) return false; - return false; - }; - if (lastTile != currentTile) _Logger.Debug("Player Tile: ", currentTile.x, " ", currentTile.y); + auto IsMapMember = [&] (int x, int y) { + std::unordered_map::const_iterator found = DungeonTiles.find({x, y}); + return found != DungeonTiles.end(); + }; + + auto IsNeighbouringMapMember = [&] (int x, int y) { + if (IsMapMember(x + 1, y)) return true; + if (IsMapMember(x - 1, y)) return true; + if (IsMapMember(x, y + 1)) return true; + if (IsMapMember(x, y - 1)) return true; + return false; + }; + // get nearby collidables std::vector nearbyCollidables; - for (int x = currentTile.x - 2; x <= currentTile.x + 2; x++) - for (int y = currentTile.y - 2; y <= currentTile.y + 2; y++) + for (int x = currentTile.x - 1; x <= currentTile.x + 1; x++) + for (int y = currentTile.y - 1; y <= currentTile.y + 1; y++) { + //_Logger.Debug("IsMapMember ", x, " ", y, " ", IsMapMember(x,y)); + //_Logger.Debug("IsNeighbouringMapMember ", x, " ", y, " ", IsNeighbouringMapMember(x,y)); + + // If isnt in the map but borders a map tile, add a void type for collision if (IsMapMember(x,y)) + { nearbyCollidables.push_back(DungeonTiles[{x, y}]); + } else + { + if (IsNeighbouringMapMember(x,y)) + nearbyCollidables.push_back(new Tile({x, y}, ETile::Type::Void, ETile::State::Default)); + } } // Passes ownership back - CollisionInfo* collisionInfo = new CollisionInfo(); - bool colliding = EntityCollide(Player, nearbyCollidables, TileSize, collisionInfo, engine); + CollisionInfo collisionInfo; + bool colliding = EntityCollide(Player, nearbyCollidables, TileSize, &collisionInfo, engine); - delete collisionInfo; + // collision response + if (colliding) + Player->Coords = oldCoords; + + //if (collisionInfo.CollidingY) + //Player->Coords.y = oldCoords.y; + //if (collisionInfo.CollidingX) + //Player->Coords.x = oldCoords.x; + + // delete nearbyCollidables that are void + for (int i = 0; i < nearbyCollidables.size(); i++) + { + if (nearbyCollidables[i]->Type == ETile::Type::Void) + delete nearbyCollidables[i]; + } lastTile = currentTile; +} + +void Dungeon::Update(olc::PixelGameEngine* engine, float fTime) +{ ActiveCamera->Update(fTime); } +olc::Pixel pixelMultiply(const int x, const int y, const olc::Pixel& pSource, const olc::Pixel& pDest) +{ + olc::Pixel ret; + ret.r = pDest.r * pSource.r; + ret.g = pDest.g * pSource.g; + ret.b = pDest.b * pSource.b; + ret.a = pDest.a * pSource.a; + return ret; +} + void Dungeon::Draw(olc::PixelGameEngine* engine) { // Maps not gonna be big enough for me to care about optimistaion - // maybe i should care? i don't :^) + // maybe i should care? i don't - //engine->SetDrawTarget(4); - //engine->Clear({38, 36, 40}); + // Entities are always (tilesize / 3) * 2 - engine->SetDrawTarget(1); + // Dungeon Layer + engine->SetDrawTarget(4); engine->Clear({38, 36, 40}); engine->SetPixelMode(olc::Pixel::ALPHA); @@ -279,14 +326,38 @@ void Dungeon::Draw(olc::PixelGameEngine* engine) // engine->SetPixelMode(olc::Pixel::NORMAL); - engine->SetDrawTarget(static_cast(0)); + // Entity Layer + engine->SetDrawTarget(3); engine->Clear(olc::BLANK); // Draw character engine->DrawPartialDecal({ static_cast(Player->Coords.x - ActiveCamera->Coords.x), static_cast(Player->Coords.y - ActiveCamera->Coords.y) }, { (static_cast(TileSize) / 3.0f) * 2.0f, (static_cast(TileSize) / 3.0f) * 2.0f }, TileSet->Decal(), { 143, 130 }, { 16, 16 }); - engine->DrawRect({(Player->HitBox->x + (int)Player->Coords.x) - (int)ActiveCamera->Coords.x, (Player->HitBox->y + (int)Player->Coords.y) - (int)ActiveCamera->Coords.y}, {Player->HitBox->w, Player->HitBox->h}, olc::RED); + // Lighting layers + engine->SetDrawTarget(2); + engine->Clear(olc::BLANK); + + static std::function fPixelMultiply = pixelMultiply; + + float lightX = static_cast(Player->Coords.x - ActiveCamera->Coords.x) - (FireOverlay->Sprite()->width / 2.0f); + float lightY = static_cast(Player->Coords.y - ActiveCamera->Coords.y) - (FireOverlay->Sprite()->height / 2.0f); + + float lightLeft = lightX; + float lightRight = lightX + FireOverlay->Sprite()->width; + float lightTop = lightY; + float lightBottom = lightY + FireOverlay->Sprite()->height; + + engine->SetPixelMode(fPixelMultiply); + engine->DrawDecal({ lightX, lightY }, FireOverlay->Decal()); + + engine->SetDrawTarget(1); + engine->Clear(olc::BLANK); + // top + + engine->FillRect({0, static_cast(lightTop)}, {engine->ScreenWidth(), engine->ScreenHeight()}, olc::BLACK); + + } Dungeon::~Dungeon() @@ -295,7 +366,6 @@ Dungeon::~Dungeon() delete ActiveCamera; delete TileSetDictionary; delete TileSet; - delete DungeonRenderTarget; for (std::pair tile : DungeonTiles) delete tile.second; for (std::pair entity : Entities) diff --git a/The Great Machine/Dungeon.hpp b/The Great Machine/Dungeon.hpp index 410ce67..433d6a9 100644 --- a/The Great Machine/Dungeon.hpp +++ b/The Great Machine/Dungeon.hpp @@ -31,7 +31,7 @@ class Dungeon Playable* Player; Camera* ActiveCamera; - int TileSize = 32; + int TileSize = 64; int DungeonWidth; int DungeonHeight; @@ -42,7 +42,7 @@ class Dungeon TileDictionary* TileSetDictionary; olc::Renderable* TileSet; - olc::Renderable* DungeonRenderTarget; + olc::Renderable* FireOverlay; ~Dungeon(); diff --git a/The Great Machine/olcPixelGameEngine.hpp b/The Great Machine/olcPixelGameEngine.hpp index a4c6fb3..e72a16c 100644 --- a/The Great Machine/olcPixelGameEngine.hpp +++ b/The Great Machine/olcPixelGameEngine.hpp @@ -283,12 +283,12 @@ int main() #endif #if defined(USE_EXPERIMENTAL_FS) || defined(FORCE_EXPERIMENTAL_FS) - // C++14 +// C++14 #define _SILENCE_EXPERIMENTAL_FILESYSTEM_DEPRECATION_WARNING #include namespace _gfs = std::experimental::filesystem::v1; #else - // C++17 +// C++17 #include namespace _gfs = std::filesystem; #endif @@ -329,13 +329,13 @@ namespace olc { class PixelGameEngine; class Sprite; - + // Pixel Game Engine Advanced Configuration constexpr uint8_t nMouseButtons = 5; constexpr uint8_t nDefaultAlpha = 0xFF; constexpr uint32_t nDefaultPixel = (nDefaultAlpha << 24); enum rcode { FAIL = 0, OK = 1, NO_FILE = -1 }; - + // O------------------------------------------------------------------------------O // | olc::Pixel - Represents a 32-Bit RGBA colour | // O------------------------------------------------------------------------------O @@ -346,33 +346,33 @@ namespace olc uint32_t n = nDefaultPixel; struct { uint8_t r; uint8_t g; uint8_t b; uint8_t a; }; }; - + enum Mode { NORMAL, MASK, ALPHA, CUSTOM }; - + Pixel(); Pixel(uint8_t red, uint8_t green, uint8_t blue, uint8_t alpha = nDefaultAlpha); Pixel(uint32_t p); bool operator==(const Pixel& p) const; bool operator!=(const Pixel& p) const; }; - + Pixel PixelF(float red, float green, float blue, float alpha = 1.0f); - - - + + + // O------------------------------------------------------------------------------O // | USEFUL CONSTANTS | // O------------------------------------------------------------------------------O static const Pixel GREY(192, 192, 192), DARK_GREY(128, 128, 128), VERY_DARK_GREY(64, 64, 64), - RED(255, 0, 0), DARK_RED(128, 0, 0), VERY_DARK_RED(64, 0, 0), - YELLOW(255, 255, 0), DARK_YELLOW(128, 128, 0), VERY_DARK_YELLOW(64, 64, 0), - GREEN(0, 255, 0), DARK_GREEN(0, 128, 0), VERY_DARK_GREEN(0, 64, 0), - CYAN(0, 255, 255), DARK_CYAN(0, 128, 128), VERY_DARK_CYAN(0, 64, 64), - BLUE(0, 0, 255), DARK_BLUE(0, 0, 128), VERY_DARK_BLUE(0, 0, 64), - MAGENTA(255, 0, 255), DARK_MAGENTA(128, 0, 128), VERY_DARK_MAGENTA(64, 0, 64), - WHITE(255, 255, 255), BLACK(0, 0, 0), BLANK(0, 0, 0, 0); - + RED(255, 0, 0), DARK_RED(128, 0, 0), VERY_DARK_RED(64, 0, 0), + YELLOW(255, 255, 0), DARK_YELLOW(128, 128, 0), VERY_DARK_YELLOW(64, 64, 0), + GREEN(0, 255, 0), DARK_GREEN(0, 128, 0), VERY_DARK_GREEN(0, 64, 0), + CYAN(0, 255, 255), DARK_CYAN(0, 128, 128), VERY_DARK_CYAN(0, 64, 64), + BLUE(0, 0, 255), DARK_BLUE(0, 0, 128), VERY_DARK_BLUE(0, 0, 64), + MAGENTA(255, 0, 255), DARK_MAGENTA(128, 0, 128), VERY_DARK_MAGENTA(64, 0, 64), + WHITE(255, 255, 255), BLACK(0, 0, 0), BLANK(0, 0, 0, 0); + enum Key { NONE, @@ -385,15 +385,15 @@ namespace olc NP0, NP1, NP2, NP3, NP4, NP5, NP6, NP7, NP8, NP9, NP_MUL, NP_DIV, NP_ADD, NP_SUB, NP_DECIMAL, PERIOD }; - - - + + + // O------------------------------------------------------------------------------O // | olc::vX2d - A generic 2D vector type | // O------------------------------------------------------------------------------O #if !defined(OLC_IGNORE_VEC2D) template - struct v2d_generic + struct v2d_generic { T x = 0; T y = 0; @@ -427,7 +427,7 @@ namespace olc operator v2d_generic() const { return { static_cast(this->x), static_cast(this->y) }; } operator v2d_generic() const { return { static_cast(this->x), static_cast(this->y) }; } }; - + // Note: joshinils has some good suggestions here, but they are complicated to implement at this moment, // however they will appear in a future version of PGE template inline v2d_generic operator * (const float& lhs, const v2d_generic& rhs) @@ -454,7 +454,7 @@ namespace olc { return v2d_generic((T)(lhs / (int)rhs.x), (T)(lhs / (int)rhs.y)); } - + typedef v2d_generic vi2d; typedef v2d_generic vu2d; typedef v2d_generic vf2d; @@ -465,7 +465,7 @@ namespace olc namespace std { template <> - struct hash + struct hash { std::size_t operator()(const olc::vi2d& k) const { @@ -476,20 +476,20 @@ namespace std } }; template <> - struct hash + struct hash { std::size_t operator()(const olc::vf2d& k) const { uint64_t h1 = static_cast(k.x) << 31; uint64_t h2 = static_cast(k.y) << 31; - + return h1 ^ h2; } }; } namespace olc { - + // O------------------------------------------------------------------------------O // | olc::HWButton - Represents the state of a hardware button (mouse/key/joy) | // O------------------------------------------------------------------------------O @@ -499,9 +499,9 @@ namespace olc { bool bReleased = false; // Set once during the frame the event occurs bool bHeld = false; // Set true for all frames between pressed and released events }; - - - + + + // O------------------------------------------------------------------------------O // | olc::ResourcePack - A virtual scrambled filesystem to pack your assets into | // O------------------------------------------------------------------------------O @@ -510,10 +510,10 @@ namespace olc { ResourceBuffer(std::ifstream& ifs, uint32_t offset, uint32_t size); std::vector vMemory; }; - + class ResourcePack : public std::streambuf { - public: + public: ResourcePack(); ~ResourcePack(); bool AddFile(const std::string& sFile); @@ -521,49 +521,49 @@ namespace olc { bool SavePack(const std::string& sFile, const std::string& sKey); ResourceBuffer GetFileBuffer(const std::string& sFile); bool Loaded(); - private: + private: struct sResourceFile { uint32_t nSize; uint32_t nOffset; }; std::map mapFiles; std::ifstream baseFile; std::vector scramble(const std::vector& data, const std::string& key); std::string makeposix(const std::string& path); }; - - + + class ImageLoader { - public: + public: ImageLoader() = default; virtual ~ImageLoader() = default; virtual olc::rcode LoadImageResource(olc::Sprite* spr, const std::string& sImageFile, olc::ResourcePack* pack) = 0; virtual olc::rcode SaveImageResource(olc::Sprite* spr, const std::string& sImageFile) = 0; }; - - + + // O------------------------------------------------------------------------------O // | olc::Sprite - An image represented by a 2D array of olc::Pixel | // O------------------------------------------------------------------------------O class Sprite { - public: + public: Sprite(); Sprite(const std::string& sImageFile, olc::ResourcePack* pack = nullptr); Sprite(int32_t w, int32_t h); Sprite(const olc::Sprite&) = delete; ~Sprite(); - - public: + + public: olc::rcode LoadFromFile(const std::string& sImageFile, olc::ResourcePack* pack = nullptr); olc::rcode LoadFromPGESprFile(const std::string& sImageFile, olc::ResourcePack* pack = nullptr); olc::rcode SaveToPGESprFile(const std::string& sImageFile); - - public: + + public: int32_t width = 0; int32_t height = 0; enum Mode { NORMAL, PERIODIC }; enum Flip { NONE = 0, HORIZ = 1, VERT = 2 }; - - public: + + public: void SetSampleMode(olc::Sprite::Mode mode = olc::Sprite::Mode::NORMAL); Pixel GetPixel(int32_t x, int32_t y) const; bool SetPixel(int32_t x, int32_t y, Pixel p); @@ -576,49 +576,49 @@ namespace olc { olc::Sprite* Duplicate(const olc::vi2d& vPos, const olc::vi2d& vSize); Pixel* pColData = nullptr; Mode modeSample = Mode::NORMAL; - + static std::unique_ptr loader; }; - + // O------------------------------------------------------------------------------O // | olc::Decal - A GPU resident storage of an olc::Sprite | // O------------------------------------------------------------------------------O class Decal { - public: + public: Decal(olc::Sprite* spr); virtual ~Decal(); void Update(); - - public: // But dont touch + + public: // But dont touch int32_t id = -1; olc::Sprite* sprite = nullptr; olc::vf2d vUVScale = { 1.0f, 1.0f }; }; - + // O------------------------------------------------------------------------------O // | olc::Renderable - Convenience class to keep a sprite and decal together | // O------------------------------------------------------------------------------O class Renderable { - public: + public: Renderable() = default; virtual ~Renderable() = default; olc::rcode Load(const std::string& sFile, ResourcePack* pack = nullptr); void Create(uint32_t width, uint32_t height); olc::Decal* Decal() const; olc::Sprite* Sprite() const; - - private: + + private: std::unique_ptr pSprite = nullptr; std::unique_ptr pDecal = nullptr; }; - - + + // O------------------------------------------------------------------------------O // | Auxilliary components internal to engine | // O------------------------------------------------------------------------------O - + struct DecalInstance { olc::Decal* decal = nullptr; @@ -627,7 +627,7 @@ namespace olc { float w[4] = { 1, 1, 1, 1 }; olc::Pixel tint[4] = { olc::WHITE, olc::WHITE, olc::WHITE, olc::WHITE };; }; - + struct DecalTriangleInstance { olc::vf2d points[3]; @@ -635,7 +635,7 @@ namespace olc { olc::Pixel colours[3]; olc::Decal* decal = nullptr; }; - + struct LayerDesc { olc::vf2d vOffset = { 0, 0 }; @@ -648,10 +648,10 @@ namespace olc { olc::Pixel tint = olc::WHITE; std::function funcHook = nullptr; }; - + class Renderer { - public: + public: virtual ~Renderer() = default; virtual void PrepareDevice() = 0; virtual olc::rcode CreateDevice(std::vector params, bool bFullScreen, bool bVSYNC) = 0; @@ -668,10 +668,10 @@ namespace olc { virtual void ClearBuffer(olc::Pixel p, bool bDepth) = 0; static olc::PixelGameEngine* ptrPGE; }; - + class Platform { - public: + public: virtual ~Platform() = default; virtual olc::rcode ApplicationStartUp() = 0; virtual olc::rcode ApplicationCleanUp() = 0; @@ -684,35 +684,35 @@ namespace olc { virtual olc::rcode HandleSystemEvent() = 0; static olc::PixelGameEngine* ptrPGE; }; - - - + + + static std::unique_ptr renderer; static std::unique_ptr platform; static std::map mapKeys; - + // O------------------------------------------------------------------------------O // | olc::PixelGameEngine - The main BASE class for your application | // O------------------------------------------------------------------------------O class PixelGameEngine { - public: + public: PixelGameEngine(); virtual ~PixelGameEngine(); - public: + public: olc::rcode Construct(int32_t screen_w, int32_t screen_h, int32_t pixel_w, int32_t pixel_h, - bool full_screen = false, bool vsync = false, bool cohesion = false); + bool full_screen = false, bool vsync = false, bool cohesion = false); olc::rcode Start(); - - public: // User Override Interfaces + + public: // User Override Interfaces // Called once on application startup, use to load your resources virtual bool OnUserCreate(); // Called every frame, and provides you with a time per frame value virtual bool OnUserUpdate(float fElapsedTime); // Called once on application termination, so you can be one clean coder virtual bool OnUserDestroy(); - - public: // Hardware Interfaces + + public: // Hardware Interfaces // Returns true if window is currently in focus bool IsFocused() const; // Get the state of a specific keyboard button @@ -729,8 +729,8 @@ namespace olc { const olc::vi2d& GetWindowMouse() const; // Gets the mouse as a vector to keep Tarriest happy const olc::vi2d& GetMousePos() const; - - public: // Utility + + public: // Utility // Returns the width of the screen in "pixels" int32_t ScreenWidth() const; // Returns the height of the screen in "pixels" @@ -756,8 +756,8 @@ namespace olc { const olc::vi2d& GetPixelSize() const; // Gets actual pixel scale const olc::vi2d& GetScreenPixelSize() const; - - public: // CONFIGURATION ROUTINES + + public: // CONFIGURATION ROUTINES // Layer targeting functions void SetDrawTarget(uint8_t layer); void EnableLayer(uint8_t layer, bool b); @@ -767,10 +767,10 @@ namespace olc { void SetLayerScale(uint8_t layer, float x, float y); void SetLayerTint(uint8_t layer, const olc::Pixel& tint); void SetLayerCustomRenderFunction(uint8_t layer, std::function f); - + std::vector& GetLayers(); uint32_t CreateLayer(); - + // Change the pixel mode for different optimisations // olc::Pixel::NORMAL = No transparency // olc::Pixel::MASK = Transparent if alpha is < 255 @@ -781,10 +781,10 @@ namespace olc { void SetPixelMode(std::function pixelMode); // Change the blend factor form between 0.0f to 1.0f; void SetPixelBlend(float fBlend); - - - - public: // DRAWING ROUTINES + + + + public: // DRAWING ROUTINES // Draws a single Pixel virtual bool Draw(int32_t x, int32_t y, Pixel p = olc::WHITE); bool Draw(const olc::vi2d& pos, Pixel p = olc::WHITE); @@ -816,9 +816,9 @@ namespace olc { // selected area is (ox,oy) to (ox+w,oy+h) void DrawPartialSprite(int32_t x, int32_t y, Sprite* sprite, int32_t ox, int32_t oy, int32_t w, int32_t h, uint32_t scale = 1, uint8_t flip = olc::Sprite::NONE); void DrawPartialSprite(const olc::vi2d& pos, Sprite* sprite, const olc::vi2d& sourcepos, const olc::vi2d& size, uint32_t scale = 1, uint8_t flip = olc::Sprite::NONE); - + // Decal Quad functions - + // Draws a whole decal, with optional scale and tinting void DrawDecal(const olc::vf2d& pos, olc::Decal* decal, const olc::vf2d& scale = { 1.0f,1.0f }, const olc::Pixel& tint = olc::WHITE); // Draws a region of a decal, with optional scale and tinting @@ -843,9 +843,9 @@ namespace olc { void FillRectDecal(const olc::vf2d& pos, const olc::vf2d& size, const olc::Pixel col = olc::WHITE); // Draws a corner shaded rectangle as a decal void GradientFillRectDecal(const olc::vf2d& pos, const olc::vf2d& size, const olc::Pixel colTL, const olc::Pixel colBL, const olc::Pixel colBR, const olc::Pixel colTR); - - - + + + // Draws a single line of text void DrawString(int32_t x, int32_t y, const std::string& sText, Pixel col = olc::WHITE, uint32_t scale = 1); void DrawString(const olc::vi2d& pos, const std::string& sText, Pixel col = olc::WHITE, uint32_t scale = 1); @@ -854,12 +854,12 @@ namespace olc { void Clear(Pixel p); // Clears the rendering back buffer void ClearBuffer(Pixel p, bool bDepth = true); - - - public: // Branding + + + public: // Branding std::string sAppName; - - private: // Inner mysterious workings + + private: // Inner mysterious workings Sprite* pDrawTarget = nullptr; Pixel::Mode nPixelMode = Pixel::NORMAL; float fBlendFactor = 1.0f; @@ -892,29 +892,29 @@ namespace olc { bool bPixelCohesion = false; std::function funcPixelMode; std::chrono::time_point m_tp1, m_tp2; - + // State of keyboard bool pKeyNewState[256] = { 0 }; bool pKeyOldState[256] = { 0 }; HWButton pKeyboardState[256] = { 0 }; - + // State of mouse bool pMouseNewState[nMouseButtons] = { 0 }; bool pMouseOldState[nMouseButtons] = { 0 }; HWButton pMouseState[nMouseButtons] = { 0 }; - + // The main engine thread void EngineThread(); - + // At the very end of this file, chooses which // components to compile void olc_ConfigureSystem(); - + // If anything sets this flag to false, the engine // "should" shut down gracefully static std::atomic bAtomActive; - - public: + + public: // "Break In" Functions void olc_UpdateMouse(int32_t x, int32_t y); void olc_UpdateMouseWheel(int32_t delta); @@ -928,23 +928,23 @@ namespace olc { void olc_UpdateMouseFocus(bool state); void olc_UpdateKeyFocus(bool state); void olc_Terminate(); - + // NOTE: Items Here are to be deprecated, I have left them in for now // in case you are using them, but they will be removed. // olc::vf2d vSubPixelOffset = { 0.0f, 0.0f }; - + friend class PGEX; }; - - - + + + // O------------------------------------------------------------------------------O // | PGE EXTENSION BASE CLASS - Permits access to PGE functions from extension | // O------------------------------------------------------------------------------O class PGEX { friend class olc::PixelGameEngine; - protected: + protected: static PixelGameEngine* pge; }; } @@ -992,33 +992,33 @@ namespace olc { r = 0; g = 0; b = 0; a = nDefaultAlpha; } - + Pixel::Pixel(uint8_t red, uint8_t green, uint8_t blue, uint8_t alpha) { n = red | (green << 8) | (blue << 16) | (alpha << 24); } // Thanks jarekpelczar - - + + Pixel::Pixel(uint32_t p) { n = p; } - + bool Pixel::operator==(const Pixel& p) const { return n == p.n; } - + bool Pixel::operator!=(const Pixel& p) const { return n != p.n; } - + Pixel PixelF(float red, float green, float blue, float alpha) { return Pixel(uint8_t(red * 255.0f), uint8_t(green * 255.0f), uint8_t(blue * 255.0f), uint8_t(alpha * 255.0f)); } - + // O------------------------------------------------------------------------------O // | olc::Sprite IMPLEMENTATION | // O------------------------------------------------------------------------------O @@ -1026,12 +1026,12 @@ namespace olc { pColData = nullptr; width = 0; height = 0; } - + Sprite::Sprite(const std::string& sImageFile, olc::ResourcePack* pack) { LoadFromFile(sImageFile, pack); } - + Sprite::Sprite(int32_t w, int32_t h) { if (pColData) delete[] pColData; @@ -1040,13 +1040,13 @@ namespace olc for (int32_t i = 0; i < width * height; i++) pColData[i] = Pixel(); } - + Sprite::~Sprite() { if (pColData) delete[] pColData; } - - + + olc::rcode Sprite::LoadFromPGESprFile(const std::string& sImageFile, olc::ResourcePack* pack) { if (pColData) delete[] pColData; @@ -1057,7 +1057,7 @@ namespace olc pColData = new Pixel[width * height]; is.read((char*)pColData, (size_t)width * (size_t)height * sizeof(uint32_t)); }; - + // These are essentially Memory Surfaces represented by olc::Sprite // which load very fast, but are completely uncompressed if (pack == nullptr) @@ -1081,11 +1081,11 @@ namespace olc } return olc::FAIL; } - + olc::rcode Sprite::SaveToPGESprFile(const std::string& sImageFile) { if (pColData == nullptr) return olc::FAIL; - + std::ofstream ofs; ofs.open(sImageFile, std::ifstream::binary); if (ofs.is_open()) @@ -1096,25 +1096,25 @@ namespace olc ofs.close(); return olc::OK; } - + return olc::FAIL; } - + void Sprite::SetSampleMode(olc::Sprite::Mode mode) { modeSample = mode; } - + Pixel Sprite::GetPixel(const olc::vi2d& a) const { return GetPixel(a.x, a.y); } - + bool Sprite::SetPixel(const olc::vi2d& a, Pixel p) { return SetPixel(a.x, a.y, p); } - + Pixel Sprite::GetPixel(int32_t x, int32_t y) const { if (modeSample == olc::Sprite::Mode::NORMAL) @@ -1129,7 +1129,7 @@ namespace olc return pColData[abs(y % height) * width + abs(x % width)]; } } - + bool Sprite::SetPixel(int32_t x, int32_t y, Pixel p) { if (x >= 0 && x < width && y >= 0 && y < height) @@ -1140,14 +1140,14 @@ namespace olc else return false; } - + Pixel Sprite::Sample(float x, float y) const { int32_t sx = std::min((int32_t)((x * (float)width)), width - 1); int32_t sy = std::min((int32_t)((y * (float)height)), height - 1); return GetPixel(sx, sy); } - + Pixel Sprite::SampleBL(float u, float v) const { u = u * width - 0.5f; @@ -1158,30 +1158,30 @@ namespace olc float v_ratio = v - y; float u_opposite = 1 - u_ratio; float v_opposite = 1 - v_ratio; - + olc::Pixel p1 = GetPixel(std::max(x, 0), std::max(y, 0)); olc::Pixel p2 = GetPixel(std::min(x + 1, (int)width - 1), std::max(y, 0)); olc::Pixel p3 = GetPixel(std::max(x, 0), std::min(y + 1, (int)height - 1)); olc::Pixel p4 = GetPixel(std::min(x + 1, (int)width - 1), std::min(y + 1, (int)height - 1)); - + return olc::Pixel( - (uint8_t)((p1.r * u_opposite + p2.r * u_ratio) * v_opposite + (p3.r * u_opposite + p4.r * u_ratio) * v_ratio), - (uint8_t)((p1.g * u_opposite + p2.g * u_ratio) * v_opposite + (p3.g * u_opposite + p4.g * u_ratio) * v_ratio), - (uint8_t)((p1.b * u_opposite + p2.b * u_ratio) * v_opposite + (p3.b * u_opposite + p4.b * u_ratio) * v_ratio)); + (uint8_t)((p1.r * u_opposite + p2.r * u_ratio) * v_opposite + (p3.r * u_opposite + p4.r * u_ratio) * v_ratio), + (uint8_t)((p1.g * u_opposite + p2.g * u_ratio) * v_opposite + (p3.g * u_opposite + p4.g * u_ratio) * v_ratio), + (uint8_t)((p1.b * u_opposite + p2.b * u_ratio) * v_opposite + (p3.b * u_opposite + p4.b * u_ratio) * v_ratio)); } - + Pixel* Sprite::GetData() { return pColData; } - - + + olc::rcode Sprite::LoadFromFile(const std::string& sImageFile, olc::ResourcePack* pack) { UNUSED(pack); return loader->LoadImageResource(this, sImageFile, pack); } - + olc::Sprite* Sprite::Duplicate() { olc::Sprite* spr = new olc::Sprite(width, height); @@ -1189,16 +1189,16 @@ namespace olc spr->modeSample = modeSample; return spr; } - + olc::Sprite* Sprite::Duplicate(const olc::vi2d& vPos, const olc::vi2d& vSize) { olc::Sprite* spr = new olc::Sprite(vSize.x, vSize.y); for (int y = 0; y < vSize.y; y++) for (int x = 0; x < vSize.x; x++) - spr->SetPixel(x, y, GetPixel(vPos.x + x, vPos.y + y)); + spr->SetPixel(x, y, GetPixel(vPos.x + x, vPos.y + y)); return spr; } - + // O------------------------------------------------------------------------------O // | olc::Decal IMPLEMENTATION | // O------------------------------------------------------------------------------O @@ -1210,7 +1210,7 @@ namespace olc id = renderer->CreateTexture(sprite->width, sprite->height); Update(); } - + void Decal::Update() { if (sprite == nullptr) return; @@ -1218,7 +1218,7 @@ namespace olc renderer->ApplyTexture(id); renderer->UpdateTexture(id, sprite); } - + Decal::~Decal() { if (id != -1) @@ -1227,13 +1227,13 @@ namespace olc id = -1; } } - + void Renderable::Create(uint32_t width, uint32_t height) { pSprite = std::make_unique(width, height); pDecal = std::make_unique(pSprite.get()); } - + olc::rcode Renderable::Load(const std::string& sFile, ResourcePack* pack) { pSprite = std::make_unique(); @@ -1249,22 +1249,22 @@ namespace olc return olc::rcode::NO_FILE; } } - + olc::Decal* Renderable::Decal() const { return pDecal.get(); } - + olc::Sprite* Renderable::Sprite() const { return pSprite.get(); } - + // O------------------------------------------------------------------------------O // | olc::ResourcePack IMPLEMENTATION | // O------------------------------------------------------------------------------O - - + + //============================================================= // Resource Packs - Allows you to store files in one large // scrambled file - Thanks MaGetzUb for debugging a null char in std::stringstream bug @@ -1274,14 +1274,14 @@ namespace olc ifs.seekg(offset); ifs.read(vMemory.data(), vMemory.size()); setg(vMemory.data(), vMemory.data(), vMemory.data() + size); } - + ResourcePack::ResourcePack() {} ResourcePack::~ResourcePack() { baseFile.close(); } - + bool ResourcePack::AddFile(const std::string& sFile) { const std::string file = makeposix(sFile); - + if (_gfs::exists(file)) { sResourceFile e; @@ -1292,34 +1292,34 @@ namespace olc } return false; } - + bool ResourcePack::LoadPack(const std::string& sFile, const std::string& sKey) { // Open the resource file baseFile.open(sFile, std::ifstream::binary); if (!baseFile.is_open()) return false; - + // 1) Read Scrambled index uint32_t nIndexSize = 0; baseFile.read((char*)&nIndexSize, sizeof(uint32_t)); - + std::vector buffer(nIndexSize); for (uint32_t j = 0; j < nIndexSize; j++) buffer[j] = baseFile.get(); - + std::vector decoded = scramble(buffer, sKey); size_t pos = 0; auto read = [&decoded, &pos](char* dst, size_t size) { memcpy((void*)dst, (const void*)(decoded.data() + pos), size); pos += size; }; - + auto get = [&read]() -> int { char c; read(&c, 1); return c; }; - + // 2) Read Map uint32_t nMapEntries = 0; read((char*)&nMapEntries, sizeof(uint32_t)); @@ -1327,28 +1327,28 @@ namespace olc { uint32_t nFilePathSize = 0; read((char*)&nFilePathSize, sizeof(uint32_t)); - + std::string sFileName(nFilePathSize, ' '); for (uint32_t j = 0; j < nFilePathSize; j++) sFileName[j] = get(); - + sResourceFile e; read((char*)&e.nSize, sizeof(uint32_t)); read((char*)&e.nOffset, sizeof(uint32_t)); mapFiles[sFileName] = e; } - + // Don't close base file! we will provide a stream // pointer when the file is requested return true; } - + bool ResourcePack::SavePack(const std::string& sFile, const std::string& sKey) { // Create/Overwrite the resource file std::ofstream ofs(sFile, std::ofstream::binary); if (!ofs.is_open()) return false; - + // Iterate through map uint32_t nIndexSize = 0; // Unknown for now ofs.write((char*)&nIndexSize, sizeof(uint32_t)); @@ -1360,12 +1360,12 @@ namespace olc size_t nPathSize = e.first.size(); ofs.write((char*)&nPathSize, sizeof(uint32_t)); ofs.write(e.first.c_str(), nPathSize); - + // Write the file entry properties ofs.write((char*)&e.second.nSize, sizeof(uint32_t)); ofs.write((char*)&e.second.nOffset, sizeof(uint32_t)); } - + // 2) Write the individual Data std::streampos offset = ofs.tellp(); nIndexSize = (uint32_t)offset; @@ -1373,18 +1373,18 @@ namespace olc { // Store beginning of file offset within resource pack file e.second.nOffset = (uint32_t)offset; - + // Load the file to be added std::vector vBuffer(e.second.nSize); std::ifstream i(e.first, std::ifstream::binary); i.read((char*)vBuffer.data(), e.second.nSize); i.close(); - + // Write the loaded file into resource pack file ofs.write((char*)vBuffer.data(), e.second.nSize); offset += e.second.nSize; } - + // 3) Scramble Index std::vector stream; auto write = [&stream](const char* data, size_t size) { @@ -1392,7 +1392,7 @@ namespace olc stream.resize(sizeNow + size); memcpy(stream.data() + sizeNow, data, size); }; - + // Iterate through map write((char*)&nMapSize, sizeof(uint32_t)); for (auto& e : mapFiles) @@ -1401,7 +1401,7 @@ namespace olc size_t nPathSize = e.first.size(); write((char*)&nPathSize, sizeof(uint32_t)); write(e.first.c_str(), nPathSize); - + // Write the file entry properties write((char*)&e.second.nSize, sizeof(uint32_t)); write((char*)&e.second.nOffset, sizeof(uint32_t)); @@ -1416,17 +1416,17 @@ namespace olc ofs.close(); return true; } - + ResourceBuffer ResourcePack::GetFileBuffer(const std::string& sFile) { return ResourceBuffer(baseFile, mapFiles[sFile].nOffset, mapFiles[sFile].nSize); } - + bool ResourcePack::Loaded() { return baseFile.is_open(); } - + std::vector ResourcePack::scramble(const std::vector& data, const std::string& key) { if (key.empty()) return data; @@ -1435,14 +1435,14 @@ namespace olc for (auto s : data) o.push_back(s ^ key[(c++) % key.size()]); return o; }; - + std::string ResourcePack::makeposix(const std::string& path) { std::string o; for (auto s : path) o += std::string(1, s == '\\' ? '/' : s); return o; }; - + // O------------------------------------------------------------------------------O // | olc::PixelGameEngine IMPLEMENTATION | // O------------------------------------------------------------------------------O @@ -1450,17 +1450,17 @@ namespace olc { sAppName = "Undefined"; olc::PGEX::pge = this; - + // Bring in relevant Platform & Rendering systems depending // on compiler parameters olc_ConfigureSystem(); } - + PixelGameEngine::~PixelGameEngine() { } - - + + olc::rcode PixelGameEngine::Construct(int32_t screen_w, int32_t screen_h, int32_t pixel_w, int32_t pixel_h, bool full_screen, bool vsync, bool cohesion) { bPixelCohesion = cohesion; @@ -1471,15 +1471,15 @@ namespace olc bFullScreen = full_screen; bEnableVSYNC = vsync; vPixel = 2.0f / vScreenSize; - + if (vPixelSize.x <= 0 || vPixelSize.y <= 0 || vScreenSize.x <= 0 || vScreenSize.y <= 0) return olc::FAIL; - - + + return olc::OK; } - - + + void PixelGameEngine::SetScreenSize(int w, int h) { vScreenSize = { w, h }; @@ -1491,38 +1491,38 @@ namespace olc layer.bUpdate = true; } SetDrawTarget(nullptr); - + renderer->ClearBuffer(olc::BLACK, true); renderer->DisplayFrame(); renderer->ClearBuffer(olc::BLACK, true); renderer->UpdateViewport(vViewPos, vViewSize); } - + #if !defined(PGE_USE_CUSTOM_START) olc::rcode PixelGameEngine::Start() { if (platform->ApplicationStartUp() != olc::OK) return olc::FAIL; - + // Construct the window if (platform->CreateWindowPane({ 30,30 }, vWindowSize, bFullScreen) != olc::OK) return olc::FAIL; olc_UpdateWindowSize(vWindowSize.x, vWindowSize.y); - + // Start the thread bAtomActive = true; std::thread t = std::thread(&PixelGameEngine::EngineThread, this); - + // Some implementations may form an event loop here platform->StartSystemEventLoop(); - + // Wait for thread to be exited t.join(); - + if (platform->ApplicationCleanUp() != olc::OK) return olc::FAIL; - + return olc::OK; } #endif - + void PixelGameEngine::SetDrawTarget(Sprite* target) { if (target) @@ -1535,7 +1535,7 @@ namespace olc pDrawTarget = vLayers[0].pDrawTarget; } } - + void PixelGameEngine::SetDrawTarget(uint8_t layer) { if (layer < vLayers.size()) @@ -1545,47 +1545,47 @@ namespace olc nTargetLayer = layer; } } - + void PixelGameEngine::EnableLayer(uint8_t layer, bool b) { if (layer < vLayers.size()) vLayers[layer].bShow = b; } - + void PixelGameEngine::SetLayerOffset(uint8_t layer, const olc::vf2d& offset) { SetLayerOffset(layer, offset.x, offset.y); } - + void PixelGameEngine::SetLayerOffset(uint8_t layer, float x, float y) { if (layer < vLayers.size()) vLayers[layer].vOffset = { x, y }; } - + void PixelGameEngine::SetLayerScale(uint8_t layer, const olc::vf2d& scale) { SetLayerScale(layer, scale.x, scale.y); } - + void PixelGameEngine::SetLayerScale(uint8_t layer, float x, float y) { if (layer < vLayers.size()) vLayers[layer].vScale = { x, y }; } - + void PixelGameEngine::SetLayerTint(uint8_t layer, const olc::Pixel& tint) { if (layer < vLayers.size()) vLayers[layer].tint = tint; } - + void PixelGameEngine::SetLayerCustomRenderFunction(uint8_t layer, std::function f) { if (layer < vLayers.size()) vLayers[layer].funcHook = f; } - + std::vector& PixelGameEngine::GetLayers() { return vLayers; } - + uint32_t PixelGameEngine::CreateLayer() { LayerDesc ld; @@ -1595,12 +1595,12 @@ namespace olc vLayers.push_back(ld); return uint32_t(vLayers.size()) - 1; } - + Sprite* PixelGameEngine::GetDrawTarget() const { return pDrawTarget; } - + int32_t PixelGameEngine::GetDrawTargetWidth() const { if (pDrawTarget) @@ -1608,7 +1608,7 @@ namespace olc else return 0; } - + int32_t PixelGameEngine::GetDrawTargetHeight() const { if (pDrawTarget) @@ -1616,104 +1616,104 @@ namespace olc else return 0; } - + uint32_t PixelGameEngine::GetFPS() const { return nLastFPS; } - + bool PixelGameEngine::IsFocused() const { return bHasInputFocus; } - + HWButton PixelGameEngine::GetKey(Key k) const { return pKeyboardState[k]; } - + HWButton PixelGameEngine::GetMouse(uint32_t b) const { return pMouseState[b]; } - + int32_t PixelGameEngine::GetMouseX() const { return vMousePos.x; } - + int32_t PixelGameEngine::GetMouseY() const { return vMousePos.y; } - + const olc::vi2d& PixelGameEngine::GetMousePos() const { return vMousePos; } - + int32_t PixelGameEngine::GetMouseWheel() const { return nMouseWheelDelta; } - + int32_t PixelGameEngine::ScreenWidth() const { return vScreenSize.x; } - + int32_t PixelGameEngine::ScreenHeight() const { return vScreenSize.y; } - + float PixelGameEngine::GetElapsedTime() const { return fLastElapsed; } - + const olc::vi2d& PixelGameEngine::GetWindowSize() const { return vWindowSize; } - + const olc::vi2d& PixelGameEngine::GetPixelSize() const { return vPixelSize; } - + const olc::vi2d& PixelGameEngine::GetScreenPixelSize() const { return vScreenPixelSize; } - + const olc::vi2d& PixelGameEngine::GetWindowMouse() const { return vMouseWindowPos; } - - + + bool PixelGameEngine::Draw(const olc::vi2d& pos, Pixel p) { return Draw(pos.x, pos.y, p); } - + // This is it, the critical function that plots a pixel bool PixelGameEngine::Draw(int32_t x, int32_t y, Pixel p) { if (!pDrawTarget) return false; - + if (nPixelMode == Pixel::NORMAL) { return pDrawTarget->SetPixel(x, y, p); } - + if (nPixelMode == Pixel::MASK) { if (p.a == 255) return pDrawTarget->SetPixel(x, y, p); } - + if (nPixelMode == Pixel::ALPHA) { Pixel d = pDrawTarget->GetPixel(x, y); @@ -1724,28 +1724,28 @@ namespace olc float b = a * (float)p.b + c * (float)d.b; return pDrawTarget->SetPixel(x, y, Pixel((uint8_t)r, (uint8_t)g, (uint8_t)b/*, (uint8_t)(p.a * fBlendFactor)*/)); } - + if (nPixelMode == Pixel::CUSTOM) { return pDrawTarget->SetPixel(x, y, funcPixelMode(x, y, p, pDrawTarget->GetPixel(x, y))); } - + return false; } - - + + void PixelGameEngine::DrawLine(const olc::vi2d& pos1, const olc::vi2d& pos2, Pixel p, uint32_t pattern) { DrawLine(pos1.x, pos1.y, pos2.x, pos2.y, p, pattern); } - + void PixelGameEngine::DrawLine(int32_t x1, int32_t y1, int32_t x2, int32_t y2, Pixel p, uint32_t pattern) { int x, y, dx, dy, dx1, dy1, px, py, xe, ye, i; dx = x2 - x1; dy = y2 - y1; - + auto rol = [&](void) { pattern = (pattern << 1) | (pattern >> 31); return pattern & 1; }; - + // straight lines idea by gurkanctn if (dx == 0) // Line is vertical { @@ -1753,14 +1753,14 @@ namespace olc for (y = y1; y <= y2; y++) if (rol()) Draw(x1, y, p); return; } - + if (dy == 0) // Line is horizontal { if (x2 < x1) std::swap(x1, x2); for (x = x1; x <= x2; x++) if (rol()) Draw(x, y1, p); return; } - + // Line is Funk-aye dx1 = abs(dx); dy1 = abs(dy); px = 2 * dy1 - dx1; py = 2 * dx1 - dy1; @@ -1774,9 +1774,9 @@ namespace olc { x = x2; y = y2; xe = x1; } - + if (rol()) Draw(x, y, p); - + for (i = 0; x < xe; i++) { x = x + 1; @@ -1800,9 +1800,9 @@ namespace olc { x = x2; y = y2; ye = y1; } - + if (rol()) Draw(x, y, p); - + for (i = 0; y < ye; i++) { y = y + 1; @@ -1817,23 +1817,23 @@ namespace olc } } } - + void PixelGameEngine::DrawCircle(const olc::vi2d& pos, int32_t radius, Pixel p, uint8_t mask) { DrawCircle(pos.x, pos.y, radius, p, mask); } - + void PixelGameEngine::DrawCircle(int32_t x, int32_t y, int32_t radius, Pixel p, uint8_t mask) { // Thanks to IanM-Matrix1 #PR121 if (radius < 0 || x < -radius || y < -radius || x - GetDrawTargetWidth() > radius || y - GetDrawTargetHeight() > radius) return; - + if (radius > 0) { int x0 = 0; int y0 = radius; int d = 3 - 2 * radius; - + while (y0 >= x0) // only formulate 1/8 of circle { // Draw even octants @@ -1848,7 +1848,7 @@ namespace olc if (mask & 0x20) Draw(x - y0, y + x0, p);// Q3 - lower lower left if (mask & 0x80) Draw(x - x0, y - y0, p);// Q1 - upper left left } - + if (d < 0) d += 4 * x0++ + 6; else @@ -1858,34 +1858,34 @@ namespace olc else Draw(x, y, p); } - + void PixelGameEngine::FillCircle(const olc::vi2d& pos, int32_t radius, Pixel p) { FillCircle(pos.x, pos.y, radius, p); } - + void PixelGameEngine::FillCircle(int32_t x, int32_t y, int32_t radius, Pixel p) { // Thanks to IanM-Matrix1 #PR121 if (radius < 0 || x < -radius || y < -radius || x - GetDrawTargetWidth() > radius || y - GetDrawTargetHeight() > radius) return; - + if (radius > 0) { int x0 = 0; int y0 = radius; int d = 3 - 2 * radius; - + auto drawline = [&](int sx, int ex, int y) { for (int x = sx; x <= ex; x++) Draw(x, y, p); }; - + while (y0 >= x0) { drawline(x - y0, x + y0, y - x0); if (x0 > 0) drawline(x - y0, x + y0, y + x0); - + if (d < 0) d += 4 * x0++ + 6; else @@ -1902,12 +1902,12 @@ namespace olc else Draw(x, y, p); } - + void PixelGameEngine::DrawRect(const olc::vi2d& pos, const olc::vi2d& size, Pixel p) { DrawRect(pos.x, pos.y, size.x, size.y, p); } - + void PixelGameEngine::DrawRect(int32_t x, int32_t y, int32_t w, int32_t h, Pixel p) { DrawLine(x, y, x + w, y, p); @@ -1915,66 +1915,66 @@ namespace olc DrawLine(x + w, y + h, x, y + h, p); DrawLine(x, y + h, x, y, p); } - + void PixelGameEngine::Clear(Pixel p) { int pixels = GetDrawTargetWidth() * GetDrawTargetHeight(); Pixel* m = GetDrawTarget()->GetData(); for (int i = 0; i < pixels; i++) m[i] = p; } - + void PixelGameEngine::ClearBuffer(Pixel p, bool bDepth) { renderer->ClearBuffer(p, bDepth); } - + void PixelGameEngine::FillRect(const olc::vi2d& pos, const olc::vi2d& size, Pixel p) { FillRect(pos.x, pos.y, size.x, size.y, p); } - + void PixelGameEngine::FillRect(int32_t x, int32_t y, int32_t w, int32_t h, Pixel p) { int32_t x2 = x + w; int32_t y2 = y + h; - + if (x < 0) x = 0; if (x >= (int32_t)GetDrawTargetWidth()) x = (int32_t)GetDrawTargetWidth(); if (y < 0) y = 0; if (y >= (int32_t)GetDrawTargetHeight()) y = (int32_t)GetDrawTargetHeight(); - + if (x2 < 0) x2 = 0; if (x2 >= (int32_t)GetDrawTargetWidth()) x2 = (int32_t)GetDrawTargetWidth(); if (y2 < 0) y2 = 0; if (y2 >= (int32_t)GetDrawTargetHeight()) y2 = (int32_t)GetDrawTargetHeight(); - + for (int i = x; i < x2; i++) for (int j = y; j < y2; j++) - Draw(i, j, p); + Draw(i, j, p); } - + void PixelGameEngine::DrawTriangle(const olc::vi2d& pos1, const olc::vi2d& pos2, const olc::vi2d& pos3, Pixel p) { DrawTriangle(pos1.x, pos1.y, pos2.x, pos2.y, pos3.x, pos3.y, p); } - + void PixelGameEngine::DrawTriangle(int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t x3, int32_t y3, Pixel p) { DrawLine(x1, y1, x2, y2, p); DrawLine(x2, y2, x3, y3, p); DrawLine(x3, y3, x1, y1, p); } - + void PixelGameEngine::FillTriangle(const olc::vi2d& pos1, const olc::vi2d& pos2, const olc::vi2d& pos3, Pixel p) { FillTriangle(pos1.x, pos1.y, pos2.x, pos2.y, pos3.x, pos3.y, p); } - + // https://www.avrfreaks.net/sites/default/files/triangles.c void PixelGameEngine::FillTriangle(int32_t x1, int32_t y1, int32_t x2, int32_t y2, int32_t x3, int32_t y3, Pixel p) { auto drawline = [&](int sx, int ex, int ny) { for (int i = sx; i <= ex; i++) Draw(i, ny, p); }; - + int t1x, t2x, y, minx, maxx, t1xp, t2xp; bool changed1 = false; bool changed2 = false; @@ -1984,26 +1984,26 @@ namespace olc if (y1 > y2) { std::swap(y1, y2); std::swap(x1, x2); } if (y1 > y3) { std::swap(y1, y3); std::swap(x1, x3); } if (y2 > y3) { std::swap(y2, y3); std::swap(x2, x3); } - + t1x = t2x = x1; y = y1; // Starting points dx1 = (int)(x2 - x1); if (dx1 < 0) { dx1 = -dx1; signx1 = -1; } else signx1 = 1; dy1 = (int)(y2 - y1); - + dx2 = (int)(x3 - x1); if (dx2 < 0) { dx2 = -dx2; signx2 = -1; } else signx2 = 1; dy2 = (int)(y3 - y1); - + if (dy1 > dx1) { std::swap(dx1, dy1); changed1 = true; } if (dy2 > dx2) { std::swap(dy2, dx2); changed2 = true; } - + e2 = (int)(dx2 >> 1); // Flat top, just process the second half if (y1 == y2) goto next; e1 = (int)(dx1 >> 1); - + for (int i = 0; i < dx1;) { t1xp = 0; t2xp = 0; @@ -2024,7 +2024,7 @@ namespace olc else t1x += signx1; } // Move line - next1: + next1: // process second line until y value is about to change while (1) { @@ -2038,37 +2038,37 @@ namespace olc if (changed2) break; else t2x += signx2; } - next2: + next2: if (minx > t1x) minx = t1x; if (minx > t2x) minx = t2x; if (maxx < t1x) maxx = t1x; if (maxx < t2x) maxx = t2x; drawline(minx, maxx, y); // Draw line from min to max points found on the y - // Now increase y + // Now increase y if (!changed1) t1x += signx1; t1x += t1xp; if (!changed2) t2x += signx2; t2x += t2xp; y += 1; if (y == y2) break; - + } - next: + next: // Second half dx1 = (int)(x3 - x2); if (dx1 < 0) { dx1 = -dx1; signx1 = -1; } else signx1 = 1; dy1 = (int)(y3 - y2); t1x = x2; - + if (dy1 > dx1) { // swap values std::swap(dy1, dx1); changed1 = true; } else changed1 = false; - + e1 = (int)(dx1 >> 1); - + for (int i = 0; i <= dx1; i++) { t1xp = 0; t2xp = 0; @@ -2088,7 +2088,7 @@ namespace olc else t1x += signx1; if (i < dx1) i++; } - next3: + next3: // process second line until y value is about to change while (t2x != x3) { @@ -2102,8 +2102,8 @@ namespace olc if (changed2) break; else t2x += signx2; } - next4: - + next4: + if (minx > t1x) minx = t1x; if (minx > t2x) minx = t2x; if (maxx < t1x) maxx = t1x; @@ -2117,22 +2117,22 @@ namespace olc if (y > y3) return; } } - + void PixelGameEngine::DrawSprite(const olc::vi2d& pos, Sprite* sprite, uint32_t scale, uint8_t flip) { DrawSprite(pos.x, pos.y, sprite, scale, flip); } - + void PixelGameEngine::DrawSprite(int32_t x, int32_t y, Sprite* sprite, uint32_t scale, uint8_t flip) { if (sprite == nullptr) return; - + int32_t fxs = 0, fxm = 1, fx = 0; int32_t fys = 0, fym = 1, fy = 0; if (flip & olc::Sprite::Flip::HORIZ) { fxs = sprite->width - 1; fxm = -1; } if (flip & olc::Sprite::Flip::VERT) { fys = sprite->height - 1; fym = -1; } - + if (scale > 1) { fx = fxs; @@ -2141,8 +2141,8 @@ namespace olc fy = fys; for (int32_t j = 0; j < sprite->height; j++, fy += fym) for (uint32_t is = 0; is < scale; is++) - for (uint32_t js = 0; js < scale; js++) - Draw(x + (i * scale) + is, y + (j * scale) + js, sprite->GetPixel(fx, fy)); + for (uint32_t js = 0; js < scale; js++) + Draw(x + (i * scale) + is, y + (j * scale) + js, sprite->GetPixel(fx, fy)); } } else @@ -2156,22 +2156,22 @@ namespace olc } } } - + void PixelGameEngine::DrawPartialSprite(const olc::vi2d& pos, Sprite* sprite, const olc::vi2d& sourcepos, const olc::vi2d& size, uint32_t scale, uint8_t flip) { DrawPartialSprite(pos.x, pos.y, sprite, sourcepos.x, sourcepos.y, size.x, size.y, scale, flip); } - + void PixelGameEngine::DrawPartialSprite(int32_t x, int32_t y, Sprite* sprite, int32_t ox, int32_t oy, int32_t w, int32_t h, uint32_t scale, uint8_t flip) { if (sprite == nullptr) return; - + int32_t fxs = 0, fxm = 1, fx = 0; int32_t fys = 0, fym = 1, fy = 0; if (flip & olc::Sprite::Flip::HORIZ) { fxs = w - 1; fxm = -1; } if (flip & olc::Sprite::Flip::VERT) { fys = h - 1; fym = -1; } - + if (scale > 1) { fx = fxs; @@ -2180,8 +2180,8 @@ namespace olc fy = fys; for (int32_t j = 0; j < h; j++, fy += fym) for (uint32_t is = 0; is < scale; is++) - for (uint32_t js = 0; js < scale; js++) - Draw(x + (i * scale) + is, y + (j * scale) + js, sprite->GetPixel(fx + ox, fy + oy)); + for (uint32_t js = 0; js < scale; js++) + Draw(x + (i * scale) + is, y + (j * scale) + js, sprite->GetPixel(fx + ox, fy + oy)); } } else @@ -2195,7 +2195,7 @@ namespace olc } } } - + void PixelGameEngine::DrawPartialDecal(const olc::vf2d& pos, olc::Decal* decal, const olc::vf2d& source_pos, const olc::vf2d& source_size, const olc::vf2d& scale, const olc::Pixel& tint) { olc::vf2d vScreenSpacePos = @@ -2203,27 +2203,27 @@ namespace olc (pos.x * vInvScreenSize.x) * 2.0f - 1.0f, ((pos.y * vInvScreenSize.y) * 2.0f - 1.0f) * -1.0f }; - + olc::vf2d vScreenSpaceDim = { vScreenSpacePos.x + (2.0f * source_size.x * vInvScreenSize.x) * scale.x, vScreenSpacePos.y - (2.0f * source_size.y * vInvScreenSize.y) * scale.y }; - + DecalInstance di; di.decal = decal; di.tint[0] = tint; - + di.pos[0] = { vScreenSpacePos.x, vScreenSpacePos.y }; di.pos[1] = { vScreenSpacePos.x, vScreenSpaceDim.y }; di.pos[2] = { vScreenSpaceDim.x, vScreenSpaceDim.y }; di.pos[3] = { vScreenSpaceDim.x, vScreenSpacePos.y }; - + olc::vf2d uvtl = source_pos * decal->vUVScale; olc::vf2d uvbr = uvtl + (source_size * decal->vUVScale); di.uv[0] = { uvtl.x, uvtl.y }; di.uv[1] = { uvtl.x, uvbr.y }; di.uv[2] = { uvbr.x, uvbr.y }; di.uv[3] = { uvbr.x, uvtl.y }; vLayers[nTargetLayer].vecDecalInstance.push_back(di); } - + void PixelGameEngine::DrawPartialDecal(const olc::vf2d& pos, const olc::vf2d& size, olc::Decal* decal, const olc::vf2d& source_pos, const olc::vf2d& source_size, const olc::Pixel& tint) { olc::vf2d vScreenSpacePos = @@ -2231,28 +2231,28 @@ namespace olc (pos.x * vInvScreenSize.x) * 2.0f - 1.0f, ((pos.y * vInvScreenSize.y) * 2.0f - 1.0f) * -1.0f }; - + olc::vf2d vScreenSpaceDim = { vScreenSpacePos.x + (2.0f * size.x * vInvScreenSize.x), vScreenSpacePos.y - (2.0f * size.y * vInvScreenSize.y) }; - + DecalInstance di; di.decal = decal; di.tint[0] = tint; - + di.pos[0] = { vScreenSpacePos.x, vScreenSpacePos.y }; di.pos[1] = { vScreenSpacePos.x, vScreenSpaceDim.y }; di.pos[2] = { vScreenSpaceDim.x, vScreenSpaceDim.y }; di.pos[3] = { vScreenSpaceDim.x, vScreenSpacePos.y }; - + olc::vf2d uvtl = source_pos * decal->vUVScale; olc::vf2d uvbr = uvtl + (source_size * decal->vUVScale); di.uv[0] = { uvtl.x, uvtl.y }; di.uv[1] = { uvtl.x, uvbr.y }; di.uv[2] = { uvbr.x, uvbr.y }; di.uv[3] = { uvbr.x, uvtl.y }; vLayers[nTargetLayer].vecDecalInstance.push_back(di); } - - + + void PixelGameEngine::DrawDecal(const olc::vf2d& pos, olc::Decal* decal, const olc::vf2d& scale, const olc::Pixel& tint) { olc::vf2d vScreenSpacePos = @@ -2260,13 +2260,13 @@ namespace olc (pos.x * vInvScreenSize.x) * 2.0f - 1.0f, ((pos.y * vInvScreenSize.y) * 2.0f - 1.0f) * -1.0f }; - + olc::vf2d vScreenSpaceDim = { vScreenSpacePos.x + (2.0f * (float(decal->sprite->width) * vInvScreenSize.x)) * scale.x, vScreenSpacePos.y - (2.0f * (float(decal->sprite->height) * vInvScreenSize.y)) * scale.y }; - + DecalInstance di; di.decal = decal; di.tint[0] = tint; @@ -2276,7 +2276,7 @@ namespace olc di.pos[3] = { vScreenSpaceDim.x, vScreenSpacePos.y }; vLayers[nTargetLayer].vecDecalInstance.push_back(di); } - + void PixelGameEngine::DrawRotatedDecal(const olc::vf2d& pos, olc::Decal* decal, const float fAngle, const olc::vf2d& center, const olc::vf2d& scale, const olc::Pixel& tint) { DecalInstance di; @@ -2295,7 +2295,7 @@ namespace olc } vLayers[nTargetLayer].vecDecalInstance.push_back(di); } - + void PixelGameEngine::DrawExplicitDecal(olc::Decal* decal, const olc::vf2d* pos, const olc::vf2d* uv, const olc::Pixel* col) { DecalInstance di; @@ -2308,7 +2308,7 @@ namespace olc } vLayers[nTargetLayer].vecDecalInstance.push_back(di); } - + void PixelGameEngine::FillRectDecal(const olc::vf2d& pos, const olc::vf2d& size, const olc::Pixel col) { std::array points = { { {pos}, {pos.x, pos.y + size.y}, {pos + size}, {pos.x + size.x, pos.y} } }; @@ -2316,7 +2316,7 @@ namespace olc std::array cols = { {col, col, col, col} }; DrawExplicitDecal(nullptr, points.data(), uvs.data(), cols.data()); } - + void PixelGameEngine::GradientFillRectDecal(const olc::vf2d& pos, const olc::vf2d& size, const olc::Pixel colTL, const olc::Pixel colBL, const olc::Pixel colBR, const olc::Pixel colTR) { std::array points = { { {pos}, {pos.x, pos.y + size.y}, {pos + size}, {pos.x + size.x, pos.y} } }; @@ -2324,8 +2324,8 @@ namespace olc std::array cols = { {colTL, colBL, colBR, colTR} }; DrawExplicitDecal(nullptr, points.data(), uvs.data(), cols.data()); } - - + + void PixelGameEngine::DrawPartialRotatedDecal(const olc::vf2d& pos, olc::Decal* decal, const float fAngle, const olc::vf2d& center, const olc::vf2d& source_pos, const olc::vf2d& source_size, const olc::vf2d& scale, const olc::Pixel& tint) { DecalInstance di; @@ -2342,15 +2342,15 @@ namespace olc di.pos[i] = di.pos[i] * vInvScreenSize * 2.0f - olc::vf2d(1.0f, 1.0f); di.pos[i].y *= -1.0f; } - + olc::vf2d uvtl = source_pos * decal->vUVScale; olc::vf2d uvbr = uvtl + (source_size * decal->vUVScale); di.uv[0] = { uvtl.x, uvtl.y }; di.uv[1] = { uvtl.x, uvbr.y }; di.uv[2] = { uvbr.x, uvbr.y }; di.uv[3] = { uvbr.x, uvtl.y }; - + vLayers[nTargetLayer].vecDecalInstance.push_back(di); } - + void PixelGameEngine::DrawPartialWarpedDecal(olc::Decal* decal, const olc::vf2d* pos, const olc::vf2d& source_pos, const olc::vf2d& source_size, const olc::Pixel& tint) { DecalInstance di; @@ -2364,7 +2364,7 @@ namespace olc olc::vf2d uvbr = uvtl + (source_size * decal->vUVScale); di.uv[0] = { uvtl.x, uvtl.y }; di.uv[1] = { uvtl.x, uvbr.y }; di.uv[2] = { uvbr.x, uvbr.y }; di.uv[3] = { uvbr.x, uvtl.y }; - + rd = 1.0f / rd; float rn = ((pos[3].x - pos[1].x) * (pos[0].y - pos[1].y) - (pos[3].y - pos[1].y) * (pos[0].x - pos[1].x)) * rd; float sn = ((pos[2].x - pos[0].x) * (pos[0].y - pos[1].y) - (pos[2].y - pos[0].y) * (pos[0].x - pos[1].x)) * rd; @@ -2379,7 +2379,7 @@ namespace olc vLayers[nTargetLayer].vecDecalInstance.push_back(di); } } - + void PixelGameEngine::DrawWarpedDecal(olc::Decal* decal, const olc::vf2d* pos, const olc::Pixel& tint) { // Thanks Nathan Reed, a brilliant article explaining whats going on here @@ -2405,27 +2405,27 @@ namespace olc vLayers[nTargetLayer].vecDecalInstance.push_back(di); } } - + void PixelGameEngine::DrawWarpedDecal(olc::Decal* decal, const std::array& pos, const olc::Pixel& tint) { DrawWarpedDecal(decal, pos.data(), tint); } - + void PixelGameEngine::DrawWarpedDecal(olc::Decal* decal, const olc::vf2d(&pos)[4], const olc::Pixel& tint) { DrawWarpedDecal(decal, &pos[0], tint); } - + void PixelGameEngine::DrawPartialWarpedDecal(olc::Decal* decal, const std::array& pos, const olc::vf2d& source_pos, const olc::vf2d& source_size, const olc::Pixel& tint) { DrawPartialWarpedDecal(decal, pos.data(), source_pos, source_size, tint); } - + void PixelGameEngine::DrawPartialWarpedDecal(olc::Decal* decal, const olc::vf2d(&pos)[4], const olc::vf2d& source_pos, const olc::vf2d& source_size, const olc::Pixel& tint) { DrawPartialWarpedDecal(decal, &pos[0], source_pos, source_size, tint); } - + void PixelGameEngine::DrawStringDecal(const olc::vf2d& pos, const std::string& sText, const Pixel col, const olc::vf2d& scale) { olc::vf2d spos = { 0.0f, 0.0f }; @@ -2444,7 +2444,7 @@ namespace olc } } } - + olc::vi2d PixelGameEngine::GetTextSize(const std::string& s) { olc::vi2d size = { 0,1 }; @@ -2458,12 +2458,12 @@ namespace olc } return size * 8; } - + void PixelGameEngine::DrawString(const olc::vi2d& pos, const std::string& sText, Pixel col, uint32_t scale) { DrawString(pos.x, pos.y, sText, col, scale); } - + void PixelGameEngine::DrawString(int32_t x, int32_t y, const std::string& sText, Pixel col, uint32_t scale) { int32_t sx = 0; @@ -2482,78 +2482,78 @@ namespace olc { int32_t ox = (c - 32) % 16; int32_t oy = (c - 32) / 16; - + if (scale > 1) { for (uint32_t i = 0; i < 8; i++) for (uint32_t j = 0; j < 8; j++) - if (fontSprite->GetPixel(i + ox * 8, j + oy * 8).r > 0) - for (uint32_t is = 0; is < scale; is++) - for (uint32_t js = 0; js < scale; js++) - Draw(x + sx + (i * scale) + is, y + sy + (j * scale) + js, col); + if (fontSprite->GetPixel(i + ox * 8, j + oy * 8).r > 0) + for (uint32_t is = 0; is < scale; is++) + for (uint32_t js = 0; js < scale; js++) + Draw(x + sx + (i * scale) + is, y + sy + (j * scale) + js, col); } else { for (uint32_t i = 0; i < 8; i++) for (uint32_t j = 0; j < 8; j++) - if (fontSprite->GetPixel(i + ox * 8, j + oy * 8).r > 0) - Draw(x + sx + i, y + sy + j, col); + if (fontSprite->GetPixel(i + ox * 8, j + oy * 8).r > 0) + Draw(x + sx + i, y + sy + j, col); } sx += 8 * scale; } } SetPixelMode(m); } - + void PixelGameEngine::SetPixelMode(Pixel::Mode m) { nPixelMode = m; } - + Pixel::Mode PixelGameEngine::GetPixelMode() { return nPixelMode; } - + void PixelGameEngine::SetPixelMode(std::function pixelMode) { funcPixelMode = pixelMode; nPixelMode = Pixel::Mode::CUSTOM; } - + void PixelGameEngine::SetPixelBlend(float fBlend) { fBlendFactor = fBlend; if (fBlendFactor < 0.0f) fBlendFactor = 0.0f; if (fBlendFactor > 1.0f) fBlendFactor = 1.0f; } - + // User must override these functions as required. I have not made // them abstract because I do need a default behaviour to occur if // they are not overwritten - + bool PixelGameEngine::OnUserCreate() { return false; } - + bool PixelGameEngine::OnUserUpdate(float fElapsedTime) { UNUSED(fElapsedTime); return false; } - + bool PixelGameEngine::OnUserDestroy() { return true; } ////////////////////////////////////////////////////////////////// - + void PixelGameEngine::olc_UpdateViewport() { int32_t ww = vScreenSize.x * vPixelSize.x; int32_t wh = vScreenSize.y * vPixelSize.y; float wasp = (float)ww / (float)wh; - + if (bPixelCohesion) { vScreenPixelSize = (vWindowSize / vScreenSize); @@ -2563,28 +2563,28 @@ namespace olc { vViewSize.x = (int32_t)vWindowSize.x; vViewSize.y = (int32_t)((float)vViewSize.x / wasp); - + if (vViewSize.y > vWindowSize.y) { vViewSize.y = vWindowSize.y; vViewSize.x = (int32_t)((float)vViewSize.y * wasp); } } - + vViewPos = (vWindowSize - vViewSize) / 2; } - + void PixelGameEngine::olc_UpdateWindowSize(int32_t x, int32_t y) { vWindowSize = { x, y }; olc_UpdateViewport(); } - + void PixelGameEngine::olc_UpdateMouseWheel(int32_t delta) { nMouseWheelDeltaCache += delta; } - + void PixelGameEngine::olc_UpdateMouse(int32_t x, int32_t y) { // Mouse coords come in screen space @@ -2601,49 +2601,49 @@ namespace olc if (vMousePosCache.x < 0) vMousePosCache.x = 0; if (vMousePosCache.y < 0) vMousePosCache.y = 0; } - + void PixelGameEngine::olc_UpdateMouseState(int32_t button, bool state) { pMouseNewState[button] = state; } - + void PixelGameEngine::olc_UpdateKeyState(int32_t key, bool state) { pKeyNewState[key] = state; } - + void PixelGameEngine::olc_UpdateMouseFocus(bool state) { bHasMouseFocus = state; } - + void PixelGameEngine::olc_UpdateKeyFocus(bool state) { bHasInputFocus = state; } - + void PixelGameEngine::olc_Terminate() { bAtomActive = false; } - + void PixelGameEngine::EngineThread() { // Allow platform to do stuff here if needed, since its now in the // context of this thread if (platform->ThreadStartUp() == olc::FAIL) return; - + // Do engine context specific initialisation olc_PrepareEngine(); - + // Create user resources as part of this thread if (!OnUserCreate()) bAtomActive = false; - + while (bAtomActive) { // Run as fast as possible while (bAtomActive) { olc_CoreUpdate(); } - + // Allow the user to free resources if they have overrided the destroy function if (!OnUserDestroy()) { @@ -2651,43 +2651,43 @@ namespace olc bAtomActive = true; } } - + platform->ThreadCleanUp(); } - + void PixelGameEngine::olc_PrepareEngine() { // Start OpenGL, the context is owned by the game thread if (platform->CreateGraphics(bFullScreen, bEnableVSYNC, vViewPos, vViewSize) == olc::FAIL) return; - + // Construct default font sheet olc_ConstructFontSheet(); - + // Create Primary Layer "0" CreateLayer(); vLayers[0].bUpdate = true; vLayers[0].bShow = true; SetDrawTarget(nullptr); - + m_tp1 = std::chrono::system_clock::now(); m_tp2 = std::chrono::system_clock::now(); } - - + + void PixelGameEngine::olc_CoreUpdate() { // Handle Timing m_tp2 = std::chrono::system_clock::now(); std::chrono::duration elapsedTime = m_tp2 - m_tp1; m_tp1 = m_tp2; - + // Our time per frame coefficient float fElapsedTime = elapsedTime.count(); fLastElapsed = fElapsedTime; - + // Some platforms will need to check for events platform->HandleSystemEvent(); - + // Compare hardware input states from previous frame auto ScanHardware = [&](HWButton* pKeys, bool* pStateOld, bool* pStateNew, uint32_t nKeyCount) { @@ -2711,30 +2711,30 @@ namespace olc pStateOld[i] = pStateNew[i]; } }; - + ScanHardware(pKeyboardState, pKeyOldState, pKeyNewState, 256); ScanHardware(pMouseState, pMouseOldState, pMouseNewState, nMouseButtons); - + // Cache mouse coordinates so they remain consistent during frame vMousePos = vMousePosCache; nMouseWheelDelta = nMouseWheelDeltaCache; nMouseWheelDeltaCache = 0; - + // renderer->ClearBuffer(olc::BLACK, true); - - // Handle Frame Update + + // Handle Frame Update if (!OnUserUpdate(fElapsedTime)) bAtomActive = false; - + // Display Frame renderer->UpdateViewport(vViewPos, vViewSize); renderer->ClearBuffer(olc::BLACK, true); - + // Layer 0 must always exist vLayers[0].bUpdate = true; vLayers[0].bShow = true; renderer->PrepareDrawing(); - + for (auto layer = vLayers.rbegin(); layer != vLayers.rend(); ++layer) { if (layer->bShow) @@ -2747,9 +2747,9 @@ namespace olc renderer->UpdateTexture(layer->nResID, layer->pDrawTarget); layer->bUpdate = false; } - + renderer->DrawLayerQuad(layer->vOffset, layer->vScale, layer->tint); - + // Display Decals in order for this layer for (auto& decal : layer->vecDecalInstance) renderer->DrawDecalQuad(decal); @@ -2762,10 +2762,10 @@ namespace olc } } } - + // Present Graphics to screen renderer->DisplayFrame(); - + // Update Title Bar fFrameTimer += fElapsedTime; nFrameCount++; @@ -2778,7 +2778,7 @@ namespace olc nFrameCount = 0; } } - + void PixelGameEngine::olc_ConstructFontSheet() { std::string data; @@ -2798,7 +2798,7 @@ namespace olc data += "Ob@8@@00Ob@8@Ga13R@8Mga172@8?PAo3R@827QoOb@820@0O`0007`0000007P0"; data += "O`000P08Od400g`<3V=P0G`673IP0`@3>1`00P@6O`P00g` PixelGameEngine::bAtomActive{ false }; @@ -2877,23 +2877,23 @@ namespace olc { class Renderer_OGL10 : public olc::Renderer { - private: + private: #if defined(__APPLE__) bool mFullScreen = false; #else glDeviceContext_t glDeviceContext = 0; glRenderContext_t glRenderContext = 0; #endif - + bool bSync = false; - + #if defined(__linux__) || defined(__FreeBSD__) X11::Display* olc_Display = nullptr; X11::Window* olc_Window = nullptr; X11::XVisualInfo* olc_VisualInfo = nullptr; #endif - - public: + + public: void PrepareDevice() override { #if defined(__APPLE__) @@ -2901,20 +2901,20 @@ namespace olc int argc = 0; char* argv[1] = { (char*)"" }; glutInit(&argc, argv); - + glutInitWindowPosition(0, 0); glutInitWindowSize(512, 512); - + glutInitDisplayMode(GLUT_DOUBLE | GLUT_DEPTH | GLUT_RGBA); - + // Creates the window and the OpenGL context for it glutCreateWindow(""); - + glEnable(GL_TEXTURE_2D); // Turn on texturing glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST); #endif } - + olc::rcode CreateDevice(std::vector params, bool bFullScreen, bool bVSYNC) override { #if defined(_WIN32) @@ -2927,20 +2927,20 @@ namespace olc PFD_TYPE_RGBA, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, PFD_MAIN_PLANE, 0, 0, 0, 0 }; - + int pf = 0; if (!(pf = ChoosePixelFormat(glDeviceContext, &pfd))) return olc::FAIL; SetPixelFormat(glDeviceContext, pf, &pfd); - + if (!(glRenderContext = wglCreateContext(glDeviceContext))) return olc::FAIL; wglMakeCurrent(glDeviceContext, glRenderContext); - + // Remove Frame cap wglSwapInterval = (wglSwapInterval_t*)wglGetProcAddress("wglSwapIntervalEXT"); if (wglSwapInterval && !bVSYNC) wglSwapInterval(0); bSync = bVSYNC; #endif - + #if defined(__linux__) || defined(__FreeBSD__) using namespace X11; // Linux has tighter coupling between OpenGL and X11, so we store @@ -2948,28 +2948,28 @@ namespace olc olc_Display = (X11::Display*)(params[0]); olc_Window = (X11::Window*)(params[1]); olc_VisualInfo = (X11::XVisualInfo*)(params[2]); - + glDeviceContext = glXCreateContext(olc_Display, olc_VisualInfo, nullptr, GL_TRUE); glXMakeCurrent(olc_Display, *olc_Window, glDeviceContext); - + XWindowAttributes gwa; XGetWindowAttributes(olc_Display, *olc_Window, &gwa); glViewport(0, 0, gwa.width, gwa.height); - + glSwapIntervalEXT = nullptr; glSwapIntervalEXT = (glSwapInterval_t*)glXGetProcAddress((unsigned char*)"glXSwapIntervalEXT"); - + if (glSwapIntervalEXT == nullptr && !bVSYNC) { printf("NOTE: Could not disable VSYNC, glXSwapIntervalEXT() was not found!\n"); printf(" Don't worry though, things will still work, it's just the\n"); printf(" frame rate will be capped to your monitors refresh rate - javidx9\n"); } - + if (glSwapIntervalEXT != nullptr && !bVSYNC) glSwapIntervalEXT(olc_Display, *olc_Window, 0); #endif - + #if defined(__APPLE__) mFullScreen = bFullScreen; if (!bVSYNC) @@ -2984,46 +2984,46 @@ namespace olc #endif return olc::rcode::OK; } - + olc::rcode DestroyDevice() override { #if defined(_WIN32) wglDeleteContext(glRenderContext); #endif - + #if defined(__linux__) || defined(__FreeBSD__) glXMakeCurrent(olc_Display, None, NULL); glXDestroyContext(olc_Display, glDeviceContext); #endif - + #if defined(__APPLE__) glutDestroyWindow(glutGetWindow()); #endif return olc::rcode::OK; } - + void DisplayFrame() override { #if defined(_WIN32) SwapBuffers(glDeviceContext); if (bSync) DwmFlush(); // Woooohooooooo!!!! SMOOOOOOOTH! #endif - + #if defined(__linux__) || defined(__FreeBSD__) X11::glXSwapBuffers(olc_Display, *olc_Window); #endif - + #if defined(__APPLE__) glutSwapBuffers(); #endif } - + void PrepareDrawing() override { glEnable(GL_BLEND); glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); } - + void DrawLayerQuad(const olc::vf2d& offset, const olc::vf2d& scale, const olc::Pixel tint) override { glBegin(GL_QUADS); @@ -3038,7 +3038,7 @@ namespace olc glVertex3f(1.0f /*+ vSubPixelOffset.x*/, -1.0f /*+ vSubPixelOffset.y*/, 0.0f); glEnd(); } - + void DrawDecalQuad(const olc::DecalInstance& decal) override { if (decal.decal == nullptr) @@ -3067,7 +3067,7 @@ namespace olc glEnd(); } } - + uint32_t CreateTexture(const uint32_t width, const uint32_t height) override { UNUSED(width); @@ -3082,31 +3082,31 @@ namespace olc glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); return id; } - + uint32_t DeleteTexture(const uint32_t id) override { glDeleteTextures(1, &id); return id; } - + void UpdateTexture(uint32_t id, olc::Sprite* spr) override { UNUSED(id); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, spr->width, spr->height, 0, GL_RGBA, GL_UNSIGNED_BYTE, spr->GetData()); } - + void ApplyTexture(uint32_t id) override { glBindTexture(GL_TEXTURE_2D, id); } - + void ClearBuffer(olc::Pixel p, bool bDepth) override { glClearColor(float(p.r) / 255.0f, float(p.g) / 255.0f, float(p.b) / 255.0f, float(p.a) / 255.0f); glClear(GL_COLOR_BUFFER_BIT); if (bDepth) glClear(GL_DEPTH_BUFFER_BIT); } - + void UpdateViewport(const olc::vi2d& pos, const olc::vi2d& size) override { #if defined(__APPLE__) @@ -3145,7 +3145,7 @@ namespace olc // at construction, by initialising the GDI subsystem static class GDIPlusStartup { - public: + public: GDIPlusStartup() { Gdiplus::GdiplusStartupInput startupInput; @@ -3153,10 +3153,10 @@ namespace olc Gdiplus::GdiplusStartup(&token, &startupInput, NULL); }; } gdistartup; - + class ImageLoader_GDIPlus : public olc::ImageLoader { - private: + private: std::wstring ConvertS2W(std::string s) { #ifdef __MINGW32__ @@ -3172,20 +3172,20 @@ namespace olc delete[] buffer; return w; } - - public: + + public: ImageLoader_GDIPlus() : ImageLoader() { } - + olc::rcode LoadImageResource(olc::Sprite* spr, const std::string& sImageFile, olc::ResourcePack* pack) override { // Check file exists if (!_gfs::exists(sImageFile)) return olc::rcode::NO_FILE; - + // It does, so clear out existing sprite if (spr->pColData != nullptr) delete[] spr->pColData; - + // Open file UNUSED(pack); Gdiplus::Bitmap* bmp = nullptr; @@ -3200,23 +3200,23 @@ namespace olc // Load sprite from file bmp = Gdiplus::Bitmap::FromFile(ConvertS2W(sImageFile).c_str()); } - + if (bmp->GetLastStatus() != Gdiplus::Ok) return olc::rcode::FAIL; spr->width = bmp->GetWidth(); spr->height = bmp->GetHeight(); spr->pColData = new Pixel[spr->width * spr->height]; - + for (int y = 0; y < spr->height; y++) for (int x = 0; x < spr->width; x++) - { - Gdiplus::Color c; - bmp->GetPixel(x, y, &c); - spr->SetPixel(x, y, olc::Pixel(c.GetRed(), c.GetGreen(), c.GetBlue(), c.GetAlpha())); - } + { + Gdiplus::Color c; + bmp->GetPixel(x, y, &c); + spr->SetPixel(x, y, olc::Pixel(c.GetRed(), c.GetGreen(), c.GetBlue(), c.GetAlpha())); + } delete bmp; return olc::rcode::OK; } - + olc::rcode SaveImageResource(olc::Sprite* spr, const std::string& sImageFile) override { return olc::rcode::OK; @@ -3243,25 +3243,25 @@ namespace olc png_voidp a = png_get_io_ptr(pngPtr); ((std::istream*)a)->read((char*)data, length); } - + class ImageLoader_LibPNG : public olc::ImageLoader { - public: + public: ImageLoader_LibPNG() : ImageLoader() { } - + olc::rcode LoadImageResource(olc::Sprite* spr, const std::string& sImageFile, olc::ResourcePack* pack) override { UNUSED(pack); - + // Check file exists if (!_gfs::exists(sImageFile)) return olc::rcode::NO_FILE; - + // It does, so clear out existing sprite if (spr->pColData != nullptr) delete[] spr->pColData; - - + + //////////////////////////////////////////////////////////////////////////// // Use libpng, Thanks to Guillaume Cottenceau // https://gist.github.com/niw/5963798 @@ -3269,7 +3269,7 @@ namespace olc // http://www.piko3d.net/tutorials/libpng-tutorial-loading-png-files-from-streams/ png_structp png; png_infop info; - + auto loadPNG = [&]() { png_read_info(png, info); @@ -3308,21 +3308,21 @@ namespace olc spr->SetPixel(x, y, Pixel(px[0], px[1], px[2], px[3])); } } - + for (int y = 0; y < spr->height; y++) // Thanks maksym33 free(row_pointers[y]); free(row_pointers); png_destroy_read_struct(&png, &info, nullptr); }; - + png = png_create_read_struct(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL); if (!png) goto fail_load; - + info = png_create_info_struct(png); if (!info) goto fail_load; - + if (setjmp(png_jmpbuf(png))) goto fail_load; - + if (pack == nullptr) { FILE* f = fopen(sImageFile.c_str(), "rb"); @@ -3338,16 +3338,16 @@ namespace olc png_set_read_fn(png, (png_voidp)&is, pngReadStream); loadPNG(); } - + return olc::rcode::OK; - - fail_load: + + fail_load: spr->width = 0; spr->height = 0; spr->pColData = nullptr; return olc::rcode::FAIL; } - + olc::rcode SaveImageResource(olc::Sprite* spr, const std::string& sImageFile) override { return olc::rcode::OK; @@ -3380,21 +3380,21 @@ namespace olc { class ImageLoader_STB : public olc::ImageLoader { - public: + public: ImageLoader_STB() : ImageLoader() { } - + olc::rcode LoadImageResource(olc::Sprite* spr, const std::string& sImageFile, olc::ResourcePack* pack) override { UNUSED(pack); - + // Check file exists if (!_gfs::exists(sImageFile)) return olc::rcode::NO_FILE; - + // It does, so clear out existing sprite if (spr->pColData != nullptr) delete[] spr->pColData; - + // Open file stbi_uc* bytes = nullptr; int w = 0, h = 0, cmp = 0; @@ -3407,7 +3407,7 @@ namespace olc { bytes = stbi_load(sImageFile.c_str(), &w, &h, &cmp, 4); } - + if (!bytes) return olc::rcode::FAIL; spr->width = w; spr->height = h; spr->pColData = new Pixel[spr->width * spr->height]; @@ -3415,7 +3415,7 @@ namespace olc delete[] bytes; return olc::rcode::OK; } - + olc::rcode SaveImageResource(olc::Sprite* spr, const std::string& sImageFile) override { return olc::rcode::OK; @@ -3438,7 +3438,7 @@ namespace olc #pragma comment(lib, "opengl32.lib") // these libs to your linker input #else - // In Code::Blocks +// In Code::Blocks #if !defined(_WIN32_WINNT) #ifdef HAVE_MSMF #define _WIN32_WINNT 0x0600 // Windows Vista @@ -3460,10 +3460,10 @@ namespace olc { class Platform_Windows : public olc::Platform { - private: + private: HWND olc_hWnd = nullptr; std::wstring wsAppName; - + std::wstring ConvertS2W(std::string s) { #ifdef __MINGW32__ @@ -3479,19 +3479,19 @@ namespace olc delete[] buffer; return w; } - - public: + + public: virtual olc::rcode ApplicationStartUp() override { return olc::rcode::OK; } virtual olc::rcode ApplicationCleanUp() override { return olc::rcode::OK; } virtual olc::rcode ThreadStartUp() override { return olc::rcode::OK; } - + virtual olc::rcode ThreadCleanUp() override { renderer->DestroyDevice(); PostMessage(olc_hWnd, WM_DESTROY, 0, 0); return olc::OK; } - + virtual olc::rcode CreateGraphics(bool bFullScreen, bool bEnableVSYNC, const olc::vi2d& vViewPos, const olc::vi2d& vViewSize) override { if (renderer->CreateDevice({ olc_hWnd }, bFullScreen, bEnableVSYNC) == olc::rcode::OK) @@ -3502,7 +3502,7 @@ namespace olc else return olc::rcode::FAIL; } - + virtual olc::rcode CreateWindowPane(const olc::vi2d& vWindowPos, olc::vi2d& vWindowSize, bool bFullScreen) override { WNDCLASS wc; @@ -3517,13 +3517,13 @@ namespace olc wc.hbrBackground = nullptr; wc.lpszClassName = olcT("OLC_PIXEL_GAME_ENGINE"); RegisterClass(&wc); - + // Define window furniture DWORD dwExStyle = WS_EX_APPWINDOW | WS_EX_WINDOWEDGE; DWORD dwStyle = WS_CAPTION | WS_SYSMENU | WS_VISIBLE | WS_THICKFRAME; - + olc::vi2d vTopLeft = vWindowPos; - + // Handle Fullscreen if (bFullScreen) { @@ -3536,16 +3536,16 @@ namespace olc vTopLeft.x = 0; vTopLeft.y = 0; } - + // Keep client size as requested RECT rWndRect = { 0, 0, vWindowSize.x, vWindowSize.y }; AdjustWindowRectEx(&rWndRect, dwStyle, FALSE, dwExStyle); int width = rWndRect.right - rWndRect.left; int height = rWndRect.bottom - rWndRect.top; - + olc_hWnd = CreateWindowEx(dwExStyle, olcT("OLC_PIXEL_GAME_ENGINE"), olcT(""), dwStyle, - vTopLeft.x, vTopLeft.y, width, height, NULL, NULL, GetModuleHandle(nullptr), this); - + vTopLeft.x, vTopLeft.y, width, height, NULL, NULL, GetModuleHandle(nullptr), this); + // Create Keyboard Mapping mapKeys[0x00] = Key::NONE; mapKeys[0x41] = Key::A; mapKeys[0x42] = Key::B; mapKeys[0x43] = Key::C; mapKeys[0x44] = Key::D; mapKeys[0x45] = Key::E; @@ -3554,29 +3554,29 @@ namespace olc mapKeys[0x50] = Key::P; mapKeys[0x51] = Key::Q; mapKeys[0x52] = Key::R; mapKeys[0x53] = Key::S; mapKeys[0x54] = Key::T; mapKeys[0x55] = Key::U; mapKeys[0x56] = Key::V; mapKeys[0x57] = Key::W; mapKeys[0x58] = Key::X; mapKeys[0x59] = Key::Y; mapKeys[0x5A] = Key::Z; - + mapKeys[VK_F1] = Key::F1; mapKeys[VK_F2] = Key::F2; mapKeys[VK_F3] = Key::F3; mapKeys[VK_F4] = Key::F4; mapKeys[VK_F5] = Key::F5; mapKeys[VK_F6] = Key::F6; mapKeys[VK_F7] = Key::F7; mapKeys[VK_F8] = Key::F8; mapKeys[VK_F9] = Key::F9; mapKeys[VK_F10] = Key::F10; mapKeys[VK_F11] = Key::F11; mapKeys[VK_F12] = Key::F12; - + mapKeys[VK_DOWN] = Key::DOWN; mapKeys[VK_LEFT] = Key::LEFT; mapKeys[VK_RIGHT] = Key::RIGHT; mapKeys[VK_UP] = Key::UP; mapKeys[VK_RETURN] = Key::ENTER; //mapKeys[VK_RETURN] = Key::RETURN; - + mapKeys[VK_BACK] = Key::BACK; mapKeys[VK_ESCAPE] = Key::ESCAPE; mapKeys[VK_RETURN] = Key::ENTER; mapKeys[VK_PAUSE] = Key::PAUSE; mapKeys[VK_SCROLL] = Key::SCROLL; mapKeys[VK_TAB] = Key::TAB; mapKeys[VK_DELETE] = Key::DEL; mapKeys[VK_HOME] = Key::HOME; mapKeys[VK_END] = Key::END; mapKeys[VK_PRIOR] = Key::PGUP; mapKeys[VK_NEXT] = Key::PGDN; mapKeys[VK_INSERT] = Key::INS; mapKeys[VK_SHIFT] = Key::SHIFT; mapKeys[VK_CONTROL] = Key::CTRL; mapKeys[VK_SPACE] = Key::SPACE; - + mapKeys[0x30] = Key::K0; mapKeys[0x31] = Key::K1; mapKeys[0x32] = Key::K2; mapKeys[0x33] = Key::K3; mapKeys[0x34] = Key::K4; mapKeys[0x35] = Key::K5; mapKeys[0x36] = Key::K6; mapKeys[0x37] = Key::K7; mapKeys[0x38] = Key::K8; mapKeys[0x39] = Key::K9; - + mapKeys[VK_NUMPAD0] = Key::NP0; mapKeys[VK_NUMPAD1] = Key::NP1; mapKeys[VK_NUMPAD2] = Key::NP2; mapKeys[VK_NUMPAD3] = Key::NP3; mapKeys[VK_NUMPAD4] = Key::NP4; mapKeys[VK_NUMPAD5] = Key::NP5; mapKeys[VK_NUMPAD6] = Key::NP6; mapKeys[VK_NUMPAD7] = Key::NP7; mapKeys[VK_NUMPAD8] = Key::NP8; mapKeys[VK_NUMPAD9] = Key::NP9; mapKeys[VK_MULTIPLY] = Key::NP_MUL; mapKeys[VK_ADD] = Key::NP_ADD; mapKeys[VK_DIVIDE] = Key::NP_DIV; mapKeys[VK_SUBTRACT] = Key::NP_SUB; mapKeys[VK_DECIMAL] = Key::NP_DECIMAL; return olc::OK; } - + virtual olc::rcode SetWindowTitle(const std::string& s) override { #ifdef UNICODE @@ -3586,7 +3586,7 @@ namespace olc #endif return olc::OK; } - + virtual olc::rcode StartSystemEventLoop() override { MSG msg; @@ -3597,37 +3597,37 @@ namespace olc } return olc::OK; } - + virtual olc::rcode HandleSystemEvent() override { return olc::rcode::FAIL; } - + // Windows Event Handler - this is statically connected to the windows event system static LRESULT CALLBACK olc_WindowEvent(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam) { switch (uMsg) { - case WM_MOUSEMOVE: - { - // Thanks @ForAbby (Discord) - uint16_t x = lParam & 0xFFFF; uint16_t y = (lParam >> 16) & 0xFFFF; - int16_t ix = *(int16_t*)&x; int16_t iy = *(int16_t*)&y; - ptrPGE->olc_UpdateMouse(ix, iy); - return 0; - } - case WM_SIZE: ptrPGE->olc_UpdateWindowSize(lParam & 0xFFFF, (lParam >> 16) & 0xFFFF); return 0; - case WM_MOUSEWHEEL: ptrPGE->olc_UpdateMouseWheel(GET_WHEEL_DELTA_WPARAM(wParam)); return 0; - case WM_MOUSELEAVE: ptrPGE->olc_UpdateMouseFocus(false); return 0; - case WM_SETFOCUS: ptrPGE->olc_UpdateKeyFocus(true); return 0; - case WM_KILLFOCUS: ptrPGE->olc_UpdateKeyFocus(false); return 0; - case WM_KEYDOWN: ptrPGE->olc_UpdateKeyState(mapKeys[wParam], true); return 0; - case WM_KEYUP: ptrPGE->olc_UpdateKeyState(mapKeys[wParam], false); return 0; - case WM_LBUTTONDOWN:ptrPGE->olc_UpdateMouseState(0, true); return 0; - case WM_LBUTTONUP: ptrPGE->olc_UpdateMouseState(0, false); return 0; - case WM_RBUTTONDOWN:ptrPGE->olc_UpdateMouseState(1, true); return 0; - case WM_RBUTTONUP: ptrPGE->olc_UpdateMouseState(1, false); return 0; - case WM_MBUTTONDOWN:ptrPGE->olc_UpdateMouseState(2, true); return 0; - case WM_MBUTTONUP: ptrPGE->olc_UpdateMouseState(2, false); return 0; - case WM_CLOSE: ptrPGE->olc_Terminate(); return 0; - case WM_DESTROY: PostQuitMessage(0); DestroyWindow(hWnd); return 0; + case WM_MOUSEMOVE: + { + // Thanks @ForAbby (Discord) + uint16_t x = lParam & 0xFFFF; uint16_t y = (lParam >> 16) & 0xFFFF; + int16_t ix = *(int16_t*)&x; int16_t iy = *(int16_t*)&y; + ptrPGE->olc_UpdateMouse(ix, iy); + return 0; + } + case WM_SIZE: ptrPGE->olc_UpdateWindowSize(lParam & 0xFFFF, (lParam >> 16) & 0xFFFF); return 0; + case WM_MOUSEWHEEL: ptrPGE->olc_UpdateMouseWheel(GET_WHEEL_DELTA_WPARAM(wParam)); return 0; + case WM_MOUSELEAVE: ptrPGE->olc_UpdateMouseFocus(false); return 0; + case WM_SETFOCUS: ptrPGE->olc_UpdateKeyFocus(true); return 0; + case WM_KILLFOCUS: ptrPGE->olc_UpdateKeyFocus(false); return 0; + case WM_KEYDOWN: ptrPGE->olc_UpdateKeyState(mapKeys[wParam], true); return 0; + case WM_KEYUP: ptrPGE->olc_UpdateKeyState(mapKeys[wParam], false); return 0; + case WM_LBUTTONDOWN:ptrPGE->olc_UpdateMouseState(0, true); return 0; + case WM_LBUTTONUP: ptrPGE->olc_UpdateMouseState(0, false); return 0; + case WM_RBUTTONDOWN:ptrPGE->olc_UpdateMouseState(1, true); return 0; + case WM_RBUTTONUP: ptrPGE->olc_UpdateMouseState(1, false); return 0; + case WM_MBUTTONDOWN:ptrPGE->olc_UpdateMouseState(2, true); return 0; + case WM_MBUTTONUP: ptrPGE->olc_UpdateMouseState(2, false); return 0; + case WM_CLOSE: ptrPGE->olc_Terminate(); return 0; + case WM_DESTROY: PostQuitMessage(0); DestroyWindow(hWnd); return 0; } return DefWindowProc(hWnd, uMsg, wParam, lParam); } @@ -3650,36 +3650,36 @@ namespace olc { class Platform_Linux : public olc::Platform { - private: + private: X11::Display* olc_Display = nullptr; X11::Window olc_WindowRoot; X11::Window olc_Window; X11::XVisualInfo* olc_VisualInfo; X11::Colormap olc_ColourMap; X11::XSetWindowAttributes olc_SetWindowAttribs; - - public: + + public: virtual olc::rcode ApplicationStartUp() override { return olc::rcode::OK; } - + virtual olc::rcode ApplicationCleanUp() override { return olc::rcode::OK; } - + virtual olc::rcode ThreadStartUp() override { return olc::rcode::OK; } - + virtual olc::rcode ThreadCleanUp() override { renderer->DestroyDevice(); return olc::OK; } - + virtual olc::rcode CreateGraphics(bool bFullScreen, bool bEnableVSYNC, const olc::vi2d& vViewPos, const olc::vi2d& vViewSize) override { if (renderer->CreateDevice({ olc_Display, &olc_Window, olc_VisualInfo }, bFullScreen, bEnableVSYNC) == olc::rcode::OK) @@ -3690,38 +3690,38 @@ namespace olc else return olc::rcode::FAIL; } - + virtual olc::rcode CreateWindowPane(const olc::vi2d& vWindowPos, olc::vi2d& vWindowSize, bool bFullScreen) override { using namespace X11; XInitThreads(); - + // Grab the deafult display and window olc_Display = XOpenDisplay(NULL); olc_WindowRoot = DefaultRootWindow(olc_Display); - + // Based on the display capabilities, configure the appearance of the window GLint olc_GLAttribs[] = { GLX_RGBA, GLX_DEPTH_SIZE, 24, GLX_DOUBLEBUFFER, None }; olc_VisualInfo = glXChooseVisual(olc_Display, 0, olc_GLAttribs); olc_ColourMap = XCreateColormap(olc_Display, olc_WindowRoot, olc_VisualInfo->visual, AllocNone); olc_SetWindowAttribs.colormap = olc_ColourMap; - + // Register which events we are interested in receiving olc_SetWindowAttribs.event_mask = ExposureMask | KeyPressMask | KeyReleaseMask | ButtonPressMask | ButtonReleaseMask | PointerMotionMask | FocusChangeMask | StructureNotifyMask; - + // Create the window olc_Window = XCreateWindow(olc_Display, olc_WindowRoot, vWindowPos.x, vWindowPos.y, - vWindowSize.x, vWindowSize.y, - 0, olc_VisualInfo->depth, InputOutput, olc_VisualInfo->visual, - CWColormap | CWEventMask, &olc_SetWindowAttribs); - + vWindowSize.x, vWindowSize.y, + 0, olc_VisualInfo->depth, InputOutput, olc_VisualInfo->visual, + CWColormap | CWEventMask, &olc_SetWindowAttribs); + Atom wmDelete = XInternAtom(olc_Display, "WM_DELETE_WINDOW", true); XSetWMProtocols(olc_Display, olc_Window, &wmDelete, 1); - + XMapWindow(olc_Display, olc_Window); XStoreName(olc_Display, olc_Window, ""); - + if (bFullScreen) // Thanks DragonEye, again :D { Atom wm_state; @@ -3739,14 +3739,14 @@ namespace olc xev.xclient.data.l[3] = 0; // source indication XMapWindow(olc_Display, olc_Window); XSendEvent(olc_Display, DefaultRootWindow(olc_Display), False, - SubstructureRedirectMask | SubstructureNotifyMask, &xev); + SubstructureRedirectMask | SubstructureNotifyMask, &xev); XFlush(olc_Display); XWindowAttributes gwa; XGetWindowAttributes(olc_Display, olc_Window, &gwa); vWindowSize.x = gwa.width; vWindowSize.y = gwa.height; } - + // Create Keyboard Mapping mapKeys[0x00] = Key::NONE; mapKeys[0x61] = Key::A; mapKeys[0x62] = Key::B; mapKeys[0x63] = Key::C; mapKeys[0x64] = Key::D; mapKeys[0x65] = Key::E; @@ -3755,41 +3755,41 @@ namespace olc mapKeys[0x70] = Key::P; mapKeys[0x71] = Key::Q; mapKeys[0x72] = Key::R; mapKeys[0x73] = Key::S; mapKeys[0x74] = Key::T; mapKeys[0x75] = Key::U; mapKeys[0x76] = Key::V; mapKeys[0x77] = Key::W; mapKeys[0x78] = Key::X; mapKeys[0x79] = Key::Y; mapKeys[0x7A] = Key::Z; - + mapKeys[XK_F1] = Key::F1; mapKeys[XK_F2] = Key::F2; mapKeys[XK_F3] = Key::F3; mapKeys[XK_F4] = Key::F4; mapKeys[XK_F5] = Key::F5; mapKeys[XK_F6] = Key::F6; mapKeys[XK_F7] = Key::F7; mapKeys[XK_F8] = Key::F8; mapKeys[XK_F9] = Key::F9; mapKeys[XK_F10] = Key::F10; mapKeys[XK_F11] = Key::F11; mapKeys[XK_F12] = Key::F12; - + mapKeys[XK_Down] = Key::DOWN; mapKeys[XK_Left] = Key::LEFT; mapKeys[XK_Right] = Key::RIGHT; mapKeys[XK_Up] = Key::UP; mapKeys[XK_KP_Enter] = Key::ENTER; mapKeys[XK_Return] = Key::ENTER; - + mapKeys[XK_BackSpace] = Key::BACK; mapKeys[XK_Escape] = Key::ESCAPE; mapKeys[XK_Linefeed] = Key::ENTER; mapKeys[XK_Pause] = Key::PAUSE; mapKeys[XK_Scroll_Lock] = Key::SCROLL; mapKeys[XK_Tab] = Key::TAB; mapKeys[XK_Delete] = Key::DEL; mapKeys[XK_Home] = Key::HOME; mapKeys[XK_End] = Key::END; mapKeys[XK_Page_Up] = Key::PGUP; mapKeys[XK_Page_Down] = Key::PGDN; mapKeys[XK_Insert] = Key::INS; mapKeys[XK_Shift_L] = Key::SHIFT; mapKeys[XK_Shift_R] = Key::SHIFT; mapKeys[XK_Control_L] = Key::CTRL; mapKeys[XK_Control_R] = Key::CTRL; mapKeys[XK_space] = Key::SPACE; mapKeys[XK_period] = Key::PERIOD; - + mapKeys[XK_0] = Key::K0; mapKeys[XK_1] = Key::K1; mapKeys[XK_2] = Key::K2; mapKeys[XK_3] = Key::K3; mapKeys[XK_4] = Key::K4; mapKeys[XK_5] = Key::K5; mapKeys[XK_6] = Key::K6; mapKeys[XK_7] = Key::K7; mapKeys[XK_8] = Key::K8; mapKeys[XK_9] = Key::K9; - + mapKeys[XK_KP_0] = Key::NP0; mapKeys[XK_KP_1] = Key::NP1; mapKeys[XK_KP_2] = Key::NP2; mapKeys[XK_KP_3] = Key::NP3; mapKeys[XK_KP_4] = Key::NP4; mapKeys[XK_KP_5] = Key::NP5; mapKeys[XK_KP_6] = Key::NP6; mapKeys[XK_KP_7] = Key::NP7; mapKeys[XK_KP_8] = Key::NP8; mapKeys[XK_KP_9] = Key::NP9; mapKeys[XK_KP_Multiply] = Key::NP_MUL; mapKeys[XK_KP_Add] = Key::NP_ADD; mapKeys[XK_KP_Divide] = Key::NP_DIV; mapKeys[XK_KP_Subtract] = Key::NP_SUB; mapKeys[XK_KP_Decimal] = Key::NP_DECIMAL; - + return olc::OK; } - + virtual olc::rcode SetWindowTitle(const std::string& s) override { X11::XStoreName(olc_Display, olc_Window, s.c_str()); return olc::OK; } - + virtual olc::rcode StartSystemEventLoop() override { return olc::OK; } - + virtual olc::rcode HandleSystemEvent() override { using namespace X11; @@ -3831,22 +3831,22 @@ namespace olc { switch (xev.xbutton.button) { - case 1: ptrPGE->olc_UpdateMouseState(0, true); break; - case 2: ptrPGE->olc_UpdateMouseState(2, true); break; - case 3: ptrPGE->olc_UpdateMouseState(1, true); break; - case 4: ptrPGE->olc_UpdateMouseWheel(120); break; - case 5: ptrPGE->olc_UpdateMouseWheel(-120); break; - default: break; + case 1: ptrPGE->olc_UpdateMouseState(0, true); break; + case 2: ptrPGE->olc_UpdateMouseState(2, true); break; + case 3: ptrPGE->olc_UpdateMouseState(1, true); break; + case 4: ptrPGE->olc_UpdateMouseWheel(120); break; + case 5: ptrPGE->olc_UpdateMouseWheel(-120); break; + default: break; } } else if (xev.type == ButtonRelease) { switch (xev.xbutton.button) { - case 1: ptrPGE->olc_UpdateMouseState(0, false); break; - case 2: ptrPGE->olc_UpdateMouseState(2, false); break; - case 3: ptrPGE->olc_UpdateMouseState(1, false); break; - default: break; + case 1: ptrPGE->olc_UpdateMouseState(0, false); break; + case 2: ptrPGE->olc_UpdateMouseState(2, false); break; + case 3: ptrPGE->olc_UpdateMouseState(1, false); break; + default: break; } } else if (xev.type == MotionNotify) @@ -3891,33 +3891,33 @@ namespace olc #if defined(__APPLE__) namespace olc { - + class Platform_GLUT : public olc::Platform { - public: + public: static std::atomic* bActiveRef; - + virtual olc::rcode ApplicationStartUp() override { return olc::rcode::OK; } - + virtual olc::rcode ApplicationCleanUp() override { return olc::rcode::OK; } - + virtual olc::rcode ThreadStartUp() override { return olc::rcode::OK; } - + virtual olc::rcode ThreadCleanUp() override { renderer->DestroyDevice(); return olc::OK; } - + virtual olc::rcode CreateGraphics(bool bFullScreen, bool bEnableVSYNC, const olc::vi2d& vViewPos, const olc::vi2d& vViewSize) override { if (renderer->CreateDevice({}, bFullScreen, bEnableVSYNC) == olc::rcode::OK) @@ -3928,7 +3928,7 @@ namespace olc else return olc::rcode::FAIL; } - + static void ExitMainLoop() { if (!ptrPGE->OnUserDestroy()) @@ -3940,7 +3940,7 @@ namespace olc platform->ApplicationCleanUp(); exit(0); } - + static void ThreadFunct() { if (!*bActiveRef) @@ -3950,30 +3950,30 @@ namespace olc } glutPostRedisplay(); } - + static void DrawFunct() { ptrPGE->olc_CoreUpdate(); } - + virtual olc::rcode CreateWindowPane(const olc::vi2d& vWindowPos, olc::vi2d& vWindowSize, bool bFullScreen) override { renderer->PrepareDevice(); - - + + if (bFullScreen) { vWindowSize.x = glutGet(GLUT_SCREEN_WIDTH); vWindowSize.y = glutGet(GLUT_SCREEN_HEIGHT); glutFullScreen(); } - + if (vWindowSize.x > glutGet(GLUT_SCREEN_WIDTH) || vWindowSize.y > glutGet(GLUT_SCREEN_HEIGHT)) { perror("ERROR: The specified window dimensions do not fit on your screen\n"); return olc::FAIL; } - + // Create Keyboard Mapping mapKeys[0x00] = Key::NONE; mapKeys['A'] = Key::A; mapKeys['B'] = Key::B; mapKeys['C'] = Key::C; mapKeys['D'] = Key::D; mapKeys['E'] = Key::E; @@ -3982,161 +3982,161 @@ namespace olc mapKeys['P'] = Key::P; mapKeys['Q'] = Key::Q; mapKeys['R'] = Key::R; mapKeys['S'] = Key::S; mapKeys['T'] = Key::T; mapKeys['U'] = Key::U; mapKeys['V'] = Key::V; mapKeys['W'] = Key::W; mapKeys['X'] = Key::X; mapKeys['Y'] = Key::Y; mapKeys['Z'] = Key::Z; - + mapKeys[GLUT_KEY_F1] = Key::F1; mapKeys[GLUT_KEY_F2] = Key::F2; mapKeys[GLUT_KEY_F3] = Key::F3; mapKeys[GLUT_KEY_F4] = Key::F4; mapKeys[GLUT_KEY_F5] = Key::F5; mapKeys[GLUT_KEY_F6] = Key::F6; mapKeys[GLUT_KEY_F7] = Key::F7; mapKeys[GLUT_KEY_F8] = Key::F8; mapKeys[GLUT_KEY_F9] = Key::F9; mapKeys[GLUT_KEY_F10] = Key::F10; mapKeys[GLUT_KEY_F11] = Key::F11; mapKeys[GLUT_KEY_F12] = Key::F12; - + mapKeys[GLUT_KEY_DOWN] = Key::DOWN; mapKeys[GLUT_KEY_LEFT] = Key::LEFT; mapKeys[GLUT_KEY_RIGHT] = Key::RIGHT; mapKeys[GLUT_KEY_UP] = Key::UP; mapKeys[13] = Key::ENTER; - + mapKeys[127] = Key::BACK; mapKeys[27] = Key::ESCAPE; mapKeys[9] = Key::TAB; mapKeys[GLUT_KEY_HOME] = Key::HOME; mapKeys[GLUT_KEY_END] = Key::END; mapKeys[GLUT_KEY_PAGE_UP] = Key::PGUP; mapKeys[GLUT_KEY_PAGE_DOWN] = Key::PGDN; mapKeys[GLUT_KEY_INSERT] = Key::INS; mapKeys[32] = Key::SPACE; mapKeys[46] = Key::PERIOD; - + mapKeys[48] = Key::K0; mapKeys[49] = Key::K1; mapKeys[50] = Key::K2; mapKeys[51] = Key::K3; mapKeys[52] = Key::K4; mapKeys[53] = Key::K5; mapKeys[54] = Key::K6; mapKeys[55] = Key::K7; mapKeys[56] = Key::K8; mapKeys[57] = Key::K9; - + glutKeyboardFunc([](unsigned char key, int x, int y) -> void { - switch (glutGetModifiers()) - { - case 0: //This is when there are no modifiers - if ('a' <= key && key <= 'z') key -= 32; - break; - case GLUT_ACTIVE_SHIFT: - ptrPGE->olc_UpdateKeyState(Key::SHIFT, true); - break; - case GLUT_ACTIVE_CTRL: - if ('a' <= key && key <= 'z') key -= 32; - ptrPGE->olc_UpdateKeyState(Key::CTRL, true); - break; - case GLUT_ACTIVE_ALT: - if ('a' <= key && key <= 'z') key -= 32; - break; - } - - if (mapKeys[key]) - ptrPGE->olc_UpdateKeyState(mapKeys[key], true); - }); - + switch (glutGetModifiers()) + { + case 0: //This is when there are no modifiers + if ('a' <= key && key <= 'z') key -= 32; + break; + case GLUT_ACTIVE_SHIFT: + ptrPGE->olc_UpdateKeyState(Key::SHIFT, true); + break; + case GLUT_ACTIVE_CTRL: + if ('a' <= key && key <= 'z') key -= 32; + ptrPGE->olc_UpdateKeyState(Key::CTRL, true); + break; + case GLUT_ACTIVE_ALT: + if ('a' <= key && key <= 'z') key -= 32; + break; + } + + if (mapKeys[key]) + ptrPGE->olc_UpdateKeyState(mapKeys[key], true); + }); + glutKeyboardUpFunc([](unsigned char key, int x, int y) -> void { - switch (glutGetModifiers()) - { - case 0: //This is when there are no modifiers - if ('a' <= key && key <= 'z') key -= 32; - break; - case GLUT_ACTIVE_SHIFT: - ptrPGE->olc_UpdateKeyState(Key::SHIFT, false); - break; - case GLUT_ACTIVE_CTRL: - if ('a' <= key && key <= 'z') key -= 32; - ptrPGE->olc_UpdateKeyState(Key::CTRL, false); - break; - case GLUT_ACTIVE_ALT: - if ('a' <= key && key <= 'z') key -= 32; - //No ALT in PGE - break; - } - - if (mapKeys[key]) - ptrPGE->olc_UpdateKeyState(mapKeys[key], false); - }); - + switch (glutGetModifiers()) + { + case 0: //This is when there are no modifiers + if ('a' <= key && key <= 'z') key -= 32; + break; + case GLUT_ACTIVE_SHIFT: + ptrPGE->olc_UpdateKeyState(Key::SHIFT, false); + break; + case GLUT_ACTIVE_CTRL: + if ('a' <= key && key <= 'z') key -= 32; + ptrPGE->olc_UpdateKeyState(Key::CTRL, false); + break; + case GLUT_ACTIVE_ALT: + if ('a' <= key && key <= 'z') key -= 32; + //No ALT in PGE + break; + } + + if (mapKeys[key]) + ptrPGE->olc_UpdateKeyState(mapKeys[key], false); + }); + //Special keys glutSpecialFunc([](int key, int x, int y) -> void { - if (mapKeys[key]) - ptrPGE->olc_UpdateKeyState(mapKeys[key], true); - }); - + if (mapKeys[key]) + ptrPGE->olc_UpdateKeyState(mapKeys[key], true); + }); + glutSpecialUpFunc([](int key, int x, int y) -> void { - if (mapKeys[key]) - ptrPGE->olc_UpdateKeyState(mapKeys[key], false); - }); - + if (mapKeys[key]) + ptrPGE->olc_UpdateKeyState(mapKeys[key], false); + }); + glutMouseFunc([](int button, int state, int x, int y) -> void { - switch (button) - { - case GLUT_LEFT_BUTTON: - if (state == GLUT_UP) ptrPGE->olc_UpdateMouseState(0, false); - else if (state == GLUT_DOWN) ptrPGE->olc_UpdateMouseState(0, true); - break; - case GLUT_MIDDLE_BUTTON: - if (state == GLUT_UP) ptrPGE->olc_UpdateMouseState(2, false); - else if (state == GLUT_DOWN) ptrPGE->olc_UpdateMouseState(2, true); - break; - case GLUT_RIGHT_BUTTON: - if (state == GLUT_UP) ptrPGE->olc_UpdateMouseState(1, false); - else if (state == GLUT_DOWN) ptrPGE->olc_UpdateMouseState(1, true); - break; - } - }); - + switch (button) + { + case GLUT_LEFT_BUTTON: + if (state == GLUT_UP) ptrPGE->olc_UpdateMouseState(0, false); + else if (state == GLUT_DOWN) ptrPGE->olc_UpdateMouseState(0, true); + break; + case GLUT_MIDDLE_BUTTON: + if (state == GLUT_UP) ptrPGE->olc_UpdateMouseState(2, false); + else if (state == GLUT_DOWN) ptrPGE->olc_UpdateMouseState(2, true); + break; + case GLUT_RIGHT_BUTTON: + if (state == GLUT_UP) ptrPGE->olc_UpdateMouseState(1, false); + else if (state == GLUT_DOWN) ptrPGE->olc_UpdateMouseState(1, true); + break; + } + }); + auto mouseMoveCall = [](int x, int y) -> void { ptrPGE->olc_UpdateMouse(x, y); }; - + glutMotionFunc(mouseMoveCall); glutPassiveMotionFunc(mouseMoveCall); - + glutEntryFunc([](int state) -> void { - if (state == GLUT_ENTERED) ptrPGE->olc_UpdateKeyFocus(true); - else if (state == GLUT_LEFT) ptrPGE->olc_UpdateKeyFocus(false); - }); - + if (state == GLUT_ENTERED) ptrPGE->olc_UpdateKeyFocus(true); + else if (state == GLUT_LEFT) ptrPGE->olc_UpdateKeyFocus(false); + }); + glutDisplayFunc(DrawFunct); glutIdleFunc(ThreadFunct); - + return olc::OK; } - + virtual olc::rcode SetWindowTitle(const std::string& s) override { glutSetWindowTitle(s.c_str()); return olc::OK; } - + virtual olc::rcode StartSystemEventLoop() override { glutMainLoop(); return olc::OK; } - + virtual olc::rcode HandleSystemEvent() override { return olc::OK; } }; - + std::atomic* Platform_GLUT::bActiveRef{ nullptr }; - + //Custom Start olc::rcode PixelGameEngine::Start() { if (platform->ApplicationStartUp() != olc::OK) return olc::FAIL; - + // Construct the window if (platform->CreateWindowPane({ 30,30 }, vWindowSize, bFullScreen) != olc::OK) return olc::FAIL; olc_UpdateWindowSize(vWindowSize.x, vWindowSize.y); - - + + if (platform->ThreadStartUp() == olc::FAIL) return olc::FAIL; - + olc_PrepareEngine(); - + if (!OnUserCreate()) return olc::FAIL; - + Platform_GLUT::bActiveRef = &bAtomActive; - + glutWMCloseFunc(Platform_GLUT::ExitMainLoop); - + bAtomActive = true; - + platform->StartSystemEventLoop(); - + //This code will not even be run but why not if (platform->ApplicationCleanUp() != olc::OK) return olc::FAIL; - + return olc::OK; } } @@ -4152,48 +4152,48 @@ namespace olc { void PixelGameEngine::olc_ConfigureSystem() { - + #if defined(PGE_ILOADER_GDI) olc::Sprite::loader = std::make_unique(); #endif - + #if defined(PGE_ILOADER_LIBPNG) olc::Sprite::loader = std::make_unique(); #endif - + #if defined(PGE_ILOADER_STB) olc::Sprite::loader = std::make_unique(); #endif - - - - + + + + #if defined(_WIN32) platform = std::make_unique(); #endif - + #if defined(__linux__) || defined(__FreeBSD__) platform = std::make_unique(); #endif - + #if defined(__APPLE__) platform = std::make_unique(); #endif - - - + + + #if defined(OLC_GFX_OPENGL10) renderer = std::make_unique(); #endif - + #if defined(OLC_GFX_OPENGL33) renderer = std::make_unique(); #endif - + #if defined(OLC_GFX_DIRECTX10) renderer = std::make_unique(); #endif - + // Associate components with PGE instance platform->ptrPGE = this; renderer->ptrPGE = this; diff --git a/The Great Machine/res/torch.png b/The Great Machine/res/torch.png new file mode 100644 index 0000000000000000000000000000000000000000..4bb2d78f5daf73e9bc5d3ccf82b3348fef4a09c7 GIT binary patch literal 81107 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

)-0m9lud+0eJL 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 literal 0 HcmV?d00001 diff --git a/res/torch.png b/res/torch.png new file mode 100644 index 0000000000000000000000000000000000000000..4bb2d78f5daf73e9bc5d3ccf82b3348fef4a09c7 GIT binary patch literal 81107 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

)-0m9lud+0eJL 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 literal 0 HcmV?d00001