Initial commit, carried over from Nuclide's Git on March 8th 2021

master
Marco Cawthorne 3 years ago
commit 67487d30cb

@ -0,0 +1,15 @@
ISC License
Copyright (c) 2016-2021, Marco "eukara" Hladik <marco@icculus.org>
Permission to use, copy, modify, and/or distribute this software for any
purpose with or without fee is hereby granted, provided that the above
copyright notice and this permission notice appear in all copies.
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.

@ -0,0 +1,34 @@
# FreeTFC
Clean-room reimplementation of Team Fortress Classic in QuakeC.
![Preview 1](img/preview1.jpg)
## Building
Clone the repository into the Nuclide-SDK:
> git clone REPOURL tfc
then either run Nuclide's ./build_game.sh shell script, or issue 'make' inside
./tfc/src!
Obviously make sure that Nuclide has fteqw and fteqcc set-up for building.
## Community
Join us on #halflife or #tfc via irc.frag-net.com and chat.
## License
ISC License
Copyright (c) 2016-2021 Marco Hladik <marco@icculus.org>
Permission to use, copy, modify, and distribute this software for any
purpose with or without fee is hereby granted, provided that the above
copyright notice and this permission notice appear in all copies.
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.

@ -0,0 +1,40 @@
// Generic Binds
bind "ESC" "togglemenu"
bind "w" "+forward"
bind "s" "+back"
bind "a" "+moveleft"
bind "d" "+moveright"
bind "SPACE" "+jump"
bind "CTRL" "+duck"
bind "SHIFT" "+speed"
bind "0" "slot10"
bind "1" "slot1"
bind "2" "slot2"
bind "3" "slot3"
bind "4" "slot4"
bind "5" "slot5"
bind "6" "slot6"
bind "7" "slot7"
bind "8" "slot8"
bind "9" "slot9"
bind "UPARROW" "+forward"
bind "DOWNARROW" "+back"
bind "LEFTARROW" "+left"
bind "RIGHTARROW" "+right"
bind "MOUSE1" "+attack"
bind "MOUSE2" "+attack2"
bind "MWHEELDOWN" "invnext"
bind "MWHEELUP" "invprev"
bind "r" "+reload"
bind "e" "+use"
bind "TAB" "+showscores"
bind "y" "messagemode"
bind "u" "messagemode2"
bind "t" "impulse 201"
bind "f" "impulse 100"
bind "f1" "vote yes"
bind "f2" "vote no"
// Game Variables
seta "hostname" "FreeTF Server"
seta "maxplayers" "8"

