Merging the Xylemon's changes to Scientist Hunt that got sent via a patch. Thanks Xylemon!

Also changed the way game-init works. Still gotta rename the Game_Worldspawn to reflect what it actually does now.
TODO: Add a Game_InitEnts alongside Game_Init?
This commit is contained in:
Marco Cawthorne 2019-03-06 14:11:23 +01:00
parent 18dfc74238
commit 5055d92c5b
26 changed files with 1578 additions and 101 deletions

View File

@ -4,6 +4,7 @@ qc-progs:
$(CC) menu-fn/progs.src
$(CC) client/valve.src
$(CC) server/valve.src
$(CC) client/scihunt.src
$(CC) server/scihunt.src
$(CC) client/cstrike.src
$(CC) server/cstrike.src

View File

@ -53,13 +53,13 @@ void CSQC_Init(float apilevel, string enginename, float engineversion)
SHADER_CULLED = shaderforname("mirror_cull");
/* Particles */
PARTICLE_SPARK = particleeffectnum("part_spark");
PARTICLE_SPARK = particleeffectnum("part_spark");
PARTICLE_PIECES_BLACK = particleeffectnum("part_pieces_black");
PARTICLE_SMOKE_GREY = particleeffectnum("part_smoke_grey");
PARTICLE_SMOKE_BROWN = particleeffectnum("part_smoke_brown");
PARTICLE_BLOOD = particleeffectnum("part_blood");
DECAL_SHOT = particleeffectnum("decal_shot");
DECAL_GLASS = particleeffectnum("decal_glass");
PARTICLE_BLOOD = particleeffectnum("part_blood");
DECAL_SHOT = particleeffectnum("decal_shot");
DECAL_GLASS = particleeffectnum("decal_glass");
/* 2D Pics */
precache_pic("gfx/vgui/icntlk_sv");

75
Source/client/scihunt.src Normal file
View File

@ -0,0 +1,75 @@
#pragma target fte
#pragma progs_dat "../../scihunt/csprogs.dat"
#define CSQC
#define VALVE
#includelist
../builtins.h
../defs.h
../math.h
../materials.h
../events.h
../entities.h
valve/defs.h
defs.h
vgui.h
util.c
scihunt/init.c
../gs-entbase/client.src
sound.c
text.c
voice.c
../shared/valve/animations.c
../shared/scihunt/player.cpp
player.c
../shared/pmove.c
predict.c
../shared/decals.c
../shared/effects.c
../shared/spraylogo.cpp
../shared/scihunt/items.h
../shared/valve/crosshair.h
../shared/scihunt/weapons.h
../shared/valve/w_crowbar.c
../shared/valve/w_glock.c
../shared/valve/w_python.c
../shared/valve/w_mp5.c
../shared/valve/w_crossbow.c
../shared/valve/w_shotgun.c
../shared/valve/w_rpg.c
../shared/valve/w_gauss.c
../shared/valve/w_egon.c
../shared/valve/w_hornetgun.c
../shared/valve/w_handgrenade.c
../shared/valve/w_tripmine.c
../shared/valve/w_satchel.c
../shared/valve/w_snark.c
../shared/scihunt/w_cannon.c
../shared/scihunt/w_chainsaw.c
../shared/scihunt/w_hammer.c
../shared/scihunt/weapons.c
valve/player.c
entities.c
valve/cmds.c
valve/game_event.c
events.c
valve/view.c
view.c
damage.c
chat.c
valve/hud.c
valve/hud_weaponselect.c
valve/scoreboard.c
valve/input.c
entry.c
#endlist

View File

@ -0,0 +1,27 @@
/***
*
* Copyright (c) 2016-2019 Marco 'eukara' Hladik. All rights reserved.
*
* See the file LICENSE attached with the sources for usage details.
*
****/
/*
=================
Client_Init
Comparable to worldspawn in SSQC in that it's mostly used for precaches
=================
*/
void Client_Init(float apilevel, string enginename, float engineversion)
{
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/chainsaw.spr");
precache_model("sprites/hammer.spr");
precache_model("sprites/w_cannon.spr");
}

View File

@ -55,9 +55,8 @@ void CModList::Draw(void)
}
if (m_selected == i) {
colo = ML_COL_2;
drawfill([g_menuofs[0] + m_x, g_menuofs[1] + pos
], [m_size[0], 29],
[84/255,45/255,0], 1.0f);
drawfill([g_menuofs[0] + m_x, g_menuofs[1] + pos], [m_size[0], 29],
[84/255,45/255,0], 1.0f);
} else {
colo = ML_COL_1;
}

View File

@ -35,5 +35,3 @@ entity eActivator;
string startspot;
string __fullspawndata;
hashtable hashMaterials;
int g_initialized;

View File

@ -78,15 +78,10 @@ void SV_ParseClientCommand(string cmd)
Game_ParseClientCommand(cmd);
}
void worldspawn(void)
void init(float prevprogs)
{
string sTemp;
if (g_initialized) {
return;
}
g_initialized = TRUE;
// Let's load materials.txt because someone thought this was the best idea
filestream fileMaterial = fopen("sound/materials.txt", FILE_READ);
hashMaterials = hash_createtab(512, HASH_ADD);
@ -104,10 +99,13 @@ void worldspawn(void)
}
PMove_Init();
}
void initents(void)
{
precache_sound("weapons/explode3.wav");
precache_sound("weapons/explode4.wav");
precache_sound("weapons/explode5.wav");
precache_sound("debris/glass1.wav");
precache_sound("debris/glass2.wav");
precache_sound("debris/glass3.wav");
@ -173,7 +171,12 @@ void worldspawn(void)
precache_sound("common/wpn_denyselect.wav");
precache_sound("player/sprayer.wav");
precache_sound("items/flashlight1.wav");
Game_Worldspawn();
Decals_Init();
}
void worldspawn(void)
{
lightstyle(0, "m");
lightstyle(1, "mmnmmommommnonmmonqnmmo");
lightstyle(2, "abcdefghijklmnopqrstuvwxyzyxwvutsrqponmlkjihgfedcba");
@ -186,9 +189,6 @@ void worldspawn(void)
lightstyle(9, "aaaaaaaazzzzzzzz");
lightstyle(10, "mmamammmmammamamaaamammma");
lightstyle(11, "abcdefghijklmnopqrrqponmlkjihgfedcba");
Game_Worldspawn();
Decals_Init();
}
float ConsoleCmd(string cmd)

View File

