How can I get the number of all connected clients (including unspawned ones)?

#player.GetAll() only works for clients that have spawned. I want to be able to count every connected client, including ones that are still spawning.

Uh. Once a player is called in the PlayerInitialSpawn hook, their player object is created, and they are added to the player.GetAll() table. If you want to count players who have attempted to connect, but do not have a player object yet, you would need to create a variable that adds 1 to itself every time the PlayerConnect hook is called, and subtracts one every time the PlayerDisconnect hook is called.

Remember that the PlayerIntialSpawn hook is called not on their actual first spawn, but when they first start sending client data to the server.

edit:

More info on that hook can be found here:

also, what are you trying to achieve with this? I may be able to help you find a more elegant solution.

I’m working on a reserve slot system using the CheckPassword hook and sv_visiblemaxplayers. I’ve got the following code to disallow people who aren’t admins etc:



if (curplayers+self.ExtraSlots)>=maxplayers then
	return false, "The server is full."
end


curplayers is currently set to #player.GetAll(), but it should be the total clients connected, otherwise if a player is joining and the server hits its visible max slots, it would still let another player in until the first player spawns and gets added to the count.

Just a theory: You might fix the problem entirely by using PlayerInitialSpawn as your hook of choice, as opposed to check password. You can then just do ply:Kick( “The server is full” ) instead. I believe you’ll see the same results, but the player.GetAll() table will be fully up to date if called inside the PlayerInitialSpawn hook, so you won’t have to worry about someone slipping past the check.

Yeah but for that I’d have to let them connect right up until sending client info to kick them. I think I’ll try your method of using PlayerConnect and PlayerDisconnect to count them - see how reliable it is.

The problem I see with that is that if a player attempts to connect but times out for whatever reason, or restarts their connection attempt in the middle of a previous connection attempt, it will mis-count the value.

True… is there no native function to get connected players then? That’s a bit stupid imo. Only other way I can think of doing it is somehow grabbing the output of the ‘status’ command and getting it from that, but that’s also stupid and probably impossible.

I’m pretty sure the status command uses player.GetAll

Just tried it, it does show players that are connecting.

Oh, interesting. Maybe it uses the PlayerAuthed hook?

There is this gatekepeer module in lua you could probably make use of.

I’m a noob, and I don’t think I have read this right, but why not



maxPlayers = 30
curPlayers = 0
reservedSlots = 5
function GM:PlayerConnect( )
	if (curPlayers + reservedSlots) > maxPlayers and *not in special list* then
		return false, "The server is full."
	else
		curPlayers = curPlayers + 1
	end
end
function GM:PlayerDisconnected( )
	curPlayers = curPlayers - 1
end


Something like that… right?
this seems to easy to be right though.

The reason that brandonj4 marked you dumb is becuase you’re overwriting the base gamemode function for handling player connections and player disconnections. Instead you want to use hook.Add, like this:




hook.Add( "PlayerConnect", "your_unique_hook_name", function()

 if ( cur_plys + reservedSlots ) > maxPlayers then

  return false, "The server is full"

 else
  
  cur_plys = cur_plys + 1
 
 end

end )

hook.Add( "PlayerDisconnect", "your_other_unique_name", function()
 cur_plys = cur_plys - 1
end )



edit: also, don’t create global variables. use local ones. You do this by simply prefacing your variable declaration with ‘local’, like this:



foo = "bar" -- this variable is globally defined. It takes up more cpu cycles to read, due to the need for a lookup table. It also can possibly overwrite/ruin other addons that use this variable name, as the global var could overwrite the local one.

local semper = "fi" -- this variable is locally defined. It's easier for the cpu to read, and can not accidentally overwrite variables used by other addons 


Ohhh okay, well, I need some fixing to do…

Your so helpful aswell, thanks so much!

That gameevent.Listen thing looks interesting - would that be a reliable method of counting players?

gmsv_gatekeeper is still the best way for anything like this. gatekeeper.GetNumClients() is exactly what you’re looking for.

Okay, though it’s a shame I have to resort to modules just for getting the player count.