diff --git a/engine/client/cl_input.c b/engine/client/cl_input.c index e007b7a4e..3218704cd 100644 --- a/engine/client/cl_input.c +++ b/engine/client/cl_input.c @@ -1326,22 +1326,46 @@ Send the intended movement message to the server */ static void CL_BaseMove (vec3_t moves, int pnum) { - float scale; + float fwdspeed = cl_forwardspeed.value; + float sidespeed = cl_sidespeed.value; + float backspeed = (*cl_backspeed.string?cl_backspeed.value:cl_forwardspeed.value); + float upspeed = (*cl_backspeed.string?cl_backspeed.value:cl_forwardspeed.value); + float scale = 1; // // adjust for speed key // - scale = ((in_speed.state[pnum] & 1) ^ cl_run.ival)?cl_movespeedkey.value:1; +#ifdef HEXEN2 + extern qboolean sbar_hexen2; + if (sbar_hexen2) + { //hexen2 is a bit different. forwardspeed is treated as something of a boolean and we need to be able to cope with the boots-of-speed without forcing it always. not really sure why that's clientside instead of serverside, but oh well. evilness. + scale = cl.playerview[pnum].statsf[STAT_H2_HASTED]; + if (!scale) + scale = 1; + if (((in_speed.state[pnum] & 1) ^ (cl_run.ival || fwdspeed > 200)) + && scale <= 1) //don't go super fast with speed boots. + scale *= cl_movespeedkey.value; + fwdspeed = backspeed = 200; + sidespeed = 225; + } + else +#endif + if ((in_speed.state[pnum] & 1) ^ cl_run.ival) + scale *= cl_movespeedkey.value; moves[0] = 0; if (! (in_klook.state[pnum] & 1) ) { - moves[0] += scale*(cl_forwardspeed.value * CL_KeyState (&in_forward, pnum, true) - - (*cl_backspeed.string?cl_backspeed.value:cl_forwardspeed.value) * CL_KeyState (&in_back, pnum, true)); + moves[0] += (fwdspeed * CL_KeyState (&in_forward, pnum, true) - + backspeed * CL_KeyState (&in_back, pnum, true)); } - moves[1] = scale*cl_sidespeed.value * (CL_KeyState (&in_moveright, pnum, true) - CL_KeyState (&in_moveleft, pnum, true)) * (in_xflip.ival?-1:1); + moves[1] = sidespeed * (CL_KeyState (&in_moveright, pnum, true) - CL_KeyState (&in_moveleft, pnum, true)) * (in_xflip.ival?-1:1); if (in_strafe.state[pnum] & 1) - moves[1] += scale*cl_sidespeed.value * (CL_KeyState (&in_right, pnum, true) - CL_KeyState (&in_left, pnum, true)) * (in_xflip.ival?-1:1); - moves[2] = scale*cl_upspeed.value * (CL_KeyState (&in_up, pnum, true) - CL_KeyState (&in_down, pnum, true)); + moves[1] += sidespeed * (CL_KeyState (&in_right, pnum, true) - CL_KeyState (&in_left, pnum, true)) * (in_xflip.ival?-1:1); + moves[2] = upspeed * (CL_KeyState (&in_up, pnum, true) - CL_KeyState (&in_down, pnum, true)); + + moves[0] *= scale; + moves[1] *= scale; + moves[2] *= scale; } void CL_ClampPitch (int pnum, float frametime) diff --git a/engine/client/m_options.c b/engine/client/m_options.c index 4d92152e6..5a5a7c3b1 100644 --- a/engine/client/m_options.c +++ b/engine/client/m_options.c @@ -184,16 +184,28 @@ emenu_t *M_Options_Title(int *y, int infosize) //these are awkward/strange static qboolean M_Options_AlwaysRun (menucheck_t *option, struct emenu_s *menu, chk_set_t set) { - if (M_GameType() == MGT_QUAKE2) + extern cvar_t cl_run; + switch (M_GameType()) { - extern cvar_t cl_run; + case MGT_HEXEN2: + //hexen2 uses forwardspeed's magnitude as an 'isrunning' boolean check, with all else hardcoded. + if (set != CHK_CHECKED) + { + if (cl_forwardspeed.value > 200 || cl_run.ival) + Cvar_SetValue(&cl_forwardspeed, 200); + else + Cvar_SetValue(&cl_forwardspeed, 400); + Cvar_Set(&cl_backspeed, ""); + Cvar_SetValue(&cl_run, 0); + } + return cl_forwardspeed.value > 200; + default: + case MGT_QUAKE2: //quake2 mods have a nasty tendancy to hack at the various cvars, which breaks everything if (set != CHK_CHECKED) Cvar_SetValue(&cl_run, !cl_run.ival); return cl_run.ival; - } - else - { + case MGT_QUAKE1: //for better compat with other quake engines, we just ignore the cl_run cvar, at least for the menu. if (set == CHK_CHECKED) return cl_forwardspeed.value > 200; diff --git a/engine/common/cmd.c b/engine/common/cmd.c index 14bec520f..ba140d0b0 100644 --- a/engine/common/cmd.c +++ b/engine/common/cmd.c @@ -914,6 +914,24 @@ static void Cmd_Exec_f (void) #if defined(HAVE_LEGACY) && defined(HAVE_CLIENT) if (l == 1914 && CalcHashInt(&hash_md4, f, l) == 0x2d7b72b9) s = (char*)replacementq1binds; +#ifdef HEXEN2 + else if (l == 1875 && CalcHashInt(&hash_md4, f, l) == 0x27b4d813) + { //hexen2 has weird stuff in there. just give it wasd. + s = va( + "%s\n" + "bind w +forward\n" + "bind a +moveleft\n" + "bind s +back\n" + "bind d +moveright\n" + + "bind mouse2 +jump\n" + "bind mouse3 +forward\n" //mneh + + "bind x +lookup\n" //moved to x instead of a + "cl_forwardspeed 400\n" //hexen2's autorun state. + , s); + } +#endif #endif } #ifndef QUAKETC diff --git a/engine/common/fs.c b/engine/common/fs.c index c2e0077b5..9e8c58216 100644 --- a/engine/common/fs.c +++ b/engine/common/fs.c @@ -55,8 +55,8 @@ #define XONCFG NEXCFG "set qport $qport_\ncom_parseutf8 1\npr_fixbrokenqccarrays 2\nset pr_csqc_memsize 64m\nset pr_ssqc_memsize 96m\n" /*some modern non-compat settings*/ #define DMFCFG "set com_parseutf8 1\npm_airstep 1\nsv_demoExtensions 1\n" -/*set some stuff so our regular qw client appears more like hexen2. sv_mintic is required to 'fix' the ravenstaff so that its projectiles don't impact upon each other*/ -#define HEX2CFG "//schemes hexen2\n" "set v_gammainverted 1\nset com_parseutf8 -1\nset gl_font gfx/hexen2\nset in_builtinkeymap 0\nset_calc cl_playerclass int (random * 5) + 1\nset cl_forwardspeed 200\nset cl_backspeed 200\ncl_sidespeed 225\nset sv_maxspeed 640\ncl_run 0\nset watervis 1\nset r_lavaalpha 1\nset r_lavastyle -2\nset r_wateralpha 0.5\nset sv_pupglow 1\ngl_shaftlight 0.5\nsv_mintic 0.015\nset r_meshpitch -1\nset r_meshroll -1\nr_sprite_backfacing 1\nset mod_warnmodels 0\nset cl_model_bobbing 1\nsv_sound_watersplash \"misc/hith2o.wav\"\nsv_sound_land \"fx/thngland.wav\"\nset sv_walkpitch 0\n" +/*set some stuff so our regular qw client appears more like hexen2. sv_mintic must be 0.015 to 'fix' the ravenstaff so that its projectiles don't impact upon each other, or even 0.05 to exactly match the hardcoded assumptions in obj_push. There's maps that depend on a low framerate via waterjump framerate-dependance too.*/ +#define HEX2CFG "//schemes hexen2\n" "set v_gammainverted 1\nset com_parseutf8 -1\nset gl_font gfx/hexen2\nset in_builtinkeymap 0\nset_calc cl_playerclass int (random * 5) + 1\nset cl_forwardspeed 200\nset cl_backspeed 200\ncl_sidespeed 225\nset sv_maxspeed 640\ncl_run 0\nset watervis 1\nset r_lavaalpha 1\nset r_lavastyle -2\nset r_wateralpha 0.5\nset sv_pupglow 1\ngl_shaftlight 0.5\nsv_mintic 0.05\nset r_meshpitch -1\nset r_meshroll -1\nr_sprite_backfacing 1\nset mod_warnmodels 0\nset cl_model_bobbing 1\nsv_sound_watersplash \"misc/hith2o.wav\"\nsv_sound_land \"fx/thngland.wav\"\nset sv_walkpitch 0\n" /*yay q2!*/ #define Q2CFG "//schemes quake2\n" "set v_gammainverted 1\nset com_parseutf8 0\ncom_gamedirnativecode 1\nset sv_bigcoords 0\nsv_port "STRINGIFY(PORT_Q2SERVER)"\ncl_defaultport "STRINGIFY(PORT_Q2SERVER)"\n" /*Q3's ui doesn't like empty model/headmodel/handicap cvars, even if the gamecode copes*/