@ -22,13 +22,13 @@ scihunt/monster_scientist.cpp
../shared/effects.c
../shared/spraylogo.cpp
../shared/valve/player.cpp
../shared/scihunt/player.cpp
valve/player.c
../shared/pmove.c
valve/spectator.c
../shared/valve/items.h
../shared/scihunt/items.h
../shared/valve/crosshair.h
../shared/valve/weapons.h
../shared/scihunt/weapons.h
../shared/valve/w_crowbar.c
../shared/valve/w_glock.c
../shared/valve/w_python.c
@ -44,12 +44,15 @@ valve/spectator.c
../shared/valve/w_satchel.c
../shared/valve/w_snark.c
valve/items.cpp
../shared/valve/weapons.c
../shared/scihunt/w_cannon.c
../shared/scihunt/w_chainsaw.c
../shared/scihunt/w_hammer.c
../shared/scihunt/weapons.c
scihunt/shdata_parse.c
spawn.c
valve/client.c
scihunt/client.c
client.c
scihunt/server.c
@ -61,7 +64,7 @@ vox.c
footsteps.c
flashlight.c
valve/input.c
scihunt/input.c
valve/spawn.c
entry.c

View File

@ -0,0 +1,181 @@
/***
*
* Copyright (c) 2016-2019 Marco 'eukara' Hladik. All rights reserved.
*
* See the file LICENSE attached with the sources for usage details.
*
****/
void Empty(void) {}
void Game_ClientConnect(void)
{
bprint(PRINT_HIGH, sprintf("%s connected\n", self.netname));
}
void Game_ClientDisconnect(void)
{
bprint(PRINT_HIGH, sprintf("%s disconnected\n", self.netname));
}
void Game_ClientKill(void)
{
}
void Game_PlayerPreThink(void)
{
}
void Game_PlayerPostThink(void)
{
player pl = (player)self;
pl.w_attack_next -= input_timelength;
pl.w_idle_next -= input_timelength;
if (pl.w_attack_next <= 0) {
pl.w_attack_next = 0;
}
if (pl.w_idle_next <= 0) {
pl.w_idle_next = 0;
}
self.SendFlags = 1;
}
void Game_RunClientCommand(void)
{
Footsteps_Update();
QPhysics_Run(self);
}
void Game_DecodeChangeParms(void)
{
player pl = (player)self;
g_landmarkpos[0] = parm1;
g_landmarkpos[1] = parm2;
g_landmarkpos[2] = parm3;
pl.angles[0] = parm4;
pl.angles[1] = parm5;
pl.angles[2] = parm6;
pl.velocity[0] = parm7;
pl.velocity[1] = parm8;
pl.velocity[2] = parm9;
pl.items = parm10;
pl.activeweapon = parm11;
}
void Game_SetChangeParms(void)
{
player pl = (player)self;
parm1 = g_landmarkpos[0];
parm2 = g_landmarkpos[1];
parm3 = g_landmarkpos[2];
parm4 = pl.angles[0];
parm5 = pl.angles[1];
parm6 = pl.angles[2];
parm7 = pl.velocity[0];
parm8 = pl.velocity[1];
parm9 = pl.velocity[2];
parm10 = pl.items;
parm11 = pl.activeweapon;
}
void Game_PutClientInServer(void)
{
if (self.classname != "player") {
spawnfunc_player();
}
player pl = (player)self;
entity spot;
pl.classname = "player";
pl.health = self.max_health = 100;
//forceinfokey(self, "*dead", "0");
pl.takedamage = DAMAGE_YES;
pl.solid = SOLID_SLIDEBOX;
pl.movetype = MOVETYPE_WALK;
pl.flags = FL_CLIENT;
pl.viewzoom = 1.0;
setmodel(pl, "models/player.mdl");
setsize(pl, VEC_HULL_MIN, VEC_HULL_MAX);
pl.view_ofs = VEC_PLAYER_VIEWPOS;
pl.velocity = [0,0,0];
pl.frame = 1;
pl.SendEntity = Player_SendEntity;
pl.customphysics = Empty;
pl.vPain = Player_Pain;
pl.vDeath = Player_Death;
pl.iBleeds = TRUE;
forceinfokey(pl, "*spec", "0");
if (cvar("sv_playerslots") == 1) {
Game_DecodeChangeParms();
if (startspot) {
setorigin(pl, Landmark_GetSpot());
} else {
spot = find(world, classname, "info_player_start");
setorigin(pl, spot.origin);
pl.angles = spot.angles;
pl.fixangle = TRUE;
}
} else {
spot = Spawn_SelectRandom("info_player_deathmatch");
setorigin(pl, spot.origin);
pl.angles = spot.angles;
pl.fixangle = TRUE;
pl.ammo_9mm = 68;
pl.ammo_buckshot = 34;
Weapons_AddItem(pl, WEAPON_CROWBAR);
Weapons_AddItem(pl, WEAPON_GLOCK);
Weapons_AddItem(pl, WEAPON_CANNON);
Weapons_AddItem(pl, WEAPON_CHAINSAW);
}
}
void SV_SendChat(entity eSender, string sMessage, entity eEnt, float fType)
{
WriteByte(MSG_MULTICAST, SVC_CGAMEPACKET);
WriteByte(MSG_MULTICAST, fType == 0 ? EV_CHAT:EV_CHAT_TEAM);
WriteByte(MSG_MULTICAST, num_for_edict(eSender) - 1);
WriteByte(MSG_MULTICAST, eSender.team);
WriteString(MSG_MULTICAST, sMessage);
if (eEnt) {
msg_entity = eEnt;
multicast([0,0,0], MULTICAST_ONE);
} else {
multicast([0,0,0], MULTICAST_ALL);
}
}
void Game_ParseClientCommand(string cmd)
{
tokenize(cmd);
/*if (argv(1) == "timeleft") {
float fTimeLeft = cvar("mp_timelimit") - (time / 60);
Vox_Singlecast(self, sprintf("we have %s minutes remaining", Vox_TimeToString(fTimeLeft)));
return;
}*/
string chat = substring(cmd, 4, strlen(cmd) - 4);
// Players talk to players, spectators to spectators.
if (argv(0) == "say") {
localcmd(sprintf("echo %s: %s\n", self.netname, chat));
SV_SendChat(self, chat, world, 0);
return;
} else if (argv(0) == "say_team") {
localcmd(sprintf("echo [TEAM %d] %s: %s\n", self.team, self.netname, chat));
for (entity eFind = world; (eFind = find(eFind, classname, "player"));) {
if (eFind.team == self.team) {
SV_SendChat(self, chat, eFind, 1);
}
}
return;
}
clientcommand(self, cmd);
}
void Game_SetNewParms(void)
{
}

View File

