Check Area for PC

Is it possible from a conversation to check if there are no players left in an area? And if there are no players left in that area, to set a variable onto the NPC with the conversation?

Edit: the area in question isn’t the same area as the NPC, it needs to be a specific area by tag.

Iterate through all PCs and check the area they are in.

int GetIsAreaEmpty(object oArea) {
    object oPC = GetFirstPC();
    while (oPC != OBJECT_INVALID) {
        if (GetArea(oPC) == oArea)
            return FALSE;
        oPC = GetNextPC();
    }
    return TRUE;
}
4 Likes

Adding another route for knowledgs’ sake:

    object oArea   = GetObjectByTag("AreaTag");
    object oTarget = GetFirstObjectInArea(oArea);
    int nAreaContainsPCs = TRUE;

    if (!GetIsObjectValid(oTarget))
        nAreaContainsPCs = FALSE;
    else if (!GetIsPC(oTarget) && !GetIsObjectValid(GetNearestCreature(CREATURE_TYPE_PLAYER_CHAR, PLAYER_CHAR_IS_PC, oTarget)))
        nAreaContainsPCs = FALSE;

    if (!nAreaContainsPCs)
        SetLocalInt(OBJECT_SELF, "NO_PLAYERS_LEFT", TRUE);
    else
        DeleteLocalInt(OBJECT_SELF, "NO_PLAYERS_LEFT");

^- Getting the first object in the area and then checking for the nearest object with tag (x) also works well for checking whether an area contains a specific type of NPC or placeable, when needed.

1 Like

If frequent checks of this sort are required for multiple purposes, it may be simpler to maintain the PC count as a local integer on each area.

In the area OnEnter script, increment by one if the entering object is a PC.

OnExit, decrement if the exiting object is a PC.

If generic scripts are used for every area, you only have to write that code once, but can refer to the PC count whenever it’s required.

3 Likes

this method was always unreliable because of the bug in GetNearestCreature function. There used to be a bug that when using this function to check players it didn’t return dead players as if IS_ALIVE/TRUE was used. Not sure if that but was fixed already now but it was there.

And now in EE this function is totally bugged so definitely recommend to do it via GetFirst/NextPC.

2 Likes

not a good idea in multiplayer environment, I was trying to do this as it seemed to me more efficient but there are just far too many issues and caveats that will cause the counter not equal to real player count. In SP game it might never happen, in MP game better not use this method.

2 Likes

Can you give some examples of things that may affect the count?

If a player exits the server while in the area in question, the server doesn’t fire the area’s on exit script. Therefor, the count will be off.

2 Likes

Just tested TheBarbarian’s script online with EE and it worked great! The GetNearestCreature function didn’t seem to bug, then again player’s can’t die in the area I’m using it…

GetNearestCreature is heavily bugged in EE, but it faiils in very specific cases (PC has aura AOE on him or very specific case of monster positioning.

If player dies and logs out area OnExit does not fire. You can account for this and workaround it via OnClientLeave but this is not the only case where it fails (though now I cannot remember the others) but if the only reason to use variable to count players in area is efficiency, having to deal with various cases where that method fails ´goest against that anyway…

2 Likes

Would something like this work then?

void main()
{
object oArea = GetObjectByTag(“storage000”);
object oPC = GetFirstPC();

while (oPC != OBJECT_INVALID)
{
    if (OBJECT_SELF == GetArea(oArea)) return;
    else oPC = GetNextPC();
}

SetLocalInt(OBJECT_SELF, "STORAGE", 0);

}

Actually, would this work?

void main()
{
object oArea = GetObjectByTag(“storage000”);
object oPC = GetFirstPC();

while (oPC != OBJECT_INVALID)
{
if (GetArea(oPC) == oArea) return;
else oPC = GetNextPC();
}

SetLocalInt(OBJECT_SELF, “STORAGE”, 0);
}

yes that should work

1 Like