1 ////////////////////////////////////////////////////////////////////////////////
2 // Scorched3D (c) 2000-2011
3 //
4 // This file is part of Scorched3D.
5 //
6 // Scorched3D is free software; you can redistribute it and/or modify
7 // it under the terms of the GNU General Public License as published by
8 // the Free Software Foundation; either version 2 of the License, or
9 // (at your option) any later version.
10 //
11 // Scorched3D is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 // GNU General Public License for more details.
15 //
16 // You should have received a copy of the GNU General Public License along
17 // with this program; if not, write to the Free Software Foundation, Inc.,
18 // 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
19 ////////////////////////////////////////////////////////////////////////////////
20
21 #include <sprites/ExplosionNukeRenderer.h>
22 #include <sprites/ExplosionTextures.h>
23 #include <client/ScorchedClient.h>
24 #include <common/Defines.h>
25 #include <graph/OptionsDisplay.h>
26 #include <landscape/Landscape.h>
27 #include <landscapemap/LandscapeMaps.h>
28 #include <math.h>
29
30 static const int AlphaSteps = int(ExplosionNukeRenderer_STEPS * 0.9f);
31
ExplosionNukeRendererEntry(Vector & position,float size)32 ExplosionNukeRendererEntry::ExplosionNukeRendererEntry(
33 Vector &position, float size) :
34 totalTime_(0.0f), size_(size),
35 startPosition_(position), cloudRotation_(0.0f)
36 {
37 float rot = RAND * 3.14f * 2.0f;
38 float width = RAND * 0.5f + 1.0f;
39
40 cloudRotation_ = RAND * 360.0f;
41 rotation_[0] = getFastSin(rot) * width;
42 rotation_[1] = getFastCos(rot) * width;
43 }
44
~ExplosionNukeRendererEntry()45 ExplosionNukeRendererEntry::~ExplosionNukeRendererEntry()
46 {
47 }
48
simulate(Particle * particle,float time)49 void ExplosionNukeRendererEntry::simulate(Particle *particle, float time)
50 {
51 totalTime_ += time;
52 cloudRotation_ += time * 5.0f;
53
54 int position = int((totalTime_ / (16.0f / 3.0f)) *
55 float(ExplosionNukeRenderer_STEPS));
56 if (position >= ExplosionNukeRenderer_STEPS)
57 position = ExplosionNukeRenderer_STEPS - 1;
58
59 float z = ExplosionNukeRenderer::positions_[position][2] * (10.0f + size_) / 30.0f;
60 float w = ExplosionNukeRenderer::positions_[position][0] + (size_ / 2.0f);
61 particle->position_[0] = startPosition_[0] + rotation_[0] * w;
62 particle->position_[1] = startPosition_[1] + rotation_[1] * w;
63 particle->position_[2] = startPosition_[2] + z;
64 }
65
66 Vector *ExplosionNukeRenderer::positions_ = 0;
67
ExplosionNukeRenderer(Vector & position,float size,GLTextureSet * set,bool animate)68 ExplosionNukeRenderer::ExplosionNukeRenderer(Vector &position, float size,
69 GLTextureSet *set,
70 bool animate)
71 : set_(set), animate_(animate), totalTime_(0.0f), time_(0.0f), position_(position), size_(size)
72 {
73 position_[2] -= size_;
74 float height = ScorchedClient::instance()->getLandscapeMaps().
75 getGroundMaps().getHeight((int) position_[0], (int) position_[1]).asFloat();
76 if (position_[2] < height) position_[2] = height;
77
78 if (!positions_)
79 {
80 positions_ = new Vector[ExplosionNukeRenderer_STEPS];
81
82 float zPos = 0.0f;
83 float width = 0.0f;
84
85 for (int i=0; i<ExplosionNukeRenderer_STEPS; i++)
86 {
87 Vector pos;
88 pos[0] = width;
89 pos[1] = 0.0f;
90 pos[2] = zPos;
91
92 if (i > (ExplosionNukeRenderer_STEPS * (0.3f))){
93 width += 0.5f;
94
95 }else{
96
97 zPos += 2.0f;
98 }
99
100 positions_[i] = pos;
101 }
102 }
103
104 emitter_.setAttributes(
105 5.0f, 5.0f, // Life
106 0.2f, 0.5f, // Mass
107 0.01f, 0.02f, // Friction
108 Vector(0.0f, 0.0f, 0.0f), Vector(0.0f, 0.0f, 0.0f), // Velocity
109 Vector(1.0f, 1.0f, 1.0f), 0.3f, // StartColor1
110 Vector(1.0f, 1.0f, 1.0f), 0.2f, // StartColor2
111 Vector(1.0f, 1.0f, 1.0f), 0.0f, // EndColor1
112 Vector(1.0f, 1.0f, 1.0f), 0.0f, // EndColor2
113 2.0f, 2.0f, 3.0f, 3.0f, // Start Size
114 4.0f, 4.0f, 6.0f, 6.0f, // EndSize
115 Vector(0.0f, 0.0f, 100.0f), // Gravity
116 false,
117 false);
118 }
119
~ExplosionNukeRenderer()120 ExplosionNukeRenderer::~ExplosionNukeRenderer()
121 {
122 }
123
draw(Action * action)124 void ExplosionNukeRenderer::draw(Action *action)
125 {
126 }
127
simulate(Action * action,float frameTime,bool & remove)128 void ExplosionNukeRenderer::simulate(Action *action, float frameTime, bool &remove)
129 {
130 float AddSmokeTime = 0.08f;
131 int SmokesPerTime = 14;
132 if (OptionsDisplay::instance()->getEffectsDetail() == 0)
133 {
134 SmokesPerTime = 8;
135 }
136 else if (OptionsDisplay::instance()->getEffectsDetail() == 2)
137 {
138 SmokesPerTime = 18;
139 }
140
141 totalTime_ += frameTime;
142 time_ += frameTime;
143
144 while (time_ > AddSmokeTime)
145 {
146 time_ -= AddSmokeTime;
147
148 // Add any new entries
149 if (totalTime_ > 1.25f)
150 {
151 if (totalTime_ < 2.25f)
152 {
153 emitter_.emitMushroom(
154 position_,
155 ScorchedClient::instance()->getParticleEngine(),
156 SmokesPerTime,
157 size_,
158 set_,
159 animate_);
160 }
161 else remove = true;
162 }
163 }
164 }
165