@ -0,0 +1,72 @@
/***
*
* Copyright (c) 2016-2019 Marco 'eukara' Hladik. All rights reserved.
*
* See the file LICENSE attached with the sources for usage details.
*
****/
/*
=================
Input_Handle
Handles impulse and whatnot
=================
*/
void Game_Input(void)
{
if (self.button0) {
Weapons_Primary();
} else if (self.button4) {
Weapons_Reload();
} else if (self.button3) {
Weapons_Secondary();
} else {
Weapons_Release();
}
if (self.button5) {
Player_UseDown();
} else {
Player_UseUp();
}
if (self.impulse == 100) {
Flashlight_Toggle();
}
if (cvar("sv_cheats") == 1) {
player pl = (player)self;
if (self.impulse == 101) {
Weapons_AddItem(pl, WEAPON_CROWBAR);
Weapons_AddItem(pl, WEAPON_GLOCK);
Weapons_AddItem(pl, WEAPON_PYTHON);
Weapons_AddItem(pl, WEAPON_MP5);
Weapons_AddItem(pl, WEAPON_SHOTGUN);
Weapons_AddItem(pl, WEAPON_CROSSBOW);
Weapons_AddItem(pl, WEAPON_RPG);
Weapons_AddItem(pl, WEAPON_GAUSS);
Weapons_AddItem(pl, WEAPON_EGON);
Weapons_AddItem(pl, WEAPON_HORNETGUN);
Weapons_AddItem(pl, WEAPON_HANDGRENADE);
Weapons_AddItem(pl, WEAPON_SATCHEL);
Weapons_AddItem(pl, WEAPON_TRIPMINE);
Weapons_AddItem(pl, WEAPON_SNARK);
Weapons_AddItem(pl, WEAPON_CANNON);
Weapons_AddItem(pl, WEAPON_CHAINSAW);
Weapons_AddItem(pl, WEAPON_HAMMER);
Weapons_AddItem(pl, AMMO_BUCKSHOT);
}
if (self.impulse == 102) {
// Respawn all the entities
for (entity a = world; (a = findfloat(a, gflags, GF_CANRESPAWN));) {
CBaseEntity caw = (CBaseEntity)a;
caw.Respawn();
}
bprint(PRINT_HIGH, "Respawning all map entities...\n");
}
}
self.impulse = 0;
}

View File

@ -65,6 +65,106 @@ string sci_snddie[] = {
"scientist/sci_die4.wav"
};
string sci_sndchitchat[] = {
"scientist/absolutely.wav",
"scientist/absolutelynot.wav",
"scientist/administrator.wav",
"scientist/alienappeal.wav",
"scientist/alientrick.wav",
"scientist/allnominal.wav",
"scientist/areyouthink.wav",
"scientist/asexpected.wav",
"scientist/beverage.wav",
"scientist/bloodsample.wav",
"scientist/cantbeserious.wav",
"scientist/chaostheory.wav",
"scientist/completelywrong.wav",
"scientist/containfail.wav",
"scientist/correcttheory.wav",
"scientist/dine.wav",
"scientist/dontknow.wav",
"scientist/donuteater.wav",
"scientist/doyousmell.wav",
"scientist/evergetout.wav",
"scientist/everseen.wav",
"scientist/fascinating.wav",
"scientist/goodpaper.wav",
"scientist/headcrab.wav",
"scientist/hideglasses.wav",
"scientist/hopenominal.wav",
"scientist/howinteresting.wav",
"scientist/hungryyet.wav",
"scientist/ibelieveso.wav",
"scientist/idontthinkso.wav",
"scientist/importantspecies.wav",
"scientist/improbable.wav",
"scientist/imsure.wav",
"scientist/inconclusive.wav",
"scientist/ipredictedthis.wav",
"scientist/justasked.wav",
"scientist/lambdalab.wav",
"scientist/limitsok.wav",
"scientist/lowervoice.wav",
"scientist/luckwillchange.wav",
"scientist/needsleep.wav",
"scientist/neverseen.wav",
"scientist/nodoubt.wav",
"scientist/nogrant.wav",
"scientist/noguess.wav",
"scientist/noidea.wav",
"scientist/noo.wav",
"scientist/notcertain.wav",
"scientist/nothostile.wav",
"scientist/notsure.wav",
"scientist/ofcourse.wav",
"scientist/ofcoursenot.wav",
"scientist/organicmatter.wav",
"scientist/perculiarmarks.wav",
"scientist/perculiarodor.wav",
"scientist/perhaps.wav",
"scientist/positively.wav",
"scientist/repeat.wav",
"scientist/reportflux.wav",
"scientist/rescueus.wav",
"scientist/ridiculous.wav",
"scientist/right.wav",
"scientist/rightway.wav",
"scientist/rumorclean.wav",
"scientist/runtest.wav",
"scientist/seencup.wav",
"scientist/shakeunification.wav",
"scientist/shutdownchart.wav",
"scientist/shutup.wav",
"scientist/simulation.wav",
"scientist/smellburning.wav",
"scientist/softethics.wav",
"scientist/stimulating.wav",
"scientist/stopasking.wav",
"scientist/thatsodd.wav",
"scientist/theoretically.wav",
"scientist/uselessphd.wav",
"scientist/waithere.wav",
"scientist/whatnext.wav",
"scientist/whocansay.wav",
"scientist/whoresponsible.wav",
"scientist/whyaskme.wav",
"scientist/yees.wav"
};
string sci_sndhear[] = {
"scientist/hearsomething.wav",
"scientist/startle1.wav",
"scientist/startle2.wav",
"scientist/startle3.wav",
"scientist/startle4.wav",
"scientist/startle5.wav",
"scientist/startle6.wav",
"scientist/startle7.wav",
"scientist/startle8.wav",
"scientist/startle9.wav",
"scientist/whatissound.wav"
};
string sci_sndpain[] = {
"scientist/sci_pain1.wav",
"scientist/sci_pain2.wav",
@ -78,6 +178,22 @@ string sci_sndpain[] = {
"scientist/sci_pain10.wav"
};
string sci_sndsee[] = {
"scientist/afellowsci.wav",
"scientist/ahfreeman.wav",
"scientist/freeman.wav",
"scientist/freemanalive.wav",
"scientist/goodtoseeyou.wav",
"scientist/greetings.wav",
"scientist/greetings2.wav",
"scientist/hello.wav",
"scientist/hellofreeman.wav",
"scientist/hellofromlab.wav",
"scientist/hellothere.wav",
"scientist/inmesstoo.wav",
"scientist/newhevsuit.wav"
};
string sci_sndscream[] = {
"scientist/scream1.wav",
"scientist/scream2.wav",
@ -112,6 +228,37 @@ string sci_sndscream[] = {
"scientist/scream25.wav"
};
string sci_sndstop[] = {
"scientist/stop1.wav",
"scientist/stop2.wav",
"scientist/stop3.wav",
"scientist/stop4.wav",
"scientist/sorryimleaving.wav"
};
string sci_snduse[] = {
"scientist/alright.wav",
"scientist/excellentteam.wav",
"scientist/fellowscientist.wav",
"scientist/fine.wav",
"scientist/hopeyouknow.wav",
"scientist/leadtheway.wav",
"scientist/letsgo.wav",
"scientist/yes3.wav",
"scientist/yesletsgo.wav"
};
string sci_snduseno[] = {
"scientist/beenaburden.wav",
"scientist/illwait.wav",
"scientist/illwaithere.wav",
"scientist/istay.wav",
"scientist/reconsider.wav",
"scientist/slowingyou.wav",
"scientist/whyleavehere.wav"
};
class monster_scientist:CBaseEntity
{
vector m_vecLastUserPos;
@ -154,6 +301,8 @@ void monster_scientist::WarnOthers(void)
if ( vlen( b.origin - origin ) < 512 ) {
monster_scientist sci = (monster_scientist)b;
sci.m_iFear = TRUE;
sci.m_eUser = world;
sci.m_eRescuer = world;
}
}
}
@ -274,15 +423,24 @@ void monster_scientist::touch(void)
void monster_scientist::PlayerUse(void)
{
if (m_iFear) {
return;
}
if ((m_eUser == world)) {
if (m_iUsed == FALSE) {
m_iUsed = TRUE;
}
int rand = floor(random(0,sci_snduse.length));
sound(this, CHAN_VOICE, sci_snduse[rand], 1.0, ATTN_NORM);
m_eUser = eActivator;
m_eRescuer = m_eUser;
m_vecLastUserPos = m_eUser.origin;
} else {
int rand = floor(random(0,sci_snduseno.length));
sound(this, CHAN_VOICE, sci_snduseno[rand], 1.0, ATTN_NORM);
m_eUser = world;
}
}
@ -346,7 +504,7 @@ void monster_scientist::Respawn(void)
frame = SCIA_IDLE1;
health = 50;
velocity = [0,0,0];
m_iUsed = m_iScared = FALSE;
m_iUsed = m_iScared = m_iFear = FALSE;
}
void monster_scientist::monster_scientist(void)
@ -360,6 +518,12 @@ void monster_scientist::monster_scientist(void)
for (int i = 0; i < sci_sndscream.length; i++) {
precache_sound(sci_sndscream[i]);
}
for (int i = 0; i < sci_snduse.length; i++) {
precache_sound(sci_snduse[i]);
}
for (int i = 0; i < sci_snduseno.length; i++) {
precache_sound(sci_snduseno[i]);
}
precache_model("models/scientist.mdl");
model = "models/scientist.mdl";

