Project SkyFire Core
SkyFire 5.4.8 server core API documentation
Toggle main menu visibility
Loading...
Searching...
No Matches
MoveSpline.cpp
Go to the documentation of this file.
1
/*
2
* This file is part of Project SkyFire https://www.projectskyfire.org.
3
* See LICENSE.md file for Copyright information
4
*/
5
6
#include "
Creature.h
"
7
#include "
Log.h
"
8
#include "
MoveSpline.h
"
9
#include <sstream>
10
11
namespace
Movement
{
12
13
Location
MoveSpline::ComputePosition
()
const
14
{
15
ASSERT
(
Initialized
());
16
17
float
u = 1.f;
18
int32
seg_time =
spline
.length(
point_Idx
,
point_Idx
+ 1);
19
if
(seg_time > 0)
20
u = (
time_passed
-
spline
.length(
point_Idx
)) / (float)seg_time;
21
Location
c;
22
c.
orientation
=
initialOrientation
;
23
spline
.evaluate_percent(
point_Idx
, u, c);
24
25
if
(
splineflags
.animation);
// MoveSplineFlag::Animation disables falling or parabolic movement
26
else
if
(
splineflags
.parabolic)
27
computeParabolicElevation
(c.z);
28
else
if
(
splineflags
.falling)
29
computeFallElevation
(c.z);
30
31
if
(
splineflags
.done &&
splineflags
.isFacing())
32
{
33
if
(
splineflags
.final_angle)
34
c.
orientation
=
facing
.angle;
35
else
if
(
splineflags
.final_point)
36
c.
orientation
= atan2(
facing
.f.y - c.y,
facing
.f.x - c.x);
37
//nothing to do for MoveSplineFlag::Final_Target flag
38
}
39
else
40
{
41
if
(!
splineflags
.hasFlag(
MoveSplineFlag::OrientationFixed
|
MoveSplineFlag::Falling
|
MoveSplineFlag::Unknown0
))
42
{
43
Vector3 hermite;
44
spline
.evaluate_derivative(
point_Idx
, u, hermite);
45
c.
orientation
= atan2(hermite.y, hermite.x);
46
}
47
48
if
(
splineflags
.orientationInversed)
49
c.
orientation
= -c.
orientation
;
50
}
51
return
c;
52
}
53
54
void
MoveSpline::computeParabolicElevation
(
float
& el)
const
55
{
56
if
(
time_passed
>
effect_start_time
)
57
{
58
float
t_passedf =
MSToSec
(
time_passed
-
effect_start_time
);
59
float
t_durationf =
MSToSec
(
Duration
() -
effect_start_time
);
//client use not modified duration here
60
61
// -a*x*x + bx + c:
62
//(dur * v3->z_acceleration * dt)/2 - (v3->z_acceleration * dt * dt)/2 + Z;
63
el += (t_durationf - t_passedf) * 0.5f *
vertical_acceleration
* t_passedf;
64
}
65
}
66
67
void
MoveSpline::computeFallElevation
(
float
& el)
const
68
{
69
float
z_now =
spline
.getPoint(
spline
.first()).z -
Movement::computeFallElevation
(
MSToSec
(
time_passed
),
false
);
70
float
final_z =
FinalDestination
().z;
71
el = std::max(z_now, final_z);
72
}
73
74
inline
uint32
computeDuration
(
float
length,
float
velocity)
75
{
76
return
SecToMS
(length / velocity);
77
}
78
79
struct
FallInitializer
80
{
81
explicit
FallInitializer
(
float
_start_elevation) :
start_elevation
(_start_elevation) { }
82
float
start_elevation
;
83
inline
int32
operator()
(
Spline<int32>
& s,
int32
i)
84
{
85
return
Movement::computeFallTime
(
start_elevation
- s.
getPoint
(i + 1).z,
false
) * 1000.f;
86
}
87
};
88
89
enum
{
90
minimal_duration
= 1
91
};
92
93
struct
CommonInitializer
94
{
95
explicit
CommonInitializer
(
float
_velocity) :
velocityInv
(1000.f / _velocity),
time
(
minimal_duration
) { }
96
float
velocityInv
;
97
int32
time
;
98
inline
int32
operator()
(
Spline<int32>
& s,
int32
i)
99
{
100
time
+= (s.
SegLength
(i) *
velocityInv
);
101
return
time
;
102
}
103
};
104
105
void
MoveSpline::init_spline
(
const
MoveSplineInitArgs
& args)
106
{
107
const
SplineBase::EvaluationMode
modes[2] = {
SplineBase::ModeLinear
,
SplineBase::ModeCatmullrom
};
108
if
(args.
flags
.
cyclic
)
109
{
110
uint32
cyclic_point = 0;
111
// MoveSplineFlag::Enter_Cycle support dropped
112
//if (splineflags & SPLINEFLAG_ENTER_CYCLE)
113
//cyclic_point = 1; // shouldn't be modified, came from client
114
spline
.init_cyclic_spline(&args.
path
[0], args.
path
.size(), modes[args.
flags
.
isSmooth
()], cyclic_point);
115
}
116
else
117
{
118
spline
.init_spline(&args.
path
[0], args.
path
.size(), modes[args.
flags
.
isSmooth
()]);
119
}
120
121
// init spline timestamps
122
if
(
splineflags
.falling)
123
{
124
FallInitializer
init(
spline
.getPoint(
spline
.first()).z);
125
spline
.initLengths(init);
126
}
127
else
128
{
129
CommonInitializer
init(args.
velocity
);
130
spline
.initLengths(init);
131
}
132
134
if
(
spline
.length() <
minimal_duration
)
135
{
136
SF_LOG_ERROR
(
"misc"
,
"MoveSpline::init_spline: zero length spline, wrong input data?"
);
137
spline
.set_length(
spline
.last(),
spline
.isCyclic() ? 1000 : 1);
138
}
139
point_Idx
=
spline
.first();
140
}
141
142
void
MoveSpline::Initialize
(
MoveSplineInitArgs
const
& args)
143
{
144
splineflags
= args.
flags
;
145
facing
= args.
facing
;
146
m_Id
= args.
splineId
;
147
point_Idx_offset
= args.
path_Idx_offset
;
148
initialOrientation
= args.
initialOrientation
;
149
150
time_passed
= 0;
151
vertical_acceleration
= 0.f;
152
effect_start_time
= 0;
153
154
// Check if its a stop spline
155
if
(args.
flags
.
done
)
156
{
157
spline
.clear();
158
return
;
159
}
160
161
init_spline
(args);
162
163
// init parabolic / animation
164
// spline initialized, duration known and i able to compute parabolic acceleration
165
if
(args.
flags
& (
MoveSplineFlag::Parabolic
|
MoveSplineFlag::Animation
))
166
{
167
effect_start_time
=
Duration
() * args.
time_perc
;
168
if
(args.
flags
.
parabolic
&&
effect_start_time
<
Duration
())
169
{
170
float
f_duration =
MSToSec
(
Duration
() -
effect_start_time
);
171
vertical_acceleration
= args.
parabolic_amplitude
* 8.f / (f_duration * f_duration);
172
}
173
}
174
}
175
176
MoveSpline::MoveSpline
() :
m_Id
(0),
time_passed
(0),
177
vertical_acceleration
(0.f),
initialOrientation
(0.f),
effect_start_time
(0),
point_Idx
(0),
point_Idx_offset
(0),
178
onTransport
(false)
179
{
180
splineflags
.done =
true
;
181
}
182
184
185
bool
MoveSplineInitArgs::Validate
(
Unit
* unit)
const
186
{
187
#define CHECK(exp) \
188
if (!(exp))\
189
{\
190
SF_LOG_ERROR("misc", "MoveSplineInitArgs::Validate: expression '%s' failed for GUID: %u Entry: %u", #exp, unit->GetTypeId() == TypeID::TYPEID_PLAYER ? unit->GetGUIDLow() : unit->ToCreature()->GetDBTableGUIDLow(), unit->GetEntry());\
191
return false;\
192
}
193
CHECK
(
path
.size() > 1);
194
CHECK
(
velocity
> 0.1f);
195
CHECK
(
time_perc
>= 0.f &&
time_perc
<= 1.f);
196
//CHECK(_checkPathBounds());
197
return
true
;
198
#undef CHECK
199
}
200
201
// MONSTER_MOVE packet format limitation for not CatmullRom movement:
202
// each vertex offset packed into 11 bytes
203
bool
MoveSplineInitArgs::_checkPathBounds
()
const
204
{
205
if
(!(
flags
&
MoveSplineFlag::Catmullrom
) &&
path
.size() > 2)
206
{
207
enum
{
208
MAX_OFFSET = (1 << 11) / 2
209
};
210
Vector3 middle = (
path
.front() +
path
.back()) / 2;
211
Vector3 offset;
212
for
(
uint32
i = 1; i <
path
.size() - 1; ++i)
213
{
214
offset =
path
[i] - middle;
215
if
(fabs(offset.x) >=
float
(MAX_OFFSET) || fabs(offset.y) >=
float
(MAX_OFFSET) || fabs(offset.z) >=
float
(MAX_OFFSET))
216
{
217
SF_LOG_ERROR
(
"misc"
,
"MoveSplineInitArgs::_checkPathBounds check failed"
);
218
return
false
;
219
}
220
}
221
}
222
return
true
;
223
}
224
226
227
MoveSpline::UpdateResult
MoveSpline::_updateState
(
int32
& ms_time_diff)
228
{
229
if
(
Finalized
())
230
{
231
ms_time_diff = 0;
232
return
Result_Arrived
;
233
}
234
235
UpdateResult
result =
Result_None
;
236
237
int32
minimal_diff = std::min(ms_time_diff,
segment_time_elapsed
());
238
ASSERT
(minimal_diff >= 0);
239
time_passed
+= minimal_diff;
240
ms_time_diff -= minimal_diff;
241
242
if
(
time_passed
>=
next_timestamp
())
243
{
244
++
point_Idx
;
245
if
(
point_Idx
<
spline
.last())
246
{
247
result =
Result_NextSegment
;
248
}
249
else
250
{
251
if
(
spline
.isCyclic())
252
{
253
point_Idx
=
spline
.first();
254
time_passed
=
time_passed
%
Duration
();
255
result =
Result_NextCycle
;
256
}
257
else
258
{
259
_Finalize
();
260
ms_time_diff = 0;
261
result =
Result_Arrived
;
262
}
263
}
264
}
265
266
return
result;
267
}
268
269
std::string
MoveSpline::ToString
()
const
270
{
271
std::stringstream str;
272
str <<
"MoveSpline"
<< std::endl;
273
str <<
"spline Id: "
<<
GetId
() << std::endl;
274
str <<
"flags: "
<<
splineflags
.ToString() << std::endl;
275
if
(
splineflags
.final_angle)
276
str <<
"facing angle: "
<<
facing
.angle;
277
else
if
(
splineflags
.final_target)
278
str <<
"facing target: "
<<
facing
.target;
279
else
if
(
splineflags
.final_point)
280
str <<
"facing point: "
<<
facing
.f.x <<
" "
<<
facing
.f.y <<
" "
<<
facing
.f.z;
281
str << std::endl;
282
str <<
"time passed: "
<<
time_passed
<< std::endl;
283
str <<
"total time: "
<<
Duration
() << std::endl;
284
str <<
"spline point Id: "
<<
point_Idx
<< std::endl;
285
str <<
"path point Id: "
<<
currentPathIdx
() << std::endl;
286
str <<
spline
.ToString();
287
return
str.str();
288
}
289
290
void
MoveSpline::_Finalize
()
291
{
292
splineflags
.done =
true
;
293
point_Idx
=
spline
.last() - 1;
294
time_passed
=
Duration
();
295
}
296
297
int32
MoveSpline::currentPathIdx
()
const
298
{
299
int32
point =
point_Idx_offset
+
point_Idx
-
spline
.first() + (int)
Finalized
();
300
if
(
isCyclic
())
301
point = point % (
spline
.last() -
spline
.first());
302
return
point;
303
}
304
}
Creature.h
int32
std::int32_t int32
Definition
Define.h:73
uint32
std::uint32_t uint32
Definition
Define.h:77
ASSERT
#define ASSERT
Definition
Errors.h:29
Log.h
SF_LOG_ERROR
#define SF_LOG_ERROR(filterType__,...)
Definition
Log.h:143
CHECK
#define CHECK(exp)
MoveSpline.h
Movement::MoveSplineFlag::parabolic
bool parabolic
Definition
MoveSplineFlag.h:126
Movement::MoveSplineFlag::cyclic
bool cyclic
Definition
MoveSplineFlag.h:113
Movement::MoveSplineFlag::isSmooth
bool isSmooth() const
Definition
MoveSplineFlag.h:76
Movement::MoveSplineFlag::OrientationFixed
@ OrientationFixed
Definition
MoveSplineFlag.h:34
Movement::MoveSplineFlag::Parabolic
@ Parabolic
Definition
MoveSplineFlag.h:49
Movement::MoveSplineFlag::Unknown0
@ Unknown0
Definition
MoveSplineFlag.h:27
Movement::MoveSplineFlag::Catmullrom
@ Catmullrom
Definition
MoveSplineFlag.h:35
Movement::MoveSplineFlag::Falling
@ Falling
Definition
MoveSplineFlag.h:30
Movement::MoveSplineFlag::Animation
@ Animation
Definition
MoveSplineFlag.h:48
Movement::MoveSplineFlag::done
bool done
Definition
MoveSplineFlag.h:106
Movement::MoveSpline::next_timestamp
int32 next_timestamp() const
Definition
MoveSpline.h:67
Movement::MoveSpline::isCyclic
bool isCyclic() const
Definition
MoveSpline.h:105
Movement::MoveSpline::MoveSpline
MoveSpline()
Definition
MoveSpline.cpp:176
Movement::MoveSpline::ToString
std::string ToString() const
Definition
MoveSpline.cpp:269
Movement::MoveSpline::_updateState
UpdateResult _updateState(int32 &ms_time_diff)
============================================================================================
Definition
MoveSpline.cpp:227
Movement::MoveSpline::Initialize
void Initialize(const MoveSplineInitArgs &)
Definition
MoveSpline.cpp:142
Movement::MoveSpline::ComputePosition
Location ComputePosition() const
Definition
MoveSpline.cpp:13
Movement::MoveSpline::_Finalize
void _Finalize()
Definition
MoveSpline.cpp:290
Movement::MoveSpline::GetId
uint32 GetId() const
Definition
MoveSpline.h:103
Movement::MoveSpline::time_passed
int32 time_passed
Definition
MoveSpline.h:49
Movement::MoveSpline::computeFallElevation
void computeFallElevation(float &el) const
Definition
MoveSpline.cpp:67
Movement::MoveSpline::Finalized
bool Finalized() const
Definition
MoveSpline.h:104
Movement::MoveSpline::FinalDestination
Vector3 FinalDestination() const
Definition
MoveSpline.h:107
Movement::MoveSpline::effect_start_time
int32 effect_start_time
Definition
MoveSpline.h:55
Movement::MoveSpline::UpdateResult
UpdateResult
Definition
MoveSpline.h:32
Movement::MoveSpline::Result_NextSegment
@ Result_NextSegment
Definition
MoveSpline.h:36
Movement::MoveSpline::Result_Arrived
@ Result_Arrived
Definition
MoveSpline.h:34
Movement::MoveSpline::Result_NextCycle
@ Result_NextCycle
Definition
MoveSpline.h:35
Movement::MoveSpline::Result_None
@ Result_None
Definition
MoveSpline.h:33
Movement::MoveSpline::currentPathIdx
int32 currentPathIdx() const
Definition
MoveSpline.cpp:297
Movement::MoveSpline::spline
MySpline spline
Definition
MoveSpline.h:41
Movement::MoveSpline::vertical_acceleration
float vertical_acceleration
Definition
MoveSpline.h:53
Movement::MoveSpline::Duration
int32 Duration() const
Definition
MoveSpline.h:73
Movement::MoveSpline::point_Idx
int32 point_Idx
Definition
MoveSpline.h:56
Movement::MoveSpline::Initialized
bool Initialized() const
Definition
MoveSpline.h:81
Movement::MoveSpline::m_Id
uint32 m_Id
Definition
MoveSpline.h:45
Movement::MoveSpline::segment_time_elapsed
int32 segment_time_elapsed() const
Definition
MoveSpline.h:68
Movement::MoveSpline::facing
FacingInfo facing
Definition
MoveSpline.h:43
Movement::MoveSpline::init_spline
void init_spline(const MoveSplineInitArgs &args)
Definition
MoveSpline.cpp:105
Movement::MoveSpline::computeParabolicElevation
void computeParabolicElevation(float &el) const
Definition
MoveSpline.cpp:54
Movement::MoveSpline::splineflags
MoveSplineFlag splineflags
Definition
MoveSpline.h:47
Movement::MoveSpline::onTransport
bool onTransport
Definition
MoveSpline.h:111
Movement::MoveSpline::initialOrientation
float initialOrientation
Definition
MoveSpline.h:54
Movement::MoveSpline::point_Idx_offset
int32 point_Idx_offset
Definition
MoveSpline.h:57
Movement::SplineBase::getPoint
const Vector3 & getPoint(index_type i) const
Definition
Spline.h:99
Movement::SplineBase::SegLength
float SegLength(index_type i) const
Definition
Spline.h:115
Movement::SplineBase::EvaluationMode
EvaluationMode
Definition
Spline.h:22
Movement::SplineBase::ModeCatmullrom
@ ModeCatmullrom
Definition
Spline.h:24
Movement::SplineBase::ModeLinear
@ ModeLinear
Definition
Spline.h:23
Movement::Spline
Definition
Spline.h:122
Unit
Definition
Unit.h:1367
Movement
Definition
Unit.h:365
Movement::computeDuration
uint32 computeDuration(float length, float velocity)
Definition
MoveSpline.cpp:74
Movement::minimal_duration
@ minimal_duration
Definition
MoveSpline.cpp:90
Movement::computeFallTime
float computeFallTime(float path_length, bool isSafeFall)
Definition
MovementUtil.cpp:24
Movement::SecToMS
uint32 SecToMS(float sec)
Definition
MovementTypedefs.h:24
Movement::computeFallElevation
float computeFallElevation(float t_passed, bool isSafeFall, float start_velocity=0.0f)
Definition
MovementUtil.cpp:48
Movement::MSToSec
float MSToSec(uint32 ms)
Definition
MovementTypedefs.h:29
Movement::CommonInitializer
Definition
MoveSpline.cpp:94
Movement::CommonInitializer::time
int32 time
Definition
MoveSpline.cpp:97
Movement::CommonInitializer::CommonInitializer
CommonInitializer(float _velocity)
Definition
MoveSpline.cpp:95
Movement::CommonInitializer::operator()
int32 operator()(Spline< int32 > &s, int32 i)
Definition
MoveSpline.cpp:98
Movement::CommonInitializer::velocityInv
float velocityInv
Definition
MoveSpline.cpp:96
Movement::FallInitializer
Definition
MoveSpline.cpp:80
Movement::FallInitializer::FallInitializer
FallInitializer(float _start_elevation)
Definition
MoveSpline.cpp:81
Movement::FallInitializer::operator()
int32 operator()(Spline< int32 > &s, int32 i)
Definition
MoveSpline.cpp:83
Movement::FallInitializer::start_elevation
float start_elevation
Definition
MoveSpline.cpp:82
Movement::Location
Definition
MoveSpline.h:15
Movement::Location::orientation
float orientation
Definition
MoveSpline.h:21
Movement::MoveSplineInitArgs
Definition
MoveSplineInitArgs.h:30
Movement::MoveSplineInitArgs::parabolic_amplitude
float parabolic_amplitude
Definition
MoveSplineInitArgs.h:43
Movement::MoveSplineInitArgs::Validate
bool Validate(Unit *unit) const
============================================================================================
Definition
MoveSpline.cpp:185
Movement::MoveSplineInitArgs::path
PointsArray path
Definition
MoveSplineInitArgs.h:38
Movement::MoveSplineInitArgs::path_Idx_offset
int32 path_Idx_offset
Definition
MoveSplineInitArgs.h:41
Movement::MoveSplineInitArgs::facing
FacingInfo facing
Definition
MoveSplineInitArgs.h:39
Movement::MoveSplineInitArgs::_checkPathBounds
bool _checkPathBounds() const
Definition
MoveSpline.cpp:203
Movement::MoveSplineInitArgs::initialOrientation
float initialOrientation
Definition
MoveSplineInitArgs.h:46
Movement::MoveSplineInitArgs::flags
MoveSplineFlag flags
Definition
MoveSplineInitArgs.h:40
Movement::MoveSplineInitArgs::splineId
uint32 splineId
Definition
MoveSplineInitArgs.h:45
Movement::MoveSplineInitArgs::velocity
float velocity
Definition
MoveSplineInitArgs.h:42
Movement::MoveSplineInitArgs::time_perc
float time_perc
Definition
MoveSplineInitArgs.h:44
src
server
game
Movement
Spline
MoveSpline.cpp
Generated on
for Project SkyFire Core by
1.17.0