return false;
}
-// decolorizes and team colors the player name when needed
-string playername(string thename, float teamid)
-{
- TC(int, teamid);
- string t;
- if (teamplay)
- {
- t = Team_ColorCode(teamid);
- return strcat(t, strdecolorize(thename));
- }
- else
- return strdecolorize(thename);
-}
-
float cvar_or(string cv, float v)
{
string s;
#define IS_DEAD(s) (((s).classname == "csqcmodel") ? (s).csqcmodel_isdead : (GetResource((s), RES_HEALTH) <= 0))
-
-// decolorizes and team colors the player name when needed
-string playername(string thename, float teamid);
-
float cvar_or(string cv, float v);
vector project_3d_to_2d(vector vec);
}
string s = entcs_GetName(this.sv_entnum - 1);
if ((autocvar_hud_shownames_decolorize == 1 && teamplay) || autocvar_hud_shownames_decolorize == 2)
- s = playername(s, entcs_GetTeam(this.sv_entnum - 1));
+ s = playername(s, entcs_GetTeam(this.sv_entnum - 1), true);
drawfontscale = '1 1 0' * resize;
s = textShortenToWidth(s, namewidth, '1 1 0' * autocvar_hud_shownames_fontsize, stringwidth_colors);
float width = stringwidth(s, true, '1 1 0' * autocvar_hud_shownames_fontsize);
#include <server/gamelog.qh>
#include <server/items/items.qh>
#include <server/teamplay.qh>
+#include <server/world.qh>
#include <common/mapobjects/platforms.qh>
#include <common/mapobjects/triggers.qh>
#include <server/command/vote.qh>
#include <server/damage.qh>
#include <server/items/items.qh>
+#include <server/world.qh>
#include <common/mapobjects/defs.qh>
#include <common/mapobjects/triggers.qh>
M_Spider_Attack_Web_Explode(this);
}
-void adaptor_think2use_hittype_splash(entity this);
-
void M_Spider_Attack_Web(entity this)
{
sound(this, CH_SHOTS, SND_ELECTRO_FIRE2, VOL_BASE, ATTEN_NORM);
#include <common/net_linked.qh>
#include <common/teams.qh>
#include <server/autocvars.qh>
+ #include <server/command/getreplies.qh>
#include <server/world.qh>
#include <server/mutators/_mod.qh>
#endif
db_put(PS_GR_OUT_DB, sprintf("%s:_playerid", p.playerstats_id), ftos(p.playerid));
if(CS(p).cvar_cl_allow_uid2name == 1 || IS_BOT_CLIENT(p))
- db_put(PS_GR_OUT_DB, sprintf("%s:_netname", p.playerstats_id), playername(p, false));
+ db_put(PS_GR_OUT_DB, sprintf("%s:_netname", p.playerstats_id), playername(p.netname, p.team, false));
if(teamplay)
db_put(PS_GR_OUT_DB, sprintf("%s:_team", p.playerstats_id), ftos(p.team));
#include "state.qh"
+#include <server/command/getreplies.qh>
+
void Inventory_new(PlayerState this);
void Inventory_delete(entity this);
delete(ps);
}
-void GetCvars(entity this, entity store, int);
void DecodeLevelParms(entity this);
void PlayerScore_Attach(entity this);
void ClientData_Attach(entity this);
#include <server/damage.qh>
#include <server/weapons/common.qh>
#include <server/weapons/weaponsystem.qh>
+#include <server/world.qh>
#include <common/mapobjects/defs.qh>
// Generic aiming
return CONTENT_EMPTY;
}
#endif
+
+#ifdef SVQC
+void attach_sameorigin(entity e, entity to, string tag)
+{
+ vector org, t_forward, t_left, t_up, e_forward, e_up;
+ float tagscale;
+
+ org = e.origin - gettaginfo(to, gettagindex(to, tag));
+ tagscale = (vlen(v_forward) ** -2); // undo a scale on the tag
+ t_forward = v_forward * tagscale;
+ t_left = v_right * -tagscale;
+ t_up = v_up * tagscale;
+
+ e.origin_x = org * t_forward;
+ e.origin_y = org * t_left;
+ e.origin_z = org * t_up;
+
+ // current forward and up directions
+ if (substring(e.model, 0, 1) == "*") // bmodels have their own rules
+ e.angles = AnglesTransform_FromVAngles(e.angles);
+ else
+ e.angles = AnglesTransform_FromAngles(e.angles);
+ fixedmakevectors(e.angles);
+
+ // untransform forward, up!
+ e_forward.x = v_forward * t_forward;
+ e_forward.y = v_forward * t_left;
+ e_forward.z = v_forward * t_up;
+ e_up.x = v_up * t_forward;
+ e_up.y = v_up * t_left;
+ e_up.z = v_up * t_up;
+
+ e.angles = fixedvectoangles2(e_forward, e_up);
+ if (substring(e.model, 0, 1) == "*") // bmodels have their own rules
+ e.angles = AnglesTransform_ToVAngles(e.angles);
+ else
+ e.angles = AnglesTransform_ToAngles(e.angles);
+
+ setattachment(e, to, tag);
+ setorigin(e, e.origin);
+}
+
+void detach_sameorigin(entity e)
+{
+ vector org;
+ org = gettaginfo(e, 0);
+ e.angles = fixedvectoangles2(v_forward, v_up);
+ if (substring(e.model, 0, 1) == "*") // bmodels have their own rules
+ e.angles = AnglesTransform_ToVAngles(e.angles);
+ else
+ e.angles = AnglesTransform_ToAngles(e.angles);
+ setorigin(e, org);
+ setattachment(e, NULL, "");
+ setorigin(e, e.origin);
+}
+
+void follow_sameorigin(entity e, entity to)
+{
+ set_movetype(e, MOVETYPE_FOLLOW); // make the hole follow
+ e.aiment = to; // make the hole follow bmodel
+ e.punchangle = to.angles; // the original angles of bmodel
+ e.view_ofs = e.origin - to.origin; // relative origin
+ e.v_angle = e.angles - to.angles; // relative angles
+}
+
+#if 0
+// TODO: unused, likely for a reason, possibly needs extensions (allow setting the new movetype as a parameter?)
+void unfollow_sameorigin(entity e)
+{
+ set_movetype(e, MOVETYPE_NONE);
+}
+#endif
+
+.string aiment_classname;
+.float aiment_deadflag;
+void SetMovetypeFollow(entity ent, entity e)
+{
+ // FIXME this may not be warpzone aware
+ set_movetype(ent, MOVETYPE_FOLLOW); // make the hole follow
+ ent.solid = SOLID_NOT; // MOVETYPE_FOLLOW is always non-solid - this means this cannot be teleported by warpzones any more! Instead, we must notice when our owner gets teleported.
+ ent.aiment = e; // make the hole follow bmodel
+ ent.punchangle = e.angles; // the original angles of bmodel
+ ent.view_ofs = ent.origin - e.origin; // relative origin
+ ent.v_angle = ent.angles - e.angles; // relative angles
+ ent.aiment_classname = strzone(e.classname);
+ ent.aiment_deadflag = e.deadflag;
+}
+void UnsetMovetypeFollow(entity ent)
+{
+ set_movetype(ent, MOVETYPE_FLY);
+ PROJECTILE_MAKETRIGGER(ent);
+ ent.aiment = NULL;
+}
+float LostMovetypeFollow(entity ent)
+{
+/*
+ if(ent.move_movetype != MOVETYPE_FOLLOW)
+ if(ent.aiment)
+ error("???");
+*/
+ if(ent.aiment)
+ {
+ if(ent.aiment.classname != ent.aiment_classname)
+ return 1;
+ if(ent.aiment.deadflag != ent.aiment_deadflag)
+ return 1;
+ }
+ return 0;
+}
+#endif
+
+#ifdef GAMEQC
+// decolorizes and team colors the player name when needed
+string playername(string thename, int teamid, bool team_colorize)
+{
+ TC(int, teamid);
+ bool do_colorize = (teamplay && team_colorize);
+#ifdef SVQC
+ if(do_colorize && !intermission_running)
+#else
+ if(do_colorize)
+#endif
+ {
+ string t = Team_ColorCode(teamid);
+ return strcat(t, strdecolorize(thename));
+ }
+ else
+ return thename;
+}
+#endif
// Returns the correct difference between two always increasing numbers
#define COMPARE_INCREASING(to,from) (to < from ? from + to + 2 : to - from)
+
+#ifdef SVQC
+void attach_sameorigin(entity e, entity to, string tag);
+
+void detach_sameorigin(entity e);
+
+void follow_sameorigin(entity e, entity to);
+
+void SetMovetypeFollow(entity ent, entity e);
+
+void UnsetMovetypeFollow(entity ent);
+
+float LostMovetypeFollow(entity ent);
+#endif
+
+#ifdef GAMEQC
+string playername(string thename, int teamid, bool team_colorize);
+#endif
## entities
entity e = new(foo);
+ IL_PUSH(g_components, e);
e.com_$component = true;
e.com_$component_$property = 42;
#include <common/weapons/_all.qh>
#include <common/stats.qh>
#include <server/utils.qh>
+ #include <server/weapons/common.qh>
#endif
#ifdef SVQC
string namestr = "";
if (source)
- namestr = playername(source, autocvar_g_chat_teamcolors);
+ namestr = playername(source.netname, source.team, (autocvar_g_chat_teamcolors && IS_PLAYER(source)));
string colorprefix = (strdecolorize(namestr) == namestr) ? "^3" : "^7";
privatemsgprefixlen = strlen(msgstr);
msgstr = strcat(msgstr, msgin);
cmsgstr = strcat(colorstr, colorprefix, namestr, "^3 tells you:\n^7", msgin);
- privatemsgprefix = strcat("\{1}\{13}* ^3You tell ", playername(privatesay, autocvar_g_chat_teamcolors), ": ^7");
+ privatemsgprefix = strcat("\{1}\{13}* ^3You tell ", playername(privatesay.netname, privatesay.team, (autocvar_g_chat_teamcolors && IS_PLAYER(privatesay))), ": ^7");
}
else if(teamsay)
{
}
if(flood)
- LOG_INFO("NOTE: ", playername(source, true), "^7 is flooding.");
+ LOG_INFO("NOTE: ", playername(source.netname, source.team, IS_PLAYER(source)), "^7 is flooding.");
// build sourcemsgstr by cutting off a prefix and replacing it by the other one
if(privatesay)
if (source) {
sprint(source, sourcemsgstr);
dedicated_print(msgstr); // send to server console too
- MX_Say(strcat(playername(source, true), "^7: ", msgin));
+ MX_Say(strcat(playername(source.netname, source.team, IS_PLAYER(source)), "^7: ", msgin));
}
FOREACH_CLIENT(IS_REAL_CLIENT(it) && it != source && !MUTATOR_CALLHOOK(ChatMessageTo, it, source), {
sprint(it, msgstr);
// if we get here, player is not allowed to cheat. Log it.
if(i)
- bprintf("Player %s^7 tried to use cheat 'impulse %d'\n", playername(this, false), i);
+ bprintf("Player %s^7 tried to use cheat 'impulse %d'\n", playername(this.netname, this.team, false), i);
else if(argc)
- bprintf("Player %s^7 tried to use cheat '%s'\n", playername(this, false), argv(0));
+ bprintf("Player %s^7 tried to use cheat '%s'\n", playername(this.netname, this.team, false), argv(0));
else if(fr)
- bprintf("Player %s^7 tried to use cheat frame %d\n", playername(this, false), fr);
+ bprintf("Player %s^7 tried to use cheat frame %d\n", playername(this.netname, this.team, false), fr);
else
- bprintf("Player %s^7 tried to use an unknown cheat\n", playername(this, false));
+ bprintf("Player %s^7 tried to use an unknown cheat\n", playername(this.netname, this.team, false));
return 0;
}
CS(this).allowed_timeouts = autocvar_sv_timeout_number;
if (autocvar_sv_eventlog)
- GameLogEcho(strcat(":join:", ftos(this.playerid), ":", ftos(etof(this)), ":", ((IS_REAL_CLIENT(this)) ? GameLog_ProcessIP(this.netaddress) : "bot"), ":", playername(this, false)));
+ GameLogEcho(strcat(":join:", ftos(this.playerid), ":", ftos(etof(this)), ":", ((IS_REAL_CLIENT(this)) ? GameLog_ProcessIP(this.netaddress) : "bot"), ":", playername(this.netname, this.team, false)));
CS(this).just_joined = true; // stop spamming the eventlog with additional lines when the client connects
// stuffcmd(this, strcat("name ", this.netname, "\n")); // maybe?
}
if (!assume_unchanged && autocvar_sv_eventlog)
- GameLogEcho(strcat(":name:", ftos(this.playerid), ":", playername(this, false)));
+ GameLogEcho(strcat(":name:", ftos(this.playerid), ":", playername(this.netname, this.team, false)));
strcpy(CS(this).netname_previous, this.netname);
}
#include <common/command/_mod.qh>
#include "common.qh"
+#include "getreplies.qh"
#include "vote.qh"
#include "../bot/api.qh"
{
caller.ready = false;
if(IS_PLAYER(caller) || caller.caplayer == 1)
- bprint(playername(caller, false), "^2 is ^1NOT^2 ready\n");
+ bprint(playername(caller.netname, caller.team, false), "^2 is ^1NOT^2 ready\n");
}
else
{
caller.ready = true;
if(IS_PLAYER(caller) || caller.caplayer == 1)
- bprint(playername(caller, false), "^2 is ready\n");
+ bprint(playername(caller.netname, caller.team, false), "^2 is ready\n");
}
// cannot reset the game while a timeout is active!
// if client return player nickname, or if server return admin nickname
string GetCallerName(entity caller)
{
- if (caller) return playername(caller, false);
+ if (caller) return playername(caller.netname, caller.team, false);
else return ((autocvar_sv_adminnick != "") ? autocvar_sv_adminnick : "SERVER ADMIN"); // autocvar_hostname
}
#include "getreplies.qh"
#include <common/weapons/_all.qh>
+#include <common/wepent.qh>
#include <common/stats.qh>
#include <server/intermission.qh>
#include <server/world.qh>
return sprintf("^7Monsters available: %s\n", monsterlist);
}
+
+/*
+=============
+GetCvars
+=============
+Called with:
+ 0: sends the request
+ >0: receives a cvar from name=argv(f) value=argv(f+1)
+*/
+void GetCvars_handleString(entity this, entity store, string thisname, float f, .string field, string name)
+{
+ if (f < 0)
+ {
+ strfree(store.(field));
+ }
+ else if (f > 0)
+ {
+ if (thisname == name)
+ {
+ strcpy(store.(field), argv(f + 1));
+ }
+ }
+ else
+ stuffcmd(this, strcat("cl_cmd sendcvar ", name, "\n"));
+}
+void GetCvars_handleString_Fixup(entity this, entity store, string thisname, float f, .string field, string name, string(entity, string) func)
+{
+ GetCvars_handleString(this, store, thisname, f, field, name);
+ if (f >= 0) // also initialize to the fitting value for "" when sending cvars out
+ if (thisname == name)
+ {
+ string s = func(this, strcat1(store.(field)));
+ if (s != store.(field))
+ {
+ strcpy(store.(field), s);
+ }
+ }
+}
+void GetCvars_handleFloat(entity this, entity store, string thisname, float f, .float field, string name)
+{
+ if (f < 0)
+ {
+ }
+ else if (f > 0)
+ {
+ if (thisname == name)
+ store.(field) = stof(argv(f + 1));
+ }
+ else
+ stuffcmd(this, strcat("cl_cmd sendcvar ", name, "\n"));
+}
+void GetCvars_handleFloatOnce(entity this, entity store, string thisname, float f, .float field, string name)
+{
+ if (f < 0)
+ {
+ }
+ else if (f > 0)
+ {
+ if (thisname == name)
+ {
+ if (!store.(field))
+ {
+ store.(field) = stof(argv(f + 1));
+ if (!store.(field))
+ store.(field) = -1;
+ }
+ }
+ }
+ else
+ {
+ if (!store.(field))
+ stuffcmd(this, strcat("cl_cmd sendcvar ", name, "\n"));
+ }
+}
+string W_FixWeaponOrder_ForceComplete_AndBuildImpulseList(entity this, string wo)
+{
+ string o = W_FixWeaponOrder_ForceComplete(wo);
+ strcpy(CS(this).weaponorder_byimpulse, W_FixWeaponOrder_BuildImpulseList(o));
+ return o;
+}
+
+/**
+ * @param f -1: cleanup, 0: request, 1: receive
+ */
+void GetCvars(entity this, entity store, int f)
+{
+ string s = string_null;
+
+ if (f == 0)
+ LOG_INFO("Warning: requesting cvar values is deprecated. Client should send them automatically using REPLICATE.\n");
+
+ if (f > 0)
+ s = strcat1(argv(f));
+
+ get_cvars_f = f;
+ get_cvars_s = s;
+ MUTATOR_CALLHOOK(GetCvars);
+
+ Notification_GetCvars(this);
+
+ ReplicateVars(this, store, s, f);
+
+ GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriority, "cl_weaponpriority", W_FixWeaponOrder_ForceComplete_AndBuildImpulseList);
+ GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[0], "cl_weaponpriority0", W_FixWeaponOrder_AllowIncomplete);
+ GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[1], "cl_weaponpriority1", W_FixWeaponOrder_AllowIncomplete);
+ GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[2], "cl_weaponpriority2", W_FixWeaponOrder_AllowIncomplete);
+ GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[3], "cl_weaponpriority3", W_FixWeaponOrder_AllowIncomplete);
+ GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[4], "cl_weaponpriority4", W_FixWeaponOrder_AllowIncomplete);
+ GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[5], "cl_weaponpriority5", W_FixWeaponOrder_AllowIncomplete);
+ GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[6], "cl_weaponpriority6", W_FixWeaponOrder_AllowIncomplete);
+ GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[7], "cl_weaponpriority7", W_FixWeaponOrder_AllowIncomplete);
+ GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[8], "cl_weaponpriority8", W_FixWeaponOrder_AllowIncomplete);
+ GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[9], "cl_weaponpriority9", W_FixWeaponOrder_AllowIncomplete);
+
+ GetCvars_handleFloat(this, store, s, f, cvar_cl_allow_uidtracking, "cl_allow_uidtracking");
+
+ // fixup of switchweapon (needed for LMS or when spectating is disabled, as PutClientInServer comes too early)
+ if (f > 0)
+ {
+ if (s == "cl_weaponpriority")
+ {
+ for(int slot = 0; slot < MAX_WEAPONSLOTS; ++slot)
+ {
+ .entity weaponentity = weaponentities[slot];
+ if (this.(weaponentity) && (this.(weaponentity).m_weapon != WEP_Null || slot == 0))
+ this.(weaponentity).m_switchweapon = w_getbestweapon(this, weaponentity);
+ }
+ }
+ if (s == "cl_allow_uidtracking")
+ PlayerStats_GameReport_AddPlayer(this);
+ //if (s == "cl_gunalign")
+ //W_ResetGunAlign(this, store.cvar_cl_gunalign);
+ }
+}
string getmaplist();
string getlsmaps();
string getmonsterlist();
+
+void GetCvars_handleFloat(entity this, entity store, string thisname, float f, .float field, string name);
+
+void GetCvars_handleString(entity this, entity store, string thisname, float f, .string field, string name);
+
+void GetCvars(entity this, entity store, int f);
sprint(client, strcat("\{1}\{13}^3", GetCallerName(NULL), "^7: ", admin_message, "\n"));
}
- successful = strcat(successful, (successful ? ", " : ""), playername(client, false));
- LOG_TRACE("Message sent to ", playername(client, false));
+ successful = strcat(successful, (successful ? ", " : ""), playername(client.netname, client.team, false));
+ LOG_TRACE("Message sent to ", playername(client.netname, client.team, false));
continue;
}
if (accepted > 0)
{
stuffcmd(client, "defer clear\n");
- LOG_INFO("defer clear stuffed to ", playername(client, false));
+ LOG_INFO("defer clear stuffed to ", playername(client.netname, client.team, false));
}
else { LOG_INFO("defer_clear: ", GetClientErrorString(accepted, argv(1)), "."); }
if (client.caplayer) client.caplayer = 0;
PutObserverInServer(client);
- successful = strcat(successful, (successful ? ", " : ""), playername(client, false));
+ successful = strcat(successful, (successful ? ", " : ""), playername(client.netname, client.team, false));
}
else
{
- LOG_INFO("Player ", ftos(GetFilteredNumber(t)), " (", playername(client, false), ") is already spectating.");
+ LOG_INFO("Player ", ftos(GetFilteredNumber(t)), " (", playername(client.netname, client.team, false), ") is already spectating.");
}
continue;
}
if (team_num == client.team) // already on the destination team
{
// keep the forcing undone
- LOG_INFO("Player ", ftos(GetFilteredNumber(t)), " (", playername(client, false), ") is already on the ", Team_ColoredFullName(client.team), (targets ? "^7, skipping to next player.\n" : "^7."));
+ LOG_INFO("Player ", ftos(GetFilteredNumber(t)), " (", playername(client.netname, client.team, false), ") is already on the ", Team_ColoredFullName(client.team), (targets ? "^7, skipping to next player.\n" : "^7."));
continue;
}
else if (team_num == 0) // auto team
Player_SetForcedTeamIndex(client, TEAM_FORCE_DEFAULT);
if (MoveToTeam(client, team_id, 6))
{
- successful = strcat(successful, (successful ? ", " : ""), playername(client, false));
- LOG_INFO("Player ", ftos(GetFilteredNumber(t)), " (", playername(client, false), ") has been moved to the ", Team_ColoredFullName(team_id), "^7.");
+ successful = strcat(successful, (successful ? ", " : ""), playername(client.netname, client.team, false));
+ LOG_INFO("Player ", ftos(GetFilteredNumber(t)), " (", playername(client.netname, client.team, false), ") has been moved to the ", Team_ColoredFullName(team_id), "^7.");
}
else
{
- LOG_INFO("Unable to move player ", ftos(GetFilteredNumber(t)), " (", playername(client, false), ")");
+ LOG_INFO("Unable to move player ", ftos(GetFilteredNumber(t)), " (", playername(client.netname, client.team, false), ")");
}
continue;
}
// If the vote_caller is still here, return their name, otherwise vote_caller_name
string OriginalCallerName()
{
- if (IS_REAL_CLIENT(vote_caller)) return playername(vote_caller, false);
+ if (IS_REAL_CLIENT(vote_caller)) return playername(vote_caller.netname, vote_caller.team, false);
return vote_caller_name;
}
#include <server/mutators/_mod.qh>
#include <server/teamplay.qh>
+#include <server/world.qh>
#include <server/weapons/common.qh>
#include <server/weapons/selection.qh>
WarpZone_traceline_antilag(pl, CS(pl).cursor_trace_start, CS(pl).cursor_trace_start + normalize(CS(pl).cursor_trace_endpos - CS(pl).cursor_trace_start) * max_shot_distance, MOVE_NORMAL, pl, ANTILAG_LATENCY(pl));
}
-/*
-=============
-GetCvars
-=============
-Called with:
- 0: sends the request
- >0: receives a cvar from name=argv(f) value=argv(f+1)
-*/
-void GetCvars_handleString(entity this, entity store, string thisname, float f, .string field, string name)
-{
- if (f < 0)
- {
- strfree(store.(field));
- }
- else if (f > 0)
- {
- if (thisname == name)
- {
- strcpy(store.(field), argv(f + 1));
- }
- }
- else
- stuffcmd(this, strcat("cl_cmd sendcvar ", name, "\n"));
-}
-void GetCvars_handleString_Fixup(entity this, entity store, string thisname, float f, .string field, string name, string(entity, string) func)
-{
- GetCvars_handleString(this, store, thisname, f, field, name);
- if (f >= 0) // also initialize to the fitting value for "" when sending cvars out
- if (thisname == name)
- {
- string s = func(this, strcat1(store.(field)));
- if (s != store.(field))
- {
- strcpy(store.(field), s);
- }
- }
-}
-void GetCvars_handleFloat(entity this, entity store, string thisname, float f, .float field, string name)
-{
- if (f < 0)
- {
- }
- else if (f > 0)
- {
- if (thisname == name)
- store.(field) = stof(argv(f + 1));
- }
- else
- stuffcmd(this, strcat("cl_cmd sendcvar ", name, "\n"));
-}
-void GetCvars_handleFloatOnce(entity this, entity store, string thisname, float f, .float field, string name)
-{
- if (f < 0)
- {
- }
- else if (f > 0)
- {
- if (thisname == name)
- {
- if (!store.(field))
- {
- store.(field) = stof(argv(f + 1));
- if (!store.(field))
- store.(field) = -1;
- }
- }
- }
- else
- {
- if (!store.(field))
- stuffcmd(this, strcat("cl_cmd sendcvar ", name, "\n"));
- }
-}
-string W_FixWeaponOrder_ForceComplete_AndBuildImpulseList(entity this, string wo)
-{
- string o = W_FixWeaponOrder_ForceComplete(wo);
- strcpy(CS(this).weaponorder_byimpulse, W_FixWeaponOrder_BuildImpulseList(o));
- return o;
-}
-
-/**
- * @param f -1: cleanup, 0: request, 1: receive
- */
-void GetCvars(entity this, entity store, int f)
-{
- string s = string_null;
-
- if (f == 0)
- LOG_INFO("Warning: requesting cvar values is deprecated. Client should send them automatically using REPLICATE.\n");
-
- if (f > 0)
- s = strcat1(argv(f));
-
- get_cvars_f = f;
- get_cvars_s = s;
- MUTATOR_CALLHOOK(GetCvars);
-
- Notification_GetCvars(this);
-
- ReplicateVars(this, store, s, f);
-
- GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriority, "cl_weaponpriority", W_FixWeaponOrder_ForceComplete_AndBuildImpulseList);
- GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[0], "cl_weaponpriority0", W_FixWeaponOrder_AllowIncomplete);
- GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[1], "cl_weaponpriority1", W_FixWeaponOrder_AllowIncomplete);
- GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[2], "cl_weaponpriority2", W_FixWeaponOrder_AllowIncomplete);
- GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[3], "cl_weaponpriority3", W_FixWeaponOrder_AllowIncomplete);
- GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[4], "cl_weaponpriority4", W_FixWeaponOrder_AllowIncomplete);
- GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[5], "cl_weaponpriority5", W_FixWeaponOrder_AllowIncomplete);
- GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[6], "cl_weaponpriority6", W_FixWeaponOrder_AllowIncomplete);
- GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[7], "cl_weaponpriority7", W_FixWeaponOrder_AllowIncomplete);
- GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[8], "cl_weaponpriority8", W_FixWeaponOrder_AllowIncomplete);
- GetCvars_handleString_Fixup(this, store, s, f, cvar_cl_weaponpriorities[9], "cl_weaponpriority9", W_FixWeaponOrder_AllowIncomplete);
-
- GetCvars_handleFloat(this, store, s, f, cvar_cl_allow_uidtracking, "cl_allow_uidtracking");
-
- // fixup of switchweapon (needed for LMS or when spectating is disabled, as PutClientInServer comes too early)
- if (f > 0)
- {
- if (s == "cl_weaponpriority")
- {
- for(int slot = 0; slot < MAX_WEAPONSLOTS; ++slot)
- {
- .entity weaponentity = weaponentities[slot];
- if (this.(weaponentity) && (this.(weaponentity).m_weapon != WEP_Null || slot == 0))
- this.(weaponentity).m_switchweapon = w_getbestweapon(this, weaponentity);
- }
- }
- if (s == "cl_allow_uidtracking")
- PlayerStats_GameReport_AddPlayer(this);
- //if (s == "cl_gunalign")
- //W_ResetGunAlign(this, store.cvar_cl_gunalign);
- }
-}
-
-// decolorizes and team colors the player name when needed
-string playername(entity p, bool team_colorize)
-{
- string t;
- if (team_colorize && teamplay && !intermission_running && IS_PLAYER(p))
- {
- t = Team_ColorCode(p.team);
- return strcat(t, strdecolorize(p.netname));
- }
- else
- return p.netname;
-}
-
float want_weapon(entity weaponinfo, float allguns)
{
int d = 0;
warmup_start_ammo_fuel = max(0, warmup_start_ammo_fuel);
}
-void precache_playermodel(string m)
-{
- int globhandle, i, n;
- string f;
-
- // remove :<skinnumber> suffix
- int j = strstrofs(m, ":", 0);
- if(j >= 0)
- m = substring(m, 0, j);
-
- if(substring(m, -9, 5) == "_lod1")
- return;
- if(substring(m, -9, 5) == "_lod2")
- return;
- precache_model(m);
- f = strcat(substring(m, 0, -5), "_lod1", substring(m, -4, -1));
- if(fexists(f))
- precache_model(f);
- f = strcat(substring(m, 0, -5), "_lod2", substring(m, -4, -1));
- if(fexists(f))
- precache_model(f);
-
- globhandle = search_begin(strcat(m, "_*.sounds"), true, false);
- if (globhandle < 0)
- return;
- n = search_getsize(globhandle);
- for (i = 0; i < n; ++i)
- {
- //print(search_getfilename(globhandle, i), "\n");
- f = search_getfilename(globhandle, i);
- PrecachePlayerSounds(f);
- }
- search_end(globhandle);
-}
-void precache_all_playermodels(string pattern)
-{
- int globhandle = search_begin(pattern, true, false);
- if (globhandle < 0) return;
- int n = search_getsize(globhandle);
- for (int i = 0; i < n; ++i)
- {
- string s = search_getfilename(globhandle, i);
- precache_playermodel(s);
- }
- search_end(globhandle);
-}
-
-void precache_playermodels(string s)
-{
- FOREACH_WORD(s, true, { precache_playermodel(it); });
-}
-
-PRECACHE(PlayerModels)
-{
- // Precache all player models if desired
- if (autocvar_sv_precacheplayermodels)
- {
- PrecachePlayerSounds("sound/player/default.sounds");
- precache_all_playermodels("models/player/*.zym");
- precache_all_playermodels("models/player/*.dpm");
- precache_all_playermodels("models/player/*.md3");
- precache_all_playermodels("models/player/*.psk");
- precache_all_playermodels("models/player/*.iqm");
- }
-
- if (autocvar_sv_defaultcharacter)
- {
- precache_playermodels(autocvar_sv_defaultplayermodel_red);
- precache_playermodels(autocvar_sv_defaultplayermodel_blue);
- precache_playermodels(autocvar_sv_defaultplayermodel_yellow);
- precache_playermodels(autocvar_sv_defaultplayermodel_pink);
- precache_playermodels(autocvar_sv_defaultplayermodel);
- }
-}
-
void InitializeEntity(entity e, void(entity this) func, int order)
{
entity prev, cur;
delete_fn = remove_unsafely;
}
-void adaptor_think2use_hittype_splash(entity this) // for timed projectile detonation
-{
- if(!(IS_ONGROUND(this))) // if onground, we ARE touching something, but HITTYPE_SPLASH is to be networked if the damage causing projectile is not touching ANYTHING
- this.projectiledeathtype |= HITTYPE_SPLASH;
- adaptor_think2use(this);
-}
-
-// deferred dropping
-void DropToFloor_Handler(entity this)
-{
- WITHSELF(this, builtin_droptofloor());
- this.dropped_origin = this.origin;
-}
-
-void droptofloor(entity this)
-{
- InitializeEntity(this, DropToFloor_Handler, INITPRIO_DROPTOFLOOR);
-}
-
-
-
float trace_hits_box_a0, trace_hits_box_a1;
float trace_hits_box_1d(float end, float thmi, float thma)
return trace_hits_box(start, end, thmi - ma, thma - mi);
}
-bool SUB_NoImpactCheck(entity this, entity toucher)
-{
- // zero hitcontents = this is not the real impact, but either the
- // mirror-impact of something hitting the projectile instead of the
- // projectile hitting the something, or a touchareagrid one. Neither of
- // these stop the projectile from moving, so...
- if(trace_dphitcontents == 0)
- {
- LOG_TRACEF("A hit from a projectile happened with no hit contents! DEBUG THIS, this should never happen for projectiles! Projectile will self-destruct. (edict: %i, classname: %s, origin: %v)", this, this.classname, this.origin);
- checkclient(this); // TODO: .health is checked in the engine with this, possibly replace with a QC function?
- }
- if (trace_dphitq3surfaceflags & Q3SURFACEFLAG_NOIMPACT)
- return true;
- if (toucher == NULL && this.size != '0 0 0')
- {
- vector tic;
- tic = this.velocity * sys_frametime;
- tic = tic + normalize(tic) * vlen(this.maxs - this.mins);
- traceline(this.origin - tic, this.origin + tic, MOVE_NORMAL, this);
- if (trace_fraction >= 1)
- {
- LOG_TRACE("Odd... did not hit...?");
- }
- else if (trace_dphitq3surfaceflags & Q3SURFACEFLAG_NOIMPACT)
- {
- LOG_TRACE("Detected and prevented the sky-grapple bug.");
- return true;
- }
- }
-
- return false;
-}
-
-bool WarpZone_Projectile_Touch_ImpactFilter_Callback(entity this, entity toucher)
-{
- // owner check
- if(toucher && toucher == this.owner)
- return true;
- if(SUB_NoImpactCheck(this, toucher))
- {
- if(this.classname == "nade")
- return false; // no checks here
- else if(this.classname == "grapplinghook")
- RemoveHook(this);
- else
- delete(this);
- return true;
- }
- if(trace_ent && trace_ent.solid > SOLID_TRIGGER)
- UpdateCSQCProjectile(this);
- return false;
-}
-
/** engine callback */
void URI_Get_Callback(float id, float status, string data)
{
{
return MoveToRandomLocationWithinBounds(e, world.mins, world.maxs, goodcontents, badcontents, badsurfaceflags, attempts, maxaboveground, minviewdistance);
}
-
-void write_recordmarker(entity pl, float tstart, float dt)
-{
- GameLogEcho(strcat(":recordset:", ftos(pl.playerid), ":", ftos(dt)));
-
- // also write a marker into demo files for demotc-race-record-extractor to find
- stuffcmd(pl,
- strcat(
- strcat("//", strconv(2, 0, 0, GetGametype()), " RECORD SET ", TIME_ENCODED_TOSTRING(TIME_ENCODE(dt))),
- " ", ftos(tstart), " ", ftos(dt), "\n"));
-}
-
-void attach_sameorigin(entity e, entity to, string tag)
-{
- vector org, t_forward, t_left, t_up, e_forward, e_up;
- float tagscale;
-
- org = e.origin - gettaginfo(to, gettagindex(to, tag));
- tagscale = (vlen(v_forward) ** -2); // undo a scale on the tag
- t_forward = v_forward * tagscale;
- t_left = v_right * -tagscale;
- t_up = v_up * tagscale;
-
- e.origin_x = org * t_forward;
- e.origin_y = org * t_left;
- e.origin_z = org * t_up;
-
- // current forward and up directions
- if (substring(e.model, 0, 1) == "*") // bmodels have their own rules
- e.angles = AnglesTransform_FromVAngles(e.angles);
- else
- e.angles = AnglesTransform_FromAngles(e.angles);
- fixedmakevectors(e.angles);
-
- // untransform forward, up!
- e_forward.x = v_forward * t_forward;
- e_forward.y = v_forward * t_left;
- e_forward.z = v_forward * t_up;
- e_up.x = v_up * t_forward;
- e_up.y = v_up * t_left;
- e_up.z = v_up * t_up;
-
- e.angles = fixedvectoangles2(e_forward, e_up);
- if (substring(e.model, 0, 1) == "*") // bmodels have their own rules
- e.angles = AnglesTransform_ToVAngles(e.angles);
- else
- e.angles = AnglesTransform_ToAngles(e.angles);
-
- setattachment(e, to, tag);
- setorigin(e, e.origin);
-}
-
-void detach_sameorigin(entity e)
-{
- vector org;
- org = gettaginfo(e, 0);
- e.angles = fixedvectoangles2(v_forward, v_up);
- if (substring(e.model, 0, 1) == "*") // bmodels have their own rules
- e.angles = AnglesTransform_ToVAngles(e.angles);
- else
- e.angles = AnglesTransform_ToAngles(e.angles);
- setorigin(e, org);
- setattachment(e, NULL, "");
- setorigin(e, e.origin);
-}
-
-void follow_sameorigin(entity e, entity to)
-{
- set_movetype(e, MOVETYPE_FOLLOW); // make the hole follow
- e.aiment = to; // make the hole follow bmodel
- e.punchangle = to.angles; // the original angles of bmodel
- e.view_ofs = e.origin - to.origin; // relative origin
- e.v_angle = e.angles - to.angles; // relative angles
-}
-
-#if 0
-// TODO: unused, likely for a reason, possibly needs extensions (allow setting the new movetype as a parameter?)
-void unfollow_sameorigin(entity e)
-{
- set_movetype(e, MOVETYPE_NONE);
-}
-#endif
-
-.string aiment_classname;
-.float aiment_deadflag;
-void SetMovetypeFollow(entity ent, entity e)
-{
- // FIXME this may not be warpzone aware
- set_movetype(ent, MOVETYPE_FOLLOW); // make the hole follow
- ent.solid = SOLID_NOT; // MOVETYPE_FOLLOW is always non-solid - this means this cannot be teleported by warpzones any more! Instead, we must notice when our owner gets teleported.
- ent.aiment = e; // make the hole follow bmodel
- ent.punchangle = e.angles; // the original angles of bmodel
- ent.view_ofs = ent.origin - e.origin; // relative origin
- ent.v_angle = ent.angles - e.angles; // relative angles
- ent.aiment_classname = strzone(e.classname);
- ent.aiment_deadflag = e.deadflag;
-}
-void UnsetMovetypeFollow(entity ent)
-{
- set_movetype(ent, MOVETYPE_FLY);
- PROJECTILE_MAKETRIGGER(ent);
- ent.aiment = NULL;
-}
-float LostMovetypeFollow(entity ent)
-{
-/*
- if(ent.move_movetype != MOVETYPE_FOLLOW)
- if(ent.aiment)
- error("???");
-*/
- if(ent.aiment)
- {
- if(ent.aiment.classname != ent.aiment_classname)
- return 1;
- if(ent.aiment.deadflag != ent.aiment_deadflag)
- return 1;
- }
- return 0;
-}
.vector dropped_origin;
-void write_recordmarker(entity pl, float tstart, float dt);
-
-void GetCvars_handleFloat(entity this, entity store, string thisname, float f, .float field, string name);
-
-void GetCvars_handleString(entity this, entity store, string thisname, float f, .string field, string name);
-
-void precache_all_playermodels(string pattern);
-
void InitializeEntitiesRun();
-void droptofloor(entity this);
-
float trace_hits_box_1d(float end, float thmi, float thma);
float trace_hits_box(vector start, vector end, vector thmi, vector thma);
float tracebox_hits_box(vector start, vector mi, vector ma, vector end, vector thmi, vector thma);
-void attach_sameorigin(entity e, entity to, string tag);
-
void crosshair_trace(entity pl);
void crosshair_trace_plusvisibletriggers(entity pl);
void WarpZone_crosshair_trace_plusvisibletriggers(entity pl);
void crosshair_trace_plusvisibletriggers__is_wz(entity pl, bool is_wz);
-void detach_sameorigin(entity e);
-
-void follow_sameorigin(entity e, entity to);
-
-void GetCvars(entity this, entity store, int f);
-
-float LostMovetypeFollow(entity ent);
-
string uid2name(string myuid);
bool MoveToRandomLocationWithinBounds(entity e, vector boundmin, vector boundmax, float goodcontents, float badcontents, float badsurfaceflags, int attempts, float maxaboveground, float minviewdistance);
float MoveToRandomMapLocation(entity e, float goodcontents, float badcontents, float badsurfaceflags, float attempts, float maxaboveground, float minviewdistance);
-string playername(entity p, bool team_colorize);
-
-void SetMovetypeFollow(entity ent, entity e);
-
float tracebox_hits_box(vector start, vector mi, vector ma, vector end, vector thmi, vector thma);
void traceline_antilag (entity source, vector v1, vector v2, float nomonst, entity forent, float lag);
GiveResourceWithLimit(targ, RES_HEALTH, amount, limit);
return true;
}
+
+void precache_playermodel(string m)
+{
+ int globhandle, i, n;
+ string f;
+
+ // remove :<skinnumber> suffix
+ int j = strstrofs(m, ":", 0);
+ if(j >= 0)
+ m = substring(m, 0, j);
+
+ if(substring(m, -9, 5) == "_lod1")
+ return;
+ if(substring(m, -9, 5) == "_lod2")
+ return;
+ precache_model(m);
+ f = strcat(substring(m, 0, -5), "_lod1", substring(m, -4, -1));
+ if(fexists(f))
+ precache_model(f);
+ f = strcat(substring(m, 0, -5), "_lod2", substring(m, -4, -1));
+ if(fexists(f))
+ precache_model(f);
+
+ globhandle = search_begin(strcat(m, "_*.sounds"), true, false);
+ if (globhandle < 0)
+ return;
+ n = search_getsize(globhandle);
+ for (i = 0; i < n; ++i)
+ {
+ //print(search_getfilename(globhandle, i), "\n");
+ f = search_getfilename(globhandle, i);
+ PrecachePlayerSounds(f);
+ }
+ search_end(globhandle);
+}
+void precache_all_playermodels(string pattern)
+{
+ int globhandle = search_begin(pattern, true, false);
+ if (globhandle < 0) return;
+ int n = search_getsize(globhandle);
+ for (int i = 0; i < n; ++i)
+ {
+ string s = search_getfilename(globhandle, i);
+ precache_playermodel(s);
+ }
+ search_end(globhandle);
+}
+
+void precache_playermodels(string s)
+{
+ FOREACH_WORD(s, true, { precache_playermodel(it); });
+}
+
+PRECACHE(PlayerModels)
+{
+ // Precache all player models if desired
+ if (autocvar_sv_precacheplayermodels)
+ {
+ PrecachePlayerSounds("sound/player/default.sounds");
+ precache_all_playermodels("models/player/*.zym");
+ precache_all_playermodels("models/player/*.dpm");
+ precache_all_playermodels("models/player/*.md3");
+ precache_all_playermodels("models/player/*.psk");
+ precache_all_playermodels("models/player/*.iqm");
+ }
+
+ if (autocvar_sv_defaultcharacter)
+ {
+ precache_playermodels(autocvar_sv_defaultplayermodel_red);
+ precache_playermodels(autocvar_sv_defaultplayermodel_blue);
+ precache_playermodels(autocvar_sv_defaultplayermodel_yellow);
+ precache_playermodels(autocvar_sv_defaultplayermodel_pink);
+ precache_playermodels(autocvar_sv_defaultplayermodel);
+ }
+}
bool PlayerHeal(entity targ, entity inflictor, float amount, float limit);
+void precache_all_playermodels(string pattern);
+
IntrusiveList g_clones;
STATIC_INIT(g_clones) { g_clones = IL_NEW(); }
#include <common/weapons/_all.qh>
#include <common/stats.qh>
#include <server/damage.qh>
+#include <server/gamelog.qh>
#include <server/intermission.qh>
#include <server/world.qh>
#include <server/miscfunctions.qh>
#include <common/vehicles/sv_vehicles.qh>
#include "../common/mutators/mutator/waypoints/waypointsprites.qh"
+void write_recordmarker(entity pl, float tstart, float dt)
+{
+ GameLogEcho(strcat(":recordset:", ftos(pl.playerid), ":", ftos(dt)));
+
+ // also write a marker into demo files for demotc-race-record-extractor to find
+ stuffcmd(pl,
+ strcat(
+ strcat("//", strconv(2, 0, 0, GetGametype()), " RECORD SET ", TIME_ENCODED_TOSTRING(TIME_ENCODE(dt))),
+ " ", ftos(tstart), " ", ftos(dt), "\n"));
+}
+
IntrusiveList g_race_targets;
IntrusiveList g_racecheckpoints;
STATIC_INIT(g_race)
.entity race_respawn_spotref; // try THIS spawn in case you respawn
// definitions for functions used outside race.qc
+void write_recordmarker(entity pl, float tstart, float dt);
+
float race_PreviousCheckpoint(float f);
float race_NextCheckpoint(float f);
void race_AbandonRaceCheck(entity p);
sk = CS(p).scorekeeper;
- s = strcat(s, playername(p, false));
+ s = strcat(s, playername(p.netname, p.team, false));
for (;;)
{
i = strlennocol(s) - NAMEWIDTH;
void Score_NicePrint_Spectator(entity to, entity p)
{
- print_to(to, strcat(" ", playername(p, false)));
+ print_to(to, strcat(" ", playername(p.netname, p.team, false)));
}
.float score_dummyfield;
#include "common.qh"
+#include <server/command/common.qh>
#include <common/weapons/_all.qh>
#include <common/stats.qh>
#include <server/damage.qh>
this.nextthink = time;
setthink(this, explode);
}
+
+void adaptor_think2use_hittype_splash(entity this) // for timed projectile detonation
+{
+ if(!(IS_ONGROUND(this))) // if onground, we ARE touching something, but HITTYPE_SPLASH is to be networked if the damage causing projectile is not touching ANYTHING
+ this.projectiledeathtype |= HITTYPE_SPLASH;
+ adaptor_think2use(this);
+}
+
+bool SUB_NoImpactCheck(entity this, entity toucher)
+{
+ // zero hitcontents = this is not the real impact, but either the
+ // mirror-impact of something hitting the projectile instead of the
+ // projectile hitting the something, or a touchareagrid one. Neither of
+ // these stop the projectile from moving, so...
+ if(trace_dphitcontents == 0)
+ {
+ LOG_TRACEF("A hit from a projectile happened with no hit contents! DEBUG THIS, this should never happen for projectiles! Projectile will self-destruct. (edict: %i, classname: %s, origin: %v)", this, this.classname, this.origin);
+ checkclient(this); // TODO: .health is checked in the engine with this, possibly replace with a QC function?
+ }
+ if (trace_dphitq3surfaceflags & Q3SURFACEFLAG_NOIMPACT)
+ return true;
+ if (toucher == NULL && this.size != '0 0 0')
+ {
+ vector tic;
+ tic = this.velocity * sys_frametime;
+ tic = tic + normalize(tic) * vlen(this.maxs - this.mins);
+ traceline(this.origin - tic, this.origin + tic, MOVE_NORMAL, this);
+ if (trace_fraction >= 1)
+ {
+ LOG_TRACE("Odd... did not hit...?");
+ }
+ else if (trace_dphitq3surfaceflags & Q3SURFACEFLAG_NOIMPACT)
+ {
+ LOG_TRACE("Detected and prevented the sky-grapple bug.");
+ return true;
+ }
+ }
+
+ return false;
+}
+
+bool WarpZone_Projectile_Touch_ImpactFilter_Callback(entity this, entity toucher)
+{
+ // owner check
+ if(toucher && toucher == this.owner)
+ return true;
+ if(SUB_NoImpactCheck(this, toucher))
+ {
+ if(this.classname == "nade")
+ return false; // no checks here
+ else if(this.classname == "grapplinghook")
+ RemoveHook(this);
+ else
+ delete(this);
+ return true;
+ }
+ if(trace_ent && trace_ent.solid > SOLID_TRIGGER)
+ UpdateCSQCProjectile(this);
+ return false;
+}
float W_CheckProjectileDamage(entity inflictor, entity projowner, int deathtype, float exception);
void W_PrepareExplosionByDamage(entity this, entity attacker, void(entity this) explode);
+void adaptor_think2use_hittype_splash(entity this);
+
+bool WarpZone_Projectile_Touch_ImpactFilter_Callback(entity this, entity toucher);
+
.float misc_bulletcounter;
.int projectiledeathtype;
if(autocvar_g_hitplots || strhasword(autocvar_g_hitplots_individuals, player.netaddress))
{
CS(player).hitplotfh = fopen(strcat("hits-", matchid, "-", player.netaddress, "-", ftos(player.playerid), ".plot"), FILE_WRITE);
- fputs(CS(player).hitplotfh, strcat("#name ", playername(player, false), "\n"));
+ fputs(CS(player).hitplotfh, strcat("#name ", playername(player.netname, player.team, false), "\n"));
}
else { CS(player).hitplotfh = -1; }
}
s = strcat(s, "spectator:");
if(to_console)
- LOG_INFO(s, playername(it, false));
+ LOG_INFO(s, playername(it.netname, it.team, false));
if(to_eventlog)
- GameLogEcho(strcat(s, ftos(it.playerid), ":", playername(it, false)));
+ GameLogEcho(strcat(s, ftos(it.playerid), ":", playername(it.netname, it.team, false)));
if(to_file)
- fputs(file, strcat(s, playername(it, false), "\n"));
+ fputs(file, strcat(s, playername(it.netname, it.team, false), "\n"));
});
if(teamplay)
FOREACH_CLIENT(IS_PLAYER(it), {
FixIntermissionClient(it);
if(it.winning)
- bprint(playername(it, false), " ^7wins.\n");
+ bprint(playername(it.netname, it.team, false), " ^7wins.\n");
});
target_music_kill();
}
}
+// deferred dropping
+void DropToFloor_Handler(entity this)
+{
+ WITHSELF(this, builtin_droptofloor());
+ this.dropped_origin = this.origin;
+}
+
+void droptofloor(entity this)
+{
+ InitializeEntity(this, DropToFloor_Handler, INITPRIO_DROPTOFLOOR);
+}
+
bool autocvar_sv_gameplayfix_multiplethinksperframe = true;
void RunThink(entity this)
{
void CheckRules_World();
float RedirectionThink();
+void droptofloor(entity this);
+
IntrusiveList g_moveables;
STATIC_INIT(g_moveables) { g_moveables = IL_NEW(); }