Complete disaster-recovery snapshot: engine/game source, game data assets, VC6 toolchain + DX SDKs, build outputs, deployed game, and _UNUSED archive. Large binaries in Git LFS; text preserved byte-for-byte (core.autocrlf=false, no eol attributes). See RECOVERY.md for the one-clone rebuild procedure.
362 lines
8.6 KiB
C++
362 lines
8.6 KiB
C++
#include "MW4Headers.hpp"
|
|
|
|
#include "AI_Groups.hpp"
|
|
|
|
#include <Adept\NameTable.hpp>
|
|
#include <Adept\Application.hpp>
|
|
#include "MWPlayer.hpp"
|
|
#include "MWMission.hpp"
|
|
#include "GroupContainer.hpp"
|
|
#include "VehicleInterface.hpp"
|
|
#include <Adept\Map.hpp>
|
|
|
|
|
|
|
|
using namespace MW4AI;
|
|
|
|
inline MWObject* GetMWObject(Adept::ObjectID object_id)
|
|
{
|
|
gosREPORT((NameTable::GetInstance() != 0),"The NameTable object does not exist");
|
|
|
|
Adept::Entity* entity = NameTable::GetInstance()->FindData(object_id);
|
|
|
|
if ((entity == 0) ||
|
|
(entity->IsDerivedFrom(MechWarrior4::MWObject::DefaultData) == false))
|
|
{
|
|
return (0);
|
|
}
|
|
|
|
return (Cast_Object(MechWarrior4::MWObject*,entity));
|
|
}
|
|
|
|
inline MechWarrior4::MWMission& GetMission()
|
|
{
|
|
gosREPORT((Adept::Mission::GetInstance() != 0),"The mission object does not exist");
|
|
gosREPORT((Adept::Mission::GetInstance()->IsDerivedFrom(MechWarrior4::MWMission::DefaultData) == true),"The mission object is not the correct type");
|
|
|
|
MechWarrior4::MWMission* mission = Cast_Object(MechWarrior4::MWMission*,Adept::Mission::GetInstance());
|
|
Check_Object(mission);
|
|
return (*mission);
|
|
}
|
|
|
|
|
|
bool Groups::AllDead(Group::identifier group)
|
|
{
|
|
if (Size(group) == 0)
|
|
{
|
|
return (false);
|
|
}
|
|
|
|
return (Size(group) == NumDead(group));
|
|
}
|
|
|
|
void Groups::AddObject(Adept::ObjectID object, Group::identifier group)
|
|
{
|
|
MWObject* mwobject = GetMWObject(object);
|
|
|
|
if (mwobject != 0)
|
|
{
|
|
GetMission().GetGroupContainer().AddObjectToGroup(*mwobject,group);
|
|
}
|
|
}
|
|
|
|
void Groups::RemoveObject(Adept::ObjectID object, Group::identifier group)
|
|
{
|
|
MWObject* mwobject = GetMWObject(object);
|
|
|
|
if (mwobject != 0)
|
|
{
|
|
GetMission().GetGroupContainer().RemoveObjectFromGroup(*mwobject,group);
|
|
}
|
|
}
|
|
|
|
int Groups::NumDead(Group::identifier group)
|
|
{
|
|
gosREPORT((Adept::Application::GetInstance() != 0),"The application object does not exist");
|
|
gosREPORT((NameTable::GetInstance() != 0),"The NameTable object does not exist");
|
|
// gosREPORT((Adept::Application::GetInstance()->networkingFlag == false),"Cannot use group NumDead(), AllDead() functions in multiplayer");
|
|
|
|
if (GetMission().GetGroupContainer().GroupExists(group) == false)
|
|
{
|
|
return (0);
|
|
}
|
|
|
|
const Group& g = GetMission().GetGroupContainer().GetGroup(group);
|
|
|
|
int num_dead = 0;
|
|
|
|
{for (Group::element_list::const_iterator i = g.GetElements().begin();
|
|
i != g.GetElements().end();
|
|
++i)
|
|
{
|
|
Adept::Entity* entity = Adept::NameTable::GetInstance()->FindData(*i);
|
|
|
|
if ((entity == 0) ||
|
|
(entity->IsDestroyed() == true))
|
|
{
|
|
++num_dead;
|
|
}
|
|
}}
|
|
|
|
return (num_dead);
|
|
}
|
|
|
|
int Groups::Size(Group::identifier group)
|
|
{
|
|
if (GetMission().GetGroupContainer().GroupExists(group) == false)
|
|
{
|
|
return (0);
|
|
}
|
|
|
|
const Group& g = GetMission().GetGroupContainer().GetGroup(group);
|
|
return (g.GetElements().size());
|
|
}
|
|
|
|
bool Groups::ContainsObject(Adept::ObjectID object, Group::identifier group)
|
|
{
|
|
MWObject* mwobject = GetMWObject(object);
|
|
|
|
if (mwobject != 0)
|
|
{
|
|
return (std::find(mwobject->GetGroups().begin(),mwobject->GetGroups().end(),group) != mwobject->GetGroups().end());
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
bool Groups::GetFirstGroup(Adept::ObjectID object, Group::identifier& group_id)
|
|
{
|
|
MWObject* v = GetMWObject(object);
|
|
|
|
if (v == 0)
|
|
{
|
|
return (false);
|
|
}
|
|
|
|
if (v->GetGroups().size() == 0)
|
|
{
|
|
return (false);
|
|
}
|
|
|
|
group_id = v->GetGroups()[0];
|
|
return (true);
|
|
}
|
|
|
|
bool Groups::GetFirstObject(Group::identifier group, Adept::ObjectID& object)
|
|
{
|
|
if (GetMission().GetGroupContainer().GroupExists(group) == false)
|
|
{
|
|
return (false);
|
|
}
|
|
|
|
const Group& g = GetMission().GetGroupContainer().GetGroup(group);
|
|
if (g.GetElements().size() == 0)
|
|
{
|
|
return (false);
|
|
}
|
|
|
|
{for (Group::element_list::const_iterator i = g.GetElements().begin();
|
|
i != g.GetElements().end();
|
|
++i)
|
|
{
|
|
MWObject* o = GetMWObject(*i);
|
|
|
|
if ((o != 0) &&
|
|
(o->IsDestroyed() == false))
|
|
{
|
|
object = *i;
|
|
return (true);
|
|
}
|
|
}}
|
|
|
|
return (false);
|
|
}
|
|
|
|
MechWarrior4::Group& Groups::GetGroup(MechWarrior4::Group::identifier group_id)
|
|
{
|
|
Verify(Adept::Mission::GetInstance() != 0);
|
|
Verify(Adept::Mission::GetInstance()->IsDerivedFrom(MechWarrior4::MWMission::DefaultData) == true);
|
|
MechWarrior4::MWMission* mission = Cast_Object(MechWarrior4::MWMission*,Adept::Mission::GetInstance());
|
|
Check_Object(mission);
|
|
Verify(mission->GetGroupContainer().GroupExists(group_id));
|
|
return (mission->GetGroupContainer().GetGroup(group_id));
|
|
}
|
|
|
|
bool IsLancemateGroup(Group::identifier group)
|
|
{
|
|
if (GetMission().GetGroupContainer().GroupExists(group) == false)
|
|
{
|
|
return (false);
|
|
}
|
|
|
|
const Group& g = GetMission().GetGroupContainer().GetGroup(group);
|
|
if (g.GetElements().size() == 0)
|
|
{
|
|
return (false);
|
|
}
|
|
|
|
if (g.HasAI() == false)
|
|
{
|
|
return (false);
|
|
}
|
|
|
|
const MW4AI::Squad::AI* group_ai = g.GetAI();
|
|
|
|
if (group_ai->GetID() != MW4AI::Squad::GROUPAI_LANCEMATE)
|
|
{
|
|
return (false);
|
|
}
|
|
|
|
Adept::Entity* entity = NameTable::GetInstance()->FindData(g.GetElements()[0]);
|
|
|
|
if ((entity != 0) &&
|
|
(entity->IsPlayerVehicle() == true))
|
|
{
|
|
return (true);
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
bool Groups::GetLancemateGroup(const std::vector<Group::identifier>& groups, Group::identifier& group_id)
|
|
{
|
|
{for (std::vector<Group::identifier>::const_iterator i = groups.begin();
|
|
i != groups.end();
|
|
++i)
|
|
{
|
|
if ((Size(*i) > 0) &&
|
|
(IsLancemateGroup(*i) == true))
|
|
{
|
|
group_id = *i;
|
|
return (true);
|
|
}
|
|
}}
|
|
|
|
return (false);
|
|
}
|
|
|
|
bool Groups::GetMember(Group::identifier group, unsigned int index, Adept::ObjectID& object)
|
|
{
|
|
if (GetMission().GetGroupContainer().GroupExists(group) == false)
|
|
{
|
|
return (false);
|
|
}
|
|
|
|
const Group& g = GetMission().GetGroupContainer().GetGroup(group);
|
|
if (index >= g.GetElements().size())
|
|
{
|
|
return (false);
|
|
}
|
|
|
|
object = g.GetElements()[index];
|
|
return (true);
|
|
}
|
|
|
|
void Groups::GetLancemates(std::vector<MWObject*>& lancemates, bool include_player)
|
|
{
|
|
if (Adept::Player::GetInstance() == 0)
|
|
{
|
|
return;
|
|
}
|
|
|
|
MechWarrior4::MWPlayer* p = Cast_Object(MechWarrior4::MWPlayer*,Adept::Player::GetInstance());
|
|
if (p == 0)
|
|
{
|
|
return;
|
|
}
|
|
|
|
Check_Object(p);
|
|
if ((p->GetInterface() == 0) ||
|
|
(p->GetInterface()->vehicle == 0))
|
|
{
|
|
return;
|
|
}
|
|
|
|
if (include_player == true)
|
|
{
|
|
lancemates.push_back(p->GetInterface()->vehicle);
|
|
}
|
|
|
|
{for (std::vector<Group::identifier>::const_iterator i = p->GetInterface()->vehicle->GetGroups().begin();
|
|
i != p->GetInterface()->vehicle->GetGroups().end();
|
|
++i)
|
|
{
|
|
if ((Size(*i) > 0) &&
|
|
(IsLancemateGroup(*i) == true))
|
|
{
|
|
const Group& g = GetMission().GetGroupContainer().GetGroup(*i);
|
|
|
|
{for (int index = 1;
|
|
index < g.GetElements().size();
|
|
++index)
|
|
{
|
|
Adept::Entity* entity = Adept::NameTable::GetInstance()->FindData(g.GetElements()[index]);
|
|
if ((entity != 0) &&
|
|
(entity->IsDerivedFrom(MWObject::DefaultData) == true))
|
|
{
|
|
MWObject* mwobject = Cast_Object(MWObject*,entity);
|
|
lancemates.push_back(mwobject);
|
|
}
|
|
}}
|
|
|
|
return;
|
|
}
|
|
}}
|
|
}
|
|
|
|
void Groups::GetGroupmates(const Adept::ObjectID& of_who, std::vector<MWObject*>& groupmates)
|
|
{
|
|
Adept::Entity* entity = Adept::NameTable::GetInstance()->FindData(of_who);
|
|
if ((entity == 0) ||
|
|
(entity->IsDerivedFrom(MWObject::DefaultData) == false))
|
|
{
|
|
return;
|
|
}
|
|
|
|
const GroupContainer& gc = GetMission().GetGroupContainer();
|
|
|
|
MWObject* mwobject = Cast_Object(MWObject*,entity);
|
|
{for (MWObject::GroupList::const_iterator i = mwobject->GetGroups().begin();
|
|
i != mwobject->GetGroups().end();
|
|
++i)
|
|
{
|
|
std::vector<MWObject*> group_members;
|
|
gc.GetGroup(*i).GetMembers(group_members);
|
|
|
|
{for (std::vector<MWObject*>::const_iterator i_members = group_members.begin();
|
|
i_members != group_members.end();
|
|
++i_members)
|
|
{
|
|
if (((*i_members)->objectID != of_who) &&
|
|
(std::find(groupmates.begin(),groupmates.end(),*i_members) == groupmates.end()))
|
|
{
|
|
groupmates.push_back(*i_members);
|
|
}
|
|
}}
|
|
}}
|
|
}
|
|
|
|
void Groups::NotifyPlayerFocusedOnEntity(MechWarrior4::MWObject& player_vehicle, Adept::Entity& entity)
|
|
{
|
|
if ((entity.IsDestroyed() == true) ||
|
|
(player_vehicle.IsDestroyed() == true) ||
|
|
(entity.GetAlignment() == player_vehicle.GetAlignment()) ||
|
|
(&entity == Adept::Map::GetInstance()))
|
|
{
|
|
return;
|
|
}
|
|
|
|
GroupContainer& gc = GetMission().GetGroupContainer();
|
|
|
|
{for (MWObject::GroupList::const_iterator i = player_vehicle.GetGroups().begin();
|
|
i != player_vehicle.GetGroups().end();
|
|
++i)
|
|
{
|
|
MW4AI::Squad::AI* squad_ai = gc.GetGroup(*i).GetAI();
|
|
if (squad_ai != 0)
|
|
{
|
|
squad_ai->SetEntityToIgnore(entity.objectID);
|
|
}
|
|
}}
|
|
}
|