@ -0,0 +1,19 @@
weapon_dbs.fire
{
sample weapons/shotgn2.wav
}
weapon_sbs.cock
{
sample weapons/scock1.wav
}
weapon_sbs.fire
{
sample weapons/sbarrel1.wav
}
weapon_sbs.reload
{
sample weapons/reload3.wav
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 123 KiB

@ -0,0 +1,5 @@
CC=fteqcc
all:
cd client && $(MAKE)
cd server && $(MAKE)

@ -0,0 +1,4 @@
CC=fteqcc
all:
$(CC) progs.src

@ -0,0 +1,26 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
int
ClientGame_EntityUpdate(float id, float new)
{
switch (id) {
default:
return FALSE;
}
return TRUE;
}

@ -0,0 +1,69 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
/*
=================
ClientGame_Init
Comparable to worldspawn in SSQC in that it's mostly used for precaches
=================
*/
void
ClientGame_Init(float apilevel, string enginename, float engineversion)
{
Obituary_Init();
}
void
ClientGame_InitDone(void)
{
// VGUI_ChooseTeam();
}
void
ClientGame_RendererRestart(string rstr)
{
Obituary_Precache();
FX_Blood_Init();
FX_BreakModel_Init();
FX_Explosion_Init();
FX_GibHuman_Init();
FX_Spark_Init();
FX_Impact_Init();
precache_model("sprites/640hud1.spr");
precache_model("sprites/640hud2.spr");
precache_model("sprites/640hud3.spr");
precache_model("sprites/640hud4.spr");
precache_model("sprites/640hud5.spr");
precache_model("sprites/640hud6.spr");
precache_model("sprites/tfc_dmsg.spr");
precache_model("sprites/tfchud01.spr");
precache_model("sprites/tfchud02.spr");
precache_model("sprites/tfchud03.spr");
precache_model("sprites/tfchud04.spr");
precache_model("sprites/tfchud05.spr");
precache_model("sprites/tfchud06.spr");
precache_model("sprites/tfchud07.spr");
precache_model("sprites/chainsaw.spr");
precache_model("sprites/hammer.spr");
precache_model("sprites/w_cannon.spr");
BEAM_TRIPMINE = particleeffectnum("weapon_tripmine.beam");
}

@ -0,0 +1,38 @@
#pragma target fte
#pragma progs_dat "../..//csprogs.dat"
#define CSQC
#define CLIENT
#define VALVE
#define CLASSIC_VGUI
#define GS_RENDERFX
#includelist
../../../src/shared/fteextensions.qc
../../../src/shared/defs.h
../../../valve/src/client/defs.h
../../../src/client/defs.h
../../../src/vgui/include.src
../../../src/gs-entbase/client.src
../../../src/gs-entbase/shared.src
../shared/include.src
../../../valve/src/client/predict.qc
init.qc
../../../valve/src/client/player.qc
entities.qc
../../../valve/src/client/cmds.qc
../../../valve/src/client/game_event.qc
../../../valve/src/client/view.qc
../../../valve/src/client/obituary.qc
../../../valve/src/client/hud.qc
../../../valve/src/client/hud_weaponselect.qc
../../../valve/src/client/scoreboard.qc
../../../valve/src/client/input.qc
../../../base/src/client/modelevent.qc
../../../src/client/include.src
../../../src/shared/include.src
#endlist

@ -0,0 +1,217 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
static CUIWindow winChooseTeam;
static CUIWindow winCTTeam;
static CUIWindow winTTeam;
typedef struct
{
string str;
void(void) ptr;
} btnarr_t;
void
VGUI_TeamJoin(float i)
{
sendevent("TeamJoin", "f", i);
}
void
VGUI_TeamBack(void)
{
}
void VGUI_JoinScout_B (void) { VGUI_TeamJoin(1); }
void VGUI_JoinSniper_B (void) { VGUI_TeamJoin(2); }
void VGUI_JoinSoldier_B (void) { VGUI_TeamJoin(3); }
void VGUI_JoinDemoman_B (void) { VGUI_TeamJoin(4); }
void VGUI_JoinMedic_B (void) { VGUI_TeamJoin(5); }
void VGUI_JoinHwguy_B (void) { VGUI_TeamJoin(6); }
void VGUI_JoinPyro_B (void) { VGUI_TeamJoin(7); }
void VGUI_JoinSpy_B (void) { VGUI_TeamJoin(8); }
void VGUI_JoinEngineer_B (void) { VGUI_TeamJoin(9); }
void VGUI_JoinScout_R (void) { VGUI_TeamJoin(11); }
void VGUI_JoinSniper_R (void) { VGUI_TeamJoin(12); }
void VGUI_JoinSoldier_R (void) { VGUI_TeamJoin(13); }
void VGUI_JoinDemoman_R (void) { VGUI_TeamJoin(14); }
void VGUI_JoinMedic_R (void) { VGUI_TeamJoin(15); }
void VGUI_JoinHwguy_R (void) { VGUI_TeamJoin(16); }
void VGUI_JoinPyro_R (void) { VGUI_TeamJoin(17); }
void VGUI_JoinSpy_R (void) { VGUI_TeamJoin(18); }
void VGUI_JoinEngineer_R (void) { VGUI_TeamJoin(19); }
void VGUI_JoinScout_Y (void) { VGUI_TeamJoin(21); }
void VGUI_JoinSniper_Y (void) { VGUI_TeamJoin(22); }
void VGUI_JoinSoldier_Y (void) { VGUI_TeamJoin(23); }
void VGUI_JoinDemoman_Y (void) { VGUI_TeamJoin(24); }
void VGUI_JoinMedic_Y (void) { VGUI_TeamJoin(25); }
void VGUI_JoinHwguy_Y (void) { VGUI_TeamJoin(26); }
void VGUI_JoinPyro_Y (void) { VGUI_TeamJoin(27); }
void VGUI_JoinSpy_Y (void) { VGUI_TeamJoin(28); }
void VGUI_JoinEngineer_Y (void) { VGUI_TeamJoin(29); }
void VGUI_JoinScout_G (void) { VGUI_TeamJoin(31); }
void VGUI_JoinSniper_G (void) { VGUI_TeamJoin(32); }
void VGUI_JoinSoldier_G (void) { VGUI_TeamJoin(33); }
void VGUI_JoinDemoman_G (void) { VGUI_TeamJoin(34); }
void VGUI_JoinMedic_G (void) { VGUI_TeamJoin(35); }
void VGUI_JoinHwguy_G (void) { VGUI_TeamJoin(36); }
void VGUI_JoinPyro_G (void) { VGUI_TeamJoin(37); }
void VGUI_JoinSpy_G (void) { VGUI_TeamJoin(38); }
void VGUI_JoinEngineer_G (void) { VGUI_TeamJoin(39); }
btnarr_t red_team[] = {
{"SCOUT", VGUI_JoinScout_R },
{"SNIPER", VGUI_JoinSniper_R },
{"SOLDIER", VGUI_JoinSoldier_R },
{"DEMOMAN", VGUI_JoinDemoman_R },
{"MEDIC", VGUI_JoinMedic_R },
{"HWGUY", VGUI_JoinHwguy_R },
{"PYRO", VGUI_JoinPyro_R },
{"SPY", VGUI_JoinSpy_R },
{"ENGINEER", VGUI_JoinEngineer_R },
{__NULL__, __NULL__ },
{"< Back", VGUI_TeamBack }
};
btnarr_t blue_team[] = {
{"SCOUT", VGUI_JoinScout_B },
{"SNIPER", VGUI_JoinSniper_B },
{"SOLDIER", VGUI_JoinSoldier_B },
{"DEMOMAN", VGUI_JoinDemoman_B },
{"MEDIC", VGUI_JoinMedic_B },
{"HWGUY", VGUI_JoinHwguy_B },
{"PYRO", VGUI_JoinPyro_B },
{"SPY", VGUI_JoinSpy_B },
{"ENGINEER", VGUI_JoinEngineer_B },
{__NULL__, __NULL__ },
{"< Back", VGUI_TeamBack }
};
void
VGUI_GoSpectator(void)
{
VGUI_TeamJoin(0);
winChooseTeam.Hide();
}
void
VGUI_ChooseTeam_Red(void)
{
static int initialized;
static CUIButton *btns;
if (!initialized) {
vector btnpos = [16,0];
initialized = TRUE;
winCTTeam = spawn(CUIWindow);
winCTTeam.SetTitle("Choose Skin");
winCTTeam.SetSize([420,320]);
g_uiDesktop.Add(winCTTeam);
btns = memalloc(sizeof(btnarr_t) * red_team.length);
for (int i = 0; i < red_team.length; i++) {
btnpos[1] += 30;
if (red_team[i].ptr == __NULL__) {
continue;
}
btns[i] = spawn(CUIButton);
btns[i].SetTitle(red_team[i].str);
btns[i].SetPos(btnpos);
btns[i].SetFunc(red_team[i].ptr);
winCTTeam.Add(btns[i]);
}
}
winChooseTeam.Hide();
winCTTeam.Show();
winCTTeam.SetPos((video_res / 2) - (winCTTeam.GetSize() / 2));
}
void
VGUI_ChooseTeam_Blue(void)
{
static int initialized;
static CUIButton *btns;
if (!initialized) {
vector btnpos = [16,0];
initialized = TRUE;
winTTeam = spawn(CUIWindow);
winTTeam.SetTitle("Choose Skin");
winTTeam.SetSize([420,320]);
g_uiDesktop.Add(winTTeam);
btns = memalloc(sizeof(btnarr_t) * blue_team.length);
for (int i = 0; i < blue_team.length; i++) {
btnpos[1] += 30;
if (blue_team[i].ptr == __NULL__) {
continue;
}
btns[i] = spawn(CUIButton);
btns[i].SetTitle(blue_team[i].str);
btns[i].SetPos(btnpos);
btns[i].SetFunc(blue_team[i].ptr);
winTTeam.Add(btns[i]);
}
}
winChooseTeam.Hide();
winTTeam.Show();
winTTeam.SetPos((video_res / 2) - (winTTeam.GetSize() / 2));
}
void
VGUI_ChooseTeam(void)
{
static int initialized;
static CUIButton btnGoRed;
static CUIButton btnGoBlue;
static CUIButton btnGoSpectator;
if (!initialized) {
initialized = TRUE;
winChooseTeam = spawn(CUIWindow);
winChooseTeam.SetTitle("Choose Team");
winChooseTeam.SetSize('420 320');
btnGoRed = spawn(CUIButton);
btnGoRed.SetTitle("Red Team");
btnGoRed.SetPos('8 132');
btnGoRed.SetFunc(VGUI_ChooseTeam_Red);
btnGoBlue = spawn(CUIButton);
btnGoBlue.SetTitle("Blue Team");
btnGoBlue.SetPos('8 162');
btnGoBlue.SetFunc(VGUI_ChooseTeam_Blue);
btnGoSpectator = spawn(CUIButton);
btnGoSpectator.SetTitle("Spectator");
btnGoSpectator.SetPos('8 192');
btnGoSpectator.SetFunc(VGUI_GoSpectator);
g_uiDesktop.Add(winChooseTeam);
winChooseTeam.Add(btnGoRed);
winChooseTeam.Add(btnGoBlue);
winChooseTeam.Add(btnGoSpectator);
}
winChooseTeam.Show();
winChooseTeam.SetPos((video_res / 2) - (winChooseTeam.GetSize() / 2));
}

@ -0,0 +1,2 @@
#pragma sourcefile client/progs.src
#pragma sourcefile server/progs.src

@ -0,0 +1,4 @@
CC=fteqcc
all:
$(CC) progs.src

@ -0,0 +1,18 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#include "gamerules.h"
#include "../../../valve/src/server/items.h"

@ -0,0 +1,26 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
class TFCGameRules:CGameRules
{
virtual void(base_player) PlayerConnect;
virtual void(base_player) PlayerDisconnect;
virtual void(base_player) PlayerPostFrame;
virtual void(base_player) PlayerSpawn;
virtual void(base_player) PlayerKill;
virtual void(void) LevelNewParms;
};

@ -0,0 +1,177 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
var int autocvar_sv_playerkeepalive = TRUE;
/* we check what fields have changed over the course of the frame and network
* only the ones that have actually changed */
void
TFCGameRules::PlayerPostFrame(base_player pp)
{
player pl = (player)pp;
Animation_PlayerUpdate();
if (autocvar_sv_playerkeepalive)
pl.SendFlags |= PLAYER_KEEPALIVE;
if (pl.old_modelindex != pl.modelindex)
pl.SendFlags |= PLAYER_MODELINDEX;
if (pl.old_origin[0] != pl.origin[0])
pl.SendFlags |= PLAYER_ORIGIN;
if (pl.old_origin[1] != pl.origin[1])
pl.SendFlags |= PLAYER_ORIGIN;
if (pl.old_origin[2] != pl.origin[2])
pl.SendFlags |= PLAYER_ORIGIN_Z;
if (pl.old_angles[0] != pl.v_angle[0])
pl.SendFlags |= PLAYER_ANGLES_X;
if (pl.old_angles[1] != pl.angles[1])
pl.SendFlags |= PLAYER_ANGLES_Y;
if (pl.old_angles[2] != pl.angles[2])
pl.SendFlags |= PLAYER_ANGLES_Z;
if (pl.old_velocity[0] != pl.velocity[0])
pl.SendFlags |= PLAYER_VELOCITY;
if (pl.old_velocity[1] != pl.velocity[1])
pl.SendFlags |= PLAYER_VELOCITY;
if (pl.old_velocity[2] != pl.velocity[2])
pl.SendFlags |= PLAYER_VELOCITY_Z;
if (pl.old_flags != pl.flags)
pl.SendFlags |= PLAYER_FLAGS;
if (pl.old_gflags != pl.gflags)
pl.SendFlags |= PLAYER_FLAGS;
if (pl.old_activeweapon != pl.activeweapon)
pl.SendFlags |= PLAYER_WEAPON;
if (pl.old_items != pl.g_items)
pl.SendFlags |= PLAYER_ITEMS;
if (pl.old_health != pl.health)
pl.SendFlags |= PLAYER_HEALTH;
if (pl.old_armor != pl.armor)
pl.SendFlags |= PLAYER_ARMOR;
if (pl.old_movetype != pl.movetype)
pl.SendFlags |= PLAYER_MOVETYPE;
if (pl.old_viewofs != pl.view_ofs[2])
pl.SendFlags |= PLAYER_VIEWOFS;
if (pl.old_baseframe != pl.baseframe)
pl.SendFlags |= PLAYER_BASEFRAME;
if (pl.old_frame != pl.frame)
pl.SendFlags |= PLAYER_FRAME;
if (pl.old_a_ammo1 != pl.a_ammo1)
pl.SendFlags |= PLAYER_AMMO1;
if (pl.old_a_ammo2 != pl.a_ammo2)
pl.SendFlags |= PLAYER_AMMO2;
if (pl.old_a_ammo3 != pl.a_ammo3)
pl.SendFlags |= PLAYER_AMMO3;
pl.old_modelindex = pl.modelindex;
pl.old_origin = pl.origin;
pl.old_angles = pl.angles;
pl.old_angles[0] = pl.v_angle[0];
pl.old_velocity = pl.velocity;
pl.old_flags = pl.flags;
pl.old_gflags = pl.gflags;
pl.old_activeweapon = pl.activeweapon;
pl.old_items = pl.g_items;
pl.old_health = pl.health;
pl.old_armor = pl.armor;
pl.old_movetype = pl.movetype;
pl.old_viewofs = pl.view_ofs[2];
pl.old_baseframe = pl.baseframe;
pl.old_frame = pl.frame;
pl.old_a_ammo1 = pl.a_ammo1;
pl.old_a_ammo2 = pl.a_ammo2;
pl.old_a_ammo3 = pl.a_ammo3;
}
void
TFCGameRules::LevelNewParms(void)
{
parm1 = parm2 = parm3 = parm4 = parm5 = parm6 = parm7 =
parm8 = parm9 = parm10 = parm11 = parm12 = parm13 = parm14 =
parm15 = parm16 = parm17 = parm18 = parm19 = parm20 = parm21 =
parm22 = parm23 = parm24 = parm25 = parm26 = parm27 = parm28 =
parm29 = parm30 = 0;
parm64 = FL_CLIENT;
}
void
TFCGameRules::PlayerConnect(base_player pl)
{
if (Plugin_PlayerConnect(pl) == FALSE)
bprint(PRINT_HIGH, sprintf("%s connected\n", pl.netname));
}
void
TFCGameRules::PlayerDisconnect(base_player pl)
{
bprint(PRINT_HIGH, sprintf("%s disconnected\n", pl.netname));
/* Make this unusable */
pl.solid = SOLID_NOT;
pl.movetype = MOVETYPE_NONE;
pl.modelindex = 0;
pl.health = 0;
pl.takedamage = 0;
pl.SendFlags = PLAYER_MODELINDEX;
}
void
TFCGameRules::PlayerKill(base_player pp)
{
player pl = (player)pp;
Damage_Apply(pl, pl, pl.health, WEAPON_NONE, DMG_SKIP_ARMOR);
}
void
TFCGameRules::PlayerSpawn(base_player pp)
{
player pl = (player)pp;
pl.classname = "spectator";
pl.health = 0;
pl.armor = 0;
pl.takedamage = DAMAGE_NO;
pl.solid = SOLID_NOT;
pl.movetype = MOVETYPE_NOCLIP;
// pl.SendEntity = Player_SendEntity;
pl.flags = FL_CLIENT;
pl.weapon = 0;
pl.viewzoom = 1.0f;
pl.model = 0;
setsize (pl, [-16,-16,-16], [16,16,16]);
pl.view_ofs = pl.velocity = [0,0,0];
forceinfokey(pl, "*spec", "2");
Spawn_ObserverCam(pl);
}

@ -0,0 +1,52 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
class info_player_teamspawn:CBaseTrigger
{
void(void) info_player_teamspawn;
};
void
info_player_teamspawn::info_player_teamspawn(void)
{
int team = 1;
for (int i = 1; i < (tokenize(__fullspawndata) - 1); i += 2) {
switch (argv(i)) {
case "team_no":
team = stoi(argv(i+1));
break;
default:
break;
}
}
switch (team) {
case 1:
classname = "info_teamspawn_blue";
break;
case 2:
classname = "info_teamspawn_red";
break;
case 3:
classname = "info_teamspawn_yellow";
break;
case 4:
classname = "info_teamspawn_green";
break;
}
}
CLASSEXPORT(i_p_t, info_player_teamspawn)

@ -0,0 +1,81 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
class info_tfgoal:CBaseTrigger
{
string m_strName;
string m_strSound;
void(void) info_tfgoal;
virtual void(void) touch;
virtual void(void) Respawn;
};
void
info_tfgoal::touch(void)
{
if (other.classname != "player") {
return;
}
sound(this, CHAN_ITEM, m_strSound, 1.0f, ATTN_NORM);
Logging_Pickup(other, this, m_strName);
if (cvar("sv_playerslots") == 1) {
remove(self);
} else {
Hide();
think = Respawn;
nextthink = time + 30.0f;
}
}
void
info_tfgoal::Respawn(void)
{
solid = SOLID_TRIGGER;
movetype = MOVETYPE_NONE;
SetModel(m_oldModel);
setsize(this, VEC_HULL_MIN, VEC_HULL_MAX);
SetOrigin(m_oldOrigin);
}
void
info_tfgoal::info_tfgoal(void)
{
for (int i = 1; i < (tokenize(__fullspawndata) - 1); i += 2) {
switch (argv(i)) {
case "netname":
m_strSound = argv(i+1);
netname = __NULL__;
break;
case "noise":
m_strSound = argv(i+1);
break;
case "mdl":
model = argv(i+1);
break;
default:
break;
}
}
precache_sound(m_strSound);
CBaseEntity::CBaseEntity();
info_tfgoal::Respawn();
}
CLASSEXPORT(i_t_g, info_tfgoal)

@ -0,0 +1,53 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
void
Game_Input(void)
{
if (input_buttons & INPUT_BUTTON0) {
Weapons_Primary();
} else if (input_buttons & INPUT_BUTTON4) {
Weapons_Reload();
} else if (input_buttons & INPUT_BUTTON3) {
Weapons_Secondary();
} else {
Weapons_Release();
}
if (input_buttons & INPUT_BUTTON5) {
Player_UseDown();
} else {
Player_UseUp();
}
if (self.impulse == 100) {
Flashlight_Toggle();
}
if (cvar("sv_cheats") == 1) {
player pl = (player)self;
if (self.impulse == 102) {
// Respawn all the entities
for (entity a = world; (a = findfloat(a, ::identity, 1));) {
CBaseEntity caw = (CBaseEntity)a;
caw.Respawn();
}
bprint(PRINT_HIGH, "Respawning all map entities...\n");
}
}
self.impulse = 0;
}

@ -0,0 +1,71 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
class item_tfgoal:CBaseTrigger
{
string m_strSound;
void(void) item_tfgoal;
virtual void(void) touch;
virtual void(void) Respawn;
};
void
item_tfgoal::touch(void)
{
if (other.classname != "player") {
return;
}
if (cvar("sv_playerslots") == 1) {
remove(self);
} else {
Hide();
think = Respawn;
nextthink = time + 20.0f;
}
}
void
item_tfgoal::Respawn(void)
{
solid = SOLID_TRIGGER;
movetype = MOVETYPE_NONE;
SetModel(m_oldModel);
setsize(this, VEC_HULL_MIN, VEC_HULL_MAX);
SetOrigin(m_oldOrigin);
}
void
item_tfgoal::item_tfgoal(void)
{
for (int i = 1; i < (tokenize(__fullspawndata) - 1); i += 2) {
switch (argv(i)) {
case "noise":
m_strSound = argv(i+1);
break;
case "mdl":
model = argv(i+1);
break;
default:
break;
}
}
precache_sound(m_strSound);
CBaseEntity::CBaseEntity();
item_tfgoal::Respawn();
}

@ -0,0 +1,46 @@
#pragma target fte
#pragma progs_dat "../../progs.dat"
#define QWSSQC
#define SERVER
#define VALVE
#define TFC
#define GS_RENDERFX
#includelist
../../../src/shared/fteextensions.qc
../../../src/gs-entbase/server/defs.h
../../../src/shared/defs.h
../../../src/server/defs.h
../../../src/gs-entbase/server.src
../../../src/gs-entbase/shared.src
../shared/include.src
defs.h
../../../valve/src/server/player.qc
../../../valve/src/server/spectator.qc
../../../valve/src/server/items.qc
info_player_teamspawn.qc
info_tfgoal.qc
item_tfgoal.qc
gamerules.qc
../../../valve/src/server/client.qc
server.qc
../../../valve/src/server/damage.qc
../../../valve/src/server/rules.qc
../../../valve/src/server/flashlight.qc
../../../base/src/server/modelevent.qc
../../../src/botlib/include.src
input.qc
spawn.qc
../../../src/server/include.src
../../../src/shared/include.src
#endlist

@ -0,0 +1,39 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
void
Game_InitRules(void)
{
g_grMode = spawn(TFCGameRules);
}
void
Game_Worldspawn(void)
{
Sound_Precache("ammo.pickup");
Sound_Precache("ammo.respawn");
Sound_Precache("player.die");
Sound_Precache("player.fall");
Sound_Precache("player.lightfall");
precache_model("models/player.mdl");
precache_model("models/w_weaponbox.mdl");
Weapons_Init();
Player_Precache();
}
void weaponbox_spawn(player pl)
{
}

@ -0,0 +1,175 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
enum
{
CLASS_SCOUT = 1,
CLASS_SNIPER,
CLASS_SOLDIER,
CLASS_DEMO,
CLASS_MEDIC,
CLASS_HVYWEAPON,
CLASS_PYRO,
CLASS_SPY,
CLASS_ENGINEER
};
string g_teammodels[] = {
"",
"models/player/scout/scout2.mdl",
"models/player/sniper/sniper2.mdl",
"models/player/soldier/soldier2.mdl",
"models/player/demo/demo.mdl",
"models/player/medic/medic2.mdl",
"models/player/hvyweapon/hvyweapon2.mdl",
"models/player/pyro/pyro2.mdl",
"models/player/spy/spy2.mdl",
"models/player/engineer/engineer2.mdl"
};
void
CSEv_TeamJoin_f(float f)
{
if (self.classname != "player") {
spawnfunc_player();
}
player pl = (player)self;
entity spot = world;
pl.classname = "player";
pl.health = self.max_health = 100;
pl.takedamage = DAMAGE_YES;
pl.solid = SOLID_SLIDEBOX;
pl.movetype = MOVETYPE_WALK;
pl.flags = FL_CLIENT;
pl.viewzoom = 1.0;
/* mess, do it better */
if (f < 10) {
pl.team = 1; /* Blue */
} else if (f < 20) {
pl.team = 2; /* Red */
f -= 10;
} else if (f < 30) {
pl.team = 3; /* Yellow */
f -= 20;
} else if (f < 40) {
pl.team = 4; /* Green */
f -= 30;
}
pl.model = g_teammodels[f];
setmodel(pl, pl.model);
setsize(pl, VEC_HULL_MIN, VEC_HULL_MAX);
pl.view_ofs = VEC_PLAYER_VIEWPOS;
pl.velocity = [0,0,0];
pl.gravity = __NULL__;
pl.frame = 1;
// pl.SendEntity = Player_SendEntity;
pl.SendFlags = UPDATE_ALL;
pl.armor = pl.activeweapon = pl.g_items = 0;
pl.customphysics = Empty;
pl.iBleeds = TRUE;
forceinfokey(pl, "*spec", "0");
forceinfokey(self, "*deaths", ftos(self.deaths));
switch (pl.team) {
case 1:
spot = Spawn_SelectRandom("info_teamspawn_blue");
break;
case 2:
spot = Spawn_SelectRandom("info_teamspawn_red");
break;
case 3:
spot = Spawn_SelectRandom("info_teamspawn_yellow");
break;
case 4:
spot = Spawn_SelectRandom("info_teamspawn_green");
break;
}
setorigin(pl, spot.origin);
pl.angles = spot.angles;
pl.fixangle = TRUE;
switch (f) {
case CLASS_SCOUT:
Weapons_AddItem(pl, WEAPON_CROWBAR, -1);
Weapons_AddItem(pl, WEAPON_SBS, -1);
Weapons_AddItem(pl, WEAPON_NAILGUN, -1);
env_message_single(pl, "HELP_SCOUT");
break;
case CLASS_SNIPER:
Weapons_AddItem(pl, WEAPON_CROWBAR, -1);
Weapons_AddItem(pl, WEAPON_SNIPER, -1);
Weapons_AddItem(pl, WEAPON_AUTORIFLE, -1);
Weapons_AddItem(pl, WEAPON_NAILGUN, -1);
env_message_single(pl, "HELP_SNIPER");
break;
case CLASS_SOLDIER:
Weapons_AddItem(pl, WEAPON_CROWBAR, -1);
Weapons_AddItem(pl, WEAPON_SBS, -1);
Weapons_AddItem(pl, WEAPON_DBS, -1);
Weapons_AddItem(pl, WEAPON_RPG, -1);
env_message_single(pl, "HELP_SOLDIER");
break;
case CLASS_DEMO:
Weapons_AddItem(pl, WEAPON_CROWBAR, -1);
Weapons_AddItem(pl, WEAPON_SBS, -1);
Weapons_AddItem(pl, WEAPON_GLAUNCHER, -1);
Weapons_AddItem(pl, WEAPON_PIPEBOMB, -1);
env_message_single(pl, "HELP_DEMOMAN");
break;
case CLASS_MEDIC:
Weapons_AddItem(pl, WEAPON_MEDKIT, -1);
Weapons_AddItem(pl, WEAPON_SBS, -1);
Weapons_AddItem(pl, WEAPON_DBS, -1);
Weapons_AddItem(pl, WEAPON_SUPERNAIL, -1);
env_message_single(pl, "HELP_MEDIC");
break;
case CLASS_HVYWEAPON:
Weapons_AddItem(pl, WEAPON_CROWBAR, -1);
Weapons_AddItem(pl, WEAPON_SBS, -1);
Weapons_AddItem(pl, WEAPON_DBS, -1);
Weapons_AddItem(pl, WEAPON_ASSCAN, -1);
env_message_single(pl, "HELP_HWGUY");
break;
case CLASS_PYRO:
Weapons_AddItem(pl, WEAPON_CROWBAR, -1);
Weapons_AddItem(pl, WEAPON_SBS, -1);
Weapons_AddItem(pl, WEAPON_FLAMER, -1);
Weapons_AddItem(pl, WEAPON_INCENDIARY, -1);
env_message_single(pl, "HELP_PYRO");
break;
case CLASS_SPY:
Weapons_AddItem(pl, WEAPON_KNIFE, -1);
Weapons_AddItem(pl, WEAPON_TRANQUIL, -1);
Weapons_AddItem(pl, WEAPON_DBS, -1);
Weapons_AddItem(pl, WEAPON_NAILGUN, -1);
env_message_single(pl, "HELP_SPY");
break;
case CLASS_ENGINEER:
Weapons_AddItem(pl, WEAPON_WRENCH, -1);
Weapons_AddItem(pl, WEAPON_RAILGUN, -1);
Weapons_AddItem(pl, WEAPON_DBS, -1);
env_message_single(pl, "HELP_ENGINEER");
break;
}
pl.g_items |= ITEM_SUIT;
}

@ -0,0 +1,41 @@
#includelist
../../../valve/src/shared/flags.h
../../../valve/src/shared/player.qc
../../../valve/src/shared/weapon_common.h
../../../valve/src/shared/animations.h
../../../valve/src/shared/animations.qc
../../../valve/src/shared/pmove.qc
../../../valve/src/shared/pmove_water.qc
../../../valve/src/shared/fx_blood.qc
../../../valve/src/shared/fx_breakmodel.qc
../../../valve/src/shared/fx_explosion.qc
../../../valve/src/shared/fx_gibhuman.qc
../../../valve/src/shared/fx_spark.qc
../../../valve/src/shared/fx_impact.qc
items.h
weapons.h
w_asscan.qc
w_autorifle.qc
w_crowbar.qc
w_dbs.qc
w_flamer.qc
w_glauncher.qc
w_grapple.qc
w_incendiary.qc
w_knife.qc
w_medkit.qc
w_nailgun.qc
w_pipebomb.qc
w_railgun.qc
w_rpg.qc
w_sbs.qc
w_sniper.qc
w_supernail.qc
w_tranquil.qc
w_umbrella.qc
w_wrench.qc
weapons.qc
../../../valve/src/shared/weapon_common.qc
#endlist

@ -0,0 +1,50 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#define ITEM_CROWBAR 0x00000001
#define ITEM_MEDKIT 0x00000002
#define ITEM_KNIFE 0x00000004
#define ITEM_WRENCH 0x00000008
#define ITEM_UMBRELLA 0x00000010
#define ITEM_SBS 0x00000020
#define ITEM_SNIPER 0x00000040
#define ITEM_TRANQUIL 0x00000080
#define ITEM_RAILGUN 0x00000100
#define ITEM_AUTORIFLE 0x00000200
#define ITEM_DBS 0x00000400
#define ITEM_NAILGUN 0x00000800
#define ITEM_GLAUNCHER 0x00001000
#define ITEM_SUPERNAIL 0x00002000
#define ITEM_FLAMER 0x00004000
#define ITEM_RPG 0x00008000
#define ITEM_PIPEBOMB 0x00010000
#define ITEM_ASSCAN 0x00020000
#define ITEM_INCENDIARY 0x00040000
#define ITEM_GRAPPLE 0x00080000
#define ITEM_SUIT 0x00100000
#define ITEM_UNUSED22 0x00200000
#define ITEM_UNUSED23 0x00400000
#define ITEM_UNUSED24 0x00800000
#define ITEM_UNUSED25 0x01000000
#define ITEM_UNUSED26 0x02000000
#define ITEM_UNUSED27 0x04000000
#define ITEM_UNUSED28 0x08000000
#define ITEM_UNUSED29 0x10000000
#define ITEM_UNUSED30 0x20000000
#define ITEM_UNUSED31 0x40000000
#define ITEM_UNUSED32 0x80000000

@ -0,0 +1,112 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
void
w_asscan_precache(void)
{
precache_model("models/v_tfac.mdl");
precache_model("models/w_asscan.mdl");
precache_model("models/p_asscan.mdl");
}
void
w_asscan_updateammo(player pl)
{
Weapons_UpdateAmmo(pl, __NULL__, __NULL__, __NULL__);
}
string
w_asscan_wmodel(void)
{
return "models/w_asscan.mdl";
}
string
w_asscan_pmodel(void)
{
return "models/p_asscan.mdl";
}
string
w_asscan_deathmsg(void)
{
return "%s was assaulted by %s's Assault Cannon.";
}
void
w_asscan_draw(void)
{
Weapons_SetModel("models/v_tfac.mdl");
Weapons_ViewAnimation(0);
}
float
w_asscan_aimanim(void)
{
return self.flags & FL_CROUCHING ? ANIM_CR_AIMCROWBAR : ANIM_AIMCROWBAR;
}
void
w_asscan_hudpic(int selected, vector pos, float a)
{
#ifdef CLIENT
if (selected) {
drawsubpic(
pos,
[170,45],
"sprites/tfchud04.spr_0.tga",
[0,90/256],
[170/256,45/256],
g_hud_color,
a,
DRAWFLAG_ADDITIVE
);
} else {
drawsubpic(
pos,
[170,45],
"sprites/tfchud03.spr_0.tga",
[0,45/256],
[170/256,45/256],
g_hud_color,
a,
DRAWFLAG_ADDITIVE
);
}
#endif
}
weapon_t w_asscan =
{
.name = "asscan",
.id = ITEM_ASSCAN,
.slot = 4,
.slot_pos = 2,
.draw = w_asscan_draw,
.holster = __NULL__,
.primary = __NULL__,
.secondary = __NULL__,
.reload = __NULL__,
.release = __NULL__,
.crosshair = __NULL__,
.precache = w_asscan_precache,
.pickup = __NULL__,
.updateammo = w_asscan_updateammo,
.wmodel = w_asscan_wmodel,
.pmodel = w_asscan_pmodel,
.deathmsg = w_asscan_deathmsg,
.aimanim = w_asscan_aimanim,
.hudpic = w_asscan_hudpic
};

@ -0,0 +1,114 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
void
w_autorifle_precache(void)
{
precache_model("models/v_tfc_sniper.mdl");
precache_model("models/w_autorifle.mdl");
precache_model("models/p_autorifle.mdl");
}
void
w_autorifle_updateammo(player pl)
{
#ifdef SERVER
Weapons_UpdateAmmo(pl, __NULL__, __NULL__, __NULL__);
#endif
}
string
w_autorifle_wmodel(void)
{
return "models/w_autorifle.mdl";
}
string
w_autorifle_pmodel(void)
{
return "models/p_autorifle.mdl";
}
string
w_autorifle_deathmsg(void)
{
return "%s was assaulted by %s's Assault Cannon.";
}
void
w_autorifle_draw(void)
{
Weapons_SetModel("models/v_tfc_sniper.mdl");
Weapons_ViewAnimation(0);
}
float
w_autorifle_aimanim(void)
{
return self.flags & FL_CROUCHING ? ANIM_CR_AIMCROWBAR : ANIM_AIMCROWBAR;
}
void
w_autorifle_hudpic(int selected, vector pos, float a)
{
#ifdef CLIENT
if (selected) {
drawsubpic(
pos,
[170,45],
"sprites/tfchud02.spr_0.tga",
[0,0],
[170/256,45/256],
g_hud_color,
a,
DRAWFLAG_ADDITIVE
);
} else {
drawsubpic(
pos,
[170,45],
"sprites/tfchud01.spr_0.tga",
[0,0],
[170/256,45/256],
g_hud_color,
a,
DRAWFLAG_ADDITIVE
);
}
#endif
}
weapon_t w_autorifle =
{
.name = "autorifle",
.id = ITEM_AUTORIFLE,
.slot = 2,
.slot_pos = 0,
.draw = w_autorifle_draw,
.holster = __NULL__,
.primary = __NULL__,
.secondary = __NULL__,
.reload = __NULL__,
.release = __NULL__,
.crosshair = __NULL__,
.precache = w_autorifle_precache,
.pickup = __NULL__,
.updateammo = w_autorifle_updateammo,
.wmodel = w_autorifle_wmodel,
.pmodel = w_autorifle_pmodel,
.deathmsg = w_autorifle_deathmsg,
.aimanim = w_autorifle_aimanim,
.hudpic = w_autorifle_hudpic
};

@ -0,0 +1,232 @@
/*
* Copyright (c) 2016-2020 Marco Hladik <marco@icculus.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
enum
{
CBAR_IDLE,
CBAR_DRAW,
CBAR_HOLSTER,
CBAR_ATTACK1HIT,
CBAR_ATTACK1MISS,
CBAR_ATTACK2MISS,
CBAR_ATTACK2HIT,
CBAR_ATTACK3MISS,
CBAR_ATTACK3HIT
};
void
w_crowbar_precache(void)
{
precache_sound("weapons/cbar_miss1.wav");
precache_sound("weapons/cbar_hit1.wav");
precache_sound("weapons/cbar_hit2.wav");
precache_sound("weapons/cbar_hitbod1.wav");
precache_sound("weapons/cbar_hitbod2.wav");
precache_sound("weapons/cbar_hitbod3.wav");
precache_model("models/v_tfc_crowbar.mdl");
precache_model("models/w_crowbar.mdl");
precache_model("models/p_crowbar.mdl");
}
void
w_crowbar_updateammo(player pl)
{
#ifdef SERVER
Weapons_UpdateAmmo(pl, __NULL__, __NULL__, __NULL__);
#endif
}
string
w_crowbar_wmodel(void)
{
return "models/w_crowbar.mdl";
}
string
w_crowbar_pmodel(void)
{
return "models/p_crowbar.mdl";
}
string
w_crowbar_deathmsg(void)
{
return "%s was assaulted by %s's Crowbar.";
}
void
w_crowbar_draw(void)
{
Weapons_SetModel("models/v_tfc_crowbar.mdl");
Weapons_ViewAnimation(CBAR_DRAW);
}
void
w_crowbar_holster(void)
{
Weapons_ViewAnimation(CBAR_HOLSTER);
}
void
w_crowbar_primary(void)
{
int anim = 0;
vector src;
player pl = (player)self;
if (pl.w_attack_next) {
return;
}
Weapons_MakeVectors();
src = pl.origin + pl.view_ofs;
traceline(src, src + (v_forward * 32), FALSE, pl);
int r = (float)input_sequence % 3;
switch (r) {
case 0:
anim = trace_fraction >= 1 ? CBAR_ATTACK1MISS:CBAR_ATTACK1HIT;
break;
case 1:
anim = trace_fraction >= 1 ? CBAR_ATTACK2MISS:CBAR_ATTACK2HIT;
break;
default:
anim = trace_fraction >= 1 ? CBAR_ATTACK3MISS:CBAR_ATTACK3HIT;
}
Weapons_ViewAnimation(anim);
if (trace_fraction >= 1.0) {
pl.w_attack_next = 0.5f;
} else {
pl.w_attack_next = 0.25f;
}
pl.w_idle_next = 2.5f;
#ifdef SERVER
if (pl.flags & FL_CROUCHING) {
Animation_PlayerTopTemp(ANIM_SHOOTCROWBAR, 0.5f);
} else {
Animation_PlayerTopTemp(ANIM_CR_SHOOTCROWBAR, 0.42f);
}
sound(pl, CHAN_WEAPON, "weapons/cbar_miss1.wav", 1, ATTN_NORM);
if (trace_fraction >= 1.0) {
return;
}
/* don't bother with decals, we got squibs */
if (trace_ent.iBleeds) {
FX_Blood(trace_endpos, [1,0,0]);
} else {
FX_Impact(IMPACT_MELEE, trace_endpos, trace_plane_normal);
}
if (trace_ent.takedamage) {
Damage_Apply(trace_ent, self, 10, WEAPON_CROWBAR, DMG_BLUNT);
if (!trace_ent.iBleeds) {
return;
}
if (random() < 0.33) {
sound(pl, 8, "weapons/cbar_hitbod1.wav", 1, ATTN_NORM);
} else if (random() < 0.66) {
sound(pl, 8, "weapons/cbar_hitbod2.wav", 1, ATTN_NORM);
} else {
sound(pl, 8, "weapons/cbar_hitbod3.wav", 1, ATTN_NORM);
}
} else {
if (random() < 0.5) {
sound(pl, 8, "weapons/cbar_hit1.wav", 1, ATTN_NORM);
} else {
sound(pl, 8, "weapons/cbar_hit2.wav", 1, ATTN_NORM);
}
}
#endif
}
void
w_crowbar_release(void)
{
player pl = (player)self;
if (pl.w_idle_next) {
return;
}
Weapons_ViewAnimation(CBAR_IDLE);
pl.w_idle_next = 15.0f;
}
float
w_crowbar_aimanim(void)
{
return self.flags & FL_CROUCHING ? ANIM_CR_AIMCROWBAR : ANIM_AIMCROWBAR;
}
void
w_crowbar_hudpic(int selected, vector pos, float a)
{