]> git.lizzy.rs Git - dragonfireclient.git/blob - src/client/particles.h
Initial Commit
[dragonfireclient.git] / src / client / particles.h
1 /*
2 Minetest
3 Copyright (C) 2013 celeron55, Perttu Ahola <celeron55@gmail.com>
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU Lesser General Public License as published by
7 the Free Software Foundation; either version 2.1 of the License, or
8 (at your option) any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13 GNU Lesser General Public License for more details.
14
15 You should have received a copy of the GNU Lesser General Public License along
16 with this program; if not, write to the Free Software Foundation, Inc.,
17 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 */
19
20 #pragma once
21
22 #include <iostream>
23 #include "irrlichttypes_extrabloated.h"
24 #include "client/tile.h"
25 #include "localplayer.h"
26 #include "tileanimation.h"
27
28 struct ClientEvent;
29 class ParticleManager;
30 class ClientEnvironment;
31 struct MapNode;
32 struct ContentFeatures;
33
34 class Particle : public scene::ISceneNode
35 {
36         public:
37         Particle(
38                 IGameDef* gamedef,
39                 LocalPlayer *player,
40                 ClientEnvironment *env,
41                 v3f pos,
42                 v3f velocity,
43                 v3f acceleration,
44                 float expirationtime,
45                 float size,
46                 bool collisiondetection,
47                 bool collision_removal,
48                 bool object_collision,
49                 bool vertical,
50                 video::ITexture *texture,
51                 v2f texpos,
52                 v2f texsize,
53                 const struct TileAnimationParams &anim,
54                 u8 glow,
55                 video::SColor color = video::SColor(0xFFFFFFFF)
56         );
57         ~Particle() = default;
58
59         virtual const aabb3f &getBoundingBox() const
60         {
61                 return m_box;
62         }
63
64         virtual u32 getMaterialCount() const
65         {
66                 return 1;
67         }
68
69         virtual video::SMaterial& getMaterial(u32 i)
70         {
71                 return m_material;
72         }
73
74         virtual void OnRegisterSceneNode();
75         virtual void render();
76
77         void step(float dtime);
78
79         bool get_expired ()
80         { return m_expiration < m_time; }
81
82 private:
83         void updateLight();
84         void updateVertices();
85
86         video::S3DVertex m_vertices[4];
87         float m_time = 0.0f;
88         float m_expiration;
89
90         ClientEnvironment *m_env;
91         IGameDef *m_gamedef;
92         aabb3f m_box;
93         aabb3f m_collisionbox;
94         video::SMaterial m_material;
95         v2f m_texpos;
96         v2f m_texsize;
97         v3f m_pos;
98         v3f m_velocity;
99         v3f m_acceleration;
100         LocalPlayer *m_player;
101         float m_size;
102         //! Color without lighting
103         video::SColor m_base_color;
104         //! Final rendered color
105         video::SColor m_color;
106         bool m_collisiondetection;
107         bool m_collision_removal;
108         bool m_object_collision;
109         bool m_vertical;
110         v3s16 m_camera_offset;
111         struct TileAnimationParams m_animation;
112         float m_animation_time = 0.0f;
113         int m_animation_frame = 0;
114         u8 m_glow;
115 };
116
117 class ParticleSpawner
118 {
119 public:
120         ParticleSpawner(IGameDef* gamedef,
121                 LocalPlayer *player,
122                 u16 amount,
123                 float time,
124                 v3f minp, v3f maxp,
125                 v3f minvel, v3f maxvel,
126                 v3f minacc, v3f maxacc,
127                 float minexptime, float maxexptime,
128                 float minsize, float maxsize,
129                 bool collisiondetection,
130                 bool collision_removal,
131                 bool object_collision,
132                 u16 attached_id,
133                 bool vertical,
134                 video::ITexture *texture,
135                 const struct TileAnimationParams &anim, u8 glow,
136                 ParticleManager* p_manager);
137
138         ~ParticleSpawner() = default;
139
140         void step(float dtime, ClientEnvironment *env);
141
142         bool get_expired ()
143         { return (m_amount <= 0) && m_spawntime != 0; }
144
145 private:
146         void spawnParticle(ClientEnvironment *env, float radius,
147                 const core::matrix4 *attached_absolute_pos_rot_matrix);
148
149         ParticleManager *m_particlemanager;
150         float m_time;
151         IGameDef *m_gamedef;
152         LocalPlayer *m_player;
153         u16 m_amount;
154         float m_spawntime;
155         v3f m_minpos;
156         v3f m_maxpos;
157         v3f m_minvel;
158         v3f m_maxvel;
159         v3f m_minacc;
160         v3f m_maxacc;
161         float m_minexptime;
162         float m_maxexptime;
163         float m_minsize;
164         float m_maxsize;
165         video::ITexture *m_texture;
166         std::vector<float> m_spawntimes;
167         bool m_collisiondetection;
168         bool m_collision_removal;
169         bool m_object_collision;
170         bool m_vertical;
171         u16 m_attached_id;
172         struct TileAnimationParams m_animation;
173         u8 m_glow;
174 };
175
176 /**
177  * Class doing particle as well as their spawners handling
178  */
179 class ParticleManager
180 {
181 friend class ParticleSpawner;
182 public:
183         ParticleManager(ClientEnvironment* env);
184         ~ParticleManager();
185
186         void step (float dtime);
187
188         void handleParticleEvent(ClientEvent *event, Client *client,
189                         LocalPlayer *player);
190
191         void addDiggingParticles(IGameDef *gamedef, LocalPlayer *player, v3s16 pos,
192                 const MapNode &n, const ContentFeatures &f);
193
194         void addNodeParticle(IGameDef *gamedef, LocalPlayer *player, v3s16 pos,
195                 const MapNode &n, const ContentFeatures &f);
196
197         /**
198          * This function is only used by client particle spawners
199          *
200          * We don't need to check the particle spawner list because client ID will n
201          * ever overlap (u64)
202          * @return new id
203          */
204         u64 generateSpawnerId()
205         {
206                 return m_next_particle_spawner_id++;
207         }
208
209 protected:
210         void addParticle(Particle* toadd);
211
212 private:
213
214         void stepParticles(float dtime);
215         void stepSpawners(float dtime);
216
217         void clearAll();
218
219         std::vector<Particle*> m_particles;
220         std::unordered_map<u64, ParticleSpawner*> m_particle_spawners;
221         // Start the particle spawner ids generated from here after u32_max. lower values are
222         // for server sent spawners.
223         u64 m_next_particle_spawner_id = U32_MAX + 1;
224
225         ClientEnvironment* m_env;
226         std::mutex m_particle_list_lock;
227         std::mutex m_spawner_list_lock;
228 };