diff --git a/config/defaults.cfg b/config/defaults.cfg index f8aa0567..6b432e5c 100644 --- a/config/defaults.cfg +++ b/config/defaults.cfg @@ -9,18 +9,12 @@ autoreload 1 // Reload the guns automatically by default. lighterror 4 //set higher (for example 8) if you experience slowdown -// NOTE: by default the zoom script just divides your sensitivity by 2 while you use the scope +// NOTE: by default the zoom script just divides your sensitivity by 1.5 while you use the scope // if you want to set your own value for it, go to the following line and -// replace (div $sensitivity 2) by your desired sensitivity value: +// replace $scopesensscale by your desired sensitivity value: -//alias scopesens [div $sensitivity 2] -alias scopesensdiv 3 -alias scopesensmul 2 -//alias scopesens [ -// echo (concatword $scopesensmul "/" $scopesensdiv "=" (* (div $sensitivity $scopesensdiv) $scopesensmul)) -// result (* (div $sensitivity $scopesensdiv) $scopesensmul) -//] -alias scopesens [ result (* (div $sensitivity $scopesensdiv) $scopesensmul) ] +alias scopesensscale 0.666 +alias scopesens [ *f $sensitivity $scopesensscale ] //bind MOUSE2 [ zoom 1; onrelease [ zoom 0 ] ] diff --git a/config/menus_settings.cfg b/config/menus_settings.cfg index 4493c389..843b4320 100644 --- a/config/menus_settings.cfg +++ b/config/menus_settings.cfg @@ -42,51 +42,12 @@ newmenu "QUICK setup" menuitemtextinput "Nickname: " "" "name $arg1" menuitemtextinput "Resolution (Width): " "$scr_w" "scr_w $arg1" menuitemtextinput "Resolution (Height): " "$scr_h" "scr_h $arg1" -menuitem "Mouse Sensitivity" "openmousemenu" +menuitemtextinput "Mouse sensitivity " "$sensitivity" "sensitivity $arg1" menuitemslider "Graphics detail: " 1 4 "(getgfxq)" 1 [Low Medium Good "Best (but slow)"] "new_gfx_quality $arg1" menuitemslider "Sound detail: " 1 3 "(getsoundq)" 1 "Low Medium High" "new_sound_quality $arg1" menuitem "" -1 menuitem " 2 [ OK ]" "resetgl" -openmousemenu = [ - alias mousesensmenus "10 100" - alias msmx (findlist $mousesensmenus $sensitivityscale) - if (= $msmx -1) [showmenu "mouse sensitivity odd"] [showmenu (concat mouse sensitivity $sensitivityscale)] -] - -closemousemenu = [ - closemenu "mouse sensitivity 10" - closemenu "mouse sensitivity 100" - closemenu "mouse sensitivity odd" -] - -//closemousemenu = [closemenu (concat mouse sensitivity $sensitivityscale)] -togglemousemenu = [ - closemousemenu - openmousemenu -] - -newmenu "mouse sensitivity odd" -menuitemtextinput "MouseSens: " "($sensitivity)" [sensitivity $arg1;togglemousemenu] -menuitemtextinput "SensScale: " "($sensitivityscale)" [sensitivityscale $arg1;togglemousemenu] -menuitemtextinput "ZoomSens MULby: " "($scopesensmul)" [alias scopesensmul $arg1;togglemousemenu] -menuitemtextinput "ZoomSens DIVby: " "($scopesensdiv)" [alias scopesensdiv $arg1;togglemousemenu] -menuitemtextinput "ZoomSens Value: " "(scopesens)" [echo "read only - use the input-fields for MUL and DIV"] - -newmenu "mouse sensitivity 10" -menuitemslider "Mouse sensitivity: " 2 150 "($sensitivity)" 2 "" "sensitivity $arg1" -menuitemslider "Mouse sensscale: " 10 100 "($sensitivityscale)" 90 "" [sensitivityscale $arg1;if (= $sensitivityscale 10) [sensitivity 30] [sensitivity 300];togglemousemenu] -menuitemslider "ZoomSens MULby: " 1 6 "($scopesensmul)" 1 "" [alias scopesensmul $arg1;togglemousemenu] -menuitemslider "ZoomSens DIVby: " 1 6 "($scopesensdiv)" 1 "" [alias scopesensdiv $arg1;togglemousemenu] -menuitemtextinput "ZoomSens Value: " "(scopesens)" [echo "read only - use the sliders"] - -newmenu "mouse sensitivity 100" -menuitemslider "Mouse sensitivity: " 20 1500 "($sensitivity)" 5 "" "sensitivity $arg1" -menuitemslider "Mouse sensscale: " 10 100 "($sensitivityscale)" 90 "" [sensitivityscale $arg1;if (= $sensitivityscale 10) [sensitivity 30] [sensitivity 300];togglemousemenu] -menuitemslider "ZoomSens MULby: " 1 6 "($scopesensmul)" 1 "" [alias scopesensmul $arg1;togglemousemenu] -menuitemslider "ZoomSens DIVby: " 1 6 "($scopesensdiv)" 1 "" [alias scopesensdiv $arg1;togglemousemenu] -menuitemtextinput "ZoomSens Value: " "(scopesens)" [echo "read only - use the sliders"] - alias getgfxq [ if (= $minlod 200) [ result 4 ] [ if (= $minlod 100) [ result 3 ] [ @@ -237,8 +198,7 @@ menuitemkeyinput "Map overview: " toggleshowmap menuitemkeyinput "Drop CTF flag: " dropflag menuitem "" -1 menuitemcheckbox "Invert mouse: " "$invmouse" "invmouse $arg1" -//menuitemslider "Mouse sensitivity: " 3 150 "($sensitivity)" 3 "" "sensitivity $arg1" -menuitem "Mouse sensitivity" "openmousemenu" +menuitemtextinput "Mouse sensitivity " "$sensitivity" "sensitivity $arg1" menuitem "" -1 menuitem "Reset keybinds to default settings..." [ showmenu "Reset Binds" ] diff --git a/source/src/command.cpp b/source/src/command.cpp index ec12ea2a..06251c35 100644 --- a/source/src/command.cpp +++ b/source/src/command.cpp @@ -128,10 +128,10 @@ int variable(const char *name, int minval, int cur, int maxval, int *storage, vo return cur; } -float fvariable(const char *name, float cur, float *storage, void (*fun)(), bool persist) +float fvariable(const char *name, float minval, float cur, float maxval, float *storage, void (*fun)(), bool persist) { if(!idents) idents = new hashtable; - ident v(ID_FVAR, name, storage, fun, persist, IEXC_CORE); + ident v(ID_FVAR, name, minval, maxval, storage, fun, persist, IEXC_CORE); idents->access(name, v); return cur; } @@ -157,7 +157,7 @@ void setvar(const char *name, int i, bool dofunc) void setfvar(const char *name, float f, bool dofunc) { _GETVAR(id, ID_FVAR, name, ); - *id->storage.f = f; + *id->storage.f = clamp(f, id->minvalf, id->maxvalf); if(dofunc && id->fun) ((void (__cdecl *)())id->fun)(); // call trigger function if available } void setsvar(const char *name, const char *str, bool dofunc) @@ -215,7 +215,7 @@ char *lookup(char *n) // find value of ident reference if(id) switch(id->type) { case ID_VAR: { string t; itoa(t, *id->storage.i); return exchangestr(n, t); } - case ID_FVAR: { s_sprintfd(t)("%f", *id->storage.f); return exchangestr(n, t); } + case ID_FVAR: return exchangestr(n, floatstr(*id->storage.f)); case ID_SVAR: return exchangestr(n, *id->storage.s); case ID_ALIAS: return exchangestr(n, id->action); } @@ -275,6 +275,18 @@ void intret(int v) commandret = newstring(t); } +const char *floatstr(float v) +{ + static string t; + ftoa(t, v); + return t; +} + +void floatret(float v) +{ + commandret = newstring(floatstr(v)); +} + void result(const char *s) { commandret = newstring(s); } char *executeret(const char *p) // all evaluation happens here, recursively @@ -352,9 +364,12 @@ char *executeret(const char *p) // all evaluation hap case ARG_DOWN: ((void (__cdecl *)(bool))id->fun)(addreleaseaction(id->name)!=NULL); break; case ARG_1EXP: intret(((int (__cdecl *)(int))id->fun)(ATOI(w[1]))); break; case ARG_2EXP: intret(((int (__cdecl *)(int, int))id->fun)(ATOI(w[1]), ATOI(w[2]))); break; + case ARG_1EXPF: floatret(((float (__cdecl *)(float))id->fun)(atof(w[1]))); break; + case ARG_2EXPF: floatret(((float (__cdecl *)(float, float))id->fun)(atof(w[1]), atof(w[2]))); break; case ARG_1EST: intret(((int (__cdecl *)(char *))id->fun)(w[1])); break; case ARG_2EST: intret(((int (__cdecl *)(char *, char *))id->fun)(w[1], w[2])); break; case ARG_IVAL: intret(((int (__cdecl *)())id->fun)()); break; + case ARG_FVAL: floatret(((float (__cdecl *)())id->fun)()); break; case ARG_SVAL: result(((const char * (__cdecl *)())id->fun)()); break; case ARG_VARI: ((void (__cdecl *)(char **, int))id->fun)(&w[1], numargs-1); break; case ARG_CONC: @@ -387,10 +402,17 @@ char *executeret(const char *p) // all evaluation hap break; case ID_FVAR: // game defined variables - if(!w[1][0]) conoutf("%s = %f", c, *id->storage.f); // var with no value just prints its current value + if(!w[1][0]) conoutf("%s = %s", c, floatstr(*id->storage.f)); // var with no value just prints its current value + else if(id->minvalf>id->maxvalf) conoutf("variable %s is read-only", id->name); else { - *id->storage.f = atof(w[1]); + float f1 = atof(w[1]); + if(f1minvalf || f1>id->maxvalf) + { + f1 = f1minvalf ? id->minvalf : id->maxvalf; // clamp to valfid range + conoutf("valid range for %s is %s..%s", id->name, floatstr(id->minvalf), floatstr(id->maxvalf)); + } + *id->storage.f = f1; if(id->fun) ((void (__cdecl *)())id->fun)(); // call trigger function if available } break; @@ -794,15 +816,26 @@ COMMAND(findlist, ARG_2STR); int add(int a, int b) { return a+b; } COMMANDN(+, add, ARG_2EXP); int mul(int a, int b) { return a*b; } COMMANDN(*, mul, ARG_2EXP); int sub(int a, int b) { return a-b; } COMMANDN(-, sub, ARG_2EXP); -int divi(int a, int b) { return b ? a/b : 0; } COMMANDN(div, divi, ARG_2EXP); -int mod(int a, int b) { return b ? a%b : 0; } COMMAND(mod, ARG_2EXP); -int nota(int a) { return (int)(!a); } COMMANDN(!, nota, ARG_1EXP); +int div_(int a, int b) { return b ? a/b : 0; } COMMANDN(div, div_, ARG_2EXP); +int mod_(int a, int b) { return b ? a%b : 0; } COMMANDN(mod, mod_, ARG_2EXP); +float addf(float a, float b) { return a+b; } COMMANDN(+f, addf, ARG_2EXPF); +float mulf(float a, float b) { return a*b; } COMMANDN(*f, mulf, ARG_2EXPF); +float subf(float a, float b) { return a-b; } COMMANDN(-f, subf, ARG_2EXPF); +float divf_(float a, float b) { return b ? a/b : 0; } COMMANDN(divf, divf_, ARG_2EXPF); +float modf_(float a, float b) { return b ? fmod(a, b) : 0; } COMMANDN(modf, modf_, ARG_2EXPF); +int not_(int a) { return (int)(!a); } COMMANDN(!, not_, ARG_1EXP); int equal(int a, int b) { return (int)(a==b); } COMMANDN(=, equal, ARG_2EXP); int notequal(int a, int b) { return (int)(a!=b); } COMMANDN(!=, notequal, ARG_2EXP); int lt(int a, int b) { return (int)(ab); } COMMANDN(>, gt, ARG_2EXP); int lte(int a, int b) { return (int)(a<=b); } COMMANDN(<=, lte, ARG_2EXP); int gte(int a, int b) { return (int)(a>=b); } COMMANDN(>=, gte, ARG_2EXP); +float equalf(float a, float b) { return (float)(a==b); } COMMANDN(=f, equalf, ARG_2EXPF); +float notequalf(float a, float b) { return (float)(a!=b); } COMMANDN(!=f, notequalf, ARG_2EXPF); +float ltf(float a, float b) { return (float)(ab); } COMMANDN(>f, gtf, ARG_2EXPF); +float ltef(float a, float b) { return (float)(a<=b); } COMMANDN(<=f, ltef, ARG_2EXPF); +float gtef(float a, float b) { return (float)(a>=b); } COMMANDN(>=f, gtef, ARG_2EXPF); void anda (char *a, char *b) { intret(execute(a)!=0 && execute(b)!=0); } void ora (char *a, char *b) { intret(execute(a)!=0 || execute(b)!=0); } @@ -831,7 +864,7 @@ void writecfg() switch(id.type) { case ID_VAR: fprintf(f, "%s %d\n", id.name, *id.storage.i); break; - case ID_FVAR: fprintf(f, "%s %f\n", id.name, *id.storage.f); break; + case ID_FVAR: fprintf(f, "%s %s\n", id.name, floatstr(*id.storage.f)); break; case ID_SVAR: fprintf(f, "%s [%s]\n", id.name, *id.storage.s); break; } ); diff --git a/source/src/command.h b/source/src/command.h index 8dc35bd1..017e746c 100644 --- a/source/src/command.h +++ b/source/src/command.h @@ -11,7 +11,16 @@ struct ident { int type; // one of ID_* above const char *name; - int minval, maxval; // ID_VAR + union + { + int minval; // ID_VAR + float minvalf; // ID_FVAR + }; + union + { + int maxval; // ID_VAR + float maxvalf; // ID_FVAR + }; union { int *i; // ID_VAR @@ -39,8 +48,8 @@ struct ident { storage.i = i; } // ID_FVAR - ident(int type, const char *name, float *f, void (*fun)(), bool persist, int context) - : type(type), name(name), minval(0), maxval(0), fun(fun), + ident(int type, const char *name, float minval, float maxval, float *f, void (*fun)(), bool persist, int context) + : type(type), name(name), minvalf(minval), maxvalf(maxval), fun(fun), narg(0), action(NULL), executing(NULL), persist(persist), context(context) { storage.f = f; } @@ -70,8 +79,9 @@ enum // function signatures for script functions, see command.cpp ARG_1STR, ARG_2STR, ARG_3STR, ARG_4STR, ARG_5STR, ARG_6STR, ARG_7STR, ARG_8STR, ARG_DOWN, ARG_1EXP, ARG_2EXP, + ARG_1EXPF, ARG_2EXPF, ARG_1EST, ARG_2EST, - ARG_IVAL, ARG_SVAL, + ARG_IVAL, ARG_FVAL, ARG_SVAL, ARG_CONC, ARG_CONCW, ARG_VARI }; @@ -89,10 +99,10 @@ enum { IEXC_CORE = 0, IEXC_CFG, IEXC_PROMPT, IEXC_MAPCFG, IEXC_NUM }; // script #define VARF(name, min, cur, max, body) void var_##name(); int name = variable(#name, min, cur, max, &name, var_##name, false); void var_##name() { body; } #define VARFP(name, min, cur, max, body) void var_##name(); int name = variable(#name, min, cur, max, &name, var_##name, true); void var_##name() { body; } -#define FVARP(name, cur) float name = fvariable(#name, cur, &name, NULL, true) -#define FVAR(name, cur) float name = fvariable(#name, cur, &name, NULL, false) -#define FVARF(name, cur, body) void var_##name(); float name = fvariable(#name, cur, &name, var_##name, false); void var_##name() { body; } -#define FVARFP(name, cur, body) void var_##name(); float name = fvariable(#name, cur, &name, var_##name, true); void var_##name() { body; } +#define FVARP(name, min, cur, max) float name = fvariable(#name, min, cur, max, &name, NULL, true) +#define FVAR(name, min, cur, max) float name = fvariable(#name, min, cur, max, &name, NULL, false) +#define FVARF(name, min, cur, max, body) void var_##name(); float name = fvariable(#name, min, cur, max, &name, var_##name, false); void var_##name() { body; } +#define FVARFP(name, min, cur, max, body) void var_##name(); float name = fvariable(#name, min, cur, max, &name, var_##name, true); void var_##name() { body; } #define SVARP(name, cur) char *name = svariable(#name, cur, &name, NULL, true) #define SVAR(name, cur) char *name = svariable(#name, cur, &name, NULL, false) diff --git a/source/src/docs.cpp b/source/src/docs.cpp index 021820a2..d99f3af6 100644 --- a/source/src/docs.cpp +++ b/source/src/docs.cpp @@ -242,21 +242,26 @@ void docwritebaseref(char *ref, char *schemalocation, char *transformation) fprintf(f, "\t\t
\n"); fprintf(f, "\t\t\t%s\n", desc); fprintf(f, "\t\t\t\n"); - + + static const int bases[] = { ARG_1INT, ARG_1STR, ARG_1EXP, ARG_1EXPF, ARG_1EST }; string name; enumerate(*idents, ident, id, { if(id.type != ID_COMMAND) continue; fprintf(f, "\t\t\t\t\n", xmlstringenc(name, id.name, _MAXDEFSTR)); fprintf(f, "\t\t\t\t\t%s\n", desc); - if(id.narg != ARG_NONE && id.narg != ARG_DOWN && id.narg != ARG_IVAL && id.narg != ARG_SVAL) + if(id.narg != ARG_NONE && id.narg != ARG_DOWN && id.narg != ARG_IVAL && id.narg != ARG_FVAL && id.narg != ARG_SVAL) { fprintf(f, "\t\t\t\t\t\n"); if(id.narg == ARG_CONC || id.narg == ARG_CONCW || id.narg == ARG_VARI) fprintf(f, "\t\t\t\t\t\t\n"); else { - int base = id.narg >= ARG_1EST ? ARG_1EST : (id.narg >= ARG_1EXP ? ARG_1EXP : (id.narg >= ARG_1STR ? ARG_1STR : ARG_1INT)); - loopj(id.narg-base+1) fprintf(f, "\t\t\t\t\t\t\n", (char)(*"A")+j); + int base = -1; + loopj(sizeof(bases)/sizeof(bases[0])) + { + if(id.narg < bases[j]) { if(j) base = bases[j-1]; break; } + } + if(base >= 0) loopj(id.narg-base+1) fprintf(f, "\t\t\t\t\t\t\n", (char)(*"A")+j); } fprintf(f, "\t\t\t\t\t\n"); } @@ -264,10 +269,20 @@ void docwritebaseref(char *ref, char *schemalocation, char *transformation) }); enumerate(*idents, ident, id, { - if(id.type != ID_VAR) continue; + if(id.type != ID_VAR && id.type != ID_FVAR) continue; fprintf(f, "\t\t\t\t\n", xmlstringenc(name, id.name, _MAXDEFSTR)); fprintf(f, "\t\t\t\t\tTODO\n"); - fprintf(f, "\t\t\t\t\t\n", id.minval>id.maxval ? "" : "token=\"N\"", id.minval, id.maxval, *id.storage.i, id.minval>id.maxval ? "readOnly=\"true\"" : ""); + switch(id.type) + { + case ID_VAR: + fprintf(f, "\t\t\t\t\t\n", id.minval>id.maxval ? "" : "token=\"N\"", id.minval, id.maxval, *id.storage.i, id.minval>id.maxval ? "readOnly=\"true\"" : ""); + break; + case ID_FVAR: + fprintf(f, "\t\t\t\t\t\n", id.minvalf>id.maxvalf ? "" : "token=\"N\"", + floatstr(id.minvalf), floatstr(id.maxvalf), floatstr(*id.storage.f), + id.minvalf>id.maxvalf ? "readOnly=\"true\"" : ""); + break; + } fprintf(f, "\t\t\t\t\n"); }); diff --git a/source/src/physics.cpp b/source/src/physics.cpp index 666e31bf..5df4bd97 100644 --- a/source/src/physics.cpp +++ b/source/src/physics.cpp @@ -732,8 +732,7 @@ void fixcamerarange(physent *cam) while(cam->yaw>=360.0f) cam->yaw -= 360.0f; } -VARP(sensitivity, 0, 30, 10000); -VARP(sensitivityscale, 1, 10, 10000); +FVARP(sensitivity, 0.0f, 3.0f, 1000.0f); VARP(invmouse, 0, 0, 1); void mousemove(int dx, int dy) @@ -742,8 +741,8 @@ void mousemove(int dx, int dy) if(player1->isspectating() && player1->spectatemode==SM_FOLLOW1ST) return; const float SENSF = 33.0f; // try match quake sens - camera1->yaw += (dx/SENSF)*(sensitivity/(float)sensitivityscale); - camera1->pitch -= (dy/SENSF)*(sensitivity/(float)sensitivityscale)*(invmouse ? -1 : 1); + camera1->yaw += (dx/SENSF)*sensitivity; + camera1->pitch -= (dy/SENSF)*sensitivity*(invmouse ? -1 : 1); fixcamerarange(); if(camera1!=player1 && player1->spectatemode!=SM_DEATHCAM) { diff --git a/source/src/protos.h b/source/src/protos.h index 60e594d8..a2fa5a55 100644 --- a/source/src/protos.h +++ b/source/src/protos.h @@ -35,7 +35,7 @@ struct color // command extern bool persistidents; extern int variable(const char *name, int min, int cur, int max, int *storage, void (*fun)(), bool persist); -extern float fvariable(const char *name, float cur, float *storage, void (*fun)(), bool persist); +extern float fvariable(const char *name, float min, float cur, float max, float *storage, void (*fun)(), bool persist); extern char *svariable(const char *name, const char *cur, char **storage, void (*fun)(), bool persist); extern void setvar(const char *name, int i, bool dofunc = false); extern void setfvar(const char *name, float f, bool dofunc = false); @@ -46,6 +46,8 @@ extern bool addcommand(const char *name, void (*fun)(), int narg); extern int execute(const char *p); extern char *executeret(const char *p); extern void intret(int v); +extern const char *floatstr(float v); +extern void floatret(float v); extern void result(const char *s); extern void exec(const char *cfgfile); extern bool execfile(const char *cfgfile); diff --git a/source/src/rendergl.cpp b/source/src/rendergl.cpp index c00ec9c0..a147abb5 100644 --- a/source/src/rendergl.cpp +++ b/source/src/rendergl.cpp @@ -129,9 +129,9 @@ void gl_init(int w, int h, int bpp, int depth, int fsaa) camera1 = player1; } -FVAR(polygonoffsetfactor, -3.0f); -FVAR(polygonoffsetunits, -3.0f); -FVAR(depthoffset, 0.005f); +FVAR(polygonoffsetfactor, -1e4f, -3.0f, 1e4f); +FVAR(polygonoffsetunits, -1e4f, -3.0f, 1e4f); +FVAR(depthoffset, -1e4f, 0.005f, 1e4f); void enablepolygonoffset(GLenum type) { diff --git a/source/src/tools.h b/source/src/tools.h index 15f335ea..3d2f4994 100644 --- a/source/src/tools.h +++ b/source/src/tools.h @@ -500,6 +500,7 @@ template struct hashtable }; #define itoa(s, i) sprintf(s, "%d", i) +#define ftoa(s, f) sprintf(s, (f) == int(f) ? "%.1f" : "%.7g", f) #define enumeratekt(ht,k,e,t,f,b) loopi((ht).size) for(hashtable::chain *enumc = (ht).table[i]; enumc;) { hashtable::const_key &e = enumc->key; t &f = enumc->data; enumc = enumc->next; b; } #define enumerate(ht,t,e,b) loopi((ht).size) for((ht).enumc = (ht).table[i]; (ht).enumc;) { t &e = (ht).enumc->data; (ht).enumc = (ht).enumc->next; b; }