diff --git a/assets/tilemap.png b/assets/tilemap.png new file mode 100644 index 0000000000000000000000000000000000000000..48ec4457cb7f48a2078e595d0f56a72cc4239534 Binary files /dev/null and b/assets/tilemap.png differ diff --git a/source/engine/graphics/front/module/TileArray_Module.cpp b/source/engine/graphics/front/module/TileArray_Module.cpp index b88a30dc6e86bc7c7c8574e9b59e4f3c54eb7ca4..cdc258fba5b57477d0256c5bd4f8e091b21095ff 100644 --- a/source/engine/graphics/front/module/TileArray_Module.cpp +++ b/source/engine/graphics/front/module/TileArray_Module.cpp @@ -34,10 +34,10 @@ namespace megu { size_t count = 0; - for(size_t y = 0; y < vertexArray.height(); ++y) { - for(size_t x = 0; x < vertexArray.width(); ++x) { + for(size_t x = 0; x < vertexArray.width(); ++x) { + for(size_t y = 0; y < vertexArray.height(); ++y) { uOffsets.push_back(glm::translate(glm::mat4(1.f), {x, y, 0.f})); - uUvs.push_back(vertexArray.uvs()[y][x]); + uUvs.push_back(vertexArray.uvs()[x][y]); if(count > 128) { this->_program.setUniform("uOffsets", uOffsets); diff --git a/source/engine/graphics/front/object/Renderable.hpp b/source/engine/graphics/front/object/Renderable.hpp index 4787c74117aa4c4f1f96ddc2d5f1b6cb9008d965..e31acdfc5fb3a7c54093ed70ebda3de1d27a7d92 100644 --- a/source/engine/graphics/front/object/Renderable.hpp +++ b/source/engine/graphics/front/object/Renderable.hpp @@ -57,7 +57,7 @@ namespace megu { return typeid(T); } - T _objects; + T & _objects; Module<T> * _module; }; diff --git a/source/engine/graphics/front/object/Sprite.cpp b/source/engine/graphics/front/object/Sprite.cpp index 22bcf5fc028122a04456b3e04eb7e18a2d51b2ba..d9dd26c1084e14d70e7a6af5514b3233298a624e 100644 --- a/source/engine/graphics/front/object/Sprite.cpp +++ b/source/engine/graphics/front/object/Sprite.cpp @@ -1,9 +1,14 @@ #include "Sprite.hpp" namespace megu { - Sprite::Sprite(const std::filesystem::path & path) + Sprite::Sprite(const std::filesystem::path & path, bool flip) : _frame(0, 0, 0, 0) { - this->load(path, true); + this->load(path, flip); + } + + Sprite::Sprite(const std::filesystem::path & path, const Frame & frame, bool flip) + : _frame(frame) { + this->load(path, flip); } void Sprite::load(const std::filesystem::path & path, bool flip) { diff --git a/source/engine/graphics/front/object/Sprite.hpp b/source/engine/graphics/front/object/Sprite.hpp index 5601f375fa46e8e0a10db7f23fa9c294fef3f719..43b9a8b88e40f24e82e0e39e38d9554ef3049932 100644 --- a/source/engine/graphics/front/object/Sprite.hpp +++ b/source/engine/graphics/front/object/Sprite.hpp @@ -13,7 +13,8 @@ namespace megu { public: using Frame = glm::vec4; - Sprite(const std::filesystem::path &); + Sprite(const std::filesystem::path &, bool = true); + Sprite(const std::filesystem::path &, const Frame &, bool = true); inline void setFrame(const Frame & frame) {this->_frame = frame;} @@ -21,7 +22,15 @@ namespace megu { inline void setOrigine(const Vec2 & pos) {this->_transformation.setOrigine(pos.x, pos.y);} inline void setSize(const Vec2 & size) {this->_transformation.setScaling(size.x, size.y);} inline void setRotation(float a) {this->_transformation.setRotation(a, Transformable::Axis::Z);} - inline void setLayer(float l) {this->_transformation.setZ(l);} + + inline const Vec3 & position() const {return this->_transformation.position();} + inline const Vec3 & origine() const {return this->_transformation.origine();} + inline const Vec3 & rotation() const {return this->_transformation.rotation();} + inline const Vec2 & size() const {return Vec2(this->_transformation.scaling().x, this->_transformation.scaling().y);} + + inline float x() const {return this->_transformation.x();} + inline float y() const {return this->_transformation.y();} + inline float z() const {return this->_transformation.z();} inline void move(const Vec2 & pos) {this->_transformation.move({pos.x, pos.y, 0.f});} inline void scale(const Vec2 & size) {this->_transformation.scale({size.x, size.y, 0.f});} diff --git a/source/engine/graphics/front/object/TileArray.cpp b/source/engine/graphics/front/object/TileArray.cpp index bf10b68084dc9acf00cce43b77f8266d6b215d84..9e1d4310a176bfb62bee19378e003a42fc6ce60a 100644 --- a/source/engine/graphics/front/object/TileArray.cpp +++ b/source/engine/graphics/front/object/TileArray.cpp @@ -11,17 +11,12 @@ namespace megu { float twidth = static_cast<float>(this->_texture.width()); float theight = static_cast<float>(this->_texture.height()); - std::cout << twidth << "/" << theight << std::endl; - - for(size_t y = 0; y < height; ++y) { + for(size_t x = 0; x < width; ++x) { std::vector<glm::vec4> rows; - for(size_t x = 0; x < width; ++x) { + for(size_t y = 0; y < height; ++y) { rows.push_back({0.f, 0.f, twidth, theight}); } this->_uvs.push_back(rows); } - - std::cout << this->_uvs.size() << std::endl; - this->_transformation.scale({size, size, 1.f}); } } \ No newline at end of file diff --git a/source/engine/graphics/front/object/TileArray.hpp b/source/engine/graphics/front/object/TileArray.hpp index f88cb682b3b5055479cd4be3f5251a35f2fdbdd4..94e66b7858bca37a1e04ee36db955f7e63c090d8 100644 --- a/source/engine/graphics/front/object/TileArray.hpp +++ b/source/engine/graphics/front/object/TileArray.hpp @@ -29,10 +29,13 @@ namespace megu { inline size_t height() const {return this->_height;} inline float size() const {return this->_size;} + inline void setUv(size_t x, size_t y, const glm::vec4 & uv) {this->_uvs[y][x] = uv;} + inline const Transformable & transformation() const {return this->_transformation;} inline const Texture & texture() const {return this->_texture;} inline const std::vector<std::vector<glm::vec4>> & uvs() const {return this->_uvs;} + std::vector<glm::vec4> & operator[](size_t index) {return this->_uvs[index];} private: Transformable _transformation; diff --git a/source/engine/utility/type.hpp b/source/engine/utility/type.hpp index c1b5340cdc62058750b05941a7db72cf79073a05..62e6bd50cf24a87f88235131e74b44d62b95b56c 100644 --- a/source/engine/utility/type.hpp +++ b/source/engine/utility/type.hpp @@ -5,7 +5,7 @@ namespace megu { using Vec2 = glm::vec2; - using Vec3 = glm::vec4; + using Vec3 = glm::vec3; using Vec4 = glm::vec4; using Color = glm::vec4; diff --git a/source/game/Game.cpp b/source/game/Game.cpp index 1920d7af3e96a4f1502d5f694bda8054c0e33db3..b9c38e1c3c5e66585bcc6f710341838a0fa1189a 100644 --- a/source/game/Game.cpp +++ b/source/game/Game.cpp @@ -26,9 +26,9 @@ namespace megu::game { megu::game::Object object(path); kernel.add(&object); - megu::game::Object object2(path); + /*megu::game::Object object2(path); object2.tmp_setPos(20, 0); - kernel.add(&object2); + kernel.add(&object2);*/ /* ------ */ while(window.isOpen()) { diff --git a/source/game/object/Test.cpp b/source/game/object/Test.cpp index 0dbade9f6fcb3948a43bfccc476b630274027f42..bcdf5552f1f0b80412255c096cb005d84eb0b431 100644 --- a/source/game/object/Test.cpp +++ b/source/game/object/Test.cpp @@ -2,5 +2,13 @@ namespace megu::game { Object::Object(std::filesystem::path & path) - : _physic(0, 0, 64, 64), _graphic(path) {} + : _physic(0, 0, 64, 64), _graphic(path), _map("assets/tilemap.png", 2, 2, 16.f, 16) { + this->_graphic.setFrame({0.f, 0.f, 51.f, 98.f}); + this->_graphic.setSize({51.f, 98.f}); + + this->_map.setValue(0, 0, 1); + this->_map.setValue(1, 0, 1); + this->_map.setValue(0, 1, 2); + this->_map.setValue(1, 1, 1); + } } \ No newline at end of file diff --git a/source/game/object/Test.hpp b/source/game/object/Test.hpp index 94fb9a655212d8fb3814073fa03c596e63737a24..cd3854e79afa448ea19b23e72057695d22a4d2c9 100644 --- a/source/game/object/Test.hpp +++ b/source/game/object/Test.hpp @@ -3,21 +3,19 @@ #include <kernel/back/props/Props.hpp> #include <kernel/front/component/physic/Fixed.hpp> #include <kernel/front/component/graphic/Sprite.hpp> +#include <kernel/front/component/graphic/TileMap.hpp> namespace megu::game { class Object : public kernel::Props { public: Object(std::filesystem::path &); - inline kernel::Physical<kernel::PhysicEngine> & getPhysicComponent() override {return this->_physic;} - inline kernel::Graphical<kernel::GraphicEngine> & getGraphicComponent() override {return this->_graphic;} - - inline void tmp_setPos(float x, float y) { - this->_graphic.tmp_setPos(x, y); - } + inline kernel::Physical<kernel::PhysicEngine> * getPhysicComponent() override {return &this->_physic;} + inline kernel::Graphical<kernel::GraphicEngine> * getGraphicComponent() override {return &this->_map;} private: kernel::Fixed _physic; kernel::Sprite _graphic; + kernel::Tilemap _map; }; } \ No newline at end of file diff --git a/source/kernel/back/engine/GraphicEngine.cpp b/source/kernel/back/engine/GraphicEngine.cpp index 6a811a4642d14e9e102084dc5a8ecb2eceea34dc..314f19b55e312e7860d3d1a8c2e22281072c534a 100644 --- a/source/kernel/back/engine/GraphicEngine.cpp +++ b/source/kernel/back/engine/GraphicEngine.cpp @@ -4,10 +4,12 @@ namespace megu::kernel { GraphicEngine::GraphicEngine(Window & window) - : _engine(window), _renderer(360, 360) {} + : _engine(window), _renderer(360, 360), _tmp_ta("assets/textures/Tile_Test_3.png", 1, 1, 32.f) {} void GraphicEngine::boot(Kernel &) { this->_engine.push(0, this->_renderer); + + //this->_engine.push(0, 0, this->_tmp_ta, &this->_tmp_mod); } void GraphicEngine::stop(Kernel &) { diff --git a/source/kernel/back/engine/GraphicEngine.hpp b/source/kernel/back/engine/GraphicEngine.hpp index f26ef134dfbabd6a1450e421c6c7b83253ab4de2..885d7a5705834f9a3d0bea2f1011e34612b9cc0d 100644 --- a/source/kernel/back/engine/GraphicEngine.hpp +++ b/source/kernel/back/engine/GraphicEngine.hpp @@ -7,6 +7,9 @@ #include <engine/graphics/front/engine/Engine.hpp> #include <engine/graphics/front/engine/Renderer.hpp> +#include <engine/graphics/front/module/TileArray_Module.hpp> +#include <engine/graphics/front/object/TileArray.hpp> + #include <kernel/back/props/Graphical.hpp> namespace megu::kernel { @@ -28,5 +31,8 @@ namespace megu::kernel { private: megu::GraphicEngine _engine; megu::Renderer _renderer; + + megu::TileArray _tmp_ta; + megu::TileArray_Module _tmp_mod; }; } \ No newline at end of file diff --git a/source/kernel/back/linker/GraphicLinker.hpp b/source/kernel/back/linker/GraphicLinker.hpp index 86b091ab66f611015e7797857522be024a435b64..12d87d04de78f318861350fe7aee28e3f57bd5af 100644 --- a/source/kernel/back/linker/GraphicLinker.hpp +++ b/source/kernel/back/linker/GraphicLinker.hpp @@ -1,21 +1,10 @@ #pragma once #include "Linker.hpp" +#include "PriorityPair.hpp" #include <kernel/back/engine/GraphicEngine.hpp> namespace megu::kernel { - struct Priority_Pair { - Priority layer; - Priority object; - - bool operator<(const Priority_Pair & pp) const { - if(this->layer == pp.layer) { - return this->object < pp.object; - } - return this->layer < pp.layer; - } - }; - template <class T> class GraphicLinker : public Linker<GraphicEngine> { public: diff --git a/source/kernel/back/linker/GraphicLinker.tpp b/source/kernel/back/linker/GraphicLinker.tpp index 29fe81f69c6382dc874e9aaaa3c0fa37fd4349f2..2fccee83be8fe35cbd9154931ffc995a0cc38e52 100644 --- a/source/kernel/back/linker/GraphicLinker.tpp +++ b/source/kernel/back/linker/GraphicLinker.tpp @@ -16,7 +16,7 @@ namespace megu::kernel { template <class T> void GraphicLinker<T>::link(GraphicEngine & engine) { for(const auto & layers : this->_waiting) { - engine.get().push(layers.layer, layers.object , this->_objects[layers], this->_module.get()); + engine.get().push(layers.layer, layers.object, this->_objects[layers], this->_module.get()); } this->_waiting.clear(); diff --git a/source/kernel/back/linker/PriorityPair.hpp b/source/kernel/back/linker/PriorityPair.hpp new file mode 100644 index 0000000000000000000000000000000000000000..091ad26ea15bbe0bdd864aaf6bc265fb6f186f53 --- /dev/null +++ b/source/kernel/back/linker/PriorityPair.hpp @@ -0,0 +1,17 @@ +#pragma once + +#include <engine/utility/Priority.hpp> + +namespace megu::kernel { + struct Priority_Pair { + Priority layer; + Priority object; + + bool operator<(const Priority_Pair & pp) const { + if(this->layer == pp.layer) { + return this->object < pp.object; + } + return this->layer < pp.layer; + } + }; +} \ No newline at end of file diff --git a/source/kernel/back/linker/UniqueLinker.hpp b/source/kernel/back/linker/UniqueLinker.hpp new file mode 100644 index 0000000000000000000000000000000000000000..9453bab77063af9d17b0f882d7fdb23e0b336649 --- /dev/null +++ b/source/kernel/back/linker/UniqueLinker.hpp @@ -0,0 +1,27 @@ +#pragma once + +#include "Linker.hpp" +#include "PriorityPair.hpp" +#include <kernel/back/engine/GraphicEngine.hpp> + +namespace megu::kernel { + template <class T> + class UniqueGraphicLinker : public Linker<GraphicEngine> { + public: + UniqueGraphicLinker(); + + void link(T &, Priority, Priority); + void link(GraphicEngine &) override; + void setModule(Module<T> *); + + inline bool haveModule() const {return this->_module.get() != nullptr;} + inline ref_set<T> & objects() {return this->_object;} + + private: + std::unique_ptr<Module<T>> _module; + std::map<Priority_Pair, ref_set<T>> _objects; + std::set<Priority_Pair> _waiting; + }; +} + +#include "UniqueLinker.tpp" \ No newline at end of file diff --git a/source/kernel/back/linker/UniqueLinker.tpp b/source/kernel/back/linker/UniqueLinker.tpp new file mode 100644 index 0000000000000000000000000000000000000000..9265d6c5541bf9649a1987a16211ed67fc55cea3 --- /dev/null +++ b/source/kernel/back/linker/UniqueLinker.tpp @@ -0,0 +1,31 @@ +#include "UniqueLinker.hpp" + +namespace megu::kernel { + template <class T> + UniqueGraphicLinker<T>::UniqueGraphicLinker() + : _module(nullptr) {} + + template <class T> + void UniqueGraphicLinker<T>::link(T & object, Priority l, Priority o) { + auto layers = Priority_Pair{l, o}; + + this->_objects[layers].insert(object); + this->_waiting.insert(layers); + } + + template <class T> + void UniqueGraphicLinker<T>::link(GraphicEngine & engine) { + for(const auto & layers : this->_waiting) { + for(auto & object : this->_objects[layers]) { + engine.get().push<T>(layers.layer, layers.object, object, this->_module.get()); + } + } + + this->_waiting.clear(); + } + + template <class T> + void UniqueGraphicLinker<T>::setModule(Module<T> * mod) { + this->_module = std::unique_ptr<Module<T>>(mod); + } +} \ No newline at end of file diff --git a/source/kernel/back/props/Props.hpp b/source/kernel/back/props/Props.hpp index a83cccac18ef2884b6150416fdc62c42e3605c3f..80dbe5838d0f074d36ca63ab5a4389ccbef855ee 100644 --- a/source/kernel/back/props/Props.hpp +++ b/source/kernel/back/props/Props.hpp @@ -10,8 +10,8 @@ namespace megu::kernel { class Props : public Identifiable { public: - virtual Physical<PhysicEngine> & getPhysicComponent() = 0; - virtual Graphical<GraphicEngine> & getGraphicComponent() = 0; + virtual Physical<PhysicEngine> * getPhysicComponent() = 0; + virtual Graphical<GraphicEngine> * getGraphicComponent() = 0; }; } \ No newline at end of file diff --git a/source/kernel/front/Kernel.cpp b/source/kernel/front/Kernel.cpp index c8ce770837a67edeeb6afa842a580c888161ef84..e5ab814bdf790cd1e0af09d2d9f59256fab45a48 100644 --- a/source/kernel/front/Kernel.cpp +++ b/source/kernel/front/Kernel.cpp @@ -26,8 +26,14 @@ namespace megu::kernel { void Kernel::add(Props * props) { this->_props[props->id()] = props; - - this->_pEngine.add(*this, props->getPhysicComponent()); - this->_gEngine.add(*this, props->getGraphicComponent()); + auto * pComponent = props->getPhysicComponent(); + if(pComponent != nullptr) { + this->_pEngine.add(*this, *pComponent); + } + + auto * gComponent = props->getGraphicComponent(); + if(gComponent != nullptr) { + this->_gEngine.add(*this, *gComponent); + } } } \ No newline at end of file diff --git a/source/kernel/front/component/graphic/Sprite.cpp b/source/kernel/front/component/graphic/Sprite.cpp index a7deac473590ed6e0c8c68825ba6a9bf820ffaa2..c5f506950b5372680b739e35504f0d5c8eb3678c 100644 --- a/source/kernel/front/component/graphic/Sprite.cpp +++ b/source/kernel/front/component/graphic/Sprite.cpp @@ -1,26 +1,82 @@ #include "Sprite.hpp" +//this->_sprite.setFrame({0.f, 0.f, 51.f, 98.f}); +//this->_sprite.setSize({50, 100}); + namespace megu::kernel { GraphicLinker<megu::Sprite> Sprite::_Linker = GraphicLinker<megu::Sprite>(); - Sprite::Sprite(std::filesystem::path & path) - : _sprite(path), _animation(""), _index(0) { - this->_sprite.setFrame({0.f, 0.f, 51.f, 98.f}); - this->_sprite.setSize({50, 100}); + Sprite::Sprite(const std::filesystem::path & path) + : Sprite(path, {0, 0, 0, 0}) {} + Sprite::Sprite(const std::filesystem::path & path, const Frame & frame) + : megu::Sprite(path, frame), _animation(""), _index(0) { if(!Sprite::_Linker.haveModule()) { Sprite::_Linker.setModule(new Sprite_Module{}); } } - void Sprite::update(double) { - if(!this->_animation.empty()) { - this->_sprite.setFrame(this->_frames[this->_animation][this->_index]); + const Frame_List & Sprite::getAnimations(const std::string & name) const { + if(this->_frames.contains(name)) { + return this->_frames.at(name); + } + throw std::runtime_error("Cannot get inexisting animation"); + } + + const Frame & Sprite::getFrame(const std::string & name, size_t index) const { + auto & frames = this->getAnimations(name); + if(frames.size() > index) { + return frames.at(index); + } + throw std::runtime_error("Cannot get inexisting frame"); + } + + void Sprite::setAnimation(const std::string & name) { + if(this->_frames.contains(name)) { + this->_animation = name; + this->_previous = 0.0; } + throw std::runtime_error("Cannot set inexisting animation"); + } + + void Sprite::push(const std::string & name, const Frame_List & frames) { + this->_frames[name] = frames; + } + + void Sprite::push(const std::string & name, const Frame & frame) { + this->_frames[name].push_back(frame); + } + + void Sprite::remove(const std::string & name) { + if(this->_frames.contains(name)) { + this->_frames.erase(name); + } + } + + void Sprite::remove(const std::string & name, size_t index) { + if(this->_frames.contains(name) && this->_frames[name].size() > index) { + this->_frames[name].erase(this->_frames[name].begin() + index); + } + } + + void Sprite::update(double time) { + /*if(!this->_animation.empty()) { + if(this->_previous == 0.0) { + this->setFrame(this->_frames[this->_animation][this->_index]); + this->_previous = time; + } + else { + double current = this->_previous - time; + if(current > this->_duration) { + this->_index = (this->_index + 1) % this->_frames[this->_animation].size(); + this->setFrame(this->_frames[this->_animation][this->_index]); + } + } + }*/ } void Sprite::apply(Kernel & kernel, GraphicEngine & engine) { - Sprite::_Linker.link(this->_sprite, this->getLayerPriority(), this->getObjectPriority()); + Sprite::_Linker.link(*this, this->getLayerPriority(), this->getObjectPriority()); Sprite::_Linker.link(engine); } } \ No newline at end of file diff --git a/source/kernel/front/component/graphic/Sprite.hpp b/source/kernel/front/component/graphic/Sprite.hpp index 1f1ad3dc168afe5eac70e5eb15a11eb33f3f6607..fbc9f1624166f1bc5067b8e55fb7631f956c8731 100644 --- a/source/kernel/front/component/graphic/Sprite.hpp +++ b/source/kernel/front/component/graphic/Sprite.hpp @@ -14,24 +14,37 @@ namespace megu::kernel { using Frame_List = std::vector<megu::Sprite::Frame>; + using Frame = megu::Sprite::Frame; - class Sprite : public Graphical<GraphicEngine> { + class Sprite : public Graphical<GraphicEngine>, public megu::Sprite { public: - Sprite(std::filesystem::path &); + Sprite(const std::filesystem::path &); + Sprite(const std::filesystem::path &, const Frame &); + + inline size_t getCurrentFrameIndex() const {return this->_index;} + inline double getDuration() const {return this->_duration;} + + const Frame_List & getAnimations(const std::string &) const; + const Frame & getFrame(const std::string &, size_t) const; + + void setAnimation(const std::string &); + void push(const std::string &, const Frame_List & = {}); + void push(const std::string &, const Frame &); + + void remove(const std::string &); + void remove(const std::string &, size_t); void update(double) override; void apply(Kernel &, GraphicEngine &) override; - inline void tmp_setPos(float x, float y) { - this->_sprite.setPosition({x, y}); - } + static const GraphicLinker<megu::Sprite> & linker() {return Sprite::_Linker;} private: - megu::Sprite _sprite; - std::map<std::string, Frame_List> _frames; std::string _animation; size_t _index; + double _duration; + double _previous; static GraphicLinker<megu::Sprite> _Linker; }; diff --git a/source/kernel/front/component/graphic/TileMap.cpp b/source/kernel/front/component/graphic/TileMap.cpp new file mode 100644 index 0000000000000000000000000000000000000000..da61dc8f6f9bb9747a2cd813ed68c09cd056f7d5 --- /dev/null +++ b/source/kernel/front/component/graphic/TileMap.cpp @@ -0,0 +1,64 @@ +#include "TileMap.hpp" + +namespace megu::kernel { + UniqueGraphicLinker<TileArray> Tilemap::_Linker = UniqueGraphicLinker<TileArray>(); + + Tilemap::Tilemap(const std::filesystem::path & path, size_t width, size_t height, float size, size_t lenght) + : TileArray(path, width , height, size), _tileSize(lenght) { + if(lenght % width != 0 && lenght % height != 0) { + throw std::runtime_error("Tilemap dimension not matching tiles size."); + } + + size_t i = 0, j = 0; + for(size_t x = 0; x < this->texture().width(); x += this->_tileSize) { + j = 0; + for(size_t y = 0; y < this->texture().height(); y += this->_tileSize) { + this->_tilesPosition.push_back({j * this->_tileSize, i * this->_tileSize}); + ++j; + } + ++i; + } + + i = 0; + for(size_t x = 0; x < width * this->_tileSize; x += this->_tileSize) { + this->_tilesValue.push_back({}); + for(size_t y = 0; y < height * this->_tileSize; y += this->_tileSize) { + this->_tilesValue[i].push_back(0); + } + ++i; + } + + if(!Tilemap::_Linker.haveModule()) { + Tilemap::_Linker.setModule(new TileArray_Module{}); + } + + this->setSize({width * size, height * size}); + } + + void Tilemap::setValue(size_t x, size_t y, size_t value) { + TilePosition position = this->_tilesPosition[value]; + glm::vec4 uv = {position.x, + this->texture().height() - position.y - this->_tileSize, + this->_tileSize, + this->_tileSize}; + + this->setUv(x, this->width() - 1 - y, uv); + this->_tilesValue[x][y] = value; + } + + size_t Tilemap::getValue(size_t x, size_t y) { + if(this->_tilesValue.size() > x && this->_tilesValue[x].size() > y) { + return this->_tilesValue[x][y]; + } + throw std::runtime_error("Tilemap coords out of bound"); + } + + void Tilemap::update(double time) { + //... Peut-être des tiles animées si j'ai le temps 🙌 (spoiler non). + } + + void Tilemap::apply(Kernel & kernel, GraphicEngine & engine) { + Tilemap::_Linker.link(*this, this->getLayerPriority(), this->getObjectPriority()); + Tilemap::_Linker.link(engine); + } +} \ No newline at end of file diff --git a/source/kernel/front/component/graphic/TileMap.hpp b/source/kernel/front/component/graphic/TileMap.hpp new file mode 100644 index 0000000000000000000000000000000000000000..38349535010d59c03aade7b4993a3547f6d44365 --- /dev/null +++ b/source/kernel/front/component/graphic/TileMap.hpp @@ -0,0 +1,44 @@ +#pragma once + +#include <map> +#include <vector> + +#include <kernel/back/engine/GraphicEngine.hpp> +#include <kernel/back/props/Graphical.hpp> +#include <kernel/back/linker/UniqueLinker.hpp> + +#include <engine/graphics/front/object/TileArray.hpp> +#include <engine/graphics/front/module/TileArray_Module.hpp> + +namespace megu::kernel { + class Tilemap : public Graphical<GraphicEngine>, public TileArray { + public: + struct TilePosition { + size_t x = 0; + size_t y = 0; + + friend bool operator<(const TilePosition & p1, const TilePosition & p2) { + if(p1.x == p2.x) { + return p1.y < p2.y; + } + return p1.x < p1.y; + } + }; + + Tilemap(const std::filesystem::path &, size_t, size_t, float, size_t); + + void setValue(size_t, size_t, size_t); + size_t getValue(size_t, size_t); + + void update(double) override; + void apply(Kernel &, GraphicEngine &) override; + + private: + std::vector<TilePosition> _tilesPosition; + std::vector<std::vector<size_t>> _tilesValue; + TileArray_Module _module; + size_t _tileSize; + + static UniqueGraphicLinker<TileArray> _Linker; + }; +} \ No newline at end of file diff --git a/source/kernel/front/resolver/GraphicResolver.cpp b/source/kernel/front/resolver/GraphicResolver.cpp index 5c7c57426e125396ceac36c9072504277642a2d7..a436473b2ebb63e9038db28a2b339de239f8b3f4 100644 --- a/source/kernel/front/resolver/GraphicResolver.cpp +++ b/source/kernel/front/resolver/GraphicResolver.cpp @@ -3,7 +3,10 @@ namespace megu::kernel { void GraphicResolver::resolve(double time, GraphicEngine &, const Identifiable_Map<Props> & props) { for(auto & [id, object] : props) { - object->getGraphicComponent().update(time); + auto * component = object->getGraphicComponent(); + if(component != nullptr) { + component->update(time); + } } } } \ No newline at end of file diff --git a/source/kernel/front/resolver/PhysicResolver.cpp b/source/kernel/front/resolver/PhysicResolver.cpp index 2c905275b5265f932d57868fb2015e218a0551dc..81ed40e42b57c13571647a6d60389821c54ac8e7 100644 --- a/source/kernel/front/resolver/PhysicResolver.cpp +++ b/source/kernel/front/resolver/PhysicResolver.cpp @@ -11,7 +11,14 @@ namespace megu::kernel { if(props.contains(source.id()) && props.contains(target.id())) { Props * props_source = props.at(source.id()); Props * props_target = props.at(target.id()); - props_source->getPhysicComponent().on_collide(time, target, props_target->getPhysicComponent()); + + auto * sComponent = props_source->getPhysicComponent(); + auto * tComponent = props_target->getPhysicComponent(); + + if(sComponent != nullptr && tComponent != nullptr) { + sComponent->on_collide(time, target, *tComponent); + } + } }