Partial port of der's map rewrite, no new azone format yet but it's coming. Will convert legacy map formats on the fly atm.

This commit is contained in:
KimLS 2014-02-23 21:17:28 -08:00
parent eabea6ea16
commit 951c321ba6
17 changed files with 517 additions and 842 deletions

View File

@ -66,7 +66,7 @@ SET(zone_sources
horse.cpp
inventory.cpp
loottables.cpp
Map.cpp
map.cpp
merc.cpp
mob.cpp
MobAI.cpp

View File

@ -754,7 +754,7 @@ void Client::AI_Process()
{
bool WaypointChanged, NodeReached;
VERTEX Goal = UpdatePath(fear_walkto_x, fear_walkto_y, fear_walkto_z,
Map::Vertex Goal = UpdatePath(fear_walkto_x, fear_walkto_y, fear_walkto_z,
GetFearSpeed(), WaypointChanged, NodeReached);
if(WaypointChanged)
@ -910,7 +910,7 @@ void Client::AI_Process()
else
{
bool WaypointChanged, NodeReached;
VERTEX Goal = UpdatePath(GetTarget()->GetX(), GetTarget()->GetY(), GetTarget()->GetZ(),
Map::Vertex Goal = UpdatePath(GetTarget()->GetX(), GetTarget()->GetY(), GetTarget()->GetZ(),
GetRunspeed(), WaypointChanged, NodeReached);
if(WaypointChanged)
@ -1022,7 +1022,7 @@ void Mob::AI_Process() {
{
bool WaypointChanged, NodeReached;
VERTEX Goal = UpdatePath(fear_walkto_x, fear_walkto_y, fear_walkto_z,
Map::Vertex Goal = UpdatePath(fear_walkto_x, fear_walkto_y, fear_walkto_z,
GetFearSpeed(), WaypointChanged, NodeReached);
if(WaypointChanged)
@ -1360,7 +1360,7 @@ void Mob::AI_Process() {
{
bool WaypointChanged, NodeReached;
VERTEX Goal = UpdatePath(target->GetX(), target->GetY(), target->GetZ(),
Map::Vertex Goal = UpdatePath(target->GetX(), target->GetY(), target->GetZ(),
GetRunspeed(), WaypointChanged, NodeReached);
if(WaypointChanged)
@ -1683,7 +1683,7 @@ void NPC::AI_DoMovement() {
{
bool WaypointChanged;
bool NodeReached;
VERTEX Goal = UpdatePath(cur_wp_x, cur_wp_y, cur_wp_z, walksp, WaypointChanged, NodeReached);
Map::Vertex Goal = UpdatePath(cur_wp_x, cur_wp_y, cur_wp_z, walksp, WaypointChanged, NodeReached);
if(WaypointChanged)
tar_ndx = 20;
@ -1722,7 +1722,7 @@ void NPC::AI_DoMovement() {
if(!((x_pos == guard_x) && (y_pos == guard_y) && (z_pos == guard_z)))
{
bool WaypointChanged, NodeReached;
VERTEX Goal = UpdatePath(guard_x, guard_y, guard_z, walksp, WaypointChanged, NodeReached);
Map::Vertex Goal = UpdatePath(guard_x, guard_y, guard_z, walksp, WaypointChanged, NodeReached);
if(WaypointChanged)
tar_ndx = 20;

View File

@ -872,133 +872,6 @@ bool Mob::CombatRange(Mob* other)
return false;
}
//Old LOS function, prolly not used anymore
//Not removed because I havent looked it over to see if anything
//useful is in here before we delete it.
bool Mob::CheckLos(Mob* other) {
if (zone->zonemap == 0)
{
return true;
}
float tmp_x = GetX();
float tmp_y = GetY();
float tmp_z = GetZ();
float trg_x = other->GetX();
float trg_y = other->GetY();
float trg_z = other->GetZ();
float perwalk_x = 0.5;
float perwalk_y = 0.5;
float perwalk_z = 0.5;
float dist_x = tmp_x - trg_x;
if (dist_x < 0)
dist_x *= -1;
float dist_y = tmp_y - trg_y;
if (dist_y < 0)
dist_y *= -1;
float dist_z = tmp_z - trg_z;
if (dist_z < 0)
dist_z *= -1;
if (dist_x < dist_y && dist_z < dist_y)
{
perwalk_x /= (dist_y/dist_x);
perwalk_z /= (dist_y/dist_z);
}
else if (dist_y < dist_x && dist_z < dist_x)
{
perwalk_y /= (dist_x/dist_y);
perwalk_z /= (dist_x/dist_z);
}
else if (dist_x < dist_z && dist_y < dist_z)
{
perwalk_x /= (dist_z/dist_x);
perwalk_y /= (dist_z/dist_y);
}
float steps = (dist_x/perwalk_x + dist_y/perwalk_y + dist_z/perwalk_z)*10; //Just a safety check to prevent endless loops.
while (steps > 0) {
steps--;
if (tmp_x < trg_x)
{
if (tmp_x + perwalk_x < trg_x)
tmp_x += perwalk_x;
else
tmp_x = trg_x;
}
if (tmp_y < trg_y)
{
if (tmp_y + perwalk_y < trg_y)
tmp_y += perwalk_y;
else
tmp_y = trg_y;
}
if (tmp_z < trg_z)
{
if (tmp_z + perwalk_z < trg_z)
tmp_z += perwalk_z;
else
tmp_z = trg_z;
}
if (tmp_x > trg_x)
{
if (tmp_x - perwalk_x > trg_x)
tmp_x -= perwalk_x;
else
tmp_x = trg_x;
}
if (tmp_y > trg_y)
{
if (tmp_y - perwalk_y > trg_y)
tmp_y -= perwalk_y;
else
tmp_y = trg_y;
}
if (tmp_z > trg_z)
{
if (tmp_z - perwalk_z > trg_z)
tmp_z -= perwalk_z;
else
tmp_z = trg_z;
}
if (tmp_y == trg_y && tmp_x == trg_x && tmp_z == trg_z)
{
return true;
}
//I believe this is contributing to breaking mob spawns when a map is loaded
// NodeRef pnode = zone->zonemap->SeekNode( zone->zonemap->GetRoot(), tmp_x, tmp_y );
NodeRef pnode = NODE_NONE;
if (pnode != NODE_NONE)
{
const int *iface = zone->zonemap->SeekFace( pnode, tmp_x, tmp_y );
if (*iface == -1) {
return false;
}
float temp_z = 0;
float best_z = 999999;
while(*iface != -1)
{
temp_z = zone->zonemap->GetFaceHeight( *iface, x_pos, y_pos );
//UMM.. OMG... sqrtf(pow(x, 2)) == x.... retards
float best_dist = sqrtf((float)(pow(best_z-tmp_z, 2)));
float tmp_dist = sqrtf((float)(pow(tmp_z-tmp_z, 2)));
if (tmp_dist < best_dist)
{
best_z = temp_z;
}
iface++;
}
/* solar: our aggro code isn't using this right now, just spells, so i'm
taking out the +-10 check for now to make it work right on hills
if (best_z - 10 > trg_z || best_z + 10 < trg_z)
{
return false;
}
*/
}
}
return true;
}
//Father Nitwit's LOS code
bool Mob::CheckLosFN(Mob* other) {
bool Result = false;
@ -1020,8 +893,8 @@ bool Mob::CheckLosFN(float posX, float posY, float posZ, float mobSize) {
#endif
}
VERTEX myloc;
VERTEX oloc;
Map::Vertex myloc;
Map::Vertex oloc;
#define LOS_DEFAULT_HEIGHT 6.0f
@ -1036,72 +909,7 @@ bool Mob::CheckLosFN(float posX, float posY, float posZ, float mobSize) {
#if LOSDEBUG>=5
LogFile->write(EQEMuLog::Debug, "LOS from (%.2f, %.2f, %.2f) to (%.2f, %.2f, %.2f) sizes: (%.2f, %.2f)", myloc.x, myloc.y, myloc.z, oloc.x, oloc.y, oloc.z, GetSize(), mobSize);
#endif
FACE *onhit;
NodeRef mynode;
NodeRef onode;
VERTEX hit;
//see if anything in our node is in the way
mynode = zone->zonemap->SeekNode( zone->zonemap->GetRoot(), myloc.x, myloc.y);
if(mynode != NODE_NONE) {
if(zone->zonemap->LineIntersectsNode(mynode, myloc, oloc, &hit, &onhit)) {
#if LOSDEBUG>=5
LogFile->write(EQEMuLog::Debug, "Check LOS for %s target position, cannot see.", GetName());
LogFile->write(EQEMuLog::Debug, "\tPoly: (%.2f, %.2f, %.2f) (%.2f, %.2f, %.2f) (%.2f, %.2f, %.2f)\n",
onhit->a.x, onhit->a.y, onhit->a.z,
onhit->b.x, onhit->b.y, onhit->b.z,
onhit->c.x, onhit->c.y, onhit->c.z);
#endif
return(false);
}
}
#if LOSDEBUG>=5
else {
LogFile->write(EQEMuLog::Debug, "WTF, I have no node, what am I standing on??? (%.2f, %.2f).", myloc.x, myloc.y);
}
#endif
//see if they are in a different node.
//if so, see if anything in their node is blocking me.
if(! zone->zonemap->LocWithinNode(mynode, oloc.x, oloc.y)) {
onode = zone->zonemap->SeekNode( zone->zonemap->GetRoot(), oloc.x, oloc.y);
if(onode != NODE_NONE && onode != mynode) {
if(zone->zonemap->LineIntersectsNode(onode, myloc, oloc, &hit, &onhit)) {
#if LOSDEBUG>=5
LogFile->write(EQEMuLog::Debug, "Check LOS for %s target position, cannot see (2).", GetName());
LogFile->write(EQEMuLog::Debug, "\tPoly: (%.2f, %.2f, %.2f) (%.2f, %.2f, %.2f) (%.2f, %.2f, %.2f)\n",
onhit->a.x, onhit->a.y, onhit->a.z,
onhit->b.x, onhit->b.y, onhit->b.z,
onhit->c.x, onhit->c.y, onhit->c.z);
#endif
return(false);
}
}
#if LOSDEBUG>=5
else if(onode == NODE_NONE) {
LogFile->write(EQEMuLog::Debug, "WTF, They have no node, what are they standing on??? (%.2f, %.2f).", myloc.x, myloc.y);
}
#endif
}
/*
if(zone->zonemap->LineIntersectsZone(myloc, oloc, CHECK_LOS_STEP, &onhit)) {
#if LOSDEBUG>=5
LogFile->write(EQEMuLog::Debug, "Check LOS for %s target %s, cannot see.", GetName(), other->GetName() );
LogFile->write(EQEMuLog::Debug, "\tPoly: (%.2f, %.2f, %.2f) (%.2f, %.2f, %.2f) (%.2f, %.2f, %.2f)\n",
onhit->a.x, onhit->a.y, onhit->a.z,
onhit->b.x, onhit->b.y, onhit->b.z,
onhit->c.x, onhit->c.y, onhit->c.z);
#endif
return(false);
}*/
#if LOSDEBUG>=5
LogFile->write(EQEMuLog::Debug, "Check LOS for %s target position, CAN SEE.", GetName());
#endif
return(true);
return zone->zonemap->CheckLoS(myloc, oloc);
}
//offensive spell aggro

View File

@ -1200,8 +1200,8 @@ protected:
Mob* bind_sight_target;
VERTEX aa_los_me;
VERTEX aa_los_them;
Map::Vertex aa_los_me;
Map::Vertex aa_los_them;
Mob *aa_los_them_mob;
bool los_status;
float aa_los_me_heading;

View File

@ -8550,10 +8550,10 @@ void Client::Handle_OP_FindPersonRequest(const EQApplicationPacket *app)
}
else
{
VERTEX Start(GetX(), GetY(), GetZ() + (GetSize() < 6.0 ? 6 : GetSize()) * HEAD_POSITION);
VERTEX End(target->GetX(), target->GetY(), target->GetZ() + (target->GetSize() < 6.0 ? 6 : target->GetSize()) * HEAD_POSITION);
Map::Vertex Start(GetX(), GetY(), GetZ() + (GetSize() < 6.0 ? 6 : GetSize()) * HEAD_POSITION);
Map::Vertex End(target->GetX(), target->GetY(), target->GetZ() + (target->GetSize() < 6.0 ? 6 : target->GetSize()) * HEAD_POSITION);
if(!zone->zonemap->LineIntersectsZone(Start, End, 1.0f, nullptr, nullptr) && zone->pathing->NoHazards(Start, End))
if(!zone->zonemap->LineIntersectsZone(Start, End, 1.0f, nullptr) && zone->pathing->NoHazards(Start, End))
{
points.resize(2);
points[0].x = Start.x;
@ -8594,7 +8594,7 @@ void Client::Handle_OP_FindPersonRequest(const EQApplicationPacket *app)
bool LeadsToTeleporter = false;
VERTEX v = zone->pathing->GetPathNodeCoordinates(pathlist.back());
Map::Vertex v = zone->pathing->GetPathNodeCoordinates(pathlist.back());
p.x = v.x;
p.y = v.y;
@ -8614,7 +8614,7 @@ void Client::Handle_OP_FindPersonRequest(const EQApplicationPacket *app)
break;
}
VERTEX v = zone->pathing->GetPathNodeCoordinates((*Iterator), false);
Map::Vertex v = zone->pathing->GetPathNodeCoordinates((*Iterator), false);
p.x = v.x;
p.y = v.y;
p.z = v.z;
@ -8785,33 +8785,32 @@ bool Client::FinishConnState2(DBAsyncWork* dbaw) {
//if we zone in with invalid Z, fix it.
if (zone->zonemap != nullptr) {
//for whatever reason, LineIntersectsNode is giving better results than FindBestZ
NodeRef pnode;
VERTEX me;
Map::Vertex me;
me.x = GetX();
me.y = GetY();
me.z = GetZ() + (GetSize()==0.0?6:GetSize());
pnode = zone->zonemap->SeekNode( zone->zonemap->GetRoot(), me.x, me.y );
me.z = GetZ() + (GetSize() == 0.0 ? 6 : GetSize());
VERTEX hit;
VERTEX below_me(me);
below_me.z -= 500;
if(!zone->zonemap->LineIntersectsNode(pnode, me, below_me, &hit, nullptr) || hit.z < -5000) {
Map::Vertex hit;
if (zone->zonemap->FindBestZ(me, &hit) == BEST_Z_INVALID)
{
#if EQDEBUG >= 5
LogFile->write(EQEMuLog::Debug, "Player %s started below the zone trying to fix! (%.3f, %.3f, %.3f)", GetName(), me.x, me.y, me.z);
#endif
//theres nothing below us... try to find something to stand on
me.z += 200; //arbitrary #
if(zone->zonemap->LineIntersectsNode(pnode, me, below_me, &hit, nullptr)) {
if (zone->zonemap->FindBestZ(me, &hit) != BEST_Z_INVALID)
{
//+10 so they dont stick in the ground
SendTo(me.x, me.y, hit.z + 10);
m_pp.z = hit.z + 10;
} else {
}
else
{
//one more, desperate try
me.z += 2000;
if(zone->zonemap->LineIntersectsNode(pnode, me, below_me, &hit, nullptr)) {
//+10 so they dont stick in the ground
if (zone->zonemap->FindBestZ(me, &hit) != BEST_Z_INVALID)
{
//+10 so they dont stick in the ground
SendTo(me.x, me.y, hit.z + 10);
m_pp.z = hit.z + 10;
}
@ -8819,14 +8818,6 @@ bool Client::FinishConnState2(DBAsyncWork* dbaw) {
}
}
//m_pp.hunger_level = 6000;
//m_pp.thirst_level = 6000;
//aa_title = m_pp.aa_title;
//m_pp.timeplayed=64;
//m_pp.birthday=1057434792;
//m_pp.lastlogin=1057464792;
if (m_pp.gm && admin < minStatusToBeGM)
m_pp.gm = 0;

View File

@ -7461,8 +7461,8 @@ void command_path(Client *c, const Seperator *sep)
if(zone->zonemap)
{
VERTEX loc(px, py, pz);
best_z = zone->zonemap->FindBestZ(MAP_ROOT_NODE, loc, nullptr, nullptr);
Map::Vertex loc(px, py, pz);
best_z = zone->zonemap->FindBestZ(loc, nullptr);
}
else
{
@ -7488,8 +7488,8 @@ void command_path(Client *c, const Seperator *sep)
if(zone->zonemap)
{
VERTEX loc(px, py, pz);
best_z = zone->zonemap->FindBestZ(MAP_ROOT_NODE, loc, nullptr, nullptr);
Map::Vertex loc(px, py, pz);
best_z = zone->zonemap->FindBestZ(loc, nullptr);
}
else
{
@ -7621,8 +7621,8 @@ void command_path(Client *c, const Seperator *sep)
{
if(c && c->GetTarget())
{
if(zone->pathing->NoHazardsAccurate(VERTEX(c->GetX(),c->GetY(),c->GetZ()),
VERTEX(c->GetTarget()->GetX(),c->GetTarget()->GetY(),c->GetTarget()->GetZ())))
if (zone->pathing->NoHazardsAccurate(Map::Vertex(c->GetX(), c->GetY(), c->GetZ()),
Map::Vertex(c->GetTarget()->GetX(), c->GetTarget()->GetY(), c->GetTarget()->GetZ())))
{
c->Message(0, "No hazards.");
}
@ -7698,7 +7698,7 @@ void command_path(Client *c, const Seperator *sep)
{
Mob *m = c->GetTarget();
VERTEX Position(m->GetX(), m->GetY(), m->GetZ());
Map::Vertex Position(m->GetX(), m->GetY(), m->GetZ());
int Node = zone->pathing->FindNearestPathNode(Position);
@ -7831,35 +7831,19 @@ void command_bestz(Client *c, const Seperator *sep) {
return;
}
NodeRef pnode;
if(c->GetTarget()) {
pnode = zone->zonemap->SeekNode( zone->zonemap->GetRoot(), c->GetTarget()->GetX(), c->GetTarget()->GetY() );
} else {
pnode = zone->zonemap->SeekNode( zone->zonemap->GetRoot(), c->GetX(), c->GetY() );
}
if (pnode == NODE_NONE) {
c->Message(0,"Unable to find your node.");
return;
}
VERTEX me;
Map::Vertex me;
me.x = c->GetX();
me.y = c->GetY();
me.z = c->GetZ() + (c->GetSize()==0.0?6:c->GetSize()) * HEAD_POSITION;
VERTEX hit;
VERTEX bme(me);
Map::Vertex hit;
Map::Vertex bme(me);
bme.z -= 500;
float best_z = zone->zonemap->FindBestZ(pnode, me, &hit, nullptr);
float best_z2 = -999990;
if(zone->zonemap->LineIntersectsNode(pnode, me, bme, &hit, nullptr)) {
best_z2 = hit.z;
}
float best_z = zone->zonemap->FindBestZ(me, &hit);
if (best_z != -999999)
{
c->Message(0,"Z is %.3f or %.3f at (%.3f, %.3f).", best_z, best_z2, me.x, me.y);
c->Message(0,"Z is %.3f at (%.3f, %.3f).", best_z, me.x, me.y);
}
else
{

View File

@ -2554,8 +2554,8 @@ void EntityList::FindPathsToAllNPCs()
auto it = npc_list.begin();
while (it != npc_list.end()) {
VERTEX Node0 = zone->pathing->GetPathNodeCoordinates(0, false);
VERTEX Dest(it->second->GetX(), it->second->GetY(), it->second->GetZ());
Map::Vertex Node0 = zone->pathing->GetPathNodeCoordinates(0, false);
Map::Vertex Dest(it->second->GetX(), it->second->GetY(), it->second->GetZ());
std::list<int> Route = zone->pathing->FindRoute(Node0, Dest);
if (Route.size() == 0)
printf("Unable to find a route to %s\n", it->second->GetName());
@ -3557,9 +3557,9 @@ bool Entity::CheckCoordLosNoZLeaps(float cur_x, float cur_y, float cur_z,
if (zone->zonemap == nullptr)
return true;
VERTEX myloc;
VERTEX oloc;
VERTEX hit;
Map::Vertex myloc;
Map::Vertex oloc;
Map::Vertex hit;
myloc.x = cur_x;
myloc.y = cur_y;
@ -3572,9 +3572,7 @@ bool Entity::CheckCoordLosNoZLeaps(float cur_x, float cur_y, float cur_z,
if (myloc.x == oloc.x && myloc.y == oloc.y && myloc.z == oloc.z)
return true;
FACE *onhit;
if (!zone->zonemap->LineIntersectsZoneNoZLeaps(myloc,oloc,perwalk,&hit,&onhit))
if (!zone->zonemap->LineIntersectsZoneNoZLeaps(myloc,oloc,perwalk,&hit))
return true;
return false;
}

View File

@ -152,11 +152,11 @@ void Mob::CalculateNewFearpoint()
{
int Node = zone->pathing->GetRandomPathNode();
VERTEX Loc = zone->pathing->GetPathNodeCoordinates(Node);
Map::Vertex Loc = zone->pathing->GetPathNodeCoordinates(Node);
++Loc.z;
VERTEX CurrentPosition(GetX(), GetY(), GetZ());
Map::Vertex CurrentPosition(GetX(), GetY(), GetZ());
std::list<int> Route = zone->pathing->FindRoute(CurrentPosition, Loc);
@ -205,429 +205,6 @@ void Mob::CalculateNewFearpoint()
}
}
//we need to start acting scared...
//old fear function, kept for ref.
/*void Mob::SetFeared(Mob *caster, uint32 duration, bool flee) {
//special args to stop fear
if(caster == nullptr && duration == 0) {
fear_state = fearStateNotFeared;
#ifdef FLEE_HP_RATIO
flee_mode = false;
#endif
safe_delete(fear_path_state);
return;
}
flee_mode = flee;
//fear dosent work without at least maps
if(zone->zonemap == nullptr) {
fear_state = fearStateStuck;
return; //just stand there
}
//if we are allready feared, and we are on a fear grid..
//then just stay happy on the grid...
if(fear_path_state != nullptr) {
if(fear_state != fearStateGrid) {
LogFile->write(EQEMuLog::Debug, "Umm... %s has a fear path state, but is not in a grid state. Wtf?", GetName());
fear_state = fearStateGrid;
}
return;
}
//try to run straight away from the caster
VERTEX hit, fear_vector;
if(FearTryStraight(caster, duration, flee, hit, fear_vector)) {
return;
}
//OK, so if we just run, we are going to hit something...
//now we have to think a little more.
//first, try to find a fear node that we can see.
if(zone->pathing != nullptr) {
fear_path_state = new MobFearState();
if(zone->pathing->FindNearestFear(fear_path_state, GetX(), GetY(), GetZ())) {
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing Start: found path, moving from (%.2f, %.2f, %.2f) to path node (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), fear_path_state->x, fear_path_state->y, fear_path_state->z);
#endif
//we found a fear node... were on our way..
cur_wp_x = fear_path_state->x;
cur_wp_y = fear_path_state->y;
cur_wp_z = fear_path_state->z;
fear_state = fearStateGrid;
return;
}
//we have failed to find a path, so we dont need this..
safe_delete(fear_path_state);
}
//if we cannot just run, and we cannot see any paths, then
//we will give one last ditch effort to find a legit path. We
//will run as far as we can away from the player, and hope we
//can see a path from there if not, we will start breaking rules
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing Start: Hope run from (%.2f, %.2f, %.2f), hit at (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), hit.x, hit.y, hit.z);
#endif
//use the hit point - a little + a little Z as the first waypoint.
cur_wp_x = hit.x - fear_vector.x * 2;
cur_wp_y = hit.y - fear_vector.y * 2;
cur_wp_z = GetZ();
fear_state = fearStateRunning;
}
//old fear function, kept for ref.
bool Mob::FearTryStraight(Mob *caster, uint32 duration, bool flee, VERTEX &hit, VERTEX &fear_vector) {
//gotta have somebody to run from
if(caster == nullptr)
return(false);
//our goal is to run along this vector...
fear_vector.x = GetX() - caster->GetX();
fear_vector.y = GetY() - caster->GetY();
fear_vector.z = 0; //I dont see any reason to use Z
float mag = sqrtf(fear_vector.x*fear_vector.x + fear_vector.y*fear_vector.y);
fear_vector.x /= mag;
fear_vector.y /= mag;
//now see if we can just run without hitting anything...
VERTEX start, end;
start.x = GetX();
start.y = GetY();
start.z = GetZ() + 5.0; //raise up a little over small bumps
//distance moved per movement tic.
float distance = NPC_SPEED_MULTIPLIER * GetFearSpeed();
//times number of movement tics in the spell.
distance *= float(duration) / float(AImovement_duration);
end.x = start.x + fear_vector.x * distance;
end.y = start.y + fear_vector.y * distance;
end.z = start.z;
if(!zone->zonemap->LineIntersectsZone(start, end, 0.5, &hit, nullptr)) {
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing Start: can run entire vector from (%.2f, %.2f, %.2f) to (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), end.x, end.y, end.z);
#endif
//no hit, we can run this whole vector.
cur_wp_x = end.x;
cur_wp_y = end.y;
cur_wp_z = GetZ();
fear_state = fearStateRunningForever;
return(true); //were done, nothing difficult needed.
}
return(false);
}
//old fear function, kept for ref.
void Mob::CalculateFearPosition() {
if(zone->zonemap == nullptr || fear_state == fearStateStuck) {
return; //just stand there
}
//This is the entire movement section, right here:
if (cur_wp_x != GetX() && cur_wp_y != GetY()) {
// not at waypoint yet, so keep moving
CalculateNewPosition2(cur_wp_x, cur_wp_y, cur_wp_z, GetFearSpeed(), true);
return;
}
//we have reached our waypoint, now what?
//figure out a new waypoint to run at...
if(fear_state == fearStateRunningForever) {
if(flee_mode) {
//a fleeing mob may run away again
VERTEX hit, fear_vector;
if(FearTryStraight(GetHateTop(), FLEE_RUN_DURATION, true, hit, fear_vector))
return; //we are running again
//else, we need to find a grid, so act like we were on a hope run
fear_state = fearStateRunning;
}
#ifndef FORCE_FEAR_TO_RUN
else {
//we were supposed to run forever, but we did not...
//should re-fear ourself or something??
fear_state = fearStateStuck;
return;
}
#endif
}
//first see if we are on a path. if so our life is easy
if(fear_state == fearStateGrid && fear_path_state) {
//assume that we have zone->pathing since we got to this state.
if(!zone->pathing->NextFearPath(fear_path_state)) {
//this is bad, we were on a path and now its giving us
//an error... we dont have a good way to deal with this
fear_state = fearStateStuck;
return;
}
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing: on path, moving from (%.2f, %.2f, %.2f) to path node (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), fear_path_state->x, fear_path_state->y, fear_path_state->z);
#endif
//we found a fear node... were on our way..
cur_wp_x = fear_path_state->x;
cur_wp_y = fear_path_state->y;
cur_wp_z = fear_path_state->z;
CalculateNewPosition2(cur_wp_x, cur_wp_y, cur_wp_z, GetFearSpeed(), true);
return;
}
//the only valid state left is fearStateRunning, where we try to
//find a grid once we reach our waypoint, which we have..
if(fear_state != fearStateRunning) {
//wtf... unknown state
LogFile->write(EQEMuLog::Debug, "Fear Pathing: Reached our fear waypoint, but we are in an unknown state %d... stopping.", fear_state);
fear_state = fearStateStuck;
return;
}
//we wanted to try to find a waypoint now, so lets try..
if(zone->pathing != nullptr) {
fear_path_state = new MobFearState();
if(zone->pathing->FindNearestFear(fear_path_state, GetX(), GetY(), GetZ())) {
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing: ran to find path, moving from (%.2f, %.2f, %.2f) to path node (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), fear_path_state->x, fear_path_state->y, fear_path_state->z);
#endif
//we found a fear node... were on our way..
cur_wp_x = fear_path_state->x;
cur_wp_y = fear_path_state->y;
cur_wp_z = fear_path_state->z;
fear_state = fearStateGrid;
CalculateNewPosition2(cur_wp_x, cur_wp_y, cur_wp_z, GetFearSpeed(), true);
return;
}
//if we get here... all valid methods have failed
#ifdef FORCE_FEAR_TO_RUN
//ok, now we start making shit up
//for now, we will limit our bullshitting to ignoring LOS
//when finding a pathing node, we SHOULD always get something..
//do not force a path if we are fleeing
if(!flee_mode && zone->pathing->FindNearestFear(fear_path_state, GetX(), GetY(), GetZ(), false)) {
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing: Bullshit Path from (%.2f, %.2f, %.2f) to path node (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), fear_path_state->x, fear_path_state->y, fear_path_state->z);
#endif
//we found a fear node... were on our way..
cur_wp_x = fear_path_state->x;
cur_wp_y = fear_path_state->y;
cur_wp_z = fear_path_state->z;
fear_state = fearStateGrid;
CalculateNewPosition2(cur_wp_x, cur_wp_y, cur_wp_z, GetFearSpeed(), true);
return;
}
#endif //FORCE_FEAR_TO_RUN
//we have failed to find a path once again, so we dont need this..
safe_delete(fear_path_state);
}
//if we get HERE... then NOTHING worked... just stick
fear_state = fearStateStuck;
//end of function, everything else is #ifdef'd out
//}
//I dont wanna get rid of this right now because it was a lot of hard
//work to write... but it dosent work reliably, so oh well..
#ifdef OLD_FEAR_PATHING
/*
The idea...
try to run along fear vector.
If we can see along it, run
otherwise, try to walk up a hill along the same vector
then try to move along a wall along largest component of FV
if cant move, change stae to stuck.
once we know a place to run, use the waypoint code to do it
then if combat ends, we will reach the waypoint and
*/
/*
//first try our original fear vector again...
VERTEX start, end, hit, normalhit;
start.x = GetX() - fear_vector.x * 0.4;
start.y = GetY() - fear_vector.y * 0.4;
start.z = GetZ() + 6.0; //raise up a little over small bumps
end.x = start.x + fear_vector.x * 10;
end.y = start.y + fear_vector.y * 10;
end.z = start.z;
if(!zone->zonemap->LineIntersectsZone(start, end, 0.5, &normalhit, nullptr)) {
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing: From (%.2f, %.2f, %.2f) normal run to (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), end.x, end.y, end.z);
#endif
//we can run along this vector without hitting anything...
cur_wp_x = end.x;
cur_wp_y = end.y;
cur_wp_z = end.z - 6.0;
CalculateNewPosition2(cur_wp_x, cur_wp_y, cur_wp_z, GetRunspeed(), true);
return;
}
//see if we can make ANY useful progress along that vector
//first, adjust normalhit to back up a little bit
//so we dont run through the wall
normalhit.x -= 0.4 * fear_vector.x;
normalhit.y -= 0.4 * fear_vector.y;
float xd = normalhit.x - start.x;
if(xd < 0)
xd = 0 - xd;
float yd = normalhit.y - start.y;
if(yd < 0)
yd = 0 - yd;
//this 2 is arbitrary
if((xd+yd) > 2.0) {
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing: From (%.2f, %.2f, %.2f) small run to (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), cur_wp_x, cur_wp_y, cur_wp_z);
#endif
cur_wp_x = normalhit.x;
cur_wp_y = normalhit.y;
cur_wp_z = GetZ();
//try and fix up the Z coord if possible
//not sure if this is worth it, since it prolly isnt up much
NodeRef c = zone->zonemap->SeekNode(zone->zonemap->GetRoot(), end.x, end.y);
if(c != NODE_NONE) {
cur_wp_z = zone->zonemap->FindBestZ(c, end, &hit, nullptr);
if(cur_wp_z < start.z)
cur_wp_z = end.z; //revert on error
}
CalculateNewPosition2(cur_wp_x, cur_wp_y, cur_wp_z, GetRunspeed(), true);
return;
}
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing: From (%.2f, %.2f, %.2f) normal hit at (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), normalhit.x, normalhit.y, normalhit.z);
#endif
//if we get here, we cannot run along our normal vector...
//try up hill first
/*
while this uphill stuff works great in outdoor zones,
it totally breaks dungeons...
float speed = GetRunspeed();
end.x = start.x + fear_vector.x * speed;
end.y = start.y + fear_vector.y * speed;
end.z = start.z + speed + speed;
if(!zone->zonemap->LineIntersectsZone(start, end, 0.5, &hit, nullptr)) {
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing: From (%.2f, %.2f, %.2f) up hill run to (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), end.x, end.y, end.z);
#endif
//we can run along this vector without hitting anything...
cur_wp_x = end.x - 0.4 * fear_vector.x;
cur_wp_y = end.y - 0.4 * fear_vector.y;
cur_wp_z = end.z;
//try and fix up the Z coord if possible
//not sure if this is worth it, since it prolly isnt up much
NodeRef c = zone->zonemap->SeekNode(zone->zonemap->GetRoot(), end.x, end.y);
if(c != NODE_NONE) {
cur_wp_z = zone->zonemap->FindBestZ(c, end, &hit, nullptr);
if(cur_wp_z < start.z)
cur_wp_z = end.z; //revert on error
}
CalculateNewPosition2(cur_wp_x, cur_wp_y, cur_wp_z, GetRunspeed(), true);
return;
}
*/
/*
//cant run along our vector at all....
//one last ditch effort... try to move to the side a little
//along the minor component of the fear vector.
//try it in one direction first...
if(fear_vector.x < fear_vector.y) {
end.x = start.x + fear_vector.x * 3;
end.y = start.y;
} else {
end.x = start.x;
end.y = start.y + fear_vector.y * 3;
}
end.z = start.z + 3; //a little lift as always
if(!zone->zonemap->LineIntersectsZone(start, end, 0.5, &hit, nullptr)) {
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing: From (%.2f, %.2f, %.2f) strafe 1 to (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), end.x, end.y, end.z);
#endif
//we can run along this vector without hitting anything...
cur_wp_x = end.x - 0.4 * fear_vector.x;
cur_wp_y = end.y - 0.4 * fear_vector.y;
cur_wp_z = end.z - 3;
CalculateNewPosition2(cur_wp_x, cur_wp_y, cur_wp_z, GetRunspeed(), true);
return;
}
//now the other...
if(fear_vector.x < fear_vector.y) {
end.x = start.x + fear_vector.x * 3;
end.y = start.y;
} else {
end.x = start.x;
end.y = start.y + fear_vector.y * 3;
}
end.z = start.z + 3; //a little lift as always
if(!zone->zonemap->LineIntersectsZone(start, end, 0.5, &hit, nullptr)) {
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing: From (%.2f, %.2f, %.2f) strafe 2 to (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), end.x, end.y, end.z);
#endif
//we can run along this vector without hitting anything...
cur_wp_x = end.x - 0.4 * fear_vector.x;
cur_wp_y = end.y - 0.4 * fear_vector.y;
cur_wp_z = end.z - 3;
CalculateNewPosition2(cur_wp_x, cur_wp_y, cur_wp_z, GetRunspeed(), true);
return;
}
//if we get here... we have wasted enough CPU cycles
//just call it quits on fear pathing...
//send them to normalhit and then stop
cur_wp_x = normalhit.x;
cur_wp_y = normalhit.y;
cur_wp_z = GetZ();
fear_state = fearStateRunningToStick;
#ifdef FEAR_PATHING_DEBUG
LogFile->write(EQEMuLog::Debug, "Fear Pathing: From (%.2f, %.2f, %.2f) final move to (%.2f, %.2f, %.2f)",
GetX(), GetY(), GetZ(), normalhit.x, normalhit.y, normalhit.z);
#endif
#endif //OLD_FEAR_PATHING
}*/

View File

@ -225,7 +225,7 @@ bool Client::CanFish() {
return false;
}
if(zone->zonemap!=nullptr && zone->watermap != nullptr && RuleB(Watermap, CheckForWaterWhenFishing)) {
if(zone->zonemap != nullptr && zone->watermap != nullptr && RuleB(Watermap, CheckForWaterWhenFishing)) {
float RodX, RodY, RodZ;
// Tweak Rod and LineLength if required
const float RodLength = RuleR(Watermap, FishingRodLength);
@ -240,24 +240,22 @@ bool Client::CanFish() {
// Do BestZ to find where the line hanging from the rod intersects the water (if it is water).
// and go 1 unit into the water.
VERTEX dest;
Map::Vertex dest;
dest.x = RodX;
dest.y = RodY;
dest.z = z_pos+10;
NodeRef n = zone->zonemap->SeekNode( zone->zonemap->GetRoot(), dest.x, dest.y);
if(n != NODE_NONE) {
RodZ = zone->zonemap->FindBestZ(n, dest, nullptr, nullptr) - 1;
bool in_lava = zone->watermap->InLava(RodX, RodY, RodZ);
bool in_water = zone->watermap->InWater(RodX, RodY, RodZ) || zone->watermap->InVWater(RodX, RodY, RodZ);
//Message(0, "Rod is at %4.3f, %4.3f, %4.3f, InWater says %d, InLava says %d", RodX, RodY, RodZ, in_water, in_lava);
if (in_lava) {
Message_StringID(MT_Skills, FISHING_LAVA); //Trying to catch a fire elemental or something?
return false;
}
if((!in_water) || (z_pos-RodZ)>LineLength) { //Didn't hit the water OR the water is too far below us
Message_StringID(MT_Skills, FISHING_LAND); //Trying to catch land sharks perhaps?
return false;
}
RodZ = zone->zonemap->FindBestZ(dest, nullptr) - 1;
bool in_lava = zone->watermap->InLava(RodX, RodY, RodZ);
bool in_water = zone->watermap->InWater(RodX, RodY, RodZ) || zone->watermap->InVWater(RodX, RodY, RodZ);
//Message(0, "Rod is at %4.3f, %4.3f, %4.3f, InWater says %d, InLava says %d", RodX, RodY, RodZ, in_water, in_lava);
if (in_lava) {
Message_StringID(MT_Skills, FISHING_LAVA); //Trying to catch a fire elemental or something?
return false;
}
if((!in_water) || (z_pos-RodZ)>LineLength) { //Didn't hit the water OR the water is too far below us
Message_StringID(MT_Skills, FISHING_LAND); //Trying to catch land sharks perhaps?
return false;
}
}
return true;

268
zone/map.cpp Normal file
View File

@ -0,0 +1,268 @@
#include "../common/debug.h"
#include "../common/MiscFunctions.h"
#include "map.h"
#include "RaycastMesh.h"
#include "zone.h"
#include <stdint.h>
#include <algorithm>
#include <locale>
#include <vector>
struct Map::impl
{
RaycastMesh *rm;
};
Map::Map() {
imp = nullptr;
}
Map::~Map() {
if(imp) {
imp->rm->release();
}
}
float Map::FindBestZ(Vertex &start, Vertex *result) const {
if (!imp)
return false;
Vertex tmp;
if(!result)
result = &tmp;
start.z += RuleI(Map, FindBestZHeightAdjust);
Vertex from = { start.x, start.y, start.z };
Vertex to = { start.x, start.y, BEST_Z_INVALID };
float hit_distance;
bool hit = false;
hit = imp->rm->raycast((const RmReal*)&from, (const RmReal*)&to, (RmReal*)result, nullptr, &hit_distance);
if(hit) {
return result->z;
}
// Find nearest Z above us
to.z = -BEST_Z_INVALID;
hit = imp->rm->raycast((const RmReal*)&from, (const RmReal*)&to, (RmReal*)result, nullptr, &hit_distance);
if (hit)
{
return result->z;
}
return BEST_Z_INVALID;
}
bool Map::LineIntersectsZone(Vertex start, Vertex end, float step, Vertex *result) const {
if(!imp)
return false;
return imp->rm->raycast((const RmReal*)&start, (const RmReal*)&end, (RmReal*)result, nullptr, nullptr);
}
bool Map::LineIntersectsZoneNoZLeaps(Vertex start, Vertex end, float step_mag, Vertex *result) const {
if (!imp)
return false;
float z = BEST_Z_INVALID;
Vertex step;
Vertex cur;
cur.x = start.x;
cur.y = start.y;
cur.z = start.z;
step.x = end.x - start.x;
step.y = end.y - start.y;
step.z = end.z - start.z;
float factor = step_mag / sqrt(step.x*step.x + step.y*step.y + step.z*step.z);
step.x *= factor;
step.y *= factor;
step.z *= factor;
int steps = 0;
if (step.x > 0 && step.x < 0.001f)
step.x = 0.001f;
if (step.y > 0 && step.y < 0.001f)
step.y = 0.001f;
if (step.z > 0 && step.z < 0.001f)
step.z = 0.001f;
if (step.x < 0 && step.x > -0.001f)
step.x = -0.001f;
if (step.y < 0 && step.y > -0.001f)
step.y = -0.001f;
if (step.z < 0 && step.z > -0.001f)
step.z = -0.001f;
//while we are not past end
//always do this once, even if start == end.
while(cur.x != end.x || cur.y != end.y || cur.z != end.z)
{
steps++;
Vertex me;
me.x = cur.x;
me.y = cur.y;
me.z = cur.z;
Vertex hit;
float best_z = FindBestZ(me, &hit);
float diff = best_z - z;
diff = diff < 0 ? -diff : diff;
if (z == -999999 || best_z == -999999 || diff < 12.0)
z = best_z;
else
return true;
//look at current location
if(LineIntersectsZone(start, end, step_mag, result))
{
return true;
}
//move 1 step
if (cur.x != end.x)
cur.x += step.x;
if (cur.y != end.y)
cur.y += step.y;
if (cur.z != end.z)
cur.z += step.z;
//watch for end conditions
if ( (cur.x > end.x && end.x >= start.x) || (cur.x < end.x && end.x <= start.x) || (step.x == 0) ) {
cur.x = end.x;
}
if ( (cur.y > end.y && end.y >= start.y) || (cur.y < end.y && end.y <= start.y) || (step.y == 0) ) {
cur.y = end.y;
}
if ( (cur.z > end.z && end.z >= start.z) || (cur.z < end.z && end.z < start.z) || (step.z == 0) ) {
cur.z = end.z;
}
}
//walked entire line and didnt run into anything...
return false;
}
bool Map::CheckLoS(Vertex myloc, Vertex oloc) const {
if(!imp)
return false;
return !imp->rm->raycast((const RmReal*)&myloc, (const RmReal*)&oloc, nullptr, nullptr, nullptr);
}
Map *Map::LoadMapFile(std::string file) {
std::string filename = MAP_DIR;
filename += "/";
std::transform(file.begin(), file.end(), file.begin(), ::tolower);
filename += file;
filename += ".map";
Map *m = new Map();
if (m->Load(filename)) {
return m;
}
delete m;
return nullptr;
}
bool Map::Load(std::string filename) {
FILE *f = fopen(filename.c_str(), "rb");
if(f) {
uint32_t version;
if(fread(&version, sizeof(version), 1, f) != 1) {
fclose(f);
return false;
}
if(version == 0x01000000) {
bool v = LoadV1(f);
fclose(f);
return v;
} else if(version == 0x02000000) {
bool v = LoadV2(f);
fclose(f);
return v;
} else {
fclose(f);
return false;
}
}
return false;
}
bool Map::LoadV1(FILE *f) {
uint32_t face_count;
uint16_t node_count;
uint32_t facelist_count;
if(fread(&face_count, sizeof(face_count), 1, f) != 1) {
return false;
}
if(fread(&node_count, sizeof(node_count), 1, f) != 1) {
return false;
}
if(fread(&facelist_count, sizeof(facelist_count), 1, f) != 1) {
return false;
}
std::vector<Vertex> verts;
std::vector<uint32_t> indices;
for(uint32_t i = 0; i < face_count; ++i) {
Vertex a;
Vertex b;
Vertex c;
float normals[4];
if(fread(&a, sizeof(Vertex), 1, f) != 1) {
return false;
}
if(fread(&b, sizeof(Vertex), 1, f) != 1) {
return false;
}
if(fread(&c, sizeof(Vertex), 1, f) != 1) {
return false;
}
if(fread(normals, sizeof(normals), 1, f) != 1) {
return false;
}
size_t sz = verts.size();
verts.push_back(a);
indices.push_back((uint32_t)sz);
verts.push_back(b);
indices.push_back((uint32_t)sz + 1);
verts.push_back(c);
indices.push_back((uint32_t)sz + 2);
}
if(imp) {
imp->rm->release();
imp->rm = nullptr;
} else {
imp = new impl;
}
imp->rm = createRaycastMesh((RmUint32)verts.size(), (const RmReal*)&verts[0], face_count, &indices[0]);
if(!imp->rm) {
delete imp;
imp = nullptr;
return false;
}
return true;
}
bool Map::LoadV2(FILE *f) {
return false;
}

67
zone/map.h Normal file
View File

@ -0,0 +1,67 @@
/*
EQEMu: Everquest Server Emulator
Copyright (C) 2001-2014 EQEMu Development Team (http://eqemulator.net)
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY except by those people which sell it, which
are required to give you total support for your newly bought product;
without even the implied warranty of MERCHANTABILITY or FITNESS FOR
A PARTICULAR PURPOSE. See the GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
#ifndef ZONE_MAP_H
#define ZONE_MAP_H
#include <stdio.h>
#include <string>
#define BEST_Z_INVALID -99999
class Map
{
public:
#pragma pack(1)
struct Vertex
{
Vertex() : x(0.0f), y(0.0f), z(0.0f) { }
Vertex(float _x, float _y, float _z) : x(_x), y(_y), z(_z) { }
~Vertex() { }
bool operator==(const Vertex &v) const
{
return((v.x == x) && (v.y == y) && (v.z == z));
}
float x;
float y;
float z;
};
#pragma pack()
Map();
~Map();
float FindBestZ(Vertex &start, Vertex *result) const;
bool LineIntersectsZone(Vertex start, Vertex end, float step, Vertex *result) const;
bool LineIntersectsZoneNoZLeaps(Vertex start, Vertex end, float step_mag, Vertex *result) const;
bool CheckLoS(Vertex myloc, Vertex oloc) const;
bool Load(std::string filename);
static Map *LoadMapFile(std::string file);
private:
bool LoadV1(FILE *f);
bool LoadV2(FILE *f);
struct impl;
impl *imp;
};
#endif

View File

@ -2933,22 +2933,17 @@ void Mob::SetTarget(Mob* mob) {
float Mob::FindGroundZ(float new_x, float new_y, float z_offset)
{
float ret = -999999;
if (zone->zonemap != 0)
if (zone->zonemap != nullptr)
{
NodeRef pnode = zone->zonemap->SeekNode( zone->zonemap->GetRoot(), new_x, new_y );
if (pnode != NODE_NONE)
Map::Vertex me;
me.x = new_x;
me.y = new_y;
me.z = z_pos+z_offset;
Map::Vertex hit;
float best_z = zone->zonemap->FindBestZ(me, &hit);
if (best_z != -999999)
{
VERTEX me;
me.x = new_x;
me.y = new_y;
me.z = z_pos+z_offset;
VERTEX hit;
FACE *onhit;
float best_z = zone->zonemap->FindBestZ(pnode, me, &hit, &onhit);
if (best_z != -999999)
{
ret = best_z;
}
ret = best_z;
}
}
return ret;
@ -2960,20 +2955,15 @@ float Mob::GetGroundZ(float new_x, float new_y, float z_offset)
float ret = -999999;
if (zone->zonemap != 0)
{
NodeRef pnode = zone->zonemap->SeekNode( zone->zonemap->GetRoot(), new_x, new_y );
if (pnode != NODE_NONE)
Map::Vertex me;
me.x = new_x;
me.y = new_y;
me.z = z_pos+z_offset;
Map::Vertex hit;
float best_z = zone->zonemap->FindBestZ(me, &hit);
if (best_z != -999999)
{
VERTEX me;
me.x = new_x;
me.y = new_y;
me.z = z_pos+z_offset;
VERTEX hit;
FACE *onhit;
float best_z = zone->zonemap->FindBestZ(pnode, me, &hit, &onhit);
if (best_z != -999999)
{
ret = best_z;
}
ret = best_z;
}
}
return ret;

View File

@ -417,7 +417,7 @@ public:
void MakeSpawnUpdate(PlayerPositionUpdateServer_Struct* spu);
void SendPosition();
void SetFlyMode(uint8 flymode);
inline void Teleport(VERTEX NewPosition) { x_pos = NewPosition.x; y_pos = NewPosition.y;
inline void Teleport(Map::Vertex NewPosition) { x_pos = NewPosition.x; y_pos = NewPosition.y;
z_pos = NewPosition.z; };
//AI
@ -447,7 +447,6 @@ public:
void ClearFeignMemory();
void PrintHateListToClient(Client *who) { hate_list.PrintToClient(who); }
std::list<tHateEntry*>& GetHateList() { return hate_list.GetHateList(); }
bool CheckLos(Mob* other);
bool CheckLosFN(Mob* other);
bool CheckLosFN(float posX, float posY, float posZ, float mobSize);
inline void SetChanged() { pLastChange = Timer::GetCurrentTime(); }
@ -981,7 +980,7 @@ protected:
bool HasDied();
void CalculateNewFearpoint();
float FindGroundZ(float new_x, float new_y, float z_offset=0.0);
VERTEX UpdatePath(float ToX, float ToY, float ToZ, float Speed, bool &WaypointChange, bool &NodeReached);
Map::Vertex UpdatePath(float ToX, float ToY, float ToZ, float Speed, bool &WaypointChange, bool &NodeReached);
void PrintRoute();
void UpdateRuneFlags();
@ -1146,8 +1145,8 @@ protected:
// Pathing
//
VERTEX PathingDestination;
VERTEX PathingLastPosition;
Map::Vertex PathingDestination;
Map::Vertex PathingLastPosition;
int PathingLoopCount;
int PathingLastNodeVisited;
std::list<int> Route;

View File

@ -21,7 +21,7 @@
extern Zone *zone;
float VertexDistance(VERTEX a, VERTEX b)
float VertexDistance(Map::Vertex a, Map::Vertex b)
{
float xdist = a.x - b.x;
float ydist = a.y - b.y;
@ -29,7 +29,7 @@ float VertexDistance(VERTEX a, VERTEX b)
return sqrtf(xdist * xdist + ydist * ydist + zdist * zdist);
}
float VertexDistanceNoRoot(VERTEX a, VERTEX b)
float VertexDistanceNoRoot(Map::Vertex a, Map::Vertex b)
{
float xdist = a.x - b.x;
float ydist = a.y - b.y;
@ -187,9 +187,9 @@ void PathManager::PrintPathing()
}
}
VERTEX PathManager::GetPathNodeCoordinates(int NodeNumber, bool BestZ)
Map::Vertex PathManager::GetPathNodeCoordinates(int NodeNumber, bool BestZ)
{
VERTEX Result;
Map::Vertex Result;
if(NodeNumber < Head.PathNodeCount)
{
@ -335,12 +335,12 @@ std::list<int> PathManager::FindRoute(int startID, int endID)
}
bool CheckLOSBetweenPoints(VERTEX start, VERTEX end) {
bool CheckLOSBetweenPoints(Map::Vertex start, Map::Vertex end) {
VERTEX hit;
FACE *face;
Map::Vertex hit;
if((zone->zonemap) && (zone->zonemap->LineIntersectsZone(start, end, 1, &hit, &face))) return false;
if((zone->zonemap) && (zone->zonemap->LineIntersectsZone(start, end, 1, &hit)))
return false;
return true;
}
@ -350,7 +350,7 @@ bool SortPathNodesByDistance(PathNodeSortStruct n1, PathNodeSortStruct n2)
return n1.Distance < n2.Distance;
}
std::list<int> PathManager::FindRoute(VERTEX Start, VERTEX End)
std::list<int> PathManager::FindRoute(Map::Vertex Start, Map::Vertex End)
{
_log(PATHING__DEBUG, "FindRoute(%8.3f, %8.3f, %8.3f, %8.3f, %8.3f, %8.3f)", Start.x, Start.y, Start.z, End.x, End.y, End.z);
@ -388,7 +388,7 @@ std::list<int> PathManager::FindRoute(VERTEX Start, VERTEX End)
{
_log(PATHING__DEBUG, "Checking Reachability of Node %i from Start Position.", PathNodes[(*Iterator).id].id);
if(!zone->zonemap->LineIntersectsZone(Start, PathNodes[(*Iterator).id].v, 1.0f, nullptr, nullptr))
if(!zone->zonemap->LineIntersectsZone(Start, PathNodes[(*Iterator).id].v, 1.0f, nullptr))
{
ClosestPathNodeToStart = (*Iterator).id;
break;
@ -429,7 +429,7 @@ std::list<int> PathManager::FindRoute(VERTEX Start, VERTEX End)
End.x, End.y, End.z,
PathNodes[(*Iterator).id].v.x, PathNodes[(*Iterator).id].v.y, PathNodes[(*Iterator).id].v.z);
if(!zone->zonemap->LineIntersectsZone(End, PathNodes[(*Iterator).id].v, 1.0f, nullptr, nullptr))
if(!zone->zonemap->LineIntersectsZone(End, PathNodes[(*Iterator).id].v, 1.0f, nullptr))
{
ClosestPathNodeToEnd = (*Iterator).id;
break;
@ -469,7 +469,7 @@ std::list<int> PathManager::FindRoute(VERTEX Start, VERTEX End)
if((*Second) < 0)
break;
if(!zone->zonemap->LineIntersectsZone(Start, PathNodes[(*Second)].v, 1.0f, nullptr, nullptr)
if(!zone->zonemap->LineIntersectsZone(Start, PathNodes[(*Second)].v, 1.0f, nullptr)
&& zone->pathing->NoHazards(Start, PathNodes[(*Second)].v))
{
noderoute.erase(First);
@ -502,7 +502,7 @@ std::list<int> PathManager::FindRoute(VERTEX Start, VERTEX End)
if((*Second) < 0)
break;
if(!zone->zonemap->LineIntersectsZone(End, PathNodes[(*Second)].v, 1.0f, nullptr, nullptr)
if(!zone->zonemap->LineIntersectsZone(End, PathNodes[(*Second)].v, 1.0f, nullptr)
&& zone->pathing->NoHazards(End, PathNodes[(*Second)].v))
{
noderoute.erase(First);
@ -652,19 +652,19 @@ void PathManager::SimpleMeshTest()
fflush(stdout);
}
VERTEX Mob::UpdatePath(float ToX, float ToY, float ToZ, float Speed, bool &WaypointChanged, bool &NodeReached)
Map::Vertex Mob::UpdatePath(float ToX, float ToY, float ToZ, float Speed, bool &WaypointChanged, bool &NodeReached)
{
WaypointChanged = false;
NodeReached = false;
VERTEX NodeLoc;
Map::Vertex NodeLoc;
VERTEX From(GetX(), GetY(), GetZ());
Map::Vertex From(GetX(), GetY(), GetZ());
VERTEX HeadPosition(From.x, From.y, From.z + (GetSize() < 6.0 ? 6 : GetSize()) * HEAD_POSITION);
Map::Vertex HeadPosition(From.x, From.y, From.z + (GetSize() < 6.0 ? 6 : GetSize()) * HEAD_POSITION);
VERTEX To(ToX, ToY, ToZ);
Map::Vertex To(ToX, ToY, ToZ);
bool SameDestination = (To == PathingDestination);
@ -761,7 +761,7 @@ VERTEX Mob::UpdatePath(float ToX, float ToY, float ToZ, float Speed, bool &Waypo
if((Distance <= RuleR(Pathing, MinDistanceForLOSCheckShort))
&& (ABS(From.z - To.z) <= RuleR(Pathing, ZDiffThreshold)))
{
if(!zone->zonemap->LineIntersectsZone(HeadPosition, To, 1.0f, nullptr, nullptr))
if(!zone->zonemap->LineIntersectsZone(HeadPosition, To, 1.0f, nullptr))
PathingLOSState = HaveLOS;
else
PathingLOSState = NoLOS;
@ -854,7 +854,7 @@ VERTEX Mob::UpdatePath(float ToX, float ToY, float ToZ, float Speed, bool &Waypo
if((Distance <= RuleR(Pathing, MinDistanceForLOSCheckShort))
&& (ABS(From.z - To.z) <= RuleR(Pathing, ZDiffThreshold)))
{
if(!zone->zonemap->LineIntersectsZone(HeadPosition, To, 1.0f, nullptr, nullptr))
if(!zone->zonemap->LineIntersectsZone(HeadPosition, To, 1.0f, nullptr))
PathingLOSState = HaveLOS;
else
PathingLOSState = NoLOS;
@ -893,7 +893,7 @@ VERTEX Mob::UpdatePath(float ToX, float ToY, float ToZ, float Speed, bool &Waypo
&& (ABS(From.z - To.z) <= RuleR(Pathing, ZDiffThreshold)))
{
mlog(PATHING__DEBUG, " Checking for short LOS at distance %8.3f.", Distance);
if(!zone->zonemap->LineIntersectsZone(HeadPosition, To, 1.0f, nullptr, nullptr))
if(!zone->zonemap->LineIntersectsZone(HeadPosition, To, 1.0f, nullptr))
PathingLOSState = HaveLOS;
else
PathingLOSState = NoLOS;
@ -1046,7 +1046,7 @@ VERTEX Mob::UpdatePath(float ToX, float ToY, float ToZ, float Speed, bool &Waypo
{
mlog(PATHING__DEBUG, " Checking for long LOS at distance %8.3f.", Distance);
if(!zone->zonemap->LineIntersectsZone(HeadPosition, To, 1.0f, nullptr, nullptr))
if(!zone->zonemap->LineIntersectsZone(HeadPosition, To, 1.0f, nullptr))
PathingLOSState = HaveLOS;
else
PathingLOSState = NoLOS;
@ -1090,7 +1090,7 @@ VERTEX Mob::UpdatePath(float ToX, float ToY, float ToZ, float Speed, bool &Waypo
}
int PathManager::FindNearestPathNode(VERTEX Position)
int PathManager::FindNearestPathNode(Map::Vertex Position)
{
// Find the nearest PathNode we have LOS to.
@ -1126,7 +1126,7 @@ int PathManager::FindNearestPathNode(VERTEX Position)
{
_log(PATHING__DEBUG, "Checking Reachability of Node %i from Start Position.", PathNodes[(*Iterator).id].id);
if(!zone->zonemap->LineIntersectsZone(Position, PathNodes[(*Iterator).id].v, 1.0f, nullptr, nullptr))
if(!zone->zonemap->LineIntersectsZone(Position, PathNodes[(*Iterator).id].v, 1.0f, nullptr))
{
ClosestPathNodeToStart = (*Iterator).id;
break;
@ -1140,13 +1140,13 @@ int PathManager::FindNearestPathNode(VERTEX Position)
return ClosestPathNodeToStart;
}
bool PathManager::NoHazards(VERTEX From, VERTEX To)
bool PathManager::NoHazards(Map::Vertex From, Map::Vertex To)
{
// Test the Z coordinate at the mid point.
//
VERTEX MidPoint((From.x + To.x) / 2, (From.y + To.y) / 2, From.z);
Map::Vertex MidPoint((From.x + To.x) / 2, (From.y + To.y) / 2, From.z);
float NewZ = zone->zonemap->FindBestZ(MAP_ROOT_NODE, MidPoint, nullptr, nullptr);
float NewZ = zone->zonemap->FindBestZ(MidPoint, nullptr);
if(ABS(NewZ - From.z) > RuleR(Pathing, ZDiffThreshold))
{
@ -1164,10 +1164,10 @@ bool PathManager::NoHazards(VERTEX From, VERTEX To)
return true;
}
bool PathManager::NoHazardsAccurate(VERTEX From, VERTEX To)
bool PathManager::NoHazardsAccurate(Map::Vertex From, Map::Vertex To)
{
float stepx, stepy, stepz, curx, cury, curz;
VERTEX cur = From;
Map::Vertex cur = From;
float last_z = From.z;
float step_size = 1.0;
@ -1181,13 +1181,13 @@ bool PathManager::NoHazardsAccurate(VERTEX From, VERTEX To)
stepy = (float)To.y - cury;
stepz = (float)To.z - curz;
float factor = sqrt(stepx*stepx + stepy*stepy + stepz*stepz);
stepx = (stepx/factor)*step_size;
stepy = (stepy/factor)*step_size;
stepz = (stepz/factor)*step_size;
stepx = (stepx / factor)*step_size;
stepy = (stepy / factor)*step_size;
stepz = (stepz / factor)*step_size;
VERTEX TestPoint(curx, cury, curz);
float NewZ = zone->zonemap->FindBestZ(MAP_ROOT_NODE, TestPoint, nullptr, nullptr);
if(ABS(NewZ - last_z) > 5.0)
Map::Vertex TestPoint = { curx, cury, curz };
float NewZ = zone->zonemap->FindBestZ(TestPoint, nullptr);
if (ABS(NewZ - last_z) > 5.0f)
{
_log(PATHING__DEBUG, " HAZARD DETECTED moving from %8.3f, %8.3f, %8.3f to %8.3f, %8.3f, %8.3f. Best Z %8.3f, Z Change is %8.3f",
From.x, From.y, From.z, TestPoint.x, TestPoint.y, TestPoint.z, NewZ, NewZ - From.z);
@ -1195,49 +1195,45 @@ bool PathManager::NoHazardsAccurate(VERTEX From, VERTEX To)
}
last_z = NewZ;
if(zone->watermap)
if (zone->watermap)
{
NodeRef n = zone->zonemap->SeekNode( zone->zonemap->GetRoot(), TestPoint.x, TestPoint.y);
if(n != NODE_NONE)
if (zone->watermap->InLiquid(From.x, From.y, From.z) || zone->watermap->InLiquid(To.x, To.y, To.z))
{
if(zone->watermap->InLiquid(From.x, From.y, From.z) || zone->watermap->InLiquid(To.x, To.y, To.z))
{
break;
}
break;
}
if(zone->watermap->InLiquid(TestPoint.x, TestPoint.y, NewZ))
if (zone->watermap->InLiquid(TestPoint.x, TestPoint.y, NewZ))
{
Map::Vertex TestPointWater = { TestPoint.x, TestPoint.y, NewZ - 0.5f };
Map::Vertex TestPointWaterDest = TestPointWater;
Map::Vertex hit;
TestPointWaterDest.z -= 500;
float best_z2 = -999990;
if (zone->zonemap->LineIntersectsZone(TestPointWater, TestPointWaterDest, 1.0f, &hit))
{
VERTEX TestPointWater(TestPoint.x, TestPoint.y, NewZ-0.5);
VERTEX TestPointWaterDest(TestPointWater);
VERTEX hit;
TestPointWaterDest.z -= 500;
float best_z2 = -999990;
if(zone->zonemap->LineIntersectsNode(n, TestPointWater, TestPointWaterDest, &hit, nullptr))
best_z2 = hit.z;
}
if (best_z2 == -999990)
{
_log(PATHING__DEBUG, " HAZARD DETECTED, really deep water/lava!");
return false;
}
else
{
if (ABS(NewZ - best_z2) > RuleR(Pathing, ZDiffThreshold))
{
best_z2 = hit.z;
}
if(best_z2 == -999990)
{
_log(PATHING__DEBUG, " HAZARD DETECTED, really deep water/lava!");
_log(PATHING__DEBUG, " HAZARD DETECTED, water is fairly deep at %8.3f units deep", ABS(NewZ - best_z2));
return false;
}
else
{
if(ABS(NewZ - best_z2) > RuleR(Pathing, ZDiffThreshold))
{
_log(PATHING__DEBUG, " HAZARD DETECTED, water is fairly deep at %8.3f units deep", ABS(NewZ - best_z2));
return false;
}
else
{
_log(PATHING__DEBUG, " HAZARD NOT DETECTED, water is shallow at %8.3f units deep", ABS(NewZ - best_z2));
}
_log(PATHING__DEBUG, " HAZARD NOT DETECTED, water is shallow at %8.3f units deep", ABS(NewZ - best_z2));
}
}
else
{
_log(PATHING__DEBUG, "Hazard point not in water or lava!");
}
}
else
{
_log(PATHING__DEBUG, "Hazard point not in water or lava!");
}
}
else
@ -1253,12 +1249,11 @@ bool PathManager::NoHazardsAccurate(VERTEX From, VERTEX To)
cur.y = cury;
cur.z = curz;
if(ABS(curx - To.x) < step_size) cur.x = To.x;
if(ABS(cury - To.y) < step_size) cur.y = To.y;
if(ABS(curz - To.z) < step_size) cur.z = To.z;
if (ABS(curx - To.x) < step_size) cur.x = To.x;
if (ABS(cury - To.y) < step_size) cur.y = To.y;
if (ABS(curz - To.z) < step_size) cur.z = To.z;
}
while(cur.x != To.x || cur.y != To.y || cur.z != To.z);
} while (cur.x != To.x || cur.y != To.y || cur.z != To.z);
return true;
}
@ -2001,8 +1996,8 @@ void PathManager::MoveNode(Client *c)
if(zone->zonemap)
{
VERTEX loc(c->GetX(), c->GetY(), c->GetZ());
Node->bestz = zone->zonemap->FindBestZ(MAP_ROOT_NODE, loc, nullptr, nullptr);
Map::Vertex loc(c->GetX(), c->GetY(), c->GetZ());
Node->bestz = zone->zonemap->FindBestZ(loc, nullptr);
}
else
{
@ -2072,14 +2067,14 @@ bool PathManager::NodesConnected(PathNode *a, PathNode *b)
return false;
}
bool PathManager::CheckLosFN(VERTEX a, VERTEX b)
bool PathManager::CheckLosFN(Map::Vertex a, Map::Vertex b)
{
if(zone->zonemap)
{
VERTEX hit;
Map::Vertex hit;
VERTEX myloc;
VERTEX oloc;
Map::Vertex myloc;
Map::Vertex oloc;
myloc.x = a.x;
myloc.y = a.y;
@ -2090,7 +2085,7 @@ bool PathManager::CheckLosFN(VERTEX a, VERTEX b)
oloc.z = b.z;
if(zone->zonemap->LineIntersectsZone(myloc, oloc, 1.0f, nullptr, nullptr))
if(zone->zonemap->LineIntersectsZone(myloc, oloc, 1.0f, nullptr))
{
return false;
}

View File

@ -31,7 +31,7 @@ struct NeighbourNode {
struct PathNode {
uint16 id;
VERTEX v;
Map::Vertex v;
float bestz;
NeighbourNode Neighbours[PATHNODENEIGHBOURS];
};
@ -61,17 +61,17 @@ public:
static PathManager *LoadPathFile(const char *ZoneName);
bool loadPaths(FILE *fp);
void PrintPathing();
std::list<int> FindRoute(VERTEX Start, VERTEX End);
std::list<int> FindRoute(Map::Vertex Start, Map::Vertex End);
std::list<int> FindRoute(int startID, int endID);
VERTEX GetPathNodeCoordinates(int NodeNumber, bool BestZ = true);
bool CheckLosFN(VERTEX a, VERTEX b);
Map::Vertex GetPathNodeCoordinates(int NodeNumber, bool BestZ = true);
bool CheckLosFN(Map::Vertex a, Map::Vertex b);
void SpawnPathNodes();
void MeshTest();
void SimpleMeshTest();
int FindNearestPathNode(VERTEX Position);
bool NoHazards(VERTEX From, VERTEX To);
bool NoHazardsAccurate(VERTEX From, VERTEX To);
int FindNearestPathNode(Map::Vertex Position);
bool NoHazards(Map::Vertex From, Map::Vertex To);
bool NoHazardsAccurate(Map::Vertex From, Map::Vertex To);
void OpenDoors(int Node1, int Node2, Mob* ForWho);
PathNode* FindPathNodeByCoordinates(float x, float y, float z);

View File

@ -234,9 +234,9 @@ void NPC::UpdateWaypoint(int wp_index)
if(!RuleB(Watermap, CheckForWaterAtWaypoints) || !zone->HasWaterMap() ||
(zone->HasWaterMap() && !zone->watermap->InWater(cur_wp_x, cur_wp_y, cur_wp_z)))
{
VERTEX dest(cur_wp_x, cur_wp_y, cur_wp_z);
Map::Vertex dest(cur_wp_x, cur_wp_y, cur_wp_z);
float newz = zone->zonemap->FindBestZ(MAP_ROOT_NODE, dest, nullptr, nullptr);
float newz = zone->zonemap->FindBestZ(dest, nullptr);
if( (newz > -2000) && ABS(newz - dest.z) < RuleR(Map, FixPathingZMaxDeltaWaypoint))
cur_wp_z = newz + 1;
@ -564,9 +564,9 @@ bool Mob::MakeNewPositionAndSendUpdate(float x, float y, float z, float speed, b
if(!RuleB(Watermap, CheckForWaterWhenMoving) || !zone->HasWaterMap() ||
(zone->HasWaterMap() && !zone->watermap->InWater(x_pos, y_pos, z_pos)))
{
VERTEX dest(x_pos, y_pos, z_pos);
Map::Vertex dest(x_pos, y_pos, z_pos);
float newz = zone->zonemap->FindBestZ(MAP_ROOT_NODE, dest, nullptr, nullptr);
float newz = zone->zonemap->FindBestZ(dest, nullptr);
mlog(AI__WAYPOINTS, "BestZ returned %4.3f at %4.3f, %4.3f, %4.3f", newz,x_pos,y_pos,z_pos);
@ -693,9 +693,9 @@ bool Mob::MakeNewPositionAndSendUpdate(float x, float y, float z, float speed, b
if(!RuleB(Watermap, CheckForWaterWhenMoving) || !zone->HasWaterMap() ||
(zone->HasWaterMap() && !zone->watermap->InWater(x_pos, y_pos, z_pos)))
{
VERTEX dest(x_pos, y_pos, z_pos);
Map::Vertex dest(x_pos, y_pos, z_pos);
float newz = zone->zonemap->FindBestZ(MAP_ROOT_NODE, dest, nullptr, nullptr);
float newz = zone->zonemap->FindBestZ(dest, nullptr);
mlog(AI__WAYPOINTS, "BestZ returned %4.3f at %4.3f, %4.3f, %4.3f", newz,x_pos,y_pos,z_pos);
@ -818,9 +818,9 @@ bool Mob::CalculateNewPosition(float x, float y, float z, float speed, bool chec
if(!RuleB(Watermap, CheckForWaterWhenMoving) || !zone->HasWaterMap() ||
(zone->HasWaterMap() && !zone->watermap->InWater(x_pos, y_pos, z_pos)))
{
VERTEX dest(x_pos, y_pos, z_pos);
Map::Vertex dest(x_pos, y_pos, z_pos);
float newz = zone->zonemap->FindBestZ(MAP_ROOT_NODE, dest, nullptr, nullptr);
float newz = zone->zonemap->FindBestZ(dest, nullptr);
mlog(AI__WAYPOINTS, "BestZ returned %4.3f at %4.3f, %4.3f, %4.3f", newz,x_pos,y_pos,z_pos);
@ -926,9 +926,9 @@ void NPC::AssignWaypoints(int32 grid) {
if(!RuleB(Watermap, CheckWaypointsInWaterWhenLoading) || !zone->HasWaterMap() ||
(zone->HasWaterMap() && !zone->watermap->InWater(newwp.x, newwp.y, newwp.z)))
{
VERTEX dest(newwp.x, newwp.y, newwp.z);
Map::Vertex dest(newwp.x, newwp.y, newwp.z);
float newz = zone->zonemap->FindBestZ(MAP_ROOT_NODE, dest, nullptr, nullptr);
float newz = zone->zonemap->FindBestZ(dest, nullptr);
if( (newz > -2000) && ABS(newz-dest.z) < RuleR(Map, FixPathingZMaxDeltaLoading))
newwp.z = newz + 1;
@ -981,9 +981,9 @@ void Mob::SendTo(float new_x, float new_y, float new_z) {
if(!RuleB(Watermap, CheckForWaterOnSendTo) || !zone->HasWaterMap() ||
(zone->HasWaterMap() && !zone->watermap->InWater(x_pos, y_pos, z_pos)))
{
VERTEX dest(x_pos, y_pos, z_pos);
Map::Vertex dest(x_pos, y_pos, z_pos);
float newz = zone->zonemap->FindBestZ(MAP_ROOT_NODE, dest, nullptr, nullptr);
float newz = zone->zonemap->FindBestZ(dest, nullptr);
mlog(AI__WAYPOINTS, "BestZ returned %4.3f at %4.3f, %4.3f, %4.3f", newz,x_pos,y_pos,z_pos);
@ -1012,9 +1012,9 @@ void Mob::SendToFixZ(float new_x, float new_y, float new_z) {
if(!RuleB(Watermap, CheckForWaterOnSendTo) || !zone->HasWaterMap() ||
(zone->HasWaterMap() && !zone->watermap->InWater(x_pos, y_pos, z_pos)))
{
VERTEX dest(x_pos, y_pos, z_pos);
Map::Vertex dest(x_pos, y_pos, z_pos);
float newz = zone->zonemap->FindBestZ(MAP_ROOT_NODE, dest, nullptr, nullptr);
float newz = zone->zonemap->FindBestZ(dest, nullptr);
mlog(AI__WAYPOINTS, "BestZ returned %4.3f at %4.3f, %4.3f, %4.3f", newz,x_pos,y_pos,z_pos);

View File

@ -103,7 +103,7 @@ bool Zone::Bootup(uint32 iZoneID, uint32 iInstanceID, bool iStaticZone) {
worldserver.SetZone(0);
return false;
}
zone->zonemap = Map::LoadMapfile(zone->map_name);
zone->zonemap = Map::LoadMapFile(zone->map_name);
zone->watermap = WaterMap::LoadWaterMapfile(zone->map_name);
zone->pathing = PathManager::LoadPathFile(zone->map_name);