mirror of
https://github.com/EQEmu/Server.git
synced 2025-12-17 22:51:30 +00:00
Merge branch 'master' of https://github.com/EQEmu/Server into feature/hot-reload
This commit is contained in:
commit
34005cd2ed
@ -35,6 +35,7 @@ static const uint32 MAX_MERC = 100;
|
|||||||
static const uint32 MAX_MERC_GRADES = 10;
|
static const uint32 MAX_MERC_GRADES = 10;
|
||||||
static const uint32 MAX_MERC_STANCES = 10;
|
static const uint32 MAX_MERC_STANCES = 10;
|
||||||
static const uint32 BLOCKED_BUFF_COUNT = 20;
|
static const uint32 BLOCKED_BUFF_COUNT = 20;
|
||||||
|
static const uint32 QUESTREWARD_COUNT = 8;
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -2180,14 +2181,7 @@ struct QuestReward_Struct
|
|||||||
/*024*/ uint32 silver; // Gives silver to the client
|
/*024*/ uint32 silver; // Gives silver to the client
|
||||||
/*028*/ uint32 gold; // Gives gold to the client
|
/*028*/ uint32 gold; // Gives gold to the client
|
||||||
/*032*/ uint32 platinum; // Gives platinum to the client
|
/*032*/ uint32 platinum; // Gives platinum to the client
|
||||||
/*036*/ uint32 item_id;
|
/*036*/ int32 item_id[QUESTREWARD_COUNT]; // -1 for nothing
|
||||||
/*040*/ uint32 unknown040;
|
|
||||||
/*044*/ uint32 unknown044;
|
|
||||||
/*048*/ uint32 unknown048;
|
|
||||||
/*052*/ uint32 unknown052;
|
|
||||||
/*056*/ uint32 unknown056;
|
|
||||||
/*060*/ uint32 unknown060;
|
|
||||||
/*064*/ uint32 unknown064;
|
|
||||||
/*068*/
|
/*068*/
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@ -89,9 +89,9 @@ namespace EQ {
|
|||||||
public:
|
public:
|
||||||
StaticPacket(void *data, size_t size) { m_data = data; m_data_length = size; m_max_data_length = size; }
|
StaticPacket(void *data, size_t size) { m_data = data; m_data_length = size; m_max_data_length = size; }
|
||||||
virtual ~StaticPacket() { }
|
virtual ~StaticPacket() { }
|
||||||
StaticPacket(const StaticPacket &o) { m_data = o.m_data; m_data_length = o.m_data_length; }
|
StaticPacket(const StaticPacket &o) { m_data = o.m_data; m_data_length = o.m_data_length; m_max_data_length = o.m_max_data_length; }
|
||||||
StaticPacket& operator=(const StaticPacket &o) { m_data = o.m_data; m_data_length = o.m_data_length; return *this; }
|
StaticPacket& operator=(const StaticPacket &o) { m_data = o.m_data; m_data_length = o.m_data_length; return *this; }
|
||||||
StaticPacket(StaticPacket &&o) { m_data = o.m_data; m_data_length = o.m_data_length; }
|
StaticPacket(StaticPacket &&o) noexcept { m_data = o.m_data; m_data_length = o.m_data_length; }
|
||||||
|
|
||||||
virtual const void *Data() const { return m_data; }
|
virtual const void *Data() const { return m_data; }
|
||||||
virtual void *Data() { return m_data; }
|
virtual void *Data() { return m_data; }
|
||||||
@ -112,7 +112,7 @@ namespace EQ {
|
|||||||
public:
|
public:
|
||||||
DynamicPacket() { }
|
DynamicPacket() { }
|
||||||
virtual ~DynamicPacket() { }
|
virtual ~DynamicPacket() { }
|
||||||
DynamicPacket(DynamicPacket &&o) { m_data = std::move(o.m_data); }
|
DynamicPacket(DynamicPacket &&o) noexcept { m_data = std::move(o.m_data); }
|
||||||
DynamicPacket(const DynamicPacket &o) { m_data = o.m_data; }
|
DynamicPacket(const DynamicPacket &o) { m_data = o.m_data; }
|
||||||
DynamicPacket& operator=(const DynamicPacket &o) { m_data = o.m_data; return *this; }
|
DynamicPacket& operator=(const DynamicPacket &o) { m_data = o.m_data; return *this; }
|
||||||
|
|
||||||
@ -127,4 +127,4 @@ namespace EQ {
|
|||||||
std::vector<char> m_data;
|
std::vector<char> m_data;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -294,6 +294,7 @@ RULE_BOOL(Pathing, Find, true, "Enable pathing for FindPerson requests from the
|
|||||||
RULE_BOOL(Pathing, Fear, true, "Enable pathing for fear")
|
RULE_BOOL(Pathing, Fear, true, "Enable pathing for fear")
|
||||||
RULE_REAL(Pathing, NavmeshStepSize, 100.0f, "")
|
RULE_REAL(Pathing, NavmeshStepSize, 100.0f, "")
|
||||||
RULE_REAL(Pathing, ShortMovementUpdateRange, 130.0f, "")
|
RULE_REAL(Pathing, ShortMovementUpdateRange, 130.0f, "")
|
||||||
|
RULE_INT(Pathing, MaxNavmeshNodes, 4092)
|
||||||
RULE_CATEGORY_END()
|
RULE_CATEGORY_END()
|
||||||
|
|
||||||
RULE_CATEGORY(Watermap)
|
RULE_CATEGORY(Watermap)
|
||||||
|
|||||||
@ -8533,13 +8533,13 @@ void Client::QuestReward(Mob* target, uint32 copper, uint32 silver, uint32 gold,
|
|||||||
memset(outapp->pBuffer, 0, sizeof(QuestReward_Struct));
|
memset(outapp->pBuffer, 0, sizeof(QuestReward_Struct));
|
||||||
QuestReward_Struct* qr = (QuestReward_Struct*)outapp->pBuffer;
|
QuestReward_Struct* qr = (QuestReward_Struct*)outapp->pBuffer;
|
||||||
|
|
||||||
qr->mob_id = target->GetID(); // Entity ID for the from mob name
|
qr->mob_id = target ? target->GetID() : 0; // Entity ID for the from mob name
|
||||||
qr->target_id = GetID(); // The Client ID (this)
|
qr->target_id = GetID(); // The Client ID (this)
|
||||||
qr->copper = copper;
|
qr->copper = copper;
|
||||||
qr->silver = silver;
|
qr->silver = silver;
|
||||||
qr->gold = gold;
|
qr->gold = gold;
|
||||||
qr->platinum = platinum;
|
qr->platinum = platinum;
|
||||||
qr->item_id = itemid;
|
qr->item_id[0] = itemid;
|
||||||
qr->exp_reward = exp;
|
qr->exp_reward = exp;
|
||||||
|
|
||||||
if (copper > 0 || silver > 0 || gold > 0 || platinum > 0)
|
if (copper > 0 || silver > 0 || gold > 0 || platinum > 0)
|
||||||
@ -8550,7 +8550,7 @@ void Client::QuestReward(Mob* target, uint32 copper, uint32 silver, uint32 gold,
|
|||||||
|
|
||||||
if (faction)
|
if (faction)
|
||||||
{
|
{
|
||||||
if (target->IsNPC())
|
if (target && target->IsNPC())
|
||||||
{
|
{
|
||||||
int32 nfl_id = target->CastToNPC()->GetNPCFactionID();
|
int32 nfl_id = target->CastToNPC()->GetNPCFactionID();
|
||||||
SetFactionLevel(CharacterID(), nfl_id, GetBaseClass(), GetBaseRace(), GetDeity(), true);
|
SetFactionLevel(CharacterID(), nfl_id, GetBaseClass(), GetBaseRace(), GetDeity(), true);
|
||||||
@ -8566,6 +8566,42 @@ void Client::QuestReward(Mob* target, uint32 copper, uint32 silver, uint32 gold,
|
|||||||
safe_delete(outapp);
|
safe_delete(outapp);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Client::QuestReward(Mob* target, const QuestReward_Struct &reward, bool faction)
|
||||||
|
{
|
||||||
|
auto outapp = new EQApplicationPacket(OP_Sound, sizeof(QuestReward_Struct));
|
||||||
|
memset(outapp->pBuffer, 0, sizeof(QuestReward_Struct));
|
||||||
|
QuestReward_Struct* qr = (QuestReward_Struct*)outapp->pBuffer;
|
||||||
|
|
||||||
|
memcpy(qr, &reward, sizeof(QuestReward_Struct));
|
||||||
|
|
||||||
|
// not set in caller because reasons
|
||||||
|
qr->mob_id = target ? target->GetID() : 0; // Entity ID for the from mob name
|
||||||
|
|
||||||
|
if (reward.copper > 0 || reward.silver > 0 || reward.gold > 0 || reward.platinum > 0)
|
||||||
|
AddMoneyToPP(reward.copper, reward.silver, reward.gold, reward.platinum, false);
|
||||||
|
|
||||||
|
for (int i = 0; i < QUESTREWARD_COUNT; ++i)
|
||||||
|
if (reward.item_id[i] > 0)
|
||||||
|
SummonItem(reward.item_id[i], 0, 0, 0, 0, 0, 0, false, EQEmu::invslot::slotCursor);
|
||||||
|
|
||||||
|
if (faction)
|
||||||
|
{
|
||||||
|
if (target && target->IsNPC())
|
||||||
|
{
|
||||||
|
int32 nfl_id = target->CastToNPC()->GetNPCFactionID();
|
||||||
|
SetFactionLevel(CharacterID(), nfl_id, GetBaseClass(), GetBaseRace(), GetDeity(), true);
|
||||||
|
qr->faction = target->CastToNPC()->GetPrimaryFaction();
|
||||||
|
qr->faction_mod = 1; // Too lazy to get real value, not sure if this is even used by client anyhow.
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (reward.exp_reward> 0)
|
||||||
|
AddEXP(reward.exp_reward);
|
||||||
|
|
||||||
|
QueuePacket(outapp, true, Client::CLIENT_CONNECTED);
|
||||||
|
safe_delete(outapp);
|
||||||
|
}
|
||||||
|
|
||||||
void Client::SendHPUpdateMarquee(){
|
void Client::SendHPUpdateMarquee(){
|
||||||
if (!this || !this->IsClient() || !this->current_hp || !this->max_hp)
|
if (!this || !this->IsClient() || !this->current_hp || !this->max_hp)
|
||||||
return;
|
return;
|
||||||
|
|||||||
@ -1282,6 +1282,7 @@ public:
|
|||||||
int32 GetMeleeDamage(Mob* other, bool GetMinDamage = false);
|
int32 GetMeleeDamage(Mob* other, bool GetMinDamage = false);
|
||||||
|
|
||||||
void QuestReward(Mob* target, uint32 copper = 0, uint32 silver = 0, uint32 gold = 0, uint32 platinum = 0, uint32 itemid = 0, uint32 exp = 0, bool faction = false);
|
void QuestReward(Mob* target, uint32 copper = 0, uint32 silver = 0, uint32 gold = 0, uint32 platinum = 0, uint32 itemid = 0, uint32 exp = 0, bool faction = false);
|
||||||
|
void QuestReward(Mob* target, const QuestReward_Struct &reward, bool faction); // TODO: Fix faction processing
|
||||||
|
|
||||||
void ResetHPUpdateTimer() { hpupdate_timer.Start(); }
|
void ResetHPUpdateTimer() { hpupdate_timer.Start(); }
|
||||||
|
|
||||||
|
|||||||
@ -11130,6 +11130,11 @@ void Client::Handle_OP_RaidCommand(const EQApplicationPacket *app)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (player_to_invite_group && player_to_invite_group->IsGroupMember(this)) {
|
||||||
|
MessageString(Chat::Red, ALREADY_IN_PARTY);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
if (player_to_invite_group && !player_to_invite_group->IsLeader(player_to_invite)) {
|
if (player_to_invite_group && !player_to_invite_group->IsLeader(player_to_invite)) {
|
||||||
Message(Chat::Red, "You can only invite an ungrouped player or group leader to join your raid.");
|
Message(Chat::Red, "You can only invite an ungrouped player or group leader to join your raid.");
|
||||||
break;
|
break;
|
||||||
|
|||||||
@ -1385,18 +1385,23 @@ void Lua_Client::QuestReward(Lua_Mob target, luabind::adl::object reward) {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32 copper = 0;
|
QuestReward_Struct quest_reward;
|
||||||
uint32 silver = 0;
|
quest_reward.mob_id = 0;
|
||||||
uint32 gold = 0;
|
quest_reward.target_id = self->GetID();
|
||||||
uint32 platinum = 0;
|
quest_reward.copper = 0;
|
||||||
uint32 itemid = 0;
|
quest_reward.silver = 0;
|
||||||
uint32 exp = 0;
|
quest_reward.gold = 0;
|
||||||
|
quest_reward.platinum = 0;
|
||||||
|
quest_reward.exp_reward = 0;
|
||||||
|
quest_reward.faction = 0;
|
||||||
|
quest_reward.faction_mod = 0;
|
||||||
bool faction = false;
|
bool faction = false;
|
||||||
|
std::fill(std::begin(quest_reward.item_id), std::end(quest_reward.item_id), -1);
|
||||||
|
|
||||||
auto cur = reward["copper"];
|
auto cur = reward["copper"];
|
||||||
if (luabind::type(cur) != LUA_TNIL) {
|
if (luabind::type(cur) != LUA_TNIL) {
|
||||||
try {
|
try {
|
||||||
copper = luabind::object_cast<uint32>(cur);
|
quest_reward.copper = luabind::object_cast<uint32>(cur);
|
||||||
} catch (luabind::cast_failed &) {
|
} catch (luabind::cast_failed &) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1404,7 +1409,7 @@ void Lua_Client::QuestReward(Lua_Mob target, luabind::adl::object reward) {
|
|||||||
cur = reward["silver"];
|
cur = reward["silver"];
|
||||||
if (luabind::type(cur) != LUA_TNIL) {
|
if (luabind::type(cur) != LUA_TNIL) {
|
||||||
try {
|
try {
|
||||||
silver = luabind::object_cast<uint32>(cur);
|
quest_reward.silver = luabind::object_cast<uint32>(cur);
|
||||||
} catch (luabind::cast_failed &) {
|
} catch (luabind::cast_failed &) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1412,7 +1417,7 @@ void Lua_Client::QuestReward(Lua_Mob target, luabind::adl::object reward) {
|
|||||||
cur = reward["gold"];
|
cur = reward["gold"];
|
||||||
if (luabind::type(cur) != LUA_TNIL) {
|
if (luabind::type(cur) != LUA_TNIL) {
|
||||||
try {
|
try {
|
||||||
gold = luabind::object_cast<uint32>(cur);
|
quest_reward.gold = luabind::object_cast<uint32>(cur);
|
||||||
} catch (luabind::cast_failed &) {
|
} catch (luabind::cast_failed &) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1420,7 +1425,7 @@ void Lua_Client::QuestReward(Lua_Mob target, luabind::adl::object reward) {
|
|||||||
cur = reward["platinum"];
|
cur = reward["platinum"];
|
||||||
if (luabind::type(cur) != LUA_TNIL) {
|
if (luabind::type(cur) != LUA_TNIL) {
|
||||||
try {
|
try {
|
||||||
platinum = luabind::object_cast<uint32>(cur);
|
quest_reward.platinum = luabind::object_cast<uint32>(cur);
|
||||||
} catch (luabind::cast_failed &) {
|
} catch (luabind::cast_failed &) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1428,7 +1433,30 @@ void Lua_Client::QuestReward(Lua_Mob target, luabind::adl::object reward) {
|
|||||||
cur = reward["itemid"];
|
cur = reward["itemid"];
|
||||||
if (luabind::type(cur) != LUA_TNIL) {
|
if (luabind::type(cur) != LUA_TNIL) {
|
||||||
try {
|
try {
|
||||||
itemid = luabind::object_cast<uint32>(cur);
|
quest_reward.item_id[0] = luabind::object_cast<uint32>(cur);
|
||||||
|
} catch (luabind::cast_failed &) {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// if you define both an itemid and items table, the itemid is thrown away
|
||||||
|
// should we error?
|
||||||
|
cur = reward["items"];
|
||||||
|
if (luabind::type(cur) == LUA_TTABLE) {
|
||||||
|
try {
|
||||||
|
// assume they defined a compatible table
|
||||||
|
for (int i = 1; i <= QUESTREWARD_COUNT; ++i) {
|
||||||
|
auto item = cur[i];
|
||||||
|
int cur_value = -1;
|
||||||
|
if (luabind::type(item) != LUA_TNIL) {
|
||||||
|
try {
|
||||||
|
cur_value = luabind::object_cast<uint32>(item);
|
||||||
|
} catch (luabind::cast_failed &) {
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
quest_reward.item_id[i - 1] = cur_value;
|
||||||
|
}
|
||||||
} catch (luabind::cast_failed &) {
|
} catch (luabind::cast_failed &) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1436,7 +1464,7 @@ void Lua_Client::QuestReward(Lua_Mob target, luabind::adl::object reward) {
|
|||||||
cur = reward["exp"];
|
cur = reward["exp"];
|
||||||
if (luabind::type(cur) != LUA_TNIL) {
|
if (luabind::type(cur) != LUA_TNIL) {
|
||||||
try {
|
try {
|
||||||
exp = luabind::object_cast<uint32>(cur);
|
quest_reward.exp_reward = luabind::object_cast<uint32>(cur);
|
||||||
} catch (luabind::cast_failed &) {
|
} catch (luabind::cast_failed &) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1449,7 +1477,7 @@ void Lua_Client::QuestReward(Lua_Mob target, luabind::adl::object reward) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
self->QuestReward(target, copper, silver, gold, platinum, itemid, exp, faction);
|
self->QuestReward(target, quest_reward, faction);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Lua_Client::IsDead() {
|
bool Lua_Client::IsDead() {
|
||||||
|
|||||||
@ -1300,7 +1300,9 @@ void MobMovementManager::PushEvadeCombat(MobMovementEntry &mob_movement_entry)
|
|||||||
*/
|
*/
|
||||||
void MobMovementManager::HandleStuckBehavior(Mob *who, float x, float y, float z, MobMovementMode mob_movement_mode)
|
void MobMovementManager::HandleStuckBehavior(Mob *who, float x, float y, float z, MobMovementMode mob_movement_mode)
|
||||||
{
|
{
|
||||||
auto sb = who->GetStuckBehavior();
|
LogDebug("Handle stuck behavior for {0} at ({1}, {2}, {3}) with movement_mode {4}", who->GetName(), x, y, z, mob_movement_mode);
|
||||||
|
|
||||||
|
auto sb = who->GetStuckBehavior();
|
||||||
MobStuckBehavior behavior = RunToTarget;
|
MobStuckBehavior behavior = RunToTarget;
|
||||||
|
|
||||||
if (sb >= 0 && sb < MaxStuckBehavior) {
|
if (sb >= 0 && sb < MaxStuckBehavior) {
|
||||||
@ -1308,7 +1310,7 @@ void MobMovementManager::HandleStuckBehavior(Mob *who, float x, float y, float z
|
|||||||
}
|
}
|
||||||
|
|
||||||
auto eiter = _impl->Entries.find(who);
|
auto eiter = _impl->Entries.find(who);
|
||||||
auto &ent = (*eiter);
|
auto &ent = (*eiter);
|
||||||
|
|
||||||
switch (sb) {
|
switch (sb) {
|
||||||
case RunToTarget:
|
case RunToTarget:
|
||||||
@ -1323,8 +1325,7 @@ void MobMovementManager::HandleStuckBehavior(Mob *who, float x, float y, float z
|
|||||||
PushStopMoving(ent.second);
|
PushStopMoving(ent.second);
|
||||||
break;
|
break;
|
||||||
case EvadeCombat:
|
case EvadeCombat:
|
||||||
//PushEvadeCombat(ent.second);
|
PushEvadeCombat(ent.second);
|
||||||
PushStopMoving(ent.second);
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -12,8 +12,6 @@
|
|||||||
|
|
||||||
extern Zone *zone;
|
extern Zone *zone;
|
||||||
|
|
||||||
const int MaxNavmeshNodes = 1024;
|
|
||||||
|
|
||||||
struct PathfinderNavmesh::Implementation
|
struct PathfinderNavmesh::Implementation
|
||||||
{
|
{
|
||||||
dtNavMesh *nav_mesh;
|
dtNavMesh *nav_mesh;
|
||||||
@ -36,19 +34,19 @@ PathfinderNavmesh::~PathfinderNavmesh()
|
|||||||
IPathfinder::IPath PathfinderNavmesh::FindRoute(const glm::vec3 &start, const glm::vec3 &end, bool &partial, bool &stuck, int flags)
|
IPathfinder::IPath PathfinderNavmesh::FindRoute(const glm::vec3 &start, const glm::vec3 &end, bool &partial, bool &stuck, int flags)
|
||||||
{
|
{
|
||||||
partial = false;
|
partial = false;
|
||||||
|
|
||||||
if (!m_impl->nav_mesh) {
|
if (!m_impl->nav_mesh) {
|
||||||
return IPath();
|
return IPath();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!m_impl->query) {
|
if (!m_impl->query) {
|
||||||
m_impl->query = dtAllocNavMeshQuery();
|
m_impl->query = dtAllocNavMeshQuery();
|
||||||
}
|
}
|
||||||
|
|
||||||
m_impl->query->init(m_impl->nav_mesh, MaxNavmeshNodes);
|
m_impl->query->init(m_impl->nav_mesh, RuleI(Pathing, MaxNavmeshNodes));
|
||||||
glm::vec3 current_location(start.x, start.z, start.y);
|
glm::vec3 current_location(start.x, start.z, start.y);
|
||||||
glm::vec3 dest_location(end.x, end.z, end.y);
|
glm::vec3 dest_location(end.x, end.z, end.y);
|
||||||
|
|
||||||
dtQueryFilter filter;
|
dtQueryFilter filter;
|
||||||
filter.setIncludeFlags(flags);
|
filter.setIncludeFlags(flags);
|
||||||
filter.setAreaCost(0, 1.0f); //Normal
|
filter.setAreaCost(0, 1.0f); //Normal
|
||||||
@ -61,48 +59,48 @@ IPathfinder::IPath PathfinderNavmesh::FindRoute(const glm::vec3 &start, const gl
|
|||||||
filter.setAreaCost(8, 1.0f); //General Area
|
filter.setAreaCost(8, 1.0f); //General Area
|
||||||
filter.setAreaCost(9, 0.1f); //Portal
|
filter.setAreaCost(9, 0.1f); //Portal
|
||||||
filter.setAreaCost(10, 0.1f); //Prefer
|
filter.setAreaCost(10, 0.1f); //Prefer
|
||||||
|
|
||||||
dtPolyRef start_ref;
|
dtPolyRef start_ref;
|
||||||
dtPolyRef end_ref;
|
dtPolyRef end_ref;
|
||||||
glm::vec3 ext(5.0f, 100.0f, 5.0f);
|
glm::vec3 ext(5.0f, 100.0f, 5.0f);
|
||||||
|
|
||||||
m_impl->query->findNearestPoly(¤t_location[0], &ext[0], &filter, &start_ref, 0);
|
m_impl->query->findNearestPoly(¤t_location[0], &ext[0], &filter, &start_ref, 0);
|
||||||
m_impl->query->findNearestPoly(&dest_location[0], &ext[0], &filter, &end_ref, 0);
|
m_impl->query->findNearestPoly(&dest_location[0], &ext[0], &filter, &end_ref, 0);
|
||||||
|
|
||||||
if (!start_ref || !end_ref) {
|
if (!start_ref || !end_ref) {
|
||||||
return IPath();
|
return IPath();
|
||||||
}
|
}
|
||||||
|
|
||||||
int npoly = 0;
|
int npoly = 0;
|
||||||
dtPolyRef path[1024] = { 0 };
|
dtPolyRef path[1024] = { 0 };
|
||||||
auto status = m_impl->query->findPath(start_ref, end_ref, ¤t_location[0], &dest_location[0], &filter, path, &npoly, 1024);
|
auto status = m_impl->query->findPath(start_ref, end_ref, ¤t_location[0], &dest_location[0], &filter, path, &npoly, 1024);
|
||||||
|
|
||||||
if (npoly) {
|
if (npoly) {
|
||||||
glm::vec3 epos = dest_location;
|
glm::vec3 epos = dest_location;
|
||||||
if (path[npoly - 1] != end_ref) {
|
if (path[npoly - 1] != end_ref) {
|
||||||
m_impl->query->closestPointOnPoly(path[npoly - 1], &dest_location[0], &epos[0], 0);
|
m_impl->query->closestPointOnPoly(path[npoly - 1], &dest_location[0], &epos[0], 0);
|
||||||
partial = true;
|
partial = true;
|
||||||
|
|
||||||
auto dist = DistanceSquared(epos, current_location);
|
auto dist = DistanceSquared(epos, current_location);
|
||||||
if (dist < 10000.0f) {
|
if (dist < 10000.0f) {
|
||||||
stuck = true;
|
stuck = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
float straight_path[2048 * 3];
|
float straight_path[2048 * 3];
|
||||||
unsigned char straight_path_flags[2048];
|
unsigned char straight_path_flags[2048];
|
||||||
|
|
||||||
int n_straight_polys;
|
int n_straight_polys;
|
||||||
dtPolyRef straight_path_polys[2048];
|
dtPolyRef straight_path_polys[2048];
|
||||||
|
|
||||||
status = m_impl->query->findStraightPath(¤t_location[0], &epos[0], path, npoly,
|
status = m_impl->query->findStraightPath(¤t_location[0], &epos[0], path, npoly,
|
||||||
straight_path, straight_path_flags,
|
straight_path, straight_path_flags,
|
||||||
straight_path_polys, &n_straight_polys, 2048, DT_STRAIGHTPATH_AREA_CROSSINGS);
|
straight_path_polys, &n_straight_polys, 2048, DT_STRAIGHTPATH_AREA_CROSSINGS);
|
||||||
|
|
||||||
if (dtStatusFailed(status)) {
|
if (dtStatusFailed(status)) {
|
||||||
return IPath();
|
return IPath();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (n_straight_polys) {
|
if (n_straight_polys) {
|
||||||
IPath Route;
|
IPath Route;
|
||||||
for (int i = 0; i < n_straight_polys; ++i)
|
for (int i = 0; i < n_straight_polys; ++i)
|
||||||
@ -111,9 +109,9 @@ IPathfinder::IPath PathfinderNavmesh::FindRoute(const glm::vec3 &start, const gl
|
|||||||
node.x = straight_path[i * 3];
|
node.x = straight_path[i * 3];
|
||||||
node.z = straight_path[i * 3 + 1];
|
node.z = straight_path[i * 3 + 1];
|
||||||
node.y = straight_path[i * 3 + 2];
|
node.y = straight_path[i * 3 + 2];
|
||||||
|
|
||||||
Route.push_back(node);
|
Route.push_back(node);
|
||||||
|
|
||||||
unsigned short flag = 0;
|
unsigned short flag = 0;
|
||||||
if (dtStatusSucceed(m_impl->nav_mesh->getPolyFlags(straight_path_polys[i], &flag))) {
|
if (dtStatusSucceed(m_impl->nav_mesh->getPolyFlags(straight_path_polys[i], &flag))) {
|
||||||
if (flag & 512) {
|
if (flag & 512) {
|
||||||
@ -121,11 +119,11 @@ IPathfinder::IPath PathfinderNavmesh::FindRoute(const glm::vec3 &start, const gl
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return Route;
|
return Route;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
IPath Route;
|
IPath Route;
|
||||||
Route.push_back(end);
|
Route.push_back(end);
|
||||||
return Route;
|
return Route;
|
||||||
@ -134,19 +132,19 @@ IPathfinder::IPath PathfinderNavmesh::FindRoute(const glm::vec3 &start, const gl
|
|||||||
IPathfinder::IPath PathfinderNavmesh::FindPath(const glm::vec3 &start, const glm::vec3 &end, bool &partial, bool &stuck, const PathfinderOptions &opts)
|
IPathfinder::IPath PathfinderNavmesh::FindPath(const glm::vec3 &start, const glm::vec3 &end, bool &partial, bool &stuck, const PathfinderOptions &opts)
|
||||||
{
|
{
|
||||||
partial = false;
|
partial = false;
|
||||||
|
|
||||||
if (!m_impl->nav_mesh) {
|
if (!m_impl->nav_mesh) {
|
||||||
return IPath();
|
return IPath();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!m_impl->query) {
|
if (!m_impl->query) {
|
||||||
m_impl->query = dtAllocNavMeshQuery();
|
m_impl->query = dtAllocNavMeshQuery();
|
||||||
}
|
}
|
||||||
|
|
||||||
m_impl->query->init(m_impl->nav_mesh, MaxNavmeshNodes);
|
m_impl->query->init(m_impl->nav_mesh, RuleI(Pathing, MaxNavmeshNodes));
|
||||||
glm::vec3 current_location(start.x, start.z, start.y);
|
glm::vec3 current_location(start.x, start.z, start.y);
|
||||||
glm::vec3 dest_location(end.x, end.z, end.y);
|
glm::vec3 dest_location(end.x, end.z, end.y);
|
||||||
|
|
||||||
dtQueryFilter filter;
|
dtQueryFilter filter;
|
||||||
filter.setIncludeFlags(opts.flags);
|
filter.setIncludeFlags(opts.flags);
|
||||||
filter.setAreaCost(0, opts.flag_cost[0]); //Normal
|
filter.setAreaCost(0, opts.flag_cost[0]); //Normal
|
||||||
@ -159,83 +157,78 @@ IPathfinder::IPath PathfinderNavmesh::FindPath(const glm::vec3 &start, const glm
|
|||||||
filter.setAreaCost(8, opts.flag_cost[7]); //General Area
|
filter.setAreaCost(8, opts.flag_cost[7]); //General Area
|
||||||
filter.setAreaCost(9, opts.flag_cost[8]); //Portal
|
filter.setAreaCost(9, opts.flag_cost[8]); //Portal
|
||||||
filter.setAreaCost(10, opts.flag_cost[9]); //Prefer
|
filter.setAreaCost(10, opts.flag_cost[9]); //Prefer
|
||||||
|
|
||||||
static const int max_polys = 256;
|
static const int max_polys = 256;
|
||||||
dtPolyRef start_ref;
|
dtPolyRef start_ref;
|
||||||
dtPolyRef end_ref;
|
dtPolyRef end_ref;
|
||||||
glm::vec3 ext(10.0f, 200.0f, 10.0f);
|
glm::vec3 ext(10.0f, 200.0f, 10.0f);
|
||||||
|
|
||||||
m_impl->query->findNearestPoly(¤t_location[0], &ext[0], &filter, &start_ref, 0);
|
m_impl->query->findNearestPoly(¤t_location[0], &ext[0], &filter, &start_ref, 0);
|
||||||
m_impl->query->findNearestPoly(&dest_location[0], &ext[0], &filter, &end_ref, 0);
|
m_impl->query->findNearestPoly(&dest_location[0], &ext[0], &filter, &end_ref, 0);
|
||||||
|
|
||||||
if (!start_ref || !end_ref) {
|
if (!start_ref || !end_ref) {
|
||||||
return IPath();
|
return IPath();
|
||||||
}
|
}
|
||||||
|
|
||||||
int npoly = 0;
|
int npoly = 0;
|
||||||
dtPolyRef path[max_polys] = { 0 };
|
dtPolyRef path[max_polys] = { 0 };
|
||||||
m_impl->query->findPath(start_ref, end_ref, ¤t_location[0], &dest_location[0], &filter, path, &npoly, max_polys);
|
auto status = m_impl->query->findPath(start_ref, end_ref, ¤t_location[0], &dest_location[0], &filter, path, &npoly, max_polys);
|
||||||
|
|
||||||
if (npoly) {
|
if (npoly) {
|
||||||
glm::vec3 epos = dest_location;
|
glm::vec3 epos = dest_location;
|
||||||
if (path[npoly - 1] != end_ref) {
|
if (path[npoly - 1] != end_ref) {
|
||||||
m_impl->query->closestPointOnPoly(path[npoly - 1], &dest_location[0], &epos[0], 0);
|
m_impl->query->closestPointOnPoly(path[npoly - 1], &dest_location[0], &epos[0], 0);
|
||||||
partial = true;
|
partial = true;
|
||||||
|
|
||||||
auto dist = DistanceSquared(epos, current_location);
|
|
||||||
if (dist < 10000.0f) {
|
|
||||||
stuck = true;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int n_straight_polys;
|
int n_straight_polys;
|
||||||
glm::vec3 straight_path[max_polys];
|
glm::vec3 straight_path[max_polys];
|
||||||
unsigned char straight_path_flags[max_polys];
|
unsigned char straight_path_flags[max_polys];
|
||||||
dtPolyRef straight_path_polys[max_polys];
|
dtPolyRef straight_path_polys[max_polys];
|
||||||
|
|
||||||
auto status = m_impl->query->findStraightPath(¤t_location[0], &epos[0], path, npoly,
|
auto status = m_impl->query->findStraightPath(¤t_location[0], &epos[0], path, npoly,
|
||||||
(float*)&straight_path[0], straight_path_flags,
|
(float*)&straight_path[0], straight_path_flags,
|
||||||
straight_path_polys, &n_straight_polys, 2048, DT_STRAIGHTPATH_AREA_CROSSINGS | DT_STRAIGHTPATH_ALL_CROSSINGS);
|
straight_path_polys, &n_straight_polys, 2048, DT_STRAIGHTPATH_AREA_CROSSINGS | DT_STRAIGHTPATH_ALL_CROSSINGS);
|
||||||
|
|
||||||
if (dtStatusFailed(status)) {
|
if (dtStatusFailed(status)) {
|
||||||
return IPath();
|
return IPath();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (n_straight_polys) {
|
if (n_straight_polys) {
|
||||||
if (opts.smooth_path) {
|
if (opts.smooth_path) {
|
||||||
IPath Route;
|
IPath Route;
|
||||||
|
|
||||||
//Add the first point
|
//Add the first point
|
||||||
{
|
{
|
||||||
auto &flag = straight_path_flags[0];
|
auto &flag = straight_path_flags[0];
|
||||||
if (flag & DT_STRAIGHTPATH_OFFMESH_CONNECTION) {
|
if (flag & DT_STRAIGHTPATH_OFFMESH_CONNECTION) {
|
||||||
auto &p = straight_path[0];
|
auto &p = straight_path[0];
|
||||||
|
|
||||||
Route.push_back(glm::vec3(p.x, p.z, p.y));
|
Route.push_back(glm::vec3(p.x, p.z, p.y));
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
auto &p = straight_path[0];
|
auto &p = straight_path[0];
|
||||||
|
|
||||||
float h = 0.0f;
|
float h = 0.0f;
|
||||||
if (dtStatusSucceed(GetPolyHeightOnPath(path, npoly, p, &h))) {
|
if (dtStatusSucceed(GetPolyHeightOnPath(path, npoly, p, &h))) {
|
||||||
p.y = h + opts.offset;
|
p.y = h + opts.offset;
|
||||||
}
|
}
|
||||||
|
|
||||||
Route.push_back(glm::vec3(p.x, p.z, p.y));
|
Route.push_back(glm::vec3(p.x, p.z, p.y));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
for (int i = 0; i < n_straight_polys - 1; ++i)
|
for (int i = 0; i < n_straight_polys - 1; ++i)
|
||||||
{
|
{
|
||||||
auto &flag = straight_path_flags[i];
|
auto &flag = straight_path_flags[i];
|
||||||
|
|
||||||
if (flag & DT_STRAIGHTPATH_OFFMESH_CONNECTION) {
|
if (flag & DT_STRAIGHTPATH_OFFMESH_CONNECTION) {
|
||||||
auto &poly = straight_path_polys[i];
|
auto &poly = straight_path_polys[i];
|
||||||
|
|
||||||
auto &p2 = straight_path[i + 1];
|
auto &p2 = straight_path[i + 1];
|
||||||
glm::vec3 node(p2.x, p2.z, p2.y);
|
glm::vec3 node(p2.x, p2.z, p2.y);
|
||||||
Route.push_back(node);
|
Route.push_back(node);
|
||||||
|
|
||||||
unsigned short pflag = 0;
|
unsigned short pflag = 0;
|
||||||
if (dtStatusSucceed(m_impl->nav_mesh->getPolyFlags(straight_path_polys[i], &pflag))) {
|
if (dtStatusSucceed(m_impl->nav_mesh->getPolyFlags(straight_path_polys[i], &pflag))) {
|
||||||
if (pflag & 512) {
|
if (pflag & 512) {
|
||||||
@ -250,12 +243,12 @@ IPathfinder::IPath PathfinderNavmesh::FindPath(const glm::vec3 &start, const glm
|
|||||||
auto dir = glm::normalize(p2 - p1);
|
auto dir = glm::normalize(p2 - p1);
|
||||||
float total = 0.0f;
|
float total = 0.0f;
|
||||||
glm::vec3 previous_pt = p1;
|
glm::vec3 previous_pt = p1;
|
||||||
|
|
||||||
while (total < dist) {
|
while (total < dist) {
|
||||||
glm::vec3 current_pt;
|
glm::vec3 current_pt;
|
||||||
float dist_to_move = opts.step_size;
|
float dist_to_move = opts.step_size;
|
||||||
float ff = opts.step_size / 2.0f;
|
float ff = opts.step_size / 2.0f;
|
||||||
|
|
||||||
if (total + dist_to_move + ff >= dist) {
|
if (total + dist_to_move + ff >= dist) {
|
||||||
current_pt = p2;
|
current_pt = p2;
|
||||||
total = dist;
|
total = dist;
|
||||||
@ -264,18 +257,18 @@ IPathfinder::IPath PathfinderNavmesh::FindPath(const glm::vec3 &start, const glm
|
|||||||
total += dist_to_move;
|
total += dist_to_move;
|
||||||
current_pt = p1 + dir * total;
|
current_pt = p1 + dir * total;
|
||||||
}
|
}
|
||||||
|
|
||||||
float h = 0.0f;
|
float h = 0.0f;
|
||||||
if (dtStatusSucceed(GetPolyHeightOnPath(path, npoly, current_pt, &h))) {
|
if (dtStatusSucceed(GetPolyHeightOnPath(path, npoly, current_pt, &h))) {
|
||||||
current_pt.y = h + opts.offset;
|
current_pt.y = h + opts.offset;
|
||||||
}
|
}
|
||||||
|
|
||||||
Route.push_back(glm::vec3(current_pt.x, current_pt.z, current_pt.y));
|
Route.push_back(glm::vec3(current_pt.x, current_pt.z, current_pt.y));
|
||||||
previous_pt = current_pt;
|
previous_pt = current_pt;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return Route;
|
return Route;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@ -285,7 +278,7 @@ IPathfinder::IPath PathfinderNavmesh::FindPath(const glm::vec3 &start, const glm
|
|||||||
auto ¤t = straight_path[i];
|
auto ¤t = straight_path[i];
|
||||||
glm::vec3 node(current.x, current.z, current.y);
|
glm::vec3 node(current.x, current.z, current.y);
|
||||||
Route.push_back(node);
|
Route.push_back(node);
|
||||||
|
|
||||||
unsigned short flag = 0;
|
unsigned short flag = 0;
|
||||||
if (dtStatusSucceed(m_impl->nav_mesh->getPolyFlags(straight_path_polys[i], &flag))) {
|
if (dtStatusSucceed(m_impl->nav_mesh->getPolyFlags(straight_path_polys[i], &flag))) {
|
||||||
if (flag & 512) {
|
if (flag & 512) {
|
||||||
@ -293,7 +286,7 @@ IPathfinder::IPath PathfinderNavmesh::FindPath(const glm::vec3 &start, const glm
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return Route;
|
return Route;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -313,7 +306,7 @@ glm::vec3 PathfinderNavmesh::GetRandomLocation(const glm::vec3 &start)
|
|||||||
|
|
||||||
if (!m_impl->query) {
|
if (!m_impl->query) {
|
||||||
m_impl->query = dtAllocNavMeshQuery();
|
m_impl->query = dtAllocNavMeshQuery();
|
||||||
m_impl->query->init(m_impl->nav_mesh, MaxNavmeshNodes);
|
m_impl->query->init(m_impl->nav_mesh, RuleI(Pathing, MaxNavmeshNodes));
|
||||||
}
|
}
|
||||||
|
|
||||||
dtQueryFilter filter;
|
dtQueryFilter filter;
|
||||||
|
|||||||
@ -417,6 +417,7 @@
|
|||||||
#define TARGET_PLAYER_FOR_GUILD_STATUS 12260
|
#define TARGET_PLAYER_FOR_GUILD_STATUS 12260
|
||||||
#define GROUP_INVITEE_NOT_FOUND 12268 //You must target a player or use /invite <name> to invite someone to your group.
|
#define GROUP_INVITEE_NOT_FOUND 12268 //You must target a player or use /invite <name> to invite someone to your group.
|
||||||
#define GROUP_INVITEE_SELF 12270 //12270 You cannot invite yourself.
|
#define GROUP_INVITEE_SELF 12270 //12270 You cannot invite yourself.
|
||||||
|
#define ALREADY_IN_PARTY 12272 //That person is already in your party.
|
||||||
#define NO_LONGER_HIDDEN 12337 //You are no longer hidden.
|
#define NO_LONGER_HIDDEN 12337 //You are no longer hidden.
|
||||||
#define STOP_SNEAKING 12338 //You stop sneaking
|
#define STOP_SNEAKING 12338 //You stop sneaking
|
||||||
#define NOT_IN_CONTROL 12368 //You do not have control of yourself right now.
|
#define NOT_IN_CONTROL 12368 //You do not have control of yourself right now.
|
||||||
|
|||||||
@ -771,7 +771,7 @@ void Mob::FixZ(int32 z_find_offset /*= 5*/, bool fix_client_z /*= false*/) {
|
|||||||
float Mob::GetZOffset() const {
|
float Mob::GetZOffset() const {
|
||||||
float offset = 3.125f;
|
float offset = 3.125f;
|
||||||
|
|
||||||
switch (race) {
|
switch (GetModel()) {
|
||||||
case RACE_BASILISK_436:
|
case RACE_BASILISK_436:
|
||||||
offset = 0.577f;
|
offset = 0.577f;
|
||||||
break;
|
break;
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user