53 s =
"^1Unregistered Player";
62 sprintf(
"//%s RECORD SET %s %f %f\n", strconv(2, 0, 0,
GetGametype()),
84 if(!mytime || mytime > t)
104 for (i = prevpos; i > newpos; --i)
135 if(
CS_CVAR(player).cvar_cl_allow_uidtracking == 1 &&
CS_CVAR(player).cvar_cl_allow_uid2name == 1)
137 if (!player.stored_netname)
139 if(player.stored_netname != player.netname)
142 strcpy(player.stored_netname, player.netname);
213 int cp = e.race_checkpoint;
216 float myrecordtime = e.race_checkpoint_record[cp];
217 float myrecordspeed = e.race_checkpoint_recordspeed[cp];
220 recordtime = myrecordtime;
221 recordspeed = myrecordspeed;
228 if(recordholder == e.netname)
248 WriteInt24_t(
MSG_ONE, recordtime);
250 WriteInt24_t(
MSG_ONE, myrecordtime);
253 WriteFloat(
MSG_ONE, recordspeed);
255 WriteFloat(
MSG_ONE, myrecordspeed);
350 for (
int i = 1; i <= m; ++i)
378 int player_prevpos = 0;
386 string oldrec_holder;
387 if (player_prevpos && (player_prevpos < newpos || !newpos))
392 Send_Notification(NOTIF_ALL,
NULL, MSG_INFO, INFO_RACE_FAIL_RANKED, mynetname, player_prevpos, t, oldrec);
415 if(
CS_CVAR(e).cvar_cl_allow_uidtracking != 1 ||
CS_CVAR(e).cvar_cl_allow_uid2name != 1
416 ||
uid2name(myuid) ==
"^1Unregistered Player")
429 if (newpos == 1 && showmessage)
438 if(newpos == player_prevpos)
455 Send_Notification(NOTIF_ALL,
NULL, MSG_INFO, INFO_RACE_NEW_BROKEN, mynetname, oldrec_holder, newpos, t, oldrec);
465 string therank =
ftos(i);
488 t += e.race_penalty_accumulator;
512 CS(e).race_completed = 1;
516 e.bot_attack =
false;
526 float recordtimespeed;
534 recordtime = e.race_checkpoint_record[cp];
535 recordtimespeed = e.race_checkpoint_recordspeed[cp];
545 if(recordholder == e.netname)
557 if(t < recordtime || recordtime == 0)
583 if(it == e || (
IS_SPEC(it) && it.enemy == e))
590 WriteInt24_t(
MSG_ONE, recordtime);
591 WriteInt24_t(
MSG_ONE, ((tvalid) ? it.race_checkpoint_record[cp] : 0));
595 WriteFloat(
MSG_ONE, recordtimespeed);
596 WriteFloat(
MSG_ONE, ((tvalid) ? it.race_checkpoint_recordspeed[cp] : 0));
604 float myrecordtime = e.race_checkpoint_record[cp];
606 if(t < myrecordtime || myrecordtime == 0)
608 e.race_checkpoint_record[cp] = t;
609 e.race_checkpoint_recordspeed[cp] =
vlen(
vec2(e.velocity));
615 float mylaps, lother, othtime;
624 mylaps = lother = othtime = 0;
678 e.race_checkpoint = 0;
680 e.race_movetime = e.race_movetime_frac = e.race_movetime_count = 0;
681 e.race_penalty_accumulator = 0;
682 e.race_lastpenalty =
NULL;
697 player = player.owner;
702 if(player.classname ==
"porto")
731 player.porto_forbidden = 2;
739 if(it.race_checkpoint >= 0)
740 this.race_checkpoint = it.race_checkpoint;
746 int cp_amount = 0, largest_cp_id = 0;
750 if(it.race_checkpoint > largest_cp_id)
754 IL_EACH(g_race_targets, it.classname ==
"target_checkpoint",
756 if(it.race_checkpoint == -2)
761 largest_cp_id = it.race_checkpoint;
762 IL_EACH(g_race_targets, it.classname ==
"target_stopTimer",
764 it.race_checkpoint = largest_cp_id + 1;
766 race_highest_checkpoint = largest_cp_id + 1;
767 race_timed_checkpoint = largest_cp_id + 1;
775 it.race_checkpoint = 1;
782 if((player.race_checkpoint == -1 &&
this.race_checkpoint == 0) || (player.race_checkpoint == this.
race_checkpoint))
786 if(player.race_lastpenalty !=
this)
788 player.race_lastpenalty =
this;
793 if(player.race_penalty)
807 if(player.race_respawn_checkpoint !=
this.race_checkpoint || !player.race_started)
808 player.race_respawn_spotref =
this;
811 player.race_started = 1;
817 player.race_laptime =
time;
818 player.race_movetime = player.race_movetime_frac = player.race_movetime_count = 0;
819 player.race_penalty_accumulator = 0;
820 player.race_lastpenalty =
NULL;
834 fputs(fh, strcat(it.targetname,
" ", ftos(it.race_checkpoint),
"\n"));
847 Damage (player,
this,
this, 10000, DEATH_HURTTRIGGER.m_id,
DMG_NOWEP, player.origin,
'0 0 0');
859 if(trigger.classname ==
"info_player_deathmatch")
871 if(view.race_checkpoint == -1 || own.race_checkpoint == -2)
873 else if(view.race_checkpoint == own.race_checkpoint)
886 if (recursionlevel > 400)
888 LOG_WARNF(
"df cp wp loop: ^4\"target\" ^3\"%s\"^7, ^4\"targetname\" ^3\"%s\"^7",
890 targeted.targetname);
893 if (recursionlevel > 420)
895 LOG_WARNF(
"Aborted creating defrag checkpoint waypointsprites for ^2%s^7 due to a loop",
896 checkpoint.classname);
900 entity s = WP_RaceCheckpoint;
901 if (checkpoint.classname ==
"target_startTimer")
903 else if (checkpoint.classname ==
"target_stopTimer")
906 for (
entity t = findchain(
target, targeted.targetname); t; t = t.chain)
911 t.sprite.realowner = checkpoint;
915 if (t.targetname && t != checkpoint)
922 static bool have_verified;
923 if (have_verified)
return;
924 have_verified =
true;
928 int pl_race_checkpoint = 0;
929 int pl_race_place = 0;
939 error(
strcat(
"Checkpoint ",
ftos(i),
" misses a spawnpoint with race_place==",
ftos(pl_race_place),
" (used for respawning in race) - bailing out"));
947 error(
strcat(
"Checkpoint ",
ftos(i),
" misses a spawnpoint with race_place==",
ftos(pl_race_place),
" (used for qualifying) - bailing out"));
955 error(
strcat(
"Checkpoint ",
ftos(i),
" misses a spawnpoint with race_place==",
ftos(pl_race_place),
" (used for initially spawning in race) - bailing out"));
966 error(
strcat(
"Checkpoint 0 misses a spawnpoint with race_place==",
ftos(pl_race_place),
" (used for qualifying) - bailing out"));
976 bool broken_defragcp =
false;
981 while ((l =
fgets(fh))) {
984 broken_defragcp =
true;
988 if (
argv(0) == cp.targetname) {
989 if(cp.race_checkpoint != -2 && cp.race_checkpoint !=
stof(
argv(1))) {
990 broken_defragcp =
true;
996 if(broken_defragcp)
break;
999 if(broken_defragcp) {
1004 cp.race_checkpoint = -2;
1014 IL_EACH(
g_race_targets, it.classname ==
"target_checkpoint" || it.classname ==
"target_startTimer" || it.classname ==
"target_stopTimer",
1016 defrag_waypointsprites(it, it, 0);
1018 if(it.classname ==
"target_checkpoint") {
1019 if(it.race_checkpoint == -2)
1020 defragcpexists = -1;
1024 float largest_cp_id = 0;
1026 if (cp.race_checkpoint > largest_cp_id) {
1027 largest_cp_id = cp.race_checkpoint;
1031 cp.race_checkpoint = largest_cp_id + 1;
1037 cp.race_checkpoint = 255;
1045 if (it.race_checkpoint == 0) {
1046 WaypointSprite_UpdateSprites(it.sprite, WP_RaceStart, WP_Null, WP_Null);
1048 WaypointSprite_UpdateSprites(it.sprite, WP_RaceFinish, WP_Null, WP_Null);
1070 if(
this == player.race_respawn_spotref || spot == player.race_respawn_spotref)
1074 int pl = player.race_place;
1077 if(pl == 0 && !player.race_started)
1079 if(spot.race_place != pl)
1103 this.
message =
"went backwards";
1105 this.
message2 =
"was pushed backwards by";
1169 this.
message =
"went backwards";
1171 this.
message2 =
"was pushed backwards by";
1175 if(this.
classname ==
"target_startTimer")
1207 CS(p).race_completed = 1;
1242 spawnfunc_info_player_deathmatch(
this);
1254 player.race_checkpoint_record[i] = 0;
1255 player.race_checkpoint_recordspeed[i] = 0;
1269 float p = it.race_place;
1279 pl.race_penalty_accumulator += penalty;
1293 pl.race_penalty =
time + penalty;
1310 if(
toucher.race_lastpenalty !=
this)
1312 toucher.race_lastpenalty =
this;
1356 float bestfraction, fraction;
1358 float nextcpindex, lastcpindex;
1360 nextcpindex =
max(e.race_checkpoint, 0);
1361 lastcpindex = e.race_respawn_checkpoint;
1362 lastcp = e.race_respawn_spotref;
1364 if(nextcpindex == lastcpindex)
1370 if(it.race_checkpoint != lastcpindex)
1375 o0 = (it.absmin + it.absmax) * 0.5;
1378 if(it.race_checkpoint != nextcpindex)
1380 o1 = (it.absmin + it.absmax) * 0.5;
1383 fraction =
bound(0.0001,
vlen(e.origin - o1) /
vlen(o0 - o1), 1);
1384 if(fraction < bestfraction)
1385 bestfraction = fraction;
float nearestwaypointtimeout
IntrusiveList g_bot_targets
void waypoint_spawnforitem_force(entity e, vector org)
#define MUTATOR_CALLHOOK(id,...)
var entity(vector mins, vector maxs,.entity tofield) findbox_tofield_OrFallback
limitations: NULL cannot be present elements can only be present once a maximum of IL_MAX lists can e...
#define autocvar_fraglimit
#define TIME_ENCODED_TOSTRING(n, compact)
const vector PL_MIN_CONST
const int INITPRIO_FINDTARGET
const vector PL_MAX_CONST
vector trace_plane_normal
void Damage(entity targ, entity inflictor, entity attacker, float damage, int deathtype,.entity weaponentity, vector hitloc, vector force)
void GameLogEcho(string s)
bool intermission_running
ERASEABLE void IL_REMOVE(IntrusiveList this, entity it)
Remove any element, anywhere in the list.
ERASEABLE entity IL_PUSH(IntrusiveList this, entity it)
Push to tail.
#define IL_EACH(this, cond, body)
void SUB_UseTargets(entity this, entity actor, entity trigger)
#define WriteHeader(to, id)
#define EXACTTRIGGER_TOUCH(e, t)
#define EXACTTRIGGER_INIT
#define db_remove(db, key)
ERASEABLE string db_get(int db, string key)
ERASEABLE void db_put(int db, string key, string value)
@ RACE_NET_CHECKPOINT_HIT_RACE_BY_OPPONENT
@ RACE_NET_SPEED_AWARD_BEST
@ RACE_NET_CHECKPOINT_NEXT_QUALIFYING
@ RACE_NET_PENALTY_QUALIFYING
@ RACE_NET_CHECKPOINT_CLEAR
@ RACE_NET_SERVER_RANKINGS
@ RACE_NET_CHECKPOINT_HIT_RACE
@ RACE_NET_CHECKPOINT_NEXT_SPEC_QUALIFYING
@ RACE_NET_CHECKPOINT_HIT_QUALIFYING
strcat(_("^F4Countdown stopped!"), "\n^BG", _("Teams are too unbalanced."))
void Send_Notification(NOTIF broadcast, entity client, MSG net_type, Notification net_name,...count)
void Portal_ClearAll(entity own)
void W_Porto_Fail(entity this, bool failhard)
void ClientData_Touch(entity e, bool to_spectators_too)
#define MAKE_INDEPENDENT_PLAYER(e)
float race_checkpoint_record[MAX_CHECKPOINTS]
float race_CheckpointNetworkID(float f)
void race_SendRanking(float pos, float prevpos, float del, float msg)
float race_readTime(string map, float pos)
float race_PreviousCheckpoint(float f)
float race_highest_checkpoint
void checkpoint_passed(entity this, entity player)
void race_SendAll(entity player, bool only_rankings)
float race_checkpoint_recordspeeds[MAX_CHECKPOINTS]
void race_PreparePlayer(entity this)
float race_checkpoint_lastlaps[MAX_CHECKPOINTS]
string race_penalty_reason
void race_SendNextCheckpoint(entity e, float spec)
void write_recordmarker(entity pl, float tstart, float dt)
void race_SpeedAwardFrame(entity player)
float race_checkpoint_recordspeed[MAX_CHECKPOINTS]
const float MAX_CHECKPOINTS
float race_timed_checkpoint
float race_readPos(string map, float t)
void race_SendTime(entity e, float cp, float t, float tvalid)
void race_ClearTime(entity e)
vector trigger_race_checkpoint_spawn_evalfunc(entity this, entity player, entity spot, vector current)
string race_readName(string map, float pos)
bool race_waypointsprite_visible_for_player(entity this, entity player, entity view)
float race_NextCheckpoint(float f)
void checkpoint_use(entity this, entity actor, entity trigger)
string uid2name(string myuid)
void race_StartCompleting()
float race_GetFractionalLapCount(entity e)
void race_checkAndWriteName(entity player)
IntrusiveList g_racecheckpoints
void race_send_speedaward_alltimebest(float msg)
void race_send_speedaward(float msg)
void race_RetractPlayer(entity this)
IntrusiveList g_race_targets
entity race_checkpoint_lastplayers[MAX_CHECKPOINTS]
void checkpoint_touch(entity this, entity toucher)
float race_checkpoint_records[MAX_CHECKPOINTS]
void race_setTime(string map, float t, string myuid, string mynetname, entity e, bool showmessage)
void race_SendStatus(float id, entity e)
void race_send_recordtime(float msg)
void defrag_waypointsprites(entity targeted, entity checkpoint, int recursionlevel)
string race_checkpoint_recordholders[MAX_CHECKPOINTS]
string race_readUID(string map, float pos)
void race_AbandonRaceCheck(entity p)
void penalty_use(entity this, entity actor, entity trigger)
float race_penalty_accumulator
void race_writeTime(string map, float t, string myuid)
void race_send_rankings_cnt(float msg)
void target_checkpoint_setup(entity this)
void race_ClearPlayerRecords(entity player)
void race_deleteTime(string map, float pos)
void trigger_race_checkpoint_verify(entity this)
float race_checkpoint_lasttimes[MAX_CHECKPOINTS]
void race_ImposePenaltyTime(entity pl, float penalty, string reason)
void penalty_touch(entity this, entity toucher)
bool autocvar_g_allow_checkpoints
bool autocvar_g_race_cptimes_onlyself
float speedaward_alltimebest
float race_lowest_place_spawn
entity race_respawn_spotref
float speedaward_lastupdate
float race_respawn_checkpoint
string speedaward_alltimebest_uid
float race_highest_place_spawn
int autocvar_g_cts_send_rankings_cnt
float speedaward_lastsent
string speedaward_alltimebest_holder
entity Spawn_FilterOutBadSpots(entity this, entity firstspot, float mindist, float teamcheck, bool targetcheck)
const int SPAWN_PRIO_RACE_PREVIOUS_SPAWN
spawn_evalfunc_t spawn_evalfunc
ClientState CS(Client this)
if(frag_attacker.flagcarried)
#define GameRules_scoring_add(client, fld, value)
#define GameRules_scoring_add_team(client, fld, value)
#define IS_REAL_CLIENT(v)
#define FOREACH_CLIENT(cond, body)
#define vdist(v, cmp, f)
Vector distance comparison, avoids sqrt()
entity WaypointSprite_SpawnFixed(entity spr, vector ofs, entity own,.entity ownfield, entity icon)
void InitializeEntity(entity e, void(entity this) func, int order)