aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/common.hpp4
-rw-r--r--include/particle.hpp42
-rw-r--r--include/texture.hpp1
-rw-r--r--include/weather.hpp67
-rw-r--r--include/world.hpp39
-rw-r--r--main.cpp9
-rw-r--r--src/engine.cpp7
-rw-r--r--src/inventory.cpp9
-rw-r--r--src/particle.cpp99
-rw-r--r--src/texture.cpp6
-rw-r--r--src/world.cpp77
-rw-r--r--xml/!town.xml1
12 files changed, 258 insertions, 103 deletions
diff --git a/include/common.hpp b/include/common.hpp
index 19af420..71039c7 100644
--- a/include/common.hpp
+++ b/include/common.hpp
@@ -91,11 +91,11 @@ struct vec2 {
}
template<typename T>
- const vec2 operator+(const T &n) {
+ vec2 operator+(T n) const {
return vec2 (x + n, y + n);
}
- const vec2 operator+(const vec2 &v) {
+ vec2 operator+(const vec2 &v) {
return vec2 (x + v.x, y + v.y);
}
diff --git a/include/particle.hpp b/include/particle.hpp
new file mode 100644
index 0000000..d9aa29f
--- /dev/null
+++ b/include/particle.hpp
@@ -0,0 +1,42 @@
+#ifndef PARTICLE_HPP_
+#define PARTICLE_HPP_
+
+#include <common.hpp>
+
+#include <list>
+
+#include <entityx/entityx.h>
+
+enum class ParticleType : char {
+ Drop,
+ Confetti
+};
+
+struct Particle {
+ vec2 location;
+ vec2 velocity;
+ ParticleType type;
+ int timeLeft;
+
+ Particle(vec2 p, ParticleType t = ParticleType::Drop)
+ : location(p), type(t), timeLeft(3000) {} // TODO times
+} __attribute__ ((packed));
+
+class ParticleSystem : public entityx::System<ParticleSystem> {
+private:
+ std::vector<Particle> parts;
+ bool max;
+
+public:
+ ParticleSystem(int count = 1024, bool m = false);
+
+ void add(const vec2& pos, const ParticleType& type);
+ void addMultiple(const int& count, const ParticleType& type, std::function<vec2(void)> f);
+
+ void render(void) const;
+ void update(entityx::EntityManager &en, entityx::EventManager &ev, entityx::TimeDelta dt) override;
+
+ int getCount(void) const;
+};
+
+#endif // PARTICLE_HPP_
diff --git a/include/texture.hpp b/include/texture.hpp
index e9082b3..878955e 100644
--- a/include/texture.hpp
+++ b/include/texture.hpp
@@ -91,6 +91,7 @@ namespace Colors {
extern ColorTex white; /**< A solid white texture. */
extern ColorTex black; /**< A solid black texture. */
extern ColorTex red; /**< A solid red texture. */
+ extern ColorTex blue; /**< A solid blue texture. */
/**
* Creates the colors.
diff --git a/include/weather.hpp b/include/weather.hpp
new file mode 100644
index 0000000..f7b53f1
--- /dev/null
+++ b/include/weather.hpp
@@ -0,0 +1,67 @@
+#ifndef WEATHER_HPP_
+#define WEATHER_HPP_
+
+#include <entityx/entityx.h>
+
+#include <common.hpp>
+#include <particle.hpp>
+
+/**
+ * The weather type enum.
+ * This enum contains every type of weather currently implemented in the game.
+ * Weather is set by the world somewhere.
+ */
+enum class Weather : unsigned char {
+ Sunny = 0, /**< Sunny */
+ Rainy, /**< Rain */
+ Snowy, /**< Snow */
+ count
+};
+
+constexpr const char *weatherStrings[] = {
+ "Sunny",
+ "Rainy",
+ "Snowy"
+};
+
+class WeatherSystem : public entityx::System<WeatherSystem> {
+private:
+ Weather weather;
+
+public:
+ WeatherSystem(Weather w = Weather::Sunny)
+ : weather(w) {}
+
+ void update(entityx::EntityManager &en, entityx::EventManager &ev, entityx::TimeDelta dt) override {
+ (void)en;
+ (void)ev;
+ (void)dt;
+
+ static auto& partSystem = *game::engine.getSystem<ParticleSystem>();
+
+ switch (weather) {
+ case Weather::Sunny:
+ break;
+ case Weather::Rainy:
+ partSystem.add(vec2(offset.x - game::SCREEN_WIDTH / 2 + randGet() % game::SCREEN_WIDTH,
+ offset.y + game::SCREEN_HEIGHT / 2 + 100),
+ ParticleType::Drop);
+ break; // TODO
+ case Weather::Snowy:
+ break; // TODO
+ default:
+ break;
+ }
+ }
+
+ inline void setWeather(const std::string& w) {
+ for (int i = 0; i < static_cast<int>(Weather::count); i++) {
+ if (w == weatherStrings[i]) {
+ weather = static_cast<Weather>(i);
+ return;
+ }
+ }
+ }
+};
+
+#endif // WEATHER_HPP_
diff --git a/include/world.hpp b/include/world.hpp
index 8864d30..14c64d0 100644
--- a/include/world.hpp
+++ b/include/world.hpp
@@ -28,36 +28,16 @@ enum class WorldBGType : unsigned int {
};
/**
- * The weather type enum.
- * This enum contains every type of weather currently implemented in the game.
- * Weather is set by the world somewhere.
- */
-enum class WorldWeather : unsigned char {
- None = 0, /**< None (sunny) */
- Rain, /**< Rain */
- Snowy /**< Snow */
-};
-
-/**
- * Strings to represent each type of weather.
- */
-constexpr const char* WorldWeatherString[3] = {
- "None",
- "Rainy",
- "Snowy"
-};
-
-/**
* The line structure.
* This structure is used to store the world's ground, stored in vertical
* lines. Dirt color and grass properties are also kept track of here.
*/
-typedef struct {
+struct WorldData {
bool grassUnpressed; /**< squishes grass if false */
float grassHeight[2]; /**< height of the two grass blades */
float groundHeight; /**< height of the 'line' */
unsigned char groundColor; /**< a value that affects the ground's color */
-} WorldData;
+} __attribute__ ((packed));
/**
* Defines how many game ticks it takes to go from day to night or vice versa.
@@ -130,11 +110,6 @@ private:
WorldData2 world;
/**
- * The current state of weather in the world.
- */
- WorldWeather weather;
-
- /**
* SDL's object for handling the background music.
*/
Mix_Music *bgmObj;
@@ -176,22 +151,16 @@ public:
inline float getWidth(void) const
{ return world.startX * -2.0f; }
+ float isAboveGround(const vec2& p) const;
+
void receive(const BGMToggleEvent &bte);
void update(entityx::EntityManager &en, entityx::EventManager &ev, entityx::TimeDelta dt) override;
void render(void);
- inline const std::string getWeatherStr(void) const
- { return WorldWeatherString[static_cast<int>(weather)]; }
-
- inline const WorldWeather& getWeatherId(void) const
- { return weather; }
-
inline const std::string& getXMLFile(void) const
{ return currentXMLFile; }
- void setWeather(const std::string &s);
-
void detect(entityx::TimeDelta dt);
void goWorldLeft(Position& p);
diff --git a/main.cpp b/main.cpp
index 17499f7..2e33a83 100644
--- a/main.cpp
+++ b/main.cpp
@@ -25,6 +25,7 @@ using namespace tinyxml2;
#include <world.hpp>
#include <render.hpp>
#include <ui.hpp>
+#include <particle.hpp>
/**
* The currently used folder to look for XML files in.
@@ -311,6 +312,7 @@ void render() {
// draw the world and player
game::engine.getSystem<WorldSystem>()->render();
+ game::engine.getSystem<ParticleSystem>()->render();
// draw the player's inventory
//player->inv->draw();
@@ -327,9 +329,10 @@ void render() {
if (ui::debug) {
auto pos = game::engine.getSystem<PlayerSystem>()->getPosition();
ui::putText(offset.x - SCREEN_WIDTH2, (offset.y + SCREEN_HEIGHT2) - ui::fontSize,
- "loc: %s\noffset: %s\nfps: %d\nticks: %d\nxml: %s",
- pos.toString().c_str(), offset.toString().c_str(), fps,
- game::time::getTickCount(), game::engine.getSystem<WorldSystem>()->getXMLFile().c_str());
+ "loc: %s\noffset: %s\nfps: %d\nticks: %d\npcount: %d\nxml: %s",
+ pos.toString().c_str(), offset.toString().c_str(), fps,
+ game::time::getTickCount(), game::engine.getSystem<ParticleSystem>()->getCount(),
+ game::engine.getSystem<WorldSystem>()->getXMLFile().c_str());
}
// draw the menu
diff --git a/src/engine.cpp b/src/engine.cpp
index 48e384d..aa0db73 100644
--- a/src/engine.cpp
+++ b/src/engine.cpp
@@ -8,6 +8,8 @@
#include <components.hpp>
#include <player.hpp>
#include <quest.hpp>
+#include <particle.hpp>
+#include <weather.hpp>
Engine::Engine(void)
: shouldRun(true), systems(game::entities, game::events)
@@ -30,6 +32,9 @@ void Engine::init(void) {
systems.add<MovementSystem>();
systems.add<DialogSystem>();
+ systems.add<ParticleSystem>();
+ systems.add<WeatherSystem>();
+
systems.configure();
ui::initSounds();
@@ -57,6 +62,8 @@ void Engine::update(entityx::TimeDelta dt)
systems.update<WorldSystem>(dt);
systems.update<PlayerSystem>(dt);
//systems.update<QuestSystem>(dt); // doesn't do anything
+ systems.update<WeatherSystem>(dt);
+ systems.update<ParticleSystem>(dt);
}
diff --git a/src/inventory.cpp b/src/inventory.cpp
index fb999ea..480c803 100644
--- a/src/inventory.cpp
+++ b/src/inventory.cpp
@@ -27,16 +27,19 @@ void InventorySystem::update(entityx::EntityManager &en, entityx::EventManager &
(void)ev;
(void)dt;
- vec2 start = vec2(offset.x, 100);// - game::SCREEN_WIDTH / 2 + 20, game::SCREEN_HEIGHT - 40);
+ // TODO TODO TODO TODO until we do something
+ return;
+
+ //vec2 start = vec2(offset.x, 100);// - game::SCREEN_WIDTH / 2 + 20, game::SCREEN_HEIGHT - 40);
//std::cout << start.x << ' ' << start.y << std::endl;
- Render::textShader.use();
+ /*Render::textShader.use();
glActiveTexture(GL_TEXTURE0);
Colors::black.use();
Render::useShader(&Render::textShader);
Render::drawRect(start, start + 20, -9.9f);
- Render::textShader.unuse();
+ Render::textShader.unuse();*/
}
void InventorySystem::receive(const KeyDownEvent &kde)
diff --git a/src/particle.cpp b/src/particle.cpp
new file mode 100644
index 0000000..8090e2d
--- /dev/null
+++ b/src/particle.cpp
@@ -0,0 +1,99 @@
+#include <particle.hpp>
+
+#include <engine.hpp>
+#include <render.hpp>
+#include <world.hpp>
+
+ParticleSystem::ParticleSystem(int count, bool m)
+ : max(m)
+{
+ parts.reserve(count);
+}
+
+void ParticleSystem::add(const vec2& pos, const ParticleType& type)
+{
+ // TODO enforce max
+ //if (max && parts.size() >= std::end(parts))
+ // return;
+
+ parts.emplace_back(pos, type);
+}
+
+void ParticleSystem::addMultiple(const int& count, const ParticleType& type, std::function<vec2(void)> f)
+{
+ int togo = count;
+ while (togo-- > 0)
+ parts.emplace_back(f(), type);
+}
+
+void ParticleSystem::render(void) const
+{
+ static const GLfloat tex[12] = {
+ 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0
+ };
+
+ Render::worldShader.use();
+ Render::worldShader.enable();
+ Colors::blue.use();
+
+ for (const auto& p : parts) {
+ GLfloat coord[18] = {
+ p.location.x, p.location.y, -1,
+ p.location.x, p.location.y + 5, -1,
+ p.location.x + 5, p.location.y + 5, -1,
+ p.location.x + 5, p.location.y + 5, -1,
+ p.location.x + 5, p.location.y, -1,
+ p.location.x, p.location.y, -1
+ };
+
+ glVertexAttribPointer(Render::worldShader.coord, 3, GL_FLOAT, GL_FALSE, 0, coord);
+ glVertexAttribPointer(Render::worldShader.tex, 2, GL_FLOAT, GL_FALSE, 0, tex);
+ glDrawArrays(GL_TRIANGLES, 0, 6);
+ }
+
+ Render::worldShader.disable();
+ Render::worldShader.unuse();
+}
+
+void ParticleSystem::update(entityx::EntityManager &en, entityx::EventManager &ev, entityx::TimeDelta dt)
+{
+ (void)en;
+ (void)ev;
+ (void)dt; // TODO use for time to die
+
+ auto& worldSystem = *game::engine.getSystem<WorldSystem>();
+
+ for (auto part = std::begin(parts); part != std::end(parts); part++) {
+ auto& p = *part;
+
+ // update timers
+ p.timeLeft -= dt;
+ if (p.timeLeft <= 0)
+ parts.erase(part);
+
+ // update movement
+ switch (p.type) {
+ case ParticleType::Drop:
+ if (p.velocity.y > -.5)
+ p.velocity.y -= 0.001f;
+ break;
+ case ParticleType::Confetti:
+ break;
+ }
+
+ // really update movement
+ p.location.x += p.velocity.x * dt;
+ p.location.y += p.velocity.y * dt;
+
+ // world collision
+ auto height = worldSystem.isAboveGround(p.location);
+ if (height != 0)
+ p.location.y = height + 5, p.velocity.y = randGet() % 10 / 40.0f;
+ }
+}
+
+int ParticleSystem::getCount(void) const
+{
+ return parts.size();
+}
+
diff --git a/src/texture.cpp b/src/texture.cpp
index 640b06e..da39ec0 100644
--- a/src/texture.cpp
+++ b/src/texture.cpp
@@ -8,11 +8,13 @@ namespace Colors
ColorTex white;
ColorTex black;
ColorTex red;
+ ColorTex blue;
void init(void) {
white = ColorTex(Color(255, 255, 255));
- black = ColorTex(Color(0, 0, 0));
- red = ColorTex(Color(255, 0, 0));
+ black = ColorTex(Color(0, 0, 0 ));
+ red = ColorTex(Color(255, 0, 0 ));
+ blue = ColorTex(Color(0, 0, 255));
}
}
diff --git a/src/world.cpp b/src/world.cpp
index 08426a8..6f31a5b 100644
--- a/src/world.cpp
+++ b/src/world.cpp
@@ -21,6 +21,7 @@ using namespace std::literals::chrono_literals;
#include <engine.hpp>
#include <components.hpp>
#include <player.hpp>
+#include <weather.hpp>
// local library headers
#include <tinyxml2.h>
@@ -74,12 +75,10 @@ const unsigned int GRASS_HEIGHT = HLINES(4);
std::string currentXML;
// pathnames of images for world themes
-using StyleList = std::array<std::string, 9>;
-
+using StyleList = std::array<std::string, 8>;
static const std::vector<StyleList> bgPaths = {
{ // Forest
- "bg.png", // daytime background
- "bgn.png", // nighttime background
+ "bg.png", // sky/background
"bgFarMountain.png", // layer 1 (furthest)
"forestTileFar.png", // layer 2
"forestTileBack.png", // layer 3
@@ -154,6 +153,15 @@ void WorldSystem::generate(int width)
world.startX = HLINES(width * -0.5);
}
+float WorldSystem::isAboveGround(const vec2& p) const
+{
+ int line = std::clamp(static_cast<int>((p.x - world.startX) / game::HLINE),
+ 0, static_cast<int>(world.data.size()));
+
+ const auto& gh = world.data[line].groundHeight;
+ return p.y >= gh ? 0 : gh;
+}
+
static Color ambient;
bool WorldSystem::save(void)
@@ -279,7 +287,8 @@ void WorldSystem::load(const std::string& file)
// weather tag
else if (tagName == "weather") {
- setWeather(wxml->GetText());
+ game::engine.getSystem<WeatherSystem>()->setWeather(wxml->GetText());
+ //setWeather(wxml->GetText());
}
// link tags
@@ -645,7 +654,7 @@ loadWorldFromXMLNoSave(std::string path) {
}*/
WorldSystem::WorldSystem(void)
- : weather(WorldWeather::None), bgmObj(nullptr) {}
+ : bgmObj(nullptr) {}
WorldSystem::~WorldSystem(void)
{
@@ -668,10 +677,6 @@ void WorldSystem::render(void)
// world width in pixels
int width = HLINES(world.data.size());
- // used for alpha values of background textures
- int alpha;
-
-
static bool ambientUpdaterStarted = false;
if (!ambientUpdaterStarted) {
ambientUpdaterStarted = true;
@@ -690,34 +695,12 @@ void WorldSystem::render(void)
thAmbient.detach();
}
-
- switch (weather) {
- case WorldWeather::Snowy:
- alpha = 150;
- break;
- case WorldWeather::Rain:
- alpha = 0;
- break;
- default:
- alpha = 255 - worldShade * 4;
- break;
- }
-
// shade value for GLSL
float shadeAmbient = std::max(0.0f, static_cast<float>(-worldShade) / 50 + 0.5f); // 0 to 1.5f
if (shadeAmbient > 0.9f)
shadeAmbient = 1;
- // draw background images.
- GLfloat tex_coord[] = { 0.0f, 1.0f,
- 1.0f, 1.0f,
- 1.0f, 0.0f,
-
- 1.0f, 0.0f,
- 0.0f, 0.0f,
- 0.0f, 1.0f,};
-
// TODO scroll backdrop
GLfloat bgOff = game::time::getTickCount() / static_cast<float>(DAY_CYCLE * 2);
@@ -759,16 +742,6 @@ void WorldSystem::render(void)
offset.x - backgroundOffset.x - 5, offset.y - backgroundOffset.y, 9.9f
};
- GLfloat fron_tex_coord[] = {
- offset.x - backgroundOffset.x - 5, offset.y + backgroundOffset.y, 9.8f,
- offset.x + backgroundOffset.x + 5, offset.y + backgroundOffset.y, 9.8f,
- offset.x + backgroundOffset.x + 5, offset.y - backgroundOffset.y, 9.8f,
-
- offset.x + backgroundOffset.x + 5, offset.y - backgroundOffset.y, 9.8f,
- offset.x - backgroundOffset.x - 5, offset.y - backgroundOffset.y, 9.8f,
- offset.x - backgroundOffset.x - 5, offset.y + backgroundOffset.y, 9.8f
- };
-
// rendering!!
glActiveTexture(GL_TEXTURE0);
@@ -789,10 +762,10 @@ void WorldSystem::render(void)
makeWorldDrawingSimplerEvenThoughAndyDoesntThinkWeCanMakeItIntoFunctions(0, back_tex_coord, scrolling_tex_coord, 6);
- bgTex++;
- glUniform4f(Render::worldShader.uniform[WU_tex_color], 1.0, 1.0, 1.0, 1.3 - static_cast<float>(alpha) / 255.0f);
-
- makeWorldDrawingSimplerEvenThoughAndyDoesntThinkWeCanMakeItIntoFunctions(0, fron_tex_coord, tex_coord, 6);
+ // no more night bg
+ //bgTex++;
+ //glUniform4f(Render::worldShader.uniform[WU_tex_color], 1.0, 1.0, 1.0, 1.3 - static_cast<float>(alpha) / 255.0f);
+ //makeWorldDrawingSimplerEvenThoughAndyDoesntThinkWeCanMakeItIntoFunctions(0, fron_tex_coord, tex_coord, 6);
// TODO make stars dynamic
/*static GLuint starTex = Texture::loadTexture("assets/style/classic/bg/star.png");
@@ -1126,18 +1099,6 @@ void WorldSystem::receive(const BGMToggleEvent &bte)
}
}
-void WorldSystem::setWeather(const std::string &s)
-{
- for (unsigned int i = 3; i--;) {
- if (WorldWeatherString[i] == s) {
- weather = static_cast<WorldWeather>(i);
- return;
- }
- }
-
- weather = WorldWeather::None;
-}
-
void WorldSystem::update(entityx::EntityManager &en, entityx::EventManager &ev, entityx::TimeDelta dt)
{
(void)en;
diff --git a/xml/!town.xml b/xml/!town.xml
index d98e8c6..c197d8d 100644
--- a/xml/!town.xml
+++ b/xml/!town.xml
@@ -4,6 +4,7 @@
<World>
<style background="0" bgm="assets/music/embark.wav" folder="assets/style/classic/"/>
<generation width="320"/>
+ <weather>Rainy</weather>
<time>6000</time>
<link right="!town2.xml"/>
<spawnx>-300</spawnx>