SuperTuxKart
cpu_particle_manager.hpp
1 // SuperTuxKart - a fun racing game with go-kart
2 // Copyright (C) 2017 SuperTuxKart-Team
3 //
4 // This program is free software; you can redistribute it and/or
5 // modify it under the terms of the GNU General Public License
6 // as published by the Free Software Foundation; either version 3
7 // of the License, or (at your option) any later version.
8 //
9 // This program is distributed in the hope that it will be useful,
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 // GNU General Public License for more details.
13 //
14 // You should have received a copy of the GNU General Public License
15 // along with this program; if not, write to the Free Software
16 // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
17 
18 #ifndef HEADER_CPU_PARTICLE_MANAGER_HPP
19 #define HEADER_CPU_PARTICLE_MANAGER_HPP
20 
21 #ifndef SERVER_ONLY
22 
23 #include "graphics/gl_headers.hpp"
24 #include "utils/constants.hpp"
25 #include "utils/mini_glm.hpp"
26 #include "utils/no_copy.hpp"
27 #include "utils/singleton.hpp"
28 
29 #include <dimension2d.h>
30 #include <IBillboardSceneNode.h>
31 #include <vector3d.h>
32 #include <SColor.h>
33 
34 #include <cassert>
35 #include <string>
36 #include <memory>
37 #include <unordered_map>
38 #include <unordered_set>
39 #include <vector>
40 
41 using namespace irr;
42 
44 {
45  core::vector3df m_position;
46  video::SColor m_color_lifetime;
47  short m_size[2];
48  // ------------------------------------------------------------------------
49  CPUParticle(const core::vector3df& position,
50  const core::vector3df& color_from,
51  const core::vector3df& color_to, float lf_time, float size)
52  : m_position(position)
53  {
54  core::vector3df ret = color_from + (color_to - color_from) * lf_time;
55  m_color_lifetime.setRed(core::clamp((int)(ret.X * 255.0f), 0, 255));
56  m_color_lifetime.setBlue(core::clamp((int)(ret.Y * 255.0f), 0, 255));
57  m_color_lifetime.setGreen(core::clamp((int)(ret.Z * 255.0f), 0, 255));
58  m_color_lifetime.setAlpha(core::clamp((int)(lf_time * 255.0f), 0, 255));
59  m_size[0] = MiniGLM::toFloat16(size);
60  m_size[1] = m_size[0];
61  }
62  // ------------------------------------------------------------------------
63  CPUParticle(scene::IBillboardSceneNode* node)
64  {
65  m_position = node->getAbsolutePosition();
66  video::SColor unused_bottom;
67  node->getColor(m_color_lifetime, unused_bottom);
68  m_size[0] = MiniGLM::toFloat16(node->getSize().Width);
69  m_size[1] = MiniGLM::toFloat16(node->getSize().Height);
70  }
71 };
72 
73 
74 class STKParticle;
75 class Material;
76 
77 class CPUParticleManager : public Singleton<CPUParticleManager>, NoCopy
78 {
79 private:
80  struct GLParticle : public NoCopy
81  {
82  GLuint m_vao;
83  GLuint m_vbo;
84  unsigned m_size;
85  // --------------------------------------------------------------------
86  GLParticle(bool flips);
87  // --------------------------------------------------------------------
88  ~GLParticle()
89  {
90  glDeleteVertexArrays(1, &m_vao);
91  glDeleteBuffers(1, &m_vbo);
92  }
93  };
94 
95  std::unordered_map<std::string, std::vector<STKParticle*> >
96  m_particles_queue;
97 
98  std::unordered_map<std::string, std::vector<scene::IBillboardSceneNode*> >
99  m_billboards_queue;
100 
101  std::unordered_map<std::string, std::vector<CPUParticle> >
102  m_particles_generated;
103 
104  std::unordered_map<std::string, std::unique_ptr<GLParticle> >
105  m_gl_particles;
106 
107  std::unordered_map<std::string, Material*> m_material_map;
108 
109  std::unordered_set<std::string> m_flips_material;
110 
111  static GLuint m_particle_quad;
112 
113  // ------------------------------------------------------------------------
114  bool isFlipsMaterial(const std::string& name)
115  { return m_flips_material.find(name) != m_flips_material.end(); }
116 
117 public:
118  // ------------------------------------------------------------------------
120  // ------------------------------------------------------------------------
122  {
123  glDeleteBuffers(1, &m_particle_quad);
124  m_particle_quad = 0;
125  }
126  // ------------------------------------------------------------------------
127  void addParticleNode(STKParticle* node);
128  // ------------------------------------------------------------------------
129  void addBillboardNode(scene::IBillboardSceneNode* node);
130  // ------------------------------------------------------------------------
131  void generateAll();
132  // ------------------------------------------------------------------------
133  void uploadAll();
134  // ------------------------------------------------------------------------
135  void drawAll();
136  // ------------------------------------------------------------------------
137  void reset()
138  {
139  for (auto& p : m_particles_queue)
140  {
141  p.second.clear();
142  }
143  for (auto& p : m_billboards_queue)
144  {
145  p.second.clear();
146  }
147  for (auto& p : m_particles_generated)
148  {
149  p.second.clear();
150  }
151  }
152  // ------------------------------------------------------------------------
153  void cleanMaterialMap()
154  {
155  m_material_map.clear();
156  m_flips_material.clear();
157  }
158 
159 };
160 
161 #endif
162 
163 #endif
Definition: cpu_particle_manager.hpp:77
Definition: cpu_particle_manager.hpp:43
Definition: three_d_animation.hpp:32
Definition: stk_particle.hpp:32
Utility class, you can inherit from this class to disallow the assignment operator and copy construct...
Definition: no_copy.hpp:25
Definition: material.hpp:47
Definition: singleton.hpp:86
Definition: cpu_particle_manager.hpp:80