From dd662a754111bc551dbcdd6294cbba5750eb93e3 Mon Sep 17 00:00:00 2001 From: div0 Date: Tue, 21 Oct 2008 06:20:01 +0000 Subject: [PATCH] add on-hand hook weapon placable by mapper (weapon_hook) git-svn-id: svn://svn.icculus.org/nexuiz/trunk@4790 f962a42d-fe04-0410-a3ab-8c8b0445ebaa --- data/defaultNexuiz.cfg | 3 +- data/effectinfo.txt | 57 +++++++++++++ data/keybinds.txt | 2 +- data/qcsrc/common/constants.qh | 5 +- data/qcsrc/server/cl_weapons.qc | 1 + data/qcsrc/server/g_hook.qc | 12 ++- data/qcsrc/server/g_hook.qh | 2 +- data/qcsrc/server/progs.src | 1 + data/qcsrc/server/w_hook.qc | 147 ++++++++++++++++++++++++++++++++ data/weapons.cfg | 16 ++++ 10 files changed, 238 insertions(+), 8 deletions(-) create mode 100644 data/qcsrc/server/w_hook.qc diff --git a/data/defaultNexuiz.cfg b/data/defaultNexuiz.cfg index 9f8f0e82d..a2fa1e290 100644 --- a/data/defaultNexuiz.cfg +++ b/data/defaultNexuiz.cfg @@ -1111,7 +1111,7 @@ set g_jump_grunt 0 // Do you make a grunting noise every time you jump? Is it th alias allready "sv_cmd allready" -seta cl_weaponpriority "10 9 8 11 7 6 5 4 3 2 1" +seta cl_weaponpriority "10 9 8 11 7 6 5 4 3 2 1 12" seta cl_weaponpriority_useforcycling 0 // impulse 200, 210, 220: seta cl_weaponpriority0 "9 8 4" // explosives (RL Hagar Mortar) @@ -1142,6 +1142,7 @@ set g_weaponreplace_8 "" set g_weaponreplace_9 "" set g_weaponreplace_10 "" set g_weaponreplace_11 "" +set g_weaponreplace_12 "" seta sv_status_privacy 1 // hide IP addresses from "status" replies shown to clients diff --git a/data/effectinfo.txt b/data/effectinfo.txt index 6541313b3..4b3269ed8 100644 --- a/data/effectinfo.txt +++ b/data/effectinfo.txt @@ -2546,3 +2546,60 @@ originjitter 5 5 5 velocityjitter 81 81 150 color 0x7cbaff 0xcfd1ff velocitymultiplier 2 + + + +// decal +effect hookbomb_explode +countabsolute 1 +type decal +tex 8 16 +size 96 96 +alpha 256 256 0 +originjitter 40 40 40 +lightradius 1600 +lightradiusfade 800 +lightcolor 1 4 8 +// fire effect which make brigt dot inside +effect hookbomb_explode +notunderwater +count 100 +type static +tex 48 55 +color 0x003fe0 0x92dfff +size 12 32 +sizeincrease 80 +alpha 512 328 756 +bounce 1 +airfriction 8 +liquidfriction 8 +originjitter 8 8 8 +velocityjitter 1024 1024 1024 +// smoke +effect hookbomb_explode +type alphastatic +notunderwater +tex 0 8 +count 160 +size 80 160 +sizeincrease 300 +alpha 500 600 556 +velocityoffset 0 0 0 +velocityjitter 256 256 256 +airfriction 0 +color 0x000000 0x111111 +bounce 6 +// underwater bubbles +effect hookbomb_explode +underwater +count 60 +type bubble +tex 62 62 +color 0x404040 0x808080 +size 3 3 +alpha 128 256 64 +gravity -0.125 +bounce 1.5 +liquidfriction 0.0625 +originjitter 16 16 16 +velocityjitter 192 192 192 diff --git a/data/keybinds.txt b/data/keybinds.txt index 023816a3d..8e39d6146 100644 --- a/data/keybinds.txt +++ b/data/keybinds.txt @@ -5,7 +5,7 @@ "+moveright" "strafe right" "+jump" "jump / swim" "+crouch" "crouch / sink" -"+hook" "grappling hook" +"+hook" "off-hand hook" "" "" "" "Attacking" "+attack" "primary fire" diff --git a/data/qcsrc/common/constants.qh b/data/qcsrc/common/constants.qh index dba6e0763..8eb4121c2 100644 --- a/data/qcsrc/common/constants.qh +++ b/data/qcsrc/common/constants.qh @@ -309,8 +309,9 @@ float WEP_HAGAR = 8; float WEPBIT_HAGAR = 128; float WEP_ROCKET_LAUNCHER = 9; float WEPBIT_ROCKET_LAUNCHER = 256; float WEP_PORTO = 10; float WEPBIT_PORTO = 512; float WEP_MINSTANEX = 11; float WEPBIT_MINSTANEX = 1024; -float WEP_LAST = 11; float WEPBIT_ALL = 2047; -float WEP_COUNT = 12; +float WEP_HOOK = 12; float WEPBIT_HOOK = 2048; +float WEP_LAST = 12; float WEPBIT_ALL = 4095; +float WEP_COUNT = 13; float IT_UNLIMITED_AMMO = 1; // when this bit is set, using a weapon does not reduce ammo. Checkpoints can give this powerup. diff --git a/data/qcsrc/server/cl_weapons.qc b/data/qcsrc/server/cl_weapons.qc index f6815e508..e7834fb62 100644 --- a/data/qcsrc/server/cl_weapons.qc +++ b/data/qcsrc/server/cl_weapons.qc @@ -451,5 +451,6 @@ void RegisterWeapons() register_weapon(WEP_ROCKET_LAUNCHER, w_rlauncher, IT_ROCKETS, 9, 1, 10000, "rl", "rocketlauncher", "Rocket Launcher"); register_weapon(WEP_PORTO, w_porto, IT_SUPERWEAPON, 0, 0, 0, "porto" , "porto", "Port-O-Launch"); register_weapon(WEP_MINSTANEX, w_minstanex, IT_CELLS, 7, 0, 10000, "minstanex", "minstanex", "MinstaNex"); + register_weapon(WEP_HOOK, w_hook, IT_CELLS, 0, 0, 0, "hook", "hook", "Grappling Hook"); register_weapons_done(); } diff --git a/data/qcsrc/server/g_hook.qc b/data/qcsrc/server/g_hook.qc index 49c723eaa..1a5f95f94 100644 --- a/data/qcsrc/server/g_hook.qc +++ b/data/qcsrc/server/g_hook.qc @@ -387,10 +387,10 @@ void GrapplingHookFrame() // offhand hook controls if(self.BUTTON_HOOK) { - if not(self.hook || (self.hook_state & HOOK_WAITING_FOR_REFIRE)) + if not(self.hook || (self.hook_state & HOOK_WAITING_FOR_RELEASE)) { self.hook_state |= HOOK_FIRING; - self.hook_state |= HOOK_WAITING_FOR_REFIRE; + self.hook_state |= HOOK_WAITING_FOR_RELEASE; } } else @@ -398,7 +398,7 @@ void GrapplingHookFrame() if(self.hook) { self.hook_state |= HOOK_REMOVING; - self.hook_state (-) HOOK_WAITING_FOR_REFIRE; + self.hook_state (-) HOOK_WAITING_FOR_RELEASE; } } @@ -415,6 +415,12 @@ void GrapplingHookFrame() } } + if(!g_grappling_hook && self.weapon != WEP_HOOK) + { + self.hook_state (-) HOOK_FIRING; + self.hook_state |= HOOK_REMOVING; + } + if (self.hook_state & HOOK_FIRING) { if (self.hook) diff --git a/data/qcsrc/server/g_hook.qh b/data/qcsrc/server/g_hook.qh index e77598361..9c214fc6d 100644 --- a/data/qcsrc/server/g_hook.qh +++ b/data/qcsrc/server/g_hook.qh @@ -10,5 +10,5 @@ float HOOK_FIRING = 1; float HOOK_REMOVING = 2; float HOOK_PULLING = 4; float HOOK_RELEASING = 8; -float HOOK_WAITING_FOR_REFIRE = 16; +float HOOK_WAITING_FOR_RELEASE = 16; .float hook_state; diff --git a/data/qcsrc/server/progs.src b/data/qcsrc/server/progs.src index 3aec1dab3..19923da56 100644 --- a/data/qcsrc/server/progs.src +++ b/data/qcsrc/server/progs.src @@ -83,6 +83,7 @@ w_minstanex.qc w_hagar.qc w_rocketlauncher.qc w_porto.qc +w_hook.qc t_items.qc cl_weapons.qc diff --git a/data/qcsrc/server/w_hook.qc b/data/qcsrc/server/w_hook.qc new file mode 100644 index 000000000..274761214 --- /dev/null +++ b/data/qcsrc/server/w_hook.qc @@ -0,0 +1,147 @@ +void W_Hook_Explode2 (void) +{ + vector org2; + + org2 = findbetterlocation (self.origin, 12); + pointparticles(particleeffectnum("hookbomb_explode"), org2, '0 0 0', 1); + sound (self, CHAN_PROJECTILE, "weapons/hookbomb_impact.wav", VOL_BASE, ATTN_NORM); + + self.event_damage = SUB_Null; + RadiusDamage (self, self.owner, cvar("g_balance_hook_secondary_damage"), cvar("g_balance_hook_secondary_edgedamage"), cvar("g_balance_hook_secondary_radius"), world, cvar("g_balance_hook_secondary_force"), self.projectiledeathtype, other); + + remove(self); +} + +void W_Hook_Touch2 (void) +{ + if (trace_dphitq3surfaceflags & Q3SURFACEFLAG_NOIMPACT) + { + remove(self); + return; + } + self.use(); +} + +void W_Hook_Attack2() +{ + local entity gren; + + if not(self.items & IT_UNLIMITED_AMMO) + self.ammo_cells = self.ammo_cells - cvar("g_balance_hook_secondary_ammo"); + W_SetupShot (self, '25 6 -8', FALSE, 4, "weapons/hookbomb_fire.wav"); + + gren = spawn (); + gren.owner = self; + gren.classname = "hookbomb"; + gren.bot_dodge = TRUE; + gren.bot_dodgerating = cvar("g_balance_hook_secondary_damage"); + gren.movetype = MOVETYPE_TOSS; + gren.solid = SOLID_BBOX; + gren.effects = EF_LOWPRECISION; + gren.modelflags = MF_TRACER2; + gren.projectiledeathtype = WEP_HOOK | HITTYPE_SECONDARY; + setmodel(gren, "models/grenademodel.md3"); // precision set above // FIXME replace + setsize(gren, '0 0 0', '0 0 0'); + setorigin(gren, w_shotorg); + + gren.nextthink = time + cvar("g_balance_hook_secondary_lifetime"); + gren.think = adaptor_think2use; + gren.use = W_Hook_Explode2; + gren.touch = W_Hook_Touch2; + gren.velocity = '0 0 1' * cvar("g_balance_hook_secondary_speed"); + gren.gravity = cvar("g_balance_hook_secondary_gravity"); + //W_SetupProjectileVelocity(gren); // just falling down! + + gren.angles = '0 0 0'; + gren.flags = FL_PROJECTILE; +} + +void spawnfunc_weapon_hook (void) +{ + weapon_defaultspawnfunc(WEP_HOOK); +} + +float w_hook(float req) +{ + if (req == WR_AIM) + { + // ... sorry ... + } + else if (req == WR_THINK) + { + if (self.BUTTON_ATCK || self.BUTTON_HOOK) + { + if(!self.hook) + if not(self.hook_state & HOOK_WAITING_FOR_RELEASE) + if (weapon_prepareattack(0, cvar("g_balance_hook_primary_refire"))) + { + if not(self.items & IT_UNLIMITED_AMMO) + self.ammo_cells = self.ammo_cells - cvar("g_balance_hook_primary_ammo"); + self.hook_state |= HOOK_FIRING; + weapon_thinkf(WFRAME_FIRE1, cvar("g_balance_hook_primary_animtime"), w_ready); + } + } + + if (self.BUTTON_ATCK2) + { + if (weapon_prepareattack(1, cvar("g_balance_hook_secondary_refire"))) + { + W_Hook_Attack2(); + weapon_thinkf(WFRAME_FIRE1, cvar("g_balance_hook_secondary_animtime"), w_ready); + } + } + + if (self.BUTTON_CROUCH) + { + self.hook_state (-) HOOK_PULLING; + if (self.BUTTON_ATCK || self.BUTTON_HOOK) + self.hook_state (-) HOOK_RELEASING; + else + self.hook_state |= HOOK_RELEASING; + } + else + { + self.hook_state |= HOOK_PULLING; + self.hook_state (-) HOOK_RELEASING; + + if (self.BUTTON_ATCK || self.BUTTON_HOOK) + { + // already fired + if(self.hook) + self.hook_state |= HOOK_WAITING_FOR_RELEASE; + } + else + { + self.hook_state |= HOOK_REMOVING; + self.hook_state (-) HOOK_WAITING_FOR_RELEASE; + } + } + } + else if (req == WR_PRECACHE) + { + precache_model ("models/weapons/g_hook.md3"); + precache_model ("models/weapons/v_hook.md3"); + precache_model ("models/weapons/w_hook.zym"); + precache_sound ("weapons/hook_fire.wav"); + precache_sound ("weapons/hook_impact.wav"); + precache_sound ("weapons/hookbomb_fire.wav"); + precache_sound ("weapons/hookbomb_impact.wav"); + } + else if (req == WR_SETUP) + { + weapon_setup(WEP_HOOK); + } + else if (req == WR_CHECKAMMO1) + { + return self.ammo_cells >= cvar("g_balance_hook_primary_ammo"); + } + else if (req == WR_CHECKAMMO2) + { + return self.ammo_cells >= cvar("g_balance_hook_secondary_ammo"); + } + else if (req == WR_SUICIDEMESSAGE) + w_deathtypestring = "did the impossible"; + else if (req == WR_KILLMESSAGE) + w_deathtypestring = "has run into #'s gravity bomb"; + return TRUE; +}; diff --git a/data/weapons.cfg b/data/weapons.cfg index eb173dbf9..3f0f4ee87 100644 --- a/data/weapons.cfg +++ b/data/weapons.cfg @@ -9,6 +9,7 @@ set g_start_weapon_hagar 0 set g_start_weapon_rocketlauncher 0 set g_start_weapon_minstanex 0 set g_start_weapon_porto 0 +set g_start_weapon_hook 0 set g_start_ammo_shells 50 set g_start_ammo_nails 0 set g_start_ammo_rockets 0 @@ -225,3 +226,18 @@ set g_balance_porto_primary_lifetime 30 set g_balance_porto_primary_ammo 25 set g_balance_portal_health 200 // these get recharged whenever the portal is used set g_balance_portal_lifetime 15 // these get recharged whenever the portal is used + +// TESTING: on-hand hook with bomb +set g_balance_hook_primary_ammo 0 // hook monkeys +set g_balance_hook_primary_refire 0 // hook monkeys +set g_balance_hook_primary_animtime 0.3 // good shoot anim +set g_balance_hook_secondary_damage 25 // not much +set g_balance_hook_secondary_edgedamage 5 // not much +set g_balance_hook_secondary_radius 800 // LOTS +set g_balance_hook_secondary_force -2000 // LOTS +set g_balance_hook_secondary_ammo 25 // a whole pack +set g_balance_hook_secondary_lifetime 30 // infinite +set g_balance_hook_secondary_speed 200 // throw it a bit upwards +set g_balance_hook_secondary_gravity 0.3 // matrix +set g_balance_hook_secondary_refire 3 // don't drop too many bombs... +set g_balance_hook_secondary_animtime 0.3 // good shoot anim -- 2.39.2