0
0
mirror of https://github.com/Nimac0/SDL_Minigame synced 2026-01-12 13:43:41 +00:00

Merge pull request #82 from VEGO-Engine/#81-zindex

Added z-Index based render order
This commit is contained in:
Freezarite 2024-10-16 13:59:55 +02:00 committed by GitHub
commit a5c3ec3683
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
18 changed files with 130 additions and 49 deletions

View File

@ -9,7 +9,6 @@ public:
virtual void init() {}
virtual void update() {}
virtual void draw() {}
virtual ~Component() = default;
};

View File

@ -42,7 +42,6 @@ public:
manager(mManager) { };
void update() const;
void draw() const;
bool isActive() const { return this->active; }
void destroy() {

View File

@ -9,6 +9,7 @@
#include "Manager.h"
#include "Vector2D.h"
#include "Entity.h"
#include "RenderManager.h"
typedef std::function<void()> gamefunction;
@ -42,8 +43,8 @@ public:
/* static */ TextureManager* textureManager;
/* static */ SoundManager* soundManager;
// moved globals
Manager manager;
RenderManager renderManager;
Map* map; // game specific, might not be needed for all types of games
std::vector<Entity*>& tiles;

View File

@ -16,7 +16,6 @@ public:
Manager(GameInternal* game) : game(game) {};
void update();
void draw();
void refresh();
void addToGroup(Entity* mEntity, Group mGroup);

29
include/RenderManager.h Normal file
View File

@ -0,0 +1,29 @@
#pragma once
#include <vector>
#include "RenderObject.h"
class RenderManager {
public:
RenderManager() {};
/*
* Remove an object from the list of objects to be rendered
* \param renderObject The object to be removed
* \sa RenderObject
*/
void remove(RenderObject* obj);
/*
* Add an object to be rendered
* \param renderObject The object to be rendered
* \sa RenderObject
*/
void add(RenderObject* obj);
void renderAll(); //!< Render all objects. If the list has been modified, sorts it based on z-index first
private:
std::vector<RenderObject*> renderObjects;
bool isSorted;
};

27
include/RenderObject.h Normal file
View File

@ -0,0 +1,27 @@
#pragma once
class RenderManager;
class RenderObject
{
public:
virtual void draw() = 0;
RenderObject(int zIndex, RenderManager& renderManager);
~RenderObject();
int getZIndex() { return this->zIndex; };
//! Comparitor to compare two ptr based on z-index
struct ZIndexComparator {
bool operator()(RenderObject const *lhs, RenderObject const *rhs ) const {
return lhs->zIndex < rhs->zIndex;
}
};
private:
int zIndex = 0;
protected:
RenderManager& renderManager;
};

View File

@ -8,10 +8,11 @@
#include "AnimationHandler.h"
#include "Component.h"
#include "Direction.h"
#include "RenderObject.h"
class TransformComponent;
class SpriteComponent : public Component
class SpriteComponent : public Component, public RenderObject
{
public:
int animationIndex = 0;
@ -31,13 +32,13 @@ private:
bool flipped = false;
public:
SpriteComponent() = default;
SpriteComponent(const char* path);
SpriteComponent(const char* path, int zIndex);
SpriteComponent(
const char* path,
bool isAnimated,
std::map<std::string, std::unique_ptr<Animation>>* animationList,
std::string defaultAnimation);
std::string defaultAnimation,
int zIndex);
~SpriteComponent();
void setTexture(const char* path);

9
include/VEGO.h Normal file
View File

@ -0,0 +1,9 @@
#include "GameInternal.h"
namespace vego {
extern GameInternal* game;
}
inline GameInternal& VEGO_Game() {
return *vego::game;
};

View File

@ -50,7 +50,7 @@ void AssetManager::createProjectile(Vector2D pos, Vector2D velocity, int scale,
auto& projectile(man->addEntity());
projectile.addComponent<TransformComponent>(pos.x, pos.y, 32, 32, scale); //32x32 is standard size for objects
projectile.addComponent<SpriteComponent>(texturePath);
projectile.addComponent<SpriteComponent>(texturePath, 4);
projectile.addComponent<ProjectileComponent>(range, speed, velocity, owner);
projectile.addComponent<ColliderComponent>("projectile", 0.6f);
projectile.addGroup((size_t)Entity::GroupLabel::PROJECTILE);
@ -62,7 +62,7 @@ void AssetManager::createPowerup(Vector2D pos, std::function<void (Entity*)> pic
powerups.addComponent<TransformComponent>(pos.x, pos.y, 32, 32, 1); //32x32 is standard size for objects
try {
powerups.addComponent<SpriteComponent>(texturePath.c_str());
powerups.addComponent<SpriteComponent>(texturePath.c_str(), 3);
}
catch (std::runtime_error e) {
std::cout << e.what() << std::endl;

View File

@ -9,11 +9,6 @@ void Entity::update() const
for (auto const& c : components) c->update();
}
void Entity::draw() const
{
for (auto const& c : components) c->draw();
}
bool Entity::hasGroup(Group mGroup)
{
return groupBitSet[mGroup];

View File

@ -4,6 +4,7 @@
#include "CollisionHandler.h"
#include "AssetManager.h"
#include "RenderManager.h"
#include "SoundManager.h"
#include "TileComponent.h"
#include "Direction.h"
@ -18,6 +19,7 @@
GameInternal::GameInternal() :
manager(this),
renderManager(),
tiles(manager.getGroup((size_t)Entity::GroupLabel::MAPTILES)),
players(manager.getGroup((size_t)Entity::GroupLabel::PLAYERS)),
projectiles(manager.getGroup((size_t)Entity::GroupLabel::PROJECTILE)),
@ -169,21 +171,7 @@ void GameInternal::update()
void GameInternal::render()
{
SDL_RenderClear(renderer);
for (auto& t : tiles)
t->draw();
for (auto& p : powerups)
p->draw();
for (auto& p : players)
p->draw();
for (auto& p : projectiles)
p->draw();
for (auto& h : hearts)
h->draw();
this->renderManager.renderAll();
SDL_RenderPresent(renderer);
}

View File

@ -6,11 +6,6 @@
#include "Constants.h"
#include "Entity.h"
void Manager::draw()
{
for (auto& e : entities) e->draw();
}
void Manager::refresh()
{
for (auto i(0u); i < MAX_GROUPS; i++)

24
src/RenderManager.cpp Normal file
View File

@ -0,0 +1,24 @@
#include "RenderManager.h"
#include "RenderObject.h"
#include <algorithm>
void RenderManager::renderAll()
{
if (!this->isSorted) {
std::ranges::sort(this->renderObjects, RenderObject::ZIndexComparator());
}
for (RenderObject* obj : this->renderObjects) {
obj->draw();
}
}
void RenderManager::add(RenderObject* renderObject) {
this->renderObjects.emplace_back(renderObject);
this->isSorted = false;
}
void RenderManager::remove(RenderObject* renderObject)
{
this->renderObjects.erase(std::remove(this->renderObjects.begin(), this->renderObjects.end(), renderObject), this->renderObjects.end());
this->isSorted = false;
}

10
src/RenderObject.cpp Normal file
View File

@ -0,0 +1,10 @@
#include "RenderObject.h"
#include "RenderManager.h"
RenderObject::RenderObject(int zIndex, RenderManager& renderManager) : zIndex(zIndex), renderManager(renderManager) {
renderManager.add(this);
}
RenderObject::~RenderObject() {
this->renderManager.remove(this);
}

View File

@ -6,13 +6,16 @@
#include "AnimationHandler.h"
#include "Direction.h"
#include "ProjectileComponent.h"
#include "RenderObject.h"
#include "TextureManager.h"
#include "Entity.h"
#include "TransformComponent.h"
#include "GameInternal.h"
#include "Manager.h"
#include "VEGO.h"
SpriteComponent::SpriteComponent(const char* path)
SpriteComponent::SpriteComponent(const char* path, int zIndex) : RenderObject(zIndex, VEGO_Game().renderManager)
{
this->texturePath = path;
}
@ -21,7 +24,8 @@ SpriteComponent::SpriteComponent(
const char* path,
bool isAnimated,
std::map<std::string, std::unique_ptr<Animation>>* animationMap,
std::string defaultAnimation)
std::string defaultAnimation,
int zIndex) : RenderObject(zIndex, VEGO_Game().renderManager)
{
animated = isAnimated;
@ -36,7 +40,7 @@ SpriteComponent::~SpriteComponent() {}
void SpriteComponent::setTexture(const char* path)
{
this->texture = this->entity->getManager().getGame()->textureManager->loadTexture(path);
this->texture = VEGO_Game().textureManager->loadTexture(path);
}
void SpriteComponent::init()
@ -68,7 +72,7 @@ void SpriteComponent::update()
void SpriteComponent::draw()
{
this->entity->getManager().getGame()->textureManager->draw(this->entity->getManager().getGame()->renderer, this->texture, this->srcRect, this->destRect, this->animated && this->flipped);
this->entity->getManager().getGame()->textureManager->draw(VEGO_Game().renderer, this->texture, this->srcRect, this->destRect, this->animated && this->flipped);
}
void SpriteComponent::playAnimation(std::string type)

View File

@ -31,7 +31,7 @@ void TileComponent::init()
this->entity->addComponent<TransformComponent>(this->tileRect.x, this->tileRect.y, this->tileRect.w, this->tileRect.h, 1);
this->transform = &entity->getComponent<TransformComponent>();
this->entity->addComponent<SpriteComponent>(this->path);
this->entity->addComponent<SpriteComponent>(this->path, 0);
this->sprite = &entity->getComponent<SpriteComponent>();
}

View File

@ -72,7 +72,7 @@ void TransformComponent::modifySpeed(int8_t modifier)
void TransformComponent::setPositionAfterCollision(Vector2D& positionChange)
{
std::initializer_list colliders = { Entity::GroupLabel::MAPTILES, Entity::GroupLabel::COLLIDERS };
std::initializer_list<Entity::GroupLabel> colliders = { Entity::GroupLabel::MAPTILES, Entity::GroupLabel::COLLIDERS };
IntersectionBitSet intersections =
(CollisionHandler::getIntersectionWithBounds(entity, Vector2D(positionChange.x, 0)) |
(this->entity->getManager()

View File

@ -1,11 +1,12 @@
#include <iostream>
#include <ctime>
#include "VEGO.h"
#include "Entity.h"
#include "GameInternal.h"
#include "Constants.h"
GameInternal* game = nullptr;
GameInternal* vego::game = nullptr;
int main(int argc, char* argv[])
{
@ -17,15 +18,15 @@ int main(int argc, char* argv[])
Uint32 frameStart;
int frameTime;
game = new GameInternal();
vego::game = new GameInternal();
game->init("No_Name_Chicken_Game", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, SCREEN_SIZE_WIDTH, SCREEN_SIZE_HEIGHT, false);
while (game->isRunning()) {
vego::game->init("No_Name_Chicken_Game", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, SCREEN_SIZE_WIDTH, SCREEN_SIZE_HEIGHT, false);
while (vego::game->isRunning()) {
frameStart = SDL_GetTicks();
game->handleEvents();
game->update();
game->render();
vego::game->handleEvents();
vego::game->update();
vego::game->render();
frameTime = SDL_GetTicks() - frameStart;
@ -34,7 +35,7 @@ int main(int argc, char* argv[])
}
}
game->clean();
vego::game->clean();
return 0;
}