forked from OctaForge/OctaCore
537 lines
19 KiB
C++
537 lines
19 KiB
C++
#include "game.hh"
|
|
|
|
namespace game
|
|
{
|
|
vector<gameent *> bestplayers;
|
|
vector<int> bestteams;
|
|
|
|
VARP(ragdoll, 0, 1, 1);
|
|
VARP(ragdollmillis, 0, 10000, 300000);
|
|
VARP(ragdollfade, 0, 100, 5000);
|
|
VARP(forceplayermodels, 0, 0, 1);
|
|
VARP(hidedead, 0, 0, 1);
|
|
|
|
extern int playermodel;
|
|
|
|
vector<gameent *> ragdolls;
|
|
|
|
void saveragdoll(gameent *d)
|
|
{
|
|
if(!d->ragdoll || !ragdollmillis || (!ragdollfade && lastmillis > d->lastpain + ragdollmillis)) return;
|
|
gameent *r = new gameent(*d);
|
|
r->lastupdate = ragdollfade && lastmillis > d->lastpain + max(ragdollmillis - ragdollfade, 0) ? lastmillis - max(ragdollmillis - ragdollfade, 0) : d->lastpain;
|
|
r->edit = NULL;
|
|
r->ai = NULL;
|
|
if(d==player1) r->playermodel = playermodel;
|
|
ragdolls.add(r);
|
|
d->ragdoll = NULL;
|
|
}
|
|
|
|
void clearragdolls()
|
|
{
|
|
ragdolls.deletecontents();
|
|
}
|
|
|
|
void moveragdolls()
|
|
{
|
|
loopv(ragdolls)
|
|
{
|
|
gameent *d = ragdolls[i];
|
|
if(lastmillis > d->lastupdate + ragdollmillis)
|
|
{
|
|
delete ragdolls.remove(i--);
|
|
continue;
|
|
}
|
|
moveragdoll(d);
|
|
}
|
|
}
|
|
|
|
static const int playercolors[] =
|
|
{
|
|
0xA12020,
|
|
0xA15B28,
|
|
0xB39D52,
|
|
0x3E752F,
|
|
0x3F748C,
|
|
0x214C85,
|
|
0xB3668C,
|
|
0x523678,
|
|
0xB3ADA3
|
|
};
|
|
|
|
static const int playercolorsazul[] =
|
|
{
|
|
0x27508A,
|
|
0x3F748C,
|
|
0x3B3B80,
|
|
0x5364B5
|
|
};
|
|
|
|
static const int playercolorsrojo[] =
|
|
{
|
|
0xAC2C2A,
|
|
0x992417,
|
|
0x802438,
|
|
0xA3435B
|
|
};
|
|
|
|
extern void changedplayercolor();
|
|
VARFP(playercolor, 0, 4, sizeof(playercolors)/sizeof(playercolors[0])-1, changedplayercolor());
|
|
VARFP(playercolorazul, 0, 0, sizeof(playercolorsazul)/sizeof(playercolorsazul[0])-1, changedplayercolor());
|
|
VARFP(playercolorrojo, 0, 0, sizeof(playercolorsrojo)/sizeof(playercolorsrojo[0])-1, changedplayercolor());
|
|
|
|
static const playermodelinfo playermodels[] =
|
|
{
|
|
{ { "player/bones", "player/bones", "player/bones" }, { "hudgun", "hudgun", "hudgun" }, { "player", "player_azul", "player_rojo" }, true }
|
|
};
|
|
|
|
extern void changedplayermodel();
|
|
VARFP(playermodel, 0, 0, sizeof(playermodels)/sizeof(playermodels[0])-1, changedplayermodel());
|
|
|
|
int chooserandomplayermodel(int seed)
|
|
{
|
|
return (seed&0xFFFF)%(sizeof(playermodels)/sizeof(playermodels[0]));
|
|
}
|
|
|
|
const playermodelinfo *getplayermodelinfo(int n)
|
|
{
|
|
if(size_t(n) >= sizeof(playermodels)/sizeof(playermodels[0])) return NULL;
|
|
return &playermodels[n];
|
|
}
|
|
|
|
const playermodelinfo &getplayermodelinfo(gameent *d)
|
|
{
|
|
const playermodelinfo *mdl = getplayermodelinfo(d==player1 || forceplayermodels ? playermodel : d->playermodel);
|
|
if(!mdl) mdl = getplayermodelinfo(playermodel);
|
|
return *mdl;
|
|
}
|
|
|
|
int getplayercolor(int team, int color)
|
|
{
|
|
#define GETPLAYERCOLOR(playercolors) \
|
|
return playercolors[color%(sizeof(playercolors)/sizeof(playercolors[0]))];
|
|
switch(team)
|
|
{
|
|
case 1: GETPLAYERCOLOR(playercolorsazul)
|
|
case 2: GETPLAYERCOLOR(playercolorsrojo)
|
|
default: GETPLAYERCOLOR(playercolors)
|
|
}
|
|
}
|
|
|
|
ICOMMAND(getplayercolor, "ii", (int *color, int *team), intret(getplayercolor(*team, *color)));
|
|
|
|
int getplayercolor(gameent *d, int team)
|
|
{
|
|
if(d==player1) switch(team)
|
|
{
|
|
case 1: return getplayercolor(1, playercolorazul);
|
|
case 2: return getplayercolor(2, playercolorrojo);
|
|
default: return getplayercolor(0, playercolor);
|
|
}
|
|
else return getplayercolor(team, (d->playercolor>>(5*team))&0x1F);
|
|
}
|
|
|
|
void changedplayermodel()
|
|
{
|
|
if(player1->clientnum < 0) player1->playermodel = playermodel;
|
|
if(player1->ragdoll) cleanragdoll(player1);
|
|
loopv(ragdolls)
|
|
{
|
|
gameent *d = ragdolls[i];
|
|
if(!d->ragdoll) continue;
|
|
if(!forceplayermodels)
|
|
{
|
|
const playermodelinfo *mdl = getplayermodelinfo(d->playermodel);
|
|
if(mdl) continue;
|
|
}
|
|
cleanragdoll(d);
|
|
}
|
|
loopv(players)
|
|
{
|
|
gameent *d = players[i];
|
|
if(d == player1 || !d->ragdoll) continue;
|
|
if(!forceplayermodels)
|
|
{
|
|
const playermodelinfo *mdl = getplayermodelinfo(d->playermodel);
|
|
if(mdl) continue;
|
|
}
|
|
cleanragdoll(d);
|
|
}
|
|
}
|
|
|
|
void changedplayercolor()
|
|
{
|
|
if(player1->clientnum < 0) player1->playercolor = playercolor | (playercolorazul<<5) | (playercolorrojo<<10);
|
|
}
|
|
|
|
void syncplayer()
|
|
{
|
|
if(player1->playermodel != playermodel)
|
|
{
|
|
player1->playermodel = playermodel;
|
|
addmsg(N_SWITCHMODEL, "ri", player1->playermodel);
|
|
}
|
|
|
|
int col = playercolor | (playercolorazul<<5) | (playercolorrojo<<10);
|
|
if(player1->playercolor != col)
|
|
{
|
|
player1->playercolor = col;
|
|
addmsg(N_SWITCHCOLOR, "ri", player1->playercolor);
|
|
}
|
|
}
|
|
|
|
void preloadplayermodel()
|
|
{
|
|
loopi(sizeof(playermodels)/sizeof(playermodels[0]))
|
|
{
|
|
const playermodelinfo *mdl = getplayermodelinfo(i);
|
|
if(!mdl) break;
|
|
if(i != playermodel && (!multiplayer(false) || forceplayermodels)) continue;
|
|
if(m_teammode)
|
|
{
|
|
loopj(MAXTEAMS) preloadmodel(mdl->model[1+j]);
|
|
}
|
|
else preloadmodel(mdl->model[0]);
|
|
}
|
|
}
|
|
|
|
int numanims() { return NUMANIMS; }
|
|
|
|
void findanims(const char *pattern, vector<int> &anims)
|
|
{
|
|
loopi(sizeof(animnames)/sizeof(animnames[0])) if(matchanim(animnames[i], pattern)) anims.add(i);
|
|
}
|
|
|
|
VAR(animoverride, -1, 0, NUMANIMS-1);
|
|
VAR(testanims, 0, 0, 1);
|
|
VAR(testpitch, -90, 0, 90);
|
|
|
|
void renderplayer(gameent *d, const playermodelinfo &mdl, int color, int team, float fade, int flags = 0, bool mainpass = true)
|
|
{
|
|
int lastaction = d->lastaction, anim = ANIM_IDLE|ANIM_LOOP, attack = 0, delay = 0;
|
|
if(d->lastattack >= 0)
|
|
{
|
|
attack = attacks[d->lastattack].anim;
|
|
delay = attacks[d->lastattack].attackdelay+50;
|
|
}
|
|
if(intermission && d->state!=CS_DEAD)
|
|
{
|
|
anim = attack = ANIM_LOSE|ANIM_LOOP;
|
|
if(validteam(team) ? bestteams.htfind(team)>=0 : bestplayers.find(d)>=0) anim = attack = ANIM_WIN|ANIM_LOOP;
|
|
}
|
|
else if(d->state==CS_ALIVE && d->lasttaunt && lastmillis-d->lasttaunt<1000 && lastmillis-d->lastaction>delay)
|
|
{
|
|
lastaction = d->lasttaunt;
|
|
anim = attack = ANIM_TAUNT;
|
|
delay = 1000;
|
|
}
|
|
modelattach a[5];
|
|
int ai = 0;
|
|
if(guns[d->gunselect].vwep)
|
|
{
|
|
int vanim = ANIM_VWEP_IDLE|ANIM_LOOP, vtime = 0;
|
|
if(lastaction && d->lastattack >= 0 && attacks[d->lastattack].gun==d->gunselect && lastmillis < lastaction + delay)
|
|
{
|
|
vanim = attacks[d->lastattack].vwepanim;
|
|
vtime = lastaction;
|
|
}
|
|
a[ai++] = modelattach("tag_weapon", guns[d->gunselect].vwep, vanim, vtime);
|
|
}
|
|
if(mainpass && !(flags&MDL_ONLYSHADOW))
|
|
{
|
|
d->muzzle = vec(-1, -1, -1);
|
|
if(guns[d->gunselect].vwep) a[ai++] = modelattach("tag_muzzle", &d->muzzle);
|
|
}
|
|
const char *mdlname = mdl.model[validteam(team) ? team : 0];
|
|
float yaw = testanims && d==player1 ? 0 : d->yaw,
|
|
pitch = testpitch && d==player1 ? testpitch : d->pitch;
|
|
vec o = d->feetpos();
|
|
int basetime = 0;
|
|
if(animoverride) anim = (animoverride<0 ? ANIM_ALL : animoverride)|ANIM_LOOP;
|
|
else if(d->state==CS_DEAD)
|
|
{
|
|
anim = ANIM_DYING|ANIM_NOPITCH;
|
|
basetime = d->lastpain;
|
|
if(ragdoll && mdl.ragdoll) anim |= ANIM_RAGDOLL;
|
|
else if(lastmillis-basetime>1000) anim = ANIM_DEAD|ANIM_LOOP|ANIM_NOPITCH;
|
|
}
|
|
else if(d->state==CS_EDITING || d->state==CS_SPECTATOR) anim = ANIM_EDIT|ANIM_LOOP;
|
|
else if(d->state==CS_LAGGED) anim = ANIM_LAG|ANIM_LOOP;
|
|
else if(!intermission)
|
|
{
|
|
if(lastmillis-d->lastpain < 300)
|
|
{
|
|
anim = ANIM_PAIN;
|
|
basetime = d->lastpain;
|
|
}
|
|
else if(d->lastpain < lastaction && lastmillis-lastaction < delay)
|
|
{
|
|
anim = attack;
|
|
basetime = lastaction;
|
|
}
|
|
|
|
if(d->inwater && d->physstate<=PHYS_FALL) anim |= (((game::allowmove(d) && (d->move || d->strafe)) || d->vel.z+d->falling.z>0 ? ANIM_SWIM : ANIM_SINK)|ANIM_LOOP)<<ANIM_SECONDARY;
|
|
else
|
|
{
|
|
static const int dirs[9] =
|
|
{
|
|
ANIM_RUN_SE, ANIM_RUN_S, ANIM_RUN_SW,
|
|
ANIM_RUN_E, 0, ANIM_RUN_W,
|
|
ANIM_RUN_NE, ANIM_RUN_N, ANIM_RUN_NW
|
|
};
|
|
int dir = dirs[(d->move+1)*3 + (d->strafe+1)];
|
|
if(d->timeinair>100) anim |= ((dir ? dir+ANIM_JUMP_N-ANIM_RUN_N : ANIM_JUMP) | ANIM_END) << ANIM_SECONDARY;
|
|
else if(dir && game::allowmove(d)) anim |= (dir | ANIM_LOOP) << ANIM_SECONDARY;
|
|
}
|
|
|
|
if(d->crouching) switch((anim>>ANIM_SECONDARY)&ANIM_INDEX)
|
|
{
|
|
case ANIM_IDLE: anim &= ~(ANIM_INDEX<<ANIM_SECONDARY); anim |= ANIM_CROUCH<<ANIM_SECONDARY; break;
|
|
case ANIM_JUMP: anim &= ~(ANIM_INDEX<<ANIM_SECONDARY); anim |= ANIM_CROUCH_JUMP<<ANIM_SECONDARY; break;
|
|
case ANIM_SWIM: anim &= ~(ANIM_INDEX<<ANIM_SECONDARY); anim |= ANIM_CROUCH_SWIM<<ANIM_SECONDARY; break;
|
|
case ANIM_SINK: anim &= ~(ANIM_INDEX<<ANIM_SECONDARY); anim |= ANIM_CROUCH_SINK<<ANIM_SECONDARY; break;
|
|
case 0: anim |= (ANIM_CROUCH|ANIM_LOOP)<<ANIM_SECONDARY; break;
|
|
case ANIM_RUN_N: case ANIM_RUN_NE: case ANIM_RUN_E: case ANIM_RUN_SE: case ANIM_RUN_S: case ANIM_RUN_SW: case ANIM_RUN_W: case ANIM_RUN_NW:
|
|
anim += (ANIM_CROUCH_N - ANIM_RUN_N) << ANIM_SECONDARY;
|
|
break;
|
|
case ANIM_JUMP_N: case ANIM_JUMP_NE: case ANIM_JUMP_E: case ANIM_JUMP_SE: case ANIM_JUMP_S: case ANIM_JUMP_SW: case ANIM_JUMP_W: case ANIM_JUMP_NW:
|
|
anim += (ANIM_CROUCH_JUMP_N - ANIM_JUMP_N) << ANIM_SECONDARY;
|
|
break;
|
|
}
|
|
|
|
if((anim&ANIM_INDEX)==ANIM_IDLE && (anim>>ANIM_SECONDARY)&ANIM_INDEX) anim >>= ANIM_SECONDARY;
|
|
}
|
|
if(!((anim>>ANIM_SECONDARY)&ANIM_INDEX)) anim |= (ANIM_IDLE|ANIM_LOOP)<<ANIM_SECONDARY;
|
|
if(d!=player1) flags |= MDL_CULL_VFC | MDL_CULL_OCCLUDED | MDL_CULL_QUERY;
|
|
if(d->type==ENT_PLAYER) flags |= MDL_FULLBRIGHT;
|
|
else flags |= MDL_CULL_DIST;
|
|
if(!mainpass) flags &= ~(MDL_FULLBRIGHT | MDL_CULL_VFC | MDL_CULL_OCCLUDED | MDL_CULL_QUERY | MDL_CULL_DIST);
|
|
float trans = d->state == CS_LAGGED ? 0.5f : 1.0f;
|
|
rendermodel(mdlname, anim, o, yaw, pitch, 0, flags, d, a[0].tag ? a : NULL, basetime, 0, fade, vec4(vec::hexcolor(color), trans));
|
|
}
|
|
|
|
static inline void renderplayer(gameent *d, float fade = 1, int flags = 0)
|
|
{
|
|
int team = m_teammode && validteam(d->team) ? d->team : 0;
|
|
renderplayer(d, getplayermodelinfo(d), getplayercolor(d, team), team, fade, flags);
|
|
}
|
|
|
|
void rendergame()
|
|
{
|
|
ai::render();
|
|
|
|
if(intermission)
|
|
{
|
|
bestteams.shrink(0);
|
|
bestplayers.shrink(0);
|
|
if(m_teammode) getbestteams(bestteams);
|
|
else getbestplayers(bestplayers);
|
|
}
|
|
|
|
bool third = isthirdperson();
|
|
gameent *f = followingplayer(), *exclude = third ? NULL : f;
|
|
loopv(players)
|
|
{
|
|
gameent *d = players[i];
|
|
if(d == player1 || d->state==CS_SPECTATOR || d->state==CS_SPAWNING || d->lifesequence < 0 || d == exclude || (d->state==CS_DEAD && hidedead)) continue;
|
|
renderplayer(d);
|
|
copystring(d->info, colorname(d));
|
|
if(d->state!=CS_DEAD)
|
|
{
|
|
int team = m_teammode && validteam(d->team) ? d->team : 0;
|
|
particle_text(d->abovehead(), d->info, PART_TEXT, 1, teamtextcolor[team], 2.0f);
|
|
}
|
|
}
|
|
loopv(ragdolls)
|
|
{
|
|
gameent *d = ragdolls[i];
|
|
float fade = 1.0f;
|
|
if(ragdollmillis && ragdollfade)
|
|
fade -= clamp(float(lastmillis - (d->lastupdate + max(ragdollmillis - ragdollfade, 0)))/min(ragdollmillis, ragdollfade), 0.0f, 1.0f);
|
|
renderplayer(d, fade);
|
|
}
|
|
if(exclude)
|
|
renderplayer(exclude, 1, MDL_ONLYSHADOW);
|
|
else if(!f && (player1->state==CS_ALIVE || (player1->state==CS_EDITING && third) || (player1->state==CS_DEAD && !hidedead)))
|
|
renderplayer(player1, 1, third ? 0 : MDL_ONLYSHADOW);
|
|
entities::renderentities();
|
|
renderbouncers();
|
|
renderprojectiles();
|
|
if(cmode) cmode->rendergame();
|
|
}
|
|
|
|
VARP(hudgun, 0, 1, 1);
|
|
VARP(hudgunsway, 0, 1, 1);
|
|
|
|
FVAR(swaystep, 1, 35.0f, 100);
|
|
FVAR(swayside, 0, 0.10f, 1);
|
|
FVAR(swayup, -1, 0.15f, 1);
|
|
|
|
float swayfade = 0, swayspeed = 0, swaydist = 0;
|
|
vec swaydir(0, 0, 0);
|
|
|
|
void swayhudgun(int curtime)
|
|
{
|
|
gameent *d = hudplayer();
|
|
if(d->state != CS_SPECTATOR)
|
|
{
|
|
if(d->physstate >= PHYS_SLOPE)
|
|
{
|
|
swayspeed = min(sqrtf(d->vel.x*d->vel.x + d->vel.y*d->vel.y), d->maxspeed);
|
|
swaydist += swayspeed*curtime/1000.0f;
|
|
swaydist = fmod(swaydist, 2*swaystep);
|
|
swayfade = 1;
|
|
}
|
|
else if(swayfade > 0)
|
|
{
|
|
swaydist += swayspeed*swayfade*curtime/1000.0f;
|
|
swaydist = fmod(swaydist, 2*swaystep);
|
|
swayfade -= 0.5f*(curtime*d->maxspeed)/(swaystep*1000.0f);
|
|
}
|
|
|
|
float k = pow(0.7f, curtime/10.0f);
|
|
swaydir.mul(k);
|
|
vec vel(d->vel);
|
|
vel.add(d->falling);
|
|
swaydir.add(vec(vel).mul((1-k)/(15*max(vel.magnitude(), d->maxspeed))));
|
|
}
|
|
}
|
|
|
|
struct hudent : dynent
|
|
{
|
|
hudent() { type = ENT_CAMERA; }
|
|
} guninterp;
|
|
|
|
void drawhudmodel(gameent *d, int anim, int basetime)
|
|
{
|
|
const char *file = guns[d->gunselect].file;
|
|
if(!file) return;
|
|
|
|
vec sway;
|
|
vecfromyawpitch(d->yaw, 0, 0, 1, sway);
|
|
float steps = swaydist/swaystep*M_PI;
|
|
sway.mul(swayside*cosf(steps));
|
|
sway.z = swayup*(fabs(sinf(steps)) - 1);
|
|
sway.add(swaydir).add(d->o);
|
|
if(!hudgunsway) sway = d->o;
|
|
|
|
const playermodelinfo &mdl = getplayermodelinfo(d);
|
|
int team = m_teammode && validteam(d->team) ? d->team : 0,
|
|
color = getplayercolor(d, team);
|
|
defformatstring(gunname, "%s/%s", mdl.hudguns[team], file);
|
|
modelattach a[2];
|
|
d->muzzle = vec(-1, -1, -1);
|
|
a[0] = modelattach("tag_muzzle", &d->muzzle);
|
|
rendermodel(gunname, anim, sway, d->yaw, d->pitch, 0, MDL_NOBATCH, NULL, a, basetime, 0, 1, vec4(vec::hexcolor(color), 1));
|
|
if(d->muzzle.x >= 0) d->muzzle = calcavatarpos(d->muzzle, 12);
|
|
}
|
|
|
|
void drawhudgun()
|
|
{
|
|
gameent *d = hudplayer();
|
|
if(d->state==CS_SPECTATOR || d->state==CS_EDITING || !hudgun || editmode)
|
|
{
|
|
d->muzzle = player1->muzzle = vec(-1, -1, -1);
|
|
return;
|
|
}
|
|
|
|
int anim = ANIM_GUN_IDLE|ANIM_LOOP, basetime = 0;
|
|
if(d->lastaction && d->lastattack >= 0 && attacks[d->lastattack].gun==d->gunselect && lastmillis-d->lastaction<attacks[d->lastattack].attackdelay)
|
|
{
|
|
anim = attacks[d->lastattack].hudanim;
|
|
basetime = d->lastaction;
|
|
}
|
|
drawhudmodel(d, anim, basetime);
|
|
}
|
|
|
|
void renderavatar()
|
|
{
|
|
drawhudgun();
|
|
}
|
|
|
|
void renderplayerpreview(int model, int color, int team, int weap)
|
|
{
|
|
static gameent *previewent = NULL;
|
|
if(!previewent)
|
|
{
|
|
previewent = new gameent;
|
|
loopi(NUMGUNS) previewent->ammo[i] = 1;
|
|
}
|
|
float height = previewent->eyeheight + previewent->aboveeye,
|
|
zrad = height/2;
|
|
vec2 xyrad = vec2(previewent->xradius, previewent->yradius).max(height/4);
|
|
previewent->o = calcmodelpreviewpos(vec(xyrad, zrad), previewent->yaw).addz(previewent->eyeheight - zrad);
|
|
previewent->gunselect = validgun(weap) ? weap : GUN_RAIL;
|
|
const playermodelinfo *mdlinfo = getplayermodelinfo(model);
|
|
if(!mdlinfo) return;
|
|
renderplayer(previewent, *mdlinfo, getplayercolor(team, color), team, 1, 0, false);
|
|
}
|
|
|
|
vec hudgunorigin(int gun, const vec &from, const vec &to, gameent *d)
|
|
{
|
|
if(d->muzzle.x >= 0) return d->muzzle;
|
|
vec offset(from);
|
|
if(d!=hudplayer() || isthirdperson())
|
|
{
|
|
vec front, right;
|
|
vecfromyawpitch(d->yaw, d->pitch, 1, 0, front);
|
|
offset.add(front.mul(d->radius));
|
|
offset.z += (d->aboveeye + d->eyeheight)*0.75f - d->eyeheight;
|
|
vecfromyawpitch(d->yaw, 0, 0, -1, right);
|
|
offset.add(right.mul(0.5f*d->radius));
|
|
offset.add(front);
|
|
return offset;
|
|
}
|
|
offset.add(vec(to).sub(from).normalize().mul(2));
|
|
if(hudgun)
|
|
{
|
|
offset.sub(vec(camup).mul(1.0f));
|
|
offset.add(vec(camright).mul(0.8f));
|
|
}
|
|
else offset.sub(vec(camup).mul(0.8f));
|
|
return offset;
|
|
}
|
|
|
|
void preloadweapons()
|
|
{
|
|
const playermodelinfo &mdl = getplayermodelinfo(player1);
|
|
loopi(NUMGUNS)
|
|
{
|
|
const char *file = guns[i].file;
|
|
if(!file) continue;
|
|
string fname;
|
|
if(m_teammode)
|
|
{
|
|
loopj(MAXTEAMS)
|
|
{
|
|
formatstring(fname, "%s/%s", mdl.hudguns[1+j], file);
|
|
preloadmodel(fname);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
formatstring(fname, "%s/%s", mdl.hudguns[0], file);
|
|
preloadmodel(fname);
|
|
}
|
|
formatstring(fname, "worldgun/%s", file);
|
|
preloadmodel(fname);
|
|
}
|
|
}
|
|
|
|
void preloadsounds()
|
|
{
|
|
for(int i = S_JUMP; i <= S_DIE2; i++) preloadsound(i);
|
|
}
|
|
|
|
void preload()
|
|
{
|
|
if(hudgun) preloadweapons();
|
|
preloadbouncers();
|
|
preloadplayermodel();
|
|
preloadsounds();
|
|
entities::preloadentities();
|
|
}
|
|
|
|
}
|
|
|