Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add more ways to collect Nav Areas #42

Merged
merged 5 commits into from
Aug 3, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions extension/extension.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ ConVar* sourcemod_version = nullptr;
IBaseNPC_Tools* g_pBaseNPCTools = new BaseNPC_Tools_API;
std::vector<sp_nativeinfo_t> gNatives;

DEFINEHANDLEOBJ(SurroundingAreasCollector, CUtlVector< CNavArea* >);
DEFINEHANDLEOBJ(AreasCollector, CUtlVector< CNavArea* >);

ConVar* g_cvDeveloper = nullptr;
extern ConVar* NextBotSpeedLookAheadRange;
Expand Down Expand Up @@ -102,7 +102,7 @@ bool CBaseNPCExt::SDK_OnLoad(char* error, size_t maxlength, bool late) {
GETGAMEDATAOFFSET("CBaseEntity::Event_Killed", iOffset);
SH_MANUALHOOK_RECONFIGURE(MEvent_Killed, iOffset, 0, 0);

CREATEHANDLETYPE(SurroundingAreasCollector);
CREATEHANDLETYPE(AreasCollector);

sharesys->AddDependency(myself, "bintools.ext", true, true);
sharesys->AddDependency(myself, "sdktools.ext", true, true);
Expand Down
4 changes: 2 additions & 2 deletions extension/extension.h
Original file line number Diff line number Diff line change
Expand Up @@ -32,8 +32,8 @@ extern HandleType_t HANDLENAME(PluginPathFollower);
extern HandleType_t HANDLENAME(PluginBotReply);
extern HandleType_t HANDLENAME(PluginBotEntityFilter);

extern HandleType_t HANDLENAME(SurroundingAreasCollector);
extern HandleType_t HANDLENAME(TSurroundingAreasCollector);
extern HandleType_t HANDLENAME(AreasCollector);
extern HandleType_t HANDLENAME(TAreasCollector);

extern HandleType_t g_CellArrayHandle;
extern HandleType_t g_KeyValueType;
Expand Down
68 changes: 64 additions & 4 deletions extension/natives/nav.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7,15 +7,15 @@

namespace natives::nav {

namespace surroundingareas {
namespace collector {

inline CUtlVector<CNavArea*>* Get(IPluginContext* context, const cell_t param) {
HandleSecurity security;
security.pOwner = nullptr;
security.pIdentity = myself->GetIdentity();
Handle_t hndlObject = static_cast<Handle_t>(param);
CUtlVector<CNavArea*>* collector = nullptr;
READHANDLE(hndlObject, SurroundingAreasCollector, collector)
READHANDLE(hndlObject, AreasCollector, collector)
return collector;
}

Expand All @@ -36,6 +36,8 @@ cell_t GetElement(IPluginContext* context, const cell_t* params) {

void setup(std::vector<sp_nativeinfo_t>& natives) {
sp_nativeinfo_t list[] = {
{"AreasCollector.Count", GetCount},
{"AreasCollector.Get", GetElement},
{"SurroundingAreasCollector.Count", GetCount},
{"SurroundingAreasCollector.Get", GetElement},
};
Expand Down Expand Up @@ -94,10 +96,65 @@ cell_t GetNavAreaByID(IPluginContext* context, const cell_t* params) {
return PtrToPawnAddress(ToolsNavMesh->GetNavAreaByID(id));
}

class CCollectorAddToTail {
public:
CCollectorAddToTail( CUtlVector<CNavArea*>* vec ) : m_vec( vec ) {}
bool operator() ( CNavArea *area ) { m_vec->AddToTail(area); return true; }

private:
CUtlVector<CNavArea*>* m_vec;
};

cell_t CollectSurroundingAreas(IPluginContext* context, const cell_t* params) {
CUtlVector<CNavArea*> *pCollector = new CUtlVector<CNavArea*>;
CollectSurroundingAreas( pCollector, (CNavArea*)PawnAddressToPtr(params[2]), sp_ctof(params[3]), sp_ctof(params[4]), sp_ctof(params[5]));
return CREATEHANDLE(SurroundingAreasCollector, pCollector);
return CREATEHANDLE(AreasCollector, pCollector);
}

cell_t CollectAreasOverlappingExtent(IPluginContext* context, const cell_t* params) {
Vector lo; Vector hi; cell_t* addr;
context->LocalToPhysAddr(params[2], &addr);
PawnVectorToVector(addr, lo);
context->LocalToPhysAddr(params[3], &addr);
PawnVectorToVector(addr, hi);

Extent extent;
extent.Init();
extent.lo = lo;
extent.hi = hi;

CUtlVector<CNavArea*> *pCollector = new CUtlVector<CNavArea*>;
CCollectorAddToTail addToTail(pCollector);

ToolsNavMesh->ForAllAreasOverlappingExtent(addToTail, extent);
return CREATEHANDLE(AreasCollector, pCollector);
}

cell_t CollectAreasInRadius(IPluginContext* context, const cell_t* params) {
cell_t* posAddr; Vector pos;
context->LocalToPhysAddr(params[2], &posAddr);
PawnVectorToVector(posAddr, pos);

float radius = sp_ctof(params[3]);

CUtlVector<CNavArea*> *pCollector = new CUtlVector<CNavArea*>;
CCollectorAddToTail addToTail(pCollector);

ToolsNavMesh->ForAllAreasInRadius(addToTail, pos, radius);
return CREATEHANDLE(AreasCollector, pCollector);
}

cell_t CollectAreasAlongLine(IPluginContext* context, const cell_t* params) {
CNavArea* startArea = (CNavArea*)PawnAddressToPtr(params[2]);
CNavArea* endArea = (CNavArea*)PawnAddressToPtr(params[3]);
cell_t* reachedEndAddr;
context->LocalToPhysAddr(params[4], &reachedEndAddr);

CUtlVector<CNavArea*> *pCollector = new CUtlVector<CNavArea*>;
CCollectorAddToTail addToTail(pCollector);

*reachedEndAddr = ToolsNavMesh->ForAllAreasAlongLine(addToTail, startArea, endArea) ? 1 : 0;
return CREATEHANDLE(AreasCollector, pCollector);
}

class SMPathCost : public IPathCost
Expand Down Expand Up @@ -199,7 +256,7 @@ cell_t BuildPath(IPluginContext* context, const cell_t* params) {

void setup(std::vector<sp_nativeinfo_t>& natives) {
area::setup(natives);
surroundingareas::setup(natives);
collector::setup(natives);

tf::nav::setup(natives);

Expand All @@ -210,6 +267,9 @@ void setup(std::vector<sp_nativeinfo_t>& natives) {
{"CNavMesh.IsOutOfDate", IsOutOfDate},
{"CNavMesh.GetNavAreaCount", GetNavAreaCount},
{"CNavMesh.CollectSurroundingAreas", CollectSurroundingAreas},
{"CNavMesh.CollectAreasOverlappingExtent", CollectAreasOverlappingExtent},
{"CNavMesh.CollectAreasInRadius", CollectAreasInRadius},
{"CNavMesh.CollectAreasAlongLine", CollectAreasAlongLine},
{"CNavMesh.GetNavAreaByID", GetNavAreaByID},
{"CNavMesh.GetNearestNavArea", GetNearestNavArea},
{"CNavMesh.BuildPath", BuildPath},
Expand Down
46 changes: 44 additions & 2 deletions extension/natives/nav/area.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -571,6 +571,26 @@ cell_t GetAdjacentArea(IPluginContext* context, const cell_t* params) {
return PtrToPawnAddress(area->GetAdjacentArea(dir, params[3]));
}

cell_t GetAdjacentLength(IPluginContext* context, const cell_t* params) {
auto area = Get(context, params[1]);
if (!area) {
return 0;
}

NavDirType dir = (NavDirType)params[2];
if (dir < 0 || dir >= NUM_DIRECTIONS) {
return context->ThrowNativeError("Invalid direction %d", dir);
}

int i = params[3];
const NavConnectVector *adjacent = area->GetAdjacentAreas(dir);
if (i < 0 || i >= adjacent->Count()) {
return context->ThrowNativeError("Array index %d is out of bounds (array size: %d)", i, adjacent->Count());
}

return sp_ftoc(adjacent->Element(i).length);
}

cell_t GetIncomingConnectionsCount(IPluginContext* context, const cell_t* params) {
auto area = Get(context, params[1]);
if (!area) {
Expand All @@ -583,7 +603,7 @@ cell_t GetIncomingConnectionsCount(IPluginContext* context, const cell_t* params
return area->GetIncomingConnections(dir)->Count();
}

cell_t GetIncomingConnections(IPluginContext* context, const cell_t* params) {
cell_t GetIncomingConnection(IPluginContext* context, const cell_t* params) {
auto area = Get(context, params[1]);
if (!area) {
return 0;
Expand All @@ -602,6 +622,26 @@ cell_t GetIncomingConnections(IPluginContext* context, const cell_t* params) {
return PtrToPawnAddress(incoming->Element(i).area);
}

cell_t GetIncomingConnectionLength(IPluginContext* context, const cell_t* params) {
auto area = Get(context, params[1]);
if (!area) {
return 0;
}

NavDirType dir = (NavDirType)params[2];
if (dir < 0 || dir >= NUM_DIRECTIONS) {
return context->ThrowNativeError("Invalid direction %d", dir);
}

int i = params[3];
const NavConnectVector *incoming = area->GetIncomingConnections(dir);
if (i < 0 || i >= incoming->Count()) {
return context->ThrowNativeError("Array index %d is out of bounds (array size: %d)", i, incoming->Count());
}

return sp_ftoc(incoming->Element(i).length);
}

cell_t IsEdge(IPluginContext* context, const cell_t* params) {
auto area = Get(context, params[1]);
if (!area) {
Expand Down Expand Up @@ -881,6 +921,7 @@ void setup(std::vector<sp_nativeinfo_t>& natives) {
{"CNavArea.GetCenter", GetCenter},
{"CNavArea.GetAdjacentCount", GetAdjacentCount},
{"CNavArea.GetAdjacentArea", GetAdjacentArea},
{"CNavArea.GetAdjacentLength", GetAdjacentLength},
{"CNavArea.IsConnected", IsConnected},
{"CNavArea.IsOverlappingX", IsOverlappingX},
{"CNavArea.IsOverlappingY", IsOverlappingY},
Expand All @@ -889,7 +930,8 @@ void setup(std::vector<sp_nativeinfo_t>& natives) {
{"CNavArea.IsOverlappingExtent", IsOverlappingExtent},
{"CNavArea.GetExtent", GetExtent},
{"CNavArea.GetIncomingConnectionCount", GetIncomingConnectionsCount},
{"CNavArea.GetIncomingConnection", GetIncomingConnections},
{"CNavArea.GetIncomingConnection", GetIncomingConnection},
{"CNavArea.GetIncomingConnectionLength", GetIncomingConnectionLength},
{"CNavArea.IsEdge", IsEdge},
{"CNavArea.Contains", Contains},
{"CNavArea.ContainsPoint", ContainsPoint},
Expand Down
Loading