CAreaPortal class represents an areaportal. It's a very simple affair in game code, but also a very unusual entity.
- Areaportals do not exist in the world
- Although portals are created as brushes in Hammer, at runtime they are something quite unique: while they do exist at a location, that location is not in the same dimension, as it were, as anything else. Any function with which you try to return a portal's origin will only give (0,0,0).
- If you really do want to give an areaportal an origin, you can add a new keyvalue to your FGD - but don't use the standard
originkey or the portal will fail to compile. Make a new KV and link it to
m_vecOriginin your DataDesc instead.
- Alternatively, you could follow
CFuncAreaPortalWindow's example and piggyback on an associated brush entity's origin.
- Areaportals are closed and opened on the server
- Since portal flow also helps decide which entities are transmitted to a client, a portal's state is decided by the server. This happens separately for each connected player. The resulting value is presumably networked to the client for rendering control somewhere outside the SDK's code.
This is the function called every tick by the server to decide whether or not the portal should be opened or closed.
As well as simply responding to a 'hard' value of closure (i.e. input, initial state, or linked door status) that is the same for every client, it calculates a 'soft' value by checking whether or not the plane facing towards the player's current area is also facing the player's origin (
vOrigin). If it isn't, which is to say if the player has doubled back around a corner from it, the portal is closed for them.
A small amount of padding is added to backfacing tests to prevent client-server latency from causing the portal to open too late (look for
server\func_areaportalbase.cpp). This is why
UpdateVisibility() is called even when the portal isn't in PVS.