TrinityCore
Position.cpp
Go to the documentation of this file.
1/*
2 * This file is part of the TrinityCore Project. See AUTHORS file for Copyright information
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms of the GNU General Public License as published by the
6 * Free Software Foundation; either version 2 of the License, or (at your
7 * option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12 * more details.
13 *
14 * You should have received a copy of the GNU General Public License along
15 * with this program. If not, see <http://www.gnu.org/licenses/>.
16 */
17
18#include "Position.h"
19#include "ByteBuffer.h"
20#include "DB2Stores.h"
21#include "GridDefines.h"
22#include "World.h"
23#include <G3D/g3dmath.h>
24#include <sstream>
25
26bool Position::operator==(Position const& a) const
27{
28 return (G3D::fuzzyEq(a.m_positionX, m_positionX) &&
29 G3D::fuzzyEq(a.m_positionY, m_positionY) &&
30 G3D::fuzzyEq(a.m_positionZ, m_positionZ) &&
31 G3D::fuzzyEq(a.m_orientation, m_orientation));
32}
33
35{
36 m_positionX = GetPositionX() + (offset.GetPositionX() * std::cos(GetOrientation()) + offset.GetPositionY() * std::sin(GetOrientation() + float(M_PI)));
37 m_positionY = GetPositionY() + (offset.GetPositionY() * std::cos(GetOrientation()) + offset.GetPositionX() * std::sin(GetOrientation()));
40}
41
43{
45}
46
47void Position::GetPositionOffsetTo(Position const& endPos, Position& retOffset) const
48{
49 float dx = endPos.GetPositionX() - GetPositionX();
50 float dy = endPos.GetPositionY() - GetPositionY();
51
52 retOffset.m_positionX = dx * std::cos(GetOrientation()) + dy * std::sin(GetOrientation());
53 retOffset.m_positionY = dy * std::cos(GetOrientation()) - dx * std::sin(GetOrientation());
54 retOffset.m_positionZ = endPos.GetPositionZ() - GetPositionZ();
55 retOffset.SetOrientation(endPos.GetOrientation() - GetOrientation());
56}
57
59{
60 Position ret(*this);
61 ret.RelocateOffset(offset);
62 return ret;
63}
64
65bool Position::IsWithinBox(Position const& center, float xradius, float yradius, float zradius) const
66{
67 // rotate the WorldObject position instead of rotating the whole cube, that way we can make a simplified
68 // is-in-cube check and we have to calculate only one point instead of 4
69
70 // 2PI = 360*, keep in mind that ingame orientation is counter-clockwise
71 double rotation = 2 * M_PI - center.GetOrientation();
72 double sinVal = std::sin(rotation);
73 double cosVal = std::cos(rotation);
74
75 float BoxDistX = GetPositionX() - center.GetPositionX();
76 float BoxDistY = GetPositionY() - center.GetPositionY();
77
78 float rotX = float(center.GetPositionX() + BoxDistX * cosVal - BoxDistY*sinVal);
79 float rotY = float(center.GetPositionY() + BoxDistY * cosVal + BoxDistX*sinVal);
80
81 // box edges are parallel to coordiante axis, so we can treat every dimension independently :D
82 float dz = GetPositionZ() - center.GetPositionZ();
83 float dx = rotX - center.GetPositionX();
84 float dy = rotY - center.GetPositionY();
85 if ((std::fabs(dx) > xradius) ||
86 (std::fabs(dy) > yradius) ||
87 (std::fabs(dz) > zradius))
88 return false;
89
90 return true;
91}
92
93bool Position::IsWithinDoubleVerticalCylinder(Position const* center, float radius, float height) const
94{
95 float verticalDelta = GetPositionZ() - center->GetPositionZ();
96 return IsInDist2d(center, radius) && std::abs(verticalDelta) <= height;
97}
98
99bool Position::HasInArc(float arc, Position const* obj, float border) const
100{
101 // always have self in arc
102 if (obj == this)
103 return true;
104
105 // move arc to range 0.. 2*pi
106 arc = NormalizeOrientation(arc);
107
108 // move angle to range -pi ... +pi
109 float angle = GetRelativeAngle(obj);
110 if (angle > float(M_PI))
111 angle -= 2.0f * float(M_PI);
112
113 float lborder = -1 * (arc / border); // in range -pi..0
114 float rborder = (arc / border); // in range 0..pi
115 return ((angle >= lborder) && (angle <= rborder));
116}
117
118bool Position::HasInLine(Position const* pos, float objSize, float width) const
119{
120 if (!HasInArc(float(M_PI), pos, 2.0f))
121 return false;
122
123 width += objSize;
124 float angle = GetRelativeAngle(pos);
125 return std::fabs(std::sin(angle)) * GetExactDist2d(pos->GetPositionX(), pos->GetPositionY()) < width;
126}
127
128std::string Position::ToString() const
129{
130 std::stringstream sstr;
131 sstr << "X: " << m_positionX << " Y: " << m_positionY << " Z: " << m_positionZ << " O: " << m_orientation;
132 return sstr.str();
133}
134
136{
137 // fmod only supports positive numbers. Thus we have
138 // to emulate negative numbers
139 if (o < 0)
140 {
141 float mod = o *-1;
142 mod = std::fmod(mod, 2.0f * static_cast<float>(M_PI));
143 mod = -mod + 2.0f * static_cast<float>(M_PI);
144 return mod;
145 }
146 return std::fmod(o, 2.0f * static_cast<float>(M_PI));
147}
148
150{
151 buf << streamer.Pos->GetPositionX();
152 buf << streamer.Pos->GetPositionY();
153 return buf;
154}
155
157{
158 float x, y;
159 buf >> x >> y;
160 streamer.Pos->Relocate(x, y);
161 return buf;
162}
163
165{
166 buf << streamer.Pos->GetPositionX();
167 buf << streamer.Pos->GetPositionY();
168 buf << streamer.Pos->GetPositionZ();
169 return buf;
170}
171
173{
174 float x, y, z;
175 buf >> x >> y >> z;
176 streamer.Pos->Relocate(x, y, z);
177 return buf;
178}
179
181{
182 buf << streamer.Pos->GetPositionX();
183 buf << streamer.Pos->GetPositionY();
184 buf << streamer.Pos->GetPositionZ();
185 buf << streamer.Pos->GetOrientation();
186 return buf;
187}
188
190{
191 float x, y, z, o;
192 buf >> x >> y >> z >> o;
193 streamer.Pos->Relocate(x, y, z, o);
194 return buf;
195}
196
198{
199 buf.appendPackXYZ(streamer.Pos->GetPositionX(), streamer.Pos->GetPositionY(), streamer.Pos->GetPositionZ());
200 return buf;
201}
202
204{
205 std::stringstream sstr;
206 MapEntry const* mapEntry = sMapStore.LookupEntry(m_mapId);
207 sstr << "MapID: " << m_mapId << " Map name: '" << (mapEntry ? mapEntry->MapName[sWorld->GetDefaultDbcLocale()] : "<not found>") <<"' " << Position::ToString();
208 return sstr.str();
209}
#define M_PI
Definition: Common.h:115
DB2Storage< MapEntry > sMapStore("Map.db2", &MapLoadInfo::Instance)
ByteBuffer & operator>>(ByteBuffer &buf, Position::Streamer< Position::XY > const &streamer)
Definition: Position.cpp:156
ByteBuffer & operator<<(ByteBuffer &buf, Position::ConstStreamer< Position::XY > const &streamer)
Definition: Position.cpp:149
void appendPackXYZ(float x, float y, float z)
Definition: ByteBuffer.h:583
std::string GetDebugInfo() const
Definition: Position.cpp:203
uint32 m_mapId
Definition: Position.h:203
#define sWorld
Definition: World.h:931
bool IsValidMapCoord(float c)
Definition: GridDefines.h:231
LocalizedString MapName
Position const * Pos
Definition: Position.h:42
Position * Pos
Definition: Position.h:50
constexpr void SetOrientation(float orientation)
Definition: Position.h:71
constexpr float GetPositionX() const
Definition: Position.h:76
float m_positionZ
Definition: Position.h:55
constexpr float GetPositionY() const
Definition: Position.h:77
float GetExactDist2d(const float x, const float y) const
Definition: Position.h:106
float GetRelativeAngle(float x, float y) const
Definition: Position.h:136
constexpr bool IsInDist2d(float x, float y, float dist) const
Definition: Position.h:140
std::string ToString() const
Definition: Position.cpp:128
static float NormalizeOrientation(float o)
Definition: Position.cpp:135
Position GetPositionWithOffset(Position const &offset) const
Definition: Position.cpp:58
float m_positionX
Definition: Position.h:53
float m_positionY
Definition: Position.h:54
bool HasInLine(Position const *pos, float objSize, float width) const
Definition: Position.cpp:118
bool HasInArc(float arcangle, Position const *pos, float border=2.0f) const
Definition: Position.cpp:99
bool IsPositionValid() const
Definition: Position.cpp:42
bool IsWithinDoubleVerticalCylinder(Position const *center, float radius, float height) const
Definition: Position.cpp:93
bool IsWithinBox(Position const &center, float xradius, float yradius, float zradius) const
Definition: Position.cpp:65
bool operator==(Position const &a) const
Definition: Position.cpp:26
constexpr void Relocate(float x, float y)
Definition: Position.h:63
float m_orientation
Definition: Position.h:58
void GetPositionOffsetTo(Position const &endPos, Position &retOffset) const
Definition: Position.cpp:47
void RelocateOffset(Position const &offset)
Definition: Position.cpp:34
constexpr float GetOrientation() const
Definition: Position.h:79
constexpr float GetPositionZ() const
Definition: Position.h:78