// bind HOME [ edittex 1 ]
// bind END [ edittex -1 ]
-
editbind G [ domodifier 1 ] // domodifier 1 -> executes delta_edit_1
editbind F [ domodifier 2 ] // etc...
editbind Q [ domodifier 3 ]
]
] "AmmoBar"
-
newgui gameclock [
guicheckbox "GameClock" gameclock
guibar
]
] "GameClock"
-
newgui hudscore [
guicheckbox "HUDScore" hudscore
guibar
shells bullets rockets riflerounds grenades cartridges
health healthboost tinyhealth tinyarmour greenarmour yellowarmour quaddamage
teleport teledest jumppad
- spotlight
]
enttypeselect = [
ent_action_teleport = [ entproperty 0 ( * $arg1 1 ) ]
ent_action_teledest = [ entproperty 1 ( * $arg1 1 ) ]
ent_action_mapmodel = [ entproperty 1 ( * $arg1 1 ) ]
-ent_action_spotlight = [ entproperty 0 ( * $arg1 5 ) ]
ent_action_light = [ entproperty 0 ( * $arg1 5 ) ]
ent_action_jumppad = [ entproperty 0 ( * $arg1 5 ) ]
ent_action_playerstart = [ entproperty 0 ( * $arg1 15 ) ]
int conpad = fullconsole ? 0 : FONTH/4,
conoff = fullconsole ? FONTH : FONTH/3,
conheight = min(fullconsole ? ((h*fullconsize/100)/FONTH)*FONTH : FONTH*consize, h - 2*(conpad + conoff)),
- conwidth = w - 2*(conpad + conoff) - (fullconsole ? 0 : game::clipconsole(w, h));
+ conwidth = w - 2*(conpad + conoff);
extern void consolebox(int x1, int y1, int x2, int y2);
if(fullconsole) consolebox(conpad, conpad, conwidth+conpad+2*conoff, conheight+conpad+2*conoff);
int y = drawconlines(conskip, fullconsole ? 0 : confade, conwidth, conheight, conpad+conoff, fullconsole ? fullconfilter : confilter);
extern void rendermaterials();
extern int visiblematerial(const cube &c, int orient, const ivec &co, int size, ushort matmask = 0);
-// server
-extern vector<const char *> gameargs;
-
extern void initserver(bool listen, bool dedicated);
extern void cleanupserver();
extern void serverslice(bool dedicated, uint timeout);
extern ENetSocket connectmaster(bool wait);
extern void localclienttoserver(int chan, ENetPacket *);
extern void localconnect();
-extern bool serveroption(char *opt);
// serverbrowser
extern bool resolverwait(const char *name, ENetAddress *address);
extern void entcancel();
extern void entitiesinoctanodes();
-extern void attachentities();
extern void freeoctaentities(cube &c);
extern bool pointinsel(const selinfo &sel, const vec &o);
ray.mul(1.0f / mag);
float angle = -ray.dot(normal);
if(angle <= 0) continue;
- if(light.attached && light.attached->type==ET_SPOTLIGHT) {
- vec spot = vec(light.attached->o).sub(light.o).normalize();
- float maxatten = sincos360[clamp(int(light.attached->attr1), 1, 89)].x, spotatten = (ray.dot(spot) - maxatten) / (1 - maxatten);
- if(spotatten <= 0) continue;
- attenuation *= spotatten;
- }
if(lmshadows && mag) {
float dist = shadowray(w->shadowraycache, light.o, ray, mag - tolerance, RAY_SHADOW | (lmshadows > 1 ? RAY_ALPHAPOLY : 0));
if(dist < mag - tolerance) continue;
float intensity = 1;
if(e.attr1)
intensity -= mag / float(e.attr1);
- if(e.attached && e.attached->type==ET_SPOTLIGHT) {
- vec spot = vec(e.attached->o).sub(e.o).normalize();
- float maxatten = sincos360[clamp(int(e.attached->attr1), 1, 89)].x, spotatten = (ray.dot(spot) - maxatten) / (1 - maxatten);
- if(spotatten <= 0) continue;
- intensity *= spotatten;
- }
vec lightcol = vec(e.attr2, e.attr3, e.attr4).mul(1.0f/255);
color.add(vec(lightcol).mul(intensity));
dir.add(vec(ray).mul(-intensity*lightcol.x*lightcol.y*lightcol.z));
float intensity = 1;
if(e.attr1)
intensity -= mag / float(e.attr1);
- if(e.attached && e.attached->type==ET_SPOTLIGHT) {
- vec spot = vec(e.attached->o).sub(e.o).normalize();
- float maxatten = sincos360[clamp(int(e.attached->attr1), 1, 89)].x, spotatten = (ray.dot(spot) - maxatten) / (1 - maxatten);
- if(spotatten <= 0) continue;
- intensity *= spotatten;
- }
if(!brightest || intensity > bintensity) {
brightest = &e;
bintensity = intensity;
extern void clear_console(); clear_console();
extern void clear_mdls(); clear_mdls();
extern void clear_sound(); clear_sound();
- closelogfile();
SDL_Quit();
}
VAR(numcpus, 1, 1, 16);
-int main(int argc, char **argv) {
- setlogfile(NULL);
+int main(void) {
int dedicated = 0;
char *load = NULL, *initscript = NULL;
initing = INIT_RESET;
- // set home dir first
- for(int i = 1; i<argc; i++) if(argv[i][0]=='-' && argv[i][1] == 'q') { sethomedir(&argv[i][2]); break; }
- // set log after home dir, but before anything else
- for(int i = 1; i<argc; i++) if(argv[i][0]=='-' && argv[i][1] == 'g') {
- const char *file = argv[i][2] ? &argv[i][2] : "log.txt";
- setlogfile(file);
- logoutf("Setting log file: %s", file);
- break;
- }
execfile("init.cfg", false);
- for(int i = 1; i<argc; i++) {
- if(argv[i][0]=='-') switch(argv[i][1]) {
- case 'q': if(homedir[0]) logoutf("Using home directory: %s", homedir); break;
- case 'r': /* compat, ignore */ break;
- case 'k': {
- const char *dir = addpackagedir(&argv[i][2]);
- if(dir) logoutf("Adding package directory: %s", dir);
- break;
- }
- case 'g': break;
- case 'd': dedicated = atoi(&argv[i][2]); if(dedicated<=0) dedicated = 2; break;
- case 'w': scr_w = clamp(atoi(&argv[i][2]), SCR_MINW, SCR_MAXW); if(!findarg(argc, argv, "-h")) scr_h = -1; break;
- case 'h': scr_h = clamp(atoi(&argv[i][2]), SCR_MINH, SCR_MAXH); if(!findarg(argc, argv, "-w")) scr_w = -1; break;
- case 'z': depthbits = atoi(&argv[i][2]); break;
- case 'b': /* compat, ignore */ break;
- case 'a': fsaa = atoi(&argv[i][2]); break;
- case 'v': /* compat, ignore */ break;
- case 't': fullscreen = atoi(&argv[i][2]); break;
- case 's': /* compat, ignore */ break;
- case 'f': /* compat, ignore */ break;
- case 'l': {
- char pkgdir[] = "packages/";
- load = strstr(path(&argv[i][2]), path(pkgdir));
- if(load) load += sizeof(pkgdir)-1;
- else load = &argv[i][2];
- break;
- }
- case 'x': initscript = &argv[i][2]; break;
- default: if(!serveroption(argv[i])) gameargs.add(argv[i]); break;
- }
- else gameargs.add(argv[i]);
- }
initing = NOT_INITING;
numcpus = clamp(SDL_GetCPUCount(), 1, 16);
if(dedicated <= 1) {
logoutf("init: sdl");
if(SDL_Init(SDL_INIT_TIMER|SDL_INIT_VIDEO|SDL_INIT_AUDIO)<0) fatal("Unable to initialize SDL: %s", SDL_GetError());
-
#ifdef SDL_VIDEO_DRIVER_X11
SDL_version version;
SDL_GetVersion(&version);
atexit(enet_deinitialize);
enet_time_set(0);
logoutf("init: game");
- game::parseoptions(gameargs);
initserver(dedicated>0, dedicated>1); // never returns if dedicated
ASSERT(dedicated <= 1);
game::initclient();
#define SERVER_LIMIT 4096
#define SERVER_DUP_LIMIT 10
-FILE *logfile = NULL;
-
struct userinfo {
char *name;
void *pubkey;
void fatal(const char *fmt, ...) {
va_list args;
va_start(args, fmt);
- vfprintf(logfile, fmt, args);
- fputc('\n', logfile);
+ vfprintf(stdout, fmt, args);
+ fputc('\n', stdout);
va_end(args);
exit(EXIT_FAILURE);
}
void conoutfv(int type, const char *fmt, va_list args) {
- vfprintf(logfile, fmt, args);
- fputc('\n', logfile);
+ vfprintf(stdout, fmt, args);
+ fputc('\n', stdout);
}
void purgeclient(int n) {
defformatstring(cfgname, "%smaster.cfg", dir);
path(logname);
path(cfgname);
- logfile = fopen(logname, "a");
- if(!logfile) logfile = stdout;
- setvbuf(logfile, NULL, _IOLBF, BUFSIZ);
+ setvbuf(stdout, NULL, _IOLBF, BUFSIZ);
signal(SIGUSR1, reloadsignal);
setupserver(port, ip);
for(;;) {
//use text<action> to do more...
-
void guilist(uint *contents) {
if(!cgui) return;
cgui->pushlist();
return 0;
}
-
bool mpedittex(int tex, int allfaces, selinfo &sel, ucharbuf &buf) {
if(!unpacktex(tex, buf)) return false;
mpedittex(tex, allfaces, sel, false);
if(o==d || d->o.reject(o->o, d->radius+o->radius)) continue;
if(plcollide(d, dir, o)) {
collideplayer = o;
- game::dynentcollide(d, o, collidewall);
return true;
}
if(collideinside > lastinside) {
}
if(insideplayer && insideplayercol) {
collideplayer = insideplayer;
- game::dynentcollide(d, insideplayer, vec(0, 0, 0));
return true;
}
return false;
if(pl->jumping && allowmove) {
pl->jumping = false;
pl->vel.z = max(pl->vel.z, JUMPVEL); // physics impulse upwards
- game::physicstrigger(pl, local, 1);
+ game::physicstrigger(pl, 1);
}
}
if(!floating && pl->physstate == PHYS_FALL) pl->timeinair = min(pl->timeinair + curtime, 1000);
d.mul(f);
loopi(moveres) if(!move(pl, d) && ++collisions<5) i--; // discrete steps collision detection & sliding
if(timeinair > 800 && !pl->timeinair) { // if we land after long time must have been a high jump, make thud sound {
- game::physicstrigger(pl, local, -1);
+ game::physicstrigger(pl, -1);
}
}
if(pl->state==CS_ALIVE) updatedynentcache(pl);
// automatically apply smooth roll when strafing
if(pl->strafe && maxroll) pl->roll = clamp(pl->roll - pow(clamp(1.0f + pl->strafe*pl->roll/maxroll, 0.0f, 1.0f), 0.33f)*pl->strafe*curtime*straferoll, -maxroll, maxroll);
else pl->roll *= curtime == PHYSFRAMETIME ? faderoll : pow(faderoll, curtime/float(PHYSFRAMETIME));
- if(pl->inwater) game::physicstrigger(pl, local, 0, pl->inwater);
+ if(pl->inwater) game::physicstrigger(pl, 0);
pl->inwater = MAT_AIR;
if(pl->state==CS_ALIVE && (pl->o.z < 0 || material&MAT_DEATH)) game::suicide(pl);
return true;
ragdollskel *ragdoll = skel->ragdoll; \
if(ragdoll->loaded) return;
-
void rdvert(float *x, float *y, float *z, float *radius) {
checkragdoll;
ragdollskel::vert &v = ragdoll->verts.add();
else if(d->type < ENT_CAMERA) pos.z += 0.75f*(d->eyeheight + d->aboveeye);
lightreaching(pos, light->color, light->dir, (flags&MDL_LIGHT_FAST)!=0);
dynlightreaching(pos, light->color, light->dir, (flags&MDL_HUD)!=0);
- game::lighteffects(d, light->color, light->dir);
light->millis = lastmillis;
}
}
} \
} while(0)
-
#define endvaquery(va, flush) \
do { \
if(va->query) { \
#define LOGSTRLEN 512
-static FILE *logfile = NULL;
-
-void closelogfile() {
- if(logfile) {
- fclose(logfile);
- logfile = NULL;
- }
-}
-
-FILE *getlogfile() {
- return logfile ? logfile : stdout;
-}
-
-void setlogfile(const char *fname) {
- closelogfile();
- if(fname && fname[0]) {
- fname = findfile(fname, "w");
- if(fname) logfile = fopen(fname, "w");
- }
- FILE *f = getlogfile();
- if(f) setvbuf(f, NULL, _IOLBF, BUFSIZ);
-}
-
void logoutf(const char *fmt, ...) {
va_list args;
va_start(args, fmt);
va_end(args);
}
-
static void writelog(FILE *file, const char *buf) {
static uchar ubuf[512];
size_t len = strlen(buf), carry = 0;
void cleanupserver();
cleanupserver();
defvformatstring(msg,fmt,fmt);
- if(logfile) logoutf("%s", msg);
+ logoutf("%s", msg);
fprintf(stderr, "server error: %s\n", msg);
- closelogfile();
exit(EXIT_FAILURE);
}
#endif
void logoutfv(const char *fmt, va_list args) {
- FILE *f = getlogfile();
+ FILE *f = stdout;
if(f) writelogv(f, fmt, args);
}
COMMAND(stoplistenserver, "");
#endif
-bool serveroption(char *opt) {
- switch(opt[1]) {
- case 'u': setvar("serveruprate", atoi(opt+2)); return true;
- case 'c': setvar("maxclients", atoi(opt+2)); return true;
- case 'i': setsvar("serverip", opt+2); return true;
- case 'j': setvar("serverport", atoi(opt+2)); return true;
- case 'm': setsvar("mastername", opt+2); setvar("updatemaster", mastername[0] ? 1 : 0); return true;
-#ifdef STANDALONE
- case 'q': logoutf("Using home directory: %s", opt); sethomedir(opt+2); return true;
- case 'k': logoutf("Adding package directory: %s", opt); addpackagedir(opt+2); return true;
- case 'g': logoutf("Setting log file: %s", opt); setlogfile(opt+2); return true;
-#endif
- default: return false;
- }
-}
-
-vector<const char *> gameargs;
-
#ifdef STANDALONE
int main(int argc, char **argv) {
- setlogfile(NULL);
if(enet_initialize()<0) fatal("Unable to initialise network module");
atexit(enet_deinitialize);
enet_time_set(0);
- for(int i = 1; i<argc; i++) if(argv[i][0]!='-' || !serveroption(argv[i])) gameargs.add(argv[i]);
- game::parseoptions(gameargs);
initserver(true, true);
return EXIT_SUCCESS;
}
else glGetProgramiv_(obj, GL_INFO_LOG_LENGTH, &length);
if(length > 1) {
conoutf(CON_ERROR, "GLSL ERROR (%s:%s)", type == GL_VERTEX_SHADER ? "VS" : (type == GL_FRAGMENT_SHADER ? "FS" : "PROG"), name);
- FILE *l = getlogfile();
+ FILE *l = stdout;
if(l) {
GLchar *log = new GLchar[length];
if(type) glGetShaderInfoLog_(obj, length, &length, log);
return e;
}
-
#define TEXTCOMMAND(f, s, d, body) ICOMMAND(f, s, d,\
editor *top = currentfocus();\
if(!top || identflags&IDF_OVERRIDDEN) return;\
char *entname(entity &e) {
static string fullentname;
copystring(fullentname, entities::entname(e.type));
- const char *einfo = entities::entnameinfo(e);
- if(*einfo) {
- concatstring(fullentname, ": ");
- concatstring(fullentname, einfo);
- }
return fullentname;
}
if(u) addundo(u);
}
-void detachentity(extentity &e) {
- if(!e.attached) return;
- e.attached->attached = NULL;
- e.attached = NULL;
-}
-
-VAR(attachradius, 1, 100, 1000);
-
-void attachentity(extentity &e) {
- switch(e.type) {
- case ET_SPOTLIGHT:
- break;
- default:
- if(e.type<ET_GAMESPECIFIC || !entities::mayattach(e)) return;
- break;
- }
- detachentity(e);
- vector<extentity *> &ents = entities::getents();
- int closest = -1;
- float closedist = 1e10f;
- loopv(ents) {
- extentity *a = ents[i];
- if(a->attached) continue;
- switch(e.type) {
- case ET_SPOTLIGHT:
- if(a->type!=ET_LIGHT) continue;
- break;
- default:
- if(e.type<ET_GAMESPECIFIC || !entities::attachent(e, *a)) continue;
- break;
- }
- float dist = e.o.dist(a->o);
- if(dist < closedist) {
- closest = i;
- closedist = dist;
- }
- }
- if(closedist>attachradius) return;
- e.attached = ents[closest];
- ents[closest]->attached = &e;
-}
-
-void attachentities() {
- vector<extentity *> &ents = entities::getents();
- loopv(ents) attachentity(*ents[i]);
-}
-
// convenience macros implicitly define:
// e entity, currently edited ent
// n int, index to currently edited ent
#define addimplicit(f) { if(entgroup.empty() && enthover>=0) { entadd(enthover); undonext = (enthover != oldhover); f; entgroup.drop(); } else f; }
-#define entfocusv(i, f, v){ int n = efocus = (i); if(n>=0) { extentity &e = *v[n]; f; } }
+#define entfocusv(i, f, v){ int n = efocus = (i); if(n>=0) { extentity &e = *v[n]; f; (void) e; } }
#define entfocus(i, f) entfocusv(i, f, entities::getents())
-#define enteditv(i, f, v) { \
- \
- entfocusv(i, { \
- \
- int oldtype = e.type; \
- removeentity(n); \
- f; \
- if(oldtype!=e.type) detachentity(e); \
- if(e.type!=ET_EMPTY) { addentity(n); if(oldtype!=e.type) attachentity(e); } \
- entities::editent(n, true); \
- }, v); \
-}
+#define enteditv(i, f, v) { entfocusv(i, { int a = 0; (void) a; }, v); }
#define entedit(i, f) enteditv(i, f, entities::getents())
#define addgroup(exp) { vector<extentity *> &ents = entities::getents(); loopv(ents) entfocusv(i, if(exp) entadd(n), ents); }
#define setgroup(exp) { entcancel(); addgroup(exp); }
loopk(3) renderentring(e, radius, k);
}
-void renderentattachment(const extentity &e) {
- if(!e.attached) return;
- gle::defvertex();
- gle::begin(GL_LINES);
- gle::attrib(e.o);
- gle::attrib(e.attached->o);
- xtraverts += gle::end();
-}
-
void renderentarrow(const extentity &e, const vec &dir, float radius) {
if(radius <= 0) return;
float arrowsize = min(radius/8, 0.5f);
if(color) gle::colorf(e.attr2/255.0f, e.attr3/255.0f, e.attr4/255.0f);
renderentsphere(e, e.attr1);
break;
- case ET_SPOTLIGHT:
- if(e.attached) {
- if(color) gle::colorf(0, 1, 1);
- float radius = e.attached->attr1;
- if(!radius) radius = 2*e.o.dist(e.attached->o);
- vec dir = vec(e.o).sub(e.attached->o).normalize();
- float angle = clamp(int(e.attr1), 1, 89);
- renderentattachment(e);
- renderentcone(*e.attached, dir, radius, angle);
- }
- break;
case ET_SOUND:
if(color) gle::colorf(0, 1, 1);
renderentsphere(e, e.attr2);
case ET_MAPMODEL:
case ET_PLAYERSTART: {
if(color) gle::colorf(0, 1, 1);
- entities::entradius(e, color);
+ entities::entradius(e);
vec dir;
vecfromyawpitch(e.attr1, 0, 1, 0, dir);
renderentarrow(e, dir, 4);
default:
if(e.type>=ET_GAMESPECIFIC) {
if(color) gle::colorf(0, 1, 1);
- entities::entradius(e, color);
+ entities::entradius(e);
}
break;
}
}
switch(drop) {
case 1:
- if(e.type != ET_LIGHT && e.type != ET_SPOTLIGHT)
- dropenttofloor(&e);
+ dropenttofloor(&e);
break;
case 2:
case 3:
groupedit(dropentity(e));
}
-void attachent() {
- if(noentedit()) return;
- groupedit(attachentity(e));
-}
-
-COMMAND(attachent, "");
-
VARP(entcamdir, 0, 1, 1);
static int keepents = 0;
if(noentedit()) return;
int type = findtype(what);
if(type != ET_EMPTY)
- groupedit(e.type=type;
- e.attr1=*a1;
- e.attr2=*a2;
- e.attr3=*a3;
- e.attr4=*a4;
- e.attr5=*a5);
-}
-
-void printent(extentity &e, char *buf, int len) {
- switch(e.type) {
- case ET_PARTICLES:
- if(printparticles(e, buf, len)) return;
- break;
- default:
- if(e.type >= ET_GAMESPECIFIC && entities::printent(e, buf, len)) return;
- break;
- }
- nformatstring(buf, len, "%s %d %d %d %d %d", entities::entname(e.type), e.attr1, e.attr2, e.attr3, e.attr4, e.attr5);
+ groupedit(e.type=type; e.attr1=*a1; e.attr2=*a2; e.attr3=*a3; e.attr4=*a4; e.attr5=*a5);
}
void nearestent() {
ICOMMAND(entselect, "e", (uint *body), if(!noentedit()) addgroup(e.type != ET_EMPTY && entgroup.find(n)<0 && executebool(body)));
ICOMMAND(entloop, "e", (uint *body), if(!noentedit()) addimplicit(groupeditloop(((void)e, execute(body)))));
ICOMMAND(insel, "", (), entfocus(efocus, intret(pointinsel(sel, e.o))));
-ICOMMAND(entget, "", (), entfocus(efocus, string s; printent(e, s, sizeof(s)); result(s)));
ICOMMAND(entindex, "", (), intret(efocus));
COMMAND(entset, "siiiii");
COMMAND(nearestent, "");
extentity *e = newentity(local, o, type, attr1, attr2, attr3, attr4, attr5, i);
if(!e) return;
addentity(i);
- attachentity(*e);
- }
- else {
- extentity &e = *ents[i];
- removeentity(i);
- int oldtype = e.type;
- if(oldtype!=type) detachentity(e);
- e.type = type;
- e.o = o;
- e.attr1 = attr1; e.attr2 = attr2; e.attr3 = attr3; e.attr4 = attr4; e.attr5 = attr5;
- addentity(i);
- if(oldtype!=type) attachentity(e);
}
entities::editent(i, local);
}
break;
}
});
- f->putchar((int)strlen(game::gameident()));
- f->write(game::gameident(), (int)strlen(game::gameident())+1);
f->putlil<ushort>(entities::extraentinfosize());
vector<char> extras;
- game::writegamedata(extras);
f->putlil<ushort>(extras.length());
f->write(extras.getbuf(), extras.length());
f->putlil<ushort>(texmru.length());
resetmap();
Texture *mapshot = textureload(picname, 3, true, false);
renderbackground("loading...", mapshot, mname, game::getmapinfo());
- game::loadingmap(cname ? cname : mname);
setvar("mapversion", hdr.version, true, false);
lilswap(&hdr.numvslots, 1);
renderprogress(0, "clearing world...");
int extrasize = f->getlil<ushort>();
vector<char> extras;
f->read(extras.pad(extrasize), extrasize);
- game::readgamedata(extras);
texmru.shrink(0);
ushort nummru = f->getlil<ushort>();
loopi(nummru) texmru.add(f->getlil<ushort>());
lilswap(&e.attr1, 5);
if(einfosize > 0) f->read(ebuf, einfosize);
if(!insideworld(e.o)) {
- if(e.type != ET_LIGHT && e.type != ET_SPOTLIGHT) {
- conoutf(CON_WARN, "warning: ent outside of world: enttype[%s] index %d (%f, %f, %f)", entities::entname(e.type), i, e.o.x, e.o.y, e.o.z);
- }
+ conoutf(CON_WARN, "warning: ent outside of world: enttype[%s] index %d (%f, %f, %f)", entities::entname(e.type), i, e.o.x, e.o.y, e.o.z);
}
}
if(ebuf) delete[] ebuf;
flushpreloadedmodels();
preloadmapsounds();
entitiesinoctanodes();
- attachentities();
initlights();
allchanged(true);
renderbackground("loading...", mapshot, mname, game::getmapinfo());
extern void render();
}
-
#ifndef STANDALONE
vector<extentity *> ents;
vector<extentity *> &getents() { return ents; }
- bool mayattach(extentity &e) { return false; }
- bool attachent(extentity &e, extentity &a) { return false; }
const char *itemname(int i) {
int t = ents[i]->type;
if(t<I_SHELLS || t>I_QUAD) return NULL;
void fixentity(extentity &e) {
if(e.type == TELEDEST) e.attr3 = e.attr2;
}
- void entradius(extentity &e, bool color) {
+ void entradius(extentity &e) {
switch(e.type) {
case TELEDEST: {
vec dir;
default: break;
}
}
- bool printent(extentity &e, char *buf, int len) {
- return false;
- }
- const char *entnameinfo(entity &e) { return ""; }
const char *entname(int i) {
static const char * const entnames[] = {
- "none?", "light", "mapmodel", "playerstart", "none?", "particles", "sound", "spotlight",
+ "none?", "light", "mapmodel", "playerstart", "none?", "particles", "sound",
"shells", "bullets", "rockets", "riflerounds", "grenades", "cartridges",
"health", "healthboost", "tinyhealth", "tinyarmour", "greenarmour", "yellowarmour", "quaddamage",
"teleport", "teledest",
extentity &e = *ents[i];
if(local) addmsg(N_EDITENT, "rii3ii5", i, (int)(e.o.x*DMF), (int)(e.o.y*DMF), (int)(e.o.z*DMF), e.type, e.attr1, e.attr2, e.attr3, e.attr4, e.attr5);
}
-
#endif
}
-
fpsent *player1 = NULL; // our client
vector<fpsent *> players; // other clients
int savedammo[NUMGUNS];
- bool clientoption(const char *arg) { return false; }
void taunt() {
if(player1->state!=CS_ALIVE || player1->physstate<PHYS_SLOPE) return;
if(lastmillis-player1->lasttaunt<1000) return;
lasthit = 0;
execident("mapstart");
}
- void loadingmap(const char *name) {
- execident("playsong");
- }
void startmap(const char *name) { // called just after a map load {
pwreset();
ai::savewaypoints();
const char *getscreenshotinfo() {
return server::modename(gamemode, NULL);
}
- void physicstrigger(physent *d, bool local, int floorlevel, int material) {
+ void physicstrigger(physent *d, int floorlevel) {
if(d->type==ENT_INANIMATE) return;
- if (floorlevel>0) { if(d==player1 || d->type!=ENT_PLAYER || ((fpsent *)d)->ai) msgsound(S_JUMP, d); }
+ if (floorlevel>0) { if(d==player1 || d->type!=ENT_PLAYER || ((fpsent *)d)->ai) msgsound(S_JUMP, d); }
else if(floorlevel<0) { if(d==player1 || d->type!=ENT_PLAYER || ((fpsent *)d)->ai) msgsound(S_LAND, d); }
}
- void dynentcollide(physent *d, physent *o, const vec &dir) {
- return;
- }
void msgsound(int n, physent *d) {
if(!d || d==player1) {
addmsg(N_SOUND, "ci", d, n);
gle::end();
}
float abovegameplayhud(int w, int h) {
+ (void)w;(void)h;
switch(hudplayer()->state) {
case CS_EDITING:
case CS_SPECTATOR:
pophudmatrix();
}
}
- int clipconsole(int w, int h) {
- return 0;
- }
VARP(teamcrosshair, 0, 1, 1);
VARP(hitcrosshair, 0, 425, 1000);
const char *defaultcrosshair(int index) {
if(d->gunwait) color.mul(0.5f);
return crosshair;
}
- void lighteffects(dynent *e, vec &color, vec &dir) {
-#if 0
- fpsent *d = (fpsent *)e;
- if(d->state!=CS_DEAD && d->quadmillis) {
- float t = 0.5f + 0.5f*sinf(2*M_PI*lastmillis/1000.0f);
- color.y = color.y*(1-t) + t;
- }
-#endif
- }
int maxsoundradius(int n) {
switch(n) {
case S_JUMP:
return false;
}
// any data written into this vector will get saved with the map data. Must take care to do own versioning, and endianess if applicable. Will not get called when loading maps from other games, so provide defaults.
- void writegamedata(vector<char> &extras) {}
- void readgamedata(vector<char> &extras) {}
const char *savedconfig() { return "config.cfg"; }
const char *restoreconfig() { return "restore.cfg"; }
const char *defaultconfig() { return "data/defaults.cfg"; }
PLAYERSTART, // attr1 = angle, attr2 = team
PARTICLES = ET_PARTICLES,
MAPSOUND = ET_SOUND,
- SPOTLIGHT = ET_SPOTLIGHT,
I_SHELLS, I_BULLETS, I_ROCKETS, I_ROUNDS, I_GRENADES, I_CARTRIDGES,
I_HEALTH, I_BOOST,
/**/I_TINYHEALTH, I_TINYARMOUR,
extern int respawnent;
extern int following;
extern int smoothmove, smoothdist;
- extern bool clientoption(const char *arg);
extern fpsent *getclient(int cn);
extern fpsent *newclient(int cn);
extern const char *colorname(fpsent *d, const char *name = NULL, const char *prefix = "", const char *suffix = "", const char *alt = NULL);
extern void forcegamespeed(int speed);
extern void hashpassword(int cn, int sessionid, const char *pwd, char *result, int maxlen = MAXSTRLEN);
extern int msgsizelookup(int msg);
- extern bool serveroption(const char *arg);
extern bool delayspawn(int type);
}
return color;
}
void renderscoreboard(g3d_gui &g, bool firstpass) {
+ (void) firstpass;
const ENetAddress *address = connectedpeer();
if(showservinfo && address) {
string hostname;
#include "game.h"
-namespace game {
- void parseoptions(vector<const char *> &args) {
- loopv(args)
-#ifndef STANDALONE
- if(!game::clientoption(args[i]))
-#endif
- if(!server::serveroption(args[i]))
- conoutf(CON_ERROR, "unknown command-line option: %s", args[i]);
- }
- const char *gameident() { return "fps"; }
-}
-
VAR(regenbluearmour, 0, 1, 1);
extern ENetAddress masteraddress;
sents.setsize(0);
//cps.reset();
}
- bool serveroption(const char *arg) {
- if(arg[0]=='-') switch(arg[1]) {
- case 'n': setsvar("serverdesc", &arg[2]); return true;
- case 'y': setsvar("serverpass", &arg[2]); return true;
- case 'p': setsvar("adminpass", &arg[2]); return true;
- case 'o': setvar("publicserver", atoi(&arg[2])); return true;
- }
- return false;
- }
void serverinit() {
smapname[0] = '\0';
resetitems();
// ET_*: the only static entity types dictated by the engine... rest are gamecode dependent
-enum { ET_EMPTY=0, ET_LIGHT, ET_MAPMODEL, ET_PLAYERSTART, ET_PARTICLES, ET_SOUND, ET_SPOTLIGHT, ET_GAMESPECIFIC };
+enum { ET_EMPTY=0, ET_LIGHT, ET_MAPMODEL, ET_PLAYERSTART, ET_PARTICLES, ET_SOUND, ET_GAMESPECIFIC };
// persistent map entity
struct entity {
struct extentity : entity {
int flags; // the only dynamic state of a map entity
entitylight light;
- extentity *attached;
- extentity() : flags(0), attached(NULL) {}
+ extentity() : flags(0) {}
bool spawned() const { return (flags&EF_SPAWNED) != 0; }
void setspawned(bool val) { if(val) flags |= EF_SPAWNED; else flags &= ~EF_SPAWNED; }
void setspawned() { flags |= EF_SPAWNED; }
vec2(0.99452190, -0.10452846), vec2(0.99619470, -0.08715574), vec2(0.99756405, -0.06975647), vec2(0.99862953, -0.05233596), vec2(0.99939083, -0.03489950), vec2(0.99984770, -0.01745241), // 714
vec2(1.00000000, 0.00000000) // 720
};
-
extern void conoutf(int type, int tag, const char *s, ...) PRINTFARGS(3, 4);
extern void conoutfv(int type, const char *fmt, va_list args);
-extern FILE *getlogfile();
-extern void setlogfile(const char *fname);
-extern void closelogfile();
extern void logoutfv(const char *fmt, va_list args);
extern void logoutf(const char *fmt, ...) PRINTFARGS(1, 2);
extern int getmapversion();
extern void renderentcone(const extentity &e, const vec &dir, float radius, float angle);
extern void renderentarrow(const extentity &e, const vec &dir, float radius);
-extern void renderentattachment(const extentity &e);
extern void renderentsphere(const extentity &e, float radius);
extern void renderentring(const extentity &e, float radius, int axis = 0);
namespace entities {
extern void editent(int i, bool local);
- extern const char *entnameinfo(entity &e);
extern const char *entname(int i);
extern int extraentinfosize();
extern void fixentity(extentity &e);
- extern void entradius(extentity &e, bool color);
- extern bool mayattach(extentity &e);
- extern bool attachent(extentity &e, extentity &a);
- extern bool printent(extentity &e, char *buf, int len);
+ extern void entradius(extentity &e);
extern extentity *newentity();
extern void deleteentity(extentity *e);
extern void clearents();
}
namespace game {
- extern void parseoptions(vector<const char *> &args);
extern void gamedisconnect(bool cleanup);
extern void parsepacketclient(int chan, packetbuf &p);
extern void connectattempt(const char *name, const char *password, const ENetAddress &address);
extern bool ispaused();
extern int scaletime(int t);
extern bool allowmouselook();
- extern const char *gameident();
extern const char *savedconfig();
extern const char *restoreconfig();
extern const char *defaultconfig();
extern void loadconfigs();
extern void updateworld();
extern void initclient();
- extern void physicstrigger(physent *d, bool local, int floorlevel, int material = 0);
+ extern void physicstrigger(physent *d, int floorlevel);
extern void bounced(physent *d, const vec &surface);
extern void edittrigger(const selinfo &sel, int op, int arg1 = 0, int arg2 = 0, int arg3 = 0, const VSlot *vs = NULL);
extern void vartrigger(ident *id);
- extern void dynentcollide(physent *d, physent *o, const vec &dir);
extern const char *getclientmap();
extern const char *getmapinfo();
extern const char *getscreenshotinfo();
extern void suicide(physent *d);
extern float ratespawn(dynent *d, const extentity &e);
extern void newmap(int size);
- extern void loadingmap(const char *name);
extern void startmap(const char *name);
extern void preload();
extern float abovegameplayhud(int w, int h);
extern void rendergame(bool mainpass);
extern void renderavatar();
extern void renderplayerpreview(int model, int team, int weap);
- extern void writegamedata(vector<char> &extras);
- extern void readgamedata(vector<char> &extras);
- extern int clipconsole(int w, int h);
extern void g3d_gamemenus();
extern const char *defaultcrosshair(int index);
extern int selectcrosshair(vec &color);
- extern void lighteffects(dynent *d, vec &color, vec &dir);
extern void setupcamera();
extern bool allowthirdperson(bool msg = false);
extern bool detachcamera();
#include <sys/types.h>
#include <dirent.h>
-string homedir = "";
struct packagedir {
char *dir, *filter;
size_t dirlen, filterlen;
return tmp;
}
-
char *path(char *s) {
for(char *curpart = s;;) {
char *endpart = strchr(curpart, '&');
return mkdir(path, 0777)==0;
}
-size_t fixpackagedir(char *dir) {
- path(dir);
- size_t len = strlen(dir);
- if(len > 0 && dir[len-1] != PATHDIV) {
- dir[len] = PATHDIV;
- dir[len+1] = '\0';
- }
- return len;
-}
-
-bool subhomedir(char *dst, int len, const char *src) {
- const char *sub = strstr(src, "$HOME");
- if(!sub) sub = strchr(src, '~');
- if(sub && sub-src < len) {
- const char *home = getenv("HOME");
- if(!home || !home[0]) return false;
- dst[sub-src] = '\0';
- concatstring(dst, home, len);
- concatstring(dst, sub+(*sub == '~' ? 1 : strlen("$HOME")), len);
- }
- return true;
-}
-
-const char *sethomedir(const char *dir) {
- string pdir;
- copystring(pdir, dir);
- if(!subhomedir(pdir, sizeof(pdir), dir) || !fixpackagedir(pdir)) return NULL;
- copystring(homedir, pdir);
- return homedir;
-}
-
-const char *addpackagedir(const char *dir) {
- string pdir;
- copystring(pdir, dir);
- if(!subhomedir(pdir, sizeof(pdir), dir) || !fixpackagedir(pdir)) return NULL;
- char *filter = pdir;
- for(;;) {
- static int len = strlen("packages");
- filter = strstr(filter, "packages");
- if(!filter) break;
- if(filter > pdir && filter[-1] == PATHDIV && filter[len] == PATHDIV) break;
- filter += len;
- }
- packagedir &pf = packagedirs.add();
- pf.dir = filter ? newstring(pdir, filter-pdir) : newstring(pdir);
- pf.dirlen = filter ? filter-pdir : strlen(pdir);
- pf.filter = filter ? newstring(filter) : NULL;
- pf.filterlen = filter ? strlen(filter) : 0;
- return pf.dir;
-}
-
const char *findfile(const char *filename, const char *mode) {
static string s;
- if(homedir[0]) {
- formatstring(s, "%s%s", homedir, filename);
- if(fileexists(s, mode)) return s;
- if(mode[0]=='w' || mode[0]=='a') {
- string dirs;
- copystring(dirs, s);
- char *dir = strchr(dirs[0]==PATHDIV ? dirs+1 : dirs, PATHDIV);
- while(dir) {
- *dir = '\0';
- if(!fileexists(dirs, "d") && !createdir(dirs)) return s;
- *dir = PATHDIV;
- dir = strchr(dir+1, PATHDIV);
- }
- return s;
- }
- }
if(mode[0]=='w' || mode[0]=='a') return filename;
loopv(packagedirs) {
packagedir &pf = packagedirs[i];
int dirs = 0;
if(listdir(dirname, true, ext, files)) dirs++;
string s;
- if(homedir[0]) {
- formatstring(s, "%s%s", homedir, dirname);
- if(listdir(s, false, ext, files)) dirs++;
- }
+ formatstring(s, "%s%s", ".", dirname);
+ if(listdir(s, false, ext, files)) dirs++;
loopv(packagedirs) {
packagedir &pf = packagedirs[i];
if(pf.filter && strncmp(dirname, pf.filter, dirlen == pf.filterlen-1 ? dirlen : pf.filterlen))
extern size_t decodeutf8(uchar *dst, size_t dstlen, const uchar *src, size_t srclen, size_t *carry = NULL);
extern size_t encodeutf8(uchar *dstbuf, size_t dstlen, const uchar *srcbuf, size_t srclen, size_t *carry = NULL);
-extern string homedir;
-
extern char *makerelpath(const char *dir, const char *file, const char *prefix = NULL, const char *cmd = NULL);
extern char *path(char *s);
extern char *path(const char *s, bool copy);
extern const char *parentdir(const char *directory);
extern bool fileexists(const char *path, const char *mode);
extern bool createdir(const char *path);
-extern size_t fixpackagedir(char *dir);
-extern const char *sethomedir(const char *dir);
-extern const char *addpackagedir(const char *dir);
extern const char *findfile(const char *filename, const char *mode);
extern bool findzipfile(const char *filename);
extern stream *openrawfile(const char *filename, const char *mode);
string mdir = "", fname;
if(mountdir) {
copystring(mdir, mountdir);
- if(fixpackagedir(mdir) <= 1) mdir[0] = '\0';
}
loopv(files) {
zipfile &f = files[i];