View File

@ -8,73 +8,7 @@
int iTotalPenetrations;
/*
=================
TraceAttack_FireSingle
Fires a single shot that can penetrate some materials
=================
*/
void TraceAttack_FireSingle(vector vPos, vector vAngle, int iDamage)
{
/*static void TraceAttack_Penetrate(vector vPos, vector vAngle ) {
if (iTotalPenetrations > 0) {
return;
}
TraceAttack_FireSingle(vPos, vAngle, iDamage);
iTotalPenetrations = 1;
}*/
#ifdef CSTRIKE
traceline(vPos, vPos + (vAngle * wptTable[self.weapon].fRange), MOVE_HITMODEL, self);
#else
traceline(vPos, vPos + (vAngle * 8196), MOVE_HITMODEL, self);
#endif
if (trace_fraction != 1.0) {
if (trace_ent.takedamage == DAMAGE_YES) {
#ifdef CSTRIKE
Damage_Apply(trace_ent, self, iDamage, trace_endpos, FALSE);
#endif
}
if (trace_ent.iBleeds == TRUE) {
Effect_CreateBlood(trace_endpos, [0,0,0]);
} else {
string sTexture = getsurfacetexture(trace_ent, getsurfacenearpoint(trace_ent, trace_endpos));
switch((float)hash_get(hashMaterials, sTexture)) {
case 'G':
case 'V':
Effect_Impact(IMPACT_METAL, trace_endpos, trace_plane_normal);
break;
case 'M':
case 'P':
Effect_Impact(IMPACT_METAL, trace_endpos, trace_plane_normal);
break;
case 'D':
case 'W':
Effect_Impact(IMPACT_WOOD, trace_endpos, trace_plane_normal);
break;
case 'Y':
Effect_Impact(IMPACT_GLASS, trace_endpos, trace_plane_normal);
break;
case 'N':
Effect_Impact(IMPACT_DEFAULT, trace_endpos, trace_plane_normal);
break;
case 'T':
default:
Effect_Impact(IMPACT_DEFAULT, trace_endpos, trace_plane_normal);
break;
}
//TraceAttack_Penetrate(trace_endpos + (v_forward * 2), vAngle);
}
}
}
void TraceAttack_FireSingleLagged(vector vPos, vector vAngle, int iDamage)
{
/*static void TraceAttack_Penetrate(vector vPos, vector vAngle ) {
if (iTotalPenetrations > 0) {
@ -95,12 +29,15 @@ void TraceAttack_FireSingleLagged(vector vPos, vector vAngle, int iDamage)
if (trace_ent.takedamage == DAMAGE_YES) {
Damage_Apply(trace_ent, self, iDamage, trace_endpos, FALSE);
/*if (trace_ent.health <= 0 && trace_ent.iBleeds == TRUE) {
makevectors(self.v_angle);
trace_ent.movetype = MOVETYPE_BOUNCE;
trace_ent.velocity = (v_forward * (150 * iDamage)) + [0,0,100 * iDamage];
}*/
}
if (trace_ent.iBleeds == TRUE) {
//Effect_CreateBlood(trace_endpos, [0,0,0]);
} else {
if (trace_ent.iBleeds != TRUE) {
string sTexture = getsurfacetexture(trace_ent, getsurfacenearpoint(trace_ent, trace_endpos));
switch ((float)hash_get(hashMaterials, sTexture)) {
@ -148,11 +85,8 @@ void TraceAttack_FireBullets(int iShots, vector vPos, int iDamage, vector vecAcc
while (iShots > 0) {
iTotalPenetrations = 0;
vDir = aim(self, 100000) + Math_CRandom()*vecAccuracy[0]*v_right + Math_CRandom()*vecAccuracy[1]*v_up;
//TraceAttack_FireSingle(vPos, vDir, iDamage);
TraceAttack_FireSingleLagged(vPos, vDir, iDamage);
TraceAttack_FireSingle(vPos, vDir, iDamage);
iShots--;
}
}

View File

@ -57,7 +57,7 @@ void itemweapon::Respawn(void)
think = __NULL__;
nextthink = -1;
sound(this, CHAN_ITEM, "items/suitchargeok1.wav", 1, ATTN_NORM);
sound(this, CHAN_ITEM, "items/suitchargeok1.wav", 1, ATTN_NORM, 150);
}
void itemweapon::itemweapon(void)

View File

@ -0,0 +1,43 @@
/***
*
* Copyright (c) 2016-2019 Marco 'eukara' Hladik. All rights reserved.
*
* See the file LICENSE attached with the sources for usage details.
*
****/
#define ITEM_CROWBAR 0x00000001
#define ITEM_GLOCK 0x00000002
#define ITEM_PYTHON 0x00000004
#define ITEM_MP5 0x00000008
#define ITEM_CROSSBOW 0x00000010
#define ITEM_SHOTGUN 0x00000020
#define ITEM_RPG 0x00000040
#define ITEM_GAUSS 0x00000080
#define ITEM_EGON 0x00000100
#define ITEM_HORNETGUN 0x00000200
#define ITEM_HANDGRENADE 0x00000400
#define ITEM_TRIPMINE 0x00000800
#define ITEM_SATCHEL 0x00001000
#define ITEM_SNARK 0x00002000
#define ITEM_SUIT 0x00004000
#define ITEM_LONGJUMP 0x00008000
#define ITEM_HEALTHKIT 0x00010000
#define ITEM_BATTERY 0x00020000
#define ITEM_CANNON 0x00040000
#define ITEM_CHAINSAW 0x00080000
#define ITEM_HAMMER 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

View File

@ -0,0 +1,55 @@
class player
{
float health;
float armor;
float w_attack_next; /* When the weapon is done firing */
float w_idle_next; /* When to play the next idle animation */
int a_ammo1; // Magazine/Clip
int a_ammo2; // Rest in the inventory
int a_ammo3; // Special ammo
float items;
float activeweapon;
float viewzoom;
vector view_ofs;
/* Weapon specific */
int cannon_mag;
int glock_mag;
#ifdef CSQC
/* External model */
entity p_model;
int p_hand_bone;
int p_model_bone;
float pitch;
float lastweapon;
/* Prediction */
vector netorigin;
vector netvelocity;
float netflags;
float net_w_attack_next; /* When the weapon is done firing */
float net_w_idle_next; /* When to play the next idle animation */
virtual void() gun_offset;
virtual void() draw;
virtual float() predraw;
#else
int ammo_9mm;
int ammo_357;
int ammo_buckshot;
int ammo_m203_grenade;
int ammo_bolt;
int ammo_rocket;
int ammo_uranium;
int ammo_handgrenade;
int ammo_satchel;
int ammo_tripmine;
int ammo_snark;
int ammo_hornet;
#endif
};

View File

@ -0,0 +1,226 @@
/***
*
* Copyright (c) 2016-2019 Marco 'eukara' Hladik. All rights reserved.
*
* See the file LICENSE attached with the sources for usage details.
*
****/
enum
{
CANNON_FIREBOTH,
CANNON_FIRELEFT,
CANNON_FIRERIGHT,
CANNON_RELOAD,
CANNON_DEPLOY,
CANNON_PUTAWAY,
CANNON_IDLE1,
CANNON_IDLE2
};
void w_cannon_precache(void)
{
precache_model("models/v_cannon.mdl");
precache_model("models/p_cannon.mdl");
precache_sound("cannon/cin.wav");
precache_sound("cannon/close.wav");
precache_sound("cannon/cout.wav");
precache_sound("cannon/fire.wav");
precache_sound("cannon/open.wav");
}
string w_cannon_vmodel(void)
{
return "models/v_cannon.mdl";
}
string w_cannon_pmodel(void)
{
return "models/p_cannon.mdl";
}
string w_cannon_deathmsg(void)
{
return "%s killed %s with handcannon.";
}
void w_cannon_reload(void)
{
player pl = (player)self;
if (pl.w_attack_next > 0) {
return;
}
#ifdef CSQC
if (pl.a_ammo1 >= 2) {
return;
}
if (!pl.a_ammo2) {
return;
}
Weapons_ViewAnimation(CANNON_RELOAD);
#else
if (pl.cannon_mag >= 2) {
return;
}
if (!pl.ammo_buckshot) {
return;
}
Weapons_ReloadWeapon(pl, player::cannon_mag, player::ammo_buckshot, 2);
Weapons_UpdateAmmo(pl, pl.cannon_mag, pl.ammo_buckshot, __NULL__);
#endif
pl.w_attack_next = 3.0f;
pl.w_idle_next = 3.0f;
}
void w_cannon_pickup(void)
{
#ifdef SSQC
player pl = (player)self;
pl.cannon_mag = bound(0, pl.cannon_mag + 2, 2);
#endif
}
void w_cannon_draw(void)
{
#ifdef SSQC
player pl = (player)self;
Weapons_ViewAnimation(CANNON_DEPLOY);
Weapons_UpdateAmmo(pl, pl.cannon_mag, pl.ammo_buckshot, __NULL__);
#endif
}
void w_cannon_holster(void)
{
#ifdef SSQC
Weapons_ViewAnimation(CANNON_PUTAWAY);
#endif
}
void w_cannon_primary(void)
{
player pl = (player)self;
if (pl.w_attack_next > 0.0) {
return;
}
#ifdef CSQC
if (pl.a_ammo1 != 2) {
w_cannon_reload();
return;
}
Weapons_ViewAnimation(CANNON_FIREBOTH);
Weapons_ViewPunchAngle([-5,0,0]);
#else
if (pl.cannon_mag != 2) {
w_cannon_reload();
return;
}
TraceAttack_FireBullets(20, pl.origin + pl.view_ofs, 5, [0.08716,0.04362]);
pl.cannon_mag -= 2;
Weapons_PlaySound(pl, CHAN_WEAPON, "cannon/fire.wav", 1, ATTN_NORM);
Weapons_UpdateAmmo(pl, pl.cannon_mag, pl.ammo_buckshot, __NULL__);
#endif
pl.w_attack_next = 1.5f;
pl.w_idle_next = 2.5f;
}
void w_cannon_secondary(void)
{
player pl = (player)self;
if (pl.w_attack_next > 0.0) {
return;
}
#ifdef CSQC
if (!pl.a_ammo1) {
w_cannon_reload();
return;
}
if (pl.a_ammo1 == 2) {
Weapons_ViewAnimation(CANNON_FIRELEFT);
} else {
Weapons_ViewAnimation(CANNON_FIRERIGHT);
}
Weapons_ViewPunchAngle([-5,0,0]);
#else
if (!pl.cannon_mag) {
w_cannon_reload();
return;
}
TraceAttack_FireBullets(10, pl.origin + pl.view_ofs, 5, [0.08716,0.04362]);
pl.cannon_mag--;
Weapons_PlaySound(pl, CHAN_WEAPON, "cannon/fire.wav", 1, ATTN_NORM);
Weapons_UpdateAmmo(pl, pl.cannon_mag, pl.ammo_buckshot, __NULL__);
#endif
pl.w_attack_next = 1.5f;
pl.w_idle_next = 2.5f;
}
void w_cannon_release(void)
{
player pl = (player)self;
if (pl.w_idle_next > 0.0) {
return;
}
int r = floor(random(0,2));
switch (r) {
case 0:
Weapons_ViewAnimation(CANNON_IDLE1);
break;
case 1:
Weapons_ViewAnimation(CANNON_IDLE2);
break;
}
pl.w_idle_next = 8.0f;
}
void w_cannon_crosshair(void)
{
#ifdef CSQC
static vector cross_pos;
cross_pos = (video_res / 2) + [-12,-12];
drawsubpic(cross_pos, [24,24], "sprites/crosshairs.spr_0.tga", [48/128,24/128], [0.1875, 0.1875], [1,1,1], 1, DRAWFLAG_NORMAL);
HUD_DrawAmmo1();
HUD_DrawAmmo2();
#endif
}
void w_cannon_hudpic(int s, vector pos)
{
#ifdef CSQC
if (s) {
drawsubpic(pos, [170,45], "sprites/w_cannon.spr_0.tga", [0,48/256], [170/256,45/256], g_hud_color, 1, DRAWFLAG_ADDITIVE);
} else {
drawsubpic(pos, [170,45], "sprites/w_cannon.spr_0.tga", [0,0], [170/256,45/256], g_hud_color, 1, DRAWFLAG_ADDITIVE);
}
#endif
}
weapon_t w_cannon =
{
ITEM_CANNON,
2,
3,
w_cannon_draw,
w_cannon_holster,
w_cannon_primary,
w_cannon_secondary,
w_cannon_reload,
w_cannon_release,
w_cannon_crosshair,
w_cannon_precache,
w_cannon_pickup,
w_cannon_vmodel,
__NULL__,
w_cannon_pmodel,
w_cannon_deathmsg,
w_cannon_hudpic
};

View File

@ -0,0 +1,166 @@
/***
*
* Copyright (c) 2016-2019 Marco 'eukara' Hladik. All rights reserved.
*
* See the file LICENSE attached with the sources for usage details.
*
****/
enum
{
CHAINSAW_STARTFIRE,
CHAINSAW_CONTINUEFIRE,
CHAINSAW_STOPFIRE,
CHAINSAW_DEPLOY,
CHAINSAW_HOLSTER,
CHAINSAW_IDLE1,
CHAINSAW_IDLE2,
};
void w_chainsaw_precache(void)
{
precache_sound("sh/chainsaw_cutinto.wav");
precache_sound("sh/chainsaw_cutintoflesh.wav");
precache_sound("sh/chainsaw_idle.wav");
precache_sound("sh/chainsaw_idle2.wav");
precache_sound("sh/chainsaw_pullout.wav");
precache_sound("sh/chainsaw_startup.wav");
precache_model("models/v_chainsaw.mdl");
precache_model("models/p_saw.mdl");
}
string w_chainsaw_vmodel(void)
{
return "models/v_chainsaw.mdl";
}
string w_chainsaw_pmodel(void)
{
return "models/p_saw.mdl";
}
string w_chainsaw_deathmsg(void)
{
return "%s killed %s with chainsaw.";
}
void w_chainsaw_draw(void)
{
#ifdef CSQC
Weapons_ViewAnimation(CHAINSAW_DEPLOY);
#else
player pl = (player)self;
Weapons_UpdateAmmo(pl, __NULL__, __NULL__, __NULL__);
#endif
}
void w_chainsaw_holster(void)
{
#ifdef CSQC
Weapons_ViewAnimation(CHAINSAW_HOLSTER);
#endif
}
void w_chainsaw_primary(void)
{
player pl = (player)self;
if (pl.w_attack_next) {
return;
}
#ifdef CSQC
if (pSeat->eViewModel.frame == CHAINSAW_STARTFIRE || pSeat->eViewModel.frame == CHAINSAW_CONTINUEFIRE) {
Weapons_ViewAnimation(CHAINSAW_CONTINUEFIRE);
} else {
Weapons_ViewAnimation(CHAINSAW_STARTFIRE);
}
#else
Weapons_MakeVectors();
vector src = pl.origin + pl.view_ofs;
traceline(src, src + (v_forward * 32), FALSE, pl);
if (trace_fraction >= 1.0) {
Weapons_PlaySound(pl, CHAN_WEAPON, "sh/chainsaw_idle2.wav", 1, ATTN_NORM);
pl.w_attack_next = 0.16f;
} else {
Effect_Impact(IMPACT_MELEE, trace_endpos, trace_plane_normal);
if (trace_ent.takedamage) {
Damage_Apply(trace_ent, self, 10, trace_endpos, FALSE );
Weapons_PlaySound(pl, CHAN_WEAPON, "sh/chainsaw_cutintoflesh.wav", 1, ATTN_NORM);
} else {
Effect_CreateSpark(trace_endpos, trace_plane_normal);
Weapons_PlaySound(pl, CHAN_WEAPON, "sh/chainsaw_cutinto.wav", 1, ATTN_NORM);
}
pl.w_attack_next = 0.1f;
}
#endif
pl.w_idle_next = 0.2f;
}
void w_chainsaw_secondary(void)
{
}
void w_chainsaw_reload(void)
{
}
void w_chainsaw_release(void)
{
#ifdef CSQC
player pl = (player)self;
if (pl.w_idle_next) {
return;
}
if (pSeat->eViewModel.frame == CHAINSAW_CONTINUEFIRE) {
Weapons_ViewAnimation(CHAINSAW_STOPFIRE);
pl.w_idle_next = 1.0f;
} else {
pl.w_idle_next = 10.0f;
}
int r = floor(random(0,2));
switch (r) {
case 0:
Weapons_ViewAnimation(CHAINSAW_IDLE1);
break;
case 1:
Weapons_ViewAnimation(CHAINSAW_IDLE2);
break;
}
#endif
}
void w_chainsaw_hudpic(int s, vector pos)
{
#ifdef CSQC
if (s) {
drawsubpic(pos, [170,45], "sprites/chainsaw.spr_0.tga", [0,48/256], [170/256,45/256], g_hud_color, 1, DRAWFLAG_ADDITIVE);
} else {
drawsubpic(pos, [170,45], "sprites/chainsaw.spr_0.tga", [0,0], [170/256,45/256], g_hud_color, 1, DRAWFLAG_ADDITIVE);
}
#endif
}
weapon_t w_chainsaw =
{
ITEM_CHAINSAW,
0,
2,
w_chainsaw_draw,
w_chainsaw_holster,
w_chainsaw_primary,
w_chainsaw_secondary,
w_chainsaw_reload,
w_chainsaw_release,
__NULL__,
w_chainsaw_precache,
__NULL__,
w_chainsaw_vmodel,
__NULL__,
w_chainsaw_pmodel,
w_chainsaw_deathmsg,
w_chainsaw_hudpic
};

View File

@ -0,0 +1,194 @@
/***
*
* Copyright (c) 2016-2019 Marco 'eukara' Hladik. All rights reserved.
*
* See the file LICENSE attached with the sources for usage details.
*
****/
enum
{
HAMMER_IDLE1,
HAMMER_DRAW,
HAMMER_HOLSTER,
HAMMER_ATTACK1,
HAMMER_ATTACK2,
HAMMER_IDLE2,
HAMMER_IDLE3,
HAMMER_HOLSTER2,
HAMMER_HOLSTER3
};
void w_hammer_precache(void)
{
precache_sound("weapons/ham_hitbod1.wav");
precache_sound("weapons/ham_hitbod2.wav");
precache_sound("weapons/ham_hitbod3.wav");
precache_sound("weapons/ham_hitw.wav");
precache_sound("weapons/ham_swing.wav");
precache_model("models/p_hammer.mdl");
precache_model("models/v_hammer.mdl");
}
string w_hammer_vmodel(void)
{
return "models/v_hammer.mdl";
}
string w_hammer_pmodel(void)
{
return "models/p_hammer.mdl";
}
string w_hammer_deathmsg(void)
{
return "%s killed %s with hammer.";
}
void w_hammer_draw(void)
{
#ifdef CSQC
Weapons_ViewAnimation(HAMMER_DRAW);
#else
player pl = (player)self;
Weapons_UpdateAmmo(pl, __NULL__, __NULL__, __NULL__);
#endif
}
void w_hammer_holster(void)
{
#ifdef CSQC
Weapons_ViewAnimation(HAMMER_HOLSTER);
#endif
}
void w_hammer_primary(void)
{
player pl = (player)self;
if (pl.w_attack_next) {
return;
}
#ifdef CSQC
Weapons_MakeVectors();
vector src = pl.origin + pl.view_ofs;
traceline(src, src + (v_forward * 32), FALSE, pl);
/** Launches ents, needs release, grab from idle
makevectors(pl.v_angle);
trace_ent.velocity = v_forward * 1200 + v_up * 240;
**/
int r = floor(random(0,3));
switch (r) {
case 0:
Weapons_ViewAnimation(trace_fraction >= 1 ? CROWBAR_ATTACK1MISS:CROWBAR_ATTACK1HIT);
break;
case 1:
Weapons_ViewAnimation(trace_fraction >= 1 ? CROWBAR_ATTACK2MISS:CROWBAR_ATTACK2HIT);
break;
default:
Weapons_ViewAnimation(trace_fraction >= 1 ? CROWBAR_ATTACK3MISS:CROWBAR_ATTACK3HIT);
}
if (trace_fraction >= 1.0) {
pl.w_attack_next = 0.5f;
} else {
pl.w_attack_next = 0.25f;
}
#else
Weapons_MakeVectors();
vector src = pl.origin + pl.view_ofs;
traceline(src, src + (v_forward * 32), FALSE, pl);
Weapons_PlaySound(pl, CHAN_WEAPON, "weapons/cbar_miss1.wav", 1, ATTN_NORM);
if (trace_fraction >= 1.0) {
pl.w_attack_next = 0.5f;
} else {
pl.w_attack_next = 0.25f;
Effect_Impact(IMPACT_MELEE, trace_endpos, trace_plane_normal);
if (trace_ent.takedamage) {
Damage_Apply(trace_ent, self, 10, trace_endpos, FALSE );
// TODO: Better way to find if it bleeds?
if (trace_ent.iBleeds == 1) {
if (random() < 0.33) {
Weapons_PlaySound(pl, 8, "weapons/cbar_hitbod1.wav", 1, ATTN_NORM);
} else if (random() < 0.66) {
Weapons_PlaySound(pl, 8, "weapons/cbar_hitbod2.wav", 1, ATTN_NORM);
} else {
Weapons_PlaySound(pl, 8, "weapons/cbar_hitbod3.wav", 1, ATTN_NORM);
}
}
} else {
if (random() < 0.5) {
Weapons_PlaySound(pl, 8, "weapons/cbar_hit1.wav", 1, ATTN_NORM);
} else {
Weapons_PlaySound(pl, 8, "weapons/cbar_hit2.wav", 1, ATTN_NORM);
}
}
}
#endif
pl.w_idle_next = 2.5f;
}
void w_hammer_secondary(void)
{
}
void w_hammer_reload(void)
{
}
void w_hammer_release(void)
{
#ifdef CSQC
player pl = (player)self;
if (pl.w_idle_next) {
return;
}
int r = floor(random(0,3));
switch (r) {
case 0:
Weapons_ViewAnimation(HAMMER_IDLE1);
break;
case 1:
Weapons_ViewAnimation(HAMMER_IDLE2);
break;
case 2:
Weapons_ViewAnimation(HAMMER_IDLE3);
break;
}
pl.w_idle_next = 10.0f;
#endif
}
void w_hammer_hudpic(int s, vector pos)
{
#ifdef CSQC
if (s) {
drawsubpic(pos, [170,45], "sprites/hammer.spr_0.tga", [0,48/256], [170/256,45/256], g_hud_color, 1, DRAWFLAG_ADDITIVE);
} else {
drawsubpic(pos, [170,45], "sprites/hammer.spr_0.tga", [0,0], [170/256,45/256], g_hud_color, 1, DRAWFLAG_ADDITIVE);
}
#endif
}
weapon_t w_hammer =
{
ITEM_HAMMER,
0,
1,
w_hammer_draw,
w_hammer_holster,
w_hammer_primary,
w_hammer_secondary,
w_hammer_reload,
w_hammer_release,
__NULL__,
w_hammer_precache,
__NULL__,
w_hammer_vmodel,
w_hammer_pmodel,
w_hammer_deathmsg,
w_hammer_hudpic
};

View File

@ -0,0 +1,250 @@
/***
*
* Copyright (c) 2016-2019 Marco 'eukara' Hladik. All rights reserved.
*
* See the file LICENSE attached with the sources for usage details.
*
****/
#ifdef SSQC
void Decals_Init(void);
#endif
weapon_t w_null = {};
weapon_t g_weapons[] = {
w_null,
w_crowbar,
w_glock,
w_python,
w_mp5,
w_shotgun,
w_crossbow,
w_rpg,
w_gauss,
w_egon,
w_hornetgun,
w_handgrenade,
w_satchel,
w_tripmine,
w_snark,
w_cannon,
w_chainsaw,
w_hammer
};
void Weapons_Init(void)
{
for (int i = 0; i < g_weapons.length; i++) {
if (g_weapons[i].precache != __NULL__) {
g_weapons[i].precache();
}
}
}
void Weapons_Draw(void)
{
player pl = (player)self;
int i = pl.activeweapon;
pl.w_attack_next = Math_Time() + 0.5f;
pl.w_idle_next = Math_Time() + 2.5f;
if (g_weapons[i].draw != __NULL__) {
g_weapons[i].draw();
}
}
void Weapons_Holster(void)
{
player pl = (player)self;
int i = pl.activeweapon;
if (g_weapons[i].holster != __NULL__) {
g_weapons[i].holster();
}
}
void Weapons_Primary(void)
{
player pl = (player)self;
int i = pl.activeweapon;
if (g_weapons[i].primary != __NULL__) {
g_weapons[i].primary();
}
}
void Weapons_Secondary(void)
{
player pl = (player)self;
int i = pl.activeweapon;
if (g_weapons[i].secondary != __NULL__) {
g_weapons[i].secondary();
}
}
void Weapons_Reload(void)
{
player pl = (player)self;
int i = pl.activeweapon;
if (g_weapons[i].reload != __NULL__) {
g_weapons[i].reload();
}
}
void Weapons_Release(void)
{
player pl = (player)self;
int i = pl.activeweapon;
if (g_weapons[i].release != __NULL__) {
g_weapons[i].release();
}
}
void Weapons_DrawCrosshair(void)
{
player pl = (player)self;
int i = pl.activeweapon;
if (g_weapons[i].crosshair != __NULL__) {
g_weapons[i].crosshair();
}
}
string Weapons_GetViewmodel(int id)
{
if (g_weapons[id].vmodel != __NULL__) {
return g_weapons[id].vmodel();
}
return "";
}
string Weapons_GetWorldmodel(int id)
{
if (g_weapons[id].wmodel != __NULL__) {
return g_weapons[id].wmodel();
}
return "";
}
string Weapons_GetPlayermodel(int id)
{
if (g_weapons[id].pmodel != __NULL__) {
return g_weapons[id].pmodel();
}
return "";
}
string Weapons_GetDeathmessage(int id)
{
if (g_weapons[id].deathmsg != __NULL__) {
return g_weapons[id].deathmsg();
}
return "";
}
#ifdef CSQC
void Weapons_HUDPic(int id, int s, vector pos)
{
if (g_weapons[id].hudpic != __NULL__) {
g_weapons[id].hudpic(s, pos);
}
}
#endif
void Weapons_MakeVectors(void)
{
#ifdef SSQC
player pl = (player)self;
makevectors(pl.v_angle);
#else
makevectors(view_angles);
#endif
}
void Weapons_ViewAnimation(int i)
{
#ifdef CSQC
View_PlayAnimation(i);
#else
WriteByte( MSG_MULTICAST, SVC_CGAMEPACKET );
WriteByte( MSG_MULTICAST, EV_VIEWMODEL );
WriteByte( MSG_MULTICAST, i );
msg_entity = self;
multicast( [0,0,0], MULTICAST_ONE );
#endif
}
void Weapons_ViewPunchAngle(vector add)
{
#ifdef CSQC
View_AddPunchAngle(add);
#endif
}
void Weapons_PlaySound(entity t, float ch, string s, float vol, float at)
{
#ifdef SSQC
sound(t, ch, s, vol, at);
#endif
}
int Weapons_IsPresent(player pl, int w)
{
if (pl.items & g_weapons[w].id) {
return TRUE;
} else {
return FALSE;
}
}
#ifdef SSQC
void Weapons_AddItem(player pl, int w)
{
entity oldself = self;
self = pl;
pl.items |= g_weapons[w].id;
pl.activeweapon = w;
if (g_weapons[w].pickup != __NULL__) {
g_weapons[w].pickup();
}
Weapons_Draw();
self = oldself;
}
void Weapons_InitItem(int w)
{
itemweapon it = (itemweapon)self;
spawnfunc_itemweapon();
it.setitem(w);
}
void Weapons_UpdateAmmo(player pl, int a1, int a2, int a3)
{
/* Networked as bytes, since we don't need more. Clamp to avoid errors */
pl.a_ammo1 = bound(0, a1, 255);
pl.a_ammo2 = bound(0, a2, 255);
pl.a_ammo3 = bound(0, a3, 255);
}
void Weapons_ReloadWeapon(player pl, .int mag, .int ammo, int max)
{
int iNeed = max - pl.(mag);
int iHave = pl.(ammo);
if ( iNeed > iHave ) {
pl.(mag) += iHave;
pl.(ammo) = 0;
} else {
pl.(mag) += iNeed;
pl.(ammo) -= iNeed;
}
}
#endif

View File

@ -0,0 +1,89 @@
/***
*
* Copyright (c) 2016-2019 Marco 'eukara' Hladik. All rights reserved.
*
* See the file LICENSE attached with the sources for usage details.
*
****/
typedef struct
{
int id; /* bitflag id */
int slot;
int slot_pos;
void() draw;
void() holster;
void() primary;
void() secondary;
void() reload;
void() release;
void() crosshair;
void() precache;
void() pickup;
string() vmodel;
string() wmodel;
string() pmodel;
string() deathmsg;
void(int, vector) hudpic;
} weapon_t;
/* Weapon Indices for the weapon table */
enum
{
WEAPON_NONE,
WEAPON_CROWBAR,
WEAPON_GLOCK,
WEAPON_PYTHON,
WEAPON_MP5,
WEAPON_SHOTGUN,
WEAPON_CROSSBOW,
WEAPON_RPG,
WEAPON_GAUSS,
WEAPON_EGON,
WEAPON_HORNETGUN,
WEAPON_HANDGRENADE,
WEAPON_SATCHEL,
WEAPON_TRIPMINE,
WEAPON_SNARK,
WEAPON_CANNON,
WEAPON_CHAINSAW,
WEAPON_HAMMER
};
/* What the weapons do support and stuff */
enum
{
AMMO_9MM,
AMMO_357,
AMMO_BUCKSHOT,
AMMO_M203_GRENADE,
AMMO_BOLT,
AMMO_ROCKET,
AMMO_URANIUM,
AMMO_HANDGRENADE,
AMMO_SATCHEL,
AMMO_TRIPMINE,
AMMO_SNARK,
AMMO_HORNET
};
void Weapons_DrawCrosshair(void);
void Decals_PlaceSmall(vector pos);
void Decals_PlaceBig(vector pos);
void Weapons_MakeVectors(void);
void Weapons_ViewAnimation(int i);
void Weapons_ViewPunchAngle(vector add);
void Weapons_PlaySound(entity t, float ch, string s, float vol, float at);
int Weapons_IsPresent(player pl, int w);
#ifdef SSQC
void Weapons_InitItem(int w);
void Weapons_AddItem(player pl, int w);
string Weapons_GetWorldmodel(int id);
void Weapons_UpdateAmmo(player pl, int a1, int a2, int a3);
void Weapons_ReloadWeapon(player pl, .int mag, .int ammo, int max);
#else
void Weapons_HUDPic(int w, int s, vector pos);
#endif

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.