set g_spawn_furthest 0.5 "this amount of the spawns shall be far away from any players"
set g_spawn_useallspawns 0 "use all spawns, e.g. also team spawns in non-teamplay, and all spawns, even enemy spawns, in teamplay"
set g_spawn_near_teammate 0 "if set, players prefer spawns near a team mate"
-set g_spawn_near_teammate_distance 384 "max distance to consider a spawn to be near a team mate"
+set g_spawn_near_teammate_distance 640 "max distance to consider a spawn to be near a team mate"
// respawn delay
set g_respawn_delay 2 "number of seconds you have to wait before you can respawn again"
set g_respawn_waves 0 "respawn in waves (every n seconds), intended to decrease overwhelming base attacks"
#define SERVERFLAG_PLAYERSTATS 4
// spawnpoint prios
-#define SPAWN_PRIO_GOOD_DISTANCE 100
-#define SPAWN_PRIO_RACE_PREVIOUS_SPAWN 50
-#define SPAWN_PRIO_NEAR_TEAMMATE 10
+#define SPAWN_PRIO_NEAR_TEAMMATE_FOUND 200
+#define SPAWN_PRIO_NEAR_TEAMMATE_SAMETEAM 100
+#define SPAWN_PRIO_RACE_PREVIOUS_SPAWN 50
+#define SPAWN_PRIO_GOOD_DISTANCE 10
prio += SPAWN_PRIO_GOOD_DISTANCE;
spawn_score = prio * '1 0 0' + shortest * '0 1 0';
- spawn_score_spot = spot;
+ spawn_spot = spot;
// filter out spots for assault
if(spot.target != "") {
race_PostSpawn(spot);
- if(autocvar_spawn_debug)
- {
- sprint(self, strcat("spawnpoint origin: ", vtos(spot.origin), "\n"));
- remove(spot); // usefull for checking if there are spawnpoints, that let drop through the floor
- }
-
//stuffcmd(self, "chase_active 0");
//stuffcmd(self, "set viewsize $tmpviewsize \n");
activator = world;
self = oldself;
+ spawn_spot = spot;
MUTATOR_CALLHOOK(PlayerSpawn);
+ if(autocvar_spawn_debug)
+ {
+ sprint(self, strcat("spawnpoint origin: ", vtos(spot.origin), "\n"));
+ remove(spot); // usefull for checking if there are spawnpoints, that let drop through the floor
+ }
+
self.switchweapon = w_getbestweapon(self);
self.cnt = -1; // W_LastWeapon will not complain
self.weapon = 0;
// called when a player becomes observer, after shared setup
MUTATOR_HOOKABLE(PlayerSpawn);
+ entity spawn_spot; // spot that was used, or world
// called when a player spawns as player, after shared setup, before his weapon is chosen (so items may be changed in here)
MUTATOR_HOOKABLE(ClientDisconnect);
// return 1 to make the spawnpoint unusable
// INPUT
entity self; // player wanting to spawn
- entity spawn_score_spot; // spot to be evaluated
+ entity spawn_spot; // spot to be evaluated
// IN+OUT
vector spawn_score; // _x is priority, _y is "distance"
float autocvar_g_spawn_near_teammate_distance;
+.entity msnt_lookat;
-MUTATOR_HOOKFUNCTION(msnt_Spawn_Score) {
+MUTATOR_HOOKFUNCTION(msnt_Spawn_Score)
+{
entity p;
+ spawn_spot.msnt_lookat = world;
+
if(!teamplay)
return 0;
+ RandomSelection_Init();
FOR_EACH_PLAYER(p) if(p != self) if(p.team == self.team) if(!p.deadflag)
{
- if(vlen(spawn_score_spot.origin - p.origin) > autocvar_g_spawn_near_teammate_distance)
+ float l = vlen(spawn_spot.origin - p.origin);
+ if(l > autocvar_g_spawn_near_teammate_distance)
continue;
- if(!checkpvs(spawn_score_spot.origin, p))
+ if(l < 48)
continue;
+ if(!checkpvs(spawn_spot.origin, p))
+ continue;
+ RandomSelection_Add(p, 0, string_null, 1, 1);
+ }
+
+ if(RandomSelection_chosen_ent)
+ {
+ spawn_spot.msnt_lookat = RandomSelection_chosen_ent;
+ spawn_score_x += SPAWN_PRIO_NEAR_TEAMMATE_FOUND;
+ }
+ else if(self.team == spawn_spot.team)
+ spawn_score_x += SPAWN_PRIO_NEAR_TEAMMATE_SAMETEAM; // prefer same team, if we can't find a spawn near teammate
+
+ return 0;
+}
+
+MUTATOR_HOOKFUNCTION(msnt_PlayerSpawn)
+{
+ if(spawn_spot.msnt_lookat)
+ {
+ self.angles = vectoangles(spawn_spot.msnt_lookat.origin - self.origin);
+ self.angles_x = -self.angles_x;
/*
- if(self == nextent(world))
- {
- te_explosion(p.origin);
- print(p.netname, " should be nearby\n");
- }
+ sprint(self, "You should be looking at ", spawn_spot.msnt_lookat.netname, "^7.\n");
+ sprint(self, "distance: ", vtos(spawn_spot.msnt_lookat.origin - self.origin), "\n");
+ sprint(self, "angles: ", vtos(self.angles), "\n");
*/
- spawn_score_x += SPAWN_PRIO_NEAR_TEAMMATE;
}
return 0;
MUTATOR_DEFINITION(mutator_spawn_near_teammate)
{
MUTATOR_HOOK(Spawn_Score, msnt_Spawn_Score, CBC_ORDER_ANY);
+ MUTATOR_HOOK(PlayerSpawn, msnt_PlayerSpawn, CBC_ORDER_ANY);
return 0;
}