diff --git a/editor/region.cpp b/editor/region.cpp new file mode 100644 index 0000000..d02f505 --- /dev/null +++ b/editor/region.cpp @@ -0,0 +1,113 @@ +/* Copyright: (c) Kayne Ruse 2013 + * + * This software is provided 'as-is', without any express or implied + * warranty. In no event will the authors be held liable for any damages + * arising from the use of this software. + * + * Permission is granted to anyone to use this software for any purpose, + * including commercial applications, and to alter it and redistribute it + * freely, subject to the following restrictions: + * + * 1. The origin of this software must not be misrepresented; you must not + * claim that you wrote the original software. If you use this software + * in a product, an acknowledgment in the product documentation would be + * appreciated but is not required. + * + * 2. Altered source versions must be plainly marked as such, and must not be + * misrepresented as being the original software. + * + * 3. This notice may not be removed or altered from any source + * distribution. +*/ +#include "region.hpp" + +#include +#include + +static int snap(int base, int x) { + if (x < 0) { + x++; + return x - x % base - base; + } + return x - x % base; +} + +Region::Region(int i, int j, int k, int l): + x(i), + y(j), + width(k), + height(l) +{ + //make sure that the region's position lines up + if (x != snap(width, x) || y != snap(height, y)) { + std::ostringstream os; + os << "Region is unaligned; x: " << x << ", y: " << y << ", width: " << width << ", height: " << height; + throw(std::runtime_error(os.str())); + } +} + +bool Region::NewTile(Tile const& tile) { + if (!InBounds(tile.x, tile.y)) { + throw(std::runtime_error("New tile location out of bounds")); + } + + bool ret = tiles.erase(tile); + tiles.insert(tile); + return ret; +} + +Tile Region::GetTile(int x, int y, int tw, int th, int minDepth) { + /* This method is used to find a tile that covers (x, y). + * This method returns the first tile above minDepth. + * Since Region & Tile do not save the tile's size, tw & th are the size of the tiles. + */ + std::set::iterator ptr = tiles.begin(); + while(ptr != tiles.end()) { + //skip the tiles that are too deep + if (ptr->depth >= minDepth) { + break; + } + ptr++; + } + while(ptr != tiles.end()) { + //find the first tile here + if ((ptr->x <= x) && (ptr->y <= y) && (ptr->x + tw > x) && (ptr->y + th > y)) { + break; + } + ptr++; + } + if (ptr != tiles.end()) { + return *ptr; + } + return {0,0,0,-1}; +} + +bool Region::DeleteTile(Tile const& tile) { + if (!InBounds(tile.x, tile.y)) { + throw(std::runtime_error("Deleted tile location out of bounds")); + } + return tiles.erase(tile); +} + +bool Region::InBounds(int x, int y) { + return (x > this->x) && (y > this->y) && (x < this->x + this->width) && (y < this->y + this->height); +} + +bool operator<(Region const& lhs, Region const& rhs) { + //sort by y -> x + if (lhs.y == rhs.y) { + return lhs.x < rhs.x; + } + return lhs.y < rhs.y; +} + +inline bool operator>(Region const& lhs, Region const& rhs) { + //wrap the other operator + return rhs < lhs; +} + +inline bool operator==(Region const& lhs, Region const& rhs) { + //comparisons work on the location ONLY + //this function is redundant as far as the std::set object is concerned + return (lhs.x == rhs.x) && (lhs.y == rhs.y); +} diff --git a/editor/region.hpp b/editor/region.hpp new file mode 100644 index 0000000..964f5f3 --- /dev/null +++ b/editor/region.hpp @@ -0,0 +1,64 @@ +/* Copyright: (c) Kayne Ruse 2013 + * + * This software is provided 'as-is', without any express or implied + * warranty. In no event will the authors be held liable for any damages + * arising from the use of this software. + * + * Permission is granted to anyone to use this software for any purpose, + * including commercial applications, and to alter it and redistribute it + * freely, subject to the following restrictions: + * + * 1. The origin of this software must not be misrepresented; you must not + * claim that you wrote the original software. If you use this software + * in a product, an acknowledgment in the product documentation would be + * appreciated but is not required. + * + * 2. Altered source versions must be plainly marked as such, and must not be + * misrepresented as being the original software. + * + * 3. This notice may not be removed or altered from any source + * distribution. +*/ +#ifndef REGION_HPP_ +#define REGION_HPP_ + +#include "tile.hpp" + +#include + +class Region { +public: + Region() = delete; + Region(int x, int y, int width, int height); + ~Region() = default; + + bool NewTile(Tile const&); + + Tile GetTile(int x, int y, int tw, int th, int minDepth); + + bool DeleteTile(int x, int y, int tw, int th, int minDepth) { return DeleteTile(GetTile(x, y, tw, th, minDepth)); } + bool DeleteTile(Tile const&); + + bool InBounds(int x, int y); + + //accessors & mutators + int GetX() const { return x; } + int GetY() const { return y; } + int GetWidth() const { return width; } + int GetHeight() const { return height; } + + std::set* GetTiles() { return &tiles; } + + friend bool operator<(Region const& lhs, Region const& rhs); + friend bool operator>(Region const& lhs, Region const& rhs); + friend bool operator==(Region const& lhs, Region const& rhs); + +private: + int const x; + int const y; + int const width; + int const height; + std::set tiles; +}; + +#endif diff --git a/editor/tile.cpp b/editor/tile.cpp new file mode 100644 index 0000000..fcb2373 --- /dev/null +++ b/editor/tile.cpp @@ -0,0 +1,44 @@ +/* Copyright: (c) Kayne Ruse 2013 + * + * This software is provided 'as-is', without any express or implied + * warranty. In no event will the authors be held liable for any damages + * arising from the use of this software. + * + * Permission is granted to anyone to use this software for any purpose, + * including commercial applications, and to alter it and redistribute it + * freely, subject to the following restrictions: + * + * 1. The origin of this software must not be misrepresented; you must not + * claim that you wrote the original software. If you use this software + * in a product, an acknowledgment in the product documentation would be + * appreciated but is not required. + * + * 2. Altered source versions must be plainly marked as such, and must not be + * misrepresented as being the original software. + * + * 3. This notice may not be removed or altered from any source + * distribution. +*/ +#include "tile.hpp" + +bool operator<(Tile const& lhs, Tile const& rhs) { + //sort by depth -> y -> x + if (lhs.depth == rhs.depth) { + if (lhs.y == rhs.y) { + return lhs.x < rhs.x; + } + return lhs.y < rhs.y; + } + return lhs.depth < rhs.depth; +} + +inline bool operator>(Tile const& lhs, Tile const& rhs) { + //wrap the other operator + return rhs < lhs; +} + +inline bool operator==(Tile const& lhs, Tile const& rhs) { + //comparisons work on the location ONLY + //this function is redundant as far as the std::set object is concerned + return (lhs.x == rhs.x) && (lhs.y == rhs.y) && (lhs.depth == rhs.depth); +} diff --git a/editor/tile.hpp b/editor/tile.hpp new file mode 100644 index 0000000..7a597ad --- /dev/null +++ b/editor/tile.hpp @@ -0,0 +1,40 @@ +/* Copyright: (c) Kayne Ruse 2013 + * + * This software is provided 'as-is', without any express or implied + * warranty. In no event will the authors be held liable for any damages + * arising from the use of this software. + * + * Permission is granted to anyone to use this software for any purpose, + * including commercial applications, and to alter it and redistribute it + * freely, subject to the following restrictions: + * + * 1. The origin of this software must not be misrepresented; you must not + * claim that you wrote the original software. If you use this software + * in a product, an acknowledgment in the product documentation would be + * appreciated but is not required. + * + * 2. Altered source versions must be plainly marked as such, and must not be + * misrepresented as being the original software. + * + * 3. This notice may not be removed or altered from any source + * distribution. +*/ +#ifndef TILE_HPP_ +#define TILE_HPP_ + +//explicitly a POD +struct Tile { + int x, y, depth; + int value; + + Tile() = default; + Tile(int i, int j, int k, int l) : x(i), y(j), depth(k), value(l) { + // + } + + friend bool operator<(Tile const& lhs, Tile const& rhs); + friend bool operator>(Tile const& lhs, Tile const& rhs); + friend bool operator==(Tile const& lhs, Tile const& rhs); +}; + +#endif