mirror of
https://github.com/Nimac0/SDL_Minigame
synced 2026-01-12 13:43:41 +00:00
Compare commits
8 Commits
361687f09f
...
e0c35aa690
| Author | SHA1 | Date | |
|---|---|---|---|
| e0c35aa690 | |||
| 1b795c3732 | |||
| eba3cdb6c8 | |||
|
|
1dc00408de | ||
|
|
e215fbd5b6 | ||
|
|
007538f760 | ||
|
|
9bb9d0fbcc | ||
| 044d957106 |
@ -12,10 +12,10 @@ set(ENGINE_BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR})
|
|||||||
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
|
||||||
set(BUILD_SHARED_LIBS FALSE)
|
set(BUILD_SHARED_LIBS FALSE)
|
||||||
|
|
||||||
set(SDL2MIXER_VENDORED ON)
|
set(SDLMIXER_VENDORED ON)
|
||||||
set(SDL2TTF_VENDORED ON)
|
set(SDLTTF_VENDORED ON)
|
||||||
|
|
||||||
set(SDL2_SOURCE_DIR “${ENGINE_SOURCE_DIR}/extern/SDL”)
|
set(SDL_SOURCE_DIR “${ENGINE_SOURCE_DIR}/extern/SDL”)
|
||||||
|
|
||||||
set(TMXLITE_STATIC_LIB TRUE)
|
set(TMXLITE_STATIC_LIB TRUE)
|
||||||
|
|
||||||
|
|||||||
@ -6,6 +6,7 @@
|
|||||||
#include <functional>
|
#include <functional>
|
||||||
|
|
||||||
#include "Entity.h"
|
#include "Entity.h"
|
||||||
|
#include "SoundEffects.h"
|
||||||
|
|
||||||
class Vector2D;
|
class Vector2D;
|
||||||
class Manager;
|
class Manager;
|
||||||
@ -24,24 +25,13 @@ public:
|
|||||||
AssetManager(Manager* manager);
|
AssetManager(Manager* manager);
|
||||||
~AssetManager();
|
~AssetManager();
|
||||||
|
|
||||||
void createProjectile(Vector2D pos, Vector2D velocity, int scale, int range, float speed, Textures textureEnum, Entity* owner);
|
|
||||||
void createPowerup(Vector2D pos, std::function<void (Entity*)> pickupFunc, Textures texture);
|
void createPowerup(Vector2D pos, std::function<void (Entity*)> pickupFunc, Textures texture);
|
||||||
|
|
||||||
Vector2D calculateSpawnPosition();
|
Vector2D calculateSpawnPosition();
|
||||||
PowerupType calculateType();
|
PowerupType calculateType();
|
||||||
|
|
||||||
|
|
||||||
// sound management
|
|
||||||
void addSoundEffect(std::string id, const char* path);
|
|
||||||
|
|
||||||
void addMusic(std::string id, const char* path);
|
|
||||||
|
|
||||||
Mix_Chunk* getSound(std::string id);
|
|
||||||
Mix_Music* getMusic(std::string id);
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
Manager* man;
|
Manager* man;
|
||||||
std::map<std::string, Mix_Chunk*> soundEffects;
|
|
||||||
std::map<std::string, Mix_Music*> music;
|
|
||||||
};
|
};
|
||||||
|
|||||||
3
include/BackgroundMusic.h
Normal file
3
include/BackgroundMusic.h
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
enum class BackgroundMusic;
|
||||||
38
include/DataComponent.h
Normal file
38
include/DataComponent.h
Normal file
@ -0,0 +1,38 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <map>
|
||||||
|
#include <any>
|
||||||
|
#include <string>
|
||||||
|
#include <optional>
|
||||||
|
#include "Component.h"
|
||||||
|
|
||||||
|
class DataComponent : public Component
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
DataComponent() {};
|
||||||
|
~DataComponent() {};
|
||||||
|
/**
|
||||||
|
* @brief Set a key-value pair of any type in the data map
|
||||||
|
* @details e.g. setEntry("speed", 180); in this case the key is "speed" and the value is set to an integer of 180
|
||||||
|
* @param key The name to store the value under
|
||||||
|
* @param value The value to store of type T
|
||||||
|
*/
|
||||||
|
template <typename T>
|
||||||
|
void setEntry(const std::string& key, const T& value) { dataMap.insert_or_assign(key, value); }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Get a value of type T from the data map
|
||||||
|
* @details e.g. getEntry<int>("speed"); in this case the key is "speed" and the value is returned as an integer
|
||||||
|
* @param key The name to retrieve the value from
|
||||||
|
* @return An optional of type T containing the value if it exists and matches in typeid, otherwise std::nullopt
|
||||||
|
*/
|
||||||
|
template<typename T>
|
||||||
|
std::optional<T> getEntry(std::string key) const {
|
||||||
|
if (!this->dataMap.contains(key)) return std::nullopt;
|
||||||
|
const std::any& value = this->dataMap.at(key);
|
||||||
|
if (value.type() != typeid(T)) { return std::nullopt; }
|
||||||
|
return std::any_cast<T>(value);
|
||||||
|
}
|
||||||
|
private:
|
||||||
|
std::map<std::string, std::any> dataMap;
|
||||||
|
};
|
||||||
@ -102,7 +102,7 @@ public:
|
|||||||
return *c;
|
return *c;
|
||||||
};
|
};
|
||||||
|
|
||||||
template <typename T> T& getComponent() const //! \returns Component of type T
|
template <typename T> T& getComponent() const //!< \todo: rewrite to use optionals
|
||||||
{
|
{
|
||||||
auto ptr(componentArray[getComponentTypeID<T>()]);
|
auto ptr(componentArray[getComponentTypeID<T>()]);
|
||||||
return *static_cast<T*>(ptr);
|
return *static_cast<T*>(ptr);
|
||||||
|
|||||||
@ -6,6 +6,10 @@
|
|||||||
class PowerupComponent : public Component
|
class PowerupComponent : public Component
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
/**
|
||||||
|
* @brief Construct a new Powerup Component object
|
||||||
|
* @param func The function to be called when the powerup is picked up
|
||||||
|
*/
|
||||||
PowerupComponent(std::function<void (Entity*)> func);
|
PowerupComponent(std::function<void (Entity*)> func);
|
||||||
~PowerupComponent() {};
|
~PowerupComponent() {};
|
||||||
|
|
||||||
|
|||||||
@ -3,6 +3,7 @@
|
|||||||
#include "Component.h"
|
#include "Component.h"
|
||||||
#include "Vector2D.h"
|
#include "Vector2D.h"
|
||||||
#include "Constants.h"
|
#include "Constants.h"
|
||||||
|
#include "SoundEffects.h"
|
||||||
|
|
||||||
class TransformComponent;
|
class TransformComponent;
|
||||||
|
|
||||||
@ -11,8 +12,8 @@ class ProjectileComponent : public Component
|
|||||||
//can maybe be split in separate .cpp file
|
//can maybe be split in separate .cpp file
|
||||||
|
|
||||||
public:
|
public:
|
||||||
ProjectileComponent(int range, int speed, Vector2D direction, Entity* owner)
|
ProjectileComponent(int range, int speed, Vector2D direction, Entity* owner, SoundEffects soundEffect)
|
||||||
: range(range), speed(speed), direction(direction), owner(owner) {}
|
: range(range), speed(speed), direction(direction), owner(owner), soundEffect(soundEffect) {}
|
||||||
~ProjectileComponent() {}
|
~ProjectileComponent() {}
|
||||||
|
|
||||||
void init() override;
|
void init() override;
|
||||||
@ -28,4 +29,6 @@ private:
|
|||||||
Entity* owner = nullptr;
|
Entity* owner = nullptr;
|
||||||
|
|
||||||
Vector2D direction;
|
Vector2D direction;
|
||||||
|
|
||||||
|
SoundEffects soundEffect;
|
||||||
};
|
};
|
||||||
3
include/SoundEffects.h
Normal file
3
include/SoundEffects.h
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
enum class SoundEffects;
|
||||||
@ -6,6 +6,8 @@
|
|||||||
|
|
||||||
#include "ECS.h"
|
#include "ECS.h"
|
||||||
#include "TextureManager.h"
|
#include "TextureManager.h"
|
||||||
|
#include "BackgroundMusic.h"
|
||||||
|
#include "SoundEffects.h"
|
||||||
|
|
||||||
class GameInternal;
|
class GameInternal;
|
||||||
|
|
||||||
@ -17,8 +19,17 @@ class GameInternal;
|
|||||||
*/
|
*/
|
||||||
class SoundManager
|
class SoundManager
|
||||||
{
|
{
|
||||||
|
|
||||||
public:
|
public:
|
||||||
SoundManager() {}
|
|
||||||
|
SoundManager() {
|
||||||
|
if (this_instance == nullptr) {
|
||||||
|
this_instance = this;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
throw std::runtime_error("SoundManager instance already exists!");
|
||||||
|
}
|
||||||
|
}
|
||||||
~SoundManager() {
|
~SoundManager() {
|
||||||
for (auto& it : this->sound_cache) {
|
for (auto& it : this->sound_cache) {
|
||||||
Mix_FreeChunk(it.second);
|
Mix_FreeChunk(it.second);
|
||||||
@ -32,35 +43,32 @@ class SoundManager
|
|||||||
SoundManager(SoundManager const&) = delete;
|
SoundManager(SoundManager const&) = delete;
|
||||||
void operator=(SoundManager const&) = delete;
|
void operator=(SoundManager const&) = delete;
|
||||||
|
|
||||||
std::map<const char*, Mix_Music*> music_cache;
|
/*
|
||||||
std::map<const char*, Mix_Chunk*> sound_cache;
|
|
||||||
|
|
||||||
/*!
|
|
||||||
* \brief Loads music from a file (mp3)
|
* \brief Loads music from a file (mp3)
|
||||||
* \returns a pointer to Mix_Music
|
* \returns a pointer to Mix_Music
|
||||||
* \sa AssetManager::AddMusic(std::string id, const char* path)
|
* \sa AssetManager::AddMusic(std::string id, const char* path)
|
||||||
*/
|
|
||||||
Mix_Music* loadMusic(const char* fileName);
|
Mix_Music* loadMusic(const char* fileName);
|
||||||
/*!
|
/*!
|
||||||
* \brief Loads sound effects from a file (wav)
|
* \brief Loads sound effects from a file (wav)
|
||||||
* \returns a pointer to Mix_Chunk
|
* \returns a pointer to Mix_Chunk
|
||||||
* \sa AssetManager::AddSound(std::string id, const char* path)
|
* \sa AssetManager::AddSound(std::string id, const char* path)
|
||||||
*/
|
|
||||||
Mix_Chunk* loadSound(const char* fileName);
|
|
||||||
|
|
||||||
|
Mix_Chunk* loadSound(const char* fileName);
|
||||||
|
*/
|
||||||
/*!
|
/*!
|
||||||
* \brief Handles playing of sound effects
|
* \brief Handles playing of sound effects
|
||||||
*
|
*
|
||||||
* Handles if sounds can overlap, how often they can loop, as well as the volume at which the specified sound effect should play
|
* Handles if sounds can overlap, how often they can loop, as well as the volume at which the specified sound effect should play
|
||||||
* and on which channel the soundeffect should play.
|
* and on which channel the soundeffect should play.
|
||||||
*/
|
*/
|
||||||
static void playSound(GameInternal* game, std::string sound, bool canOverlap, int loops, int volume, int channel);
|
static void playSound(SoundEffects sound, bool canOverlap, int loops, int volume, int channel);
|
||||||
/*!
|
/*!
|
||||||
* \brief Handles playing of music
|
* \brief Handles playing of music
|
||||||
*
|
*
|
||||||
* Handles how often track can loop, as well as the volume at which the specified track should play and if it fades in.
|
* Handles how often track can loop, as well as the volume at which the specified track should play and if it fades in.
|
||||||
*/
|
*/
|
||||||
static void playMusic(GameInternal* game, std::string sound, int loops, int volume, int ms);
|
static void playMusic(BackgroundMusic sound, int loops, int volume, int milliseconds);
|
||||||
|
|
||||||
static void setSoundVolume(int volume, int channel); //!< Volume handling for sound effects (either all or on a specific channel)
|
static void setSoundVolume(int volume, int channel); //!< Volume handling for sound effects (either all or on a specific channel)
|
||||||
static void setMusicVolume(int volume); //!< Volume handling for music track
|
static void setMusicVolume(int volume); //!< Volume handling for music track
|
||||||
@ -73,5 +81,29 @@ class SoundManager
|
|||||||
|
|
||||||
static void fadeOutMusic(int ms); //!< Handles fading out a music track
|
static void fadeOutMusic(int ms); //!< Handles fading out a music track
|
||||||
|
|
||||||
|
/*!
|
||||||
|
* \brief Initializes sound-effects and adds them to a cache
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
static void addSoundEffects(const std::map<SoundEffects, const char*> &effects);
|
||||||
|
|
||||||
|
/*!
|
||||||
|
* \brief Initializes background-music and adds them to a cache
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
static void addBackgroundMusic(const std::map<BackgroundMusic, const char*> &backgroundMusic);
|
||||||
|
|
||||||
|
static SoundManager* getInstance() {
|
||||||
|
return this_instance;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
|
std::map<BackgroundMusic, Mix_Music*> music_cache;
|
||||||
|
std::map<SoundEffects, Mix_Chunk*> sound_cache;
|
||||||
|
static SoundManager* this_instance;
|
||||||
|
|
||||||
|
static void addSingleBackgroundMusic(BackgroundMusic backgroundMusic, const char* path);
|
||||||
|
static void addSingleSoundEffect(SoundEffects soundEffect, const char* path);
|
||||||
};
|
};
|
||||||
@ -3,11 +3,15 @@
|
|||||||
#include "Constants.h"
|
#include "Constants.h"
|
||||||
#include <cstdint>
|
#include <cstdint>
|
||||||
#include <array>
|
#include <array>
|
||||||
|
#include <functional>
|
||||||
|
|
||||||
enum class Stats
|
/**
|
||||||
{
|
* @brief Struct to hold the duration, reset function and start time of a stat effect
|
||||||
MOVEMENT_SPEED,
|
*/
|
||||||
ATTACK_SPEED
|
struct StatEffect {
|
||||||
|
uint32_t duration; //!< Duration of the effect in milliseconds
|
||||||
|
std::function<void()> resetFunction; //!< Function to reset the effect, will be called on expiry of duration
|
||||||
|
uint32_t startTime;
|
||||||
};
|
};
|
||||||
|
|
||||||
class StatEffectsComponent : public Component{
|
class StatEffectsComponent : public Component{
|
||||||
@ -17,12 +21,13 @@ public:
|
|||||||
|
|
||||||
void init() override;
|
void init() override;
|
||||||
void update(uint_fast16_t diffTime) override;
|
void update(uint_fast16_t diffTime) override;
|
||||||
|
/**
|
||||||
void modifyStatDur(Stats stat, int duration, int value);
|
* @brief Add a stat effect to the entity
|
||||||
|
* @param duration The duration of the effect in milliseconds
|
||||||
void modifyStatValue(Stats stat, int modifier);
|
* @param resetFunction The function to reset the effect, will be called on expiry of duration
|
||||||
void resetStatValue(Stats stat);
|
*/
|
||||||
|
void addEffect(uint32_t duration, std::function<void()> resetFunction);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::array<int, MAX_STATS> buffs = { 0 };
|
std::vector<StatEffect> effects = {};
|
||||||
};
|
};
|
||||||
@ -3,6 +3,7 @@
|
|||||||
#include "Component.h"
|
#include "Component.h"
|
||||||
#include "Vector2D.h"
|
#include "Vector2D.h"
|
||||||
#include "Constants.h"
|
#include "Constants.h"
|
||||||
|
#include "DataComponent.h"
|
||||||
|
|
||||||
class TransformComponent : public Component
|
class TransformComponent : public Component
|
||||||
{
|
{
|
||||||
@ -14,22 +15,14 @@ public:
|
|||||||
int width = 32;
|
int width = 32;
|
||||||
int scale = 1;
|
int scale = 1;
|
||||||
|
|
||||||
int getSpeed() { return speed + speedMod; };
|
explicit TransformComponent(int scale = 1);
|
||||||
void resetSpeedMod() { speedMod = 0; };
|
TransformComponent(float x, float y, int scale = 1);
|
||||||
|
TransformComponent(float x, float y, int w, int h, int scale = 1);
|
||||||
TransformComponent();
|
|
||||||
explicit TransformComponent(int scale);
|
|
||||||
TransformComponent(float x, float y);
|
|
||||||
TransformComponent(float x, float y, int scale);
|
|
||||||
TransformComponent(float x, float y, int w, int h, int scale);
|
|
||||||
|
|
||||||
void init() override;
|
void init() override;
|
||||||
/*! TODO: document usage of collision handler */
|
/*! TODO: document usage of collision handler */
|
||||||
void update(uint_fast16_t diffTime) override;
|
void update(uint_fast16_t diffTime) override;
|
||||||
void setPositionAfterCollision(Vector2D& positionChange);
|
void setPositionAfterCollision(Vector2D& positionChange);
|
||||||
void modifySpeed(int8_t modifier);
|
int getSpeed();
|
||||||
|
|
||||||
private:
|
|
||||||
int speed = 180;
|
|
||||||
int speedMod = 0;
|
|
||||||
};
|
};
|
||||||
|
|||||||
@ -22,36 +22,6 @@ AssetManager::AssetManager(Manager* manager) : man(manager) {}
|
|||||||
|
|
||||||
AssetManager::~AssetManager() {}
|
AssetManager::~AssetManager() {}
|
||||||
|
|
||||||
void AssetManager::addSoundEffect(std::string id, const char* path)
|
|
||||||
{
|
|
||||||
soundEffects.emplace(id, this->man->getGame()->soundManager->loadSound(path));
|
|
||||||
}
|
|
||||||
|
|
||||||
void AssetManager::addMusic(std::string id, const char* path)
|
|
||||||
{
|
|
||||||
music.emplace(id, this->man->getGame()->soundManager->loadMusic(path));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
Mix_Chunk* AssetManager::getSound(std::string id) {
|
|
||||||
return soundEffects.at(id);
|
|
||||||
}
|
|
||||||
|
|
||||||
Mix_Music* AssetManager::getMusic(std::string id)
|
|
||||||
{
|
|
||||||
return music.at(id);
|
|
||||||
}
|
|
||||||
|
|
||||||
void AssetManager::createProjectile(Vector2D pos, Vector2D velocity, int scale, int range, float speed, Textures textureEnum, Entity* owner) {
|
|
||||||
|
|
||||||
auto& projectile(man->addEntity());
|
|
||||||
projectile.addComponent<TransformComponent>(pos.x, pos.y, 32, 32, scale); //32x32 is standard size for objects
|
|
||||||
projectile.addComponent<SpriteComponent>(textureEnum, 4);
|
|
||||||
projectile.addComponent<ProjectileComponent>(range, speed, velocity, owner);
|
|
||||||
projectile.addComponent<ColliderComponent>("projectile", 0.6f);
|
|
||||||
projectile.addGroup((size_t)Entity::GroupLabel::PROJECTILE);
|
|
||||||
}
|
|
||||||
|
|
||||||
void AssetManager::createPowerup(Vector2D pos, std::function<void (Entity*)> pickupFunc, Textures texture) {
|
void AssetManager::createPowerup(Vector2D pos, std::function<void (Entity*)> pickupFunc, Textures texture) {
|
||||||
|
|
||||||
auto& powerups(man->addEntity());
|
auto& powerups(man->addEntity());
|
||||||
|
|||||||
@ -14,7 +14,7 @@ void ProjectileComponent::init()
|
|||||||
{
|
{
|
||||||
transformComponent = &entity->getComponent<TransformComponent>();
|
transformComponent = &entity->getComponent<TransformComponent>();
|
||||||
transformComponent->direction = direction;
|
transformComponent->direction = direction;
|
||||||
SoundManager::playSound(this->entity->getManager().getGame(), "throw_egg", true, PLAY_ONCE, MAX_VOLUME, -1);
|
SoundManager::playSound(this->soundEffect, true, PLAY_ONCE, MAX_VOLUME, -1);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ProjectileComponent::update(uint_fast16_t diffTime)
|
void ProjectileComponent::update(uint_fast16_t diffTime)
|
||||||
|
|||||||
@ -8,9 +8,10 @@
|
|||||||
#include "GameInternal.h"
|
#include "GameInternal.h"
|
||||||
#include "AssetManager.h"
|
#include "AssetManager.h"
|
||||||
|
|
||||||
|
/*
|
||||||
Mix_Music* SoundManager::loadMusic(const char* fileName)
|
Mix_Music* SoundManager::loadMusic(const char* fileName)
|
||||||
{
|
{
|
||||||
auto it = this->music_cache.find(fileName);
|
//auto it = this->music_cache.find(fileName);
|
||||||
|
|
||||||
if (it != this->music_cache.end()) {
|
if (it != this->music_cache.end()) {
|
||||||
return it->second;
|
return it->second;
|
||||||
@ -48,14 +49,21 @@ Mix_Chunk* SoundManager::loadSound(const char* fileName)
|
|||||||
return sound;
|
return sound;
|
||||||
}
|
}
|
||||||
|
|
||||||
void SoundManager::playSound(GameInternal* game, std::string sound, bool canOverlap, int loops, int volume, int channel)
|
*/
|
||||||
|
|
||||||
|
void SoundManager::playSound(SoundEffects sound, bool canOverlap, int loops, int volume, int channel)
|
||||||
{
|
{
|
||||||
|
if (!this_instance->sound_cache.contains(sound)) {
|
||||||
|
std::cerr << "Error playing Sound-Effect: sound effect not found" << std::endl;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if(!canOverlap)
|
if(!canOverlap)
|
||||||
{
|
{
|
||||||
// dev needs to specify a channel for this check to work, if they set it to -1 and let sdl pick the first available
|
// dev needs to specify a channel for this check to work, if they set it to -1 and let sdl pick the first available
|
||||||
// channel mix_getchunk() won't work
|
// channel mix_getchunk() won't work
|
||||||
if (Mix_Playing(channel) != 0 &&
|
if (Mix_Playing(channel) != 0 &&
|
||||||
Mix_GetChunk(channel) == game->assets->getSound(sound) &&
|
Mix_GetChunk(channel) == this_instance->sound_cache.at(sound) &&
|
||||||
channel != -1)
|
channel != -1)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
@ -64,25 +72,30 @@ void SoundManager::playSound(GameInternal* game, std::string sound, bool canOver
|
|||||||
Mix_HaltChannel(channel);
|
Mix_HaltChannel(channel);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(Mix_VolumeChunk(game->assets->getSound(sound), volume) == -1)
|
if(Mix_VolumeChunk(this_instance->sound_cache.at(sound), volume) == -1)
|
||||||
{
|
{
|
||||||
std::cerr << "Error adjusting volume: " << SDL_GetError() << std::endl;
|
std::cerr << "Error adjusting volume: " << SDL_GetError() << std::endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Mix_PlayChannel(channel, game->assets->getSound(sound), loops) == -1)
|
if (Mix_PlayChannel(channel, this_instance->sound_cache.at(sound), loops) == -1)
|
||||||
{
|
{
|
||||||
std::cerr << "Error playing sound '" << sound << "': " << SDL_GetError() << std::endl;
|
std::cerr << "Error playing sound " << ": " << SDL_GetError() << std::endl;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void SoundManager::playMusic(GameInternal* game, std::string music, int loops, int volume, int ms)
|
void SoundManager::playMusic(BackgroundMusic music, int loops, int volume, int milliseconds)
|
||||||
{
|
{
|
||||||
|
if (!this_instance->music_cache.contains(music)) {
|
||||||
|
std::cerr << "Error playing music: music not found" << std::endl;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (Mix_PlayingMusic() != 0 || Mix_Fading() == Mix_Fading::MIX_FADING_IN)
|
if (Mix_PlayingMusic() != 0 || Mix_Fading() == Mix_Fading::MIX_FADING_IN)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if(ms > 0)
|
if(milliseconds > 0)
|
||||||
{
|
{
|
||||||
Mix_FadeInMusic(game->assets->getMusic(music), loops, ms);
|
Mix_FadeInMusic(this_instance->music_cache.at(music), loops, milliseconds);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -90,11 +103,6 @@ void SoundManager::playMusic(GameInternal* game, std::string music, int loops, i
|
|||||||
{
|
{
|
||||||
std::cerr << "Error adjusting volume: " << SDL_GetError() << std::endl;
|
std::cerr << "Error adjusting volume: " << SDL_GetError() << std::endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Mix_PlayMusic(game->assets->getMusic(music), loops) == -1)
|
|
||||||
{
|
|
||||||
std::cerr << "Error playing music '" << music << "': " << SDL_GetError() << std::endl;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void SoundManager::setSoundVolume(int volume, int channel)
|
void SoundManager::setSoundVolume(int volume, int channel)
|
||||||
@ -134,3 +142,51 @@ void SoundManager::fadeOutMusic(int ms)
|
|||||||
|
|
||||||
Mix_FadeOutMusic(ms);
|
Mix_FadeOutMusic(ms);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void SoundManager::addSingleSoundEffect(SoundEffects soundEffect, const char *path) {
|
||||||
|
if (this_instance->sound_cache.contains(soundEffect)) {
|
||||||
|
std::cerr << "Error when adding Sound-Effect: sound-effect with that key already in cache" << std::endl;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Mix_Chunk* sound = Mix_LoadWAV(path);
|
||||||
|
|
||||||
|
if (sound == nullptr) {
|
||||||
|
std::cerr << "Error when loading Sound-Effect: could not load sound effect from " << path << std::endl;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
this_instance->sound_cache.emplace(soundEffect, sound);
|
||||||
|
}
|
||||||
|
|
||||||
|
void SoundManager::addSingleBackgroundMusic(BackgroundMusic backgroundMusic, const char *path) {
|
||||||
|
if (this_instance->music_cache.contains(backgroundMusic)) {
|
||||||
|
std::cerr << "Error when adding Sound-Effect: sound-effect with that key already in cache" << std::endl;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Mix_Music* music = Mix_LoadMUS(path);
|
||||||
|
|
||||||
|
if (music == nullptr) {
|
||||||
|
std::cerr << "Error when loading Sound-Effect: could not load sound effect from " << path << std::endl;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
this_instance->music_cache.emplace(backgroundMusic, music);
|
||||||
|
}
|
||||||
|
|
||||||
|
void SoundManager::addSoundEffects(const std::map<SoundEffects, const char *> &effects) {
|
||||||
|
for (auto effect : effects)
|
||||||
|
addSingleSoundEffect(effect.first, effect.second);
|
||||||
|
}
|
||||||
|
|
||||||
|
void SoundManager::addBackgroundMusic(const std::map<BackgroundMusic, const char *> &backgroundMusic) {
|
||||||
|
for (auto track : backgroundMusic)
|
||||||
|
addSingleBackgroundMusic(track.first, track.second);
|
||||||
|
}
|
||||||
|
|
||||||
|
SoundManager* SoundManager::this_instance = nullptr;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@ -1,7 +1,6 @@
|
|||||||
#include "StatEffectsComponent.h"
|
#include "StatEffectsComponent.h"
|
||||||
#include "Entity.h"
|
#include "Entity.h"
|
||||||
#include "TransformComponent.h"
|
#include "TransformComponent.h"
|
||||||
// #include "KeyboardController.h"
|
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
@ -10,45 +9,18 @@ void StatEffectsComponent::init()
|
|||||||
|
|
||||||
void StatEffectsComponent::update(uint_fast16_t diffTime)
|
void StatEffectsComponent::update(uint_fast16_t diffTime)
|
||||||
{
|
{
|
||||||
for (int i = 0; i < MAX_STATS; i++)
|
for (auto it = effects.begin(); it != effects.end(); ) {
|
||||||
{
|
it->duration -= diffTime;
|
||||||
this->buffs.at(i) -= diffTime;
|
|
||||||
if (this->buffs.at(i) <= 0) {
|
if (it->duration <= 0) {
|
||||||
this->resetStatValue((Stats)i);
|
it->resetFunction();
|
||||||
|
it = effects.erase(it);
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
}
|
it++;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void StatEffectsComponent::modifyStatDur(Stats stat, int duration, int value)
|
void StatEffectsComponent::addEffect(uint32_t duration, std::function<void()> resetFunction) {
|
||||||
{
|
effects.push_back({duration, resetFunction});
|
||||||
if(this->buffs.at((uint8_t)stat) == 0) this->modifyStatValue(stat, value);
|
|
||||||
this->buffs.at((uint8_t)stat) += duration;
|
|
||||||
}
|
|
||||||
|
|
||||||
void StatEffectsComponent::modifyStatValue(Stats stat, int modifier) //modifier is basically there so the modifyfuncs in the components know if stats should be increased or decreased
|
|
||||||
{
|
|
||||||
switch (stat)
|
|
||||||
{
|
|
||||||
case Stats::MOVEMENT_SPEED:
|
|
||||||
this->entity->getComponent<TransformComponent>().modifySpeed(modifier);
|
|
||||||
break;
|
|
||||||
case Stats::ATTACK_SPEED:
|
|
||||||
// this->entity->getComponent<KeyboardController>().modifyAtkSpeed(modifier);
|
|
||||||
break;
|
|
||||||
default: break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void StatEffectsComponent::resetStatValue(Stats stat)
|
|
||||||
{
|
|
||||||
switch (stat)
|
|
||||||
{
|
|
||||||
case Stats::MOVEMENT_SPEED:
|
|
||||||
this->entity->getComponent<TransformComponent>().resetSpeedMod();
|
|
||||||
break;
|
|
||||||
case Stats::ATTACK_SPEED:
|
|
||||||
// this->entity->getComponent<KeyboardController>().resetAtkSpeedMod();
|
|
||||||
break;
|
|
||||||
default: break;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
@ -9,26 +9,16 @@
|
|||||||
#include <cstdio>
|
#include <cstdio>
|
||||||
#include <initializer_list>
|
#include <initializer_list>
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
#include <optional>
|
||||||
|
|
||||||
#include "SoundManager.h"
|
#include "SoundManager.h"
|
||||||
|
|
||||||
TransformComponent::TransformComponent()
|
|
||||||
{
|
|
||||||
position.zero();
|
|
||||||
}
|
|
||||||
|
|
||||||
TransformComponent::TransformComponent(int scale)
|
TransformComponent::TransformComponent(int scale)
|
||||||
{
|
{
|
||||||
position.zero();
|
position.zero();
|
||||||
this->scale = scale;
|
this->scale = scale;
|
||||||
}
|
}
|
||||||
|
|
||||||
TransformComponent::TransformComponent(float x, float y)
|
|
||||||
{
|
|
||||||
this->position.x = x;
|
|
||||||
this->position.y = y;
|
|
||||||
}
|
|
||||||
|
|
||||||
TransformComponent::TransformComponent(float x, float y, int scale)
|
TransformComponent::TransformComponent(float x, float y, int scale)
|
||||||
{
|
{
|
||||||
this->position.x = x;
|
this->position.x = x;
|
||||||
@ -65,9 +55,11 @@ void TransformComponent::update(uint_fast16_t diffTime)
|
|||||||
position += positionChange;
|
position += positionChange;
|
||||||
}
|
}
|
||||||
|
|
||||||
void TransformComponent::modifySpeed(int8_t modifier)
|
int TransformComponent::getSpeed()
|
||||||
{
|
{
|
||||||
this->speedMod += modifier;
|
return (this->entity->hasComponent<DataComponent>()
|
||||||
|
? this->entity->getComponent<DataComponent>().getEntry<int>("speed").value_or(0)
|
||||||
|
: 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
void TransformComponent::setPositionAfterCollision(Vector2D& positionChange)
|
void TransformComponent::setPositionAfterCollision(Vector2D& positionChange)
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user