]> de.git.xonotic.org Git - xonotic/xonotic-data.pk3dir.git/commitdiff
Merge branch 'master' into Mario/weapons
authorMario <mario.mario@y7mail.com>
Sun, 15 Jun 2014 05:04:40 +0000 (15:04 +1000)
committerMario <mario.mario@y7mail.com>
Sun, 15 Jun 2014 05:04:40 +0000 (15:04 +1000)
34 files changed:
1  2 
bal-wep-xonotic.cfg
balance-xonotic.cfg
defaultXonotic.cfg
oldbalance25.cfg
oldbalanceFruitieX.cfg
oldbalanceXDF.cfg
oldbalanceXPM.cfg
qcsrc/client/Main.qc
qcsrc/client/View.qc
qcsrc/client/autocvars.qh
qcsrc/client/hook.qc
qcsrc/client/scoreboard.qc
qcsrc/client/waypointsprites.qc
qcsrc/common/monsters/monster/mage.qc
qcsrc/common/monsters/monster/shambler.qc
qcsrc/common/monsters/monster/spider.qc
qcsrc/common/monsters/monster/wyvern.qc
qcsrc/common/monsters/sv_monsters.qc
qcsrc/common/notifications.qh
qcsrc/menu/xonotic/util.qc
qcsrc/server/autocvars.qh
qcsrc/server/bot/havocbot/havocbot.qc
qcsrc/server/bot/havocbot/roles.qc
qcsrc/server/cl_client.qc
qcsrc/server/cl_physics.qc
qcsrc/server/cl_player.qc
qcsrc/server/g_damage.qc
qcsrc/server/g_hook.qc
qcsrc/server/g_world.qc
qcsrc/server/mutators/base.qh
qcsrc/server/mutators/gamemode_nexball.qc
qcsrc/server/t_teleporters.qc
qcsrc/server/weapons/hitplot.qc
qcsrc/server/weapons/tracing.qc

diff --combined bal-wep-xonotic.cfg
index 562119b7e65c305ab8f0bdb2ab3b7f65cfee3525,0000000000000000000000000000000000000000..db8d41dd22f87e651406fa8b5eb6b03df8732a0d
mode 100644,000000..100644
--- /dev/null
@@@ -1,751 -1,0 +1,751 @@@
- set g_balance_hook_primary_refire 0
 +// {{{ #1: Blaster
 +set g_balance_blaster_primary_animtime 0.2
 +set g_balance_blaster_primary_damage 25
 +set g_balance_blaster_primary_delay 0
 +set g_balance_blaster_primary_edgedamage 12.5
 +set g_balance_blaster_primary_force 300
 +set g_balance_blaster_primary_lifetime 5
 +set g_balance_blaster_primary_radius 70
 +set g_balance_blaster_primary_refire 0.7
 +set g_balance_blaster_primary_shotangle 0
 +set g_balance_blaster_primary_speed 6000
 +set g_balance_blaster_primary_spread 0
 +set g_balance_blaster_secondary 0
 +set g_balance_blaster_secondary_animtime 0.2
 +set g_balance_blaster_secondary_damage 25
 +set g_balance_blaster_secondary_delay 0
 +set g_balance_blaster_secondary_edgedamage 12.5
 +set g_balance_blaster_secondary_force 300
 +set g_balance_blaster_secondary_lifetime 5
 +set g_balance_blaster_secondary_radius 70
 +set g_balance_blaster_secondary_refire 0.7
 +set g_balance_blaster_secondary_shotangle 0
 +set g_balance_blaster_secondary_speed 6000
 +set g_balance_blaster_secondary_spread 0
 +set g_balance_blaster_switchdelay_drop 0.15
 +set g_balance_blaster_switchdelay_raise 0.15
 +set g_balance_blaster_weaponreplace ""
 +set g_balance_blaster_weaponstart 1
 +set g_balance_blaster_weaponstartoverride -1
 +set g_balance_blaster_weaponthrowable 0
 +// }}}
 +// {{{ #2: Shockwave
 +set g_balance_shockwave_blast_animtime 0.3
 +set g_balance_shockwave_blast_damage 20
 +set g_balance_shockwave_blast_distance 1000
 +set g_balance_shockwave_blast_edgedamage 0
 +set g_balance_shockwave_blast_force 200
 +set g_balance_shockwave_blast_force_forwardbias 50
 +set g_balance_shockwave_blast_force_zscale 2
 +set g_balance_shockwave_blast_jump_damage 20
 +set g_balance_shockwave_blast_jump_edgedamage 0
 +set g_balance_shockwave_blast_jump_force 300
 +set g_balance_shockwave_blast_jump_force_velocitybias 0
 +set g_balance_shockwave_blast_jump_force_zscale 1.25
 +set g_balance_shockwave_blast_jump_multiplier_accuracy 0.5
 +set g_balance_shockwave_blast_jump_multiplier_distance 0.5
 +set g_balance_shockwave_blast_jump_multiplier_min 0
 +set g_balance_shockwave_blast_jump_radius 150
 +set g_balance_shockwave_blast_multiplier_accuracy 0.5
 +set g_balance_shockwave_blast_multiplier_distance 0.5
 +set g_balance_shockwave_blast_multiplier_min 0
 +set g_balance_shockwave_blast_refire 0.75
 +set g_balance_shockwave_blast_splash_damage 15
 +set g_balance_shockwave_blast_splash_edgedamage 0
 +set g_balance_shockwave_blast_splash_force 100
 +set g_balance_shockwave_blast_splash_force_forwardbias 50
 +set g_balance_shockwave_blast_splash_multiplier_accuracy 0.5
 +set g_balance_shockwave_blast_splash_multiplier_distance 0.5
 +set g_balance_shockwave_blast_splash_multiplier_min 0
 +set g_balance_shockwave_blast_splash_radius 70
 +set g_balance_shockwave_blast_spread_max 120
 +set g_balance_shockwave_blast_spread_min 25
 +set g_balance_shockwave_melee_animtime 1.3
 +set g_balance_shockwave_melee_damage 80
 +set g_balance_shockwave_melee_delay 0.25
 +set g_balance_shockwave_melee_force 200
 +set g_balance_shockwave_melee_multihit 1
 +set g_balance_shockwave_melee_no_doubleslap 1
 +set g_balance_shockwave_melee_nonplayerdamage 40
 +set g_balance_shockwave_melee_range 120
 +set g_balance_shockwave_melee_refire 1.25
 +set g_balance_shockwave_melee_swing_side 120
 +set g_balance_shockwave_melee_swing_up 30
 +set g_balance_shockwave_melee_time 0.15
 +set g_balance_shockwave_melee_traces 10
 +set g_balance_shockwave_switchdelay_drop 0.2
 +set g_balance_shockwave_switchdelay_raise 0.2
 +set g_balance_shockwave_weaponreplace ""
 +set g_balance_shockwave_weaponstart 1
 +set g_balance_shockwave_weaponstartoverride -1
 +set g_balance_shockwave_weaponthrowable 0
 +// }}}
 +// {{{ #3: Machine Gun
 +set g_balance_machinegun_burst 3
 +set g_balance_machinegun_burst_ammo 3
 +set g_balance_machinegun_burst_animtime 0.3
 +set g_balance_machinegun_burst_refire 0.06
 +set g_balance_machinegun_burst_refire2 0.45
 +set g_balance_machinegun_burst_speed 0
 +set g_balance_machinegun_first 1
 +set g_balance_machinegun_first_ammo 1
 +set g_balance_machinegun_first_damage 14
 +set g_balance_machinegun_first_force 5
 +set g_balance_machinegun_first_refire 0.125
 +set g_balance_machinegun_first_spread 0.03
 +set g_balance_machinegun_mode 1
 +set g_balance_machinegun_reload_ammo 60
 +set g_balance_machinegun_reload_time 2
 +set g_balance_machinegun_solidpenetration 13.1
 +set g_balance_machinegun_spread_add 0.012
 +set g_balance_machinegun_spread_max 0.05
 +set g_balance_machinegun_spread_min 0.02
 +set g_balance_machinegun_sustained_ammo 1
 +set g_balance_machinegun_sustained_damage 10
 +set g_balance_machinegun_sustained_force 5
 +set g_balance_machinegun_sustained_refire 0.1
 +set g_balance_machinegun_sustained_spread 0.03
 +set g_balance_machinegun_switchdelay_drop 0.2
 +set g_balance_machinegun_switchdelay_raise 0.2
 +set g_balance_machinegun_weaponreplace "arc"
 +set g_balance_machinegun_weaponstart 0
 +set g_balance_machinegun_weaponstartoverride -1
 +set g_balance_machinegun_weaponthrowable 1
 +// }}}
 +// {{{ #4: Mortar
 +set g_balance_mortar_bouncefactor 0.5
 +set g_balance_mortar_bouncestop 0.075
 +set g_balance_mortar_primary_ammo 2
 +set g_balance_mortar_primary_animtime 0.3
 +set g_balance_mortar_primary_damage 50
 +set g_balance_mortar_primary_damageforcescale 0
 +set g_balance_mortar_primary_edgedamage 25
 +set g_balance_mortar_primary_force 250
 +set g_balance_mortar_primary_health 15
 +set g_balance_mortar_primary_lifetime 5
 +set g_balance_mortar_primary_lifetime_stick 0
 +set g_balance_mortar_primary_radius 120
 +set g_balance_mortar_primary_refire 0.8
 +set g_balance_mortar_primary_remote_minbouncecnt 0
 +set g_balance_mortar_primary_speed 1900
 +set g_balance_mortar_primary_speed_up 225
 +set g_balance_mortar_primary_speed_z 0
 +set g_balance_mortar_primary_spread 0
 +set g_balance_mortar_primary_type 0
 +set g_balance_mortar_reload_ammo 0
 +set g_balance_mortar_reload_time 2
 +set g_balance_mortar_secondary_ammo 2
 +set g_balance_mortar_secondary_animtime 0.3
 +set g_balance_mortar_secondary_damage 60
 +set g_balance_mortar_secondary_damageforcescale 4
 +set g_balance_mortar_secondary_edgedamage 30
 +set g_balance_mortar_secondary_force 250
 +set g_balance_mortar_secondary_health 30
 +set g_balance_mortar_secondary_lifetime 5
 +set g_balance_mortar_secondary_lifetime_bounce 0.5
 +set g_balance_mortar_secondary_lifetime_stick 0
 +set g_balance_mortar_secondary_radius 120
 +set g_balance_mortar_secondary_refire 0.7
 +set g_balance_mortar_secondary_remote_detonateprimary 0
 +set g_balance_mortar_secondary_speed 1400
 +set g_balance_mortar_secondary_speed_up 150
 +set g_balance_mortar_secondary_speed_z 0
 +set g_balance_mortar_secondary_spread 0
 +set g_balance_mortar_secondary_type 1
 +set g_balance_mortar_switchdelay_drop 0.2
 +set g_balance_mortar_switchdelay_raise 0.2
 +set g_balance_mortar_weaponreplace ""
 +set g_balance_mortar_weaponstart 0
 +set g_balance_mortar_weaponstartoverride -1
 +set g_balance_mortar_weaponthrowable 1
 +// }}}
 +// {{{ #5: Mine Layer (MUTATOR WEAPON)
 +set g_balance_minelayer_ammo 4
 +set g_balance_minelayer_animtime 0.4
 +set g_balance_minelayer_damage 40
 +set g_balance_minelayer_damageforcescale 0
 +set g_balance_minelayer_detonatedelay -1
 +set g_balance_minelayer_edgedamage 20
 +set g_balance_minelayer_force 250
 +set g_balance_minelayer_health 15
 +set g_balance_minelayer_lifetime 10
 +set g_balance_minelayer_lifetime_countdown 0.5
 +set g_balance_minelayer_limit 3
 +set g_balance_minelayer_protection 0
 +set g_balance_minelayer_proximityradius 150
 +set g_balance_minelayer_radius 175
 +set g_balance_minelayer_refire 1.5
 +set g_balance_minelayer_reload_ammo 0
 +set g_balance_minelayer_reload_time 2
 +set g_balance_minelayer_remote_damage 45
 +set g_balance_minelayer_remote_edgedamage 40
 +set g_balance_minelayer_remote_force 300
 +set g_balance_minelayer_remote_radius 200
 +set g_balance_minelayer_speed 1000
 +set g_balance_minelayer_switchdelay_drop 0.2
 +set g_balance_minelayer_switchdelay_raise 0.2
 +set g_balance_minelayer_time 0.5
 +set g_balance_minelayer_weaponreplace ""
 +set g_balance_minelayer_weaponstart 0
 +set g_balance_minelayer_weaponstartoverride -1
 +set g_balance_minelayer_weaponthrowable 1
 +// }}}
 +// {{{ #6: Electro
 +set g_balance_electro_combo_comboradius 300
 +set g_balance_electro_combo_comboradius_thruwall 200
 +set g_balance_electro_combo_damage 50
 +set g_balance_electro_combo_edgedamage 25
 +set g_balance_electro_combo_force 120
 +set g_balance_electro_combo_radius 150
 +set g_balance_electro_combo_safeammocheck 1
 +set g_balance_electro_combo_speed 2000
 +set g_balance_electro_primary_ammo 4
 +set g_balance_electro_primary_animtime 0.3
 +set g_balance_electro_primary_comboradius 300
 +set g_balance_electro_primary_damage 40
 +set g_balance_electro_primary_edgedamage 20
 +set g_balance_electro_primary_force 200
 +set g_balance_electro_primary_lifetime 5
 +set g_balance_electro_primary_midaircombo_explode 1
 +set g_balance_electro_primary_midaircombo_interval 0.1
 +set g_balance_electro_primary_midaircombo_radius 100
 +set g_balance_electro_primary_radius 100
 +set g_balance_electro_primary_refire 0.6
 +set g_balance_electro_primary_speed 2500
 +set g_balance_electro_primary_spread 0
 +set g_balance_electro_reload_ammo 0
 +set g_balance_electro_reload_time 2
 +set g_balance_electro_secondary_ammo 2
 +set g_balance_electro_secondary_animtime 0.2
 +set g_balance_electro_secondary_bouncefactor 0.3
 +set g_balance_electro_secondary_bouncestop 0.05
 +set g_balance_electro_secondary_count 3
 +set g_balance_electro_secondary_damage 40
 +set g_balance_electro_secondary_damagedbycontents 1
 +set g_balance_electro_secondary_damageforcescale 4
 +set g_balance_electro_secondary_edgedamage 20
 +set g_balance_electro_secondary_force 50
 +set g_balance_electro_secondary_health 5
 +set g_balance_electro_secondary_lifetime 4
 +set g_balance_electro_secondary_radius 150
 +set g_balance_electro_secondary_refire 0.2
 +set g_balance_electro_secondary_refire2 1.6
 +set g_balance_electro_secondary_speed 1000
 +set g_balance_electro_secondary_speed_up 200
 +set g_balance_electro_secondary_speed_z 0
 +set g_balance_electro_secondary_spread 0.04
 +set g_balance_electro_secondary_touchexplode 0
 +set g_balance_electro_switchdelay_drop 0.2
 +set g_balance_electro_switchdelay_raise 0.2
 +set g_balance_electro_weaponreplace ""
 +set g_balance_electro_weaponstart 0
 +set g_balance_electro_weaponstartoverride -1
 +set g_balance_electro_weaponthrowable 1
 +// }}}
 +// {{{ #7: Arc
 +set g_balance_arc_beam_ammo 0
 +set g_balance_arc_beam_animtime 0.2
 +set g_balance_arc_beam_botaimlifetime 0
 +set g_balance_arc_beam_botaimspeed 0
 +set g_balance_arc_beam_damage 150
 +set g_balance_arc_beam_degreespersegment 1
 +set g_balance_arc_beam_distancepersegment 0
 +set g_balance_arc_beam_falloff_halflifedist 0
 +set g_balance_arc_beam_falloff_maxdist 0
 +set g_balance_arc_beam_falloff_mindist 0
 +set g_balance_arc_beam_force 2000
 +set g_balance_arc_beam_healing_amax 200
 +set g_balance_arc_beam_healing_aps 50
 +set g_balance_arc_beam_healing_hmax 200
 +set g_balance_arc_beam_healing_hps 50
 +set g_balance_arc_beam_maxangle 10
 +set g_balance_arc_beam_nonplayerdamage 80
 +set g_balance_arc_beam_range 1000
 +set g_balance_arc_beam_refire 0.5
 +set g_balance_arc_beam_returnspeed 8
 +set g_balance_arc_beam_tightness 0.5
 +set g_balance_arc_burst_ammo 0
 +set g_balance_arc_burst_damage 500
 +set g_balance_arc_burst_healing_aps 100
 +set g_balance_arc_burst_healing_hps 100
 +set g_balance_arc_switchdelay_drop 0.3
 +set g_balance_arc_switchdelay_raise 0.3
 +set g_balance_arc_weaponreplace ""
 +set g_balance_arc_weaponstart 0
 +set g_balance_arc_weaponstartoverride -1
 +set g_balance_arc_weaponthrowable 1
 +// }}}
 +// {{{ #8: Crylink
 +set g_balance_crylink_primary_ammo 3
 +set g_balance_crylink_primary_animtime 0.3
 +set g_balance_crylink_primary_bouncedamagefactor 0.5
 +set g_balance_crylink_primary_bounces 1
 +set g_balance_crylink_primary_damage 12
 +set g_balance_crylink_primary_edgedamage 6
 +set g_balance_crylink_primary_force -50
 +set g_balance_crylink_primary_joindelay 0.1
 +set g_balance_crylink_primary_joinexplode 1
 +set g_balance_crylink_primary_joinexplode_damage 0
 +set g_balance_crylink_primary_joinexplode_edgedamage 0
 +set g_balance_crylink_primary_joinexplode_force 0
 +set g_balance_crylink_primary_joinexplode_radius 0
 +set g_balance_crylink_primary_joinspread 0.2
 +set g_balance_crylink_primary_linkexplode 1
 +set g_balance_crylink_primary_middle_fadetime 5
 +set g_balance_crylink_primary_middle_lifetime 5
 +set g_balance_crylink_primary_other_fadetime 5
 +set g_balance_crylink_primary_other_lifetime 5
 +set g_balance_crylink_primary_radius 80
 +set g_balance_crylink_primary_refire 0.7
 +set g_balance_crylink_primary_shots 6
 +set g_balance_crylink_primary_speed 2000
 +set g_balance_crylink_primary_spread 0.08
 +set g_balance_crylink_reload_ammo 0
 +set g_balance_crylink_reload_time 2
 +set g_balance_crylink_secondary 1
 +set g_balance_crylink_secondary_ammo 2
 +set g_balance_crylink_secondary_animtime 0.2
 +set g_balance_crylink_secondary_bouncedamagefactor 0.5
 +set g_balance_crylink_secondary_bounces 0
 +set g_balance_crylink_secondary_damage 10
 +set g_balance_crylink_secondary_edgedamage 5
 +set g_balance_crylink_secondary_force -250
 +set g_balance_crylink_secondary_joindelay 0
 +set g_balance_crylink_secondary_joinexplode 0
 +set g_balance_crylink_secondary_joinexplode_damage 0
 +set g_balance_crylink_secondary_joinexplode_edgedamage 0
 +set g_balance_crylink_secondary_joinexplode_force 0
 +set g_balance_crylink_secondary_joinexplode_radius 0
 +set g_balance_crylink_secondary_joinspread 0
 +set g_balance_crylink_secondary_linkexplode 1
 +set g_balance_crylink_secondary_middle_fadetime 5
 +set g_balance_crylink_secondary_middle_lifetime 5
 +set g_balance_crylink_secondary_other_fadetime 5
 +set g_balance_crylink_secondary_other_lifetime 5
 +set g_balance_crylink_secondary_radius 100
 +set g_balance_crylink_secondary_refire 0.7
 +set g_balance_crylink_secondary_shots 5
 +set g_balance_crylink_secondary_speed 3000
 +set g_balance_crylink_secondary_spread 0.01
 +set g_balance_crylink_secondary_spreadtype 1
 +set g_balance_crylink_switchdelay_drop 0.2
 +set g_balance_crylink_switchdelay_raise 0.2
 +set g_balance_crylink_weaponreplace ""
 +set g_balance_crylink_weaponstart 0
 +set g_balance_crylink_weaponstartoverride -1
 +set g_balance_crylink_weaponthrowable 1
 +// }}}
 +// {{{ #9: Vortex
 +set g_balance_vortex_charge 1
 +set g_balance_vortex_charge_animlimit 0.5
 +set g_balance_vortex_charge_limit 1
 +set g_balance_vortex_charge_maxspeed 800
 +set g_balance_vortex_charge_mindmg 40
 +set g_balance_vortex_charge_minspeed 400
 +set g_balance_vortex_charge_rate 0.4
 +set g_balance_vortex_charge_rot_pause 0
 +set g_balance_vortex_charge_rot_rate 0
 +set g_balance_vortex_charge_shot_multiplier 0
 +set g_balance_vortex_charge_start 0.5
 +set g_balance_vortex_charge_velocity_rate 0
 +set g_balance_vortex_primary_ammo 6
 +set g_balance_vortex_primary_animtime 0.6
 +set g_balance_vortex_primary_damage 80
 +set g_balance_vortex_primary_damagefalloff_forcehalflife 0
 +set g_balance_vortex_primary_damagefalloff_halflife 0
 +set g_balance_vortex_primary_damagefalloff_maxdist 0
 +set g_balance_vortex_primary_damagefalloff_mindist 0
 +set g_balance_vortex_primary_force 400
 +set g_balance_vortex_primary_refire 1.5
 +set g_balance_vortex_reload_ammo 0
 +set g_balance_vortex_reload_time 2
 +set g_balance_vortex_secondary 0
 +set g_balance_vortex_secondary_ammo 2
 +set g_balance_vortex_secondary_animtime 0
 +set g_balance_vortex_secondary_chargepool 0
 +set g_balance_vortex_secondary_chargepool_pause_regen 1
 +set g_balance_vortex_secondary_chargepool_regen 0.15
 +set g_balance_vortex_secondary_damage 0
 +set g_balance_vortex_secondary_damagefalloff_forcehalflife 0
 +set g_balance_vortex_secondary_damagefalloff_halflife 0
 +set g_balance_vortex_secondary_damagefalloff_maxdist 0
 +set g_balance_vortex_secondary_damagefalloff_mindist 0
 +set g_balance_vortex_secondary_force 0
 +set g_balance_vortex_secondary_refire 0
 +set g_balance_vortex_switchdelay_drop 0.3
 +set g_balance_vortex_switchdelay_raise 0.25
 +set g_balance_vortex_weaponreplace ""
 +set g_balance_vortex_weaponstart 0
 +set g_balance_vortex_weaponstartoverride -1
 +set g_balance_vortex_weaponthrowable 1
 +// }}}
 +// {{{ #10: Hagar
 +set g_balance_hagar_primary_ammo 1
 +set g_balance_hagar_primary_damage 25
 +set g_balance_hagar_primary_damageforcescale 0
 +set g_balance_hagar_primary_edgedamage 12.5
 +set g_balance_hagar_primary_force 100
 +set g_balance_hagar_primary_health 15
 +set g_balance_hagar_primary_lifetime 5
 +set g_balance_hagar_primary_radius 65
 +set g_balance_hagar_primary_refire 0.16667
 +set g_balance_hagar_primary_speed 2500
 +set g_balance_hagar_primary_spread 0.03
 +set g_balance_hagar_reload_ammo 0
 +set g_balance_hagar_reload_time 2
 +set g_balance_hagar_secondary 1
 +set g_balance_hagar_secondary_ammo 1
 +set g_balance_hagar_secondary_damage 40
 +set g_balance_hagar_secondary_damageforcescale 0
 +set g_balance_hagar_secondary_edgedamage 20
 +set g_balance_hagar_secondary_force 75
 +set g_balance_hagar_secondary_health 15
 +set g_balance_hagar_secondary_lifetime_min 10
 +set g_balance_hagar_secondary_lifetime_rand 0
 +set g_balance_hagar_secondary_load 1
 +set g_balance_hagar_secondary_load_abort 0
 +set g_balance_hagar_secondary_load_animtime 0.2
 +set g_balance_hagar_secondary_load_hold 4
 +set g_balance_hagar_secondary_load_linkexplode 0
 +set g_balance_hagar_secondary_load_max 4
 +set g_balance_hagar_secondary_load_releasedeath 0
 +set g_balance_hagar_secondary_load_speed 0.5
 +set g_balance_hagar_secondary_load_spread 0.075
 +set g_balance_hagar_secondary_load_spread_bias 0.5
 +set g_balance_hagar_secondary_radius 80
 +set g_balance_hagar_secondary_refire 0.5
 +set g_balance_hagar_secondary_speed 2500
 +set g_balance_hagar_secondary_spread 0.05
 +set g_balance_hagar_switchdelay_drop 0.2
 +set g_balance_hagar_switchdelay_raise 0.2
 +set g_balance_hagar_weaponreplace ""
 +set g_balance_hagar_weaponstart 0
 +set g_balance_hagar_weaponstartoverride -1
 +set g_balance_hagar_weaponthrowable 1
 +// }}}
 +// {{{ #11: Devastator
 +set g_balance_devastator_ammo 4
 +set g_balance_devastator_animtime 0.4
 +set g_balance_devastator_damage 70
 +set g_balance_devastator_damageforcescale 1
 +set g_balance_devastator_detonatedelay 0.02
 +set g_balance_devastator_edgedamage 35
 +set g_balance_devastator_force 450
 +set g_balance_devastator_guidedelay 0.2
 +set g_balance_devastator_guidegoal 512
 +set g_balance_devastator_guiderate 70
 +set g_balance_devastator_guideratedelay 0.01
 +set g_balance_devastator_guidestop 0
 +set g_balance_devastator_health 30
 +set g_balance_devastator_lifetime 10
 +set g_balance_devastator_radius 110
 +set g_balance_devastator_refire 1.2
 +set g_balance_devastator_reload_ammo 0
 +set g_balance_devastator_reload_time 2
 +set g_balance_devastator_remote_damage 70
 +set g_balance_devastator_remote_edgedamage 35
 +set g_balance_devastator_remote_force 400
 +set g_balance_devastator_remote_jump_damage 40
 +set g_balance_devastator_remote_jump_radius 200
 +set g_balance_devastator_remote_jump_velocity_z_add 500
 +set g_balance_devastator_remote_jump_velocity_z_max 1500
 +set g_balance_devastator_remote_jump_velocity_z_min 500
 +set g_balance_devastator_remote_radius 110
 +set g_balance_devastator_speed 1300
 +set g_balance_devastator_speedaccel 1300
 +set g_balance_devastator_speedstart 1000
 +set g_balance_devastator_switchdelay_drop 0.3
 +set g_balance_devastator_switchdelay_raise 0.2
 +set g_balance_devastator_weaponreplace ""
 +set g_balance_devastator_weaponstart 0
 +set g_balance_devastator_weaponstartoverride -1
 +set g_balance_devastator_weaponthrowable 1
 +// }}}
 +// {{{ #12: Port-O-Launch
 +set g_balance_porto_primary_animtime 0.3
 +set g_balance_porto_primary_lifetime 5
 +set g_balance_porto_primary_refire 1.5
 +set g_balance_porto_primary_speed 1000
 +set g_balance_porto_secondary 1
 +set g_balance_porto_secondary_animtime 0.3
 +set g_balance_porto_secondary_lifetime 5
 +set g_balance_porto_secondary_refire 1.5
 +set g_balance_porto_secondary_speed 1000
 +set g_balance_porto_switchdelay_drop 0.2
 +set g_balance_porto_switchdelay_raise 0.2
 +set g_balance_porto_weaponreplace ""
 +set g_balance_porto_weaponstart 0
 +set g_balance_porto_weaponstartoverride -1
 +set g_balance_porto_weaponthrowable 1
 +// }}}
 +// {{{ #13: Vaporizer
 +set g_balance_vaporizer_primary_ammo 10
 +set g_balance_vaporizer_primary_animtime 0.3
 +set g_balance_vaporizer_primary_refire 1
 +set g_balance_vaporizer_reload_ammo 0
 +set g_balance_vaporizer_reload_time 0
 +set g_balance_vaporizer_secondary_ammo 0
 +set g_balance_vaporizer_secondary_animtime 0.2
 +set g_balance_vaporizer_secondary_damage 25
 +set g_balance_vaporizer_secondary_delay 0
 +set g_balance_vaporizer_secondary_edgedamage 12.5
 +set g_balance_vaporizer_secondary_force 400
 +set g_balance_vaporizer_secondary_lifetime 5
 +set g_balance_vaporizer_secondary_radius 70
 +set g_balance_vaporizer_secondary_refire 0.7
 +set g_balance_vaporizer_secondary_shotangle 0
 +set g_balance_vaporizer_secondary_speed 6000
 +set g_balance_vaporizer_secondary_spread 0
 +set g_balance_vaporizer_switchdelay_drop 0.2
 +set g_balance_vaporizer_switchdelay_raise 0.2
 +set g_balance_vaporizer_weaponreplace ""
 +set g_balance_vaporizer_weaponstart 0
 +set g_balance_vaporizer_weaponstartoverride -1
 +set g_balance_vaporizer_weaponthrowable 0
 +// }}}
 +// {{{ #14: Grappling Hook
 +set g_balance_hook_primary_ammo 5
 +set g_balance_hook_primary_animtime 0.3
 +set g_balance_hook_primary_hooked_ammo 5
 +set g_balance_hook_primary_hooked_time_free 2
 +set g_balance_hook_primary_hooked_time_max 0
++set g_balance_hook_primary_refire 0.2
 +set g_balance_hook_secondary_animtime 0.3
 +set g_balance_hook_secondary_damage 25
 +set g_balance_hook_secondary_damageforcescale 0
 +set g_balance_hook_secondary_duration 1.5
 +set g_balance_hook_secondary_edgedamage 5
 +set g_balance_hook_secondary_force -2000
 +set g_balance_hook_secondary_gravity 5
 +set g_balance_hook_secondary_health 15
 +set g_balance_hook_secondary_lifetime 5
 +set g_balance_hook_secondary_power 3
 +set g_balance_hook_secondary_radius 500
 +set g_balance_hook_secondary_refire 3
 +set g_balance_hook_secondary_speed 0
 +set g_balance_hook_switchdelay_drop 0.2
 +set g_balance_hook_switchdelay_raise 0.2
 +set g_balance_hook_weaponreplace ""
 +set g_balance_hook_weaponstart 0
 +set g_balance_hook_weaponstartoverride -1
 +set g_balance_hook_weaponthrowable 1
 +// }}}
 +// {{{ #15: Heavy Laser Assault Cannon (MUTATOR WEAPON)
 +set g_balance_hlac_primary_ammo 1
 +set g_balance_hlac_primary_animtime 0.4
 +set g_balance_hlac_primary_damage 18
 +set g_balance_hlac_primary_edgedamage 9
 +set g_balance_hlac_primary_force 90
 +set g_balance_hlac_primary_lifetime 5
 +set g_balance_hlac_primary_radius 70
 +set g_balance_hlac_primary_refire 0.15
 +set g_balance_hlac_primary_speed 9000
 +set g_balance_hlac_primary_spread_add 0.0045
 +set g_balance_hlac_primary_spread_crouchmod 0.25
 +set g_balance_hlac_primary_spread_max 0.25
 +set g_balance_hlac_primary_spread_min 0.01
 +set g_balance_hlac_reload_ammo 0
 +set g_balance_hlac_reload_time 2
 +set g_balance_hlac_secondary 1
 +set g_balance_hlac_secondary_ammo 10
 +set g_balance_hlac_secondary_animtime 0.3
 +set g_balance_hlac_secondary_damage 15
 +set g_balance_hlac_secondary_edgedamage 7.5
 +set g_balance_hlac_secondary_force 90
 +set g_balance_hlac_secondary_lifetime 5
 +set g_balance_hlac_secondary_radius 70
 +set g_balance_hlac_secondary_refire 1
 +set g_balance_hlac_secondary_shots 6
 +set g_balance_hlac_secondary_speed 9000
 +set g_balance_hlac_secondary_spread 0.15
 +set g_balance_hlac_secondary_spread_crouchmod 0.5
 +set g_balance_hlac_switchdelay_drop 0.2
 +set g_balance_hlac_switchdelay_raise 0.2
 +set g_balance_hlac_weaponreplace ""
 +set g_balance_hlac_weaponstart 0
 +set g_balance_hlac_weaponstartoverride -1
 +set g_balance_hlac_weaponthrowable 1
 +// }}}
 +// {{{ #16: @!#%'n Tuba
 +set g_balance_tuba_animtime 0.05
 +set g_balance_tuba_attenuation 0.5
 +set g_balance_tuba_damage 5
 +set g_balance_tuba_edgedamage 0
 +set g_balance_tuba_force 40
 +set g_balance_tuba_radius 200
 +set g_balance_tuba_refire 0.05
 +set g_balance_tuba_switchdelay_drop 0.2
 +set g_balance_tuba_switchdelay_raise 0.2
 +set g_balance_tuba_weaponreplace ""
 +set g_balance_tuba_weaponstart 0
 +set g_balance_tuba_weaponstartoverride -1
 +set g_balance_tuba_weaponthrowable 1
 +// }}}
 +// {{{ #17: Rifle (MUTATOR WEAPON)
 +set g_balance_rifle_bursttime 0
 +set g_balance_rifle_primary_ammo 10
 +set g_balance_rifle_primary_animtime 0.4
 +set g_balance_rifle_primary_bullethail 0
 +set g_balance_rifle_primary_burstcost 0
 +set g_balance_rifle_primary_damage 80
 +set g_balance_rifle_primary_force 100
 +set g_balance_rifle_primary_refire 1.2
 +set g_balance_rifle_primary_shots 1
 +set g_balance_rifle_primary_solidpenetration 62.2
 +set g_balance_rifle_primary_spread 0
 +set g_balance_rifle_primary_tracer 1
 +set g_balance_rifle_reload_ammo 80
 +set g_balance_rifle_reload_time 2
 +set g_balance_rifle_secondary 1
 +set g_balance_rifle_secondary_ammo 10
 +set g_balance_rifle_secondary_animtime 0.3
 +set g_balance_rifle_secondary_bullethail 0
 +set g_balance_rifle_secondary_burstcost 0
 +set g_balance_rifle_secondary_damage 20
 +set g_balance_rifle_secondary_force 50
 +set g_balance_rifle_secondary_refire 0.9
 +set g_balance_rifle_secondary_reload 0
 +set g_balance_rifle_secondary_shots 4
 +set g_balance_rifle_secondary_solidpenetration 15.5
 +set g_balance_rifle_secondary_spread 0.04
 +set g_balance_rifle_secondary_tracer 0
 +set g_balance_rifle_switchdelay_drop 0.2
 +set g_balance_rifle_switchdelay_raise 0.2
 +set g_balance_rifle_weaponreplace ""
 +set g_balance_rifle_weaponstart 0
 +set g_balance_rifle_weaponstartoverride -1
 +set g_balance_rifle_weaponthrowable 1
 +// }}}
 +// {{{ #18: Fireball
 +set g_balance_fireball_primary_animtime 0.2
 +set g_balance_fireball_primary_bfgdamage 100
 +set g_balance_fireball_primary_bfgforce 0
 +set g_balance_fireball_primary_bfgradius 1000
 +set g_balance_fireball_primary_damage 200
 +set g_balance_fireball_primary_damageforcescale 0
 +set g_balance_fireball_primary_edgedamage 50
 +set g_balance_fireball_primary_force 600
 +set g_balance_fireball_primary_health 0
 +set g_balance_fireball_primary_laserburntime 0.5
 +set g_balance_fireball_primary_laserdamage 80
 +set g_balance_fireball_primary_laseredgedamage 20
 +set g_balance_fireball_primary_laserradius 256
 +set g_balance_fireball_primary_lifetime 15
 +set g_balance_fireball_primary_radius 200
 +set g_balance_fireball_primary_refire 2
 +set g_balance_fireball_primary_refire2 0
 +set g_balance_fireball_primary_speed 1200
 +set g_balance_fireball_primary_spread 0
 +set g_balance_fireball_secondary_animtime 0.3
 +set g_balance_fireball_secondary_damage 40
 +set g_balance_fireball_secondary_damageforcescale 4
 +set g_balance_fireball_secondary_damagetime 5
 +set g_balance_fireball_secondary_laserburntime 0.5
 +set g_balance_fireball_secondary_laserdamage 50
 +set g_balance_fireball_secondary_laseredgedamage 20
 +set g_balance_fireball_secondary_laserradius 110
 +set g_balance_fireball_secondary_lifetime 7
 +set g_balance_fireball_secondary_refire 1.5
 +set g_balance_fireball_secondary_speed 900
 +set g_balance_fireball_secondary_speed_up 100
 +set g_balance_fireball_secondary_speed_z 0
 +set g_balance_fireball_secondary_spread 0
 +set g_balance_fireball_switchdelay_drop 0.2
 +set g_balance_fireball_switchdelay_raise 0.2
 +set g_balance_fireball_weaponreplace ""
 +set g_balance_fireball_weaponstart 0
 +set g_balance_fireball_weaponstartoverride -1
 +set g_balance_fireball_weaponthrowable 0
 +// }}}
 +// {{{ #19: T.A.G. Seeker (MUTATOR WEAPON)
 +set g_balance_seeker_flac_ammo 1
 +set g_balance_seeker_flac_animtime 0.1
 +set g_balance_seeker_flac_damage 15
 +set g_balance_seeker_flac_edgedamage 10
 +set g_balance_seeker_flac_force 50
 +set g_balance_seeker_flac_lifetime 0.1
 +set g_balance_seeker_flac_lifetime_rand 0.05
 +set g_balance_seeker_flac_radius 100
 +set g_balance_seeker_flac_refire 0.1
 +set g_balance_seeker_flac_speed 3000
 +set g_balance_seeker_flac_speed_up 1000
 +set g_balance_seeker_flac_speed_z 0
 +set g_balance_seeker_flac_spread 0.4
 +set g_balance_seeker_missile_accel 1400
 +set g_balance_seeker_missile_ammo 2
 +set g_balance_seeker_missile_animtime 0.2
 +set g_balance_seeker_missile_count 3
 +set g_balance_seeker_missile_damage 30
 +set g_balance_seeker_missile_damageforcescale 4
 +set g_balance_seeker_missile_decel 1400
 +set g_balance_seeker_missile_delay 0.25
 +set g_balance_seeker_missile_edgedamage 10
 +set g_balance_seeker_missile_force 150
 +set g_balance_seeker_missile_health 5
 +set g_balance_seeker_missile_lifetime 15
 +set g_balance_seeker_missile_proxy 0
 +set g_balance_seeker_missile_proxy_delay 0.2
 +set g_balance_seeker_missile_proxy_maxrange 45
 +set g_balance_seeker_missile_radius 80
 +set g_balance_seeker_missile_refire 0.5
 +set g_balance_seeker_missile_smart 1
 +set g_balance_seeker_missile_smart_mindist 800
 +set g_balance_seeker_missile_smart_trace_max 2500
 +set g_balance_seeker_missile_smart_trace_min 1000
 +set g_balance_seeker_missile_speed 700
 +set g_balance_seeker_missile_speed_max 1300
 +set g_balance_seeker_missile_speed_up 300
 +set g_balance_seeker_missile_speed_z 0
 +set g_balance_seeker_missile_spread 0
 +set g_balance_seeker_missile_turnrate 0.65
 +set g_balance_seeker_reload_ammo 0
 +set g_balance_seeker_reload_time 2
 +set g_balance_seeker_switchdelay_drop 0.2
 +set g_balance_seeker_switchdelay_raise 0.2
 +set g_balance_seeker_tag_ammo 1
 +set g_balance_seeker_tag_animtime 0.2
 +set g_balance_seeker_tag_damageforcescale 4
 +set g_balance_seeker_tag_health 5
 +set g_balance_seeker_tag_lifetime 15
 +set g_balance_seeker_tag_refire 0.75
 +set g_balance_seeker_tag_speed 5000
 +set g_balance_seeker_tag_spread 0
 +set g_balance_seeker_tag_tracker_lifetime 10
 +set g_balance_seeker_type 0
 +set g_balance_seeker_weaponreplace ""
 +set g_balance_seeker_weaponstart 0
 +set g_balance_seeker_weaponstartoverride -1
 +set g_balance_seeker_weaponthrowable 1
 +// }}}
 +// {{{ #20: Shotgun (MUTATOR WEAPON)
 +set g_balance_shotgun_primary_ammo 1
 +set g_balance_shotgun_primary_animtime 0.2
 +set g_balance_shotgun_primary_bullets 14
 +set g_balance_shotgun_primary_damage 4
 +set g_balance_shotgun_primary_force 15
 +set g_balance_shotgun_primary_refire 0.75
 +set g_balance_shotgun_primary_solidpenetration 3.8
 +set g_balance_shotgun_primary_spread 0.12
 +set g_balance_shotgun_reload_ammo 0
 +set g_balance_shotgun_reload_time 2
 +set g_balance_shotgun_secondary 1
 +set g_balance_shotgun_secondary_animtime 1
 +set g_balance_shotgun_secondary_damage 80
 +set g_balance_shotgun_secondary_force 200
 +set g_balance_shotgun_secondary_melee_delay 0.25
 +set g_balance_shotgun_secondary_melee_multihit 1
 +set g_balance_shotgun_secondary_melee_no_doubleslap 1
 +set g_balance_shotgun_secondary_melee_nonplayerdamage 40
 +set g_balance_shotgun_secondary_melee_range 120
 +set g_balance_shotgun_secondary_melee_swing_side 120
 +set g_balance_shotgun_secondary_melee_swing_up 30
 +set g_balance_shotgun_secondary_melee_time 0.15
 +set g_balance_shotgun_secondary_melee_traces 10
 +set g_balance_shotgun_secondary_refire 1.25
 +set g_balance_shotgun_switchdelay_drop 0.2
 +set g_balance_shotgun_switchdelay_raise 0.2
 +set g_balance_shotgun_weaponreplace ""
 +set g_balance_shotgun_weaponstart 0
 +set g_balance_shotgun_weaponstartoverride -1
 +set g_balance_shotgun_weaponthrowable 1
 +// }}}
diff --combined balance-xonotic.cfg
index 23d4c774eac37e2308e4c966e01138747b8552bf,0000000000000000000000000000000000000000..dc4b4b9937917e14707214123d445b04dafe2cf2
mode 100644,000000..100644
--- /dev/null
@@@ -1,236 -1,0 +1,237 @@@
 +g_mod_balance Xonotic
 +
 +// {{{ starting gear
 +set g_start_weapon_laser -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_shotgun -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_machinegun -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_mortar -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_electro -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_crylink -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_vortex -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_hagar -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_devastator -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_vaporizer -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_porto -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_hook -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_tuba -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_fireball -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_balance_health_start 100
 +set g_balance_armor_start 0
 +set g_start_ammo_shells 15
 +set g_start_ammo_nails 0
 +set g_start_ammo_rockets 0
 +set g_start_ammo_cells 0
 +set g_start_ammo_plasma 0
 +set g_start_ammo_fuel 0
 +set g_warmup_start_health 100 "starting values when being in warmup-stage"
 +set g_warmup_start_armor 100 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_shells 30 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_nails 160 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_rockets 80 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_cells 90 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_plasma 90 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_fuel 0 "starting values when being in warmup-stage"
 +set g_lms_start_health 200
 +set g_lms_start_armor 200
 +set g_lms_start_ammo_shells 60
 +set g_lms_start_ammo_nails 320
 +set g_lms_start_ammo_rockets 160
 +set g_lms_start_ammo_cells 180
 +set g_lms_start_ammo_plasma 180
 +set g_lms_start_ammo_fuel 0
 +set g_balance_nix_roundtime 25
 +set g_balance_nix_incrtime 1.6
 +set g_balance_nix_ammo_shells 60
 +set g_balance_nix_ammo_nails 320
 +set g_balance_nix_ammo_rockets 160
 +set g_balance_nix_ammo_cells 180
 +set g_balance_nix_ammo_plasma 180
 +set g_balance_nix_ammo_fuel 0
 +set g_balance_nix_ammoincr_shells 2 // eh this will need figured out later I assume
 +set g_balance_nix_ammoincr_nails 6
 +set g_balance_nix_ammoincr_rockets 2
 +set g_balance_nix_ammoincr_cells 2
 +set g_balance_nix_ammoincr_plasma 2
 +set g_balance_nix_ammoincr_fuel 2
 +// }}}
 +
 +// {{{ pickup items
 +set g_pickup_ammo_anyway 1
 +set g_pickup_weapons_anyway 1
 +set g_pickup_shells 15
 +set g_pickup_shells_weapon 15
 +set g_pickup_shells_max 60
 +set g_pickup_nails 80
 +set g_pickup_nails_weapon 80
 +set g_pickup_nails_max 320
 +set g_pickup_rockets 40
 +set g_pickup_rockets_weapon 40
 +set g_pickup_rockets_max 160
 +set g_pickup_cells 30
 +set g_pickup_cells_weapon 30
 +set g_pickup_cells_max 180
 +set g_pickup_plasma 30
 +set g_pickup_plasma_weapon 30
 +set g_pickup_plasma_max 180
 +set g_pickup_fuel 50
 +set g_pickup_fuel_weapon 50
 +set g_pickup_fuel_jetpack 100
 +set g_pickup_fuel_max 100
 +set g_pickup_armorsmall 5
 +set g_pickup_armorsmall_max 200
 +set g_pickup_armorsmall_anyway 1
 +set g_pickup_armormedium 25
 +set g_pickup_armormedium_max 200
 +set g_pickup_armormedium_anyway 1
 +set g_pickup_armorbig 50
 +set g_pickup_armorbig_max 200
 +set g_pickup_armorbig_anyway 1
 +set g_pickup_armorlarge 100
 +set g_pickup_armorlarge_max 200
 +set g_pickup_armorlarge_anyway 1
 +set g_pickup_healthsmall 5
 +set g_pickup_healthsmall_max 200
 +set g_pickup_healthsmall_anyway 1
 +set g_pickup_healthmedium 25
 +set g_pickup_healthmedium_max 200
 +set g_pickup_healthmedium_anyway 1
 +set g_pickup_healthlarge 50
 +set g_pickup_healthlarge_max 200
 +set g_pickup_healthlarge_anyway 1
 +set g_pickup_healthmega 100
 +set g_pickup_healthmega_max 200
 +set g_pickup_healthmega_anyway 1
 +set g_pickup_respawntime_short 15
 +set g_pickup_respawntime_medium 20
 +set g_pickup_respawntime_long 30
 +set g_pickup_respawntime_powerup 120
 +set g_pickup_respawntime_weapon 10
 +set g_pickup_respawntime_superweapon 120
 +set g_pickup_respawntime_ammo 10
 +set g_pickup_respawntimejitter_short 0
 +set g_pickup_respawntimejitter_medium 0
 +set g_pickup_respawntimejitter_long 0
 +set g_pickup_respawntimejitter_powerup 30
 +set g_pickup_respawntimejitter_weapon 0
 +set g_pickup_respawntimejitter_superweapon 10
 +set g_pickup_respawntimejitter_ammo 0
 +// }}}
 +
 +// {{{ regen/rot
 +set g_balance_health_regen 0.08
 +set g_balance_health_regenlinear 0.5
 +set g_balance_pause_health_regen 5
 +set g_balance_pause_health_regen_spawn 0
 +set g_balance_health_rot 0.04
 +set g_balance_health_rotlinear 0.75
 +set g_balance_pause_health_rot 1
 +set g_balance_pause_health_rot_spawn 5
 +set g_balance_health_regenstable 100
 +set g_balance_health_rotstable 100
 +set g_balance_health_limit 999
 +set g_balance_armor_regen 0
 +set g_balance_armor_regenlinear 0
 +set g_balance_armor_rot 0.04
 +set g_balance_armor_rotlinear 0.75
 +set g_balance_pause_armor_rot 1
 +set g_balance_pause_armor_rot_spawn 5
 +set g_balance_armor_regenstable 100
 +set g_balance_armor_rotstable 100
 +set g_balance_armor_limit 999
 +set g_balance_armor_blockpercent 0.6
 +set g_balance_fuel_regen 0.1 "fuel regeneration (only applies if the player owns IT_FUEL_REGEN)"
 +set g_balance_fuel_regenlinear 0
 +set g_balance_pause_fuel_regen 2 // other than this, fuel uses the health regen counter
 +set g_balance_fuel_rot 0.05
 +set g_balance_fuel_rotlinear 0
 +set g_balance_pause_fuel_rot 5
 +set g_balance_pause_fuel_rot_spawn 10
 +set g_balance_fuel_regenstable 50
 +set g_balance_fuel_rotstable 100
 +set g_balance_fuel_limit 999
 +// }}}
 +
 +// {{{ misc
 +set g_balance_selfdamagepercent 0.65
 +set g_weaponspeedfactor 1 "weapon projectile speed multiplier"
 +set g_weaponratefactor 1 "weapon fire rate multiplier"
 +set g_weapondamagefactor 1 "weapon damage multiplier"
 +set g_weaponforcefactor 1 "weapon force multiplier"
 +set g_weaponspreadfactor 1 "weapon spread multiplier"
 +set g_balance_firetransfer_time 0.9
 +set g_balance_firetransfer_damage 0.8
 +set g_throughfloor_damage 0.75
 +set g_throughfloor_force 0.75
 +set g_projectiles_damage 2
 +// possible values:
 +// -2: absolutely no damage to projectiles (no exceptions)
 +// -1: no damage other than the exceptions (electro combo, hagar join explode, ML mines)
 +// 0: only damage from contents (lava/slime) or exceptions
 +// 1: only self damage or damage from contents or exceptions
 +// 2: allow all damage to projectiles normally
 +set g_projectiles_keep_owner 0
 +set g_projectiles_newton_style 2
 +// possible values:
 +// 0: absolute velocity projectiles (like Quake)
 +// 1: relative velocity projectiles, "Newtonian" (like Tribes 2)
 +// 2: relative velocity projectiles, but aim is precorrected so projectiles hit the crosshair (note: strafe rockets then are SLOWER than ones shot while standing, happens in 1 too when aiming correctly which is hard)
 +set g_projectiles_newton_style_2_minfactor 0.8
 +set g_projectiles_newton_style_2_maxfactor 1.5
 +set g_projectiles_spread_style 7
 +// possible values:
 +// 0: forward + solid sphere (like Quake) - varies velocity
 +// 1: forward + flattened solid sphere
 +// 2: forward + solid circle
 +// 3: forward + normal distribution 3D - varies velocity
 +// 4: forward + normal distribution on a plane
 +// 5: forward + circle with 1-r falloff
 +// 6: forward + circle with 1-r^2 falloff
 +// 7: forward + circle with (1-r)(2-r) falloff
 +set g_balance_falldamage_deadminspeed 250
 +set g_balance_falldamage_minspeed 900
 +set g_balance_falldamage_factor 0.20
 +set g_balance_falldamage_maxdamage 40
 +set g_balance_damagepush_speedfactor 2.5
 +set g_balance_contents_damagerate 0.2 // ticrate interval for applying damage with playerdamage/projectiledamage
 +set g_balance_contents_drowndelay 10 // time under water before a player begins drowning
 +set g_balance_contents_playerdamage_drowning 20 // damage per second for while player is drowning
 +set g_balance_contents_playerdamage_lava 50 // damage per second for while player is inside lava
 +set g_balance_contents_playerdamage_slime 30 // damage per second for while player is inside slime
 +set g_balance_contents_projectiledamage 10000 // instantly kill projectiles upon touching lava/slime
 +set g_maxpushtime 8.0 "timeout for kill credit when your damage knocks someone into a death trap"
 +// }}}
 +
 +// {{{ powerups
 +set g_balance_powerup_invincible_takedamage 0.25 // only 1/4th damage is taken
 +set g_balance_powerup_invincible_time 30
 +set g_balance_powerup_strength_damage 3
 +set g_balance_powerup_strength_force 3
 +set g_balance_powerup_strength_time 30
 +set g_balance_powerup_strength_selfdamage 1.5
 +set g_balance_powerup_strength_selfforce 1.5
 +set g_balance_superweapons_time 30
 +// }}}
 +
 +// {{{ jetpack/hook
 +set g_jetpack_antigravity 0.8 "factor of gravity compensation of the jetpack"
 +set g_jetpack_acceleration_side 1200 "acceleration of the jetpack in xy direction"
 +set g_jetpack_acceleration_up 600 "acceleration of the jetpack in z direction (note: you have to factor in gravity here, if antigravity is not 1)"
 +set g_jetpack_maxspeed_side 1200 "max speed of the jetpack in xy direction"
 +set g_jetpack_maxspeed_up 600 "max speed of the jetpack in z direction"
 +set g_jetpack_fuel 8 "fuel per second for jetpack"
 +set g_jetpack_attenuation 2 "jetpack sound attenuation"
 +
 +set g_grappling_hook_tarzan 2 // 2: can also pull players
 +set g_balance_grapplehook_speed_fly 1800
 +set g_balance_grapplehook_speed_pull 2000
 +set g_balance_grapplehook_force_rubber 2000
 +set g_balance_grapplehook_force_rubber_overstretch 1000
 +set g_balance_grapplehook_length_min 50
 +set g_balance_grapplehook_stretch 50
 +set g_balance_grapplehook_airfriction 0.2
 +set g_balance_grapplehook_health 50
 +set g_balance_grapplehook_damagedbycontents 1
++set g_balance_grapplehook_refire 0.2
 +// }}}
 +
 +exec bal-wep-xonotic.cfg
diff --combined defaultXonotic.cfg
index f833ab0ec721ae759ca181973cc95ceb4f3af438,2c048b39eac92ecebba09fbd6006e7623a6ca201..fff503ebd76eba566e5d3153e7672fe75fc08a35
@@@ -56,8 -56,8 +56,8 @@@ _cl_playermodel models/player/erebus.iq
  _cl_playerskin 0
  
  seta cl_reticle 1 "control for toggling whether ANY zoom reticles are shown"
- seta cl_reticle_stretch 0 "whether to stretch reticles so they fit the screen (brakes image proportions)"
+ seta cl_reticle_stretch 0 "whether to stretch reticles so they fit the screen (breaks image proportions)"
 -seta cl_reticle_item_nex 1 "draw aiming reticle for the nex weapon's zoom, 0 disables and values between 0 and 1 change alpha"
 +seta cl_reticle_item_vortex 1 "draw aiming reticle for the vortex weapon's zoom, 0 disables and values between 0 and 1 change alpha"
  seta cl_reticle_item_normal 1 "draw reticle when zooming with the zoom button, 0 disables and values between 0 and 1 change alpha"
  fov 100
  seta cl_velocityzoom 0        "velocity based zooming of fov, negative values zoom out"
@@@ -224,6 -224,7 +224,7 @@@ seta cl_hitsound 1 "play a hit notifie
  set cl_hitsound_antispam_time 0.05 "don't play the hitsound more often than this"
  
  seta cl_eventchase_death 1 "camera goes into 3rd person mode when the player is dead"
+ seta cl_eventchase_nexball 1 "camera goes into 3rd person mode when in nexball game-mode"
  seta cl_eventchase_distance 140 "final camera distance"
  seta cl_eventchase_speed 1.3 "how fast the camera slides back, 0 is instant"
  seta cl_eventchase_maxs "12 12 8" "max size of eventchase camera bbox"
@@@ -359,9 -360,9 +360,9 @@@ set bot_ai_keyboard_threshold 0.5
  set bot_ai_aimskill_offset 0.3 "Amount of error induced to the bots aim"
  set bot_ai_aimskill_think 1 "Aiming velocity. Use values below 1 for slower aiming"
  set bot_ai_custom_weapon_priority_distances "300 850" "Define close and far distances in any order. Based on the distance to the enemy bots will choose different weapons"
 -set bot_ai_custom_weapon_priority_far   "minstanex nex rifle electro rocketlauncher grenadelauncher hagar hlac crylink laser uzi fireball seeker shotgun tuba minelayer"      "Desired weapons for far distances ordered by priority"
 -set bot_ai_custom_weapon_priority_mid   "minstanex rocketlauncher nex fireball seeker grenadelauncher electro uzi crylink hlac hagar shotgun laser rifle tuba minelayer"      "Desired weapons for middle distances ordered by priority"
 -set bot_ai_custom_weapon_priority_close "minstanex shotgun nex uzi hlac tuba seeker hagar crylink grenadelauncher electro rocketlauncher laser fireball rifle minelayer"      "Desired weapons for close distances ordered by priority"
 +set bot_ai_custom_weapon_priority_far   "vaporizer vortex rifle electro rocketlauncher grenadelauncher hagar hlac crylink laser machinegun fireball seeker shotgun tuba minelayer"    "Desired weapons for far distances ordered by priority"
 +set bot_ai_custom_weapon_priority_mid   "vaporizer rocketlauncher vortex fireball seeker grenadelauncher electro machinegun crylink hlac hagar shotgun laser rifle tuba minelayer"    "Desired weapons for middle distances ordered by priority"
 +set bot_ai_custom_weapon_priority_close "vaporizer shotgun vortex machinegun hlac tuba seeker hagar crylink grenadelauncher electro rocketlauncher laser fireball rifle minelayer"    "Desired weapons for close distances ordered by priority"
  set bot_ai_weapon_combo 1     "Enable bots to do weapon combos"
  set bot_ai_weapon_combo_threshold 0.4 "Try to make a combo N seconds after the last attack"
  set bot_ai_friends_aware_pickup_radius "500"  "Bots will not pickup items if a team mate is this distance near the item"
@@@ -1137,12 -1138,12 +1138,12 @@@ sv_allowdownloads 0 // download protoco
  
  set g_jump_grunt 0    "Do you make a grunting noise every time you jump? Is it the same grunting noise every time?"
  
 -seta cl_weaponpriority "minstanex nex fireball grenadelauncher uzi hagar rifle electro rocketlauncher crylink minelayer shotgun hlac tuba laser porto seeker hook" "weapon priority list"
 +seta cl_weaponpriority "minstanex vortex fireball grenadelauncher machinegun hagar rifle electro rocketlauncher crylink minelayer shotgun hlac tuba laser porto seeker hook" "weapon priority list"
  seta cl_weaponpriority_useforcycling 0 "when set, weapon cycling by the mouse wheel makes use of the weapon priority list (the special value 2 uses the weapon ID list for cycling)"
  seta cl_weaponpriority0 "rocketlauncher grenadelauncher hagar seeker fireball" "use impulse 200 for prev gun from this list, 210 for best gun, 220 for next gun.  Default value: explosives"
 -seta cl_weaponpriority1 "minstanex nex crylink hlac electro laser"             "use impulse 201 for prev gun from this list, 211 for best gun, 221 for next gun.  Default value: energy"
 -seta cl_weaponpriority2 "minstanex nex rifle"                           "use impulse 202 for prev gun from this list, 212 for best gun, 222 for next gun.  Default value: hitscan exact"
 -seta cl_weaponpriority3 "minstanex nex rifle uzi shotgun"               "use impulse 203 for prev gun from this list, 213 for best gun, 223 for next gun.  Default value: hitscan all"
 +seta cl_weaponpriority1 "minstanex vortex crylink hlac electro laser"             "use impulse 201 for prev gun from this list, 211 for best gun, 221 for next gun.  Default value: energy"
 +seta cl_weaponpriority2 "minstanex vortex rifle"                           "use impulse 202 for prev gun from this list, 212 for best gun, 222 for next gun.  Default value: hitscan exact"
 +seta cl_weaponpriority3 "minstanex vortex rifle machinegun shotgun"               "use impulse 203 for prev gun from this list, 213 for best gun, 223 for next gun.  Default value: hitscan all"
  seta cl_weaponpriority4 "grenadelauncher minelayer hlac hagar crylink seeker shotgun"    "use impulse 204 for prev gun from this list, 214 for best gun, 224 for next gun.  Default value: spam weapons"
  seta cl_weaponpriority5 "laser hook porto"                                     "use impulse 205 for prev gun from this list, 215 for best gun, 225 for next gun.  Default value: weapons for moving"
  seta cl_weaponpriority6 "" "use impulse 206 for prev gun from this list, 216 for best gun, 226 for next gun"
@@@ -1376,19 -1377,19 +1377,19 @@@ cl_decals_newsystem 
  // set the cvars to "0" to totally disable a weapon
  set g_weaponreplace_laser ""
  set g_weaponreplace_shotgun ""
 -set g_weaponreplace_uzi ""
 +set g_weaponreplace_machinegun ""
  set g_weaponreplace_grenadelauncher ""
  set g_weaponreplace_electro ""
  set g_weaponreplace_crylink ""
 -set g_weaponreplace_nex ""
 +set g_weaponreplace_vortex ""
  set g_weaponreplace_hagar ""
  set g_weaponreplace_rocketlauncher ""
  set g_weaponreplace_porto ""
 -set g_weaponreplace_minstanex ""
 +set g_weaponreplace_vaporizer ""
  set g_weaponreplace_hook ""
  set g_weaponreplace_tuba ""
  set g_weaponreplace_fireball ""
 -set sv_q3acompat_machineshotgunswap 0 "shorthand for swapping uzi and shotgun (for Q3A map compatibility in mapinfo files)"
 +set sv_q3acompat_machineshotgunswap 0 "shorthand for swapping machinegun and shotgun (for Q3A map compatibility in mapinfo files)"
  
  set g_movement_highspeed 1 "movement speed modification factor (only changes movement when above maxspeed)"
  
@@@ -1541,7 -1542,8 +1542,7 @@@ scr_loadingscreen_scale_base 
  scr_loadingscreen_scale_limit 2
  
  // other config files
 -exec mutator_new_toys.cfg // run BEFORE balance to make sure balance wins
 -exec balanceXonotic.cfg
 +exec balance-xonotic.cfg
  exec effects-normal.cfg
  exec physicsX.cfg
  exec turrets.cfg
diff --combined oldbalance25.cfg
index e32b459b003e898d96cd0403378fb5265a64b8c0,0000000000000000000000000000000000000000..df43b549ee297f478aa8ff26b4c7bcd2165315ab
mode 100644,000000..100644
--- /dev/null
@@@ -1,779 -1,0 +1,780 @@@
- set g_balance_hook_primary_refire 0 // hook monkeys set 0
 +g_mod_balance Nexuiz25
 +
 +// {{{ starting gear
 +set g_start_weapon_laser -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_shotgun -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_uzi -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_grenadelauncher -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_electro -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_crylink -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_nex -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_hagar -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_rocketlauncher -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_minstanex -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_porto -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_hook -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_tuba -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_fireball -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_balance_health_start 150
 +set g_balance_armor_start 0
 +set g_start_ammo_shells 40
 +set g_start_ammo_nails 0
 +set g_start_ammo_rockets 0
 +set g_start_ammo_cells 0
 +set g_start_ammo_fuel 0
 +set g_warmup_start_health 250 "starting values when being in warmup-stage"
 +set g_warmup_start_armor 100 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_shells 50 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_nails 150 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_rockets 50 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_cells 50 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_fuel 0 "starting values when being in warmup-stage"
 +set g_lms_start_health 250
 +set g_lms_start_armor 100
 +set g_lms_start_ammo_shells 50
 +set g_lms_start_ammo_nails 150
 +set g_lms_start_ammo_rockets 50
 +set g_lms_start_ammo_cells 50
 +set g_lms_start_ammo_fuel 0
 +set g_balance_nix_roundtime 25
 +set g_balance_nix_incrtime 1.6
 +set g_balance_nix_ammo_shells 15
 +set g_balance_nix_ammo_nails 45
 +set g_balance_nix_ammo_rockets 15
 +set g_balance_nix_ammo_cells 15
 +set g_balance_nix_ammo_fuel 0
 +set g_balance_nix_ammoincr_shells 2
 +set g_balance_nix_ammoincr_nails 6
 +set g_balance_nix_ammoincr_rockets 2
 +set g_balance_nix_ammoincr_cells 2
 +set g_balance_nix_ammoincr_fuel 2
 +// }}}
 +
 +// {{{ pickup items
 +set g_pickup_ammo_anyway 0
 +set g_pickup_weapons_anyway 0
 +set g_pickup_shells 15
 +set g_pickup_shells_weapon 15
 +set g_pickup_shells_max 999
 +set g_pickup_nails 80
 +set g_pickup_nails_weapon 80
 +set g_pickup_nails_max 999
 +set g_pickup_rockets 15
 +set g_pickup_rockets_weapon 15
 +set g_pickup_rockets_max 999
 +set g_pickup_cells 25
 +set g_pickup_cells_weapon 25
 +set g_pickup_cells_max 999
 +set g_pickup_fuel 25
 +set g_pickup_fuel_weapon 25
 +set g_pickup_fuel_jetpack 50
 +set g_pickup_fuel_max 999
 +set g_pickup_armorsmall 5
 +set g_pickup_armorsmall_max 999
 +set g_pickup_armorsmall_anyway 0
 +set g_pickup_armormedium 25
 +set g_pickup_armormedium_max 999
 +set g_pickup_armormedium_anyway 0
 +set g_pickup_armorbig 50
 +set g_pickup_armorbig_max 999
 +set g_pickup_armorbig_anyway 0
 +set g_pickup_armorlarge 100
 +set g_pickup_armorlarge_max 999
 +set g_pickup_armorlarge_anyway 0
 +set g_pickup_healthsmall 5
 +set g_pickup_healthsmall_max 999
 +set g_pickup_healthsmall_anyway 0
 +set g_pickup_healthmedium 25
 +set g_pickup_healthmedium_max 999
 +set g_pickup_healthmedium_anyway 0
 +set g_pickup_healthlarge 50
 +set g_pickup_healthlarge_max 999
 +set g_pickup_healthlarge_anyway 0
 +set g_pickup_healthmega 100
 +set g_pickup_healthmega_max 999
 +set g_pickup_healthmega_anyway 0
 +set g_pickup_respawntime_short 15
 +set g_pickup_respawntime_medium 20
 +set g_pickup_respawntime_long 30
 +set g_pickup_respawntime_powerup 120
 +set g_pickup_respawntime_weapon 15
 +set g_pickup_respawntime_superweapon 120
 +set g_pickup_respawntime_ammo 15
 +set g_pickup_respawntimejitter_short 0
 +set g_pickup_respawntimejitter_medium 0
 +set g_pickup_respawntimejitter_long 0
 +set g_pickup_respawntimejitter_powerup 10
 +set g_pickup_respawntimejitter_weapon 0
 +set g_pickup_respawntimejitter_superweapon 10
 +set g_pickup_respawntimejitter_ammo 0
 +// }}}
 +
 +// {{{ regen/rot
 +set g_balance_health_regen 0.1
 +set g_balance_health_regenlinear 0
 +set g_balance_pause_health_regen 5
 +set g_balance_pause_health_regen_spawn 0
 +set g_balance_health_rot 0.1
 +set g_balance_health_rotlinear 0
 +set g_balance_pause_health_rot 5
 +set g_balance_pause_health_rot_spawn 10
 +set g_balance_health_regenstable 100
 +set g_balance_health_rotstable 100
 +set g_balance_health_limit 999
 +set g_balance_armor_regen 0
 +set g_balance_armor_regenlinear 0
 +set g_balance_armor_rot 0.1
 +set g_balance_armor_rotlinear 0
 +set g_balance_pause_armor_rot 5
 +set g_balance_pause_armor_rot_spawn 10
 +set g_balance_armor_regenstable 100
 +set g_balance_armor_rotstable 100
 +set g_balance_armor_limit 999
 +set g_balance_armor_blockpercent 0.6
 +set g_balance_fuel_regen 0.1 "fuel regeneration (only applies if the player owns IT_FUEL_REGEN)"
 +set g_balance_fuel_regenlinear 0
 +set g_balance_pause_fuel_regen 2 // other than this, fuel uses the health regen counter
 +set g_balance_fuel_rot 0.05
 +set g_balance_fuel_rotlinear 0
 +set g_balance_pause_fuel_rot 5
 +set g_balance_pause_fuel_rot_spawn 10
 +set g_balance_fuel_regenstable 50
 +set g_balance_fuel_rotstable 100
 +set g_balance_fuel_limit 999
 +// }}}
 +
 +// {{{ misc
 +set g_balance_selfdamagepercent 0.6
 +set g_weaponspeedfactor 1 "weapon projectile speed multiplier"
 +set g_weaponratefactor 1 "weapon fire rate multiplier"
 +set g_weapondamagefactor 1 "weapon damage multiplier"
 +set g_weaponforcefactor 1 "weapon force multiplier"
 +set g_weaponspreadfactor 1 "weapon spread multiplier"
 +set g_balance_firetransfer_time 0.9
 +set g_balance_firetransfer_damage 0.8
 +set g_throughfloor_damage 1
 +set g_throughfloor_force 1
 +set g_projectiles_damage 2
 +// possible values:
 +// -2: absolutely no damage to projectiles (no exceptions)
 +// -1: no damage other than the exceptions (electro combo, hagar join explode, ML mines)
 +// 0: only damage from contents (lava/slime) or exceptions
 +// 1: only self damage or damage from contents or exceptions
 +// 2: allow all damage to projectiles normally
 +set g_projectiles_keep_owner 0
 +set g_projectiles_newton_style 2
 +// possible values:
 +// 0: absolute velocity projectiles (like Quake)
 +// 1: relative velocity projectiles, "Newtonian" (like Tribes 2)
 +// 2: relative velocity projectiles, but aim is precorrected so projectiles hit the crosshair (note: strafe rockets then are SLOWER than ones shot while standing, happens in 1 too when aiming correctly which is hard)
 +set g_projectiles_newton_style_2_minfactor 0.7
 +set g_projectiles_newton_style_2_maxfactor 5
 +set g_projectiles_spread_style 0
 +// possible values:
 +// 0: forward + solid sphere (like Quake) - varies velocity
 +// 1: forward + flattened solid sphere
 +// 2: forward + solid circle
 +// 3: forward + normal distribution 3D - varies velocity
 +// 4: forward + normal distribution on a plane
 +// 5: forward + circle with 1-r falloff
 +// 6: forward + circle with 1-r^2 falloff
 +// 7: forward + circle with (1-r)(2-r) falloff
 +set g_balance_falldamage_deadminspeed 150
 +set g_balance_falldamage_minspeed 1400
 +set g_balance_falldamage_factor 0.15
 +set g_balance_falldamage_maxdamage 25
 +set g_balance_damagepush_speedfactor 0
 +set g_balance_contents_damagerate 0.2 // ticrate interval for applying damage with playerdamage/projectiledamage
 +set g_balance_contents_drowndelay 10 // time under water before a player begins drowning
 +set g_balance_contents_playerdamage_drowning 20 // damage per second for while player is drowning
 +set g_balance_contents_playerdamage_lava 50 // damage per second for while player is inside lava
 +set g_balance_contents_playerdamage_slime 30 // damage per second for while player is inside slime
 +set g_balance_contents_projectiledamage 10000 // instantly kill projectiles upon touching lava/slime
 +set g_maxpushtime 8.0 "timeout for kill credit when your damage knocks someone into a death trap"
 +// }}}
 +
 +// {{{ powerups
 +set g_balance_powerup_invincible_takedamage 0.2
 +set g_balance_powerup_invincible_time 30
 +set g_balance_powerup_strength_damage 3
 +set g_balance_powerup_strength_force 4
 +set g_balance_powerup_strength_time 30
 +set g_balance_powerup_strength_selfdamage 1.5
 +set g_balance_powerup_strength_selfforce 1.5
 +set g_balance_superweapons_time 30
 +// }}}
 +
 +// {{{ jetpack/hook
 +set g_jetpack_antigravity 0.8 "factor of gravity compensation of the jetpack"
 +set g_jetpack_acceleration_side 1200 "acceleration of the jetpack in xy direction"
 +set g_jetpack_acceleration_up 600 "acceleration of the jetpack in z direction (note: you have to factor in gravity here, if antigravity is not 1)"
 +set g_jetpack_maxspeed_side 1500 "max speed of the jetpack in xy direction"
 +set g_jetpack_maxspeed_up 600 "max speed of the jetpack in z direction"
 +set g_jetpack_fuel 8 "fuel per second for jetpack"
 +set g_jetpack_attenuation 2 "jetpack sound attenuation"
 +
 +set g_grappling_hook_tarzan 2 // 2: can also pull players
 +set g_balance_grapplehook_speed_fly 1800
 +set g_balance_grapplehook_speed_pull 2000
 +set g_balance_grapplehook_force_rubber 2000
 +set g_balance_grapplehook_force_rubber_overstretch 1000
 +set g_balance_grapplehook_length_min 50
 +set g_balance_grapplehook_stretch 50
 +set g_balance_grapplehook_airfriction 0.2
 +set g_balance_grapplehook_health 130
 +set g_balance_grapplehook_damagedbycontents 0
++set g_balance_grapplehook_refire 0.2
 +// }}}
 +
 +// {{{ weapon properties
 +// {{{ laser
 +set g_balance_laser_melee_animtime 0.3
 +set g_balance_laser_melee_damage 80
 +set g_balance_laser_melee_delay 0.25
 +set g_balance_laser_melee_force 200
 +set g_balance_laser_melee_multihit 1
 +set g_balance_laser_melee_no_doubleslap 1
 +set g_balance_laser_melee_nonplayerdamage 40
 +set g_balance_laser_melee_range 120
 +set g_balance_laser_melee_refire 1.25
 +set g_balance_laser_melee_swing_side 120
 +set g_balance_laser_melee_swing_up 30
 +set g_balance_laser_melee_time 0.15
 +set g_balance_laser_melee_traces 10
 +
 +set g_balance_laser_primary 1 // 0 = shockwave attack, 1 = projectile primary
 +set g_balance_laser_primary_damage 35
 +set g_balance_laser_primary_edgedamage 10
 +set g_balance_laser_primary_force 400
 +set g_balance_laser_primary_radius 70
 +set g_balance_laser_primary_speed 9000
 +set g_balance_laser_primary_spread 0
 +set g_balance_laser_primary_refire 0.7
 +set g_balance_laser_primary_animtime 0.3
 +set g_balance_laser_primary_lifetime 30
 +set g_balance_laser_primary_shotangle 0
 +set g_balance_laser_primary_delay 0.05
 +set g_balance_laser_primary_force_zscale 1
 +set g_balance_laser_primary_force_velocitybias 0
 +set g_balance_laser_primary_force_other_scale 1
 +
 +set g_balance_laser_secondary 0 // 0 = switch away to last used weapon, 1 = projectile secondary, 2 = melee secondary
 +set g_balance_laser_secondary_damage 35
 +set g_balance_laser_secondary_edgedamage 10
 +set g_balance_laser_secondary_force 400
 +set g_balance_laser_secondary_radius 70
 +set g_balance_laser_secondary_speed 9000
 +set g_balance_laser_secondary_spread 0
 +set g_balance_laser_secondary_refire 0.7
 +set g_balance_laser_secondary_animtime 0.3
 +set g_balance_laser_secondary_lifetime 30
 +set g_balance_laser_secondary_shotangle 0
 +set g_balance_laser_secondary_delay 0
 +set g_balance_laser_secondary_force_zscale 1
 +set g_balance_laser_secondary_force_velocitybias 0
 +set g_balance_laser_secondary_force_other_scale 1
 +
 +set g_balance_laser_shockwave_damage 20
 +set g_balance_laser_shockwave_distance 2000
 +set g_balance_laser_shockwave_edgedamage 0
 +set g_balance_laser_shockwave_force 200
 +set g_balance_laser_shockwave_force_forwardbias 50
 +set g_balance_laser_shockwave_force_zscale 1.5
 +set g_balance_laser_shockwave_jump_damage 20
 +set g_balance_laser_shockwave_jump_edgedamage 0
 +set g_balance_laser_shockwave_jump_force 300
 +set g_balance_laser_shockwave_jump_force_velocitybias 0
 +set g_balance_laser_shockwave_jump_force_zscale 1.25
 +set g_balance_laser_shockwave_jump_multiplier_accuracy 0.5
 +set g_balance_laser_shockwave_jump_multiplier_distance 0.5
 +set g_balance_laser_shockwave_jump_multiplier_min 0
 +set g_balance_laser_shockwave_jump_radius 150
 +set g_balance_laser_shockwave_multiplier_accuracy 0.5
 +set g_balance_laser_shockwave_multiplier_distance 0.5
 +set g_balance_laser_shockwave_multiplier_min 0
 +set g_balance_laser_shockwave_splash_damage 15
 +set g_balance_laser_shockwave_splash_edgedamage 0
 +set g_balance_laser_shockwave_splash_force 100
 +set g_balance_laser_shockwave_splash_force_forwardbias 50
 +set g_balance_laser_shockwave_splash_multiplier_accuracy 0.5
 +set g_balance_laser_shockwave_splash_multiplier_distance 0.5
 +set g_balance_laser_shockwave_splash_multiplier_min 0
 +set g_balance_laser_shockwave_splash_radius 70
 +set g_balance_laser_shockwave_spread_max 100
 +set g_balance_laser_shockwave_spread_min 20
 +
 +set g_balance_laser_switchdelay_drop 0.15
 +set g_balance_laser_switchdelay_raise 0.15
 +set g_balance_laser_reload_ammo 0 //default: 6
 +set g_balance_laser_reload_time 2
 +// }}}
 +// {{{ shotgun
 +set g_balance_shotgun_primary_bullets 6
 +set g_balance_shotgun_primary_damage 9
 +set g_balance_shotgun_primary_force 60
 +set g_balance_shotgun_primary_spread 0.07
 +set g_balance_shotgun_primary_refire 0.5
 +set g_balance_shotgun_primary_animtime 0.2
 +set g_balance_shotgun_primary_ammo 1
 +set g_balance_shotgun_primary_solidpenetration 3.8
 +set g_balance_shotgun_secondary 1
 +set g_balance_shotgun_secondary_melee_delay 0.25 // 0.35 was too slow
 +set g_balance_shotgun_secondary_melee_range 120
 +set g_balance_shotgun_secondary_melee_swing_side 120
 +set g_balance_shotgun_secondary_melee_swing_up 30
 +set g_balance_shotgun_secondary_melee_time 0.15
 +set g_balance_shotgun_secondary_melee_traces 10
 +set g_balance_shotgun_secondary_melee_no_doubleslap 1
 +set g_balance_shotgun_secondary_melee_nonplayerdamage 0
 +set g_balance_shotgun_secondary_melee_multihit 1
 +set g_balance_shotgun_secondary_damage 115
 +set g_balance_shotgun_secondary_force 150
 +set g_balance_shotgun_secondary_refire 1.1
 +set g_balance_shotgun_secondary_animtime 1
 +set g_balance_shotgun_switchdelay_drop 0.15
 +set g_balance_shotgun_switchdelay_raise 0.15
 +set g_balance_shotgun_reload_ammo 0 //default: 5
 +set g_balance_shotgun_reload_time 2
 +// }}}
 +// {{{ uzi
 +set g_balance_uzi_mode 0                              // Activates varible spread for sustained & burst mode secondary
 +set g_balance_uzi_spread_min 0.02
 +set g_balance_uzi_spread_max 0.6
 +set g_balance_uzi_spread_add 0.012
 +
 +set g_balance_uzi_burst 0                             // # of bullets in a burst (if set to 2 or more)
 +set g_balance_uzi_burst_animtime 0.75
 +set g_balance_uzi_burst_refire 0.05           // refire between burst bullets
 +set g_balance_uzi_burst_refire2 0.75  // refire after burst
 +set g_balance_uzi_burst_spread 0.04
 +set g_balance_uzi_burst_damage 18
 +set g_balance_uzi_burst_force 50
 +set g_balance_uzi_burst_ammo 3
 +
 +set g_balance_uzi_first 1
 +set g_balance_uzi_first_damage 30
 +set g_balance_uzi_first_force 50
 +set g_balance_uzi_first_spread 0.015
 +set g_balance_uzi_first_refire 0.2
 +set g_balance_uzi_first_ammo 1
 +
 +set g_balance_uzi_sustained_damage 15
 +set g_balance_uzi_sustained_force 27
 +set g_balance_uzi_sustained_spread 0.05
 +set g_balance_uzi_sustained_refire 0.1
 +set g_balance_uzi_sustained_ammo 1
 +
 +set g_balance_uzi_solidpenetration 13.1
 +
 +set g_balance_uzi_switchdelay_drop 0.15
 +set g_balance_uzi_switchdelay_raise 0.15
 +
 +set g_balance_uzi_reload_ammo 0 //default: 30
 +set g_balance_uzi_reload_time 2
 +// }}}
 +// {{{ mortar
 +set g_balance_grenadelauncher_primary_type 0
 +set g_balance_grenadelauncher_primary_damage 70
 +set g_balance_grenadelauncher_primary_edgedamage 38
 +set g_balance_grenadelauncher_primary_force 400
 +set g_balance_grenadelauncher_primary_radius 140
 +set g_balance_grenadelauncher_primary_speed 2000
 +set g_balance_grenadelauncher_primary_speed_up 200
 +set g_balance_grenadelauncher_primary_speed_z 0
 +set g_balance_grenadelauncher_primary_spread 0
 +set g_balance_grenadelauncher_primary_lifetime 30
 +set g_balance_grenadelauncher_primary_lifetime2 1
 +set g_balance_grenadelauncher_primary_refire 0.8
 +set g_balance_grenadelauncher_primary_animtime 0.3
 +set g_balance_grenadelauncher_primary_ammo 2
 +set g_balance_grenadelauncher_primary_health 25
 +set g_balance_grenadelauncher_primary_damageforcescale 4
 +set g_balance_grenadelauncher_primary_remote_minbouncecnt 0
 +
 +set g_balance_grenadelauncher_secondary_type 1
 +set g_balance_grenadelauncher_secondary_damage 70
 +set g_balance_grenadelauncher_secondary_edgedamage 38
 +set g_balance_grenadelauncher_secondary_force 400
 +set g_balance_grenadelauncher_secondary_radius 140
 +set g_balance_grenadelauncher_secondary_speed 1400
 +set g_balance_grenadelauncher_secondary_speed_up 200
 +set g_balance_grenadelauncher_secondary_speed_z 0
 +set g_balance_grenadelauncher_secondary_spread 0
 +set g_balance_grenadelauncher_secondary_lifetime 2.5
 +set g_balance_grenadelauncher_secondary_lifetime_bounce 0
 +set g_balance_grenadelauncher_secondary_lifetime_stick 0
 +set g_balance_grenadelauncher_secondary_refire 0.7
 +set g_balance_grenadelauncher_secondary_animtime 0.3
 +set g_balance_grenadelauncher_secondary_ammo 2
 +set g_balance_grenadelauncher_secondary_health 10
 +set g_balance_grenadelauncher_secondary_damageforcescale 4
 +set g_balance_grenadelauncher_secondary_remote_detonateprimary 0
 +
 +set g_balance_grenadelauncher_bouncefactor 0.5
 +set g_balance_grenadelauncher_bouncestop 0.075
 +
 +set g_balance_grenadelauncher_switchdelay_drop 0.15
 +set g_balance_grenadelauncher_switchdelay_raise 0.15
 +
 +set g_balance_grenadelauncher_reload_ammo 0 //default: 12
 +set g_balance_grenadelauncher_reload_time 2
 +// }}}
 +// {{{ electro
 +set g_balance_electro_lightning 0
 +set g_balance_electro_primary_damage 65
 +set g_balance_electro_primary_edgedamage 0
 +set g_balance_electro_primary_force 200
 +set g_balance_electro_primary_force_up 0
 +set g_balance_electro_primary_radius 150
 +set g_balance_electro_primary_comboradius 0
 +set g_balance_electro_primary_speed 2000
 +set g_balance_electro_primary_spread 0
 +set g_balance_electro_primary_lifetime 30
 +set g_balance_electro_primary_refire 0.6
 +set g_balance_electro_primary_animtime 0.3
 +set g_balance_electro_primary_ammo 2
 +set g_balance_electro_primary_range 0
 +set g_balance_electro_primary_falloff_mindist 255 // 0.3 * radius
 +set g_balance_electro_primary_falloff_maxdist 850
 +set g_balance_electro_primary_falloff_halflifedist 425
 +set g_balance_electro_secondary_damage 50
 +set g_balance_electro_secondary_edgedamage 0
 +set g_balance_electro_secondary_force 200
 +set g_balance_electro_secondary_radius 150
 +set g_balance_electro_secondary_speed 900
 +set g_balance_electro_secondary_speed_up 200
 +set g_balance_electro_secondary_speed_z 0
 +set g_balance_electro_secondary_spread 0
 +set g_balance_electro_secondary_lifetime 5
 +set g_balance_electro_secondary_refire 0.3
 +set g_balance_electro_secondary_refire2 0
 +set g_balance_electro_secondary_animtime 0.3
 +set g_balance_electro_secondary_ammo 2
 +set g_balance_electro_secondary_health 5
 +set g_balance_electro_secondary_damageforcescale 4
 +set g_balance_electro_secondary_damagedbycontents 0
 +set g_balance_electro_secondary_count 1
 +set g_balance_electro_secondary_bouncefactor 0.5
 +set g_balance_electro_secondary_bouncestop 0.075
 +set g_balance_electro_combo_damage 80
 +set g_balance_electro_combo_edgedamage 0
 +set g_balance_electro_combo_force 200
 +set g_balance_electro_combo_radius 250
 +set g_balance_electro_combo_comboradius 0
 +set g_balance_electro_combo_speed 2000
 +set g_balance_electro_combo_safeammocheck 0
 +set g_balance_electro_switchdelay_drop 0.15
 +set g_balance_electro_switchdelay_raise 0.15
 +set g_balance_electro_reload_ammo 0 //default: 20
 +set g_balance_electro_reload_time 2
 +// }}}
 +// {{{ lightning
 +set g_balance_lightning_primary_ammo 5
 +set g_balance_lightning_primary_animtime 0.2
 +set g_balance_lightning_primary_damage 100
 +set g_balance_lightning_primary_edgedamage 0
 +set g_balance_lightning_primary_falloff_mindist 0
 +set g_balance_lightning_primary_falloff_maxdist 0
 +set g_balance_lightning_primary_falloff_halflifedist 0
 +set g_balance_lightning_primary_force 425
 +set g_balance_lightning_primary_lifetime 0
 +set g_balance_lightning_primary_radius 850
 +set g_balance_lightning_primary_range 800
 +set g_balance_lightning_primary_refire 0.4
 +set g_balance_lightning_primary_speed 0
 +set g_balance_lightning_primary_spread 0
 +set g_balance_lightning_secondary_ammo 5
 +set g_balance_lightning_secondary_animtime 0.5
 +set g_balance_lightning_secondary_damage 100
 +set g_balance_lightning_secondary_damageforcescale 4
 +set g_balance_lightning_secondary_edgedamage 80
 +set g_balance_lightning_secondary_flyingdamage 1
 +set g_balance_lightning_secondary_flyingforce -80
 +set g_balance_lightning_secondary_flyingradius 200
 +set g_balance_lightning_secondary_force -200
 +set g_balance_lightning_secondary_health 1
 +set g_balance_lightning_secondary_lifetime 30
 +set g_balance_lightning_secondary_radius 300
 +set g_balance_lightning_secondary_refire 5
 +set g_balance_lightning_secondary_speed 600
 +// }}}
 +// {{{ crylink
 +set g_balance_crylink_primary_damage 18
 +set g_balance_crylink_primary_edgedamage 0
 +set g_balance_crylink_primary_force -55
 +set g_balance_crylink_primary_radius 80
 +set g_balance_crylink_primary_speed 7000
 +set g_balance_crylink_primary_spread 0.03
 +set g_balance_crylink_primary_shots 4
 +set g_balance_crylink_primary_bounces 1
 +set g_balance_crylink_primary_refire 0.4
 +set g_balance_crylink_primary_animtime 0.3
 +set g_balance_crylink_primary_ammo 2
 +set g_balance_crylink_primary_bouncedamagefactor 0.5
 +set g_balance_crylink_primary_joindelay 0
 +set g_balance_crylink_primary_joinspread 0
 +set g_balance_crylink_primary_joinexplode 0
 +set g_balance_crylink_primary_joinexplode_damage 0
 +set g_balance_crylink_primary_joinexplode_edgedamage 0
 +set g_balance_crylink_primary_joinexplode_radius 0
 +set g_balance_crylink_primary_joinexplode_force 0
 +set g_balance_crylink_primary_linkexplode 1
 +
 +set g_balance_crylink_primary_middle_lifetime 5 // range: 35000 full, fades to 70000
 +set g_balance_crylink_primary_middle_fadetime 5
 +set g_balance_crylink_primary_other_lifetime 0.1 // range: 700 full, fades to 2450
 +set g_balance_crylink_primary_other_fadetime 0.25
 +
 +set g_balance_crylink_secondary 1
 +set g_balance_crylink_secondary_damage 18
 +set g_balance_crylink_secondary_edgedamage 0
 +set g_balance_crylink_secondary_force -55
 +set g_balance_crylink_secondary_radius 3
 +set g_balance_crylink_secondary_speed 7000
 +set g_balance_crylink_secondary_spread 0.08
 +set g_balance_crylink_secondary_spreadtype 0
 +set g_balance_crylink_secondary_shots 7
 +set g_balance_crylink_secondary_bounces 0
 +set g_balance_crylink_secondary_refire 0.5
 +set g_balance_crylink_secondary_animtime 0.3
 +set g_balance_crylink_secondary_ammo 2
 +set g_balance_crylink_secondary_bouncedamagefactor 0.5
 +set g_balance_crylink_secondary_joindelay 0
 +set g_balance_crylink_secondary_joinspread 0
 +set g_balance_crylink_secondary_joinexplode 0
 +set g_balance_crylink_secondary_joinexplode_damage 0
 +set g_balance_crylink_secondary_joinexplode_edgedamage 0
 +set g_balance_crylink_secondary_joinexplode_radius 0
 +set g_balance_crylink_secondary_joinexplode_force 0
 +set g_balance_crylink_secondary_linkexplode 1
 +
 +set g_balance_crylink_secondary_middle_lifetime 5 // range: 35000 full, fades to 70000
 +set g_balance_crylink_secondary_middle_fadetime 5
 +set g_balance_crylink_secondary_line_lifetime 2 // range: 35000 full, fades to 70000
 +set g_balance_crylink_secondary_line_fadetime 2
 +
 +set g_balance_crylink_switchdelay_drop 0.15
 +set g_balance_crylink_switchdelay_raise 0.15
 +
 +set g_balance_crylink_reload_ammo 0 //default: 10
 +set g_balance_crylink_reload_time 2
 +// }}}
 +// {{{ nex
 +set g_balance_nex_primary_damage 100
 +set g_balance_nex_primary_force 600
 +set g_balance_nex_primary_refire 1.5
 +set g_balance_nex_primary_animtime 0.3
 +set g_balance_nex_primary_ammo 5
 +set g_balance_nex_primary_damagefalloff_mindist 0
 +set g_balance_nex_primary_damagefalloff_maxdist 0
 +set g_balance_nex_primary_damagefalloff_halflife 0
 +set g_balance_nex_primary_damagefalloff_forcehalflife 0
 +
 +set g_balance_nex_secondary 0
 +set g_balance_nex_secondary_charge 0
 +set g_balance_nex_secondary_charge_rate 0.1
 +set g_balance_nex_secondary_chargepool 0
 +set g_balance_nex_secondary_chargepool_regen 0.15
 +set g_balance_nex_secondary_chargepool_pause_regen 1
 +set g_balance_nex_secondary_chargepool_pause_health_regen 1
 +set g_balance_nex_secondary_damage 100
 +set g_balance_nex_secondary_force 600
 +set g_balance_nex_secondary_refire 1.5
 +set g_balance_nex_secondary_animtime 0.3
 +set g_balance_nex_secondary_ammo 5
 +set g_balance_nex_secondary_damagefalloff_mindist 0
 +set g_balance_nex_secondary_damagefalloff_maxdist 0
 +set g_balance_nex_secondary_damagefalloff_halflife 0
 +set g_balance_nex_secondary_damagefalloff_forcehalflife 0
 +
 +set g_balance_nex_charge 0
 +set g_balance_nex_charge_mindmg 40
 +set g_balance_nex_charge_start 0
 +set g_balance_nex_charge_rate 0.1
 +set g_balance_nex_charge_animlimit 0.5
 +set g_balance_nex_charge_limit 0.5
 +set g_balance_nex_charge_rot_rate 0
 +set g_balance_nex_charge_rot_pause 0 // Dont rot down until this long after release of charge button
 +set g_balance_nex_charge_shot_multiplier 0.5
 +set g_balance_nex_charge_velocity_rate 0.2
 +set g_balance_nex_charge_minspeed 400
 +set g_balance_nex_charge_maxspeed 1000
 +
 +set g_balance_nex_switchdelay_drop 0.15
 +set g_balance_nex_switchdelay_raise 0.15
 +
 +set g_balance_nex_reload_ammo 0 //default: 25
 +set g_balance_nex_reload_time 2
 +// }}}
 +// {{{ minstanex
 +set g_balance_minstanex_refire 1
 +set g_balance_minstanex_animtime 0.3
 +set g_balance_minstanex_ammo 10
 +set g_balance_minstanex_laser_ammo 0
 +set g_balance_minstanex_laser_animtime 0.3
 +set g_balance_minstanex_laser_refire 0.7
 +set g_balance_minstanex_switchdelay_drop 0.15
 +set g_balance_minstanex_switchdelay_raise 0.15
 +set g_balance_minstanex_reload_ammo 0 //default: 50
 +set g_balance_minstanex_reload_time 2
 +// }}}
 +// {{{ hagar
 +set g_balance_hagar_primary_damage 37
 +set g_balance_hagar_primary_edgedamage 15
 +set g_balance_hagar_primary_force 100
 +set g_balance_hagar_primary_health 0
 +set g_balance_hagar_primary_damageforcescale 0
 +set g_balance_hagar_primary_radius 65
 +set g_balance_hagar_primary_spread 0.010
 +set g_balance_hagar_primary_speed 3000
 +set g_balance_hagar_primary_lifetime 30
 +set g_balance_hagar_primary_refire 0.15
 +set g_balance_hagar_primary_ammo 1
 +set g_balance_hagar_secondary 1
 +set g_balance_hagar_secondary_load 0
 +set g_balance_hagar_secondary_load_speed 0.6
 +set g_balance_hagar_secondary_load_spread 0.075
 +set g_balance_hagar_secondary_load_spread_bias 0.5
 +set g_balance_hagar_secondary_load_max 4
 +set g_balance_hagar_secondary_load_hold 0
 +set g_balance_hagar_secondary_load_releasedeath 1
 +set g_balance_hagar_secondary_load_abort 1
 +set g_balance_hagar_secondary_load_linkexplode 0
 +set g_balance_hagar_secondary_load_animtime 0.2
 +set g_balance_hagar_secondary_damage 37
 +set g_balance_hagar_secondary_edgedamage 15
 +set g_balance_hagar_secondary_force 100
 +set g_balance_hagar_secondary_health 0
 +set g_balance_hagar_secondary_damageforcescale 0
 +set g_balance_hagar_secondary_radius 65
 +set g_balance_hagar_secondary_spread 0.015
 +set g_balance_hagar_secondary_speed 1400
 +set g_balance_hagar_secondary_lifetime_min 30
 +set g_balance_hagar_secondary_lifetime_rand 0
 +set g_balance_hagar_secondary_refire 0.15
 +set g_balance_hagar_secondary_ammo 1
 +set g_balance_hagar_switchdelay_drop 0.15
 +set g_balance_hagar_switchdelay_raise 0.15
 +set g_balance_hagar_reload_ammo 0 //default: 25
 +set g_balance_hagar_reload_time 2
 +// }}}
 +// {{{ rocketlauncher
 +set g_balance_rocketlauncher_damage 105
 +set g_balance_rocketlauncher_edgedamage 40
 +set g_balance_rocketlauncher_force 600
 +set g_balance_rocketlauncher_radius 150
 +set g_balance_rocketlauncher_speed 850
 +set g_balance_rocketlauncher_speedaccel 0
 +set g_balance_rocketlauncher_speedstart 850
 +set g_balance_rocketlauncher_lifetime 30
 +set g_balance_rocketlauncher_refire 1
 +set g_balance_rocketlauncher_animtime 0.3
 +set g_balance_rocketlauncher_ammo 3
 +set g_balance_rocketlauncher_health 40
 +set g_balance_rocketlauncher_damageforcescale 4
 +set g_balance_rocketlauncher_detonatedelay 0.2 // positive: timer till detonation is allowed, negative: "security device" that prevents ANY remote detonation if it could hurt its owner, zero: detonatable at any time
 +set g_balance_rocketlauncher_guiderate 90 // max degrees per second
 +set g_balance_rocketlauncher_guideratedelay 0.01 // immediate
 +set g_balance_rocketlauncher_guidegoal 512 // goal distance for (non-laser) guiding (higher = less control, lower = erratic)
 +set g_balance_rocketlauncher_guidedelay 0.15 // delay before guiding kicks in
 +set g_balance_rocketlauncher_guidestop 0 // stop guiding when firing again
 +set g_balance_rocketlauncher_remote_damage 105
 +set g_balance_rocketlauncher_remote_edgedamage 40
 +set g_balance_rocketlauncher_remote_radius 150
 +set g_balance_rocketlauncher_remote_force 600
 +set g_balance_rocketlauncher_switchdelay_drop 0.15
 +set g_balance_rocketlauncher_switchdelay_raise 0.15
 +set g_balance_rocketlauncher_reload_ammo 0 //default: 25
 +set g_balance_rocketlauncher_reload_time 2
 +// }}}
 +// {{{ porto
 +set g_balance_porto_primary_refire 1.5
 +set g_balance_porto_primary_animtime 0.3
 +set g_balance_porto_primary_speed 2000
 +set g_balance_porto_primary_lifetime 30
 +set g_balance_porto_secondary 0
 +set g_balance_porto_secondary_refire 1.5
 +set g_balance_porto_secondary_animtime 0.3
 +set g_balance_porto_secondary_speed 2000
 +set g_balance_porto_secondary_lifetime 30
 +set g_balance_porto_switchdelay_drop 0.15
 +set g_balance_porto_switchdelay_raise 0.15
 +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
 +// }}}
 +// {{{ hook
 +set g_balance_hook_primary_fuel 5 // hook monkeys set 0
++set g_balance_hook_primary_refire 0.2 // hook monkeys set 0
 +set g_balance_hook_primary_animtime 0.3 // good shoot anim
 +set g_balance_hook_primary_hooked_time_max 0 // infinite
 +set g_balance_hook_primary_hooked_time_free 2 // 2s being hooked are free
 +set g_balance_hook_primary_hooked_fuel 5 // fuel per second hooked
 +set g_balance_hook_secondary_damage 25 // not much
 +set g_balance_hook_secondary_edgedamage 5 // not much
 +set g_balance_hook_secondary_radius 500 // LOTS
 +set g_balance_hook_secondary_force -2000 // LOTS
 +set g_balance_hook_secondary_ammo 50 // a whole pack
 +set g_balance_hook_secondary_lifetime 30 // infinite
 +set g_balance_hook_secondary_speed 0 // not much throwing
 +set g_balance_hook_secondary_gravity 5 // fast falling
 +set g_balance_hook_secondary_refire 3 // don't drop too many bombs...
 +set g_balance_hook_secondary_animtime 0.3 // good shoot anim
 +set g_balance_hook_secondary_power 3 // effect behaves like a square function
 +set g_balance_hook_secondary_duration 1.5 // effect runs for three seconds
 +set g_balance_hook_secondary_health 0
 +set g_balance_hook_secondary_damageforcescale 0
 +set g_balance_hook_switchdelay_drop 0.15
 +set g_balance_hook_switchdelay_raise 0.15
 +// }}}
 +// {{{ tuba
 +set g_balance_tuba_refire 0.05
 +set g_balance_tuba_animtime 0.05
 +set g_balance_tuba_attenuation 0.5
 +set g_balance_tuba_volume 1
 +set g_balance_tuba_fadetime 0.25
 +set g_balance_tuba_damage 5
 +set g_balance_tuba_edgedamage 0
 +set g_balance_tuba_radius 200
 +set g_balance_tuba_force 40
 +set g_balance_tuba_pitchstep 6
 +set g_balance_tuba_switchdelay_drop 0.15
 +set g_balance_tuba_switchdelay_raise 0.15
 +// }}}
 +// {{{ fireball
 +set g_balance_fireball_primary_animtime 0.15
 +set g_balance_fireball_primary_bfgdamage 100
 +set g_balance_fireball_primary_bfgforce 0
 +set g_balance_fireball_primary_bfgradius 1000
 +set g_balance_fireball_primary_damage 200
 +set g_balance_fireball_primary_damageforcescale 4
 +set g_balance_fireball_primary_edgedamage 0
 +set g_balance_fireball_primary_force 700
 +set g_balance_fireball_primary_health 50
 +set g_balance_fireball_primary_laserburntime 0.5
 +set g_balance_fireball_primary_laserdamage 80
 +set g_balance_fireball_primary_laseredgedamage 20
 +set g_balance_fireball_primary_laserradius 256
 +set g_balance_fireball_primary_lifetime 15
 +set g_balance_fireball_primary_radius 200
 +set g_balance_fireball_primary_refire 5
 +set g_balance_fireball_primary_refire2 0
 +set g_balance_fireball_primary_speed 650
 +set g_balance_fireball_primary_spread 0
 +set g_balance_fireball_secondary_animtime 0.3
 +set g_balance_fireball_secondary_damage 40
 +set g_balance_fireball_secondary_damageforcescale 4
 +set g_balance_fireball_secondary_damagetime 5
 +set g_balance_fireball_secondary_force 100
 +set g_balance_fireball_secondary_laserburntime 0.5
 +set g_balance_fireball_secondary_laserdamage 50
 +set g_balance_fireball_secondary_laseredgedamage 20
 +set g_balance_fireball_secondary_laserradius 110
 +set g_balance_fireball_secondary_lifetime 7
 +set g_balance_fireball_secondary_refire 2
 +set g_balance_fireball_secondary_speed 900
 +set g_balance_fireball_secondary_speed_up 100
 +set g_balance_fireball_secondary_speed_z 0
 +set g_balance_fireball_secondary_spread 0
 +set g_balance_fireball_switchdelay_drop 0.15
 +set g_balance_fireball_switchdelay_raise 0.15
 +// }}}
diff --combined oldbalanceFruitieX.cfg
index 844bdd59ee7b94e48c328c9865e5f48afd5c8e8f,0000000000000000000000000000000000000000..d5b6a9a2df43aa8065f922e83cf945564f51dac8
mode 100644,000000..100644
--- /dev/null
@@@ -1,779 -1,0 +1,780 @@@
- set g_balance_hook_primary_refire 0 // hook monkeys set 0
 +g_mod_balance FruitieX
 +
 +// {{{ starting gear
 +set g_start_weapon_laser -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_shotgun -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_uzi -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_grenadelauncher -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_electro -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_crylink -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_nex -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_hagar -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_rocketlauncher -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_minstanex -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_porto -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_hook -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_tuba -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_fireball -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_balance_health_start 125
 +set g_balance_armor_start 0
 +set g_start_ammo_shells 20
 +set g_start_ammo_nails 0
 +set g_start_ammo_rockets 0
 +set g_start_ammo_cells 0
 +set g_start_ammo_fuel 0
 +set g_warmup_start_health 200 "starting values when being in warmup-stage"
 +set g_warmup_start_armor 100 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_shells 50 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_nails 150 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_rockets 50 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_cells 50 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_fuel 0 "starting values when being in warmup-stage"
 +set g_lms_start_health 200
 +set g_lms_start_armor 100
 +set g_lms_start_ammo_shells 30
 +set g_lms_start_ammo_nails 200
 +set g_lms_start_ammo_rockets 150
 +set g_lms_start_ammo_cells 150
 +set g_lms_start_ammo_fuel 0
 +set g_balance_nix_roundtime 25
 +set g_balance_nix_incrtime 1.6
 +set g_balance_nix_ammo_shells 15
 +set g_balance_nix_ammo_nails 45
 +set g_balance_nix_ammo_rockets 15
 +set g_balance_nix_ammo_cells 15
 +set g_balance_nix_ammo_fuel 0
 +set g_balance_nix_ammoincr_shells 2
 +set g_balance_nix_ammoincr_nails 6
 +set g_balance_nix_ammoincr_rockets 2
 +set g_balance_nix_ammoincr_cells 2
 +set g_balance_nix_ammoincr_fuel 2
 +// }}}
 +
 +// {{{ pickup items
 +set g_pickup_ammo_anyway 1
 +set g_pickup_weapons_anyway 1
 +set g_pickup_shells 20
 +set g_pickup_shells_weapon 10
 +set g_pickup_shells_max 45
 +set g_pickup_nails 120
 +set g_pickup_nails_weapon 60
 +set g_pickup_nails_max 300
 +set g_pickup_rockets 25
 +set g_pickup_rockets_weapon 15
 +set g_pickup_rockets_max 150
 +set g_pickup_cells 30
 +set g_pickup_cells_weapon 20
 +set g_pickup_cells_max 150
 +set g_pickup_fuel 25
 +set g_pickup_fuel_weapon 15
 +set g_pickup_fuel_jetpack 50
 +set g_pickup_fuel_max 100
 +set g_pickup_armorsmall 5
 +set g_pickup_armorsmall_max 150
 +set g_pickup_armorsmall_anyway 1
 +set g_pickup_armormedium 25
 +set g_pickup_armormedium_max 50
 +set g_pickup_armormedium_anyway 0
 +set g_pickup_armorbig 50
 +set g_pickup_armorbig_max 75; // LOG: to allow a little more armor from medium armor
 +set g_pickup_armorbig_anyway 0
 +set g_pickup_armorlarge 100
 +set g_pickup_armorlarge_max 150
 +set g_pickup_armorlarge_anyway 1
 +set g_pickup_healthsmall 5
 +set g_pickup_healthsmall_max 250
 +set g_pickup_healthsmall_anyway 1
 +set g_pickup_healthmedium 25
 +set g_pickup_healthmedium_max 100
 +set g_pickup_healthmedium_anyway 0
 +set g_pickup_healthlarge 50
 +set g_pickup_healthlarge_max 150
 +set g_pickup_healthlarge_anyway 0
 +set g_pickup_healthmega 100
 +set g_pickup_healthmega_max 250
 +set g_pickup_healthmega_anyway 1
 +set g_pickup_respawntime_short 15
 +set g_pickup_respawntime_medium 20
 +set g_pickup_respawntime_long 30
 +set g_pickup_respawntime_powerup 120
 +set g_pickup_respawntime_weapon 10
 +set g_pickup_respawntime_superweapon 120
 +set g_pickup_respawntime_ammo 25
 +set g_pickup_respawntimejitter_short 0
 +set g_pickup_respawntimejitter_medium 0
 +set g_pickup_respawntimejitter_long 0
 +set g_pickup_respawntimejitter_powerup 10
 +set g_pickup_respawntimejitter_weapon 0
 +set g_pickup_respawntimejitter_superweapon 10
 +set g_pickup_respawntimejitter_ammo 0
 +// }}}
 +
 +// {{{ regen/rot
 +set g_balance_health_regen 0.05
 +set g_balance_health_regenlinear 0
 +set g_balance_pause_health_regen 5
 +set g_balance_pause_health_regen_spawn 0
 +set g_balance_health_rot 0
 +set g_balance_health_rotlinear 1
 +set g_balance_pause_health_rot 1
 +set g_balance_pause_health_rot_spawn 0
 +set g_balance_health_regenstable 100
 +set g_balance_health_rotstable 100
 +set g_balance_health_limit 999
 +set g_balance_armor_regen 0
 +set g_balance_armor_regenlinear 0
 +set g_balance_armor_rot 0
 +set g_balance_armor_rotlinear 1
 +set g_balance_pause_armor_rot 1
 +set g_balance_pause_armor_rot_spawn 0
 +set g_balance_armor_regenstable 100
 +set g_balance_armor_rotstable 100
 +set g_balance_armor_limit 999
 +set g_balance_armor_blockpercent 0.7
 +set g_balance_fuel_regen 0.1 "fuel regeneration (only applies if the player owns IT_FUEL_REGEN)"
 +set g_balance_fuel_regenlinear 0
 +set g_balance_pause_fuel_regen 2 // other than this, fuel uses the health regen counter
 +set g_balance_fuel_rot 0.05
 +set g_balance_fuel_rotlinear 0
 +set g_balance_pause_fuel_rot 5
 +set g_balance_pause_fuel_rot_spawn 10
 +set g_balance_fuel_regenstable 50
 +set g_balance_fuel_rotstable 100
 +set g_balance_fuel_limit 999
 +// }}}
 +
 +// {{{ misc
 +set g_balance_selfdamagepercent 0.65
 +set g_weaponspeedfactor 1 "weapon projectile speed multiplier"
 +set g_weaponratefactor 1 "weapon fire rate multiplier"
 +set g_weapondamagefactor 1 "weapon damage multiplier"
 +set g_weaponforcefactor 1 "weapon force multiplier"
 +set g_weaponspreadfactor 1 "weapon spread multiplier"
 +set g_balance_firetransfer_time 0.9
 +set g_balance_firetransfer_damage 0.8
 +set g_throughfloor_damage 0.7
 +set g_throughfloor_force 0.8
 +set g_projectiles_damage 2
 +// possible values:
 +// -2: absolutely no damage to projectiles (no exceptions)
 +// -1: no damage other than the exceptions (electro combo, hagar join explode, ML mines)
 +// 0: only damage from contents (lava/slime) or exceptions
 +// 1: only self damage or damage from contents or exceptions
 +// 2: allow all damage to projectiles normally
 +set g_projectiles_keep_owner 0
 +set g_projectiles_newton_style 2
 +// possible values:
 +// 0: absolute velocity projectiles (like Quake)
 +// 1: relative velocity projectiles, "Newtonian" (like Tribes 2)
 +// 2: relative velocity projectiles, but aim is precorrected so projectiles hit the crosshair (note: strafe rockets then are SLOWER than ones shot while standing, happens in 1 too when aiming correctly which is hard)
 +set g_projectiles_newton_style_2_minfactor 0.7
 +set g_projectiles_newton_style_2_maxfactor 5
 +set g_projectiles_spread_style 7
 +// possible values:
 +// 0: forward + solid sphere (like Quake) - varies velocity
 +// 1: forward + flattened solid sphere
 +// 2: forward + solid circle
 +// 3: forward + normal distribution 3D - varies velocity
 +// 4: forward + normal distribution on a plane
 +// 5: forward + circle with 1-r falloff
 +// 6: forward + circle with 1-r^2 falloff
 +// 7: forward + circle with (1-r)(2-r) falloff
 +set g_balance_falldamage_deadminspeed 150
 +set g_balance_falldamage_minspeed 800
 +set g_balance_falldamage_factor 0.20
 +set g_balance_falldamage_maxdamage 15
 +set g_balance_damagepush_speedfactor 2.5
 +set g_balance_contents_damagerate 0.2 // ticrate interval for applying damage with playerdamage/projectiledamage
 +set g_balance_contents_drowndelay 10 // time under water before a player begins drowning
 +set g_balance_contents_playerdamage_drowning 20 // damage per second for while player is drowning
 +set g_balance_contents_playerdamage_lava 50 // damage per second for while player is inside lava
 +set g_balance_contents_playerdamage_slime 30 // damage per second for while player is inside slime
 +set g_balance_contents_projectiledamage 10000 // instantly kill projectiles upon touching lava/slime
 +set g_maxpushtime 8.0 "timeout for kill credit when your damage knocks someone into a death trap"
 +// }}}
 +
 +// {{{ powerups
 +set g_balance_powerup_invincible_takedamage 0.6
 +set g_balance_powerup_invincible_time 30
 +set g_balance_powerup_strength_damage 3
 +set g_balance_powerup_strength_force 4
 +set g_balance_powerup_strength_time 30
 +set g_balance_powerup_strength_selfdamage 1.5
 +set g_balance_powerup_strength_selfforce 1.5
 +set g_balance_superweapons_time 30
 +// }}}
 +
 +// {{{ jetpack/hook
 +set g_jetpack_antigravity 0.8 "factor of gravity compensation of the jetpack"
 +set g_jetpack_acceleration_side 1200 "acceleration of the jetpack in xy direction"
 +set g_jetpack_acceleration_up 600 "acceleration of the jetpack in z direction (note: you have to factor in gravity here, if antigravity is not 1)"
 +set g_jetpack_maxspeed_side 1500 "max speed of the jetpack in xy direction"
 +set g_jetpack_maxspeed_up 600 "max speed of the jetpack in z direction"
 +set g_jetpack_fuel 8 "fuel per second for jetpack"
 +set g_jetpack_attenuation 2 "jetpack sound attenuation"
 +
 +set g_grappling_hook_tarzan 2 // 2: can also pull players
 +set g_balance_grapplehook_speed_fly 1800
 +set g_balance_grapplehook_speed_pull 2000
 +set g_balance_grapplehook_force_rubber 2000
 +set g_balance_grapplehook_force_rubber_overstretch 1000
 +set g_balance_grapplehook_length_min 50
 +set g_balance_grapplehook_stretch 50
 +set g_balance_grapplehook_airfriction 0.2
 +set g_balance_grapplehook_health 130
 +set g_balance_grapplehook_damagedbycontents 0
++set g_balance_grapplehook_refire 0.2
 +// }}}
 +
 +// {{{ weapon properties
 +// {{{ laser
 +set g_balance_laser_melee_animtime 0.3
 +set g_balance_laser_melee_damage 80
 +set g_balance_laser_melee_delay 0.25
 +set g_balance_laser_melee_force 200
 +set g_balance_laser_melee_multihit 1
 +set g_balance_laser_melee_no_doubleslap 1
 +set g_balance_laser_melee_nonplayerdamage 40
 +set g_balance_laser_melee_range 120
 +set g_balance_laser_melee_refire 1.25
 +set g_balance_laser_melee_swing_side 120
 +set g_balance_laser_melee_swing_up 30
 +set g_balance_laser_melee_time 0.15
 +set g_balance_laser_melee_traces 10
 +
 +set g_balance_laser_primary 1 // 0 = shockwave attack, 1 = projectile primary
 +set g_balance_laser_primary_damage 20 // dps 33, hope that's not too high
 +set g_balance_laser_primary_edgedamage 20
 +set g_balance_laser_primary_force 150 // this looks insanely low, but actually isn't with zscale and velocitybias
 +set g_balance_laser_primary_radius 60
 +set g_balance_laser_primary_speed 5000
 +set g_balance_laser_primary_spread 0
 +set g_balance_laser_primary_refire 0.6
 +set g_balance_laser_primary_animtime 0.4
 +set g_balance_laser_primary_lifetime 5
 +set g_balance_laser_primary_shotangle 0
 +set g_balance_laser_primary_delay 0
 +set g_balance_laser_primary_force_zscale 2 // 300 upforce
 +set g_balance_laser_primary_force_velocitybias 0.3
 +set g_balance_laser_primary_force_other_scale 2.5 // force 375 when pushing others around
 +
 +set g_balance_laser_secondary 0 // 0 = switch away to last used weapon, 1 = projectile secondary, 2 = melee secondary
 +set g_balance_laser_secondary_damage 200 // dps
 +set g_balance_laser_secondary_edgedamage 0
 +set g_balance_laser_secondary_force 1300
 +set g_balance_laser_secondary_radius 60
 +set g_balance_laser_secondary_speed 0
 +set g_balance_laser_secondary_spread 0
 +set g_balance_laser_secondary_refire 0.066
 +set g_balance_laser_secondary_animtime 0.066
 +set g_balance_laser_secondary_lifetime 0
 +set g_balance_laser_secondary_shotangle 0
 +set g_balance_laser_secondary_delay 0
 +set g_balance_laser_secondary_force_zscale 1.25
 +set g_balance_laser_secondary_force_velocitybias 0
 +set g_balance_laser_secondary_force_other_scale 0
 +
 +set g_balance_laser_shockwave_damage 20
 +set g_balance_laser_shockwave_distance 2000
 +set g_balance_laser_shockwave_edgedamage 0
 +set g_balance_laser_shockwave_force 200
 +set g_balance_laser_shockwave_force_forwardbias 50
 +set g_balance_laser_shockwave_force_zscale 1.5
 +set g_balance_laser_shockwave_jump_damage 20
 +set g_balance_laser_shockwave_jump_edgedamage 0
 +set g_balance_laser_shockwave_jump_force 300
 +set g_balance_laser_shockwave_jump_force_velocitybias 0
 +set g_balance_laser_shockwave_jump_force_zscale 1.25
 +set g_balance_laser_shockwave_jump_multiplier_accuracy 0.5
 +set g_balance_laser_shockwave_jump_multiplier_distance 0.5
 +set g_balance_laser_shockwave_jump_multiplier_min 0
 +set g_balance_laser_shockwave_jump_radius 150
 +set g_balance_laser_shockwave_multiplier_accuracy 0.5
 +set g_balance_laser_shockwave_multiplier_distance 0.5
 +set g_balance_laser_shockwave_multiplier_min 0
 +set g_balance_laser_shockwave_splash_damage 15
 +set g_balance_laser_shockwave_splash_edgedamage 0
 +set g_balance_laser_shockwave_splash_force 100
 +set g_balance_laser_shockwave_splash_force_forwardbias 50
 +set g_balance_laser_shockwave_splash_multiplier_accuracy 0.5
 +set g_balance_laser_shockwave_splash_multiplier_distance 0.5
 +set g_balance_laser_shockwave_splash_multiplier_min 0
 +set g_balance_laser_shockwave_splash_radius 70
 +set g_balance_laser_shockwave_spread_max 100
 +set g_balance_laser_shockwave_spread_min 20
 +
 +set g_balance_laser_switchdelay_drop 0.15
 +set g_balance_laser_switchdelay_raise 0.15
 +set g_balance_laser_reload_ammo 0 //default: 6
 +set g_balance_laser_reload_time 2
 +// }}}
 +// {{{ shotgun
 +set g_balance_shotgun_primary_bullets 18
 +set g_balance_shotgun_primary_damage 3.5 // LOG: changed from 4 to 3.5, total damage 63
 +set g_balance_shotgun_primary_force 20
 +set g_balance_shotgun_primary_spread 0.16 // LOG: changed from 0.18 -> 0.16 to compensate a little for lower damage
 +set g_balance_shotgun_primary_refire 1
 +set g_balance_shotgun_primary_animtime 0.3
 +set g_balance_shotgun_primary_ammo 1
 +set g_balance_shotgun_primary_solidpenetration 3.8
 +set g_balance_shotgun_secondary 1
 +set g_balance_shotgun_secondary_melee_delay 0.25 // 0.35 was too slow
 +set g_balance_shotgun_secondary_melee_range 120
 +set g_balance_shotgun_secondary_melee_swing_side 120
 +set g_balance_shotgun_secondary_melee_swing_up 30
 +set g_balance_shotgun_secondary_melee_time 0.15
 +set g_balance_shotgun_secondary_melee_traces 10
 +set g_balance_shotgun_secondary_melee_no_doubleslap 1
 +set g_balance_shotgun_secondary_melee_nonplayerdamage 0
 +set g_balance_shotgun_secondary_melee_multihit 1
 +set g_balance_shotgun_secondary_damage 110
 +set g_balance_shotgun_secondary_force 150
 +set g_balance_shotgun_secondary_refire 1.1
 +set g_balance_shotgun_secondary_animtime 1
 +set g_balance_shotgun_switchdelay_drop 0.15
 +set g_balance_shotgun_switchdelay_raise 0.15
 +set g_balance_shotgun_reload_ammo 0 //default: 5
 +set g_balance_shotgun_reload_time 2
 +// }}}
 +// {{{ uzi
 +set g_balance_uzi_mode 1                              // Activates varible spread for sustained & burst mode secondary
 +set g_balance_uzi_spread_min 0.02
 +set g_balance_uzi_spread_max 0.3 // LOG: 0.6 -> 0.3
 +set g_balance_uzi_spread_add 0.008
 +
 +set g_balance_uzi_burst 3                             // # of bullets in a burst (if set to 2 or more)
 +set g_balance_uzi_burst_animtime 0.45
 +set g_balance_uzi_burst_refire 0.05           // refire between burst bullets
 +set g_balance_uzi_burst_refire2 0.45  // refire after burst
 +set g_balance_uzi_burst_spread 0.07
 +set g_balance_uzi_burst_damage 25
 +set g_balance_uzi_burst_force 50
 +set g_balance_uzi_burst_ammo 3
 +
 +set g_balance_uzi_first 1
 +set g_balance_uzi_first_damage 15 / f/ LOG: 22 -> 15
 +set g_balance_uzi_first_force 50
 +set g_balance_uzi_first_spread 0.03
 +set g_balance_uzi_first_refire 0.2
 +set g_balance_uzi_first_ammo 2
 +
 +set g_balance_uzi_sustained_damage 12   // 120 dps
 +set g_balance_uzi_sustained_force 12
 +set g_balance_uzi_sustained_spread 0.06
 +set g_balance_uzi_sustained_refire 0.1
 +set g_balance_uzi_sustained_ammo 1
 +
 +set g_balance_uzi_solidpenetration 13.1
 +
 +set g_balance_uzi_switchdelay_drop 0.15
 +set g_balance_uzi_switchdelay_raise 0.15
 +
 +set g_balance_uzi_reload_ammo 0 //default: 30
 +set g_balance_uzi_reload_time 2
 +// }}}
 +// {{{ mortar
 +set g_balance_grenadelauncher_primary_type 0
 +set g_balance_grenadelauncher_primary_damage 44
 +set g_balance_grenadelauncher_primary_edgedamage 32
 +set g_balance_grenadelauncher_primary_force 300
 +set g_balance_grenadelauncher_primary_radius 115
 +set g_balance_grenadelauncher_primary_speed 1500
 +set g_balance_grenadelauncher_primary_speed_up 225
 +set g_balance_grenadelauncher_primary_speed_z 0
 +set g_balance_grenadelauncher_primary_spread 0
 +set g_balance_grenadelauncher_primary_lifetime 5
 +set g_balance_grenadelauncher_primary_lifetime2 0.65
 +set g_balance_grenadelauncher_primary_refire 0.8
 +set g_balance_grenadelauncher_primary_animtime 0.3
 +set g_balance_grenadelauncher_primary_ammo 2
 +set g_balance_grenadelauncher_primary_health 80
 +set g_balance_grenadelauncher_primary_damageforcescale 0
 +set g_balance_grenadelauncher_primary_remote_minbouncecnt 0
 +
 +set g_balance_grenadelauncher_secondary_type 1
 +set g_balance_grenadelauncher_secondary_damage 62
 +set g_balance_grenadelauncher_secondary_edgedamage 32
 +set g_balance_grenadelauncher_secondary_force 300
 +set g_balance_grenadelauncher_secondary_radius 150
 +set g_balance_grenadelauncher_secondary_speed 1000
 +set g_balance_grenadelauncher_secondary_speed_up 250
 +set g_balance_grenadelauncher_secondary_speed_z 0
 +set g_balance_grenadelauncher_secondary_spread 0
 +set g_balance_grenadelauncher_secondary_lifetime 3
 +set g_balance_grenadelauncher_secondary_lifetime_bounce 0
 +set g_balance_grenadelauncher_secondary_lifetime_stick 0.65
 +set g_balance_grenadelauncher_secondary_refire 0.8
 +set g_balance_grenadelauncher_secondary_animtime 0.3
 +set g_balance_grenadelauncher_secondary_ammo 2
 +set g_balance_grenadelauncher_secondary_health 40
 +set g_balance_grenadelauncher_secondary_damageforcescale 0
 +set g_balance_grenadelauncher_secondary_remote_detonateprimary 0
 +
 +set g_balance_grenadelauncher_bouncefactor 0.5
 +set g_balance_grenadelauncher_bouncestop 0.12
 +
 +set g_balance_grenadelauncher_switchdelay_drop 0.15
 +set g_balance_grenadelauncher_switchdelay_raise 0.15
 +
 +set g_balance_grenadelauncher_reload_ammo 0 //default: 12
 +set g_balance_grenadelauncher_reload_time 2
 +// }}}
 +// {{{ electro
 +set g_balance_electro_lightning 1
 +set g_balance_electro_primary_damage 100
 +set g_balance_electro_primary_edgedamage 0
 +set g_balance_electro_primary_force 425
 +set g_balance_electro_primary_force_up 125
 +set g_balance_electro_primary_radius 850
 +set g_balance_electro_primary_comboradius 150
 +set g_balance_electro_primary_speed 0
 +set g_balance_electro_primary_spread 0
 +set g_balance_electro_primary_lifetime 0
 +set g_balance_electro_primary_refire 0.4
 +set g_balance_electro_primary_animtime 0.2
 +set g_balance_electro_primary_ammo 5
 +set g_balance_electro_primary_range 800
 +set g_balance_electro_primary_falloff_mindist 0
 +set g_balance_electro_primary_falloff_maxdist 0
 +set g_balance_electro_primary_falloff_halflifedist 0
 +set g_balance_electro_secondary_damage 25
 +set g_balance_electro_secondary_edgedamage 0
 +set g_balance_electro_secondary_force 100
 +set g_balance_electro_secondary_radius 100
 +set g_balance_electro_secondary_speed 700
 +set g_balance_electro_secondary_speed_up 200
 +set g_balance_electro_secondary_speed_z 0
 +set g_balance_electro_secondary_spread 0.08
 +set g_balance_electro_secondary_lifetime 3.5
 +set g_balance_electro_secondary_refire 0.2
 +set g_balance_electro_secondary_refire2 2
 +set g_balance_electro_secondary_animtime 0.2
 +set g_balance_electro_secondary_ammo 2
 +set g_balance_electro_secondary_health 10
 +set g_balance_electro_secondary_damageforcescale 4
 +set g_balance_electro_secondary_damagedbycontents 0
 +set g_balance_electro_secondary_count 3
 +set g_balance_electro_secondary_bouncefactor 0.5
 +set g_balance_electro_secondary_bouncestop 0.075
 +set g_balance_electro_combo_damage 50
 +set g_balance_electro_combo_edgedamage 0
 +set g_balance_electro_combo_force 80
 +set g_balance_electro_combo_radius 250
 +set g_balance_electro_combo_comboradius 0
 +set g_balance_electro_combo_speed 400
 +set g_balance_electro_combo_safeammocheck 1
 +set g_balance_electro_switchdelay_drop 0.15
 +set g_balance_electro_switchdelay_raise 0.15
 +set g_balance_electro_reload_ammo 0 //default: 20
 +set g_balance_electro_reload_time 2
 +// }}}
 +// {{{ lightning
 +set g_balance_lightning_primary_ammo 5
 +set g_balance_lightning_primary_animtime 0.2
 +set g_balance_lightning_primary_damage 100
 +set g_balance_lightning_primary_edgedamage 0
 +set g_balance_lightning_primary_falloff_mindist 0
 +set g_balance_lightning_primary_falloff_maxdist 0
 +set g_balance_lightning_primary_falloff_halflifedist 0
 +set g_balance_lightning_primary_force 425
 +set g_balance_lightning_primary_lifetime 0
 +set g_balance_lightning_primary_radius 850
 +set g_balance_lightning_primary_range 800
 +set g_balance_lightning_primary_refire 0.4
 +set g_balance_lightning_primary_speed 0
 +set g_balance_lightning_primary_spread 0
 +set g_balance_lightning_secondary_ammo 5
 +set g_balance_lightning_secondary_animtime 0.5
 +set g_balance_lightning_secondary_damage 100
 +set g_balance_lightning_secondary_damageforcescale 4
 +set g_balance_lightning_secondary_edgedamage 80
 +set g_balance_lightning_secondary_flyingdamage 1
 +set g_balance_lightning_secondary_flyingforce -80
 +set g_balance_lightning_secondary_flyingradius 200
 +set g_balance_lightning_secondary_force -200
 +set g_balance_lightning_secondary_health 1
 +set g_balance_lightning_secondary_lifetime 30
 +set g_balance_lightning_secondary_radius 300
 +set g_balance_lightning_secondary_refire 5
 +set g_balance_lightning_secondary_speed 600
 +// }}}
 +// {{{ crylink
 +set g_balance_crylink_primary_damage 7 // LOG: 10 -> 7
 +set g_balance_crylink_primary_edgedamage 4 // LOG: 6 -> 4
 +set g_balance_crylink_primary_force 35
 +set g_balance_crylink_primary_radius 80
 +set g_balance_crylink_primary_speed 1500
 +set g_balance_crylink_primary_spread 0.05
 +set g_balance_crylink_primary_shots 7
 +set g_balance_crylink_primary_bounces 2
 +set g_balance_crylink_primary_refire 0.8
 +set g_balance_crylink_primary_animtime 0.3
 +set g_balance_crylink_primary_ammo 2
 +set g_balance_crylink_primary_bouncedamagefactor 0.2
 +set g_balance_crylink_primary_joindelay 0
 +set g_balance_crylink_primary_joinspread 0.2
 +set g_balance_crylink_primary_joinexplode 0
 +set g_balance_crylink_primary_joinexplode_damage 0
 +set g_balance_crylink_primary_joinexplode_edgedamage 0
 +set g_balance_crylink_primary_joinexplode_radius 0
 +set g_balance_crylink_primary_joinexplode_force 0
 +set g_balance_crylink_primary_linkexplode 1
 +
 +set g_balance_crylink_primary_middle_lifetime 5 // range: 10000 full, fades to 20000
 +set g_balance_crylink_primary_middle_fadetime 5
 +set g_balance_crylink_primary_other_lifetime 2 // range: 800 full, fades to 1300
 +set g_balance_crylink_primary_other_fadetime 0.25
 +
 +set g_balance_crylink_secondary 1
 +set g_balance_crylink_secondary_damage 5 // LOG: 8 -> 5
 +set g_balance_crylink_secondary_edgedamage 3
 +set g_balance_crylink_secondary_force 16 // LOG: 20 -> 16
 +set g_balance_crylink_secondary_radius 15 // LOG: 20 -> 15
 +set g_balance_crylink_secondary_speed 1250 // LOG: 1500 -> 1250
 +set g_balance_crylink_secondary_spread 0.1
 +set g_balance_crylink_secondary_spreadtype 0
 +set g_balance_crylink_secondary_shots 6
 +set g_balance_crylink_secondary_bounces 2
 +set g_balance_crylink_secondary_refire 0.9 // LOG: 0.8 -> 0.9
 +set g_balance_crylink_secondary_animtime 0.3
 +set g_balance_crylink_secondary_ammo 3 // LOG: 2 -> 3
 +set g_balance_crylink_secondary_bouncedamagefactor 0.4 // LOG: 0.2 -> 0.4
 +set g_balance_crylink_secondary_joindelay 0
 +set g_balance_crylink_secondary_joinspread 0.2
 +set g_balance_crylink_secondary_joinexplode 0
 +set g_balance_crylink_secondary_joinexplode_damage 0
 +set g_balance_crylink_secondary_joinexplode_edgedamage 0
 +set g_balance_crylink_secondary_joinexplode_radius 0
 +set g_balance_crylink_secondary_joinexplode_force 0
 +set g_balance_crylink_secondary_linkexplode 0
 +
 +set g_balance_crylink_secondary_middle_lifetime 5 // range: 10000 full, fades to 10000
 +set g_balance_crylink_secondary_middle_fadetime 5
 +set g_balance_crylink_secondary_line_lifetime 2 // range: 4000 full, fades to 8000
 +set g_balance_crylink_secondary_line_fadetime 0.25
 +
 +set g_balance_crylink_switchdelay_drop 0.15
 +set g_balance_crylink_switchdelay_raise 0.15
 +
 +set g_balance_crylink_reload_ammo 0 //default: 10
 +set g_balance_crylink_reload_time 2
 +// }}}
 +// {{{ nex
 +set g_balance_nex_primary_damage 90
 +set g_balance_nex_primary_force 500
 +set g_balance_nex_primary_refire 1
 +set g_balance_nex_primary_animtime 0.3
 +set g_balance_nex_primary_ammo 5
 +set g_balance_nex_primary_damagefalloff_mindist 0
 +set g_balance_nex_primary_damagefalloff_maxdist 0
 +set g_balance_nex_primary_damagefalloff_halflife 0
 +set g_balance_nex_primary_damagefalloff_forcehalflife 0
 +
 +set g_balance_nex_secondary 0 // LOG: disable secondary
 +set g_balance_nex_secondary_charge 0 // LOG: disable secondary charge
 +set g_balance_nex_secondary_charge_rate 0.4
 +set g_balance_nex_secondary_chargepool 1
 +set g_balance_nex_secondary_chargepool_regen 0.25
 +set g_balance_nex_secondary_chargepool_pause_regen 2
 +set g_balance_nex_secondary_chargepool_pause_health_regen 0.5
 +set g_balance_nex_secondary_damage 0
 +set g_balance_nex_secondary_force 0
 +set g_balance_nex_secondary_refire 0
 +set g_balance_nex_secondary_animtime 0
 +set g_balance_nex_secondary_ammo 0.4 // full charge pool is 1, so it depletes in 2.5 secs
 +set g_balance_nex_secondary_damagefalloff_mindist 0
 +set g_balance_nex_secondary_damagefalloff_maxdist 0
 +set g_balance_nex_secondary_damagefalloff_halflife 0
 +set g_balance_nex_secondary_damagefalloff_forcehalflife 0
 +
 +set g_balance_nex_charge 1
 +set g_balance_nex_charge_mindmg 20
 +set g_balance_nex_charge_start 0.5
 +set g_balance_nex_charge_rate 0.5
 +set g_balance_nex_charge_animlimit 0.5
 +set g_balance_nex_charge_limit 1 // LOG: 0.5 -> 1 - allow to fully charge automaticaly
 +set g_balance_nex_charge_rot_rate 0 // LOG: 0.1 -> 0 - disable rot
 +set g_balance_nex_charge_rot_pause 0.5 // Dont rot down until this long after release of charge button
 +set g_balance_nex_charge_shot_multiplier 0
 +set g_balance_nex_charge_velocity_rate 0
 +set g_balance_nex_charge_minspeed 600
 +set g_balance_nex_charge_maxspeed 1000
 +
 +set g_balance_nex_switchdelay_drop 0.15
 +set g_balance_nex_switchdelay_raise 0.15
 +
 +set g_balance_nex_reload_ammo 0 //default: 25
 +set g_balance_nex_reload_time 2
 +// }}}
 +// {{{ minstanex
 +set g_balance_minstanex_refire 1
 +set g_balance_minstanex_animtime 0.50
 +set g_balance_minstanex_ammo 10
 +set g_balance_minstanex_laser_ammo 0
 +set g_balance_minstanex_laser_animtime 0.3
 +set g_balance_minstanex_laser_refire 0.6
 +set g_balance_minstanex_switchdelay_drop 0.15
 +set g_balance_minstanex_switchdelay_raise 0.15
 +set g_balance_minstanex_reload_ammo 0 //default: 50
 +set g_balance_minstanex_reload_time 2
 +// }}}
 +// {{{ hagar
 +set g_balance_hagar_primary_damage 14
 +set g_balance_hagar_primary_edgedamage 6
 +set g_balance_hagar_primary_force 70
 +set g_balance_hagar_primary_health 0
 +set g_balance_hagar_primary_damageforcescale 0
 +set g_balance_hagar_primary_radius 110
 +set g_balance_hagar_primary_spread 0.1
 +set g_balance_hagar_primary_speed 1800
 +set g_balance_hagar_primary_lifetime 5
 +set g_balance_hagar_primary_refire 0.12
 +set g_balance_hagar_primary_ammo 1
 +set g_balance_hagar_secondary 1
 +set g_balance_hagar_secondary_load 0
 +set g_balance_hagar_secondary_load_speed 0.6
 +set g_balance_hagar_secondary_load_spread 0.075
 +set g_balance_hagar_secondary_load_spread_bias 0.5
 +set g_balance_hagar_secondary_load_max 4
 +set g_balance_hagar_secondary_load_hold 0
 +set g_balance_hagar_secondary_load_releasedeath 1
 +set g_balance_hagar_secondary_load_abort 1
 +set g_balance_hagar_secondary_load_linkexplode 0
 +set g_balance_hagar_secondary_load_animtime 0.2
 +set g_balance_hagar_secondary_damage 14 // default for _load: 32
 +set g_balance_hagar_secondary_edgedamage 6 // default for _load: 10
 +set g_balance_hagar_secondary_force 70 // default for _load: 160
 +set g_balance_hagar_secondary_health 0
 +set g_balance_hagar_secondary_damageforcescale 0
 +set g_balance_hagar_secondary_radius 125
 +set g_balance_hagar_secondary_spread 0.15 // default for _load: 0.08
 +set g_balance_hagar_secondary_speed 1800
 +set g_balance_hagar_secondary_lifetime_min 5
 +set g_balance_hagar_secondary_lifetime_rand 0
 +set g_balance_hagar_secondary_refire 0.12 // default for _load: 0.8
 +set g_balance_hagar_secondary_ammo 1
 +set g_balance_hagar_switchdelay_drop 0.15
 +set g_balance_hagar_switchdelay_raise 0.15
 +set g_balance_hagar_reload_ammo 0 //default: 25
 +set g_balance_hagar_reload_time 2
 +// }}}
 +// {{{ rocketlauncher
 +set g_balance_rocketlauncher_damage 82
 +set g_balance_rocketlauncher_edgedamage 32
 +set g_balance_rocketlauncher_force 350
 +set g_balance_rocketlauncher_radius 130
 +set g_balance_rocketlauncher_speed 1400
 +set g_balance_rocketlauncher_speedaccel 1400
 +set g_balance_rocketlauncher_speedstart 800
 +set g_balance_rocketlauncher_lifetime 5
 +set g_balance_rocketlauncher_refire 1
 +set g_balance_rocketlauncher_animtime 0.3
 +set g_balance_rocketlauncher_ammo 3
 +set g_balance_rocketlauncher_health 0
 +set g_balance_rocketlauncher_damageforcescale 0
 +set g_balance_rocketlauncher_detonatedelay 0.05 // positive: timer till detonation is allowed, negative: "security device" that prevents ANY remote detonation if it could hurt its owner, zero: detonatable at any time
 +set g_balance_rocketlauncher_guiderate 42 // max degrees per second
 +set g_balance_rocketlauncher_guideratedelay 0.01 // immediate
 +set g_balance_rocketlauncher_guidegoal 512 // goal distance for (non-laser) guiding (higher = less control, lower = erratic)
 +set g_balance_rocketlauncher_guidedelay 0.15 // delay before guiding kicks in
 +set g_balance_rocketlauncher_guidestop 0 // stop guiding when firing again
 +set g_balance_rocketlauncher_remote_damage 60
 +set g_balance_rocketlauncher_remote_edgedamage 20
 +set g_balance_rocketlauncher_remote_radius 120
 +set g_balance_rocketlauncher_remote_force 350
 +set g_balance_rocketlauncher_switchdelay_drop 0.15
 +set g_balance_rocketlauncher_switchdelay_raise 0.15
 +set g_balance_rocketlauncher_reload_ammo 0 //default: 25
 +set g_balance_rocketlauncher_reload_time 2
 +// }}}
 +// {{{ porto
 +set g_balance_porto_primary_refire 1.5
 +set g_balance_porto_primary_animtime 0.2
 +set g_balance_porto_primary_speed 2000
 +set g_balance_porto_primary_lifetime 5
 +set g_balance_porto_secondary 0
 +set g_balance_porto_secondary_refire 1.5
 +set g_balance_porto_secondary_animtime 0.2
 +set g_balance_porto_secondary_speed 2000
 +set g_balance_porto_secondary_lifetime 5
 +set g_balance_porto_switchdelay_drop 0.15
 +set g_balance_porto_switchdelay_raise 0.15
 +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
 +// }}}
 +// {{{ hook
 +set g_balance_hook_primary_fuel 5 // hook monkeys set 0
++set g_balance_hook_primary_refire 0.2 // hook monkeys set 0
 +set g_balance_hook_primary_animtime 0.2 // good shoot anim
 +set g_balance_hook_primary_hooked_time_max 0 // infinite
 +set g_balance_hook_primary_hooked_time_free 2 // 2s being hooked are free
 +set g_balance_hook_primary_hooked_fuel 5 // fuel per second hooked
 +set g_balance_hook_secondary_damage 25 // not much
 +set g_balance_hook_secondary_edgedamage 5 // not much
 +set g_balance_hook_secondary_radius 500 // LOTS
 +set g_balance_hook_secondary_force -2000 // LOTS
 +set g_balance_hook_secondary_ammo 50 // a whole pack
 +set g_balance_hook_secondary_lifetime 5 // infinite
 +set g_balance_hook_secondary_speed 0 // not much throwing
 +set g_balance_hook_secondary_gravity 5 // fast falling
 +set g_balance_hook_secondary_refire 3 // don't drop too many bombs...
 +set g_balance_hook_secondary_animtime 0.2 // good shoot anim
 +set g_balance_hook_secondary_power 3 // effect behaves like a square function
 +set g_balance_hook_secondary_duration 1.5 // effect runs for three seconds
 +set g_balance_hook_secondary_health 0
 +set g_balance_hook_secondary_damageforcescale 0
 +set g_balance_hook_switchdelay_drop 0.15
 +set g_balance_hook_switchdelay_raise 0.15
 +// }}}
 +// {{{ tuba
 +set g_balance_tuba_refire 0.05
 +set g_balance_tuba_animtime 0.05
 +set g_balance_tuba_attenuation 0.5
 +set g_balance_tuba_volume 1
 +set g_balance_tuba_fadetime 0.25
 +set g_balance_tuba_damage 5
 +set g_balance_tuba_edgedamage 0
 +set g_balance_tuba_radius 200
 +set g_balance_tuba_force 40
 +set g_balance_tuba_pitchstep 6
 +set g_balance_tuba_switchdelay_drop 0.15
 +set g_balance_tuba_switchdelay_raise 0.15
 +// }}}
 +// {{{ fireball
 +set g_balance_fireball_primary_animtime 0.2
 +set g_balance_fireball_primary_bfgdamage 100
 +set g_balance_fireball_primary_bfgforce 0
 +set g_balance_fireball_primary_bfgradius 1000
 +set g_balance_fireball_primary_damage 200
 +set g_balance_fireball_primary_damageforcescale 4
 +set g_balance_fireball_primary_edgedamage 0
 +set g_balance_fireball_primary_force 700
 +set g_balance_fireball_primary_health 50
 +set g_balance_fireball_primary_laserburntime 0.5
 +set g_balance_fireball_primary_laserdamage 80
 +set g_balance_fireball_primary_laseredgedamage 20
 +set g_balance_fireball_primary_laserradius 256
 +set g_balance_fireball_primary_lifetime 15
 +set g_balance_fireball_primary_radius 200
 +set g_balance_fireball_primary_refire 5
 +set g_balance_fireball_primary_refire2 0
 +set g_balance_fireball_primary_speed 650
 +set g_balance_fireball_primary_spread 0
 +set g_balance_fireball_secondary_animtime 0.2
 +set g_balance_fireball_secondary_damage 40
 +set g_balance_fireball_secondary_damageforcescale 4
 +set g_balance_fireball_secondary_damagetime 5
 +set g_balance_fireball_secondary_force 100
 +set g_balance_fireball_secondary_laserburntime 0.5
 +set g_balance_fireball_secondary_laserdamage 50
 +set g_balance_fireball_secondary_laseredgedamage 20
 +set g_balance_fireball_secondary_laserradius 110
 +set g_balance_fireball_secondary_lifetime 7
 +set g_balance_fireball_secondary_refire 2
 +set g_balance_fireball_secondary_speed 900
 +set g_balance_fireball_secondary_speed_up 100
 +set g_balance_fireball_secondary_speed_z 0
 +set g_balance_fireball_secondary_spread 0
 +set g_balance_fireball_switchdelay_drop 0.15
 +set g_balance_fireball_switchdelay_raise 0.15
 +// }}}
diff --combined oldbalanceXDF.cfg
index 3e8f0d2c013d8583ae29976ab710003a1b2ee45a,0000000000000000000000000000000000000000..cbc380bfab17ce6e65b872688ee4a9ac58c62fd3
mode 100644,000000..100644
--- /dev/null
@@@ -1,749 -1,0 +1,750 @@@
- set g_balance_hook_primary_refire 0 // hook monkeys set 0
 +g_mod_balance XDF
 +
 +// {{{ starting gear
 +set g_start_weapon_laser 0 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_shotgun 0 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_uzi 1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_grenadelauncher -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_electro -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_crylink -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_nex -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_hagar -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default" // UNTIL IT CAN BE REMOVED FROM CODE
 +set g_start_weapon_rocketlauncher -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_minstanex -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_porto -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_hook -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_tuba -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_start_weapon_fireball -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default"
 +set g_balance_health_start 100
 +set g_balance_armor_start 0
 +set g_start_ammo_shells 15
 +set g_start_ammo_nails 0
 +set g_start_ammo_rockets 0
 +set g_start_ammo_cells 0
 +set g_start_ammo_fuel 0
 +set g_warmup_start_health 100 "starting values when being in warmup-stage"
 +set g_warmup_start_armor 100 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_shells 30 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_nails 160 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_rockets 80 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_cells 90 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_fuel 0 "starting values when being in warmup-stage"
 +set g_lms_start_health 200
 +set g_lms_start_armor 200
 +set g_lms_start_ammo_shells 60
 +set g_lms_start_ammo_nails 320
 +set g_lms_start_ammo_rockets 160
 +set g_lms_start_ammo_cells 180
 +set g_lms_start_ammo_fuel 0
 +set g_balance_nix_roundtime 25
 +set g_balance_nix_incrtime 1.6
 +set g_balance_nix_ammo_shells 60
 +set g_balance_nix_ammo_nails 320
 +set g_balance_nix_ammo_rockets 160
 +set g_balance_nix_ammo_cells 180
 +set g_balance_nix_ammo_fuel 0
 +set g_balance_nix_ammoincr_shells 2 // eh this will need figured out later I assume
 +set g_balance_nix_ammoincr_nails 6
 +set g_balance_nix_ammoincr_rockets 2
 +set g_balance_nix_ammoincr_cells 2
 +set g_balance_nix_ammoincr_fuel 2
 +// }}}
 +
 +// {{{ pickup items
 +set g_pickup_ammo_anyway 1
 +set g_pickup_weapons_anyway 1
 +set g_pickup_shells 15
 +set g_pickup_shells_weapon 15
 +set g_pickup_shells_max 60
 +set g_pickup_nails 80
 +set g_pickup_nails_weapon 80
 +set g_pickup_nails_max 320
 +set g_pickup_rockets 40
 +set g_pickup_rockets_weapon 40
 +set g_pickup_rockets_max 160
 +set g_pickup_cells 30
 +set g_pickup_cells_weapon 30
 +set g_pickup_cells_max 180
 +set g_pickup_fuel 50
 +set g_pickup_fuel_weapon 50
 +set g_pickup_fuel_jetpack 100
 +set g_pickup_fuel_max 100
 +set g_pickup_armorsmall 5
 +set g_pickup_armorsmall_max 200
 +set g_pickup_armorsmall_anyway 1
 +set g_pickup_armormedium 25
 +set g_pickup_armormedium_max 200
 +set g_pickup_armormedium_anyway 1
 +set g_pickup_armorbig 50
 +set g_pickup_armorbig_max 200
 +set g_pickup_armorbig_anyway 1
 +set g_pickup_armorlarge 100
 +set g_pickup_armorlarge_max 200
 +set g_pickup_armorlarge_anyway 1
 +set g_pickup_healthsmall 5
 +set g_pickup_healthsmall_max 200
 +set g_pickup_healthsmall_anyway 1
 +set g_pickup_healthmedium 25
 +set g_pickup_healthmedium_max 200
 +set g_pickup_healthmedium_anyway 1
 +set g_pickup_healthlarge 50
 +set g_pickup_healthlarge_max 200
 +set g_pickup_healthlarge_anyway 1
 +set g_pickup_healthmega 100
 +set g_pickup_healthmega_max 200
 +set g_pickup_healthmega_anyway 1
 +set g_pickup_respawntime_short 0.1
 +set g_pickup_respawntime_medium 0.1
 +set g_pickup_respawntime_long 0.1
 +set g_pickup_respawntime_powerup 0.1
 +set g_pickup_respawntime_weapon 0.1
 +set g_pickup_respawntime_superweapon 0.1
 +set g_pickup_respawntime_ammo 0.1
 +set g_pickup_respawntimejitter_short 0
 +set g_pickup_respawntimejitter_medium 0
 +set g_pickup_respawntimejitter_long 0
 +set g_pickup_respawntimejitter_powerup 30
 +set g_pickup_respawntimejitter_weapon 0
 +set g_pickup_respawntimejitter_superweapon 10
 +set g_pickup_respawntimejitter_ammo 0
 +// }}}
 +
 +// {{{ regen/rot
 +set g_balance_health_regen 0.08
 +set g_balance_health_regenlinear 0.5
 +set g_balance_pause_health_regen 5
 +set g_balance_pause_health_regen_spawn 0
 +set g_balance_health_rot 0.04
 +set g_balance_health_rotlinear 0.75
 +set g_balance_pause_health_rot 1
 +set g_balance_pause_health_rot_spawn 5
 +set g_balance_health_regenstable 100
 +set g_balance_health_rotstable 100
 +set g_balance_health_limit 999
 +set g_balance_armor_regen 0
 +set g_balance_armor_regenlinear 0
 +set g_balance_armor_rot 0.04
 +set g_balance_armor_rotlinear 0.75
 +set g_balance_pause_armor_rot 1
 +set g_balance_pause_armor_rot_spawn 5
 +set g_balance_armor_regenstable 100
 +set g_balance_armor_rotstable 100
 +set g_balance_armor_limit 999
 +set g_balance_armor_blockpercent 0.6
 +set g_balance_fuel_regen 0.1 "fuel regeneration (only applies if the player owns IT_FUEL_REGEN)"
 +set g_balance_fuel_regenlinear 0
 +set g_balance_pause_fuel_regen 2 // other than this, fuel uses the health regen counter
 +set g_balance_fuel_rot 0.05
 +set g_balance_fuel_rotlinear 0
 +set g_balance_pause_fuel_rot 5
 +set g_balance_pause_fuel_rot_spawn 10
 +set g_balance_fuel_regenstable 50
 +set g_balance_fuel_rotstable 100
 +set g_balance_fuel_limit 999
 +// }}}
 +
 +// {{{ misc
 +set g_balance_selfdamagepercent 0
 +set g_weaponspeedfactor 1 "weapon projectile speed multiplier"
 +set g_weaponratefactor 1 "weapon fire rate multiplier"
 +set g_weapondamagefactor 1 "weapon damage multiplier"
 +set g_weaponforcefactor 1 "weapon force multiplier"
 +set g_weaponspreadfactor 1 "weapon spread multiplier"
 +set g_balance_firetransfer_time 0.9
 +set g_balance_firetransfer_damage 0.8
 +set g_throughfloor_damage 0.4
 +set g_throughfloor_force 0.7
 +set g_projectiles_damage 2
 +// possible values:
 +// -2: absolutely no damage to projectiles (no exceptions)
 +// -1: no damage other than the exceptions (electro combo, hagar join explode, ML mines)
 +// 0: only damage from contents (lava/slime) or exceptions
 +// 1: only self damage or damage from contents or exceptions
 +// 2: allow all damage to projectiles normally
 +set g_projectiles_keep_owner 0
 +set g_projectiles_newton_style 2
 +// possible values:
 +// 0: absolute velocity projectiles (like Quake)
 +// 1: relative velocity projectiles, "Newtonian" (like Tribes 2)
 +// 2: relative velocity projectiles, but aim is precorrected so projectiles hit the crosshair (note: strafe rockets then are SLOWER than ones shot while standing, happens in 1 too when aiming correctly which is hard)
 +set g_projectiles_newton_style_2_minfactor 0.8
 +set g_projectiles_newton_style_2_maxfactor 1.5
 +set g_projectiles_spread_style 7
 +// possible values:
 +// 0: forward + solid sphere (like Quake) - varies velocity
 +// 1: forward + flattened solid sphere
 +// 2: forward + solid circle
 +// 3: forward + normal distribution 3D - varies velocity
 +// 4: forward + normal distribution on a plane
 +// 5: forward + circle with 1-r falloff
 +// 6: forward + circle with 1-r^2 falloff
 +// 7: forward + circle with (1-r)(2-r) falloff
 +set g_balance_falldamage_deadminspeed 250
 +set g_balance_falldamage_minspeed 900
 +set g_balance_falldamage_factor 0.20
 +set g_balance_falldamage_maxdamage 40
 +set g_balance_damagepush_speedfactor 2.5
 +set g_balance_contents_damagerate 0.2 // ticrate interval for applying damage with playerdamage/projectiledamage
 +set g_balance_contents_drowndelay 10 // time under water before a player begins drowning
 +set g_balance_contents_playerdamage_drowning 20 // damage per second for while player is drowning
 +set g_balance_contents_playerdamage_lava 50 // damage per second for while player is inside lava
 +set g_balance_contents_playerdamage_slime 30 // damage per second for while player is inside slime
 +set g_balance_contents_projectiledamage 10000 // instantly kill projectiles upon touching lava/slime
 +set g_maxpushtime 8.0 "timeout for kill credit when your damage knocks someone into a death trap"
 +// }}}
 +
 +// {{{ powerups
 +set g_balance_powerup_invincible_takedamage 0.25 // only 1/4th damage is taken
 +set g_balance_powerup_invincible_time 999
 +set g_balance_powerup_strength_damage 3
 +set g_balance_powerup_strength_force 3
 +set g_balance_powerup_strength_time 999
 +set g_balance_powerup_strength_selfdamage 1.5
 +set g_balance_powerup_strength_selfforce 1.5
 +set g_balance_superweapons_time 30
 +// }}}
 +
 +// {{{ jetpack/hook
 +set g_jetpack_antigravity 0.8 "factor of gravity compensation of the jetpack"
 +set g_jetpack_acceleration_side 1200 "acceleration of the jetpack in xy direction"
 +set g_jetpack_acceleration_up 600 "acceleration of the jetpack in z direction (note: you have to factor in gravity here, if antigravity is not 1)"
 +set g_jetpack_maxspeed_side 1200 "max speed of the jetpack in xy direction"
 +set g_jetpack_maxspeed_up 600 "max speed of the jetpack in z direction"
 +set g_jetpack_fuel 8 "fuel per second for jetpack"
 +set g_jetpack_attenuation 2 "jetpack sound attenuation"
 +
 +set g_grappling_hook_tarzan 2 // 2: can also pull players
 +set g_balance_grapplehook_speed_fly 1800
 +set g_balance_grapplehook_speed_pull 2000
 +set g_balance_grapplehook_force_rubber 2000
 +set g_balance_grapplehook_force_rubber_overstretch 1000
 +set g_balance_grapplehook_length_min 50
 +set g_balance_grapplehook_stretch 50
 +set g_balance_grapplehook_airfriction 0.2
 +set g_balance_grapplehook_health 130
 +set g_balance_grapplehook_damagedbycontents 0
++set g_balance_grapplehook_refire 0.2
 +// }}}
 +
 +// {{{ weapon properties
 +// {{{ laser
 +set g_balance_laser_melee_animtime 0.3
 +set g_balance_laser_melee_damage 80
 +set g_balance_laser_melee_delay 0.25
 +set g_balance_laser_melee_force 200
 +set g_balance_laser_melee_multihit 1
 +set g_balance_laser_melee_no_doubleslap 1
 +set g_balance_laser_melee_nonplayerdamage 40
 +set g_balance_laser_melee_range 120
 +set g_balance_laser_melee_refire 1.25
 +set g_balance_laser_melee_swing_side 120
 +set g_balance_laser_melee_swing_up 30
 +set g_balance_laser_melee_time 0.15
 +set g_balance_laser_melee_traces 10
 +
 +set g_balance_laser_primary 1 // 0 = shockwave attack, 1 = projectile primary
 +set g_balance_laser_primary_damage 25
 +set g_balance_laser_primary_edgedamage 12.5
 +set g_balance_laser_primary_force 250
 +set g_balance_laser_primary_radius 70
 +set g_balance_laser_primary_speed 6000
 +set g_balance_laser_primary_spread 0
 +set g_balance_laser_primary_refire 0.7
 +set g_balance_laser_primary_animtime 0.3
 +set g_balance_laser_primary_lifetime 5
 +set g_balance_laser_primary_shotangle 0
 +set g_balance_laser_primary_delay 0
 +set g_balance_laser_primary_force_zscale 1.5
 +set g_balance_laser_primary_force_velocitybias 0
 +set g_balance_laser_primary_force_other_scale 1
 +
 +set g_balance_laser_secondary 0 // 0 = switch away to last used weapon, 1 = projectile secondary, 2 = melee secondary
 +set g_balance_laser_secondary_damage 25
 +set g_balance_laser_secondary_edgedamage 12.5
 +set g_balance_laser_secondary_force 400
 +set g_balance_laser_secondary_radius 70
 +set g_balance_laser_secondary_speed 12000
 +set g_balance_laser_secondary_spread 0
 +set g_balance_laser_secondary_refire 0.7
 +set g_balance_laser_secondary_animtime 0.2
 +set g_balance_laser_secondary_lifetime 5
 +set g_balance_laser_secondary_shotangle -90
 +set g_balance_laser_secondary_delay 0
 +set g_balance_laser_secondary_force_zscale 1.25
 +set g_balance_laser_secondary_force_velocitybias 0
 +set g_balance_laser_secondary_force_other_scale 1
 +
 +set g_balance_laser_shockwave_damage 20
 +set g_balance_laser_shockwave_distance 2000
 +set g_balance_laser_shockwave_edgedamage 0
 +set g_balance_laser_shockwave_force 200
 +set g_balance_laser_shockwave_force_forwardbias 50
 +set g_balance_laser_shockwave_force_zscale 2
 +set g_balance_laser_shockwave_jump_damage 20
 +set g_balance_laser_shockwave_jump_edgedamage 0
 +set g_balance_laser_shockwave_jump_force 300
 +set g_balance_laser_shockwave_jump_force_velocitybias 0
 +set g_balance_laser_shockwave_jump_force_zscale 1.25
 +set g_balance_laser_shockwave_jump_multiplier_accuracy 0.5
 +set g_balance_laser_shockwave_jump_multiplier_distance 0.5
 +set g_balance_laser_shockwave_jump_multiplier_min 0
 +set g_balance_laser_shockwave_jump_radius 150
 +set g_balance_laser_shockwave_multiplier_accuracy 0.5
 +set g_balance_laser_shockwave_multiplier_distance 0.5
 +set g_balance_laser_shockwave_multiplier_min 0
 +set g_balance_laser_shockwave_splash_damage 15
 +set g_balance_laser_shockwave_splash_edgedamage 0
 +set g_balance_laser_shockwave_splash_force 100
 +set g_balance_laser_shockwave_splash_force_forwardbias 50
 +set g_balance_laser_shockwave_splash_multiplier_accuracy 0.5
 +set g_balance_laser_shockwave_splash_multiplier_distance 0.5
 +set g_balance_laser_shockwave_splash_multiplier_min 0
 +set g_balance_laser_shockwave_splash_radius 70
 +set g_balance_laser_shockwave_spread_max 120
 +set g_balance_laser_shockwave_spread_min 25
 +
 +set g_balance_laser_switchdelay_drop 0
 +set g_balance_laser_switchdelay_raise 0
 +set g_balance_laser_reload_ammo 0 //default: 6
 +set g_balance_laser_reload_time 2
 +// }}}
 +// {{{ shotgun
 +set g_balance_shotgun_primary_bullets 14
 +set g_balance_shotgun_primary_damage 4
 +set g_balance_shotgun_primary_force 15
 +set g_balance_shotgun_primary_spread 0.12
 +set g_balance_shotgun_primary_refire 0.75
 +set g_balance_shotgun_primary_animtime 0.2
 +set g_balance_shotgun_primary_ammo 1
 +set g_balance_shotgun_primary_solidpenetration 3.8
 +set g_balance_shotgun_secondary 1
 +set g_balance_shotgun_secondary_melee_delay 0.25 // 0.35 was too slow
 +set g_balance_shotgun_secondary_melee_range 120
 +set g_balance_shotgun_secondary_melee_swing_side 120
 +set g_balance_shotgun_secondary_melee_swing_up 30
 +set g_balance_shotgun_secondary_melee_time 0.15
 +set g_balance_shotgun_secondary_melee_traces 10
 +set g_balance_shotgun_secondary_melee_no_doubleslap 1
 +set g_balance_shotgun_secondary_melee_nonplayerdamage 40
 +set g_balance_shotgun_secondary_melee_multihit 1
 +set g_balance_shotgun_secondary_damage 80
 +set g_balance_shotgun_secondary_force 200
 +set g_balance_shotgun_secondary_refire 1.25
 +set g_balance_shotgun_secondary_animtime 1
 +set g_balance_shotgun_switchdelay_drop 0
 +set g_balance_shotgun_switchdelay_raise 0
 +set g_balance_shotgun_reload_ammo 0 //default: 5
 +set g_balance_shotgun_reload_time 2
 +// }}}
 +// {{{ uzi
 +set g_balance_uzi_mode 1                              // Activates varible spread for sustained & burst mode secondary
 +set g_balance_uzi_spread_min 0
 +set g_balance_uzi_spread_max 0
 +set g_balance_uzi_spread_add 0
 +
 +set g_balance_uzi_burst 3                             // # of bullets in a burst (if set to 2 or more)
 +set g_balance_uzi_burst_animtime 0.3
 +set g_balance_uzi_burst_refire 0.06           // refire between burst bullets
 +set g_balance_uzi_burst_refire2 0.45  // refire after burst
 +set g_balance_uzi_burst_spread 0.03
 +set g_balance_uzi_burst_damage 25
 +set g_balance_uzi_burst_force 20
 +set g_balance_uzi_burst_ammo 3
 +
 +set g_balance_uzi_first 1
 +set g_balance_uzi_first_damage 14
 +set g_balance_uzi_first_force 5
 +set g_balance_uzi_first_spread 0.03
 +set g_balance_uzi_first_refire 0.4
 +set g_balance_uzi_first_ammo 1
 +
 +set g_balance_uzi_sustained_damage 12
 +set g_balance_uzi_sustained_force 5
 +set g_balance_uzi_sustained_spread 0
 +set g_balance_uzi_sustained_refire 0.1
 +set g_balance_uzi_sustained_ammo 1
 +
 +set g_balance_uzi_solidpenetration 13.1
 +
 +set g_balance_uzi_switchdelay_drop 0
 +set g_balance_uzi_switchdelay_raise 0
 +
 +set g_balance_uzi_reload_ammo 0 //default: 30
 +set g_balance_uzi_reload_time 2
 +// }}}
 +// {{{ mortar
 +set g_balance_grenadelauncher_primary_type 0
 +set g_balance_grenadelauncher_primary_damage 50
 +set g_balance_grenadelauncher_primary_edgedamage 25
 +set g_balance_grenadelauncher_primary_force 250
 +set g_balance_grenadelauncher_primary_radius 100
 +set g_balance_grenadelauncher_primary_speed 2000
 +set g_balance_grenadelauncher_primary_speed_up 200
 +set g_balance_grenadelauncher_primary_speed_z 0
 +set g_balance_grenadelauncher_primary_spread 0
 +set g_balance_grenadelauncher_primary_lifetime 5
 +set g_balance_grenadelauncher_primary_lifetime2 1
 +set g_balance_grenadelauncher_primary_refire 0.7
 +set g_balance_grenadelauncher_primary_animtime 0.3
 +set g_balance_grenadelauncher_primary_ammo 2
 +set g_balance_grenadelauncher_primary_health 0
 +set g_balance_grenadelauncher_primary_damageforcescale 0
 +set g_balance_grenadelauncher_primary_remote_minbouncecnt 0
 +
 +set g_balance_grenadelauncher_secondary_type 1
 +set g_balance_grenadelauncher_secondary_damage 60
 +set g_balance_grenadelauncher_secondary_edgedamage 30
 +set g_balance_grenadelauncher_secondary_force 300
 +set g_balance_grenadelauncher_secondary_radius 200
 +set g_balance_grenadelauncher_secondary_speed 800
 +set g_balance_grenadelauncher_secondary_speed_up 0
 +set g_balance_grenadelauncher_secondary_speed_z 200
 +set g_balance_grenadelauncher_secondary_spread 0
 +set g_balance_grenadelauncher_secondary_lifetime 8
 +set g_balance_grenadelauncher_secondary_lifetime_bounce 0.5
 +set g_balance_grenadelauncher_secondary_lifetime_stick 0
 +set g_balance_grenadelauncher_secondary_refire 0.7
 +set g_balance_grenadelauncher_secondary_animtime 0.5
 +set g_balance_grenadelauncher_secondary_ammo 2
 +set g_balance_grenadelauncher_secondary_health 0
 +set g_balance_grenadelauncher_secondary_damageforcescale 0
 +set g_balance_grenadelauncher_secondary_remote_detonateprimary 0
 +
 +set g_balance_grenadelauncher_bouncefactor 0.5
 +set g_balance_grenadelauncher_bouncestop 0.075
 +
 +set g_balance_grenadelauncher_switchdelay_drop 0
 +set g_balance_grenadelauncher_switchdelay_raise 0
 +
 +set g_balance_grenadelauncher_reload_ammo 0 //default: 12
 +set g_balance_grenadelauncher_reload_time 2
 +// }}}
 +// {{{ electro
 +set g_balance_electro_lightning 0
 +set g_balance_electro_primary_damage 55
 +set g_balance_electro_primary_edgedamage 27.5
 +set g_balance_electro_primary_force 200
 +set g_balance_electro_primary_force_up 0
 +set g_balance_electro_primary_radius 100
 +set g_balance_electro_primary_comboradius 150
 +set g_balance_electro_primary_speed 2500
 +set g_balance_electro_primary_spread 0
 +set g_balance_electro_primary_lifetime 5
 +set g_balance_electro_primary_refire 0.6
 +set g_balance_electro_primary_animtime 0.1
 +set g_balance_electro_primary_ammo 4
 +set g_balance_electro_primary_range 0
 +set g_balance_electro_primary_falloff_mindist 255 // 0.3 * radius
 +set g_balance_electro_primary_falloff_maxdist 850
 +set g_balance_electro_primary_falloff_halflifedist 425
 +set g_balance_electro_secondary_damage 40
 +set g_balance_electro_secondary_edgedamage 20
 +set g_balance_electro_secondary_force 200
 +set g_balance_electro_secondary_radius 150
 +set g_balance_electro_secondary_speed 900
 +set g_balance_electro_secondary_speed_up 200
 +set g_balance_electro_secondary_speed_z 0
 +set g_balance_electro_secondary_spread 0.05
 +set g_balance_electro_secondary_lifetime 3
 +set g_balance_electro_secondary_refire 0.2
 +set g_balance_electro_secondary_refire2 1.5
 +set g_balance_electro_secondary_animtime 0.2
 +set g_balance_electro_secondary_ammo 2
 +set g_balance_electro_secondary_health 5
 +set g_balance_electro_secondary_damageforcescale 4
 +set g_balance_electro_secondary_damagedbycontents 1
 +set g_balance_electro_secondary_count 3
 +set g_balance_electro_secondary_bouncefactor 0.4
 +set g_balance_electro_secondary_bouncestop 0.05
 +set g_balance_electro_combo_damage 40
 +set g_balance_electro_combo_edgedamage 20
 +set g_balance_electro_combo_force 120
 +set g_balance_electro_combo_radius 175
 +set g_balance_electro_combo_comboradius 275
 +set g_balance_electro_combo_speed 2000
 +set g_balance_electro_combo_safeammocheck 1
 +set g_balance_electro_switchdelay_drop 0
 +set g_balance_electro_switchdelay_raise 0
 +set g_balance_electro_reload_ammo 0 //default: 20
 +set g_balance_electro_reload_time 2
 +// }}}
 +// {{{ crylink
 +set g_balance_crylink_primary_damage 12
 +set g_balance_crylink_primary_edgedamage 6
 +set g_balance_crylink_primary_force -50
 +set g_balance_crylink_primary_radius 80
 +set g_balance_crylink_primary_speed 2000
 +set g_balance_crylink_primary_spread 0.08
 +set g_balance_crylink_primary_shots 6
 +set g_balance_crylink_primary_bounces 1
 +set g_balance_crylink_primary_refire 0.7
 +set g_balance_crylink_primary_animtime 0.3
 +set g_balance_crylink_primary_ammo 3
 +set g_balance_crylink_primary_bouncedamagefactor 0.5
 +set g_balance_crylink_primary_joindelay 0.1
 +set g_balance_crylink_primary_joinspread 0.2
 +set g_balance_crylink_primary_joinexplode 1
 +set g_balance_crylink_primary_joinexplode_damage 0
 +set g_balance_crylink_primary_joinexplode_edgedamage 0
 +set g_balance_crylink_primary_joinexplode_radius 0
 +set g_balance_crylink_primary_joinexplode_force 0
 +set g_balance_crylink_primary_linkexplode 1
 +
 +set g_balance_crylink_primary_middle_lifetime 5 // range: 35000 full, fades to 70000
 +set g_balance_crylink_primary_middle_fadetime 5
 +set g_balance_crylink_primary_other_lifetime 5
 +set g_balance_crylink_primary_other_fadetime 5
 +
 +set g_balance_crylink_secondary 1
 +set g_balance_crylink_secondary_damage 10
 +set g_balance_crylink_secondary_edgedamage 5
 +set g_balance_crylink_secondary_force -150
 +set g_balance_crylink_secondary_radius 100
 +set g_balance_crylink_secondary_speed 3000
 +set g_balance_crylink_secondary_spread 0.01
 +set g_balance_crylink_secondary_spreadtype 1
 +set g_balance_crylink_secondary_shots 5
 +set g_balance_crylink_secondary_bounces 0
 +set g_balance_crylink_secondary_refire 0.7
 +set g_balance_crylink_secondary_animtime 0.2
 +set g_balance_crylink_secondary_ammo 2
 +set g_balance_crylink_secondary_bouncedamagefactor 0.5
 +set g_balance_crylink_secondary_joindelay 0
 +set g_balance_crylink_secondary_joinspread 0
 +set g_balance_crylink_secondary_joinexplode 0
 +set g_balance_crylink_secondary_joinexplode_damage 0
 +set g_balance_crylink_secondary_joinexplode_edgedamage 0
 +set g_balance_crylink_secondary_joinexplode_radius 0
 +set g_balance_crylink_secondary_joinexplode_force 0
 +set g_balance_crylink_secondary_linkexplode 1
 +
 +set g_balance_crylink_secondary_middle_lifetime 5 // range: 35000 full, fades to 70000
 +set g_balance_crylink_secondary_middle_fadetime 5
 +set g_balance_crylink_secondary_line_lifetime 5
 +set g_balance_crylink_secondary_line_fadetime 5
 +
 +set g_balance_crylink_switchdelay_drop 0
 +set g_balance_crylink_switchdelay_raise 0
 +
 +set g_balance_crylink_reload_ammo 0 //default: 10
 +set g_balance_crylink_reload_time 2
 +// }}}
 +// {{{ nex
 +set g_balance_nex_primary_damage 90
 +set g_balance_nex_primary_force 400
 +set g_balance_nex_primary_refire 1.5
 +set g_balance_nex_primary_animtime 0.4
 +set g_balance_nex_primary_ammo 6
 +set g_balance_nex_primary_damagefalloff_mindist 0 // 1000    For tZork ;3
 +set g_balance_nex_primary_damagefalloff_maxdist 0 // 3000
 +set g_balance_nex_primary_damagefalloff_halflife 0 // 1500
 +set g_balance_nex_primary_damagefalloff_forcehalflife 0 // 1500
 +
 +set g_balance_nex_secondary 0
 +set g_balance_nex_secondary_charge 0
 +set g_balance_nex_secondary_charge_rate 0.1
 +set g_balance_nex_secondary_chargepool 0
 +set g_balance_nex_secondary_chargepool_regen 0.15
 +set g_balance_nex_secondary_chargepool_pause_regen 1
 +set g_balance_nex_secondary_chargepool_pause_health_regen 1
 +set g_balance_nex_secondary_damage 0
 +set g_balance_nex_secondary_force 0
 +set g_balance_nex_secondary_refire 0
 +set g_balance_nex_secondary_animtime 0
 +set g_balance_nex_secondary_ammo 2
 +set g_balance_nex_secondary_damagefalloff_mindist 0
 +set g_balance_nex_secondary_damagefalloff_maxdist 0
 +set g_balance_nex_secondary_damagefalloff_halflife 0
 +set g_balance_nex_secondary_damagefalloff_forcehalflife 0
 +
 +set g_balance_nex_charge 1
 +set g_balance_nex_charge_mindmg 40
 +set g_balance_nex_charge_start 0.5
 +set g_balance_nex_charge_rate 0.4
 +set g_balance_nex_charge_animlimit 0.5
 +set g_balance_nex_charge_limit 1
 +set g_balance_nex_charge_rot_rate 0
 +set g_balance_nex_charge_rot_pause 0 // Dont rot down untill this long after release of charge button
 +set g_balance_nex_charge_shot_multiplier 0
 +set g_balance_nex_charge_velocity_rate 0
 +set g_balance_nex_charge_minspeed 400
 +set g_balance_nex_charge_maxspeed 800
 +
 +set g_balance_nex_switchdelay_drop 0
 +set g_balance_nex_switchdelay_raise 0
 +
 +set g_balance_nex_reload_ammo 0 //default: 25
 +set g_balance_nex_reload_time 2
 +// }}}
 +// {{{ minstanex
 +set g_balance_minstanex_refire 1
 +set g_balance_minstanex_animtime 0.3
 +set g_balance_minstanex_ammo 10
 +set g_balance_minstanex_laser_ammo 0
 +set g_balance_minstanex_laser_animtime 0.3
 +set g_balance_minstanex_laser_refire 0.7
 +set g_balance_minstanex_switchdelay_drop 0
 +set g_balance_minstanex_switchdelay_raise 0
 +set g_balance_minstanex_reload_ammo 0 //default: 50
 +set g_balance_minstanex_reload_time 2
 +// }}}
 +// {{{ hagar
 +set g_balance_hagar_primary_damage 25
 +set g_balance_hagar_primary_edgedamage 12.5
 +set g_balance_hagar_primary_force 92
 +set g_balance_hagar_primary_health 15
 +set g_balance_hagar_primary_damageforcescale 0
 +set g_balance_hagar_primary_radius 25
 +set g_balance_hagar_primary_spread 0.03
 +set g_balance_hagar_primary_speed 2000
 +set g_balance_hagar_primary_lifetime 5
 +set g_balance_hagar_primary_refire 0.11
 +set g_balance_hagar_primary_ammo 1
 +set g_balance_hagar_secondary 0
 +set g_balance_hagar_secondary_load 1
 +set g_balance_hagar_secondary_load_speed 0.5
 +set g_balance_hagar_secondary_load_spread 0.075
 +set g_balance_hagar_secondary_load_spread_bias 0.5
 +set g_balance_hagar_secondary_load_max 4
 +set g_balance_hagar_secondary_load_hold 4
 +set g_balance_hagar_secondary_load_releasedeath 0
 +set g_balance_hagar_secondary_load_abort 0
 +set g_balance_hagar_secondary_load_linkexplode 0
 +set g_balance_hagar_secondary_load_animtime 0.2
 +set g_balance_hagar_secondary_damage 40
 +set g_balance_hagar_secondary_edgedamage 20
 +set g_balance_hagar_secondary_force 75
 +set g_balance_hagar_secondary_health 15
 +set g_balance_hagar_secondary_damageforcescale 0
 +set g_balance_hagar_secondary_radius 80
 +set g_balance_hagar_secondary_spread 0.05
 +set g_balance_hagar_secondary_speed 2000
 +set g_balance_hagar_secondary_lifetime_min 10
 +set g_balance_hagar_secondary_lifetime_rand 0
 +set g_balance_hagar_secondary_refire 0.5
 +set g_balance_hagar_secondary_ammo 1
 +set g_balance_hagar_switchdelay_drop 0
 +set g_balance_hagar_switchdelay_raise 0
 +set g_balance_hagar_reload_ammo 0 //default: 25
 +set g_balance_hagar_reload_time 2
 +// }}}
 +// {{{ rocketlauncher
 +set g_balance_rocketlauncher_damage 80
 +set g_balance_rocketlauncher_edgedamage 40
 +set g_balance_rocketlauncher_force 350
 +set g_balance_rocketlauncher_radius 110
 +set g_balance_rocketlauncher_speed 1000
 +set g_balance_rocketlauncher_speedaccel 0
 +set g_balance_rocketlauncher_speedstart 1000
 +set g_balance_rocketlauncher_lifetime 100
 +set g_balance_rocketlauncher_refire 0.9
 +set g_balance_rocketlauncher_animtime 0.7
 +set g_balance_rocketlauncher_ammo 4
 +set g_balance_rocketlauncher_health 0 // 30 // 5 hitpoints above maximum laser value -- this way lasers can't blow it up, but grenadelauncher still can most the time.
 +set g_balance_rocketlauncher_damageforcescale 0 // low damage force scale so that it can still be affected by other hits, but not so much that it does a 90 degree turn
 +set g_balance_rocketlauncher_detonatedelay 999 // positive: timer till detonation is allowed, negative: "security device" that prevents ANY remote detonation if it could hurt its owner, zero: detonatable at any time
 +set g_balance_rocketlauncher_guiderate 0 // max degrees per second
 +set g_balance_rocketlauncher_guideratedelay 0.01 // immediate
 +set g_balance_rocketlauncher_guidegoal 512 // goal distance for (non-laser) guiding (higher = less control, lower = erratic)
 +set g_balance_rocketlauncher_guidedelay 0.2 // delay before guiding kicks in
 +set g_balance_rocketlauncher_guidestop 1 // stop guiding when firing again
 +set g_balance_rocketlauncher_remote_damage 70
 +set g_balance_rocketlauncher_remote_edgedamage 35
 +set g_balance_rocketlauncher_remote_radius 110
 +set g_balance_rocketlauncher_remote_force 350
 +set g_balance_rocketlauncher_switchdelay_drop 0
 +set g_balance_rocketlauncher_switchdelay_raise 0
 +set g_balance_rocketlauncher_reload_ammo 0 //default: 25
 +set g_balance_rocketlauncher_reload_time 2
 +// }}}
 +// {{{ porto
 +set g_balance_porto_primary_refire 1.5
 +set g_balance_porto_primary_animtime 0.3
 +set g_balance_porto_primary_speed 5000
 +set g_balance_porto_primary_lifetime 5
 +set g_balance_porto_secondary 1
 +set g_balance_porto_secondary_refire 1.5
 +set g_balance_porto_secondary_animtime 0.3
 +set g_balance_porto_secondary_speed 1000
 +set g_balance_porto_secondary_lifetime 5
 +set g_balance_porto_switchdelay_drop 0
 +set g_balance_porto_switchdelay_raise 0
 +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
 +// }}}
 +// {{{ hook
 +set g_balance_hook_primary_fuel 5 // hook monkeys set 0
++set g_balance_hook_primary_refire 0.2 // hook monkeys set 0
 +set g_balance_hook_primary_animtime 0.3 // good shoot anim
 +set g_balance_hook_primary_hooked_time_max 0 // infinite
 +set g_balance_hook_primary_hooked_time_free 2 // 2s being hooked are free
 +set g_balance_hook_primary_hooked_fuel 5 // fuel per second hooked
 +set g_balance_hook_secondary_damage 25 // not much
 +set g_balance_hook_secondary_edgedamage 5 // not much
 +set g_balance_hook_secondary_radius 500 // LOTS
 +set g_balance_hook_secondary_force -2000 // LOTS
 +set g_balance_hook_secondary_ammo 50 // a whole pack
 +set g_balance_hook_secondary_lifetime 5 // infinite
 +set g_balance_hook_secondary_speed 0 // not much throwing
 +set g_balance_hook_secondary_gravity 5 // fast falling
 +set g_balance_hook_secondary_refire 3 // don't drop too many bombs...
 +set g_balance_hook_secondary_animtime 0.3 // good shoot anim
 +set g_balance_hook_secondary_power 3 // effect behaves like a square function
 +set g_balance_hook_secondary_duration 1.5 // effect runs for three seconds
 +set g_balance_hook_secondary_health 15
 +set g_balance_hook_secondary_damageforcescale 0
 +set g_balance_hook_switchdelay_drop 0
 +set g_balance_hook_switchdelay_raise 0
 +// }}}
 +// {{{ tuba
 +set g_balance_tuba_refire 0.05
 +set g_balance_tuba_animtime 0.05
 +set g_balance_tuba_attenuation 0.5
 +set g_balance_tuba_volume 1
 +set g_balance_tuba_fadetime 0.25
 +set g_balance_tuba_damage 5
 +set g_balance_tuba_edgedamage 0
 +set g_balance_tuba_radius 200
 +set g_balance_tuba_force 40
 +set g_balance_tuba_pitchstep 6
 +set g_balance_tuba_switchdelay_drop 0
 +set g_balance_tuba_switchdelay_raise 0
 +// }}}
 +// {{{ fireball // this is a superweapon -- lets make it behave as one.
 +set g_balance_fireball_primary_animtime 0.2
 +set g_balance_fireball_primary_bfgdamage 100
 +set g_balance_fireball_primary_bfgforce 0
 +set g_balance_fireball_primary_bfgradius 1000
 +set g_balance_fireball_primary_damage 200
 +set g_balance_fireball_primary_damageforcescale 0
 +set g_balance_fireball_primary_edgedamage 50
 +set g_balance_fireball_primary_force 600
 +set g_balance_fireball_primary_health 0
 +set g_balance_fireball_primary_laserburntime 0.5
 +set g_balance_fireball_primary_laserdamage 80
 +set g_balance_fireball_primary_laseredgedamage 20
 +set g_balance_fireball_primary_laserradius 256
 +set g_balance_fireball_primary_lifetime 15
 +set g_balance_fireball_primary_radius 200
 +set g_balance_fireball_primary_refire 2
 +set g_balance_fireball_primary_refire2 0
 +set g_balance_fireball_primary_speed 1200
 +set g_balance_fireball_primary_spread 0
 +set g_balance_fireball_secondary_animtime 0.3
 +set g_balance_fireball_secondary_damage 40
 +set g_balance_fireball_secondary_damageforcescale 4
 +set g_balance_fireball_secondary_damagetime 5
 +set g_balance_fireball_secondary_force 100
 +set g_balance_fireball_secondary_laserburntime 0.5
 +set g_balance_fireball_secondary_laserdamage 50
 +set g_balance_fireball_secondary_laseredgedamage 20
 +set g_balance_fireball_secondary_laserradius 110
 +set g_balance_fireball_secondary_lifetime 7
 +set g_balance_fireball_secondary_refire 1.5
 +set g_balance_fireball_secondary_speed 900
 +set g_balance_fireball_secondary_speed_up 100
 +set g_balance_fireball_secondary_speed_z 0
 +set g_balance_fireball_secondary_spread 0
 +set g_balance_fireball_switchdelay_drop 0
 +set g_balance_fireball_switchdelay_raise 0
 +// }}}
diff --combined oldbalanceXPM.cfg
index 65e3a7909576d685f6d3a7d95c0b660f821bf2b8,0000000000000000000000000000000000000000..f7b088aae9bd79ed361dfc30d3b8f9942a0d2ff7
mode 100644,000000..100644
--- /dev/null
@@@ -1,779 -1,0 +1,780 @@@
- set g_balance_hook_primary_refire 0 // hook monkeys set 0
 +g_mod_balance XPM
 +
 +// {{{ starting gear
 +set g_start_weapon_laser -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_shotgun -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_uzi -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_grenadelauncher -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_electro -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_crylink -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_nex -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_hagar -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms" // UNTIL IT CAN BE REMOVED FROM CODE
 +set g_start_weapon_rocketlauncher -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_minstanex -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_porto -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_hook -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_tuba -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_start_weapon_fireball -1 "0 = never provide the weapon, 1 = always provide the weapon, -1 = game mode default, -2 = provide the weapon in ca and lms"
 +set g_balance_health_start 100
 +set g_balance_armor_start 0
 +set g_start_ammo_shells 15
 +set g_start_ammo_nails 0
 +set g_start_ammo_rockets 0
 +set g_start_ammo_cells 0
 +set g_start_ammo_fuel 0
 +set g_warmup_start_health 100 "starting values when being in warmup-stage"
 +set g_warmup_start_armor 100 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_shells 30 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_nails 160 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_rockets 80 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_cells 90 "starting values when being in warmup-stage"
 +set g_warmup_start_ammo_fuel 0 "starting values when being in warmup-stage"
 +set g_lms_start_health 200
 +set g_lms_start_armor 200
 +set g_lms_start_ammo_shells 60
 +set g_lms_start_ammo_nails 320
 +set g_lms_start_ammo_rockets 160
 +set g_lms_start_ammo_cells 180
 +set g_lms_start_ammo_fuel 0
 +set g_balance_nix_roundtime 25
 +set g_balance_nix_incrtime 1.6
 +set g_balance_nix_ammo_shells 60
 +set g_balance_nix_ammo_nails 320
 +set g_balance_nix_ammo_rockets 160
 +set g_balance_nix_ammo_cells 180
 +set g_balance_nix_ammo_fuel 0
 +set g_balance_nix_ammoincr_shells 2 // eh this will need figured out later I assume
 +set g_balance_nix_ammoincr_nails 6
 +set g_balance_nix_ammoincr_rockets 2
 +set g_balance_nix_ammoincr_cells 2
 +set g_balance_nix_ammoincr_fuel 2
 +// }}}
 +
 +// {{{ pickup items
 +set g_pickup_ammo_anyway 1
 +set g_pickup_weapons_anyway 1
 +set g_pickup_shells 15
 +set g_pickup_shells_weapon 15
 +set g_pickup_shells_max 60
 +set g_pickup_nails 80
 +set g_pickup_nails_weapon 80
 +set g_pickup_nails_max 320
 +set g_pickup_rockets 40
 +set g_pickup_rockets_weapon 40
 +set g_pickup_rockets_max 160
 +set g_pickup_cells 30
 +set g_pickup_cells_weapon 30
 +set g_pickup_cells_max 180
 +set g_pickup_fuel 50
 +set g_pickup_fuel_weapon 50
 +set g_pickup_fuel_jetpack 100
 +set g_pickup_fuel_max 100
 +set g_pickup_armorsmall 5
 +set g_pickup_armorsmall_max 200
 +set g_pickup_armorsmall_anyway 0
 +set g_pickup_armormedium 25
 +set g_pickup_armormedium_max 100
 +set g_pickup_armormedium_anyway 0
 +set g_pickup_armorbig 50
 +set g_pickup_armorbig_max 100
 +set g_pickup_armorbig_anyway 0
 +set g_pickup_armorlarge 100
 +set g_pickup_armorlarge_max 200
 +set g_pickup_armorlarge_anyway 0
 +set g_pickup_healthsmall 5
 +set g_pickup_healthsmall_max 200
 +set g_pickup_healthsmall_anyway 0
 +set g_pickup_healthmedium 25
 +set g_pickup_healthmedium_max 100
 +set g_pickup_healthmedium_anyway 0
 +set g_pickup_healthlarge 50
 +set g_pickup_healthlarge_max 100
 +set g_pickup_healthlarge_anyway 0
 +set g_pickup_healthmega 100
 +set g_pickup_healthmega_max 200
 +set g_pickup_healthmega_anyway 0
 +set g_pickup_respawntime_short 15
 +set g_pickup_respawntime_medium 20
 +set g_pickup_respawntime_long 30
 +set g_pickup_respawntime_powerup 120
 +set g_pickup_respawntime_weapon 10
 +set g_pickup_respawntime_superweapon 120
 +set g_pickup_respawntime_ammo 15
 +set g_pickup_respawntimejitter_short 0
 +set g_pickup_respawntimejitter_medium 0
 +set g_pickup_respawntimejitter_long 0
 +set g_pickup_respawntimejitter_powerup 30
 +set g_pickup_respawntimejitter_weapon 0
 +set g_pickup_respawntimejitter_superweapon 10
 +set g_pickup_respawntimejitter_ammo 0
 +// }}}
 +
 +// {{{ regen/rot
 +set g_balance_health_regen 0.08
 +set g_balance_health_regenlinear 0.5
 +set g_balance_pause_health_regen 5
 +set g_balance_pause_health_regen_spawn 0
 +set g_balance_health_rot 0.03
 +set g_balance_health_rotlinear 0.75
 +set g_balance_pause_health_rot 1
 +set g_balance_pause_health_rot_spawn 5
 +set g_balance_health_regenstable 100
 +set g_balance_health_rotstable 100
 +set g_balance_health_limit 999
 +set g_balance_armor_regen 0
 +set g_balance_armor_regenlinear 0
 +set g_balance_armor_rot 0.03
 +set g_balance_armor_rotlinear 0.75
 +set g_balance_pause_armor_rot 1
 +set g_balance_pause_armor_rot_spawn 5
 +set g_balance_armor_regenstable 100
 +set g_balance_armor_rotstable 100
 +set g_balance_armor_limit 999
 +set g_balance_armor_blockpercent 0.6
 +set g_balance_fuel_regen 0.1 "fuel regeneration (only applies if the player owns IT_FUEL_REGEN)"
 +set g_balance_fuel_regenlinear 0
 +set g_balance_pause_fuel_regen 2 // other than this, fuel uses the health regen counter
 +set g_balance_fuel_rot 0.05
 +set g_balance_fuel_rotlinear 0
 +set g_balance_pause_fuel_rot 5
 +set g_balance_pause_fuel_rot_spawn 10
 +set g_balance_fuel_regenstable 50
 +set g_balance_fuel_rotstable 100
 +set g_balance_fuel_limit 999
 +// }}}
 +
 +// {{{ misc
 +set g_balance_selfdamagepercent 0.65
 +set g_weaponspeedfactor 1 "weapon projectile speed multiplier"
 +set g_weaponratefactor 1 "weapon fire rate multiplier"
 +set g_weapondamagefactor 1 "weapon damage multiplier"
 +set g_weaponforcefactor 1 "weapon force multiplier"
 +set g_weaponspreadfactor 1 "weapon spread multiplier"
 +set g_balance_firetransfer_time 0.9
 +set g_balance_firetransfer_damage 0.8
 +set g_throughfloor_damage 0.75
 +set g_throughfloor_force 0.75
 +set g_projectiles_damage 1
 +// possible values:
 +// -2: absolutely no damage to projectiles (no exceptions)
 +// -1: no damage other than the exceptions (electro combo, hagar join explode, ML mines)
 +// 0: only damage from contents (lava/slime) or exceptions
 +// 1: only self damage or damage from contents or exceptions
 +// 2: allow all damage to projectiles normally
 +set g_projectiles_keep_owner 0
 +set g_projectiles_newton_style 0
 +// possible values:
 +// 0: absolute velocity projectiles (like Quake)
 +// 1: relative velocity projectiles, "Newtonian" (like Tribes 2)
 +// 2: relative velocity projectiles, but aim is precorrected so projectiles hit the crosshair (note: strafe rockets then are SLOWER than ones shot while standing, happens in 1 too when aiming correctly which is hard)
 +set g_projectiles_newton_style_2_minfactor 0.8
 +set g_projectiles_newton_style_2_maxfactor 1.5
 +set g_projectiles_spread_style 7
 +// possible values:
 +// 0: forward + solid sphere (like Quake) - varies velocity
 +// 1: forward + flattened solid sphere
 +// 2: forward + solid circle
 +// 3: forward + normal distribution 3D - varies velocity
 +// 4: forward + normal distribution on a plane
 +// 5: forward + circle with 1-r falloff
 +// 6: forward + circle with 1-r^2 falloff
 +// 7: forward + circle with (1-r)(2-r) falloff
 +set g_balance_falldamage_deadminspeed 250
 +set g_balance_falldamage_minspeed 900
 +set g_balance_falldamage_factor 0.20
 +set g_balance_falldamage_maxdamage 40
 +set g_balance_damagepush_speedfactor 2.5
 +set g_balance_contents_damagerate 0.2 // ticrate interval for applying damage with playerdamage/projectiledamage
 +set g_balance_contents_drowndelay 10 // time under water before a player begins drowning
 +set g_balance_contents_playerdamage_drowning 20 // damage per second for while player is drowning
 +set g_balance_contents_playerdamage_lava 50 // damage per second for while player is inside lava
 +set g_balance_contents_playerdamage_slime 30 // damage per second for while player is inside slime
 +set g_balance_contents_projectiledamage 10000 // instantly kill projectiles upon touching lava/slime
 +set g_maxpushtime 8.0 "timeout for kill credit when your damage knocks someone into a death trap"
 +// }}}
 +
 +// {{{ powerups
 +set g_balance_powerup_invincible_takedamage 0.25 // only 1/4th damage is taken
 +set g_balance_powerup_invincible_time 30
 +set g_balance_powerup_strength_damage 3
 +set g_balance_powerup_strength_force 3
 +set g_balance_powerup_strength_time 30
 +set g_balance_powerup_strength_selfdamage 1.5
 +set g_balance_powerup_strength_selfforce 1.5
 +set g_balance_superweapons_time 30
 +// }}}
 +
 +// {{{ jetpack/hook
 +set g_jetpack_antigravity 0.8 "factor of gravity compensation of the jetpack"
 +set g_jetpack_acceleration_side 1200 "acceleration of the jetpack in xy direction"
 +set g_jetpack_acceleration_up 600 "acceleration of the jetpack in z direction (note: you have to factor in gravity here, if antigravity is not 1)"
 +set g_jetpack_maxspeed_side 1200 "max speed of the jetpack in xy direction"
 +set g_jetpack_maxspeed_up 600 "max speed of the jetpack in z direction"
 +set g_jetpack_fuel 8 "fuel per second for jetpack"
 +set g_jetpack_attenuation 2 "jetpack sound attenuation"
 +
 +set g_grappling_hook_tarzan 2 // 2: can also pull players
 +set g_balance_grapplehook_speed_fly 1800
 +set g_balance_grapplehook_speed_pull 2000
 +set g_balance_grapplehook_force_rubber 2000
 +set g_balance_grapplehook_force_rubber_overstretch 1000
 +set g_balance_grapplehook_length_min 50
 +set g_balance_grapplehook_stretch 50
 +set g_balance_grapplehook_airfriction 0.2
 +set g_balance_grapplehook_health 50
 +set g_balance_grapplehook_damagedbycontents 1
++set g_balance_grapplehook_refire 0.2
 +// }}}
 +
 +// {{{ weapon properties
 +// {{{ laser
 +set g_balance_laser_melee_animtime 0.3
 +set g_balance_laser_melee_damage 80
 +set g_balance_laser_melee_delay 0.25
 +set g_balance_laser_melee_force 200
 +set g_balance_laser_melee_multihit 1
 +set g_balance_laser_melee_no_doubleslap 1
 +set g_balance_laser_melee_nonplayerdamage 40
 +set g_balance_laser_melee_range 120
 +set g_balance_laser_melee_refire 1.25
 +set g_balance_laser_melee_swing_side 120
 +set g_balance_laser_melee_swing_up 30
 +set g_balance_laser_melee_time 0.15
 +set g_balance_laser_melee_traces 10
 +
 +set g_balance_laser_primary 0 // 0 = shockwave attack, 1 = projectile primary
 +set g_balance_laser_primary_damage 25
 +set g_balance_laser_primary_edgedamage 12.5
 +set g_balance_laser_primary_force 300
 +set g_balance_laser_primary_radius 70
 +set g_balance_laser_primary_speed 6000
 +set g_balance_laser_primary_spread 0
 +set g_balance_laser_primary_refire 0.7
 +set g_balance_laser_primary_animtime 0.2
 +set g_balance_laser_primary_lifetime 5
 +set g_balance_laser_primary_shotangle 0
 +set g_balance_laser_primary_delay 0
 +set g_balance_laser_primary_force_zscale 1.2
 +set g_balance_laser_primary_force_velocitybias 0
 +set g_balance_laser_primary_force_other_scale 1
 +
 +set g_balance_laser_secondary 2 // 0 = switch away to last used weapon, 1 = projectile secondary, 2 = melee secondary
 +set g_balance_laser_secondary_damage 25
 +set g_balance_laser_secondary_edgedamage 12.5
 +set g_balance_laser_secondary_force 400
 +set g_balance_laser_secondary_radius 70
 +set g_balance_laser_secondary_speed 12000
 +set g_balance_laser_secondary_spread 0
 +set g_balance_laser_secondary_refire 0.7
 +set g_balance_laser_secondary_animtime 0.2
 +set g_balance_laser_secondary_lifetime 5
 +set g_balance_laser_secondary_shotangle -90
 +set g_balance_laser_secondary_delay 0
 +set g_balance_laser_secondary_force_zscale 1.25
 +set g_balance_laser_secondary_force_velocitybias 0
 +set g_balance_laser_secondary_force_other_scale 1
 +
 +set g_balance_laser_shockwave_damage 20
 +set g_balance_laser_shockwave_distance 2000
 +set g_balance_laser_shockwave_edgedamage 0
 +set g_balance_laser_shockwave_force 200
 +set g_balance_laser_shockwave_force_forwardbias 50
 +set g_balance_laser_shockwave_force_zscale 2
 +set g_balance_laser_shockwave_jump_damage 20
 +set g_balance_laser_shockwave_jump_edgedamage 0
 +set g_balance_laser_shockwave_jump_force 300
 +set g_balance_laser_shockwave_jump_force_velocitybias 0
 +set g_balance_laser_shockwave_jump_force_zscale 1.25
 +set g_balance_laser_shockwave_jump_multiplier_accuracy 0.5
 +set g_balance_laser_shockwave_jump_multiplier_distance 0.5
 +set g_balance_laser_shockwave_jump_multiplier_min 0
 +set g_balance_laser_shockwave_jump_radius 150
 +set g_balance_laser_shockwave_multiplier_accuracy 0.5
 +set g_balance_laser_shockwave_multiplier_distance 0.5
 +set g_balance_laser_shockwave_multiplier_min 0
 +set g_balance_laser_shockwave_splash_damage 15
 +set g_balance_laser_shockwave_splash_edgedamage 0
 +set g_balance_laser_shockwave_splash_force 100
 +set g_balance_laser_shockwave_splash_force_forwardbias 50
 +set g_balance_laser_shockwave_splash_multiplier_accuracy 0.5
 +set g_balance_laser_shockwave_splash_multiplier_distance 0.5
 +set g_balance_laser_shockwave_splash_multiplier_min 0
 +set g_balance_laser_shockwave_splash_radius 70
 +set g_balance_laser_shockwave_spread_max 120
 +set g_balance_laser_shockwave_spread_min 25
 +
 +set g_balance_laser_switchdelay_drop 0.15
 +set g_balance_laser_switchdelay_raise 0.15
 +set g_balance_laser_reload_ammo 0 //default: 6
 +set g_balance_laser_reload_time 2
 +// }}}
 +// {{{ shotgun
 +set g_balance_shotgun_primary_bullets 14
 +set g_balance_shotgun_primary_damage 4
 +set g_balance_shotgun_primary_force 15
 +set g_balance_shotgun_primary_spread 0.12
 +set g_balance_shotgun_primary_refire 0.75
 +set g_balance_shotgun_primary_animtime 0.2
 +set g_balance_shotgun_primary_ammo 1
 +set g_balance_shotgun_primary_solidpenetration 3.8
 +set g_balance_shotgun_secondary 1
 +set g_balance_shotgun_secondary_melee_delay 0.25 // 0.35 was too slow
 +set g_balance_shotgun_secondary_melee_range 120
 +set g_balance_shotgun_secondary_melee_swing_side 120
 +set g_balance_shotgun_secondary_melee_swing_up 30
 +set g_balance_shotgun_secondary_melee_time 0.15
 +set g_balance_shotgun_secondary_melee_traces 10
 +set g_balance_shotgun_secondary_melee_no_doubleslap 1
 +set g_balance_shotgun_secondary_melee_nonplayerdamage 40
 +set g_balance_shotgun_secondary_melee_multihit 1
 +set g_balance_shotgun_secondary_damage 80
 +set g_balance_shotgun_secondary_force 200
 +set g_balance_shotgun_secondary_refire 1.25
 +set g_balance_shotgun_secondary_animtime 1
 +set g_balance_shotgun_switchdelay_drop 0.2
 +set g_balance_shotgun_switchdelay_raise 0.2
 +set g_balance_shotgun_reload_ammo 0 //default: 5
 +set g_balance_shotgun_reload_time 2
 +// }}}
 +// {{{ uzi
 +set g_balance_uzi_mode 1                              // Activates varible spread for sustained & burst mode secondary
 +set g_balance_uzi_spread_min 0.02
 +set g_balance_uzi_spread_max 0.05
 +set g_balance_uzi_spread_add 0.012
 +
 +set g_balance_uzi_burst 3                             // # of bullets in a burst (if set to 2 or more)
 +set g_balance_uzi_burst_animtime 0.3
 +set g_balance_uzi_burst_refire 0.06           // refire between burst bullets
 +set g_balance_uzi_burst_refire2 0.45  // refire after burst
 +set g_balance_uzi_burst_spread 0.02
 +set g_balance_uzi_burst_damage 25
 +set g_balance_uzi_burst_force 20
 +set g_balance_uzi_burst_ammo 3
 +
 +set g_balance_uzi_first 1
 +set g_balance_uzi_first_damage 14
 +set g_balance_uzi_first_force 5
 +set g_balance_uzi_first_spread 0.03
 +set g_balance_uzi_first_refire 0.125
 +set g_balance_uzi_first_ammo 1
 +
 +set g_balance_uzi_sustained_damage 10 // 100 dps
 +set g_balance_uzi_sustained_force 5
 +set g_balance_uzi_sustained_spread 0.03
 +set g_balance_uzi_sustained_refire 0.1
 +set g_balance_uzi_sustained_ammo 1
 +
 +set g_balance_uzi_solidpenetration 13.1
 +
 +set g_balance_uzi_switchdelay_drop 0.2
 +set g_balance_uzi_switchdelay_raise 0.2
 +
 +set g_balance_uzi_reload_ammo 60 //default: 30
 +set g_balance_uzi_reload_time 2
 +// }}}
 +// {{{ mortar
 +set g_balance_grenadelauncher_primary_type 0
 +set g_balance_grenadelauncher_primary_damage 50
 +set g_balance_grenadelauncher_primary_edgedamage 25
 +set g_balance_grenadelauncher_primary_force 250
 +set g_balance_grenadelauncher_primary_radius 120
 +set g_balance_grenadelauncher_primary_speed 1900
 +set g_balance_grenadelauncher_primary_speed_up 225
 +set g_balance_grenadelauncher_primary_speed_z 0
 +set g_balance_grenadelauncher_primary_spread 0
 +set g_balance_grenadelauncher_primary_lifetime 5
 +set g_balance_grenadelauncher_primary_lifetime2 1
 +set g_balance_grenadelauncher_primary_refire 0.8
 +set g_balance_grenadelauncher_primary_animtime 0.3
 +set g_balance_grenadelauncher_primary_ammo 2
 +set g_balance_grenadelauncher_primary_health 15
 +set g_balance_grenadelauncher_primary_damageforcescale 0
 +set g_balance_grenadelauncher_primary_remote_minbouncecnt 0
 +
 +set g_balance_grenadelauncher_secondary_type 1
 +set g_balance_grenadelauncher_secondary_damage 60
 +set g_balance_grenadelauncher_secondary_edgedamage 30
 +set g_balance_grenadelauncher_secondary_force 250
 +set g_balance_grenadelauncher_secondary_radius 120
 +set g_balance_grenadelauncher_secondary_speed 1400
 +set g_balance_grenadelauncher_secondary_speed_up 150
 +set g_balance_grenadelauncher_secondary_speed_z 0
 +set g_balance_grenadelauncher_secondary_spread 0
 +set g_balance_grenadelauncher_secondary_lifetime 5
 +set g_balance_grenadelauncher_secondary_lifetime_bounce 0.5
 +set g_balance_grenadelauncher_secondary_lifetime_stick 0
 +set g_balance_grenadelauncher_secondary_refire 0.7
 +set g_balance_grenadelauncher_secondary_animtime 0.3
 +set g_balance_grenadelauncher_secondary_ammo 2
 +set g_balance_grenadelauncher_secondary_health 30
 +set g_balance_grenadelauncher_secondary_damageforcescale 4
 +set g_balance_grenadelauncher_secondary_remote_detonateprimary 0
 +
 +set g_balance_grenadelauncher_bouncefactor 0.5
 +set g_balance_grenadelauncher_bouncestop 0.075
 +
 +set g_balance_grenadelauncher_switchdelay_drop 0.2
 +set g_balance_grenadelauncher_switchdelay_raise 0.2
 +
 +set g_balance_grenadelauncher_reload_ammo 0 //default: 12
 +set g_balance_grenadelauncher_reload_time 2
 +// }}}
 +// {{{ electro
 +set g_balance_electro_lightning 0
 +set g_balance_electro_primary_damage 40
 +set g_balance_electro_primary_edgedamage 20
 +set g_balance_electro_primary_force 200
 +set g_balance_electro_primary_force_up 0
 +set g_balance_electro_primary_radius 100
 +set g_balance_electro_primary_comboradius 300
 +set g_balance_electro_primary_speed 2500
 +set g_balance_electro_primary_spread 0
 +set g_balance_electro_primary_lifetime 5
 +set g_balance_electro_primary_refire 0.6
 +set g_balance_electro_primary_animtime 0.3
 +set g_balance_electro_primary_ammo 4
 +set g_balance_electro_primary_range 0
 +set g_balance_electro_primary_falloff_mindist 255 // 0.3 * radius
 +set g_balance_electro_primary_falloff_maxdist 850
 +set g_balance_electro_primary_falloff_halflifedist 425
 +set g_balance_electro_secondary_damage 40
 +set g_balance_electro_secondary_edgedamage 20
 +set g_balance_electro_secondary_force 50
 +set g_balance_electro_secondary_radius 150
 +set g_balance_electro_secondary_speed 1000
 +set g_balance_electro_secondary_speed_up 200
 +set g_balance_electro_secondary_speed_z 0
 +set g_balance_electro_secondary_spread 0.04
 +set g_balance_electro_secondary_lifetime 4
 +set g_balance_electro_secondary_refire 0.2
 +set g_balance_electro_secondary_refire2 1.6
 +set g_balance_electro_secondary_animtime 0.2
 +set g_balance_electro_secondary_ammo 2
 +set g_balance_electro_secondary_health 5
 +set g_balance_electro_secondary_damageforcescale 4
 +set g_balance_electro_secondary_damagedbycontents 1
 +set g_balance_electro_secondary_count 3
 +set g_balance_electro_secondary_bouncefactor 0.3
 +set g_balance_electro_secondary_bouncestop 0.05
 +set g_balance_electro_combo_damage 50
 +set g_balance_electro_combo_edgedamage 25
 +set g_balance_electro_combo_force 120
 +set g_balance_electro_combo_radius 150
 +set g_balance_electro_combo_comboradius 300
 +set g_balance_electro_combo_speed 2000
 +set g_balance_electro_combo_safeammocheck 1
 +set g_balance_electro_switchdelay_drop 0.2
 +set g_balance_electro_switchdelay_raise 0.2
 +set g_balance_electro_reload_ammo 0 //default: 20
 +set g_balance_electro_reload_time 2
 +// }}}
 +// {{{ lightning
 +set g_balance_lightning_primary_ammo 5
 +set g_balance_lightning_primary_animtime 0.2
 +set g_balance_lightning_primary_damage 100
 +set g_balance_lightning_primary_edgedamage 0
 +set g_balance_lightning_primary_falloff_mindist 0
 +set g_balance_lightning_primary_falloff_maxdist 0
 +set g_balance_lightning_primary_falloff_halflifedist 0
 +set g_balance_lightning_primary_force 425
 +set g_balance_lightning_primary_lifetime 0
 +set g_balance_lightning_primary_radius 850
 +set g_balance_lightning_primary_range 800
 +set g_balance_lightning_primary_refire 0.4
 +set g_balance_lightning_primary_speed 0
 +set g_balance_lightning_primary_spread 0
 +set g_balance_lightning_secondary_ammo 5
 +set g_balance_lightning_secondary_animtime 0.5
 +set g_balance_lightning_secondary_damage 100
 +set g_balance_lightning_secondary_damageforcescale 4
 +set g_balance_lightning_secondary_edgedamage 80
 +set g_balance_lightning_secondary_flyingdamage 1
 +set g_balance_lightning_secondary_flyingforce -80
 +set g_balance_lightning_secondary_flyingradius 200
 +set g_balance_lightning_secondary_force -200
 +set g_balance_lightning_secondary_health 1
 +set g_balance_lightning_secondary_lifetime 30
 +set g_balance_lightning_secondary_radius 300
 +set g_balance_lightning_secondary_refire 5
 +set g_balance_lightning_secondary_speed 600
 +// }}}
 +// {{{ crylink 
 +set g_balance_crylink_primary_damage 12
 +set g_balance_crylink_primary_edgedamage 6
 +set g_balance_crylink_primary_force -50
 +set g_balance_crylink_primary_radius 80
 +set g_balance_crylink_primary_speed 2000
 +set g_balance_crylink_primary_spread 0.08
 +set g_balance_crylink_primary_shots 6
 +set g_balance_crylink_primary_bounces 1
 +set g_balance_crylink_primary_refire 0.7
 +set g_balance_crylink_primary_animtime 0.3
 +set g_balance_crylink_primary_ammo 3
 +set g_balance_crylink_primary_bouncedamagefactor 0.5
 +set g_balance_crylink_primary_joindelay 0.1
 +set g_balance_crylink_primary_joinspread 0.2
 +set g_balance_crylink_primary_joinexplode 1
 +set g_balance_crylink_primary_joinexplode_damage 0
 +set g_balance_crylink_primary_joinexplode_edgedamage 0
 +set g_balance_crylink_primary_joinexplode_radius 0
 +set g_balance_crylink_primary_joinexplode_force 0
 +set g_balance_crylink_primary_linkexplode 1
 +
 +set g_balance_crylink_primary_middle_lifetime 5 // range: 35000 full, fades to 70000
 +set g_balance_crylink_primary_middle_fadetime 5
 +set g_balance_crylink_primary_other_lifetime 5
 +set g_balance_crylink_primary_other_fadetime 5
 +
 +set g_balance_crylink_secondary 1
 +set g_balance_crylink_secondary_damage 10
 +set g_balance_crylink_secondary_edgedamage 5
 +set g_balance_crylink_secondary_force -250
 +set g_balance_crylink_secondary_radius 100
 +set g_balance_crylink_secondary_speed 3000
 +set g_balance_crylink_secondary_spread 0.01
 +set g_balance_crylink_secondary_spreadtype 1
 +set g_balance_crylink_secondary_shots 5
 +set g_balance_crylink_secondary_bounces 0
 +set g_balance_crylink_secondary_refire 0.7
 +set g_balance_crylink_secondary_animtime 0.2
 +set g_balance_crylink_secondary_ammo 2
 +set g_balance_crylink_secondary_bouncedamagefactor 0.5
 +set g_balance_crylink_secondary_joindelay 0
 +set g_balance_crylink_secondary_joinspread 0
 +set g_balance_crylink_secondary_joinexplode 0
 +set g_balance_crylink_secondary_joinexplode_damage 0
 +set g_balance_crylink_secondary_joinexplode_edgedamage 0
 +set g_balance_crylink_secondary_joinexplode_radius 0
 +set g_balance_crylink_secondary_joinexplode_force 0
 +set g_balance_crylink_secondary_linkexplode 1
 +
 +set g_balance_crylink_secondary_middle_lifetime 5 // range: 35000 full, fades to 70000
 +set g_balance_crylink_secondary_middle_fadetime 5
 +set g_balance_crylink_secondary_line_lifetime 5
 +set g_balance_crylink_secondary_line_fadetime 5
 +
 +set g_balance_crylink_switchdelay_drop 0.2
 +set g_balance_crylink_switchdelay_raise 0.2
 +
 +set g_balance_crylink_reload_ammo 0 //default: 10
 +set g_balance_crylink_reload_time 2
 +// }}}
 +// {{{ nex
 +set g_balance_nex_primary_damage 80
 +set g_balance_nex_primary_force 400
 +set g_balance_nex_primary_refire 1.5
 +set g_balance_nex_primary_animtime 0.6
 +set g_balance_nex_primary_ammo 6
 +set g_balance_nex_primary_damagefalloff_mindist 0 // 1000    For tZork ;3
 +set g_balance_nex_primary_damagefalloff_maxdist 0 // 3000
 +set g_balance_nex_primary_damagefalloff_halflife 0 // 1500
 +set g_balance_nex_primary_damagefalloff_forcehalflife 0 // 1500
 +
 +set g_balance_nex_secondary 0
 +set g_balance_nex_secondary_charge 0
 +set g_balance_nex_secondary_charge_rate 0.1
 +set g_balance_nex_secondary_chargepool 0
 +set g_balance_nex_secondary_chargepool_regen 0.15
 +set g_balance_nex_secondary_chargepool_pause_regen 1
 +set g_balance_nex_secondary_chargepool_pause_health_regen 1
 +set g_balance_nex_secondary_damage 0
 +set g_balance_nex_secondary_force 0
 +set g_balance_nex_secondary_refire 0
 +set g_balance_nex_secondary_animtime 0
 +set g_balance_nex_secondary_ammo 2
 +set g_balance_nex_secondary_damagefalloff_mindist 0
 +set g_balance_nex_secondary_damagefalloff_maxdist 0
 +set g_balance_nex_secondary_damagefalloff_halflife 0
 +set g_balance_nex_secondary_damagefalloff_forcehalflife 0
 +
 +set g_balance_nex_charge 1
 +set g_balance_nex_charge_mindmg 40
 +set g_balance_nex_charge_start 0.5
 +set g_balance_nex_charge_rate 0.4
 +set g_balance_nex_charge_animlimit 0.5
 +set g_balance_nex_charge_limit 1
 +set g_balance_nex_charge_rot_rate 0
 +set g_balance_nex_charge_rot_pause 0 // Dont rot down until this long after release of charge button
 +set g_balance_nex_charge_shot_multiplier 0
 +set g_balance_nex_charge_velocity_rate 0
 +set g_balance_nex_charge_minspeed 400
 +set g_balance_nex_charge_maxspeed 800
 +
 +set g_balance_nex_switchdelay_drop 0.3
 +set g_balance_nex_switchdelay_raise 0.25
 +
 +set g_balance_nex_reload_ammo 0 //default: 25
 +set g_balance_nex_reload_time 2
 +// }}}
 +// {{{ minstanex
 +set g_balance_minstanex_refire 1
 +set g_balance_minstanex_animtime 0.3
 +set g_balance_minstanex_ammo 10
 +set g_balance_minstanex_laser_ammo 0
 +set g_balance_minstanex_laser_animtime 0.3
 +set g_balance_minstanex_laser_refire 0.7
 +set g_balance_minstanex_switchdelay_drop 0.2
 +set g_balance_minstanex_switchdelay_raise 0.2
 +set g_balance_minstanex_reload_ammo 0 //default: 50
 +set g_balance_minstanex_reload_time 2
 +// }}}
 +// {{{ hagar
 +set g_balance_hagar_primary_damage 25
 +set g_balance_hagar_primary_edgedamage 12.5
 +set g_balance_hagar_primary_force 100
 +set g_balance_hagar_primary_health 15
 +set g_balance_hagar_primary_damageforcescale 0
 +set g_balance_hagar_primary_radius 65
 +set g_balance_hagar_primary_spread 0.03
 +set g_balance_hagar_primary_speed 2500
 +set g_balance_hagar_primary_lifetime 5
 +set g_balance_hagar_primary_refire 0.16667 // 6 rockets per second
 +set g_balance_hagar_primary_ammo 1
 +set g_balance_hagar_secondary 1
 +set g_balance_hagar_secondary_load 1
 +set g_balance_hagar_secondary_load_speed 0.5
 +set g_balance_hagar_secondary_load_spread 0.075
 +set g_balance_hagar_secondary_load_spread_bias 0.5
 +set g_balance_hagar_secondary_load_max 4
 +set g_balance_hagar_secondary_load_hold 4
 +set g_balance_hagar_secondary_load_releasedeath 0
 +set g_balance_hagar_secondary_load_abort 0
 +set g_balance_hagar_secondary_load_linkexplode 0
 +set g_balance_hagar_secondary_load_animtime 0.2
 +set g_balance_hagar_secondary_damage 40
 +set g_balance_hagar_secondary_edgedamage 20
 +set g_balance_hagar_secondary_force 75
 +set g_balance_hagar_secondary_health 15
 +set g_balance_hagar_secondary_damageforcescale 0
 +set g_balance_hagar_secondary_radius 80
 +set g_balance_hagar_secondary_spread 0.05
 +set g_balance_hagar_secondary_speed 2000
 +set g_balance_hagar_secondary_lifetime_min 10
 +set g_balance_hagar_secondary_lifetime_rand 0
 +set g_balance_hagar_secondary_refire 0.5
 +set g_balance_hagar_secondary_ammo 1
 +set g_balance_hagar_switchdelay_drop 0.2
 +set g_balance_hagar_switchdelay_raise 0.2
 +set g_balance_hagar_reload_ammo 0 //default: 25
 +set g_balance_hagar_reload_time 2
 +// }}}
 +// {{{ rocketlauncher
 +set g_balance_rocketlauncher_damage 70
 +set g_balance_rocketlauncher_edgedamage 35
 +set g_balance_rocketlauncher_force 450
 +set g_balance_rocketlauncher_radius 110
 +set g_balance_rocketlauncher_speed 1300
 +set g_balance_rocketlauncher_speedaccel 1300
 +set g_balance_rocketlauncher_speedstart 1000
 +set g_balance_rocketlauncher_lifetime 10
 +set g_balance_rocketlauncher_refire 1.2
 +set g_balance_rocketlauncher_animtime 0.4
 +set g_balance_rocketlauncher_ammo 4
 +set g_balance_rocketlauncher_health 30 // 30 // 5 hitpoints above maximum laser value -- this way lasers can't blow it up, but grenadelauncher still can most the time.
 +set g_balance_rocketlauncher_damageforcescale 1 // low damage force scale so that it can still be affected by other hits, but not so much that it does a 90 degree turn
 +set g_balance_rocketlauncher_detonatedelay 0.02 // positive: timer till detonation is allowed, negative: "security device" that prevents ANY remote detonation if it could hurt its owner, zero: detonatable at any time
 +set g_balance_rocketlauncher_guiderate 70 // max degrees per second
 +set g_balance_rocketlauncher_guideratedelay 0.01 // immediate
 +set g_balance_rocketlauncher_guidegoal 512 // goal distance for (non-laser) guiding (higher = less control, lower = erratic)
 +set g_balance_rocketlauncher_guidedelay 0.2 // delay before guiding kicks in
 +set g_balance_rocketlauncher_guidestop 0 // stop guiding when firing again
 +set g_balance_rocketlauncher_remote_damage 70
 +set g_balance_rocketlauncher_remote_edgedamage 35
 +set g_balance_rocketlauncher_remote_radius 110
 +set g_balance_rocketlauncher_remote_force 400
 +set g_balance_rocketlauncher_switchdelay_drop 0.3
 +set g_balance_rocketlauncher_switchdelay_raise 0.2
 +set g_balance_rocketlauncher_reload_ammo 0 //default: 25
 +set g_balance_rocketlauncher_reload_time 2
 +// }}}
 +// {{{ porto
 +set g_balance_porto_primary_refire 1.5
 +set g_balance_porto_primary_animtime 0.3
 +set g_balance_porto_primary_speed 1000
 +set g_balance_porto_primary_lifetime 5
 +set g_balance_porto_secondary 1
 +set g_balance_porto_secondary_refire 1.5
 +set g_balance_porto_secondary_animtime 0.3
 +set g_balance_porto_secondary_speed 1000
 +set g_balance_porto_secondary_lifetime 5
 +set g_balance_porto_switchdelay_drop 0.2
 +set g_balance_porto_switchdelay_raise 0.2
 +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
 +// }}}
 +// {{{ hook
 +set g_balance_hook_primary_fuel 5 // hook monkeys set 0
++set g_balance_hook_primary_refire 0.2 // hook monkeys set 0
 +set g_balance_hook_primary_animtime 0.3 // good shoot anim
 +set g_balance_hook_primary_hooked_time_max 0 // infinite
 +set g_balance_hook_primary_hooked_time_free 2 // 2s being hooked are free
 +set g_balance_hook_primary_hooked_fuel 5 // fuel per second hooked
 +set g_balance_hook_secondary_damage 25 // not much
 +set g_balance_hook_secondary_edgedamage 5 // not much
 +set g_balance_hook_secondary_radius 500 // LOTS
 +set g_balance_hook_secondary_force -2000 // LOTS
 +set g_balance_hook_secondary_ammo 30 // a whole pack
 +set g_balance_hook_secondary_lifetime 5 // infinite
 +set g_balance_hook_secondary_speed 0 // not much throwing
 +set g_balance_hook_secondary_gravity 5 // fast falling
 +set g_balance_hook_secondary_refire 3 // don't drop too many bombs...
 +set g_balance_hook_secondary_animtime 0.3 // good shoot anim
 +set g_balance_hook_secondary_power 3 // effect behaves like a square function
 +set g_balance_hook_secondary_duration 1.5 // effect runs for three seconds
 +set g_balance_hook_secondary_health 15
 +set g_balance_hook_secondary_damageforcescale 0
 +set g_balance_hook_switchdelay_drop 0.2
 +set g_balance_hook_switchdelay_raise 0.2
 +// }}}
 +// {{{ tuba
 +set g_balance_tuba_refire 0.05
 +set g_balance_tuba_animtime 0.05
 +set g_balance_tuba_attenuation 0.5
 +set g_balance_tuba_volume 1
 +set g_balance_tuba_fadetime 0.25
 +set g_balance_tuba_damage 5
 +set g_balance_tuba_edgedamage 0
 +set g_balance_tuba_radius 200
 +set g_balance_tuba_force 40
 +set g_balance_tuba_pitchstep 6
 +set g_balance_tuba_switchdelay_drop 0.2
 +set g_balance_tuba_switchdelay_raise 0.2
 +// }}}
 +// {{{ fireball // this is a superweapon -- lets make it behave as one.
 +set g_balance_fireball_primary_animtime 0.2
 +set g_balance_fireball_primary_bfgdamage 100
 +set g_balance_fireball_primary_bfgforce 0
 +set g_balance_fireball_primary_bfgradius 1000
 +set g_balance_fireball_primary_damage 200
 +set g_balance_fireball_primary_damageforcescale 0
 +set g_balance_fireball_primary_edgedamage 50
 +set g_balance_fireball_primary_force 600
 +set g_balance_fireball_primary_health 0
 +set g_balance_fireball_primary_laserburntime 0.5
 +set g_balance_fireball_primary_laserdamage 80
 +set g_balance_fireball_primary_laseredgedamage 20
 +set g_balance_fireball_primary_laserradius 256
 +set g_balance_fireball_primary_lifetime 15
 +set g_balance_fireball_primary_radius 200
 +set g_balance_fireball_primary_refire 2
 +set g_balance_fireball_primary_refire2 0
 +set g_balance_fireball_primary_speed 1200
 +set g_balance_fireball_primary_spread 0
 +set g_balance_fireball_secondary_animtime 0.3
 +set g_balance_fireball_secondary_damage 40
 +set g_balance_fireball_secondary_damageforcescale 4
 +set g_balance_fireball_secondary_damagetime 5
 +set g_balance_fireball_secondary_force 100
 +set g_balance_fireball_secondary_laserburntime 0.5
 +set g_balance_fireball_secondary_laserdamage 50
 +set g_balance_fireball_secondary_laseredgedamage 20
 +set g_balance_fireball_secondary_laserradius 110
 +set g_balance_fireball_secondary_lifetime 7
 +set g_balance_fireball_secondary_refire 1.5
 +set g_balance_fireball_secondary_speed 900
 +set g_balance_fireball_secondary_speed_up 100
 +set g_balance_fireball_secondary_speed_z 0
 +set g_balance_fireball_secondary_spread 0
 +set g_balance_fireball_switchdelay_drop 0.2
 +set g_balance_fireball_switchdelay_raise 0.2
 +// }}}
diff --combined qcsrc/client/Main.qc
index 9a3f587d322e5009be64c35c11c573329ca8caba,4ea750ce5dbc5c465713037d84ada9ad97b579c0..83098ea29d4dbf0824be5d7390630aeb174f2903
@@@ -121,6 -121,7 +121,6 @@@ void CSQC_Init(void
        Hook_Precache();
        GibSplash_Precache();
        Casings_Precache();
 -      DamageInfo_Precache();
        Vehicles_Precache();
        turrets_precache();
        Tuba_Precache();
  
        if(autocvar_cl_reticle)
        {
 -              if(autocvar_cl_reticle_item_normal) { precache_pic("gfx/reticle_normal"); }
 -              if(autocvar_cl_reticle_item_nex) { precache_pic("gfx/reticle_nex"); }
 +              precache_pic("gfx/reticle_normal");
 +              // weapon reticles are precached in weapon files
        }
  
        get_mi_min_max_texcoords(1); // try the CLEVER way first
@@@ -213,7 -214,7 +213,7 @@@ float SetTeam(entity o, float Team
                        default:
                                if(GetTeam(Team, false) == world)
                                {
-                                       printf(_("trying to switch to unsupported team %d\n"), Team);
+                                       dprintf("trying to switch to unsupported team %d\n", Team);
                                        Team = NUM_SPECTATOR;
                                }
                                break;
                        default:
                                if(GetTeam(Team, false) == world)
                                {
-                                       printf(_("trying to switch to unsupported team %d\n"), Team);
+                                       dprintf("trying to switch to unsupported team %d\n", Team);
                                        Team = NUM_SPECTATOR;
                                }
                                break;
@@@ -818,7 -819,8 +818,7 @@@ void CSQC_Ent_Update(float bIsNewEntity
                case ENT_CLIENT_WARPZONE_TELEPORTED: WarpZone_Teleported_Read(bIsNewEntity); break;
                case ENT_CLIENT_TRIGGER_MUSIC: Ent_ReadTriggerMusic(); break;
                case ENT_CLIENT_HOOK: Ent_ReadHook(bIsNewEntity, ENT_CLIENT_HOOK); break;
 -              case ENT_CLIENT_LGBEAM: Ent_ReadHook(bIsNewEntity, ENT_CLIENT_LGBEAM); break;
 -              case ENT_CLIENT_GAUNTLET: Ent_ReadHook(bIsNewEntity, ENT_CLIENT_GAUNTLET); break;
 +              case ENT_CLIENT_ARC_BEAM: Ent_ReadArcBeam(bIsNewEntity); break;
                case ENT_CLIENT_ACCURACY: Ent_ReadAccuracy(); break;
                case ENT_CLIENT_AUXILIARYXHAIR: Net_AuXair2(bIsNewEntity); break;
                case ENT_CLIENT_TURRET: ent_turret(); break;
@@@ -957,10 -959,14 +957,10 @@@ void Ent_Init(
        hook_shotorigin[1] = decompressShotOrigin(ReadInt24_t());
        hook_shotorigin[2] = decompressShotOrigin(ReadInt24_t());
        hook_shotorigin[3] = decompressShotOrigin(ReadInt24_t());
 -      electro_shotorigin[0] = decompressShotOrigin(ReadInt24_t());
 -      electro_shotorigin[1] = decompressShotOrigin(ReadInt24_t());
 -      electro_shotorigin[2] = decompressShotOrigin(ReadInt24_t());
 -      electro_shotorigin[3] = decompressShotOrigin(ReadInt24_t());
 -      gauntlet_shotorigin[0] = decompressShotOrigin(ReadInt24_t());
 -      gauntlet_shotorigin[1] = decompressShotOrigin(ReadInt24_t());
 -      gauntlet_shotorigin[2] = decompressShotOrigin(ReadInt24_t());
 -      gauntlet_shotorigin[3] = decompressShotOrigin(ReadInt24_t());
 +      arc_shotorigin[0] = decompressShotOrigin(ReadInt24_t());
 +      arc_shotorigin[1] = decompressShotOrigin(ReadInt24_t());
 +      arc_shotorigin[2] = decompressShotOrigin(ReadInt24_t());
 +      arc_shotorigin[3] = decompressShotOrigin(ReadInt24_t());
  
        if(forcefog)
                strunzone(forcefog);
        g_balance_electro_secondary_bouncefactor = ReadCoord();
        g_balance_electro_secondary_bouncestop = ReadCoord();
  
 -      nex_scope = !ReadByte();
 +      vortex_scope = !ReadByte();
        rifle_scope = !ReadByte();
  
        serverflags = ReadByte();
@@@ -1170,7 -1176,7 +1170,7 @@@ void Net_WeaponComplain(
  
        if(complain_weapon_name)
                strunzone(complain_weapon_name);
 -      complain_weapon_name = strzone(ReadString());
 +      complain_weapon_name = strzone(WEP_NAME(complain_weapon));
  
        complain_weapon_type = ReadByte();
  
@@@ -1214,16 -1220,16 +1214,16 @@@ float CSQC_Parse_TempEntity(
                        Net_ReadRace();
                        bHandled = true;
                        break;
 -              case TE_CSQC_NEXGUNBEAMPARTICLE:
 -                      Net_ReadNexgunBeamParticle();
 +              case TE_CSQC_VORTEXBEAMPARTICLE:
 +                      Net_ReadVortexBeamParticle();
                        bHandled = true;
                        break;
                case TE_CSQC_TEAMNAGGER:
                        Net_TeamNagger();
                        bHandled = true;
                        break;
 -              case TE_CSQC_LIGHTNINGARC:
 -                      Net_ReadLightningarc();
 +              case TE_CSQC_ARC:
 +                      Net_ReadArc();
                        bHandled = true;
                        break;
                case TE_CSQC_PINGPLREPORT:
                        cl_notice_read();
                        bHandled = true;
                        break;
 +              case TE_CSQC_SHOCKWAVEPARTICLE:
 +                      Net_ReadShockwaveParticle();
 +                      bHandled = true;
 +                      break;
                default:
                        // No special logic for this temporary entity; return 0 so the engine can handle it
                        bHandled = false;
diff --combined qcsrc/client/View.qc
index ecc3fa126f05d62f1ea4df0a85f1bb1f610b62be,2a41ba13c673c601f9134052a5f4cba68425a5ee..5e162cb7c96fe4c4267592ff482f4726e85f8344
@@@ -104,7 -104,7 +104,7 @@@ vector GetCurrentFov(float fov
  
        zoomdir = button_zoom;
        if(hud == HUD_NORMAL)
 -      if((activeweapon == WEP_NEX && nex_scope) || (activeweapon == WEP_RIFLE && rifle_scope)) // do NOT use switchweapon here
 +      if((activeweapon == WEP_VORTEX && vortex_scope) || (activeweapon == WEP_RIFLE && rifle_scope)) // do NOT use switchweapon here
                zoomdir += button_attack2;
        if(spectatee_status > 0 || isdemo())
        {
@@@ -269,7 -269,7 +269,7 @@@ float EnemyHitCheck(
  
  float TrueAimCheck()
  {
 -      float nudge = 1; // added to traceline target and subtracted from result
 +      float nudge = 1; // added to traceline target and subtracted from result TOOD(divVerent): do we still need this? Doesn't the engine do this now for us?
        vector vecs, trueaimpoint, w_shotorg;
        vector mi, ma, dv;
        float shottype;
        ta = trueaim;
        mv = MOVE_NOMONSTERS;
  
 -      switch(activeweapon)
 +      switch(activeweapon) // WEAPONTODO
        {
                case WEP_TUBA: // no aim
                case WEP_PORTO: // shoots from eye
                case WEP_HOOK: // no trueaim
 -              case WEP_GRENADE_LAUNCHER: // toss curve
 +              case WEP_MORTAR: // toss curve
                        return SHOTTYPE_HITWORLD;
 -              case WEP_NEX:
 -              case WEP_MINSTANEX:
 +              case WEP_VORTEX:
 +              case WEP_VAPORIZER:
                        mv = MOVE_NORMAL;
                        break;
                case WEP_RIFLE:
                                return EnemyHitCheck();
                        }
                        break;
 -              case WEP_ROCKET_LAUNCHER: // projectile has a size!
 +              case WEP_DEVASTATOR: // projectile has a size!
                        mi = '-3 -3 -3';
                        ma = '3 3 3';
                        break;
@@@ -365,7 -365,6 +365,7 @@@ float camera_mode
  const float CAMERA_FREE = 1;
  const float CAMERA_CHASE = 2;
  float reticle_type;
 +string reticle_image;
  string NextFrameCommand;
  void CSQC_SPIDER_HUD();
  void CSQC_RAPTOR_HUD();
@@@ -378,7 -377,7 +378,7 @@@ float pickup_crosshair_time, pickup_cro
  float hit_time, typehit_time;
  float nextsound_hit_time, nextsound_typehit_time;
  float hitindication_crosshair_time, hitindication_crosshair_size;
 -float use_nex_chargepool;
 +float use_vortex_chargepool;
  
  float myhealth, myhealth_prev;
  float myhealth_flash;
@@@ -493,7 -492,8 +493,8 @@@ void CSQC_UpdateView(float w, float h
        // event chase camera
        if(autocvar_chase_active <= 0) // greater than 0 means it's enabled manually, and this code is skipped
        {
-               if(((spectatee_status >= 0 && (autocvar_cl_eventchase_death && is_dead)) || intermission) && !autocvar_cl_orthoview)
+               WepSet weapons_stat = WepSet_GetFromStat();
+               if(((spectatee_status >= 0 && (autocvar_cl_eventchase_death && is_dead)) || intermission) && !autocvar_cl_orthoview || (autocvar_cl_eventchase_nexball && gametype == MAPINFO_TYPE_NEXBALL && !(weapons_stat & WepSet_FromWeapon(WEP_PORTO))))
                {
                        // make special vector since we can't use view_origin (It is one frame old as of this code, it gets set later with the results this code makes.)
                        vector current_view_origin = (csqcplayer ? csqcplayer.origin : pmove_org);
                R_EndPolygon();
        }
  
 -      // Draw the aiming reticle for weapons that use it
 -      // reticle_type is changed to the item we are zooming / aiming with, to decide which reticle to use
 -      // It must be a persisted float for fading out to work properly (you let go of the zoom button for
 -      // the view to go back to normal, so reticle_type would become 0 as we fade out)
 -      if(spectatee_status || is_dead || hud != HUD_NORMAL)
 -              reticle_type = 0; // prevent reticle from showing during the respawn zoom effect or for spectators
 -      else if((activeweapon == WEP_NEX || activeweapon == WEP_RIFLE || activeweapon == WEP_MINSTANEX) && (button_zoom || zoomscript_caught))
 -              reticle_type = 2; // nex zoom
 -      else if(button_zoom || zoomscript_caught)
 -              reticle_type = 1; // normal zoom
 -      else if((activeweapon == WEP_NEX) && button_attack2)
 -              reticle_type = 2; // nex zoom
 -
 -      if(reticle_type && autocvar_cl_reticle)
 +      if(autocvar_cl_reticle)
        {
 -              if(autocvar_cl_reticle_stretch)
 +              // Draw the aiming reticle for weapons that use it
 +              // reticle_type is changed to the item we are zooming / aiming with, to decide which reticle to use
 +              // It must be a persisted float for fading out to work properly (you let go of the zoom button for
 +              // the view to go back to normal, so reticle_type would become 0 as we fade out)
 +              if(spectatee_status || is_dead || hud != HUD_NORMAL)
                {
 -                      reticle_size_x = vid_conwidth;
 -                      reticle_size_y = vid_conheight;
 -                      reticle_pos_x = 0;
 -                      reticle_pos_y = 0;
 +                      // no zoom reticle while dead
 +                      reticle_type = 0;
                }
 -              else
 +              else if(WEP_ACTION(activeweapon, WR_ZOOMRETICLE) && autocvar_cl_reticle_weapon)
                {
 -                      reticle_size_x = max(vid_conwidth, vid_conheight);
 -                      reticle_size_y = max(vid_conwidth, vid_conheight);
 -                      reticle_pos_x = (vid_conwidth - reticle_size_x) / 2;
 -                      reticle_pos_y = (vid_conheight - reticle_size_y) / 2;
 +                      if(reticle_image != "") { reticle_type = 2; }
 +                      else { reticle_type = 0; }
                }
 -
 -              f = current_zoomfraction;
 -              if(zoomscript_caught)
 -                      f = 1;
 -              if(autocvar_cl_reticle_item_normal)
 +              else if(button_zoom || zoomscript_caught)
                {
 -                      if(reticle_type == 1 && f)
 -                              drawpic(reticle_pos, "gfx/reticle_normal", reticle_size, '1 1 1', f * autocvar_cl_reticle_item_normal, DRAWFLAG_NORMAL);
 +                      // normal zoom
 +                      reticle_type = 1;
                }
 -              if(autocvar_cl_reticle_item_nex)
 +
 +              if(reticle_type)
                {
 -                      if(reticle_type == 2 && f)
 -                              drawpic(reticle_pos, "gfx/reticle_nex", reticle_size, '1 1 1', f * autocvar_cl_reticle_item_nex, DRAWFLAG_NORMAL);
 +                      if(autocvar_cl_reticle_stretch)
 +                      {
 +                              reticle_size_x = vid_conwidth;
 +                              reticle_size_y = vid_conheight;
 +                              reticle_pos_x = 0;
 +                              reticle_pos_y = 0;
 +                      }
 +                      else
 +                      {
 +                              reticle_size_x = max(vid_conwidth, vid_conheight);
 +                              reticle_size_y = max(vid_conwidth, vid_conheight);
 +                              reticle_pos_x = (vid_conwidth - reticle_size_x) / 2;
 +                              reticle_pos_y = (vid_conheight - reticle_size_y) / 2;
 +                      }
 +
 +                      if(zoomscript_caught)
 +                              f = 1;
 +                      else 
 +                              f = current_zoomfraction;
 +
 +                      if(f)
 +                      {
 +                              switch(reticle_type)
 +                              {
 +                                      case 1: drawpic(reticle_pos, "gfx/reticle_normal", reticle_size, '1 1 1', f * autocvar_cl_reticle_normal_alpha, DRAWFLAG_NORMAL); break;
 +                                      case 2: drawpic(reticle_pos, reticle_image, reticle_size, '1 1 1', f * autocvar_cl_reticle_weapon_alpha, DRAWFLAG_NORMAL); break;
 +                              }
 +                      }
                }
        }
 +      else
 +      {
 +              if(reticle_type != 0) { reticle_type = 0; }
 +      }
  
  
        // improved polyblend
                                shottype = SHOTTYPE_HITWORLD;
  
                        vector wcross_color = '0 0 0', wcross_size = '0 0 0';
 -                      string wcross_wep = "", wcross_name;
 +                      string wcross_name = "";
                        float wcross_scale, wcross_blur;
  
 -                      if (autocvar_crosshair_per_weapon || (autocvar_crosshair_color_special == 1))
 +                      if(autocvar_crosshair_per_weapon || (autocvar_crosshair_color_special == 1))
                        {
                                e = get_weaponinfo(switchingweapon);
 -                              if (e && e.netname != "")
 +                              if(e)
                                {
 -                                      wcross_wep = e.netname;
                                        if(autocvar_crosshair_per_weapon)
                                        {
 -                                              wcross_resolution *= cvar(strcat("crosshair_", wcross_wep, "_size"));
 -                                              if (wcross_resolution == 0)
 -                                                      return;
 -                                              wcross_alpha *= cvar(strcat("crosshair_", wcross_wep, "_alpha"));
 -                                              if (wcross_alpha == 0)
 -                                                      return;
 -
 -                                              wcross_style = cvar_string(strcat("crosshair_", wcross_wep));
 -                                              if(wcross_style == "" || wcross_style == "0")
 -                                                      wcross_style = wcross_wep;
 +                                              // WEAPONTODO: access these through some general settings (with non-balance config settings)
 +                                              //wcross_resolution *= cvar(strcat("crosshair_", wcross_wep, "_size"));
 +                                              //if (wcross_resolution == 0)
 +                                                      //return;
 +
 +                                              //wcross_style = cvar_string(strcat("crosshair_", wcross_wep));
 +                                              wcross_resolution *= e.w_crosshair_size;
 +                                              wcross_name = e.w_crosshair;
                                        }
                                }
                        }
  
 -                      //printf("crosshair style: %s\n", wcross_style);
 -                      wcross_name = strcat("gfx/crosshair", wcross_style);
 +                      if(wcross_name == "")
 +                              wcross_name = strcat("gfx/crosshair", wcross_style);
  
                        // MAIN CROSSHAIR COLOR DECISION
                        switch(autocvar_crosshair_color_special)
                        {
                                case 1: // crosshair_color_per_weapon
                                {
 -                                      if(wcross_wep != "")
 +                                      if(e)
                                        {
 -                                              wcross_color = stov(cvar_string(sprintf("crosshair_%s_color", wcross_wep)));
 +                                              wcross_color = e.wpcolor;
                                                break;
                                        }
                                        else { goto normalcolor; }
                                        weapon_clipload = getstati(STAT_WEAPON_CLIPLOAD);
                                        weapon_clipsize = getstati(STAT_WEAPON_CLIPSIZE);
  
 -                                      float nex_charge, nex_chargepool;
 -                                      nex_charge = getstatf(STAT_NEX_CHARGE);
 -                                      nex_chargepool = getstatf(STAT_NEX_CHARGEPOOL);
 +                                      float vortex_charge, vortex_chargepool;
 +                                      vortex_charge = getstatf(STAT_VORTEX_CHARGE);
 +                                      vortex_chargepool = getstatf(STAT_VORTEX_CHARGEPOOL);
  
 -                                      if(nex_charge_movingavg == 0) // this should only happen if we have just loaded up the game
 -                                              nex_charge_movingavg = nex_charge;
 +                                      if(vortex_charge_movingavg == 0) // this should only happen if we have just loaded up the game
 +                                              vortex_charge_movingavg = vortex_charge;
  
  
                                        // handle the values
 -                                      if (autocvar_crosshair_ring && activeweapon == WEP_NEX && nex_charge && autocvar_crosshair_ring_nex) // ring around crosshair representing velocity-dependent damage for the nex
 +                                      if (autocvar_crosshair_ring && activeweapon == WEP_VORTEX && vortex_charge && autocvar_crosshair_ring_vortex) // ring around crosshair representing velocity-dependent damage for the vortex
                                        {
 -                                              if (nex_chargepool || use_nex_chargepool) {
 -                                                      use_nex_chargepool = 1;
 -                                                      ring_inner_value = nex_chargepool;
 +                                              if (vortex_chargepool || use_vortex_chargepool) {
 +                                                      use_vortex_chargepool = 1;
 +                                                      ring_inner_value = vortex_chargepool;
                                                } else {
 -                                                      nex_charge_movingavg = (1 - autocvar_crosshair_ring_nex_currentcharge_movingavg_rate) * nex_charge_movingavg + autocvar_crosshair_ring_nex_currentcharge_movingavg_rate * nex_charge;
 -                                                      ring_inner_value = bound(0, autocvar_crosshair_ring_nex_currentcharge_scale * (nex_charge - nex_charge_movingavg), 1);
 +                                                      vortex_charge_movingavg = (1 - autocvar_crosshair_ring_vortex_currentcharge_movingavg_rate) * vortex_charge_movingavg + autocvar_crosshair_ring_vortex_currentcharge_movingavg_rate * vortex_charge;
 +                                                      ring_inner_value = bound(0, autocvar_crosshair_ring_vortex_currentcharge_scale * (vortex_charge - vortex_charge_movingavg), 1);
                                                }
  
 -                                              ring_inner_alpha = autocvar_crosshair_ring_nex_inner_alpha;
 -                                              ring_inner_rgb = eX * autocvar_crosshair_ring_nex_inner_color_red + eY * autocvar_crosshair_ring_nex_inner_color_green + eZ * autocvar_crosshair_ring_nex_inner_color_blue;
 +                                              ring_inner_alpha = autocvar_crosshair_ring_vortex_inner_alpha;
 +                                              ring_inner_rgb = eX * autocvar_crosshair_ring_vortex_inner_color_red + eY * autocvar_crosshair_ring_vortex_inner_color_green + eZ * autocvar_crosshair_ring_vortex_inner_color_blue;
                                                ring_inner_image = "gfx/crosshair_ring_inner.tga";
  
                                                // draw the outer ring to show the current charge of the weapon
 -                                              ring_value = nex_charge;
 -                                              ring_alpha = autocvar_crosshair_ring_nex_alpha;
 +                                              ring_value = vortex_charge;
 +                                              ring_alpha = autocvar_crosshair_ring_vortex_alpha;
                                                ring_rgb = wcross_color;
                                                ring_image = "gfx/crosshair_ring_nexgun.tga";
                                        }
index bb2c6ce091f81fd36a1e6c8baffaaa9e46fe0dd1,67a03259382feba3d5e14adf53087c834eac6491..67a6f522a2496c8095e33829886d79e0fd7787db
@@@ -62,9 -62,8 +62,9 @@@ float autocvar_cl_particles_quality
  float autocvar_cl_projectiles_sloppy;
  float autocvar_cl_readpicture_force;
  var float autocvar_cl_reticle = 1;
 -float autocvar_cl_reticle_item_nex;
 -float autocvar_cl_reticle_item_normal;
 +var float autocvar_cl_reticle_normal_alpha = 1;
 +var float autocvar_cl_reticle_weapon = 1;
 +var float autocvar_cl_reticle_weapon_alpha = 1;
  float autocvar_cl_reticle_stretch;
  float autocvar_cl_spawn_event_particles;
  var float autocvar_cl_spawn_event_sound = 1;
@@@ -126,14 -125,14 +126,14 @@@ float autocvar_crosshair_ring_minelayer
  float autocvar_crosshair_ring_minelayer_alpha;
  float autocvar_crosshair_ring_hagar;
  float autocvar_crosshair_ring_hagar_alpha;
 -float autocvar_crosshair_ring_nex;
 -float autocvar_crosshair_ring_nex_alpha;
 -float autocvar_crosshair_ring_nex_currentcharge_movingavg_rate;
 -float autocvar_crosshair_ring_nex_currentcharge_scale;
 -float autocvar_crosshair_ring_nex_inner_alpha;
 -float autocvar_crosshair_ring_nex_inner_color_blue;
 -float autocvar_crosshair_ring_nex_inner_color_green;
 -float autocvar_crosshair_ring_nex_inner_color_red;
 +float autocvar_crosshair_ring_vortex;
 +float autocvar_crosshair_ring_vortex_alpha;
 +float autocvar_crosshair_ring_vortex_currentcharge_movingavg_rate;
 +float autocvar_crosshair_ring_vortex_currentcharge_scale;
 +float autocvar_crosshair_ring_vortex_inner_alpha;
 +float autocvar_crosshair_ring_vortex_inner_color_blue;
 +float autocvar_crosshair_ring_vortex_inner_color_green;
 +float autocvar_crosshair_ring_vortex_inner_color_red;
  float autocvar_crosshair_ring_size;
  float autocvar_crosshair_ring_reload;
  float autocvar_crosshair_ring_reload_alpha;
@@@ -322,7 -321,6 +322,7 @@@ float autocvar_hud_panel_weapons_ammo
  float autocvar_hud_panel_weapons_ammo_alpha;
  string autocvar_hud_panel_weapons_ammo_color;
  float autocvar_hud_panel_weapons_ammo_full_cells;
 +float autocvar_hud_panel_weapons_ammo_full_plasma;
  float autocvar_hud_panel_weapons_ammo_full_fuel;
  float autocvar_hud_panel_weapons_ammo_full_nails;
  float autocvar_hud_panel_weapons_ammo_full_rockets;
@@@ -412,6 -410,7 +412,7 @@@ float autocvar_viewsize
  float autocvar_cl_hitsound;
  float autocvar_cl_hitsound_antispam_time;
  var float autocvar_cl_eventchase_death = 1;
+ var float autocvar_cl_eventchase_nexball = 1;
  var float autocvar_cl_eventchase_distance = 140;
  var float autocvar_cl_eventchase_speed = 1.3;
  var vector autocvar_cl_eventchase_maxs = '12 12 8';
diff --combined qcsrc/client/hook.qc
index e2fd94434ef7bd1bd7794980e6f4ac0e885b7e34,889e75d2679dc65cb7bfd18726479fd38fd8f97f..8b2ffca19cdb6e9997edddd5f6c566d93a7b104a
@@@ -75,12 -75,15 +75,12 @@@ void Draw_GrapplingHook(
                case ENT_CLIENT_HOOK:
                        vs = hook_shotorigin[s];
                        break;
 -              case ENT_CLIENT_LGBEAM:
 -                      vs = electro_shotorigin[s];
 -                      break;
 -              case ENT_CLIENT_GAUNTLET:
 -                      vs = gauntlet_shotorigin[s];
 +              case ENT_CLIENT_ARC_BEAM:
 +                      vs = lightning_shotorigin[s];
                        break;
        }
  
-       if((self.owner.sv_entnum == player_localentnum - 1))
+       if((self.owner.sv_entnum == player_localentnum - 1) && autocvar_chase_active <= 0)
        {
                switch(self.HookType)
                {
@@@ -89,7 -92,8 +89,7 @@@
                                a = view_origin + view_forward * vs_x + view_right * -vs_y + view_up * vs_z;
                                b = self.origin;
                                break;
 -                      case ENT_CLIENT_LGBEAM:
 -                      case ENT_CLIENT_GAUNTLET:
 +                      case ENT_CLIENT_ARC_BEAM:
                                if(self.HookRange)
                                        b = view_origin + view_forward * self.HookRange;
                                else
                                a = self.velocity;
                                b = self.origin;
                                break;
 -                      case ENT_CLIENT_LGBEAM:
 -                      case ENT_CLIENT_GAUNTLET:
 +                      case ENT_CLIENT_ARC_BEAM:
                                a = self.origin;
                                b = self.velocity;
                                break;
                case ENT_CLIENT_HOOK:
                        intensity = 1;
                        offset = 0;
-                       if(t == NUM_TEAM_1)
+                       switch(t)
                        {
-                               tex = "particles/hook_red";
-                               rgb = '1 .3 .3';
-                       }
-                       else if(t == NUM_TEAM_2)
-                       {
-                               tex = "particles/hook_blue";
-                               rgb = '.3 .3 1';
-                       }
-                       else if(t == NUM_TEAM_3)
-                       {
-                               tex = "particles/hook_yellow";
-                               rgb = '1 1 .3';
-                       }
-                       else if(t == NUM_TEAM_4)
-                       {
-                               tex = "particles/hook_pink";
-                               rgb = '1 .3 1';
-                       }
-                       else
-                       {
-                               tex = "particles/hook_green";
-                               rgb = '.3 1 .3';
+                               case NUM_TEAM_1: tex = "particles/hook_red"; rgb = '1 0.3 0.3'; break;
+                               case NUM_TEAM_2: tex = "particles/hook_blue"; rgb = '0.3 0.3 1'; break;
+                               case NUM_TEAM_3: tex = "particles/hook_yellow"; rgb = '1 1 0.3'; break;
+                               case NUM_TEAM_4: tex = "particles/hook_pink"; rgb = '1 0.3 1'; break;
+                               default: tex = "particles/hook_white"; rgb = getcsqcplayercolor(self.sv_entnum); break;
                        }
                        break;
 -              case ENT_CLIENT_LGBEAM:
 +              case ENT_CLIENT_ARC_BEAM: // todo
                        intensity = bound(0.2, 1 + Noise_Pink(self, frametime) * 1 + Noise_Burst(self, frametime, 0.03) * 0.3, 2);
                        offset = Noise_Brown(self, frametime) * 10;
                        tex = "particles/lgbeam";
                        rgb = '1 1 1';
                        break;
 -              case ENT_CLIENT_GAUNTLET:
 -                      intensity = 1;
 -                      offset = Noise_White(self, frametime);
 -                      tex = "particles/gauntletbeam";
 -                      rgb = '1 1 1';
 -                      break;
        }
  
        Draw_GrapplingHook_trace_callback_tex = tex;
                                self.drawmask = 0;
                        }
                        break;
 -              case ENT_CLIENT_LGBEAM:
 -              case ENT_CLIENT_GAUNTLET:
 +              case ENT_CLIENT_ARC_BEAM:
                        setorigin(self, a); // beam origin!
                        break;
        }
                default:
                case ENT_CLIENT_HOOK:
                        break;
 -              case ENT_CLIENT_LGBEAM:
 -                      pointparticles(particleeffectnum("electro_lightning"), trace_endpos, normalize(atrans - trace_endpos), frametime * intensity);
 -                      break;
 -              case ENT_CLIENT_GAUNTLET:
 -                      pointparticles(particleeffectnum("gauntlet_lightning"), b, normalize(a - b), frametime * intensity);
 +              case ENT_CLIENT_ARC_BEAM:
 +                      pointparticles(particleeffectnum("electro_lightning"), trace_endpos, normalize(atrans - trace_endpos), frametime * intensity); // todo: new effect
                        break;
        }
  }
@@@ -217,14 -215,17 +200,16 @@@ void Ent_ReadHook(float bIsNew, float t
  
        if(sf & 1)
        {
-               self.owner = playerslots[ReadByte() - 1];
+               float myowner = ReadByte();
+               self.owner = playerslots[myowner - 1];
+               self.sv_entnum = myowner;
                switch(self.HookType)
                {
                        default:
                        case ENT_CLIENT_HOOK:
 -                      case ENT_CLIENT_GAUNTLET:
                                self.HookRange = 0;
                                break;
 -                      case ENT_CLIENT_LGBEAM:
 +                      case ENT_CLIENT_ARC_BEAM:
                                self.HookRange = ReadCoord();
                                break;
                }
                                setmodel(self, "models/hook.md3");
                                self.drawmask = MASK_NORMAL;
                                break;
 -                      case ENT_CLIENT_LGBEAM:
 +                      case ENT_CLIENT_ARC_BEAM:
                                sound (self, CH_SHOTS_SINGLE, "weapons/lgbeam_fly.wav", VOL_BASE, ATTEN_NORM);
                                break;
 -                      case ENT_CLIENT_GAUNTLET:
 -                              sound (self, CH_SHOTS_SINGLE, "weapons/gauntletbeam_fly.wav", VOL_BASE, ATTEN_NORM);
 -                              break;
                }
        }
  
  void Hook_Precache()
  {
        precache_sound("weapons/lgbeam_fly.wav");
 -      precache_sound("weapons/gauntletbeam_fly.wav");
        precache_model("models/hook.md3");
  }
  
index 23f4c1d770bc08508510682cc4371b23602aa77b,46dcfb4c451f09c46287aa21a5a4bde008c8426e..b206e2a7f1eda55b7629b94826431d854cc315be
@@@ -955,7 -955,7 +955,7 @@@ float average_accuracy
  vector HUD_DrawScoreboardAccuracyStats(vector pos, vector rgb, vector bg_size)
  {
        float i;
 -      float weapon_cnt = WEP_COUNT - 3; // either minstanex/nex are hidden, no port-o-launch, no tuba
 +      float weapon_cnt = WEP_COUNT - 3; // either vaporizer/nex are hidden, no port-o-launch, no tuba
        float rows;
        if(autocvar_scoreboard_accuracy_doublerows)
                rows = 2;
        if(rows == 2)
                pos_x += weapon_width / 2;
  
 -      if(switchweapon == WEP_MINSTANEX)
 +      if(switchweapon == WEP_VAPORIZER)
                g_minstagib = 1; // TODO: real detection for minstagib?
  
        float weapon_stats;
                self = get_weaponinfo(i);
                if (!self.weapon)
                        continue;
 -              if ((i == WEP_NEX && g_minstagib) || i == WEP_PORTO || (i == WEP_MINSTANEX && !g_minstagib) || i == WEP_TUBA) // skip port-o-launch, nex || minstanex and tuba
 +              if ((i == WEP_VORTEX && g_minstagib) || i == WEP_PORTO || (i == WEP_VAPORIZER && !g_minstagib) || i == WEP_TUBA) // skip port-o-launch, vortex || vaporizer and tuba
                        continue;
                weapon_stats = weapon_accuracy[i-WEP_FIRST];
  
                        weapon_alpha = 0.2 * scoreboard_alpha_fg;
  
                // weapon icon
 -              drawpic_aspect_skin(pos, strcat("weapon", self.netname), '1 0 0' * weapon_width + '0 1 0' * weapon_height, '1 1 1', weapon_alpha, DRAWFLAG_NORMAL);
 +              drawpic_aspect_skin(pos, self.model2, '1 0 0' * weapon_width + '0 1 0' * weapon_height, '1 1 1', weapon_alpha, DRAWFLAG_NORMAL);
                // the accuracy
                if(weapon_stats >= 0) {
                        weapons_with_stats += 1;
@@@ -1313,7 -1313,7 +1313,7 @@@ void HUD_DrawScoreboard(
                }
                pos = HUD_DrawScoreboardRankings(pos, playerslots[player_localnum], rgb, bg_size);
        }
-       else if(autocvar_scoreboard_accuracy && spectatee_status != -1 && !warmup_stage) {
+       else if(autocvar_scoreboard_accuracy && spectatee_status == 0 && !warmup_stage && gametype != MAPINFO_TYPE_NEXBALL) {
                if(teamplay)
                        pos = HUD_DrawScoreboardAccuracyStats(pos, Team_ColorRGB(myteam), bg_size);
                else
  
        // Print info string
        float tl, fl, ll;
-       str = sprintf(_("playing on ^2%s^7"), shortmapname);
+       str = sprintf(_("playing ^3%s^7 on ^2%s^7"), MapInfo_Type_ToText(gametype), shortmapname);
        tl = getstatf(STAT_TIMELIMIT);
        fl = getstatf(STAT_FRAGLIMIT);
        ll = getstatf(STAT_LEADLIMIT);
  
        // print information about respawn status
        float respawn_time = getstatf(STAT_RESPAWN_TIME);
+       if(!intermission)
        if(respawn_time)
        {
                if(respawn_time < 0)
index 68ecfd74b022f2dc77f04afdad869c02cd1f644d,1367501a8a3743ab17b2c2fa5dbb02c9a7870911..24b200d3467d0d3378b50632ed09672a3e6cc402
@@@ -217,20 -217,30 +217,20 @@@ float spritelookupblinkvalue(string s
  }
  vector spritelookupcolor(string s, vector def)
  {
 +      if(substring(s, 0, 4) == "wpn-")
 +              return (get_weaponinfo(stof(substring(s, 4, strlen(s)))).wpcolor);
 +
        switch(s)
        {
                case "keycarrier-friend": return '0 1 0';
 -              case "wpn-laser":         return '1 0.5 0.5';
 -              case "wpn-shotgun":       return '0.5 0.25 0';
 -              case "wpn-uzi":           return '1 1 0';
 -              case "wpn-gl":            return '1 0 0';
 -              case "wpn-electro":       return '0 0.5 1';
 -              case "wpn-crylink":       return '1 0.5 1';
 -              case "wpn-nex":           return '0.5 1 1';
 -              case "wpn-hagar":         return '1 1 0.5';
 -              case "wpn-rl":            return '1 1 0';
 -              case "wpn-porto":         return '0.5 0.5 0.5';
 -              case "wpn-minstanex":     return '0.5 1 1';
 -              case "wpn-hookgun":       return '0 0.5 0';
 -              case "wpn-fireball":      return '1 0.5 0';
 -              case "wpn-hlac":          return '0 1 0';
 -              case "wpn-campingrifle":  return '0.5 1 0';
 -              case "wpn-minelayer":     return '0.75 1 0';
                default:                  return def;
        }
  }
  string spritelookuptext(string s)
  {
 +      if(substring(s, 0, 4) == "wpn-")
 +              return (get_weaponinfo(stof(substring(s, 4, strlen(s)))).message);
 +
        switch(s)
        {
                case "as-push": return _("Push");
                case "race-finish": return _("Finish");
                case "race-start": return _("Start");
                case "race-start-finish": return (race_checkpointtime || race_mycheckpointtime) ? _("Finish") : _("Start");
+               case "goal": return _("Goal");
                case "nb-ball": return _("Ball");
                case "ka-ball": return _("Ball");
                case "ka-ballcarrier": return _("Ball carrier");
 -              case "wpn-laser": return _("Laser");
 -              case "wpn-shotgun": return _("Shotgun");
 -              case "wpn-uzi": return _("Machine Gun");
 -              case "wpn-gl": return _("Mortar");
 -              case "wpn-electro": return _("Electro");
 -              case "wpn-crylink": return _("Crylink");
 -              case "wpn-nex": return _("Nex");
 -              case "wpn-hagar": return _("Hagar");
 -              case "wpn-rl": return _("Rocket Launcher");
 -              case "wpn-porto": return _("Port-O-Launch");
 -              case "wpn-minstanex": return _("Minstanex");
 -              case "wpn-hookgun": return _("Hook");
 -              case "wpn-fireball": return _("Fireball");
 -              case "wpn-hlac": return _("HLAC");
 -              case "wpn-campingrifle": return _("Rifle");
 -              case "wpn-minelayer": return _("Mine Layer");
                case "dom-neut": return _("Control point");
                case "dom-red": return _("Control point");
                case "dom-blue": return _("Control point");
index d7cf63a9d7b0890ceab5fbefb2f1da404195dfce,bda48d5cb91dee7ae2fd20b5c1cb3d001c17d1b7..fd86dbbfc4e7595dbfad9a5c4f155fb810e3a9eb
@@@ -70,7 -70,7 +70,7 @@@ float friend_needshelp(entity e
        switch(self.skin)
        {
                case 0: return (e.health < autocvar_g_balance_health_regenstable);
 -              case 1: return ((e.ammo_cells && e.ammo_cells < g_pickup_cells_max) || (e.ammo_rockets && e.ammo_rockets < g_pickup_rockets_max) || (e.ammo_nails && e.ammo_nails < g_pickup_nails_max) || (e.ammo_shells && e.ammo_shells < g_pickup_shells_max));
 +              case 1: return ((e.ammo_cells && e.ammo_cells < g_pickup_cells_max) || (e.ammo_plasma && e.ammo_plasma < g_pickup_plasma_max) || (e.ammo_rockets && e.ammo_rockets < g_pickup_rockets_max) || (e.ammo_nails && e.ammo_nails < g_pickup_nails_max) || (e.ammo_shells && e.ammo_shells < g_pickup_shells_max));
                case 2: return (e.armorvalue < autocvar_g_balance_armor_regenstable);
                case 3: return (e.health > 0);
        }
@@@ -87,7 -87,7 +87,7 @@@ void mage_spike_explode(
        self.realowner.mage_spike = world;
  
        pointparticles(particleeffectnum("explosion_small"), self.origin, '0 0 0', 1);
 -      RadiusDamage (self, self.realowner, (autocvar_g_monster_mage_attack_spike_damage), (autocvar_g_monster_mage_attack_spike_damage) * 0.5, (autocvar_g_monster_mage_attack_spike_radius), world, 0, DEATH_MONSTER_MAGE, other);
 +      RadiusDamage (self, self.realowner, (autocvar_g_monster_mage_attack_spike_damage), (autocvar_g_monster_mage_attack_spike_damage) * 0.5, (autocvar_g_monster_mage_attack_spike_radius), world, world, 0, DEATH_MONSTER_MAGE, other);
  
        remove (self);
  }
@@@ -209,7 -209,6 +209,7 @@@ void mage_heal(
                                        break;
                                case 1:
                                        if(head.ammo_cells) head.ammo_cells = bound(head.ammo_cells, head.ammo_cells + 1, g_pickup_cells_max);
 +                                      if(head.ammo_plasma) head.ammo_plasma = bound(head.ammo_plasma, head.ammo_plasma + 1, g_pickup_plasma_max);
                                        if(head.ammo_rockets) head.ammo_rockets = bound(head.ammo_rockets, head.ammo_rockets + 1, g_pickup_rockets_max);
                                        if(head.ammo_shells) head.ammo_shells = bound(head.ammo_shells, head.ammo_shells + 2, g_pickup_shells_max);
                                        if(head.ammo_nails) head.ammo_nails = bound(head.ammo_nails, head.ammo_nails + 5, g_pickup_nails_max);
                {
                        pointparticles(particleeffectnum("healing_fx"), head.origin, '0 0 0', 1);
                        head.health = bound(0, head.health + (autocvar_g_monster_mage_heal_allies), head.max_health);
-                       WaypointSprite_UpdateHealth(head.sprite, head.health);
+                       if(!(head.spawnflags & MONSTERFLAG_INVINCIBLE))
+                               WaypointSprite_UpdateHealth(head.sprite, head.health);
                }
        }
  
  void mage_push()
  {
        sound(self, CH_SHOTS, "weapons/tagexp1.wav", 1, ATTEN_NORM);
 -      RadiusDamage (self, self, (autocvar_g_monster_mage_attack_push_damage), (autocvar_g_monster_mage_attack_push_damage), (autocvar_g_monster_mage_attack_push_radius), world, (autocvar_g_monster_mage_attack_push_force), DEATH_MONSTER_MAGE, self.enemy);
 +      RadiusDamage (self, self, (autocvar_g_monster_mage_attack_push_damage), (autocvar_g_monster_mage_attack_push_damage), (autocvar_g_monster_mage_attack_push_radius), world, world, (autocvar_g_monster_mage_attack_push_force), DEATH_MONSTER_MAGE, self.enemy);
        pointparticles(particleeffectnum("TE_EXPLOSION"), self.origin, '0 0 0', 1);
  
        self.frame = mage_anim_attack;
@@@ -336,12 -336,7 +337,7 @@@ void spawnfunc_monster_mage(
  {
        self.classname = "monster_mage";
  
-       self.monster_spawnfunc = spawnfunc_monster_mage;
-       if(Monster_CheckAppearFlags(self))
-               return;
-       if(!monster_initialize(MON_MAGE, FALSE)) { remove(self); return; }
+       if(!monster_initialize(MON_MAGE)) { remove(self); return; }
  }
  
  // compatibility with old spawns
@@@ -398,7 -393,7 +394,7 @@@ float m_mage(float req
                }
                case MR_PRECACHE:
                {
-                       precache_model ("models/monsters/mage.dpm");
+                       precache_model("models/monsters/mage.dpm");
                        precache_sound ("weapons/grenade_impact.wav");
                        precache_sound ("weapons/tagexp1.wav");
                        return TRUE;
@@@ -416,7 -411,6 +412,6 @@@ float m_mage(float req
        {
                case MR_PRECACHE:
                {
-                       precache_model ("models/monsters/mage.dpm");
                        return TRUE;
                }
        }
index 655648784a105eefad53ca96c4db3444c19a1e9c,0e82fe8d290e726974fd4b9d493a78fda4349096..7c46a1da15f087bf1cbf15e001bbb5f84978dafc
@@@ -74,7 -74,7 +74,7 @@@ void shambler_lightning_explode(
        if(self.movetype == MOVETYPE_NONE)
                self.velocity = self.oldvelocity;
  
 -      RadiusDamage (self, self.realowner, (autocvar_g_monster_shambler_attack_lightning_damage), (autocvar_g_monster_shambler_attack_lightning_damage), (autocvar_g_monster_shambler_attack_lightning_radius), world, (autocvar_g_monster_shambler_attack_lightning_force), self.projectiledeathtype, other);
 +      RadiusDamage (self, self.realowner, (autocvar_g_monster_shambler_attack_lightning_damage), (autocvar_g_monster_shambler_attack_lightning_damage), (autocvar_g_monster_shambler_attack_lightning_radius), world, world, (autocvar_g_monster_shambler_attack_lightning_force), self.projectiledeathtype, other);
  
        for(head = findradius(self.origin, (autocvar_g_monster_shambler_attack_lightning_radius_zap)); head; head = head.chain) if(head != self.realowner) if(head.takedamage)
        {
@@@ -148,7 -148,7 +148,7 @@@ void shambler_lightning(
        gren.event_damage = shambler_lightning_damage;
        gren.damagedbycontents = TRUE;
        gren.missile_flags = MIF_SPLASH | MIF_ARC;
 -      W_SetupProjectileVelocityEx(gren, v_forward, v_up, (autocvar_g_monster_shambler_attack_lightning_speed), (autocvar_g_monster_shambler_attack_lightning_speed_up), 0, 0, FALSE);
 +      W_SetupProjVelocity_Explicit(gren, v_forward, v_up, (autocvar_g_monster_shambler_attack_lightning_speed), (autocvar_g_monster_shambler_attack_lightning_speed_up), 0, 0, FALSE);
  
        gren.angles = vectoangles (gren.velocity);
        gren.flags = FL_PROJECTILE;
@@@ -168,6 -168,7 +168,7 @@@ float shambler_attack(float attack_type
                case MONSTER_ATTACK_RANGED:
                {
                        if(time >= self.shambler_lastattack) // shambler doesn't attack much
+                       if(self.flags & FL_ONGROUND)
                        if(random() <= 0.5 && vlen(self.enemy.origin - self.origin) <= 500)
                        {
                                self.frame = shambler_anim_smash;
@@@ -196,12 -197,7 +197,7 @@@ void spawnfunc_monster_shambler(
  {
        self.classname = "monster_shambler";
  
-       self.monster_spawnfunc = spawnfunc_monster_shambler;
-       if(Monster_CheckAppearFlags(self))
-               return;
-       if(!monster_initialize(MON_SHAMBLER, FALSE)) { remove(self); return; }
+       if(!monster_initialize(MON_SHAMBLER)) { remove(self); return; }
  }
  
  float m_shambler(float req)
                        self.monster_loot = spawnfunc_item_health_mega;
                        self.monster_attackfunc = shambler_attack;
                        self.frame = shambler_anim_stand;
 -                      self.weapon = WEP_NEX;
 +                      self.weapon = WEP_VORTEX;
  
                        return TRUE;
                }
                case MR_PRECACHE:
                {
-                       precache_model ("models/monsters/shambler.mdl");
+                       precache_model("models/monsters/shambler.mdl");
                        return TRUE;
                }
        }
@@@ -248,7 -244,6 +244,6 @@@ float m_shambler(float req
        {
                case MR_PRECACHE:
                {
-                       precache_model ("models/monsters/shambler.mdl");
                        return TRUE;
                }
        }
index 84281157ba587c6442d16413664272d6a9c2124d,7e35b8b1626d04e56ac5ad0748cb1e2904b4f184..c6c454547f4898bb96e946cb5994bd585b073e02
@@@ -35,9 -35,9 +35,9 @@@ void spider_web_explode(
        if(self)
        {
                pointparticles(particleeffectnum("electro_impact"), self.origin, '0 0 0', 1);
 -              RadiusDamage(self, self.realowner, 0, 0, 25, world, 25, self.projectiledeathtype, world);
 +              RadiusDamage(self, self.realowner, 0, 0, 25, world, world, 25, self.projectiledeathtype, world);
  
-               for(e = findradius(self.origin, 25); e; e = e.chain) if(e != self) if(e.takedamage && e.deadflag == DEAD_NO) if(e.health > 0)
+               for(e = findradius(self.origin, 25); e; e = e.chain) if(e != self) if(e.takedamage && e.deadflag == DEAD_NO) if(e.health > 0) if(e.monsterid != MON_SPIDER)
                        e.spider_slowness = time + (autocvar_g_monster_spider_attack_web_damagetime);
  
                remove(self);
@@@ -72,7 -72,7 +72,7 @@@ void spider_shootweb(
        //proj.glow_size = 50;
        //proj.glow_color = 45;
        proj.movetype = MOVETYPE_BOUNCE;
 -      W_SetupProjectileVelocityEx(proj, v_forward, v_up, (autocvar_g_monster_spider_attack_web_speed), (autocvar_g_monster_spider_attack_web_speed_up), 0, 0, FALSE);
 +      W_SetupProjVelocity_Explicit(proj, v_forward, v_up, (autocvar_g_monster_spider_attack_web_speed), (autocvar_g_monster_spider_attack_web_speed_up), 0, 0, FALSE);
        proj.touch = spider_web_touch;
        setsize(proj, '-4 -4 -4', '4 4 4');
        proj.takedamage = DAMAGE_NO;
@@@ -119,12 -119,7 +119,7 @@@ void spawnfunc_monster_spider(
  {
        self.classname = "monster_spider";
  
-       self.monster_spawnfunc = spawnfunc_monster_spider;
-       if(Monster_CheckAppearFlags(self))
-               return;
-       if(!monster_initialize(MON_SPIDER, FALSE)) { remove(self); return; }
+       if(!monster_initialize(MON_SPIDER)) { remove(self); return; }
  }
  
  float m_spider(float req)
                }
                case MR_PRECACHE:
                {
-                       precache_model ("models/monsters/spider.dpm");
+                       precache_model("models/monsters/spider.dpm");
                        precache_sound ("weapons/electro_fire2.wav");
                        return TRUE;
                }
@@@ -171,7 -166,6 +166,6 @@@ float m_spider(float req
        {
                case MR_PRECACHE:
                {
-                       precache_model ("models/monsters/spider.dpm");
                        return TRUE;
                }
        }
index ad8c6b02dcc209e760ecb9a7fb46111157330df8,ed4962d061ccd47934bd551d6c336189e1d103d8..a44f6d9c7ab2fe089dea4c821a8857fa3e98c0c0
@@@ -35,7 -35,7 +35,7 @@@ void wyvern_fireball_explode(
        {
                pointparticles(particleeffectnum("fireball_explode"), self.origin, '0 0 0', 1);
  
 -              RadiusDamage(self, self.realowner, (autocvar_g_monster_wyvern_attack_fireball_damage), (autocvar_g_monster_wyvern_attack_fireball_edgedamage), (autocvar_g_monster_wyvern_attack_fireball_force), world, (autocvar_g_monster_wyvern_attack_fireball_radius), self.projectiledeathtype, world);
 +              RadiusDamage(self, self.realowner, (autocvar_g_monster_wyvern_attack_fireball_damage), (autocvar_g_monster_wyvern_attack_fireball_edgedamage), (autocvar_g_monster_wyvern_attack_fireball_force), world, world, (autocvar_g_monster_wyvern_attack_fireball_radius), self.projectiledeathtype, world);
  
                for(e = world; (e = findfloat(e, takedamage, DAMAGE_AIM)); ) if(vlen(e.origin - self.origin) <= (autocvar_g_monster_wyvern_attack_fireball_radius))
                        Fire_AddDamage(e, self, 5 * Monster_SkillModifier(), (autocvar_g_monster_wyvern_attack_fireball_damagetime), self.projectiledeathtype);
@@@ -96,12 -96,7 +96,7 @@@ void spawnfunc_monster_wyvern(
  {
        self.classname = "monster_wyvern";
  
-       self.monster_spawnfunc = spawnfunc_monster_wyvern;
-       if(Monster_CheckAppearFlags(self))
-               return;
-       if(!monster_initialize(MON_WYVERN, TRUE)) { remove(self); return; }
+       if(!monster_initialize(MON_WYVERN)) { remove(self); return; }
  }
  
  // compatibility with old spawns
@@@ -136,7 -131,7 +131,7 @@@ float m_wyvern(float req
                }
                case MR_PRECACHE:
                {
-                       precache_model ("models/monsters/wizard.mdl");
+                       precache_model("models/monsters/wizard.mdl");
                        return TRUE;
                }
        }
@@@ -152,7 -147,6 +147,6 @@@ float m_wyvern(float req
        {
                case MR_PRECACHE:
                {
-                       precache_model ("models/monsters/wizard.mdl");
                        return TRUE;
                }
        }
index 013eea7436b122149ed78db98f0fff22d6bbc93a,34e7ceb9901ebbb30583e88b3862ba3204cd28fb..5d52bc18c4e16c962991448cf48490666d037982
@@@ -3,30 -3,13 +3,13 @@@
  // =========================
  
  
- void monster_item_spawn()
- {
-       if(self.monster_loot)
-               self.monster_loot();
-       self.gravity = 1;
-       self.reset = SUB_Remove;
-       self.noalign = TRUE;
-       self.velocity = randomvec() * 175 + '0 0 325';
-       self.classname = "droppedweapon"; // hax
-       self.item_spawnshieldtime = time + 0.7;
-       SUB_SetFade(self, time + autocvar_g_monsters_drop_time, 1);
- }
  void monster_dropitem()
  {
        if(!self.candrop || !self.monster_loot)
                return;
  
        vector org = self.origin + ((self.mins + self.maxs) * 0.5);
-       entity e = spawn();
-       setorigin(e, org);
+       entity e = spawn(), oldself = self;
  
        e.monster_loot = self.monster_loot;
  
        MUTATOR_CALLHOOK(MonsterDropItem);
        e = other;
  
-       if(e)
+       if(e && e.monster_loot)
        {
-               e.think = monster_item_spawn;
-               e.nextthink = time + 0.3;
+               self = e;
+               e.noalign = TRUE;
+               e.monster_loot();
+               e.gravity = 1;
+               e.movetype = MOVETYPE_TOSS;
+               e.reset = SUB_Remove;
+               setorigin(e, org);
+               e.velocity = randomvec() * 175 + '0 0 325';
+               e.item_spawnshieldtime = time + 0.7;
+               e.classname = "droppedweapon"; // use weapon handling to remove it on touch
+               SUB_SetFade(e, time + autocvar_g_monsters_drop_time, 1);
+               self = oldself;
        }
  }
  
@@@ -56,10 -49,10 +49,10 @@@ float monster_isvalidtarget (entity tar
        if(targ == ent)
                return FALSE; // don't attack ourselves
  
-       traceline(ent.origin, targ.origin, MOVE_NORMAL, ent);
+       //traceline(ent.origin, targ.origin, MOVE_NORMAL, ent);
  
-       if(trace_ent != targ)
-               return FALSE;
+       //if(trace_ent != targ)
+               //return FALSE;
  
        if(targ.vehicle_flags & VHF_ISVEHICLE)
        if(!((get_monsterinfo(ent.monsterid)).spawnflags & MON_FLAG_RANGED))
@@@ -68,9 -61,6 +61,6 @@@
        if(time < game_starttime)
                return FALSE; // monsters do nothing before the match has started
  
-       if(vlen(targ.origin - ent.origin) >= ent.target_range)
-               return FALSE; // enemy is too far away
        if(targ.takedamage == DAMAGE_NO)
                return FALSE; // enemy can't be damaged
  
        if (targ.freezetag_frozen)
                return FALSE; // ignore frozen
  
-       if(autocvar_g_monsters_target_infront || ent.spawnflags & MONSTERFLAG_INFRONT)
+       if(autocvar_g_monsters_target_infront || (ent.spawnflags & MONSTERFLAG_INFRONT))
        if(ent.enemy != targ)
        {
                float dot;
@@@ -128,6 -118,7 +118,7 @@@ entity FindTarget (entity ent
  
        entity head, closest_target = world;
        head = findradius(ent.origin, ent.target_range);
+       //head = WarpZone_FindRadius(ent.origin, ent.target_range, TRUE);
  
        while(head) // find the closest acceptable target to pass to
        {
                {
                        // if it's a player, use the view origin as reference (stolen from RadiusDamage functions in g_damage.qc)
                        vector head_center = CENTER_OR_VIEWOFS(head);
+                       //vector head_center = WarpZone_UnTransformOrigin(head, CENTER_OR_VIEWOFS(head));
                        vector ent_center = CENTER_OR_VIEWOFS(ent);
  
-                       //if(ctf_CheckPassDirection(head_center, ent_center, ent.v_angle, head.WarpZone_findradius_nearest))
+                       traceline(ent_center, head_center, MOVE_NORMAL, ent);
+                       if(trace_ent == head)
                        if(closest_target)
                        {
                                vector closest_target_center = CENTER_OR_VIEWOFS(closest_target);
+                               //vector closest_target_center = WarpZone_UnTransformOrigin(closest_target, CENTER_OR_VIEWOFS(closest_target));
                                if(vlen(ent_center - head_center) < vlen(ent_center - closest_target_center))
                                        { closest_target = head; }
                        }
@@@ -279,7 -274,10 +274,10 @@@ void UpdateMonsterSounds(
  
  void MonsterSound(.string samplefield, float sound_delay, float delaytoo, float chan)
  {
-       if(delaytoo && time < self.msound_delay)
+       if(!autocvar_g_monsters_sounds) { return; }
+       if(delaytoo)
+       if(time < self.msound_delay)
                return; // too early
        GlobalSound(self.samplefield, chan, VOICETYPE_PLAYERSOUND);
  
@@@ -337,7 -335,7 +335,7 @@@ void Monster_CheckMinibossFlag (
                self.health += autocvar_g_monsters_miniboss_healthboost;
                self.effects |= EF_RED;
                if(!self.weapon)
 -                      self.weapon = WEP_NEX;
 +                      self.weapon = WEP_VORTEX;
        }
  }
  
@@@ -357,14 -355,21 +355,21 @@@ float Monster_CanRespawn(entity ent
        return TRUE;
  }
  
+ float monster_initialize(float mon_id);
+ void monster_respawn()
+ {
+       // is this function really needed?
+       monster_initialize(self.monsterid);
+ }
  void Monster_Fade ()
  {
        if(Monster_CanRespawn(self))
        {
                self.spawnflags |= MONSTERFLAG_RESPAWNED;
-               self.think = self.monster_spawnfunc;
+               self.think = monster_respawn;
                self.nextthink = time + self.respawntime;
-               self.ltime = 0;
+               self.monster_lifetime = 0;
                self.deadflag = DEAD_RESPAWNING;
                if(self.spawnflags & MONSTER_RESPAWN_DEATHPOINT)
                {
                // number of monsters spawned with mobspawn command
                totalspawned -= 1;
  
-               if(IS_CLIENT(self.realowner))
-                       self.realowner.monstercount -= 1;
                SUB_SetFade(self, time + 3, 1);
        }
  }
@@@ -472,10 -474,40 +474,40 @@@ vector monster_pickmovetarget(entity ta
        // enemy is always preferred target
        if(self.enemy)
        {
-               makevectors(self.angles);
+               vector targ_origin = ((self.enemy.absmin + self.enemy.absmax) * 0.5);
+               targ_origin = WarpZone_RefSys_TransformOrigin(self.enemy, self, targ_origin); // origin of target as seen by the monster (us)
+               WarpZone_TraceLine(self.origin, targ_origin, MOVE_NOMONSTERS, self);
+               
+               if((self.enemy == world)
+                       || (self.enemy.deadflag != DEAD_NO || self.enemy.health < 1)
+                       || (self.enemy.freezetag_frozen)
+                       || (self.enemy.flags & FL_NOTARGET)
+                       || (self.enemy.alpha < 0.5)
+                       || (self.enemy.takedamage == DAMAGE_NO)
+                       || (vlen(self.origin - targ_origin) > self.target_range)
+                       || ((trace_fraction < 1) && (trace_ent != self.enemy)))
+                       //|| (time > self.ctf_droptime + autocvar_g_ctf_pass_timelimit)) // TODO: chase timelimit?
+               {
+                       self.enemy = world;
+                       self.pass_distance = 0;
+               }
+               
+               if(self.enemy)
+               {
+                       /*WarpZone_TrailParticles(world, particleeffectnum("red_pass"), self.origin, targ_origin);
+                       print("Trace origin: ", vtos(targ_origin), "\n");
+                       print("Target origin: ", vtos(self.enemy.origin), "\n");
+                       print("My origin: ", vtos(self.origin), "\n"); */
+                       
+                       self.monster_movestate = MONSTER_MOVE_ENEMY;
+                       self.last_trace = time + 1.2;
+                       return targ_origin;
+               }
+       
+               /*makevectors(self.angles);
                self.monster_movestate = MONSTER_MOVE_ENEMY;
                self.last_trace = time + 1.2;
-               return self.enemy.origin;
+               return self.enemy.origin; */
        }
  
        switch(self.monster_moveflags)
                {
                        vector pos;
                        self.monster_movestate = MONSTER_MOVE_WANDER;
-                       self.last_trace = time + 2;
-                       self.angles_y = rint(random() * 500);
-                       makevectors(self.angles);
-                       pos = self.origin + v_forward * 600;
-                       if(self.flags & FL_FLY || self.flags & FL_SWIM)
-                       if(self.spawnflags & MONSTERFLAG_FLY_VERTICAL)
-                       {
-                               pos_z = random() * 200;
-                               if(random() >= 0.5)
-                                       pos_z *= -1;
-                       }
  
                        if(targ)
                        {
                                self.last_trace = time + 0.5;
                                pos = targ.origin;
                        }
+                       else
+                       {
+                               self.last_trace = time + self.wander_delay;
+                               self.angles_y = rint(random() * 500);
+                               makevectors(self.angles);
+                               pos = self.origin + v_forward * self.wander_distance;
+                               if(((self.flags & FL_FLY) && (self.spawnflags & MONSTERFLAG_FLY_VERTICAL)) || (self.flags & FL_SWIM))
+                               {
+                                       pos_z = random() * 200;
+                                       if(random() >= 0.5)
+                                               pos_z *= -1;
+                               }
+                       }
  
                        return pos;
                }
        }
  }
  
+ void monster_CalculateVelocity(entity mon, vector to, vector from, float turnrate, float movespeed)
+ {
+       float current_distance = vlen((('1 0 0' * to_x) + ('0 1 0' * to_y)) - (('1 0 0' * from_x) + ('0 1 0' * from_y))); // for the sake of this check, exclude Z axis
+       float initial_height = 0; //min(50, (targ_distance * tanh(20)));
+       float current_height = (initial_height * min(1, (current_distance / self.pass_distance)));
+       //print("current_height = ", ftos(current_height), ", initial_height = ", ftos(initial_height), ".\n");
+       vector targpos;
+       if(current_height) // make sure we can actually do this arcing path
+       {
+               targpos = (to + ('0 0 1' * current_height));
+               WarpZone_TraceLine(mon.origin, targpos, MOVE_NOMONSTERS, mon);
+               if(trace_fraction < 1)
+               {
+                       //print("normal arc line failed, trying to find new pos...");
+                       WarpZone_TraceLine(to, targpos, MOVE_NOMONSTERS, mon);
+                       targpos = (trace_endpos + '0 0 -10');
+                       WarpZone_TraceLine(mon.origin, targpos, MOVE_NOMONSTERS, mon);
+                       if(trace_fraction < 1) { targpos = to; /* print(" ^1FAILURE^7, reverting to original direction.\n"); */ }
+                       /*else { print(" ^3SUCCESS^7, using new arc line.\n"); } */
+               }
+       }
+       else { targpos = to; }
+       //mon.angles = normalize(('0 1 0' * to_y) - ('0 1 0' * from_y));
+       vector desired_direction = normalize(targpos - from);
+       if(turnrate) { mon.velocity = (normalize(normalize(mon.velocity) + (desired_direction * 50)) * movespeed); }
+       else { mon.velocity = (desired_direction * movespeed); }
+       //mon.steerto = steerlib_attract2(targpos, 0.5, 500, 0.95);
+       //mon.angles = vectoangles(mon.velocity);
+ }
  void monster_move(float runspeed, float walkspeed, float stopspeed, float manim_run, float manim_walk, float manim_idle)
  {
-       fixedmakevectors(self.angles);
+       //fixedmakevectors(self.angles);
  
        if(self.target2)
                self.goalentity = find(world, targetname, self.target2);
        monster_speed_run = runspeed;
        monster_speed_walk = walkspeed;
  
-       if(MUTATOR_CALLHOOK(MonsterMove) || gameover || (round_handler_IsActive() && !round_handler_IsRoundStarted()) || time < game_starttime || (autocvar_g_campaign && !campaign_bots_may_start) || time < self.spawn_time)
+       if(MUTATOR_CALLHOOK(MonsterMove) || gameover || self.draggedby != world || (round_handler_IsActive() && !round_handler_IsRoundStarted()) || time < game_starttime || (autocvar_g_campaign && !campaign_bots_may_start) || time < self.spawn_time)
        {
                runspeed = walkspeed = 0;
                if(time >= self.spawn_time)
        if(DIFF_TEAM(self.monster_owner, self))
                self.monster_owner = world;
  
-       if(self.enemy && self.enemy.health < 1)
-               self.enemy = world; // enough!
        if(time >= self.last_enemycheck)
        {
-               if(!monster_isvalidtarget(self.enemy, self))
-                       self.enemy = world;
                if(!self.enemy)
                {
                        self.enemy = FindTarget(self);
                        if(self.enemy)
+                       {
+                               WarpZone_RefSys_Copy(self.enemy, self);
+                               WarpZone_RefSys_AddInverse(self.enemy, self); // wz1^-1 ... wzn^-1 receiver
+                               self.moveto = WarpZone_RefSys_TransformOrigin(self.enemy, self, (0.5 * (self.enemy.absmin + self.enemy.absmax)));
+                               
+                               self.pass_distance = vlen((('1 0 0' * self.enemy.origin_x) + ('0 1 0' * self.enemy.origin_y)) - (('1 0 0' *  self.origin_x) + ('0 1 0' *  self.origin_y)));
                                MonsterSound(monstersound_sight, 0, FALSE, CH_VOICE);
+                       }
                }
  
-               self.last_enemycheck = time + 0.5;
+               self.last_enemycheck = time + 1; // check for enemies every second
        }
  
        if(self.state == MONSTER_STATE_ATTACK_MELEE && time >= self.attack_finished_single)
        if(!self.enemy)
                MonsterSound(monstersound_idle, 7, TRUE, CH_VOICE);
  
-       if(self.state != MONSTER_STATE_ATTACK_LEAP && self.state != MONSTER_STATE_ATTACK_MELEE)
-               self.steerto = steerlib_attract2(self.moveto, 0.5, 500, 0.95);
        if(self.state == MONSTER_STATE_ATTACK_LEAP && (self.flags & FL_ONGROUND))
        {
                self.state = 0;
                self.touch = MonsterTouch;
        }
  
-       //self.steerto = steerlib_attract2(self.moveto, 0.5, 500, 0.95);
-       float turny = 0;
-       vector real_angle = vectoangles(self.steerto) - self.angles;
-       if(self.state != MONSTER_STATE_ATTACK_LEAP && self.state != MONSTER_STATE_ATTACK_MELEE)
-               turny = 20;
-       if(self.flags & FL_SWIM)
-               turny = vlen(self.angles - self.moveto);
-       if(turny)
-       {
-               turny = bound(turny * -1, shortangle_f(real_angle_y, self.angles_y), turny);
-               self.angles_y += turny;
-       }
        if(self.state == MONSTER_STATE_ATTACK_MELEE)
                self.moveto = self.origin;
  
        if(self.enemy && self.enemy.vehicle)
                runspeed = 0;
  
-       if(((self.flags & FL_FLY) || (self.flags & FL_SWIM)) && self.spawnflags & MONSTERFLAG_FLY_VERTICAL)
-               v_forward = normalize(self.moveto - self.origin);
-       else
+       if(!(((self.flags & FL_FLY) && (self.spawnflags & MONSTERFLAG_FLY_VERTICAL)) || (self.flags & FL_SWIM)))
+               //v_forward = normalize(self.moveto - self.origin);
+       //else
                self.moveto_z = self.origin_z;
  
        if(vlen(self.origin - self.moveto) > 64)
        {
-               if(self.flags & FL_FLY || self.flags & FL_SWIM)
+               if((self.flags & FL_ONGROUND) || ((self.flags & FL_FLY) || (self.flags & FL_SWIM)))
+                       monster_CalculateVelocity(self, self.moveto, self.origin, TRUE, ((self.enemy) ? runspeed : walkspeed));
+               
+               /*&if(self.flags & FL_FLY || self.flags & FL_SWIM)
                        movelib_move_simple(v_forward, ((self.enemy) ? runspeed : walkspeed), 0.6);
                else
-                       movelib_move_simple_gravity(v_forward, ((self.enemy) ? runspeed : walkspeed), 0.6);
+                       movelib_move_simple_gravity(v_forward, ((self.enemy) ? runspeed : walkspeed), 0.6); */
  
                if(time > self.pain_finished)
                if(time > self.attack_finished_single)
                if (vlen(self.velocity) <= 30)
                        self.frame = manim_idle;
        }
+       
+       self.steerto = steerlib_attract2(self.moveto, 0.5, 500, 0.95);
+       
+       vector real_angle = vectoangles(self.steerto) - self.angles;
+       float turny = 25;
+       if(self.state == MONSTER_STATE_ATTACK_MELEE)
+               turny = 0;
+       if(turny)
+       {
+               turny = bound(turny * -1, shortangle_f(real_angle_y, self.angles_y), turny);
+               self.angles_y += turny;
+       }
  
        monster_checkattack(self, self.enemy);
  }
@@@ -723,8 -787,8 +787,8 @@@ void monster_dead_think(
  
        CSQCMODEL_AUTOUPDATE();
  
-       if(self.ltime != 0)
-       if(time >= self.ltime)
+       if(self.monster_lifetime != 0)
+       if(time >= self.monster_lifetime)
        {
                Monster_Fade();
                return;
@@@ -740,16 -804,17 +804,17 @@@ void monsters_setstatus(
  void Monster_Appear()
  {
        self.enemy = activator;
-       self.spawnflags &= ~MONSTERFLAG_APPEAR;
-       self.monster_spawnfunc();
+       self.spawnflags &= ~MONSTERFLAG_APPEAR; // otherwise, we get an endless loop
+       monster_initialize(self.monsterid);
  }
  
- float Monster_CheckAppearFlags(entity ent)
+ float Monster_CheckAppearFlags(entity ent, float monster_id)
  {
        if(!(ent.spawnflags & MONSTERFLAG_APPEAR))
                return FALSE;
  
        ent.think = func_null;
+       ent.monsterid = monster_id; // set so this monster is properly registered (otherwise, normal initialization is used)
        ent.nextthink = 0;
        ent.use = Monster_Appear;
        ent.flags = FL_MONSTER; // set so this monster can get butchered
@@@ -783,11 -848,9 +848,9 @@@ void monsters_corpse_damage (entity inf
                // number of monsters spawned with mobspawn command
                totalspawned -= 1;
  
-               if(IS_CLIENT(self.realowner))
-                       self.realowner.monstercount -= 1;
                self.think = SUB_Remove;
                self.nextthink = time + 0.1;
+               self.event_damage = func_null;
        }
  }
  
@@@ -795,7 -858,7 +858,7 @@@ void monster_die(entity attacker, floa
  {
        self.think = monster_dead_think;
        self.nextthink = time;
-       self.ltime = time + 5;
+       self.monster_lifetime = time + 5;
  
        monster_dropitem();
  
        {
                // number of monsters spawned with mobspawn command
                totalspawned -= 1;
-               if(IS_CLIENT(self.realowner))
-                       self.realowner.monstercount -= 1;
        }
  
        if(self.candrop && self.weapon)
                W_ThrowNewWeapon(self, self.weapon, 0, self.origin, randomvec() * 150 + '0 0 325');
  
-       self.event_damage       = monsters_corpse_damage;
+       self.event_damage       = ((gibbed) ? func_null : monsters_corpse_damage);
        self.solid                      = SOLID_CORPSE;
        self.takedamage         = DAMAGE_AIM;
        self.deadflag           = DEAD_DEAD;
        self.state                      = 0;
        self.attack_finished_single = 0;
  
-       if(!(self.flags & FL_FLY))
+       if(!((self.flags & FL_FLY) || (self.flags & FL_SWIM)))
                self.velocity = '0 0 0';
  
        MON_ACTION(self.monsterid, MR_DEATH);
  
  void monsters_damage (entity inflictor, entity attacker, float damage, float deathtype, vector hitloc, vector force)
  {
+       if((self.spawnflags & MONSTERFLAG_INVINCIBLE) && deathtype != DEATH_KILL)
+               return;
        if(time < self.pain_finished && deathtype != DEATH_KILL)
                return;
  
        if(time < self.spawnshieldtime && deathtype != DEATH_KILL)
                return;
  
+       if(deathtype == DEATH_FALL && self.draggedby != world)
+               return;
        vector v;
        float take, save;
  
        }
  }
  
- void monster_setupcolors()
+ void monster_setupcolors(entity mon)
  {
-       if(IS_PLAYER(self.monster_owner))
-               self.colormap = self.monster_owner.colormap;
-       else if(teamplay && self.team)
-               self.colormap = 1024 + (self.team - 1) * 17;
+       if(IS_PLAYER(mon.monster_owner))
+               mon.colormap = mon.monster_owner.colormap;
+       else if(teamplay && mon.team)
+               mon.colormap = 1024 + (mon.team - 1) * 17;
        else
        {
-               if(self.monster_skill <= MONSTER_SKILL_EASY)
-                       self.colormap = 1029;
-               else if(self.monster_skill <= MONSTER_SKILL_MEDIUM)
-                       self.colormap = 1027;
-               else if(self.monster_skill <= MONSTER_SKILL_HARD)
-                       self.colormap = 1038;
-               else if(self.monster_skill <= MONSTER_SKILL_INSANE)
-                       self.colormap = 1028;
-               else if(self.monster_skill <= MONSTER_SKILL_NIGHTMARE)
-                       self.colormap = 1032;
+               if(mon.monster_skill <= MONSTER_SKILL_EASY)
+                       mon.colormap = 1029;
+               else if(mon.monster_skill <= MONSTER_SKILL_MEDIUM)
+                       mon.colormap = 1027;
+               else if(mon.monster_skill <= MONSTER_SKILL_HARD)
+                       mon.colormap = 1038;
+               else if(mon.monster_skill <= MONSTER_SKILL_INSANE)
+                       mon.colormap = 1028;
+               else if(mon.monster_skill <= MONSTER_SKILL_NIGHTMARE)
+                       mon.colormap = 1032;
                else
-                       self.colormap = 1024;
+                       mon.colormap = 1024;
+       }
+ }
+ void monster_changeteam(entity ent, float newteam)
+ {
+       if(!teamplay) { return; }
+       
+       ent.team = newteam;
+       ent.monster_attack = TRUE; // new team, activate attacking
+       monster_setupcolors(ent);
+       
+       if(ent.sprite)
+       {
+               WaypointSprite_UpdateTeamRadar(ent.sprite, RADARICON_DANGER, ((newteam) ? Team_ColorRGB(newteam) : '1 0 0'));
+               ent.sprite.team = newteam;
+               ent.sprite.SendFlags |= 1;
        }
  }
  
@@@ -930,8 -1013,8 +1013,8 @@@ void monster_think(
        self.think = monster_think;
        self.nextthink = self.ticrate;
  
-       if(self.ltime)
-       if(time >= self.ltime)
+       if(self.monster_lifetime)
+       if(time >= self.monster_lifetime)
        {
                Damage(self, self, self, self.health + self.max_health, DEATH_KILL, self.origin, self.origin);
                return;
@@@ -965,6 -1048,9 +1048,9 @@@ float monster_spawn(
        if(!self.attack_range)
                self.attack_range = autocvar_g_monsters_attack_range;
  
+       if(!self.wander_delay) { self.wander_delay = 2; }
+       if(!self.wander_distance) { self.wander_distance = 600; }
        precache_monstersounds();
        UpdateMonsterSounds();
  
        MonsterSound(monstersound_spawn, 0, FALSE, CH_VOICE);
  
        WaypointSprite_Spawn(M_NAME(self.monsterid), 0, 1024, self, '0 0 1' * (self.maxs_z + 15), world, self.team, self, sprite, TRUE, RADARICON_DANGER, ((self.team) ? Team_ColorRGB(self.team) : '1 0 0'));
-       WaypointSprite_UpdateMaxHealth(self.sprite, self.max_health);
-       WaypointSprite_UpdateHealth(self.sprite, self.health);
+       if(!(self.spawnflags & MONSTERFLAG_INVINCIBLE))
+       {
+               WaypointSprite_UpdateMaxHealth(self.sprite, self.max_health);
+               WaypointSprite_UpdateHealth(self.sprite, self.health);
+       }
  
        self.think = monster_think;
        self.nextthink = time + self.ticrate;
        return TRUE;
  }
  
- float monster_initialize(float mon_id, float nodrop)
+ float monster_initialize(float mon_id)
  {
-       if(!autocvar_g_monsters)
-               return FALSE;
+       if(!autocvar_g_monsters) { return FALSE; }
+       if(!(self.spawnflags & MONSTERFLAG_RESPAWNED)) { MON_ACTION(mon_id, MR_PRECACHE); }
+       if(Monster_CheckAppearFlags(self, mon_id)) { return TRUE; } // return true so the monster isn't removed
  
        entity mon = get_monsterinfo(mon_id);
  
                self.team = 0;
  
        if(!(self.spawnflags & MONSTERFLAG_SPAWNED)) // naturally spawned monster
-       if(!(self.spawnflags & MONSTERFLAG_RESPAWNED))
+       if(!(self.spawnflags & MONSTERFLAG_RESPAWNED)) // don't count re-spawning monsters either
                monsters_total += 1;
  
        setmodel(self, mon.model);
-       setsize(self, mon.mins, mon.maxs);
+       //setsize(self, mon.mins, mon.maxs);
        self.flags                              = FL_MONSTER;
        self.takedamage                 = DAMAGE_AIM;
        self.bot_attack                 = TRUE;
        self.candrop                    = TRUE;
        self.view_ofs                   = '0 0 1' * (self.maxs_z * 0.5);
        self.oldtarget2                 = self.target2;
+       self.pass_distance              = 0;
        self.deadflag                   = DEAD_NO;
-       self.scale                              = 1;
-       self.noalign                    = nodrop;
+       self.noalign                    = ((mon.spawnflags & MONSTER_TYPE_FLY) || (mon.spawnflags & MONSTER_TYPE_SWIM));
        self.spawn_time                 = time;
        self.spider_slowness    = 0;
        self.gravity                    = 1;
        self.dphitcontentsmask  = DPCONTENTS_SOLID | DPCONTENTS_BODY | DPCONTENTS_BOTCLIP | DPCONTENTS_MONSTERCLIP;
  
+       if(!self.scale)
+               self.scale = 1;
+       if(autocvar_g_monsters_edit)
+               self.grab = 1; // owner may carry their monster
        if(autocvar_g_fullbrightplayers)
                self.effects |= EF_FULLBRIGHT;
  
        }
  
        if(mon.spawnflags & MONSTER_SIZE_BROKEN)
-               self.scale = 1.3;
+       if(!(self.spawnflags & MONSTERFLAG_RESPAWNED))
+               self.scale *= 1.3;
+               
+       setsize(self, mon.mins * self.scale, mon.maxs * self.scale);
  
        if(!self.ticrate)
                self.ticrate = autocvar_g_monsters_think_delay;
                return FALSE;
  
        if(!(self.spawnflags & MONSTERFLAG_RESPAWNED))
-               monster_setupcolors();
+               monster_setupcolors(self);
  
        CSQCMODEL_AUTOINIT();
  
index 6df3fe9d6235e9640410dcdfa5f19fde83b2cddf,117965f7bb016aacb21fbb0ce5733197db86e231..c0d06abccaa6b1d82fd9f987f4378e8e271a0ecc
@@@ -482,18 -482,13 +482,18 @@@ void Send_Notification_WOCOVA
        MSG_INFO_NOTIF(1, INFO_WATERMARK,                      1, 0, "s1", "",                          "",                     _("^F3SVQC Build information: ^F4%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_ACCORDEON_MURDER,              3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weapontuba",             _("^BG%s%s^K1 died of ^BG%s^K1's great playing on the @!#%%'n Accordeon%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_ACCORDEON_SUICIDE,             2, 1, "s1 s2loc spree_lost", "s1",                 "weapontuba",             _("^BG%s^K1 hurt their own ears with the @!#%%'n Accordeon%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_BLASTER_MURDER,                3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponlaser",            _("^BG%s%s^K1 was shot to death by ^BG%s^K1's Blaster%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_BLASTER_SUICIDE,               2, 1, "s1 s2loc spree_lost", "s1",                 "weaponlaser",            _("^BG%s^K1 shot themself to hell with their Blaster%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_CRYLINK_MURDER,                3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponcrylink",          _("^BG%s%s^K1 felt the strong pull of ^BG%s^K1's Crylink%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_CRYLINK_SUICIDE,               2, 1, "s1 s2loc spree_lost", "s1",                 "weaponcrylink",          _("^BG%s^K1 felt the strong pull of their Crylink%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_DEVASTATOR_MURDER_DIRECT,      3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponrocketlauncher",   _("^BG%s%s^K1 ate ^BG%s^K1's rocket%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_DEVASTATOR_MURDER_SPLASH,      3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponrocketlauncher",   _("^BG%s%s^K1 got too close ^BG%s^K1's rocket%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_DEVASTATOR_SUICIDE,            2, 1, "s1 s2loc spree_lost", "s1",                 "weaponrocketlauncher",   _("^BG%s^K1 blew themself up with their Devastator%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_ELECTRO_MURDER_BOLT,           3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponelectro",          _("^BG%s%s^K1 was blasted by ^BG%s^K1's Electro bolt%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_ELECTRO_MURDER_COMBO,          3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponelectro",          _("^BG%s%s^K1 felt the electrifying air of ^BG%s^K1's Electro combo%s%s"), "") \
 -      MSG_INFO_NOTIF(1, INFO_WEAPON_ELECTRO_MURDER_ORBS,           3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponelectro",          _("^BG%s%s^K1 got too close to ^BG%s^K1's Electro plasma%s%s"), "") \
 -      MSG_INFO_NOTIF(1, INFO_WEAPON_ELECTRO_SUICIDE_BOLT,          2, 1, "s1 s2loc spree_lost", "s1",                 "weaponelectro",          _("^BG%s^K1 played with Electro plasma%s%s"), "") \
 -      MSG_INFO_NOTIF(1, INFO_WEAPON_ELECTRO_SUICIDE_ORBS,          2, 1, "s1 s2loc spree_lost", "s1",                 "weaponelectro",          _("^BG%s^K1 could not remember where they put their Electro plasma%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_ELECTRO_MURDER_ORBS,           3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponelectro",          _("^BG%s%s^K1 got too close to ^BG%s^K1's Electro orb%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_ELECTRO_SUICIDE_BOLT,          2, 1, "s1 s2loc spree_lost", "s1",                 "weaponelectro",          _("^BG%s^K1 played with Electro bolts%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_ELECTRO_SUICIDE_ORBS,          2, 1, "s1 s2loc spree_lost", "s1",                 "weaponelectro",          _("^BG%s^K1 could not remember where they put their Electro orb%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_FIREBALL_MURDER_BLAST,         3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponfireball",         _("^BG%s%s^K1 got too close to ^BG%s^K1's fireball%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_FIREBALL_MURDER_FIREMINE,      3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponfireball",         _("^BG%s%s^K1 got burnt by ^BG%s^K1's firemine%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_FIREBALL_SUICIDE_BLAST,        2, 1, "s1 s2loc spree_lost", "s1",                 "weaponfireball",         _("^BG%s^K1 should have used a smaller gun%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_HOOK_MURDER,                   3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponhook",             _("^BG%s%s^K1 was caught in ^BG%s^K1's Hook gravity bomb%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_KLEINBOTTLE_MURDER,            3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weapontuba",             _("^BG%s%s^K1 died of ^BG%s^K1's great playing on the @!#%%'n Klein Bottle%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_KLEINBOTTLE_SUICIDE,           2, 1, "s1 s2loc spree_lost", "s1",                 "weapontuba",             _("^BG%s^K1 hurt their own ears with the @!#%%'n Klein Bottle%s%s"), "") \
 -      MSG_INFO_NOTIF(1, INFO_WEAPON_LASER_MURDER,                  3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponlaser",            _("^BG%s%s^K1 was shot to death by ^BG%s^K1's Laser%s%s"), "") \
 -      MSG_INFO_NOTIF(1, INFO_WEAPON_LASER_SUICIDE,                 2, 1, "s1 s2loc spree_lost", "s1",                 "weaponlaser",            _("^BG%s^K1 shot themself to hell with their Laser%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_MACHINEGUN_MURDER_SNIPE,       3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponuzi",              _("^BG%s%s^K1 was sniped by ^BG%s^K1's Machine Gun%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_MACHINEGUN_MURDER_SPRAY,       3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponuzi",              _("^BG%s%s^K1 was riddled full of holes by ^BG%s^K1's Machine Gun%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_MINELAYER_MURDER,              3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponminelayer",        _("^BG%s%s^K1 got too close to ^BG%s^K1's mine%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_MINELAYER_SUICIDE,             2, 1, "s1 s2loc spree_lost", "s1",                 "weaponminelayer",        _("^BG%s^K1 forgot about their mine%s%s"), "") \
 -      MSG_INFO_NOTIF(1, INFO_WEAPON_MINSTANEX_MURDER,              3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponminstanex",        _("^BG%s%s^K1 has been vaporized by ^BG%s^K1's Minstanex%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_MORTAR_MURDER_BOUNCE,          3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weapongrenadelauncher",  _("^BG%s%s^K1 got too close to ^BG%s^K1's Mortar grenade%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_MORTAR_MURDER_EXPLODE,         3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weapongrenadelauncher",  _("^BG%s%s^K1 ate ^BG%s^K1's Mortar grenade%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_MORTAR_SUICIDE_BOUNCE,         2, 1, "s1 s2loc spree_lost", "s1",                 "weapongrenadelauncher",  _("^BG%s^K1 didn't see their own Mortar grenade%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_MORTAR_SUICIDE_EXPLODE,        2, 1, "s1 s2loc spree_lost", "s1",                 "weapongrenadelauncher",  _("^BG%s^K1 blew themself up with their own Mortar%s%s"), "") \
 -      MSG_INFO_NOTIF(1, INFO_WEAPON_NEX_MURDER,                    3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponnex",              _("^BG%s%s^K1 has been vaporized by ^BG%s^K1's Nex%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_RIFLE_MURDER,                  3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponrifle",            _("^BG%s%s^K1 was sniped with a Rifle by ^BG%s^K1%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_RIFLE_MURDER_HAIL,             3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponrifle",            _("^BG%s%s^K1 died in ^BG%s^K1's Rifle bullet hail%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_RIFLE_MURDER_HAIL_PIERCING,    3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponrifle",            _("^BG%s%s^K1 failed to hide from ^BG%s^K1's Rifle bullet hail%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_RIFLE_MURDER_PIERCING,         3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponrifle",            _("^BG%s%s^K1 failed to hide from ^BG%s^K1's Rifle%s%s"), "") \
 -      MSG_INFO_NOTIF(1, INFO_WEAPON_ROCKETLAUNCHER_MURDER_DIRECT,  3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponrocketlauncher",   _("^BG%s%s^K1 ate ^BG%s^K1's rocket%s%s"), "") \
 -      MSG_INFO_NOTIF(1, INFO_WEAPON_ROCKETLAUNCHER_MURDER_SPLASH,  3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponrocketlauncher",   _("^BG%s%s^K1 got too close ^BG%s^K1's rocket%s%s"), "") \
 -      MSG_INFO_NOTIF(1, INFO_WEAPON_ROCKETLAUNCHER_SUICIDE,        2, 1, "s1 s2loc spree_lost", "s1",                 "weaponrocketlauncher",   _("^BG%s^K1 blew themself up with their Rocketlauncher%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_SEEKER_MURDER_SPRAY,           3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponseeker",           _("^BG%s%s^K1 was pummeled by ^BG%s^K1's Seeker rockets%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_SEEKER_MURDER_TAG,             3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponseeker",           _("^BG%s%s^K1 was tagged by ^BG%s^K1's Seeker%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_SEEKER_SUICIDE,                2, 1, "s1 s2loc spree_lost", "s1",                 "weaponseeker",           _("^BG%s^K1 played with tiny Seeker rockets%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_SHOCKWAVE_MURDER,              3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponshotgun",          _("^BG%s%s^K1 was gunned down by ^BG%s^K1's Shockwave%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_SHOCKWAVE_MURDER_SLAP,         3, 2, "spree_inf s2 s1 s3loc spree_end", "s2 s1",  "notify_melee_shotgun",   _("^BG%s%s^K1 slapped ^BG%s^K1 around a bit with a large Shockwave%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_SHOTGUN_MURDER,                3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponshotgun",          _("^BG%s%s^K1 was gunned down by ^BG%s^K1's Shotgun%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_SHOTGUN_MURDER_SLAP,           3, 2, "spree_inf s2 s1 s3loc spree_end", "s2 s1",  "notify_melee_shotgun",   _("^BG%s%s^K1 slapped ^BG%s^K1 around a bit with a large Shotgun%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_THINKING_WITH_PORTALS,         2, 1, "s1 s2loc spree_lost", "s1",                 "notify_selfkill",        _("^BG%s^K1 is now thinking with portals%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_TUBA_MURDER,                   3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weapontuba",             _("^BG%s%s^K1 died of ^BG%s^K1's great playing on the @!#%%'n Tuba%s%s"), "") \
        MSG_INFO_NOTIF(1, INFO_WEAPON_TUBA_SUICIDE,                  2, 1, "s1 s2loc spree_lost", "s1",                 "weapontuba",             _("^BG%s^K1 hurt their own ears with the @!#%%'n Tuba%s%s"), "") \
 -      MSG_INFO_NOTIF(1, INFO_WEAPON_UZI_MURDER_SNIPE,              3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponuzi",              _("^BG%s%s^K1 was sniped by ^BG%s^K1's Machine Gun%s%s"), "") \
 -      MSG_INFO_NOTIF(1, INFO_WEAPON_UZI_MURDER_SPRAY,              3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponuzi",              _("^BG%s%s^K1 was riddled full of holes by ^BG%s^K1's Machine Gun%s%s"), "")
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_VAPORIZER_MURDER,              3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponminstanex",        _("^BG%s%s^K1 has been sublimated by ^BG%s^K1's Vaporizer%s%s"), "") \
 +      MSG_INFO_NOTIF(1, INFO_WEAPON_VORTEX_MURDER,                 3, 2, "spree_inf s1 s2 s3loc spree_end", "s2 s1",  "weaponnex",              _("^BG%s%s^K1 has been vaporized by ^BG%s^K1's Vortex%s%s"), "")
  
  #define MULTITEAM_CENTER2(default,prefix,strnum,flnum,args,cpid,durcnt,normal,gentle) \
        MSG_CENTER_NOTIF(default, prefix##RED, strnum, flnum, args, cpid, durcnt, TCR(normal, COL_TEAM_1, strtoupper(NAME_TEAM_1)), TCR(gentle, COL_TEAM_1, strtoupper(NAME_TEAM_1))) \
        MSG_CENTER_NOTIF(1, CENTER_JOIN_PREVENT,                0, 0, "",              CPID_PREVENT_JOIN,     "0 0", _("^K1You may not join the game at this time.\nThe player limit reached maximum capacity."), "") \
        MSG_CENTER_NOTIF(1, CENTER_KEEPAWAY_DROPPED,            1, 0, "s1",            CPID_KEEPAWAY,         "0 0", _("^BG%s^BG has dropped the ball!"), "") \
        MSG_CENTER_NOTIF(1, CENTER_KEEPAWAY_PICKUP,             1, 0, "s1",            CPID_KEEPAWAY,         "0 0", _("^BG%s^BG has picked up the ball!"), "") \
+       MSG_CENTER_NOTIF(1, CENTER_KEEPAWAY_PICKUP_SELF,        0, 0, "",              CPID_KEEPAWAY,         "0 0", _("^BGYou picked up the ball"), "") \
        MSG_CENTER_NOTIF(1, CENTER_KEEPAWAY_WARN,               0, 0, "",              CPID_KEEPAWAY_WARN,    "0 0", _("^BGKilling people while you don't have the ball gives no points!"), "") \
        MSG_CENTER_NOTIF(1, CENTER_KEYHUNT_HELP,                0, 0, "",              CPID_KEYHUNT,          "0 0", _("^BGAll keys are in your team's hands!\nHelp the key carriers to meet!"), "") \
        MULTITEAM_CENTER(1, CENTER_KEYHUNT_INTERFERE_, 4,       0, 0, "",              CPID_KEYHUNT,          "0 0", _("^BGAll keys are in ^TC^TT team^BG's hands!\nInterfere ^F4NOW^BG!"), "") \
        MSG_MULTI_NOTIF(1, MULTI_MINSTA_FINDAMMO,                ANNCE_NUM_10,  NO_MSG,                                    CENTER_MINSTA_FINDAMMO_FIRST) \
        MSG_MULTI_NOTIF(1, WEAPON_ACCORDEON_MURDER,              NO_MSG,        INFO_WEAPON_ACCORDEON_MURDER,              NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_ACCORDEON_SUICIDE,             NO_MSG,        INFO_WEAPON_ACCORDEON_SUICIDE,             CENTER_DEATH_SELF_GENERIC) \
 +      MSG_MULTI_NOTIF(1, WEAPON_BLASTER_MURDER,                NO_MSG,        INFO_WEAPON_BLASTER_MURDER,                NO_MSG) \
 +      MSG_MULTI_NOTIF(1, WEAPON_BLASTER_SUICIDE,               NO_MSG,        INFO_WEAPON_BLASTER_SUICIDE,               CENTER_DEATH_SELF_GENERIC) \
        MSG_MULTI_NOTIF(1, WEAPON_CRYLINK_MURDER,                NO_MSG,        INFO_WEAPON_CRYLINK_MURDER,                NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_CRYLINK_SUICIDE,               NO_MSG,        INFO_WEAPON_CRYLINK_SUICIDE,               CENTER_DEATH_SELF_GENERIC) \
 +      MSG_MULTI_NOTIF(1, WEAPON_DEVASTATOR_MURDER_DIRECT,      NO_MSG,        INFO_WEAPON_DEVASTATOR_MURDER_DIRECT,      NO_MSG) \
 +      MSG_MULTI_NOTIF(1, WEAPON_DEVASTATOR_MURDER_SPLASH,      NO_MSG,        INFO_WEAPON_DEVASTATOR_MURDER_SPLASH,      NO_MSG) \
 +      MSG_MULTI_NOTIF(1, WEAPON_DEVASTATOR_SUICIDE,            NO_MSG,        INFO_WEAPON_DEVASTATOR_SUICIDE,            CENTER_DEATH_SELF_GENERIC) \
        MSG_MULTI_NOTIF(1, WEAPON_ELECTRO_MURDER_BOLT,           NO_MSG,        INFO_WEAPON_ELECTRO_MURDER_BOLT,           NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_ELECTRO_MURDER_COMBO,          NO_MSG,        INFO_WEAPON_ELECTRO_MURDER_COMBO,          NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_ELECTRO_MURDER_ORBS,           NO_MSG,        INFO_WEAPON_ELECTRO_MURDER_ORBS,           NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_HOOK_MURDER,                   NO_MSG,        INFO_WEAPON_HOOK_MURDER,                   NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_KLEINBOTTLE_MURDER,            NO_MSG,        INFO_WEAPON_KLEINBOTTLE_MURDER,            NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_KLEINBOTTLE_SUICIDE,           NO_MSG,        INFO_WEAPON_KLEINBOTTLE_SUICIDE,           CENTER_DEATH_SELF_GENERIC) \
 -      MSG_MULTI_NOTIF(1, WEAPON_LASER_MURDER,                  NO_MSG,        INFO_WEAPON_LASER_MURDER,                  NO_MSG) \
 -      MSG_MULTI_NOTIF(1, WEAPON_LASER_SUICIDE,                 NO_MSG,        INFO_WEAPON_LASER_SUICIDE,                 CENTER_DEATH_SELF_GENERIC) \
 +      MSG_MULTI_NOTIF(1, WEAPON_MACHINEGUN_MURDER_SNIPE,       NO_MSG,        INFO_WEAPON_MACHINEGUN_MURDER_SNIPE,       NO_MSG) \
 +      MSG_MULTI_NOTIF(1, WEAPON_MACHINEGUN_MURDER_SPRAY,       NO_MSG,        INFO_WEAPON_MACHINEGUN_MURDER_SPRAY,       NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_MINELAYER_MURDER,              NO_MSG,        INFO_WEAPON_MINELAYER_MURDER,              NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_MINELAYER_SUICIDE,             NO_MSG,        INFO_WEAPON_MINELAYER_SUICIDE,             CENTER_DEATH_SELF_GENERIC) \
 -      MSG_MULTI_NOTIF(1, WEAPON_MINSTANEX_MURDER,              NO_MSG,        INFO_WEAPON_MINSTANEX_MURDER,              NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_MORTAR_MURDER_BOUNCE,          NO_MSG,        INFO_WEAPON_MORTAR_MURDER_BOUNCE,          NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_MORTAR_MURDER_EXPLODE,         NO_MSG,        INFO_WEAPON_MORTAR_MURDER_EXPLODE,         NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_MORTAR_SUICIDE_BOUNCE,         NO_MSG,        INFO_WEAPON_MORTAR_SUICIDE_BOUNCE,         CENTER_DEATH_SELF_GENERIC) \
        MSG_MULTI_NOTIF(1, WEAPON_MORTAR_SUICIDE_EXPLODE,        NO_MSG,        INFO_WEAPON_MORTAR_SUICIDE_EXPLODE,        CENTER_DEATH_SELF_GENERIC) \
 -      MSG_MULTI_NOTIF(1, WEAPON_NEX_MURDER,                    NO_MSG,        INFO_WEAPON_NEX_MURDER,                    NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_RIFLE_MURDER,                  NO_MSG,        INFO_WEAPON_RIFLE_MURDER,                  NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_RIFLE_MURDER_HAIL,             NO_MSG,        INFO_WEAPON_RIFLE_MURDER_HAIL,             NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_RIFLE_MURDER_HAIL_PIERCING,    NO_MSG,        INFO_WEAPON_RIFLE_MURDER_HAIL_PIERCING,    NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_RIFLE_MURDER_PIERCING,         NO_MSG,        INFO_WEAPON_RIFLE_MURDER_PIERCING,         NO_MSG) \
 -      MSG_MULTI_NOTIF(1, WEAPON_ROCKETLAUNCHER_MURDER_DIRECT,  NO_MSG,        INFO_WEAPON_ROCKETLAUNCHER_MURDER_DIRECT,  NO_MSG) \
 -      MSG_MULTI_NOTIF(1, WEAPON_ROCKETLAUNCHER_MURDER_SPLASH,  NO_MSG,        INFO_WEAPON_ROCKETLAUNCHER_MURDER_SPLASH,  NO_MSG) \
 -      MSG_MULTI_NOTIF(1, WEAPON_ROCKETLAUNCHER_SUICIDE,        NO_MSG,        INFO_WEAPON_ROCKETLAUNCHER_SUICIDE,        CENTER_DEATH_SELF_GENERIC) \
        MSG_MULTI_NOTIF(1, WEAPON_SEEKER_MURDER_SPRAY,           NO_MSG,        INFO_WEAPON_SEEKER_MURDER_SPRAY,           NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_SEEKER_MURDER_TAG,             NO_MSG,        INFO_WEAPON_SEEKER_MURDER_TAG,             NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_SEEKER_SUICIDE,                NO_MSG,        INFO_WEAPON_SEEKER_SUICIDE,                CENTER_DEATH_SELF_GENERIC) \
 +      MSG_MULTI_NOTIF(1, WEAPON_SHOCKWAVE_MURDER,              NO_MSG,        INFO_WEAPON_SHOCKWAVE_MURDER,              NO_MSG) \
 +      MSG_MULTI_NOTIF(1, WEAPON_SHOCKWAVE_MURDER_SLAP,         NO_MSG,        INFO_WEAPON_SHOCKWAVE_MURDER_SLAP,         NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_SHOTGUN_MURDER,                NO_MSG,        INFO_WEAPON_SHOTGUN_MURDER,                NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_SHOTGUN_MURDER_SLAP,           NO_MSG,        INFO_WEAPON_SHOTGUN_MURDER_SLAP,           NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_THINKING_WITH_PORTALS,         NO_MSG,        INFO_WEAPON_THINKING_WITH_PORTALS,         CENTER_DEATH_SELF_GENERIC) \
        MSG_MULTI_NOTIF(1, WEAPON_TUBA_MURDER,                   NO_MSG,        INFO_WEAPON_TUBA_MURDER,                   NO_MSG) \
        MSG_MULTI_NOTIF(1, WEAPON_TUBA_SUICIDE,                  NO_MSG,        INFO_WEAPON_TUBA_SUICIDE,                  CENTER_DEATH_SELF_GENERIC) \
 -      MSG_MULTI_NOTIF(1, WEAPON_UZI_MURDER_SNIPE,              NO_MSG,        INFO_WEAPON_UZI_MURDER_SNIPE,              NO_MSG) \
 -      MSG_MULTI_NOTIF(1, WEAPON_UZI_MURDER_SPRAY,              NO_MSG,        INFO_WEAPON_UZI_MURDER_SPRAY,              NO_MSG)
 +      MSG_MULTI_NOTIF(1, WEAPON_VAPORIZER_MURDER,              NO_MSG,        INFO_WEAPON_VAPORIZER_MURDER,              NO_MSG) \
 +      MSG_MULTI_NOTIF(1, WEAPON_VORTEX_MURDER,                 NO_MSG,        INFO_WEAPON_VORTEX_MURDER,                 NO_MSG)
  
  #define MULTITEAM_CHOICE2(default,challow,prefix,chtype,optiona,optionb) \
        MSG_CHOICE_NOTIF(default, challow, prefix##RED, chtype, optiona##RED, optionb##RED) \
@@@ -988,7 -985,7 +989,7 @@@ string arg_slot[NOTIF_MAX_ARGS]
      ARG_CASE(ARG_CS_SV,     "spree_inf",     (autocvar_notification_show_sprees ? notif_arg_spree_inf(1, input, s2, f2) : "")) \
      ARG_CASE(ARG_CS_SV,     "spree_end",     (autocvar_notification_show_sprees ? notif_arg_spree_inf(-1, "", "", f1) : "")) \
      ARG_CASE(ARG_CS_SV,     "spree_lost",    (autocvar_notification_show_sprees ? notif_arg_spree_inf(-2, "", "", f1) : "")) \
 -    ARG_CASE(ARG_CS_SV,     "item_wepname",  W_Name(f1)) \
 +    ARG_CASE(ARG_CS_SV,     "item_wepname",  WEP_NAME(f1)) \
      ARG_CASE(ARG_CS_SV,     "item_wepammo",  (s1 != "" ? sprintf(_(" with %s"), s1) : "")) \
      ARG_CASE(ARG_DC,        "item_centime",  ftos(autocvar_notification_item_centerprinttime)) \
      ARG_CASE(ARG_SV,        "death_team",    Team_ColoredFullName(f1)) \
index 76abad81fbe715fcf514c2082e80ae1bfb95380a,74b60d30aef98a01243a99b34117b8a19e00ae37..8b78a0f0aed2ab3f014bc833985abab610f31fb8
@@@ -343,6 -343,7 +343,6 @@@ void UpdateNotification_URI_Get_Callbac
                
                switch(substring(argv(i), 0, 1))
                {
 -                      #define APPEND_TO_STRING(list,sep,add) ((list) = (((list) != "") ? strcat(list, sep, add) : (add)))
                        case "V":
                        {
                                un_version = s;
@@@ -655,7 -656,7 +655,7 @@@ float updateCompression(
        GAMETYPE(MAPINFO_TYPE_LMS) \
        GAMETYPE(MAPINFO_TYPE_NEXBALL) \
        GAMETYPE(MAPINFO_TYPE_ONSLAUGHT) \
-       GAMETYPE(MAPINFO_TYPE_RACE) \
+       if (cvar("developer")) GAMETYPE(MAPINFO_TYPE_RACE) \
        GAMETYPE(MAPINFO_TYPE_CTS) \
        GAMETYPE(MAPINFO_TYPE_TEAM_DEATHMATCH) \
        //GAMETYPE(MAPINFO_TYPE_INVASION) \
@@@ -666,7 -667,7 +666,7 @@@ float GameType_GetID(float cnt
        float i;
        i = 0;
  
-       #define GAMETYPE(id) if(i++ == cnt) return id;
+       #define GAMETYPE(id) { if(i++ == cnt) return id; }
        GAMETYPES
        #undef GAMETYPE
  
index 06d21415849c9dfbefa8950ee8886999c1f4dd8a,080d701d866c083a81858fa90e22ae048e8f5111..8387dc6037b05d1a6e167cfcd56824d688463f0b
@@@ -80,6 -80,33 +80,6 @@@ float autocvar_g_balance_armor_rot
  float autocvar_g_balance_armor_rotlinear;
  float autocvar_g_balance_armor_rotstable;
  float autocvar_g_balance_armor_start;
 -float autocvar_g_balance_rifle_bursttime;
 -float autocvar_g_balance_rifle_primary_ammo;
 -float autocvar_g_balance_rifle_primary_animtime;
 -float autocvar_g_balance_rifle_primary_bullethail;
 -float autocvar_g_balance_rifle_primary_burstcost;
 -float autocvar_g_balance_rifle_primary_damage;
 -float autocvar_g_balance_rifle_primary_force;
 -float autocvar_g_balance_rifle_primary_refire;
 -float autocvar_g_balance_rifle_primary_shots;
 -float autocvar_g_balance_rifle_primary_solidpenetration;
 -float autocvar_g_balance_rifle_primary_spread;
 -float autocvar_g_balance_rifle_primary_tracer;
 -float autocvar_g_balance_rifle_secondary;
 -float autocvar_g_balance_rifle_secondary_ammo;
 -float autocvar_g_balance_rifle_secondary_animtime;
 -float autocvar_g_balance_rifle_secondary_bullethail;
 -float autocvar_g_balance_rifle_secondary_burstcost;
 -float autocvar_g_balance_rifle_secondary_damage;
 -float autocvar_g_balance_rifle_secondary_force;
 -float autocvar_g_balance_rifle_secondary_reload;
 -float autocvar_g_balance_rifle_secondary_refire;
 -float autocvar_g_balance_rifle_secondary_shots;
 -float autocvar_g_balance_rifle_secondary_solidpenetration;
 -float autocvar_g_balance_rifle_secondary_spread;
 -float autocvar_g_balance_rifle_secondary_tracer;
 -float autocvar_g_balance_rifle_reload_ammo;
 -float autocvar_g_balance_rifle_reload_time;
  float autocvar_g_balance_cloaked_alpha;
  float autocvar_g_balance_contents_damagerate;
  float autocvar_g_balance_contents_drowndelay;
@@@ -87,11 -114,134 +87,11 @@@ float autocvar_g_balance_contents_playe
  float autocvar_g_balance_contents_playerdamage_lava;
  float autocvar_g_balance_contents_playerdamage_slime;
  float autocvar_g_balance_contents_projectiledamage;
 -float autocvar_g_balance_crylink_primary_ammo;
 -float autocvar_g_balance_crylink_primary_animtime;
 -float autocvar_g_balance_crylink_primary_bouncedamagefactor;
 -float autocvar_g_balance_crylink_primary_bounces;
 -float autocvar_g_balance_crylink_primary_damage;
 -float autocvar_g_balance_crylink_primary_edgedamage;
 -float autocvar_g_balance_crylink_primary_force;
 -float autocvar_g_balance_crylink_primary_joindelay;
 -float autocvar_g_balance_crylink_primary_joinexplode;
 -float autocvar_g_balance_crylink_primary_joinexplode_damage;
 -float autocvar_g_balance_crylink_primary_joinexplode_edgedamage;
 -float autocvar_g_balance_crylink_primary_joinexplode_force;
 -float autocvar_g_balance_crylink_primary_joinexplode_radius;
 -float autocvar_g_balance_crylink_primary_joinspread;
 -float autocvar_g_balance_crylink_primary_linkexplode;
 -float autocvar_g_balance_crylink_primary_middle_fadetime;
 -float autocvar_g_balance_crylink_primary_middle_lifetime;
 -float autocvar_g_balance_crylink_primary_other_fadetime;
 -float autocvar_g_balance_crylink_primary_other_lifetime;
 -float autocvar_g_balance_crylink_primary_radius;
 -float autocvar_g_balance_crylink_primary_refire;
 -float autocvar_g_balance_crylink_primary_shots;
 -float autocvar_g_balance_crylink_primary_speed;
 -float autocvar_g_balance_crylink_primary_spread;
 -float autocvar_g_balance_crylink_secondary;
 -float autocvar_g_balance_crylink_secondary_ammo;
 -float autocvar_g_balance_crylink_secondary_animtime;
 -float autocvar_g_balance_crylink_secondary_bouncedamagefactor;
 -float autocvar_g_balance_crylink_secondary_bounces;
 -float autocvar_g_balance_crylink_secondary_damage;
 -float autocvar_g_balance_crylink_secondary_edgedamage;
 -float autocvar_g_balance_crylink_secondary_force;
 -float autocvar_g_balance_crylink_secondary_joindelay;
 -float autocvar_g_balance_crylink_secondary_joinexplode;
 -float autocvar_g_balance_crylink_secondary_joinexplode_damage;
 -float autocvar_g_balance_crylink_secondary_joinexplode_edgedamage;
 -float autocvar_g_balance_crylink_secondary_joinexplode_force;
 -float autocvar_g_balance_crylink_secondary_joinexplode_radius;
 -float autocvar_g_balance_crylink_secondary_joinspread;
 -float autocvar_g_balance_crylink_secondary_line_fadetime;
 -float autocvar_g_balance_crylink_secondary_line_lifetime;
 -float autocvar_g_balance_crylink_secondary_linkexplode;
 -float autocvar_g_balance_crylink_secondary_middle_fadetime;
 -float autocvar_g_balance_crylink_secondary_middle_lifetime;
 -float autocvar_g_balance_crylink_secondary_radius;
 -float autocvar_g_balance_crylink_secondary_refire;
 -float autocvar_g_balance_crylink_secondary_shots;
 -float autocvar_g_balance_crylink_secondary_speed;
 -float autocvar_g_balance_crylink_secondary_spread;
 -float autocvar_g_balance_crylink_secondary_spreadtype;
 -float autocvar_g_balance_crylink_reload_ammo;
 -float autocvar_g_balance_crylink_reload_time;
  float autocvar_g_balance_damagepush_speedfactor;
 -float autocvar_g_balance_electro_combo_comboradius;
 -float autocvar_g_balance_electro_combo_damage;
 -float autocvar_g_balance_electro_combo_edgedamage;
 -float autocvar_g_balance_electro_combo_force;
 -float autocvar_g_balance_electro_combo_radius;
 -float autocvar_g_balance_electro_combo_speed;
 -float autocvar_g_balance_electro_combo_safeammocheck;
 -float autocvar_g_balance_electro_lightning;
 -float autocvar_g_balance_electro_primary_ammo;
 -float autocvar_g_balance_electro_primary_animtime;
 -float autocvar_g_balance_electro_primary_comboradius;
 -float autocvar_g_balance_electro_primary_damage;
 -float autocvar_g_balance_electro_primary_edgedamage;
 -float autocvar_g_balance_electro_primary_falloff_halflifedist;
 -float autocvar_g_balance_electro_primary_falloff_maxdist;
 -float autocvar_g_balance_electro_primary_falloff_mindist;
 -float autocvar_g_balance_electro_primary_force;
 -float autocvar_g_balance_electro_primary_force_up;
 -float autocvar_g_balance_electro_primary_lifetime;
 -float autocvar_g_balance_electro_primary_radius;
 -float autocvar_g_balance_electro_primary_range;
 -float autocvar_g_balance_electro_primary_refire;
 -float autocvar_g_balance_electro_primary_speed;
 -float autocvar_g_balance_electro_secondary_ammo;
 -float autocvar_g_balance_electro_secondary_animtime;
 -float autocvar_g_balance_electro_secondary_bouncefactor;
 -float autocvar_g_balance_electro_secondary_bouncestop;
 -float autocvar_g_balance_electro_secondary_count;
 -float autocvar_g_balance_electro_secondary_damage;
 -float autocvar_g_balance_electro_secondary_damageforcescale;
 -float autocvar_g_balance_electro_secondary_damagedbycontents;
 -float autocvar_g_balance_electro_secondary_edgedamage;
 -float autocvar_g_balance_electro_secondary_force;
 -float autocvar_g_balance_electro_secondary_health;
 -float autocvar_g_balance_electro_secondary_lifetime;
 -float autocvar_g_balance_electro_secondary_radius;
 -float autocvar_g_balance_electro_secondary_refire;
 -float autocvar_g_balance_electro_secondary_refire2;
 -float autocvar_g_balance_electro_secondary_speed;
 -float autocvar_g_balance_electro_reload_ammo;
 -float autocvar_g_balance_electro_reload_time;
  float autocvar_g_balance_falldamage_deadminspeed;
  float autocvar_g_balance_falldamage_factor;
  float autocvar_g_balance_falldamage_maxdamage;
  float autocvar_g_balance_falldamage_minspeed;
 -float autocvar_g_balance_fireball_primary_animtime;
 -float autocvar_g_balance_fireball_primary_bfgdamage;
 -float autocvar_g_balance_fireball_primary_bfgforce;
 -float autocvar_g_balance_fireball_primary_bfgradius;
 -float autocvar_g_balance_fireball_primary_damage;
 -float autocvar_g_balance_fireball_primary_damageforcescale;
 -float autocvar_g_balance_fireball_primary_edgedamage;
 -float autocvar_g_balance_fireball_primary_force;
 -float autocvar_g_balance_fireball_primary_health;
 -float autocvar_g_balance_fireball_primary_laserburntime;
 -float autocvar_g_balance_fireball_primary_laserdamage;
 -float autocvar_g_balance_fireball_primary_laseredgedamage;
 -float autocvar_g_balance_fireball_primary_laserradius;
 -float autocvar_g_balance_fireball_primary_lifetime;
 -float autocvar_g_balance_fireball_primary_radius;
 -float autocvar_g_balance_fireball_primary_refire;
 -float autocvar_g_balance_fireball_primary_refire2;
 -float autocvar_g_balance_fireball_primary_speed;
 -float autocvar_g_balance_fireball_secondary_animtime;
 -float autocvar_g_balance_fireball_secondary_damage;
 -float autocvar_g_balance_fireball_secondary_damageforcescale;
 -float autocvar_g_balance_fireball_secondary_damagetime;
 -float autocvar_g_balance_fireball_secondary_laserburntime;
 -float autocvar_g_balance_fireball_secondary_laserdamage;
 -float autocvar_g_balance_fireball_secondary_laseredgedamage;
 -float autocvar_g_balance_fireball_secondary_laserradius;
 -float autocvar_g_balance_fireball_secondary_lifetime;
 -float autocvar_g_balance_fireball_secondary_refire;
 -float autocvar_g_balance_fireball_secondary_speed;
 -float autocvar_g_balance_fireball_secondary_speed_up;
  float autocvar_g_balance_firetransfer_damage;
  float autocvar_g_balance_firetransfer_time;
  float autocvar_g_balance_fuel_limit;
@@@ -110,6 -260,76 +110,7 @@@ float autocvar_g_balance_grapplehook_sp
  float autocvar_g_balance_grapplehook_speed_pull;
  float autocvar_g_balance_grapplehook_stretch;
  float autocvar_g_balance_grapplehook_damagedbycontents;
 -float autocvar_g_balance_grenadelauncher_bouncefactor;
 -float autocvar_g_balance_grenadelauncher_bouncestop;
 -float autocvar_g_balance_grenadelauncher_primary_ammo;
 -float autocvar_g_balance_grenadelauncher_primary_animtime;
 -float autocvar_g_balance_grenadelauncher_primary_damage;
 -float autocvar_g_balance_grenadelauncher_primary_damageforcescale;
 -float autocvar_g_balance_grenadelauncher_primary_edgedamage;
 -float autocvar_g_balance_grenadelauncher_primary_force;
 -float autocvar_g_balance_grenadelauncher_primary_health;
 -float autocvar_g_balance_grenadelauncher_primary_lifetime;
 -float autocvar_g_balance_grenadelauncher_primary_lifetime_stick;
 -float autocvar_g_balance_grenadelauncher_primary_radius;
 -float autocvar_g_balance_grenadelauncher_primary_refire;
 -float autocvar_g_balance_grenadelauncher_primary_remote_minbouncecnt;
 -float autocvar_g_balance_grenadelauncher_primary_speed;
 -float autocvar_g_balance_grenadelauncher_primary_speed_up;
 -float autocvar_g_balance_grenadelauncher_primary_type;
 -float autocvar_g_balance_grenadelauncher_secondary_ammo;
 -float autocvar_g_balance_grenadelauncher_secondary_animtime;
 -float autocvar_g_balance_grenadelauncher_secondary_damage;
 -float autocvar_g_balance_grenadelauncher_secondary_damageforcescale;
 -float autocvar_g_balance_grenadelauncher_secondary_edgedamage;
 -float autocvar_g_balance_grenadelauncher_secondary_force;
 -float autocvar_g_balance_grenadelauncher_secondary_health;
 -float autocvar_g_balance_grenadelauncher_secondary_lifetime;
 -float autocvar_g_balance_grenadelauncher_secondary_lifetime_bounce;
 -float autocvar_g_balance_grenadelauncher_secondary_lifetime_stick;
 -float autocvar_g_balance_grenadelauncher_secondary_radius;
 -float autocvar_g_balance_grenadelauncher_secondary_refire;
 -float autocvar_g_balance_grenadelauncher_secondary_speed;
 -float autocvar_g_balance_grenadelauncher_secondary_speed_up;
 -float autocvar_g_balance_grenadelauncher_secondary_type;
 -float autocvar_g_balance_grenadelauncher_reload_ammo;
 -float autocvar_g_balance_grenadelauncher_reload_time;
 -float autocvar_g_balance_hagar_primary_ammo;
 -float autocvar_g_balance_hagar_primary_damage;
 -float autocvar_g_balance_hagar_primary_edgedamage;
 -float autocvar_g_balance_hagar_primary_force;
 -float autocvar_g_balance_hagar_primary_health;
 -float autocvar_g_balance_hagar_primary_damageforcescale;
 -float autocvar_g_balance_hagar_primary_lifetime;
 -float autocvar_g_balance_hagar_primary_radius;
 -float autocvar_g_balance_hagar_primary_refire;
 -float autocvar_g_balance_hagar_primary_speed;
 -float autocvar_g_balance_hagar_secondary;
 -float autocvar_g_balance_hagar_secondary_load;
 -float autocvar_g_balance_hagar_secondary_load_speed;
 -float autocvar_g_balance_hagar_secondary_load_spread;
 -float autocvar_g_balance_hagar_secondary_load_spread_bias;
 -float autocvar_g_balance_hagar_secondary_load_max;
 -float autocvar_g_balance_hagar_secondary_load_hold;
 -float autocvar_g_balance_hagar_secondary_load_releasedeath;
 -float autocvar_g_balance_hagar_secondary_load_abort;
 -float autocvar_g_balance_hagar_secondary_load_linkexplode;
 -float autocvar_g_balance_hagar_secondary_load_animtime;
 -float autocvar_g_balance_hagar_secondary_ammo;
 -float autocvar_g_balance_hagar_secondary_damage;
 -float autocvar_g_balance_hagar_secondary_edgedamage;
 -float autocvar_g_balance_hagar_secondary_force;
 -float autocvar_g_balance_hagar_secondary_health;
 -float autocvar_g_balance_hagar_secondary_damageforcescale;
 -float autocvar_g_balance_hagar_secondary_lifetime_min;
 -float autocvar_g_balance_hagar_secondary_lifetime_rand;
 -float autocvar_g_balance_hagar_secondary_radius;
 -float autocvar_g_balance_hagar_secondary_refire;
 -float autocvar_g_balance_hagar_secondary_speed;
 -float autocvar_g_balance_hagar_secondary_spread;
 -float autocvar_g_balance_hagar_reload_ammo;
 -float autocvar_g_balance_hagar_reload_time;
+ float autocvar_g_balance_grapplehook_refire;
  float autocvar_g_balance_health_limit;
  float autocvar_g_balance_health_regen;
  float autocvar_g_balance_health_regenlinear;
@@@ -117,6 -337,54 +118,6 @@@ float autocvar_g_balance_health_regenst
  float autocvar_g_balance_health_rot;
  float autocvar_g_balance_health_rotlinear;
  float autocvar_g_balance_health_rotstable;
 -float autocvar_g_balance_hlac_primary_ammo;
 -float autocvar_g_balance_hlac_primary_animtime;
 -float autocvar_g_balance_hlac_primary_damage;
 -float autocvar_g_balance_hlac_primary_edgedamage;
 -float autocvar_g_balance_hlac_primary_force;
 -float autocvar_g_balance_hlac_primary_lifetime;
 -float autocvar_g_balance_hlac_primary_radius;
 -float autocvar_g_balance_hlac_primary_refire;
 -float autocvar_g_balance_hlac_primary_speed;
 -float autocvar_g_balance_hlac_primary_spread_add;
 -float autocvar_g_balance_hlac_primary_spread_crouchmod;
 -float autocvar_g_balance_hlac_primary_spread_max;
 -float autocvar_g_balance_hlac_primary_spread_min;
 -float autocvar_g_balance_hlac_secondary;
 -float autocvar_g_balance_hlac_secondary_ammo;
 -float autocvar_g_balance_hlac_secondary_animtime;
 -float autocvar_g_balance_hlac_secondary_damage;
 -float autocvar_g_balance_hlac_secondary_edgedamage;
 -float autocvar_g_balance_hlac_secondary_force;
 -float autocvar_g_balance_hlac_secondary_lifetime;
 -float autocvar_g_balance_hlac_secondary_radius;
 -float autocvar_g_balance_hlac_secondary_refire;
 -float autocvar_g_balance_hlac_secondary_shots;
 -float autocvar_g_balance_hlac_secondary_speed;
 -float autocvar_g_balance_hlac_secondary_spread;
 -float autocvar_g_balance_hlac_secondary_spread_crouchmod;
 -float autocvar_g_balance_hlac_reload_ammo;
 -float autocvar_g_balance_hlac_reload_time;
 -float autocvar_g_balance_hook_primary_animtime;
 -float autocvar_g_balance_hook_primary_fuel;
 -float autocvar_g_balance_hook_primary_hooked_fuel;
 -float autocvar_g_balance_hook_primary_hooked_time_free;
 -float autocvar_g_balance_hook_primary_hooked_time_max;
 -float autocvar_g_balance_hook_primary_refire;
 -float autocvar_g_balance_hook_secondary_ammo;
 -float autocvar_g_balance_hook_secondary_animtime;
 -float autocvar_g_balance_hook_secondary_damage;
 -float autocvar_g_balance_hook_secondary_duration;
 -float autocvar_g_balance_hook_secondary_edgedamage;
 -float autocvar_g_balance_hook_secondary_force;
 -float autocvar_g_balance_hook_secondary_gravity;
 -float autocvar_g_balance_hook_secondary_lifetime;
 -float autocvar_g_balance_hook_secondary_power;
 -float autocvar_g_balance_hook_secondary_radius;
 -float autocvar_g_balance_hook_secondary_refire;
 -float autocvar_g_balance_hook_secondary_speed;
 -float autocvar_g_balance_hook_secondary_health;
 -float autocvar_g_balance_hook_secondary_damageforcescale;
  float autocvar_g_balance_keyhunt_damageforcescale;
  float autocvar_g_balance_keyhunt_delay_collect;
  float autocvar_g_balance_keyhunt_delay_return;
@@@ -134,6 -402,102 +135,6 @@@ float autocvar_g_balance_keyhunt_score_
  float autocvar_g_balance_keyhunt_throwvelocity;
  float autocvar_g_balance_kill_delay;
  float autocvar_g_balance_kill_antispam;
 -float autocvar_g_balance_laser_primary_animtime;
 -float autocvar_g_balance_laser_primary_damage;
 -float autocvar_g_balance_laser_primary_delay;
 -float autocvar_g_balance_laser_primary_edgedamage;
 -float autocvar_g_balance_laser_primary_force;
 -float autocvar_g_balance_laser_primary_force_other_scale;
 -float autocvar_g_balance_laser_primary_force_velocitybias;
 -float autocvar_g_balance_laser_primary_force_zscale;
 -float autocvar_g_balance_laser_primary_lifetime;
 -float autocvar_g_balance_laser_primary_radius;
 -float autocvar_g_balance_laser_primary_refire;
 -float autocvar_g_balance_laser_primary_shotangle;
 -float autocvar_g_balance_laser_primary_speed;
 -float autocvar_g_balance_laser_secondary;
 -float autocvar_g_balance_laser_secondary_animtime;
 -float autocvar_g_balance_laser_secondary_damage;
 -float autocvar_g_balance_laser_secondary_edgedamage;
 -float autocvar_g_balance_laser_secondary_force;
 -float autocvar_g_balance_laser_secondary_force_other_scale;
 -float autocvar_g_balance_laser_secondary_force_velocitybias;
 -float autocvar_g_balance_laser_secondary_force_zscale;
 -float autocvar_g_balance_laser_secondary_lifetime;
 -float autocvar_g_balance_laser_secondary_radius;
 -float autocvar_g_balance_laser_secondary_speed;
 -float autocvar_g_balance_laser_reload_ammo;
 -float autocvar_g_balance_laser_reload_time;
 -float autocvar_g_balance_minelayer_ammo;
 -float autocvar_g_balance_minelayer_animtime;
 -float autocvar_g_balance_minelayer_damage;
 -float autocvar_g_balance_minelayer_damageforcescale;
 -float autocvar_g_balance_minelayer_detonatedelay;
 -float autocvar_g_balance_minelayer_edgedamage;
 -float autocvar_g_balance_minelayer_force;
 -float autocvar_g_balance_minelayer_health;
 -float autocvar_g_balance_minelayer_lifetime;
 -float autocvar_g_balance_minelayer_lifetime_countdown;
 -float autocvar_g_balance_minelayer_limit;
 -float autocvar_g_balance_minelayer_protection;
 -float autocvar_g_balance_minelayer_proximityradius;
 -float autocvar_g_balance_minelayer_radius;
 -float autocvar_g_balance_minelayer_refire;
 -float autocvar_g_balance_minelayer_remote_damage;
 -float autocvar_g_balance_minelayer_remote_edgedamage;
 -float autocvar_g_balance_minelayer_remote_force;
 -float autocvar_g_balance_minelayer_remote_radius;
 -float autocvar_g_balance_minelayer_speed;
 -float autocvar_g_balance_minelayer_time;
 -float autocvar_g_balance_minelayer_reload_ammo;
 -float autocvar_g_balance_minelayer_reload_time;
 -float autocvar_g_balance_minstanex_ammo;
 -float autocvar_g_balance_minstanex_laser_ammo;
 -float autocvar_g_balance_minstanex_laser_animtime;
 -float autocvar_g_balance_minstanex_laser_refire;
 -float autocvar_g_balance_minstanex_animtime;
 -float autocvar_g_balance_minstanex_refire;
 -float autocvar_g_balance_minstanex_reload_ammo;
 -float autocvar_g_balance_minstanex_reload_time;
 -float autocvar_g_balance_nex_charge;
 -float autocvar_g_balance_nex_charge_animlimit;
 -float autocvar_g_balance_nex_charge_limit;
 -float autocvar_g_balance_nex_charge_maxspeed;
 -float autocvar_g_balance_nex_charge_mindmg;
 -float autocvar_g_balance_nex_charge_minspeed;
 -float autocvar_g_balance_nex_charge_rate;
 -float autocvar_g_balance_nex_charge_rot_pause;
 -float autocvar_g_balance_nex_charge_rot_rate;
 -float autocvar_g_balance_nex_charge_shot_multiplier;
 -float autocvar_g_balance_nex_charge_start;
 -float autocvar_g_balance_nex_charge_velocity_rate;
 -float autocvar_g_balance_nex_primary_ammo;
 -float autocvar_g_balance_nex_primary_animtime;
 -float autocvar_g_balance_nex_primary_damage;
 -float autocvar_g_balance_nex_primary_damagefalloff_forcehalflife;
 -float autocvar_g_balance_nex_primary_damagefalloff_halflife;
 -float autocvar_g_balance_nex_primary_damagefalloff_maxdist;
 -float autocvar_g_balance_nex_primary_damagefalloff_mindist;
 -float autocvar_g_balance_nex_primary_force;
 -float autocvar_g_balance_nex_primary_refire;
 -float autocvar_g_balance_nex_secondary;
 -float autocvar_g_balance_nex_secondary_ammo;
 -float autocvar_g_balance_nex_secondary_animtime;
 -float autocvar_g_balance_nex_secondary_charge;
 -float autocvar_g_balance_nex_secondary_charge_rate;
 -float autocvar_g_balance_nex_secondary_chargepool;
 -float autocvar_g_balance_nex_secondary_chargepool_pause_health_regen;
 -float autocvar_g_balance_nex_secondary_chargepool_pause_regen;
 -float autocvar_g_balance_nex_secondary_chargepool_regen;
 -float autocvar_g_balance_nex_secondary_damage;
 -float autocvar_g_balance_nex_secondary_damagefalloff_forcehalflife;
 -float autocvar_g_balance_nex_secondary_damagefalloff_halflife;
 -float autocvar_g_balance_nex_secondary_damagefalloff_maxdist;
 -float autocvar_g_balance_nex_secondary_damagefalloff_mindist;
 -float autocvar_g_balance_nex_secondary_force;
 -float autocvar_g_balance_nex_secondary_refire;
 -float autocvar_g_balance_nex_reload_ammo;
 -float autocvar_g_balance_nex_reload_time;
  float autocvar_g_balance_nexball_primary_animtime;
  float autocvar_g_balance_nexball_primary_refire;
  float autocvar_g_balance_nexball_primary_speed;
@@@ -143,13 -507,11 +144,13 @@@ float autocvar_g_balance_nexball_second
  float autocvar_g_balance_nexball_secondary_refire;
  float autocvar_g_balance_nexball_secondary_speed;
  float autocvar_g_balance_nix_ammo_cells;
 +float autocvar_g_balance_nix_ammo_plasma;
  float autocvar_g_balance_nix_ammo_fuel;
  float autocvar_g_balance_nix_ammo_nails;
  float autocvar_g_balance_nix_ammo_rockets;
  float autocvar_g_balance_nix_ammo_shells;
  float autocvar_g_balance_nix_ammoincr_cells;
 +float autocvar_g_balance_nix_ammoincr_plasma;
  float autocvar_g_balance_nix_ammoincr_fuel;
  float autocvar_g_balance_nix_ammoincr_nails;
  float autocvar_g_balance_nix_ammoincr_rockets;
@@@ -167,6 -529,15 +168,6 @@@ float autocvar_g_balance_pause_health_r
  float autocvar_g_balance_pause_health_rot_spawn;
  float autocvar_g_balance_portal_health;
  float autocvar_g_balance_portal_lifetime;
 -float autocvar_g_balance_porto_primary_animtime;
 -float autocvar_g_balance_porto_primary_lifetime;
 -float autocvar_g_balance_porto_primary_refire;
 -float autocvar_g_balance_porto_primary_speed;
 -float autocvar_g_balance_porto_secondary;
 -float autocvar_g_balance_porto_secondary_animtime;
 -float autocvar_g_balance_porto_secondary_lifetime;
 -float autocvar_g_balance_porto_secondary_refire;
 -float autocvar_g_balance_porto_secondary_speed;
  float autocvar_g_balance_powerup_invincible_takedamage;
  float autocvar_g_balance_powerup_invincible_time;
  float autocvar_g_balance_powerup_strength_damage;
@@@ -175,10 -546,133 +176,10 @@@ float autocvar_g_balance_powerup_streng
  float autocvar_g_balance_powerup_strength_selfforce;
  float autocvar_g_balance_powerup_strength_time;
  float autocvar_g_balance_superweapons_time;
 -float autocvar_g_balance_rocketlauncher_ammo;
 -float autocvar_g_balance_rocketlauncher_animtime;
 -float autocvar_g_balance_rocketlauncher_damage;
 -float autocvar_g_balance_rocketlauncher_damageforcescale;
 -float autocvar_g_balance_rocketlauncher_detonatedelay;
 -float autocvar_g_balance_rocketlauncher_edgedamage;
 -float autocvar_g_balance_rocketlauncher_force;
 -float autocvar_g_balance_rocketlauncher_guidedelay;
 -float autocvar_g_balance_rocketlauncher_guidegoal;
 -float autocvar_g_balance_rocketlauncher_guiderate;
 -float autocvar_g_balance_rocketlauncher_guideratedelay;
 -float autocvar_g_balance_rocketlauncher_guidestop;
 -float autocvar_g_balance_rocketlauncher_health;
 -float autocvar_g_balance_rocketlauncher_lifetime;
 -float autocvar_g_balance_rocketlauncher_radius;
 -float autocvar_g_balance_rocketlauncher_refire;
 -float autocvar_g_balance_rocketlauncher_remote_damage;
 -float autocvar_g_balance_rocketlauncher_remote_edgedamage;
 -float autocvar_g_balance_rocketlauncher_remote_force;
 -float autocvar_g_balance_rocketlauncher_remote_radius;
 -float autocvar_g_balance_rocketlauncher_speed;
 -float autocvar_g_balance_rocketlauncher_speedaccel;
 -float autocvar_g_balance_rocketlauncher_speedstart;
 -float autocvar_g_balance_rocketlauncher_reload_ammo;
 -float autocvar_g_balance_rocketlauncher_reload_time;
 -float autocvar_g_balance_seeker_type;
 -float autocvar_g_balance_seeker_flac_ammo;
 -float autocvar_g_balance_seeker_flac_animtime;
 -float autocvar_g_balance_seeker_flac_damage;
 -float autocvar_g_balance_seeker_flac_edgedamage;
 -float autocvar_g_balance_seeker_flac_force;
 -float autocvar_g_balance_seeker_flac_lifetime;
 -float autocvar_g_balance_seeker_flac_lifetime_rand;
 -float autocvar_g_balance_seeker_flac_radius;
 -float autocvar_g_balance_seeker_flac_refire;
 -float autocvar_g_balance_seeker_missile_accel;
 -float autocvar_g_balance_seeker_missile_ammo;
 -float autocvar_g_balance_seeker_missile_animtime;
 -float autocvar_g_balance_seeker_missile_count;
 -float autocvar_g_balance_seeker_missile_damage;
 -float autocvar_g_balance_seeker_missile_damageforcescale;
 -float autocvar_g_balance_seeker_missile_decel;
 -float autocvar_g_balance_seeker_missile_delay;
 -float autocvar_g_balance_seeker_missile_edgedamage;
 -float autocvar_g_balance_seeker_missile_force;
 -float autocvar_g_balance_seeker_missile_health;
 -float autocvar_g_balance_seeker_missile_lifetime;
 -float autocvar_g_balance_seeker_missile_proxy;
 -float autocvar_g_balance_seeker_missile_proxy_delay;
 -float autocvar_g_balance_seeker_missile_proxy_maxrange;
 -float autocvar_g_balance_seeker_missile_radius;
 -float autocvar_g_balance_seeker_missile_refire;
 -float autocvar_g_balance_seeker_missile_smart;
 -float autocvar_g_balance_seeker_missile_smart_mindist;
 -float autocvar_g_balance_seeker_missile_smart_trace_max;
 -float autocvar_g_balance_seeker_missile_smart_trace_min;
 -float autocvar_g_balance_seeker_missile_speed_max;
 -float autocvar_g_balance_seeker_missile_turnrate;
 -float autocvar_g_balance_seeker_tag_ammo;
 -float autocvar_g_balance_seeker_tag_animtime;
 -float autocvar_g_balance_seeker_tag_damageforcescale;
 -float autocvar_g_balance_seeker_tag_health;
 -float autocvar_g_balance_seeker_tag_lifetime;
 -float autocvar_g_balance_seeker_tag_refire;
 -float autocvar_g_balance_seeker_tag_speed;
 -float autocvar_g_balance_seeker_tag_tracker_lifetime;
 -float autocvar_g_balance_seeker_reload_ammo;
 -float autocvar_g_balance_seeker_reload_time;
  float autocvar_g_balance_selfdamagepercent;
 -float autocvar_g_balance_shotgun_primary_ammo;
 -float autocvar_g_balance_shotgun_primary_animtime;
 -float autocvar_g_balance_shotgun_primary_bullets;
 -float autocvar_g_balance_shotgun_primary_damage;
 -float autocvar_g_balance_shotgun_primary_force;
 -float autocvar_g_balance_shotgun_primary_refire;
 -float autocvar_g_balance_shotgun_primary_solidpenetration;
 -float autocvar_g_balance_shotgun_primary_spread;
 -float autocvar_g_balance_shotgun_secondary;
 -float autocvar_g_balance_shotgun_secondary_animtime;
 -float autocvar_g_balance_shotgun_secondary_damage;
 -float autocvar_g_balance_shotgun_secondary_force;
 -float autocvar_g_balance_shotgun_secondary_melee_delay;
 -float autocvar_g_balance_shotgun_secondary_melee_range;
 -float autocvar_g_balance_shotgun_secondary_melee_swing_side;
 -float autocvar_g_balance_shotgun_secondary_melee_swing_up;
 -float autocvar_g_balance_shotgun_secondary_melee_time;
 -float autocvar_g_balance_shotgun_secondary_melee_traces;
 -float autocvar_g_balance_shotgun_secondary_melee_no_doubleslap;
 -float autocvar_g_balance_shotgun_secondary_melee_nonplayerdamage;
 -float autocvar_g_balance_shotgun_secondary_melee_multihit;
 -float autocvar_g_balance_shotgun_secondary_refire;
 -float autocvar_g_balance_shotgun_reload_ammo;
 -float autocvar_g_balance_shotgun_reload_time;
  float autocvar_g_balance_teams;
  float autocvar_g_balance_teams_prevent_imbalance;
  float autocvar_g_balance_teams_scorefactor;
 -float autocvar_g_balance_tuba_animtime;
 -float autocvar_g_balance_tuba_attenuation;
 -float autocvar_g_balance_tuba_damage;
 -float autocvar_g_balance_tuba_edgedamage;
 -float autocvar_g_balance_tuba_force;
 -float autocvar_g_balance_tuba_radius;
 -float autocvar_g_balance_tuba_refire;
 -float autocvar_g_balance_uzi_burst;
 -float autocvar_g_balance_uzi_burst_ammo;
 -float autocvar_g_balance_uzi_burst_animtime;
 -float autocvar_g_balance_uzi_burst_refire;
 -float autocvar_g_balance_uzi_burst_refire2;
 -float autocvar_g_balance_uzi_burst_spread;
 -float autocvar_g_balance_uzi_first;
 -float autocvar_g_balance_uzi_first_ammo;
 -float autocvar_g_balance_uzi_first_damage;
 -float autocvar_g_balance_uzi_first_force;
 -float autocvar_g_balance_uzi_first_refire;
 -float autocvar_g_balance_uzi_first_spread;
 -float autocvar_g_balance_uzi_mode;
 -float autocvar_g_balance_uzi_solidpenetration;
 -float autocvar_g_balance_uzi_spread_add;
 -float autocvar_g_balance_uzi_spread_max;
 -float autocvar_g_balance_uzi_spread_min;
 -float autocvar_g_balance_uzi_sustained_ammo;
 -float autocvar_g_balance_uzi_sustained_damage;
 -float autocvar_g_balance_uzi_sustained_force;
 -float autocvar_g_balance_uzi_sustained_refire;
 -float autocvar_g_balance_uzi_sustained_spread;
 -float autocvar_g_balance_uzi_reload_ammo;
 -float autocvar_g_balance_uzi_reload_time;
  float autocvar_g_ballistics_density_corpse;
  float autocvar_g_ballistics_density_player;
  float autocvar_g_ballistics_mindistance;
@@@ -430,7 -924,6 +431,7 @@@ float autocvar_g_onslaught_cp_health
  float autocvar_g_onslaught_cp_regen;
  float autocvar_g_onslaught_gen_health;
  float autocvar_g_pickup_cells_max;
 +float autocvar_g_pickup_plasma_max;
  float autocvar_g_pickup_fuel_max;
  float autocvar_g_pickup_items;
  float autocvar_g_pickup_nails_max;
@@@ -729,6 -1222,7 +730,7 @@@ float autocvar_g_physical_items_damagef
  float autocvar_g_physical_items_reset;
  float autocvar_g_monsters;
  float autocvar_g_monsters_edit;
+ float autocvar_g_monsters_sounds;
  float autocvar_g_monsters_think_delay;
  float autocvar_g_monsters_max;
  float autocvar_g_monsters_max_perplayer;
@@@ -752,7 -1246,10 +754,10 @@@ float autocvar_g_touchexplode_damage
  float autocvar_g_touchexplode_edgedamage;
  float autocvar_g_touchexplode_force;
  float autocvar_g_invasion_round_timelimit;
- #define autocvar_g_invasion_round_limit cvar("g_invasion_round_limit")
+ float autocvar_g_invasion_teams;
+ float autocvar_g_invasion_team_spawns;
+ float autocvar_g_invasion_spawnpoint_spawn_delay;
+ #define autocvar_g_invasion_point_limit cvar("g_invasion_point_limit")
  float autocvar_g_invasion_warmup;
  float autocvar_g_invasion_monster_count;
  float autocvar_g_invasion_zombies_only;
index 124e2cdb64ae05f32f7412eb58d4d3612379b628,2e57eecb3b1c6cf3e2b7e0e7bbc4e15e6b2a6867..2ce9706a2ff40cdcb67557a2d1d6979a9d4e5dd3
@@@ -92,7 -92,7 +92,7 @@@ void havocbot_ai(
  
                if(self.weapons)
                {
 -                      weapon_action(self.weapon, WR_AIM);
 +                      WEP_ACTION(self.weapon, WR_AIM);
                        if (autocvar_bot_nofire || IS_INDEPENDENT_PLAYER(self))
                        {
                                self.BUTTON_ATCK = FALSE;
                        for(i = WEP_FIRST; i <= WEP_LAST; ++i)
                        {
                                e = get_weaponinfo(i);
 -                              if ((self.weapons & WepSet_FromWeapon(i)) && (e.spawnflags & WEP_FLAG_RELOADABLE) && (self.weapon_load[i] < cvar(strcat("g_balance_", e.netname, "_reload_ammo"))))
 +                              if ((self.weapons & WepSet_FromWeapon(i)) && (e.spawnflags & WEP_FLAG_RELOADABLE) && (self.weapon_load[i] < e.reloading_ammo))
                                        self.switchweapon = i;
                        }
                }
@@@ -590,10 -590,10 +590,10 @@@ void havocbot_movetogoal(
  
                        return;
                }
 -              else if(self.health>autocvar_g_balance_rocketlauncher_damage*0.5)
 +              else if(self.health>WEP_CVAR(devastator, damage)*0.5)
                {
                        if(self.velocity_z < 0)
 -                      if(client_hasweapon(self, WEP_ROCKET_LAUNCHER, TRUE, FALSE))
 +                      if(client_hasweapon(self, WEP_DEVASTATOR, TRUE, FALSE))
                        {
                                self.movement_x = maxspeed;
  
                                        return;
                                }
  
 -                              self.switchweapon = WEP_ROCKET_LAUNCHER;
 +                              self.switchweapon = WEP_DEVASTATOR;
                                self.v_angle_x = 90;
                                self.BUTTON_ATCK = TRUE;
 -                              self.rocketjumptime = time + autocvar_g_balance_rocketlauncher_detonatedelay;
 +                              self.rocketjumptime = time + WEP_CVAR(devastator, detonatedelay);
                                return;
                        }
                }
                        vector dst_ahead, dst_down;
                        makevectors(self.v_angle_y * '0 1 0');
                        dst_ahead = self.origin + self.view_ofs + (self.velocity * 0.4) + (v_forward * 32 * 3);
-                       dst_down = dst_ahead + '0 0 -1500';
+                       dst_down = dst_ahead - '0 0 1500';
  
                        // Look ahead
-                       traceline(self.origin + self.view_ofs , dst_ahead, TRUE, world);
+                       traceline(self.origin + self.view_ofs, dst_ahead, TRUE, world);
  
                        // Check head-banging against walls
                        if(vlen(self.origin + self.view_ofs - trace_endpos) < 25 && !(self.aistatus & AI_STATUS_OUT_WATER))
@@@ -956,7 -956,7 +956,7 @@@ float havocbot_chooseweapon_checkreload
                for(i = WEP_FIRST; i <= WEP_LAST; ++i)
                {
                        // if we are out of ammo for all other weapons, it's an emergency to switch to anything else
 -                      if (weapon_action(i, WR_CHECKAMMO1) + weapon_action(i, WR_CHECKAMMO2))
 +                      if (WEP_ACTION(i, WR_CHECKAMMO1) + WEP_ACTION(i, WR_CHECKAMMO2))
                                other_weapon_available = TRUE;
                }
                if(other_weapon_available)
@@@ -982,7 -982,7 +982,7 @@@ void havocbot_chooseweapon(
        {
                // If no weapon was chosen get the first available weapon
                if(self.weapon==0)
 -              for(i=WEP_LASER + 1; i < WEP_COUNT ; ++i)
 +              for(i=WEP_BLASTER + 1; i < WEP_COUNT ; ++i) // Samual: This seems strange compared to other weapon loops...
                {
                        if(client_hasweapon(self, i, TRUE, FALSE))
                        {
index f9faf528077b97da627cb3b97931290ef22433a5,45f5a6e692c4bbc0cda20f2a1d99a10caa0f805c..f682b692630449eef191a779bb9ea8a981e81cd9
@@@ -98,10 -98,7 +98,10 @@@ void havocbot_goalrating_items(float ra
                                        if (head.ammo_rockets && player.ammo_rockets > self.ammo_rockets)
                                                continue;
  
 -                                      if (head.ammo_cells && player.ammo_cells > self.ammo_cells )
 +                                      if (head.ammo_cells && player.ammo_cells > self.ammo_cells)
 +                                              continue;
 +
 +                                      if (head.ammo_plasma && player.ammo_plasma > self.ammo_plasma)
                                                continue;
  
                                        discard = FALSE;
@@@ -272,7 -269,7 +272,7 @@@ void havocbot_chooserole(
  {
        dprint("choosing a role...\n");
        self.bot_strategytime = 0;
-       if (MUTATOR_CALLHOOK(HavocBot_ChooseRule))
+       if (MUTATOR_CALLHOOK(HavocBot_ChooseRole))
                return;
        else if (g_keyhunt)
                havocbot_chooserole_kh();
index 0e0a271276c43afbfab43a0c102de4468f0c081e,4ab1836e8c0e242828aa2b0e7cf470b1897ea71b..c29523bfce730fee240f67ef86c8938a0d6632ca
@@@ -283,7 -283,7 +283,7 @@@ void FixPlayermodel(
                if(teamplay)
                {
                        string s;
-                       s = Team_ColorName_Lower(self.team);
+                       s = Static_Team_ColorName_Lower(self.team);
                        if(s != "neutral")
                        {
                                defaultmodel = cvar_string(strcat("sv_defaultplayermodel_", s));
@@@ -428,11 -428,11 +428,11 @@@ void PutClientInServer (void
                self.effects |= EF_TELEPORT_BIT | EF_RESTARTANIM_BIT;
                self.air_finished = time + 12;
                self.dmg = 2;
 -              if(autocvar_g_balance_nex_charge)
 +              if(WEP_CVAR(vortex, charge))
                {
 -                      if(autocvar_g_balance_nex_secondary_chargepool)
 -                              self.nex_chargepool_ammo = 1;
 -                      self.nex_charge = autocvar_g_balance_nex_charge_start;
 +                      if(WEP_CVAR_SEC(vortex, chargepool))
 +                              self.vortex_chargepool_ammo = 1;
 +                      self.vortex_charge = WEP_CVAR(vortex, charge_start);
                }
  
                if(warmup_stage)
                        self.ammo_nails = warmup_start_ammo_nails;
                        self.ammo_rockets = warmup_start_ammo_rockets;
                        self.ammo_cells = warmup_start_ammo_cells;
 +                      self.ammo_plasma = warmup_start_ammo_plasma;
                        self.ammo_fuel = warmup_start_ammo_fuel;
                        self.health = warmup_start_health;
                        self.armorvalue = warmup_start_armorvalue;
                        self.ammo_nails = start_ammo_nails;
                        self.ammo_rockets = start_ammo_rockets;
                        self.ammo_cells = start_ammo_cells;
 +                      self.ammo_plasma = start_ammo_plasma;
                        self.ammo_fuel = start_ammo_fuel;
                        self.health = start_health;
                        self.armorvalue = start_armorvalue;
                else
                        self.superweapons_finished = 0;
  
 -              if(g_weaponarena_random)
 +              if(g_weaponarena_random) // WEAPONTODO: more stuff that should be in a mutator. also: rename those cvars
                {
                        if(g_weaponarena_random_with_laser)
 -                              self.weapons &= ~WEPSET_LASER;
 +                              self.weapons &= ~WEPSET_BLASTER;
                        W_RandomWeapons(self, g_weaponarena_random);
                        if(g_weaponarena_random_with_laser)
 -                              self.weapons |= WEPSET_LASER;
 +                              self.weapons |= WEPSET_BLASTER;
                }
  
                self.items = start_items;
                // reset fields the weapons may use
                for (j = WEP_FIRST; j <= WEP_LAST; ++j)
                {
 -                      weapon_action(j, WR_RESETPLAYER);
 +                      WEP_ACTION(j, WR_RESETPLAYER);
  
                        // all weapons must be fully loaded when we spawn
                        entity e;
                        e = get_weaponinfo(j);
                        if(e.spawnflags & WEP_FLAG_RELOADABLE) // prevent accessing undefined cvars
 -                              self.(weapon_load[j]) = cvar(strcat("g_balance_", e.netname, "_reload_ammo"));
 +                              self.(weapon_load[j]) = e.reloading_ammo;
                }
  
                oldself = self;
@@@ -632,27 -630,30 +632,27 @@@ float ClientInit_SendEntity(entity to, 
        WriteInt24_t(MSG_ENTITY, compressShotOrigin(hook_shotorigin[1]));
        WriteInt24_t(MSG_ENTITY, compressShotOrigin(hook_shotorigin[2]));
        WriteInt24_t(MSG_ENTITY, compressShotOrigin(hook_shotorigin[3]));
 -      WriteInt24_t(MSG_ENTITY, compressShotOrigin(electro_shotorigin[0]));
 -      WriteInt24_t(MSG_ENTITY, compressShotOrigin(electro_shotorigin[1]));
 -      WriteInt24_t(MSG_ENTITY, compressShotOrigin(electro_shotorigin[2]));
 -      WriteInt24_t(MSG_ENTITY, compressShotOrigin(electro_shotorigin[3]));
 -      WriteInt24_t(MSG_ENTITY, compressShotOrigin(gauntlet_shotorigin[0]));
 -      WriteInt24_t(MSG_ENTITY, compressShotOrigin(gauntlet_shotorigin[1]));
 -      WriteInt24_t(MSG_ENTITY, compressShotOrigin(gauntlet_shotorigin[2]));
 -      WriteInt24_t(MSG_ENTITY, compressShotOrigin(gauntlet_shotorigin[3]));
 +      WriteInt24_t(MSG_ENTITY, compressShotOrigin(arc_shotorigin[0]));
 +      WriteInt24_t(MSG_ENTITY, compressShotOrigin(arc_shotorigin[1]));
 +      WriteInt24_t(MSG_ENTITY, compressShotOrigin(arc_shotorigin[2]));
 +      WriteInt24_t(MSG_ENTITY, compressShotOrigin(arc_shotorigin[3]));
 +
        if(sv_foginterval && world.fog != "")
                WriteString(MSG_ENTITY, world.fog);
        else
                WriteString(MSG_ENTITY, "");
        WriteByte(MSG_ENTITY, self.count * 255.0); // g_balance_armor_blockpercent
 -      WriteCoord(MSG_ENTITY, self.bouncefactor); // g_balance_grenadelauncher_bouncefactor
 -      WriteCoord(MSG_ENTITY, self.bouncestop); // g_balance_grenadelauncher_bouncestop
 -      WriteCoord(MSG_ENTITY, self.ebouncefactor); // g_balance_grenadelauncher_bouncefactor
 -      WriteCoord(MSG_ENTITY, self.ebouncestop); // g_balance_grenadelauncher_bouncestop
 -      WriteByte(MSG_ENTITY, autocvar_g_balance_nex_secondary); // client has to know if it should zoom or not
 -      WriteByte(MSG_ENTITY, autocvar_g_balance_rifle_secondary); // client has to know if it should zoom or not
 +      WriteCoord(MSG_ENTITY, self.bouncefactor); // g_balance_mortar_bouncefactor // WEAPONTODO
 +      WriteCoord(MSG_ENTITY, self.bouncestop); // g_balance_mortar_bouncestop
 +      WriteCoord(MSG_ENTITY, self.ebouncefactor); // g_balance_mortar_bouncefactor
 +      WriteCoord(MSG_ENTITY, self.ebouncestop); // g_balance_mortar_bouncestop
 +      WriteByte(MSG_ENTITY, WEP_CVAR(vortex, secondary)); // client has to know if it should zoom or not // WEAPONTODO
 +      WriteByte(MSG_ENTITY, WEP_CVAR(rifle, secondary)); // client has to know if it should zoom or not // WEAPONTODO
        WriteByte(MSG_ENTITY, serverflags); // client has to know if it should zoom or not
 -      WriteByte(MSG_ENTITY, autocvar_g_balance_minelayer_limit); // minelayer max mines
 -      WriteByte(MSG_ENTITY, autocvar_g_balance_hagar_secondary_load_max); // hagar max loadable rockets
 +      WriteByte(MSG_ENTITY, WEP_CVAR(minelayer, limit)); // minelayer max mines // WEAPONTODO
 +      WriteByte(MSG_ENTITY, WEP_CVAR_SEC(hagar, load_max)); // hagar max loadable rockets // WEAPONTODO
        WriteCoord(MSG_ENTITY, autocvar_g_trueaim_minrange);
 -      WriteByte(MSG_ENTITY, autocvar_g_balance_porto_secondary);
 +      WriteByte(MSG_ENTITY, WEP_CVAR(porto, secondary)); // WEAPONTODO
        return TRUE;
  }
  
@@@ -664,14 -665,14 +664,14 @@@ void ClientInit_CheckUpdate(
                self.count = autocvar_g_balance_armor_blockpercent;
                self.SendFlags |= 1;
        }
 -      if(self.bouncefactor != autocvar_g_balance_grenadelauncher_bouncefactor)
 +      if(self.bouncefactor != autocvar_g_balance_mortar_bouncefactor) // WEAPONTODO
        {
 -              self.bouncefactor = autocvar_g_balance_grenadelauncher_bouncefactor;
 +              self.bouncefactor = autocvar_g_balance_mortar_bouncefactor;
                self.SendFlags |= 1;
        }
 -      if(self.bouncestop != autocvar_g_balance_grenadelauncher_bouncestop)
 +      if(self.bouncestop != autocvar_g_balance_mortar_bouncestop)
        {
 -              self.bouncestop = autocvar_g_balance_grenadelauncher_bouncestop;
 +              self.bouncestop = autocvar_g_balance_mortar_bouncestop;
                self.SendFlags |= 1;
        }
        if(self.ebouncefactor != autocvar_g_balance_electro_secondary_bouncefactor)
@@@ -1200,7 -1201,13 +1200,7 @@@ void ClientConnect (void
        if(!sv_foginterval && world.fog != "")
                stuffcmd(self, strcat("\nfog ", world.fog, "\nr_fog_exp2 0\nr_drawfog 1\n"));
  
 -      if(autocvar_g_hitplots || strstrofs(strcat(" ", autocvar_g_hitplots_individuals, " "), strcat(" ", self.netaddress, " "), 0) >= 0)
 -      {
 -              self.hitplotfh = fopen(strcat("hits-", matchid, "-", self.netaddress, "-", ftos(self.playerid), ".plot"), FILE_WRITE);
 -              fputs(self.hitplotfh, strcat("#name ", self.netname, "\n"));
 -      }
 -      else
 -              self.hitplotfh = -1;
 +      W_HitPlotOpen(self);
  
        if(g_race || g_cts) {
                string rr;
@@@ -1260,7 -1267,11 +1260,7 @@@ void ClientDisconnect (void
  
        CheatShutdownClient();
  
 -      if(self.hitplotfh >= 0)
 -      {
 -              fclose(self.hitplotfh);
 -              self.hitplotfh = -1;
 -      }
 +      W_HitPlotClose(self);
  
        anticheat_report();
        anticheat_shutdown();
@@@ -1414,7 -1425,7 +1414,7 @@@ void player_powerups (void
        // add a way to see what the items were BEFORE all of these checks for the mutator hook
        olditems = self.items;
  
-       if((self.items & IT_USING_JETPACK) && !self.deadflag)
+       if((self.items & IT_USING_JETPACK) && !self.deadflag && !gameover)
                self.modelflags |= MF_ROCKET;
        else
                self.modelflags &= ~MF_ROCKET;
@@@ -1688,7 -1699,6 +1688,7 @@@ void SpectateCopy(entity spectatee) 
        self.armortype = spectatee.armortype;
        self.armorvalue = spectatee.armorvalue;
        self.ammo_cells = spectatee.ammo_cells;
 +      self.ammo_plasma = spectatee.ammo_plasma;
        self.ammo_shells = spectatee.ammo_shells;
        self.ammo_nails = spectatee.ammo_nails;
        self.ammo_rockets = spectatee.ammo_rockets;
        self.switchweapon = spectatee.switchweapon;
        self.switchingweapon = spectatee.switchingweapon;
        self.weapon = spectatee.weapon;
 -      self.nex_charge = spectatee.nex_charge;
 -      self.nex_chargepool_ammo = spectatee.nex_chargepool_ammo;
 +      self.vortex_charge = spectatee.vortex_charge;
 +      self.vortex_chargepool_ammo = spectatee.vortex_chargepool_ammo;
        self.hagar_load = spectatee.hagar_load;
        self.minelayer_mines = spectatee.minelayer_mines;
        self.punchangle = spectatee.punchangle;
@@@ -2264,17 -2274,17 +2264,17 @@@ void PlayerPreThink (void
  
                if(frametime)
                {
 -                      if(self.weapon == WEP_NEX && autocvar_g_balance_nex_charge)
 +                      if(self.weapon == WEP_VORTEX && WEP_CVAR(vortex, charge))
                        {
 -                              self.weaponentity_glowmod_x = autocvar_g_weapon_charge_colormod_hdrmultiplier * autocvar_g_weapon_charge_colormod_red_half * min(1, self.nex_charge / autocvar_g_balance_nex_charge_animlimit);
 -                              self.weaponentity_glowmod_y = autocvar_g_weapon_charge_colormod_hdrmultiplier * autocvar_g_weapon_charge_colormod_green_half * min(1, self.nex_charge / autocvar_g_balance_nex_charge_animlimit);
 -                              self.weaponentity_glowmod_z = autocvar_g_weapon_charge_colormod_hdrmultiplier * autocvar_g_weapon_charge_colormod_blue_half * min(1, self.nex_charge / autocvar_g_balance_nex_charge_animlimit);
 +                              self.weaponentity_glowmod_x = autocvar_g_weapon_charge_colormod_hdrmultiplier * autocvar_g_weapon_charge_colormod_red_half * min(1, self.vortex_charge / WEP_CVAR(vortex, charge_animlimit));
 +                              self.weaponentity_glowmod_y = autocvar_g_weapon_charge_colormod_hdrmultiplier * autocvar_g_weapon_charge_colormod_green_half * min(1, self.vortex_charge / WEP_CVAR(vortex, charge_animlimit));
 +                              self.weaponentity_glowmod_z = autocvar_g_weapon_charge_colormod_hdrmultiplier * autocvar_g_weapon_charge_colormod_blue_half * min(1, self.vortex_charge / WEP_CVAR(vortex, charge_animlimit));
  
 -                              if(self.nex_charge > autocvar_g_balance_nex_charge_animlimit)
 +                              if(self.vortex_charge > WEP_CVAR(vortex, charge_animlimit))
                                {
 -                                      self.weaponentity_glowmod_x = self.weaponentity_glowmod_x + autocvar_g_weapon_charge_colormod_hdrmultiplier * autocvar_g_weapon_charge_colormod_red_full * (self.nex_charge - autocvar_g_balance_nex_charge_animlimit) / (1 - autocvar_g_balance_nex_charge_animlimit);
 -                                      self.weaponentity_glowmod_y = self.weaponentity_glowmod_y + autocvar_g_weapon_charge_colormod_hdrmultiplier * autocvar_g_weapon_charge_colormod_green_full * (self.nex_charge - autocvar_g_balance_nex_charge_animlimit) / (1 - autocvar_g_balance_nex_charge_animlimit);
 -                                      self.weaponentity_glowmod_z = self.weaponentity_glowmod_z + autocvar_g_weapon_charge_colormod_hdrmultiplier * autocvar_g_weapon_charge_colormod_blue_full * (self.nex_charge - autocvar_g_balance_nex_charge_animlimit) / (1 - autocvar_g_balance_nex_charge_animlimit);
 +                                      self.weaponentity_glowmod_x = self.weaponentity_glowmod_x + autocvar_g_weapon_charge_colormod_hdrmultiplier * autocvar_g_weapon_charge_colormod_red_full * (self.vortex_charge - WEP_CVAR(vortex, charge_animlimit)) / (1 - WEP_CVAR(vortex, charge_animlimit));
 +                                      self.weaponentity_glowmod_y = self.weaponentity_glowmod_y + autocvar_g_weapon_charge_colormod_hdrmultiplier * autocvar_g_weapon_charge_colormod_green_full * (self.vortex_charge - WEP_CVAR(vortex, charge_animlimit)) / (1 - WEP_CVAR(vortex, charge_animlimit));
 +                                      self.weaponentity_glowmod_z = self.weaponentity_glowmod_z + autocvar_g_weapon_charge_colormod_hdrmultiplier * autocvar_g_weapon_charge_colormod_blue_full * (self.vortex_charge - WEP_CVAR(vortex, charge_animlimit)) / (1 - WEP_CVAR(vortex, charge_animlimit));
                                }
                        }
                        else
                        do_crouch = 0;
                if(self.freezetag_frozen)
                        do_crouch = 0;
 -              if(self.weapon == WEP_SHOTGUN && self.weaponentity.wframe == WFRAME_FIRE2 && time < self.weapon_nextthink)
 +
 +              // WEAPONTODO: THIS SHIT NEEDS TO GO EVENTUALLY
 +              // It cannot be predicted by the engine! 
 +              if((self.weapon == WEP_SHOCKWAVE || self.weapon == WEP_SHOTGUN) && self.weaponentity.wframe == WFRAME_FIRE2 && time < self.weapon_nextthink)
                        do_crouch = 0;
  
                if (do_crouch)
  
                player_regen();
  
 +              // WEAPONTODO: Add a weapon request for this 
                // rot nex charge to the charge limit
 -              if(autocvar_g_balance_nex_charge_rot_rate && self.nex_charge > autocvar_g_balance_nex_charge_limit && self.nex_charge_rottime < time)
 -                      self.nex_charge = bound(autocvar_g_balance_nex_charge_limit, self.nex_charge - autocvar_g_balance_nex_charge_rot_rate * frametime / W_TICSPERFRAME, 1);
 +              if(WEP_CVAR(vortex, charge_rot_rate) && self.vortex_charge > WEP_CVAR(vortex, charge_limit) && self.vortex_charge_rottime < time)
 +                      self.vortex_charge = bound(WEP_CVAR(vortex, charge_limit), self.vortex_charge - WEP_CVAR(vortex, charge_rot_rate) * frametime / W_TICSPERFRAME, 1);
  
                if(frametime)
                        player_anim();
                SpectatorThink();
        }
  
 +      // WEAPONTODO: Add weapon request for this
        if(!zoomstate_set)
 -              SetZoomState(self.BUTTON_ZOOM || self.BUTTON_ZOOMSCRIPT || (self.BUTTON_ATCK2 && self.weapon == WEP_NEX) || (self.BUTTON_ATCK2 && self.weapon == WEP_RIFLE && autocvar_g_balance_rifle_secondary == 0));
 +              SetZoomState(self.BUTTON_ZOOM || self.BUTTON_ZOOMSCRIPT || (self.BUTTON_ATCK2 && self.weapon == WEP_VORTEX) || (self.BUTTON_ATCK2 && self.weapon == WEP_RIFLE && WEP_CVAR(rifle, secondary) == 0)); // WEAPONTODO
  
        float oldspectatee_status;
        oldspectatee_status = self.spectatee_status;
  
        target_voicescript_next(self);
  
 +      // WEAPONTODO: Move into weaponsystem somehow
        // if a player goes unarmed after holding a loaded weapon, empty his clip size and remove the crosshair ammo ring
        if(!self.weapon)
                self.clip_load = self.clip_size = 0;
index bdac55e6755af00f6c2191102065ef49346c8732,43c7be517958e718b864f25bbf46e699b741c90d..6f05c456804e73a8ba4371067dd21ff3ad3e3967
@@@ -19,6 -19,9 +19,9 @@@ When you press the jump ke
  */
  void PlayerJump (void)
  {
+       if(self.player_blocked)
+               return; // no jumping while blocked
        float doublejump = FALSE;
  
        player_multijump = doublejump;
@@@ -636,9 -639,7 +639,7 @@@ void SV_PlayerPhysics(
  
        maxspd_mod = 1;
        if(self.ballcarried)
-               if(g_nexball)
-                       maxspd_mod *= autocvar_g_nexball_basketball_carrier_highspeed;
-               else if(g_keepaway)
+               if(g_keepaway)
                        maxspd_mod *= autocvar_g_keepaway_ballcarrier_highspeed;
  
        maxspd_mod *= autocvar_g_movement_highspeed;
                }
        }
  
 +      // WEAPONTODO
        float xyspeed;
        xyspeed = vlen('1 0 0' * self.velocity_x + '0 1 0' * self.velocity_y);
 -      if(self.weapon == WEP_NEX && autocvar_g_balance_nex_charge && autocvar_g_balance_nex_charge_velocity_rate && xyspeed > autocvar_g_balance_nex_charge_minspeed)
 +      if(self.weapon == WEP_VORTEX && WEP_CVAR(vortex, charge) && WEP_CVAR(vortex, charge_velocity_rate) && xyspeed > WEP_CVAR(vortex, charge_minspeed))
        {
                // add a maximum of charge_velocity_rate when going fast (f = 1), gradually increasing from minspeed (f = 0) to maxspeed
 -              xyspeed = min(xyspeed, autocvar_g_balance_nex_charge_maxspeed);
 -              f = (xyspeed - autocvar_g_balance_nex_charge_minspeed) / (autocvar_g_balance_nex_charge_maxspeed - autocvar_g_balance_nex_charge_minspeed);
 +              xyspeed = min(xyspeed, WEP_CVAR(vortex, charge_maxspeed));
 +              f = (xyspeed - WEP_CVAR(vortex, charge_minspeed)) / (WEP_CVAR(vortex, charge_maxspeed) - WEP_CVAR(vortex, charge_minspeed));
                // add the extra charge
 -              self.nex_charge = min(1, self.nex_charge + autocvar_g_balance_nex_charge_velocity_rate * f * frametime);
 +              self.vortex_charge = min(1, self.vortex_charge + WEP_CVAR(vortex, charge_velocity_rate) * f * frametime);
        }
  :end
        if(self.flags & FL_ONGROUND)
index 0fbd35fc532def9e01bad42307f9e3288a1807ef,0fe71f1448c7dd72fbfad0ab3e23066e1f9f166f..630cad61fbc1f0c7bde31a9fc6800f4e3a79ca06
@@@ -1,3 -1,126 +1,3 @@@
 -.entity accuracy;
 -.float accuracy_frags[WEP_MAXCOUNT];
 -
 -float weaponstats_buffer;
 -
 -void WeaponStats_Init()
 -{
 -      if(autocvar_sv_weaponstats_file != "")
 -              weaponstats_buffer = buf_create();
 -      else
 -              weaponstats_buffer = -1;
 -}
 -
 -#define WEAPONSTATS_GETINDEX(awep,abot,vwep,vbot) (((vwep) + (awep) * (WEP_LAST - WEP_FIRST + 1) - (WEP_FIRST + WEP_FIRST * (WEP_LAST - WEP_FIRST + 1))) * 4 + (abot) * 2 + (vbot))
 -
 -void WeaponStats_ready(entity fh, entity pass, float status)
 -{
 -      float i, j, n, ibot, jbot, idx;
 -      vector v;
 -      string prefix, s;
 -      switch(status)
 -      {
 -              case URL_READY_CANWRITE:
 -                      // we can write
 -                      prefix = strcat(autocvar_hostname, "\t", GetGametype(), "_", GetMapname(), "\t");
 -                      url_fputs(fh, "#begin statsfile\n");
 -                      url_fputs(fh, strcat("#date ", strftime(TRUE, "%a %b %e %H:%M:%S %Z %Y"), "\n"));
 -#ifdef WATERMARK
 -                      url_fputs(fh, strcat("#version ", WATERMARK, "\n"));
 -#endif
 -                      url_fputs(fh, strcat("#config ", ftos(crc16(FALSE, cvar_purechanges)), "\n"));
 -                      url_fputs(fh, strcat("#cvar_purechanges ", ftos(cvar_purechanges_count), "\n"));
 -                      n = tokenizebyseparator(cvar_purechanges, "\n");
 -                      for(i = 0; i < n; ++i)
 -                              url_fputs(fh, strcat("#cvar_purechange ", argv(i), "\n"));
 -                      for(i = WEP_FIRST; i <= WEP_LAST; ++i) for(ibot = 0; ibot <= 1; ++ibot)
 -                              for(j = WEP_FIRST; j <= WEP_LAST; ++j) for(jbot = 0; jbot <= 1; ++jbot)
 -                              {
 -                                      idx = WEAPONSTATS_GETINDEX(i, ibot, j, jbot);
 -                                      v = stov(bufstr_get(weaponstats_buffer, idx));
 -                                      if(v != '0 0 0')
 -                                      {
 -                                              //vector is: kills hits damage
 -                                              url_fputs(fh, sprintf("%s%d %d\t%d %d\t", prefix, i, ibot, j, jbot));
 -                                              url_fputs(fh, sprintf("%d %d %g\n", v_x, v_y, v_z));
 -                                      }
 -                              }
 -                      url_fputs(fh, "#end\n\n");
 -                      url_fclose(fh);
 -                      break;
 -              case URL_READY_CANREAD:
 -                      // url_fclose is processing, we got a response for writing the data
 -                      // this must come from HTTP
 -                      print("Got response from weapon stats server:\n");
 -                      while((s = url_fgets(fh)))
 -                              print("  ", s, "\n");
 -                      print("End of response.\n");
 -                      url_fclose(fh);
 -                      break;
 -              case URL_READY_CLOSED:
 -                      // url_fclose has finished
 -                      print("Weapon stats written\n");
 -                      buf_del(weaponstats_buffer);
 -                      weaponstats_buffer = -1;
 -                      break;
 -              case URL_READY_ERROR:
 -              default:
 -                      print("Weapon stats writing failed: ", ftos(status), "\n");
 -                      buf_del(weaponstats_buffer);
 -                      weaponstats_buffer = -1;
 -                      break;
 -      }
 -}
 -
 -void WeaponStats_Shutdown()
 -{
 -      if(weaponstats_buffer < 0)
 -              return;
 -      if(autocvar_sv_weaponstats_file != "")
 -      {
 -              url_multi_fopen(autocvar_sv_weaponstats_file, FILE_APPEND, WeaponStats_ready, world);
 -      }
 -      else
 -      {
 -              buf_del(weaponstats_buffer);
 -              weaponstats_buffer = -1;
 -      }
 -}
 -
 -void WeaponStats_LogItem(float awep, float abot, float vwep, float vbot, vector item)
 -{
 -      float idx;
 -      if(weaponstats_buffer < 0)
 -              return;
 -      if(awep < WEP_FIRST || vwep < WEP_FIRST)
 -              return;
 -      if(awep > WEP_LAST || vwep > WEP_LAST)
 -              return;
 -      idx = WEAPONSTATS_GETINDEX(awep,abot,vwep,vbot);
 -      bufstr_set(weaponstats_buffer, idx, vtos(stov(bufstr_get(weaponstats_buffer, idx)) + item));
 -}
 -void WeaponStats_LogDamage(float awep, float abot, float vwep, float vbot, float damage)
 -{
 -      if(damage < 0)
 -              error("negative damage?");
 -      WeaponStats_LogItem(awep, abot, vwep, vbot, '0 0 1' * damage + '0 1 0');
 -}
 -void WeaponStats_LogKill(float awep, float abot, float vwep, float vbot)
 -{
 -      WeaponStats_LogItem(awep, abot, vwep, vbot, '1 0 0');
 -}
 -
 -// changes by LordHavoc on 03/29/04 and 03/30/04 at Vermeulen's request
 -// merged player_run and player_stand to player_anim
 -// added death animations to player_anim
 -// can now spawn thrown weapons from anywhere, not just from players
 -// thrown weapons now fade out after 20 seconds
 -// created PlayerGib function
 -// PlayerDie no longer uses hitloc or damage
 -// PlayerDie now supports dying animations as well as gibbing
 -// cleaned up PlayerDie a lot
 -// added CopyBody
 -
  .entity pusher;
  .float pushltime;
  .float istypefrag;
@@@ -138,6 -261,13 +138,6 @@@ void player_anim (void
        }
  }
  
 -void SpawnThrownWeapon (vector org, float w)
 -{
 -      if(self.weapons & WepSet_FromWeapon(self.weapon))
 -              if(W_IsWeaponThrowable(self.weapon))
 -                      W_ThrowNewWeapon(self, self.weapon, FALSE, org, randomvec() * 125 + '0 0 200');
 -}
 -
  void PlayerCorpseDamage (entity inflictor, entity attacker, float damage, float deathtype, vector hitloc, vector force)
  {
        float take, save;
@@@ -424,7 -554,7 +424,7 @@@ void PlayerDamage (entity inflictor, en
                                        }
  
                                        if(sound_allowed(MSG_BROADCAST, attacker))
 -                                      if(!DEATH_ISWEAPON(deathtype, WEP_LASER) || attacker != self || self.health < 2 * autocvar_g_balance_laser_primary_damage * autocvar_g_balance_selfdamagepercent + 1)
 +                                      if(!DEATH_ISWEAPON(deathtype, WEP_BLASTER) || attacker != self || self.health < 2 * WEP_CVAR_PRI(blaster, damage) * autocvar_g_balance_selfdamagepercent + 1) // WEAPONTODO: create separate limit for pain notification with laser
                                        if(self.health > 1)
                                        // exclude pain sounds for laserjumps as long as you aren't REALLY low on health and would die of the next two
                                        {
                frag_deathtype = deathtype;
                MUTATOR_CALLHOOK(PlayerDies);
  
 -              weapon_action(self.weapon, WR_PLAYERDEATH);
 +              WEP_ACTION(self.weapon, WR_PLAYERDEATH);
  
                RemoveGrapplingHook(self);
  
                Portal_ClearAllLater(self);
  
-               if(IS_REAL_CLIENT(self))
-               {
-                       self.fixangle = TRUE;
-                       //msg_entity = self;
-                       //WriteByte (MSG_ONE, SVC_SETANGLE);
-                       //WriteAngle (MSG_ONE, self.v_angle_x);
-                       //WriteAngle (MSG_ONE, self.v_angle_y);
-                       //WriteAngle (MSG_ONE, 80);
-               }
+               self.fixangle = TRUE;
  
                if(defer_ClientKill_Now_TeamChange)
                        ClientKill_Now_TeamChange(); // can turn player into spectator
                // reset fields the weapons may use just in case
                for (j = WEP_FIRST; j <= WEP_LAST; ++j)
                {
 -                      weapon_action(j, WR_RESETPLAYER);
 +                      WEP_ACTION(j, WR_RESETPLAYER);
                        ATTACK_FINISHED_FOR(self, j) = 0;
                }
        }
@@@ -628,7 -750,7 +620,7 @@@ float Say(entity source, float teamsay
  //   0 = reject
  //  -1 = fake accept
  {
-       string msgstr, colorstr, cmsgstr, namestr, fullmsgstr, sourcemsgstr, fullcmsgstr, sourcecmsgstr;
+       string msgstr, colorstr, cmsgstr, namestr, fullmsgstr, sourcemsgstr, fullcmsgstr, sourcecmsgstr, colorprefix;
        float flood;
        var .float flood_field;
        entity head;
        else
                namestr = source.netname;
  
+       if(strdecolorize(namestr) == namestr)
+               colorprefix = "^3";
+       else
+               colorprefix = "^7";
        if(msgin != "")
        {
                if(privatesay)
                {
-                       msgstr = strcat("\{1}\{13}* ^3", namestr, "^3 tells you: ^7");
+                       msgstr = strcat("\{1}\{13}* ", colorprefix, namestr, "^3 tells you: ^7");
                        privatemsgprefixlen = strlen(msgstr);
                        msgstr = strcat(msgstr, msgin);
-                       cmsgstr = strcat(colorstr, "^3", namestr, "^3 tells you:\n^7", msgin);
+                       cmsgstr = strcat(colorstr, colorprefix, namestr, "^3 tells you:\n^7", msgin);
                        if(autocvar_g_chat_teamcolors)
                                privatemsgprefix = strcat("\{1}\{13}* ^3You tell ", playername(privatesay), ": ^7");
                        else
                }
                else if(teamsay)
                {
-                       msgstr = strcat("\{1}\{13}", colorstr, "(^3", namestr, colorstr, ") ^7", msgin);
-                       cmsgstr = strcat(colorstr, "(^3", namestr, colorstr, ")\n^7", msgin);
+                       msgstr = strcat("\{1}\{13}", colorstr, "(", colorprefix, namestr, colorstr, ") ^7", msgin);
+                       cmsgstr = strcat(colorstr, "(", colorprefix, namestr, colorstr, ")\n^7", msgin);
                }
                else
                {
-                       msgstr = strcat("\{1}", namestr, "^7: ", msgin);
+                       msgstr = strcat("\{1}", colorprefix, namestr, "^7: ", msgin);
                        cmsgstr = "";
                }
                msgstr = strcat(strreplace("\n", " ", msgstr), "\n"); // newlines only are good for centerprint
diff --combined qcsrc/server/g_damage.qc
index f93665c4ff9acc1716fdb1a05396a9c65735e9fa,42dee6a98fc479c89fb260bfaa593e5e7c831859..6f0b0e439395af19a78958908d26a636d5ec2a03
@@@ -115,7 -115,7 +115,7 @@@ void GiveFrags (entity attacker, entit
                else if(!(attacker.weapons & WepSet_FromWeapon(culprit)))
                        culprit = attacker.weapon;
  
 -              if(g_weaponarena_random_with_laser && culprit == WEP_LASER)
 +              if(g_weaponarena_random_with_laser && culprit == WEP_BLASTER) // WEAPONTODO: Shouldn't this be in a mutator?
                {
                        // no exchange
                }
@@@ -287,7 -287,7 +287,7 @@@ float Obituary_WeaponDeath
        if(death_weapon)
        {
                w_deathtype = deathtype;
 -              float death_message = weapon_action(death_weapon, ((murder) ? WR_KILLMESSAGE : WR_SUICIDEMESSAGE));
 +              float death_message = WEP_ACTION(death_weapon, ((murder) ? WR_KILLMESSAGE : WR_SUICIDEMESSAGE));
                w_deathtype = FALSE;
  
                if(death_message)
@@@ -817,10 -817,11 +817,10 @@@ void Damage (entity targ, entity inflic
  }
  
  float RadiusDamage_running;
 -float RadiusDamage (entity inflictor, entity attacker, float coredamage, float edgedamage, float rad, entity ignore, float forceintensity, float deathtype, entity directhitentity)
 +float RadiusDamageForSource (entity inflictor, vector inflictororigin, vector inflictorvelocity, entity attacker, float coredamage, float edgedamage, float rad, entity cantbe, entity mustbe, float inflictorselfdamage, float forceintensity, float deathtype, entity directhitentity)
        // Returns total damage applies to creatures
  {
        entity  targ;
 -      vector  blastorigin;
        vector  force;
        float   total_damage_to_creatures;
        entity  next;
        tfloordmg = autocvar_g_throughfloor_damage;
        tfloorforce = autocvar_g_throughfloor_force;
  
 -      blastorigin = (inflictor.origin + (inflictor.mins + inflictor.maxs) * 0.5);
        total_damage_to_creatures = 0;
  
        if(deathtype != (WEP_HOOK | HITTYPE_SECONDARY | HITTYPE_BOUNCE)) // only send gravity bomb damage once
                if(DEATH_WEAPONOF(deathtype) != WEP_TUBA) // do not send tuba damage (bandwidth hog)
                {
 -                      force = inflictor.velocity;
 +                      force = inflictorvelocity;
                        if(vlen(force) == 0)
                                force = '0 0 -1';
                        else
                                force = normalize(force);
                        if(forceintensity >= 0)
 -                              Damage_DamageInfo(blastorigin, coredamage, edgedamage, rad, forceintensity * force, deathtype, 0, attacker);
 +                              Damage_DamageInfo(inflictororigin, coredamage, edgedamage, rad, forceintensity * force, deathtype, 0, attacker);
                        else
 -                              Damage_DamageInfo(blastorigin, coredamage, edgedamage, -rad, (-forceintensity) * force, deathtype, 0, attacker);
 +                              Damage_DamageInfo(inflictororigin, coredamage, edgedamage, -rad, (-forceintensity) * force, deathtype, 0, attacker);
                }
  
        stat_damagedone = 0;
  
 -      targ = WarpZone_FindRadius (blastorigin, rad + MAX_DAMAGEEXTRARADIUS, FALSE);
 +      targ = WarpZone_FindRadius (inflictororigin, rad + MAX_DAMAGEEXTRARADIUS, FALSE);
        while (targ)
        {
                next = targ.chain;
 -              if (targ != inflictor)
 -                      if (ignore != targ) if(targ.takedamage)
 +              if ((targ != inflictor) || inflictorselfdamage)
 +              if (((cantbe != targ) && !mustbe) || (mustbe == targ))
 +              if (targ.takedamage)
 +              {
 +                      vector nearest;
 +                      vector diff;
 +                      float power;
 +
 +                      // LordHavoc: measure distance to nearest point on target (not origin)
 +                      // (this guarentees 100% damage on a touch impact)
 +                      nearest = targ.WarpZone_findradius_nearest;
 +                      diff = targ.WarpZone_findradius_dist;
 +                      // round up a little on the damage to ensure full damage on impacts
 +                      // and turn the distance into a fraction of the radius
 +                      power = 1 - ((vlen (diff) - bound(MIN_DAMAGEEXTRARADIUS, targ.damageextraradius, MAX_DAMAGEEXTRARADIUS)) / rad);
 +                      //bprint(" ");
 +                      //bprint(ftos(power));
 +                      //if (targ == attacker)
 +                      //      print(ftos(power), "\n");
 +                      if (power > 0)
                        {
 -                              vector nearest;
 -                              vector diff;
 -                              float power;
 -
 -                              // LordHavoc: measure distance to nearest point on target (not origin)
 -                              // (this guarentees 100% damage on a touch impact)
 -                              nearest = targ.WarpZone_findradius_nearest;
 -                              diff = targ.WarpZone_findradius_dist;
 -                              // round up a little on the damage to ensure full damage on impacts
 -                              // and turn the distance into a fraction of the radius
 -                              power = 1 - ((vlen (diff) - bound(MIN_DAMAGEEXTRARADIUS, targ.damageextraradius, MAX_DAMAGEEXTRARADIUS)) / rad);
 -                              //bprint(" ");
 -                              //bprint(ftos(power));
 -                              //if (targ == attacker)
 -                              //      print(ftos(power), "\n");
 -                              if (power > 0)
 +                              float finaldmg;
 +                              if (power > 1)
 +                                      power = 1;
 +                              finaldmg = coredamage * power + edgedamage * (1 - power);
 +                              if (finaldmg > 0)
                                {
 -                                      float finaldmg;
 -                                      if (power > 1)
 -                                              power = 1;
 -                                      finaldmg = coredamage * power + edgedamage * (1 - power);
 -                                      if (finaldmg > 0)
 -                                      {
 -                                              float a;
 -                                              float c;
 -                                              vector hitloc;
 -                                              vector myblastorigin;
 -                                              vector center;
 +                                      float a;
 +                                      float c;
 +                                      vector hitloc;
 +                                      vector myblastorigin;
 +                                      vector center;
  
 -                                              myblastorigin = WarpZone_TransformOrigin(targ, blastorigin);
 +                                      myblastorigin = WarpZone_TransformOrigin(targ, inflictororigin);
  
 -                                              // if it's a player, use the view origin as reference
 -                                              center = CENTER_OR_VIEWOFS(targ);
 +                                      // if it's a player, use the view origin as reference
 +                                      center = CENTER_OR_VIEWOFS(targ);
  
 -                                              force = normalize(center - myblastorigin);
 -                                              force = force * (finaldmg / coredamage) * forceintensity;
 -                                              hitloc = nearest;
 -
 -                                              if(targ != directhitentity)
 -                                              {
 -                                                      float hits;
 -                                                      float total;
 -                                                      float hitratio;
 -                                                      float mininv_f, mininv_d;
 +                                      force = normalize(center - myblastorigin);
 +                                      force = force * (finaldmg / coredamage) * forceintensity;
 +                                      hitloc = nearest;
  
 -                                                      // test line of sight to multiple positions on box,
 -                                                      // and do damage if any of them hit
 -                                                      hits = 0;
 +                                      if(targ != directhitentity)
 +                                      {
 +                                              float hits;
 +                                              float total;
 +                                              float hitratio;
 +                                              float mininv_f, mininv_d;
  
 -                                                      // we know: max stddev of hitratio = 1 / (2 * sqrt(n))
 -                                                      // so for a given max stddev:
 -                                                      // n = (1 / (2 * max stddev of hitratio))^2
 +                                              // test line of sight to multiple positions on box,
 +                                              // and do damage if any of them hit
 +                                              hits = 0;
  
 -                                                      mininv_d = (finaldmg * (1-tfloordmg)) / autocvar_g_throughfloor_damage_max_stddev;
 -                                                      mininv_f = (vlen(force) * (1-tfloorforce)) / autocvar_g_throughfloor_force_max_stddev;
 +                                              // we know: max stddev of hitratio = 1 / (2 * sqrt(n))
 +                                              // so for a given max stddev:
 +                                              // n = (1 / (2 * max stddev of hitratio))^2
  
 -                                                      if(autocvar_g_throughfloor_debug)
 -                                                              printf("THROUGHFLOOR: D=%f F=%f max(dD)=1/%f max(dF)=1/%f", finaldmg, vlen(force), mininv_d, mininv_f);
 +                                              mininv_d = (finaldmg * (1-tfloordmg)) / autocvar_g_throughfloor_damage_max_stddev;
 +                                              mininv_f = (vlen(force) * (1-tfloorforce)) / autocvar_g_throughfloor_force_max_stddev;
  
 -                                                      total = 0.25 * pow(max(mininv_f, mininv_d), 2);
 +                                              if(autocvar_g_throughfloor_debug)
 +                                                      printf("THROUGHFLOOR: D=%f F=%f max(dD)=1/%f max(dF)=1/%f", finaldmg, vlen(force), mininv_d, mininv_f);
  
 -                                                      if(autocvar_g_throughfloor_debug)
 -                                                              printf(" steps=%f", total);
  
 -                                                      if (IS_PLAYER(targ))
 -                                                              total = ceil(bound(autocvar_g_throughfloor_min_steps_player, total, autocvar_g_throughfloor_max_steps_player));
 -                                                      else
 -                                                              total = ceil(bound(autocvar_g_throughfloor_min_steps_other, total, autocvar_g_throughfloor_max_steps_other));
 +                                              total = 0.25 * pow(max(mininv_f, mininv_d), 2);
  
 -                                                      if(autocvar_g_throughfloor_debug)
 -                                                              printf(" steps=%f dD=%f dF=%f", total, finaldmg * (1-tfloordmg) / (2 * sqrt(total)), vlen(force) * (1-tfloorforce) / (2 * sqrt(total)));
 +                                              if(autocvar_g_throughfloor_debug)
 +                                                      printf(" steps=%f", total);
  
 -                                                      for(c = 0; c < total; ++c)
 -                                                      {
 -                                                              //traceline(targ.WarpZone_findradius_findorigin, nearest, MOVE_NOMONSTERS, inflictor);
 -                                                              WarpZone_TraceLine(blastorigin, WarpZone_UnTransformOrigin(targ, nearest), MOVE_NOMONSTERS, inflictor);
 -                                                              if (trace_fraction == 1 || trace_ent == targ)
 -                                                              {
 -                                                                      ++hits;
 -                                                                      if (hits > 1)
 -                                                                              hitloc = hitloc + nearest;
 -                                                                      else
 -                                                                              hitloc = nearest;
 -                                                              }
 -                                                              nearest_x = targ.origin_x + targ.mins_x + random() * targ.size_x;
 -                                                              nearest_y = targ.origin_y + targ.mins_y + random() * targ.size_y;
 -                                                              nearest_z = targ.origin_z + targ.mins_z + random() * targ.size_z;
 -                                                      }
  
 -                                                      nearest = hitloc * (1 / max(1, hits));
 -                                                      hitratio = (hits / total);
 -                                                      a = bound(0, tfloordmg + (1-tfloordmg) * hitratio, 1);
 -                                                      finaldmg = finaldmg * a;
 -                                                      a = bound(0, tfloorforce + (1-tfloorforce) * hitratio, 1);
 -                                                      force = force * a;
 +                                              if (IS_PLAYER(targ))
 +                                                      total = ceil(bound(autocvar_g_throughfloor_min_steps_player, total, autocvar_g_throughfloor_max_steps_player));
 +                                              else
 +                                                      total = ceil(bound(autocvar_g_throughfloor_min_steps_other, total, autocvar_g_throughfloor_max_steps_other));
  
 -                                                      if(autocvar_g_throughfloor_debug)
 -                                                              printf(" D=%f F=%f\n", finaldmg, vlen(force));
 -                                              }
 +                                              if(autocvar_g_throughfloor_debug)
 +                                                      printf(" steps=%f dD=%f dF=%f", total, finaldmg * (1-tfloordmg) / (2 * sqrt(total)), vlen(force) * (1-tfloorforce) / (2 * sqrt(total)));
  
 -                                              // laser force adjustments :P
 -                                              if(DEATH_WEAPONOF(deathtype) == WEP_LASER)
 +                                              for(c = 0; c < total; ++c)
                                                {
 -                                                      if (targ == attacker)
 -                                                      {
 -                                                              vector vel;
 -
 -                                                              float force_zscale;
 -                                                              float force_velocitybiasramp;
 -                                                              float force_velocitybias;
 -
 -                                                              force_velocitybiasramp = autocvar_sv_maxspeed;
 -                                                              if(deathtype & HITTYPE_SECONDARY)
 -                                                              {
 -                                                                      force_zscale = autocvar_g_balance_laser_secondary_force_zscale;
 -                                                                      force_velocitybias = autocvar_g_balance_laser_secondary_force_velocitybias;
 -                                                              }
 -                                                              else
 -                                                              {
 -                                                                      force_zscale = autocvar_g_balance_laser_primary_force_zscale;
 -                                                                      force_velocitybias = autocvar_g_balance_laser_primary_force_velocitybias;
 -                                                              }
 -
 -                                                              vel = targ.velocity;
 -                                                              vel_z = 0;
 -                                                              vel = normalize(vel) * bound(0, vlen(vel) / force_velocitybiasramp, 1) * force_velocitybias;
 -                                                              force =
 -                                                                      vlen(force)
 -                                                                      *
 -                                                                      normalize(normalize(force) + vel);
 -
 -                                                              force_z *= force_zscale;
 -                                                      }
 -                                                      else
 +                                                      //traceline(targ.WarpZone_findradius_findorigin, nearest, MOVE_NOMONSTERS, inflictor);
 +                                                      WarpZone_TraceLine(inflictororigin, WarpZone_UnTransformOrigin(targ, nearest), MOVE_NOMONSTERS, inflictor);
 +                                                      if (trace_fraction == 1 || trace_ent == targ)
                                                        {
 -                                                              if(deathtype & HITTYPE_SECONDARY)
 -                                                              {
 -                                                                      force *= autocvar_g_balance_laser_secondary_force_other_scale;
 -                                                              }
 +                                                              ++hits;
 +                                                              if (hits > 1)
 +                                                                      hitloc = hitloc + nearest;
                                                                else
 -                                                              {
 -                                                                      force *= autocvar_g_balance_laser_primary_force_other_scale;
 -                                                              }
 +                                                                      hitloc = nearest;
                                                        }
 +                                                      nearest_x = targ.origin_x + targ.mins_x + random() * targ.size_x;
 +                                                      nearest_y = targ.origin_y + targ.mins_y + random() * targ.size_y;
 +                                                      nearest_z = targ.origin_z + targ.mins_z + random() * targ.size_z;
                                                }
  
 -                                              //if (targ == attacker)
 -                                              //{
 -                                              //      print("hits ", ftos(hits), " / ", ftos(total));
 -                                              //      print(" finaldmg ", ftos(finaldmg), " force ", vtos(force));
 -                                              //      print(" (", ftos(a), ")\n");
 -                                              //}
 -                                              if(finaldmg || vlen(force))
 -                                              {
 -                                                      if(targ.iscreature)
 -                                                      {
 -                                                              total_damage_to_creatures += finaldmg;
 +                                              nearest = hitloc * (1 / max(1, hits));
 +                                              hitratio = (hits / total);
 +                                              a = bound(0, tfloordmg + (1-tfloordmg) * hitratio, 1);
 +                                              finaldmg = finaldmg * a;
 +                                              a = bound(0, tfloorforce + (1-tfloorforce) * hitratio, 1);
 +                                              force = force * a;
  
 -                                                              if(accuracy_isgooddamage(attacker, targ))
 -                                                                      stat_damagedone += finaldmg;
 -                                                      }
 +                                              if(autocvar_g_throughfloor_debug)
 +                                                      printf(" D=%f F=%f\n", finaldmg, vlen(force));
 +                                      }
  
 -                                                      if(targ == directhitentity || DEATH_ISSPECIAL(deathtype))
 -                                                              Damage (targ, inflictor, attacker, finaldmg, deathtype, nearest, force);
 -                                                      else
 -                                                              Damage (targ, inflictor, attacker, finaldmg, deathtype | HITTYPE_SPLASH, nearest, force);
 +                                      //if (targ == attacker)
 +                                      //{
 +                                      //      print("hits ", ftos(hits), " / ", ftos(total));
 +                                      //      print(" finaldmg ", ftos(finaldmg), " force ", vtos(force));
 +                                      //      print(" (", ftos(a), ")\n");
 +                                      //}
 +                                      if(finaldmg || vlen(force))
 +                                      {
 +                                              if(targ.iscreature)
 +                                              {
 +                                                      total_damage_to_creatures += finaldmg;
 +
 +                                                      if(accuracy_isgooddamage(attacker, targ))
 +                                                              stat_damagedone += finaldmg;
                                                }
 +
 +                                              if(targ == directhitentity || DEATH_ISSPECIAL(deathtype))
 +                                                      Damage (targ, inflictor, attacker, finaldmg, deathtype, nearest, force);
 +                                              else
 +                                                      Damage (targ, inflictor, attacker, finaldmg, deathtype | HITTYPE_SPLASH, nearest, force);
                                        }
                                }
                        }
 +              }
                targ = next;
        }
  
        return total_damage_to_creatures;
  }
  
 +float RadiusDamage (entity inflictor, entity attacker, float coredamage, float edgedamage, float rad, entity cantbe, entity mustbe, float forceintensity, float deathtype, entity directhitentity)
 +{
 +      return RadiusDamageForSource (inflictor, (inflictor.origin + (inflictor.mins + inflictor.maxs) * 0.5), inflictor.velocity, attacker, coredamage, edgedamage, rad, cantbe, mustbe, FALSE, forceintensity, deathtype, directhitentity);
 +}
 +
  .float fire_damagepersec;
  .float fire_endtime;
  .float fire_deathtype;
@@@ -1177,6 -1217,7 +1177,7 @@@ void Fire_ApplyDamage(entity e
        e.fire_hitsound = TRUE;
  
        if (!IS_INDEPENDENT_PLAYER(e))
+       if(!e.freezetag_frozen)
        FOR_EACH_PLAYER(other) if(e != other)
        {
                if(IS_PLAYER(other))
diff --combined qcsrc/server/g_hook.qc
index 7b0648f705d28e2bbd2a6beeb34efe18f68da1f8,4e1b634008fb6d063f760a4f2f747af352363bcd..90b91ad3d0880158f339c8c344e9985a4688592f
@@@ -335,7 -335,7 +335,7 @@@ void FireGrapplingHook (void
  
        missile.state = 0; // not latched onto anything
  
 -      W_SetupProjectileVelocityEx(missile, v_forward, v_up, autocvar_g_balance_grapplehook_speed_fly, 0, 0, 0, FALSE);
 +      W_SetupProjVelocity_Explicit(missile, v_forward, v_up, autocvar_g_balance_grapplehook_speed_fly, 0, 0, 0, FALSE);
  
        missile.angles = vectoangles (missile.velocity);
        //missile.glow_color = 250; // 244, 250
@@@ -383,7 -383,7 +383,7 @@@ void GrapplingHookFrame(
                // offhand hook controls
                if(self.BUTTON_HOOK)
                {
-                       if (!(self.hook || (self.hook_state & HOOK_WAITING_FOR_RELEASE)))
+                       if (!(self.hook || (self.hook_state & HOOK_WAITING_FOR_RELEASE)) && (time > self.hook_refire))
                        {
                                self.hook_state |= HOOK_FIRING;
                                self.hook_state |= HOOK_WAITING_FOR_RELEASE;
                        RemoveGrapplingHook(self);
                FireGrapplingHook();
                self.hook_state &= ~HOOK_FIRING;
+               self.hook_refire = max(self.hook_refire, time + autocvar_g_balance_grapplehook_refire * W_WeaponRateFactor());
        }
        else if(self.hook_state & HOOK_REMOVING)
        {
@@@ -475,7 -476,7 +476,7 @@@ void GrappleHookInit(
        }
        else
        {
 -              weapon_action(WEP_HOOK, WR_PRECACHE);
 +              WEP_ACTION(WEP_HOOK, WR_INIT);
                hook_shotorigin[0] = shotorg_adjust_values(CL_Weapon_GetShotOrg(WEP_HOOK), FALSE, FALSE, 1);
                hook_shotorigin[1] = shotorg_adjust_values(CL_Weapon_GetShotOrg(WEP_HOOK), FALSE, FALSE, 2);
                hook_shotorigin[2] = shotorg_adjust_values(CL_Weapon_GetShotOrg(WEP_HOOK), FALSE, FALSE, 3);
diff --combined qcsrc/server/g_world.qc
index d1306f5c26b44460c80811802fbb344bad597f29,f635bff2a2f6399e209588a9487536201c340646..b7c970715fe7e2e175d651bd98fc3b176911a5f6
@@@ -652,6 -652,8 +652,6 @@@ void spawnfunc_worldspawn (void
        InitGameplayMode();
        readlevelcvars();
        GrappleHookInit();
 -      ElectroInit();
 -      LaserInit();
  
        player_count = 0;
        bot_waypoints_for_items = autocvar_g_waypoints_for_items;
        addstat(STAT_SUPERWEAPONS_FINISHED, AS_FLOAT, superweapons_finished);
        addstat(STAT_PRESSED_KEYS, AS_FLOAT, pressedkeys);
        addstat(STAT_FUEL, AS_INT, ammo_fuel);
 +      addstat(STAT_PLASMA, AS_INT, ammo_plasma);
        addstat(STAT_SHOTORG, AS_INT, stat_shotorg);
        addstat(STAT_LEADLIMIT, AS_FLOAT, stat_leadlimit);
        addstat(STAT_WEAPON_CLIPLOAD, AS_INT, clip_load);
        addstat(STAT_TYPEHIT_TIME, AS_FLOAT, typehit_time);
        addstat(STAT_LAYED_MINES, AS_INT, minelayer_mines);
  
 -      addstat(STAT_NEX_CHARGE, AS_FLOAT, nex_charge);
 -      addstat(STAT_NEX_CHARGEPOOL, AS_FLOAT, nex_chargepool_ammo);
 +      addstat(STAT_VORTEX_CHARGE, AS_FLOAT, vortex_charge);
 +      addstat(STAT_VORTEX_CHARGEPOOL, AS_FLOAT, vortex_chargepool_ammo);
  
        addstat(STAT_HAGAR_LOAD, AS_INT, hagar_load);
  
@@@ -1575,7 -1576,7 +1575,7 @@@ float InitiateSuddenDeath(
        // - for this timelimit_overtime needs to be >0 of course
        // - also check the winning condition calculated in the previous frame and only add normal overtime
        //   again, if at the point at which timelimit would be extended again, still no winner was found
-       if (!autocvar_g_campaign && (checkrules_overtimesadded >= 0) && (checkrules_overtimesadded < autocvar_timelimit_overtimes) && autocvar_timelimit_overtime && !(g_race && !g_race_qualifying))
+       if (!autocvar_g_campaign && (checkrules_overtimesadded >= 0) && (checkrules_overtimesadded < autocvar_timelimit_overtimes || autocvar_timelimit_overtimes < 0) && autocvar_timelimit_overtime && !(g_race && !g_race_qualifying))
        {
                return 1; // need to call InitiateOvertime later
        }
@@@ -2729,6 -2730,8 +2729,8 @@@ string GotoMap(string m
  
  void EndFrame()
  {
+       anticheat_endframe();
        float altime;
        FOR_EACH_REALCLIENT(self)
        {
index 9d7ee17f6e620058d192951e0f5688fb1188538c,78a08c551e540dc77a3dd5c2e8b4d56bebdb3ddd..4ee54f0493468291e82e1b4c89b98b46c2c23520
@@@ -103,7 -103,7 +103,7 @@@ MUTATOR_HOOKABLE(ForbidThrowCurrentWeap
        // returns 1 if throwing the current weapon shall not be allowed
  
  MUTATOR_HOOKABLE(SetStartItems);
 -      // adjusts {warmup_}start_{items,weapons,ammo_{cells,rockets,nails,shells,fuel}}
 +      // adjusts {warmup_}start_{items,weapons,ammo_{cells,plasma,rockets,nails,shells,fuel}}
  
  MUTATOR_HOOKABLE(BuildMutatorsString);
        // appends ":mutatorname" to ret_string for logging
@@@ -353,7 -353,7 +353,7 @@@ MUTATOR_HOOKABLE(ClientConnect)
        // called at when a player connect
        entity self;    // player
  
- MUTATOR_HOOKABLE(HavocBot_ChooseRule);
+ MUTATOR_HOOKABLE(HavocBot_ChooseRole);
        entity self;
  
  MUTATOR_HOOKABLE(AccuracyTargetValid);
index 408ce34f27a91d625de2afb69d8afa830af029e0,014d37ec20169fd6497b6f3b50764b51deb1d91c..176fb1eac5e9fcee4270c01fdc705dd25e28d3f8
@@@ -142,7 -142,7 +142,7 @@@ void GiveBall(entity plyr, entity ball
        self.weaponentity.weapons = self.weapons;
        self.weaponentity.switchweapon = self.weapon;
        self.weapons = WEPSET_PORTO;
 -      weapon_action(WEP_PORTO, WR_RESETPLAYER);
 +      WEP_ACTION(WEP_PORTO, WR_RESETPLAYER);
        self.switchweapon = WEP_PORTO;
        W_SwitchWeapon(WEP_PORTO);
        self = ownr;
@@@ -457,11 -457,21 +457,21 @@@ void nb_spawnteams(void
        }
  }
  
+ // scoreboard setup
+ void nb_ScoreRules(float teams)
+ {
+       ScoreRules_basics(teams, 0, 0, TRUE);
+       ScoreInfo_SetLabel_TeamScore(   ST_NEXBALL_GOALS,  "goals", SFL_SORT_PRIO_PRIMARY);
+       ScoreInfo_SetLabel_PlayerScore( SP_NEXBALL_GOALS,  "goals", SFL_SORT_PRIO_PRIMARY);
+       ScoreInfo_SetLabel_PlayerScore(SP_NEXBALL_FAULTS, "faults", SFL_SORT_PRIO_SECONDARY | SFL_LOWER_IS_BETTER);
+       ScoreRules_basics_end();
+ }
  void nb_delayedinit(void)
  {
        if(find(world, classname, "nexball_team") == world)
                nb_spawnteams();
-       ScoreRules_nexball(nb_teams);
+       nb_ScoreRules(nb_teams);
  }
  
  
  
  void SpawnBall(void)
  {
-       if(!g_nexball)
-       {
-               remove(self);
-               return;
-       }
+       if(!g_nexball) { remove(self); return; }
  
  //    balls += 4; // using the remaining bits to count balls will leave more than the max edict count, so it's fine
  
@@@ -559,14 -565,28 +565,28 @@@ void spawnfunc_nexball_football(void
        SpawnBall();
  }
  
+ float nb_Goal_Customize()
+ {
+       entity e, wp_owner;
+       e = WaypointSprite_getviewentity(other);
+       wp_owner = self.owner;
+       if(SAME_TEAM(e, wp_owner)) { return FALSE; }
+       return TRUE;
+ }
  void SpawnGoal(void)
  {
-       if(!g_nexball)
+       if(!g_nexball) { remove(self); return; }
+       EXACTTRIGGER_INIT;
+       if(self.team != GOAL_OUT && Team_TeamToNumber(self.team) != -1)
        {
-               remove(self);
-               return;
+               WaypointSprite_SpawnFixed("goal", (self.absmin + self.absmax) * 0.5, self, sprite, RADARICON_NONE, ((self.team) ? Team_ColorRGB(self.team) : '1 0.5 0'));
+               self.sprite.customizeentityforclient = nb_Goal_Customize;
        }
-       EXACTTRIGGER_INIT;
        self.classname = "nexball_goal";
        if(self.noise == "")
                self.noise = "ctf/respawn.wav";
@@@ -674,7 -694,7 +694,7 @@@ void W_Nexball_Touch(void
  
        PROJECTILE_TOUCH;
        if(attacker.team != other.team || autocvar_g_nexball_basketball_teamsteal)
-               if((ball = other.ballcarried) && (IS_PLAYER(attacker)))
+               if((ball = other.ballcarried) && !other.deadflag && (IS_PLAYER(attacker)))
                {
                        other.velocity = other.velocity + normalize(self.velocity) * other.damageforcescale * autocvar_g_balance_nexball_secondary_force;
                        other.flags &= ~FL_ONGROUND;
                                LogNB("stole", attacker);
                                sound(other, CH_TRIGGER, ball.noise2, VOL_BASE, ATTEN_NORM);
  
-                               if(attacker.team == other.team && time > attacker.teamkill_complain)
+                               if(SAME_TEAM(attacker, other) && time > attacker.teamkill_complain)
                                {
                                        attacker.teamkill_complain = time + 5;
                                        attacker.teamkill_soundtime = time + 0.4;
@@@ -760,11 -780,11 +780,11 @@@ void W_Nexball_Attack2(void
        missile.movetype = MOVETYPE_FLY;
        PROJECTILE_MAKETRIGGER(missile);
  
-       setmodel(missile, "models/elaser.mdl");  // precision set below
+       //setmodel(missile, "models/elaser.mdl");  // precision set below
        setsize(missile, '0 0 0', '0 0 0');
        setorigin(missile, w_shotorg);
  
 -      W_SetupProjectileVelocity(missile, autocvar_g_balance_nexball_secondary_speed, 0);
 +      W_SetupProjVelocity_Basic(missile, autocvar_g_balance_nexball_secondary_speed, 0);
        missile.angles = vectoangles(missile.velocity);
        missile.touch = W_Nexball_Touch;
        missile.think = SUB_Remove;
  
        missile.effects = EF_BRIGHTFIELD | EF_LOWPRECISION;
        missile.flags = FL_PROJECTILE;
+       CSQCProjectile(missile, TRUE, PROJECTILE_ELECTRO, TRUE);
  }
  
  float ball_customize()
@@@ -833,7 -855,7 +855,7 @@@ float w_nexball_weapon(float req
                        weapon_thinkf(WFRAME_FIRE1, autocvar_g_balance_nexball_primary_animtime, w_ready);
                }
        }
 -      else if(req == WR_PRECACHE)
 +      else if(req == WR_INIT)
        {
                precache_model("models/weapons/g_porto.md3");
                precache_model("models/weapons/v_porto.md3");
        }
        else if(req == WR_SETUP)
        {
 -              weapon_setup(WEP_PORTO);
 +              //weapon_setup(WEP_PORTO);
        }
        // No need to check WR_CHECKAMMO* or WR_AIM, it should always return TRUE
        return TRUE;
@@@ -859,18 -881,6 +881,6 @@@ MUTATOR_HOOKFUNCTION(nexball_BallDrop
        return 0;
  }
  
- MUTATOR_HOOKFUNCTION(nexball_BuildMutatorsString)
- {
-       ret_string = strcat(ret_string, ":NB");
-       return 0;
- }
- MUTATOR_HOOKFUNCTION(nexball_BuildMutatorsPrettyString)
- {
-       ret_string = strcat(ret_string, ", NexBall");
-       return 0;
- }
  MUTATOR_HOOKFUNCTION(nexball_PlayerPreThink)
  {
        makevectors(self.v_angle);
                        if(self.weaponentity.weapons)
                        {
                                self.weapons = self.weaponentity.weapons;
 -                              weapon_action(WEP_PORTO, WR_RESETPLAYER);
 +                              WEP_ACTION(WEP_PORTO, WR_RESETPLAYER);
                                self.switchweapon = self.weaponentity.switchweapon;
                                W_SwitchWeapon(self.switchweapon);
  
@@@ -947,6 -957,16 +957,16 @@@ MUTATOR_HOOKFUNCTION(nexball_PlayerSpaw
        return FALSE;
  }
  
+ MUTATOR_HOOKFUNCTION(nexball_PlayerPhysics)
+ {
+       if(self.ballcarried)
+       {
+               self.stat_sv_airspeedlimit_nonqw *= autocvar_g_nexball_basketball_carrier_highspeed;
+               self.stat_sv_maxspeed *= autocvar_g_nexball_basketball_carrier_highspeed;
+       }
+       return FALSE;
+ }
  MUTATOR_HOOKFUNCTION(nexball_SetStartItems)
  {
        start_items |= IT_UNLIMITED_SUPERWEAPONS; // FIXME BAD BAD BAD BAD HACK, NEXBALL SHOULDN'T ABUSE PORTO'S WEAPON SLOT
        return FALSE;
  }
  
 -      if(self.weapon == WEP_GRENADE_LAUNCHER)
+ MUTATOR_HOOKFUNCTION(nexball_ForbidThrowing)
+ {
 -      if(self.weapon == WEP_GRENADE_LAUNCHER)
++      if(self.weapon == WEP_MORTAR)
+               return TRUE;
+       return FALSE;
+ }
+ MUTATOR_HOOKFUNCTION(nexball_FilterItem)
+ {
+       if(self.classname == "droppedweapon")
++      if(self.weapon == WEP_MORTAR)
+               return TRUE;
+       return FALSE;
+ }
  MUTATOR_DEFINITION(gamemode_nexball)
  {
        MUTATOR_HOOK(PlayerDies, nexball_BallDrop, CBC_ORDER_ANY);
        MUTATOR_HOOK(MakePlayerObserver, nexball_BallDrop, CBC_ORDER_ANY);
        MUTATOR_HOOK(ClientDisconnect, nexball_BallDrop, CBC_ORDER_ANY);
-       MUTATOR_HOOK(BuildMutatorsPrettyString, nexball_BuildMutatorsPrettyString, CBC_ORDER_ANY);
-       MUTATOR_HOOK(BuildMutatorsString, nexball_BuildMutatorsString, CBC_ORDER_ANY);
        MUTATOR_HOOK(PlayerSpawn, nexball_PlayerSpawn, CBC_ORDER_ANY);
        MUTATOR_HOOK(PlayerPreThink, nexball_PlayerPreThink, CBC_ORDER_ANY);
+       MUTATOR_HOOK(PlayerPhysics, nexball_PlayerPhysics, CBC_ORDER_ANY);
        MUTATOR_HOOK(SetStartItems, nexball_SetStartItems, CBC_ORDER_ANY);
+       MUTATOR_HOOK(ForbidThrowCurrentWeapon, nexball_ForbidThrowing, CBC_ORDER_ANY);
+       MUTATOR_HOOK(FilterItem, nexball_FilterItem, CBC_ORDER_ANY);
  
        MUTATOR_ONADD
        {
                g_nexball_meter_period = rint(g_nexball_meter_period * 32) / 32; //Round to 1/32ths to send as a byte multiplied by 32
                addstat(STAT_NB_METERSTART, AS_FLOAT, metertime);
  
 -              w_porto(WR_PRECACHE); // abuse
++              W_Porto(WR_INIT); // abuse
                // General settings
                /*
                CVTOV(g_nexball_football_boost_forward);   //100
index 943f01ae392a2ef0620923b1f7355e9c81c7c3eb,6e7c35b6a662f7f75ac5d6a5578d7da56517f103..543c1cf0bb66919b8576259587a058f8e7a2fd99
@@@ -80,7 -80,6 +80,7 @@@ void spawn_tdeath(vector v0, entity e, 
  #define TELEPORT_NORMAL 1 // play sounds/effects etc
  #define TELEPORT_SIMPLE 2 // only do teleport, nothing special
  
 +void Reset_ArcBeam(entity player, vector forward);
  void TeleportPlayer(entity teleporter, entity player, vector to, vector to_angles, vector to_velocity, vector telefragmin, vector telefragmax, float tflags)
  {
        entity telefragger;
        player.velocity = to_velocity;
        BITXOR_ASSIGN(player.effects, EF_TELEPORT_BIT);
  
 +      makevectors(player.angles);
 +      Reset_ArcBeam(player, v_forward);
        UpdateCSQCProjectileAfterTeleport(player);
  
        if(IS_PLAYER(player))
@@@ -340,9 -337,13 +340,15 @@@ void spawnfunc_trigger_teleport (void
  
  void WarpZone_PostTeleportPlayer_Callback(entity pl)
  {
 +      makevectors(pl.angles);
 +      Reset_ArcBeam(pl, v_forward);
        UpdateCSQCProjectileAfterTeleport(pl);
+       {
+               entity oldself = self;
+               self = pl;
+               anticheat_fixangle();
+               self = oldself;
+       }
        // "disown" projectiles after teleport
        if(pl.owner)
        if(pl.owner == pl.realowner)
index 279537f26bc881057022e6fd5dc3867da0bb6728,0000000000000000000000000000000000000000..685741dabc0cf4be042412decea63555fe344ca7
mode 100644,000000..100644
--- /dev/null
@@@ -1,91 -1,0 +1,91 @@@
-               if(IS_CLIENT(trace_ent))
 +vector W_HitPlotUnnormalizedUntransform(vector screenforward, vector screenright, vector screenup, vector v)
 +{
 +      vector ret;
 +      ret_x = screenright * v;
 +      ret_y = screenup * v;
 +      ret_z = screenforward * v;
 +      return ret;
 +}
 +
 +vector W_HitPlotNormalizedUntransform(vector org, entity targ, vector screenforward, vector screenright, vector screenup, vector v)
 +{
 +      float i, j, k;
 +      vector mi, ma, thisv, myv, ret;
 +
 +      myv = W_HitPlotUnnormalizedUntransform(screenforward, screenright, screenup, org);
 +
 +      // x = 0..1 relative to hitbox; y = 0..1 relative to hitbox; z = distance
 +
 +      mi = ma = targ.origin + 0.5 * (targ.mins + targ.maxs);
 +      for(i = 0; i < 2; ++i) for(j = 0; j < 2; ++j) for(k = 0; k < 2; ++k)
 +      {
 +              thisv = targ.origin;
 +              if(i) thisv_x += targ.maxs_x; else thisv_x += targ.mins_x;
 +              if(j) thisv_y += targ.maxs_y; else thisv_y += targ.mins_y;
 +              if(k) thisv_z += targ.maxs_z; else thisv_z += targ.mins_z;
 +              thisv = W_HitPlotUnnormalizedUntransform(screenforward, screenright, screenup, thisv);
 +              if(i || j || k)
 +              {
 +                      if(mi_x > thisv_x) mi_x = thisv_x; if(ma_x < thisv_x) ma_x = thisv_x;
 +                      if(mi_y > thisv_y) mi_y = thisv_y; if(ma_y < thisv_y) ma_y = thisv_y;
 +                      //if(mi_z > thisv_z) mi_z = thisv_z; if(ma_z < thisv_z) ma_y = thisv_z;
 +              }
 +              else
 +              {
 +                      // first run
 +                      mi = ma = thisv;
 +              }
 +      }
 +
 +      thisv = W_HitPlotUnnormalizedUntransform(screenforward, screenright, screenup, v);
 +      ret_x = (thisv_x - mi_x) / (ma_x - mi_x);
 +      ret_y = (thisv_y - mi_y) / (ma_y - mi_y);
 +      ret_z = thisv_z - myv_z;
 +      return ret;
 +}
 +
 +void W_HitPlotAnalysis(entity player, vector screenforward, vector screenright, vector screenup)
 +{
 +      vector hitplot;
 +      vector org;
 +      float lag;
 +
 +      if(player.hitplotfh >= 0)
 +      {
 +              lag = ANTILAG_LATENCY(player);
 +              if(lag < 0.001)
 +                      lag = 0;
 +              if(!IS_REAL_CLIENT(player))
 +                      lag = 0; // only antilag for clients
 +
 +              org = player.origin + player.view_ofs;
 +              traceline_antilag_force(player, org, org + screenforward * MAX_SHOT_DISTANCE, MOVE_NORMAL, player, lag);
++              if(IS_CLIENT(trace_ent) || (trace_ent.flags & FL_MONSTER))
 +              {
 +                      antilag_takeback(trace_ent, time - lag);
 +                      hitplot = W_HitPlotNormalizedUntransform(org, trace_ent, screenforward, screenright, screenup, trace_endpos);
 +                      antilag_restore(trace_ent);
 +                      fputs(player.hitplotfh, strcat(ftos(hitplot_x), " ", ftos(hitplot_y), " ", ftos(hitplot_z), " ", ftos(player.switchweapon), "\n"));
 +                      //print(strcat(ftos(hitplot_x), " ", ftos(hitplot_y), " ", ftos(hitplot_z), "\n"));
 +              }
 +      }
 +}
 +
 +void W_HitPlotOpen(entity player)
 +{
 +      if(autocvar_g_hitplots || strstrofs(strcat(" ", autocvar_g_hitplots_individuals, " "), strcat(" ", player.netaddress, " "), 0) >= 0)
 +      {
 +              player.hitplotfh = fopen(strcat("hits-", matchid, "-", player.netaddress, "-", ftos(player.playerid), ".plot"), FILE_WRITE);
 +              fputs(player.hitplotfh, strcat("#name ", player.netname, "\n"));
 +      }
 +      else { player.hitplotfh = -1; }
 +}
 +
 +void W_HitPlotClose(entity player)
 +{
 +      if(player.hitplotfh >= 0)
 +      {
 +              fclose(player.hitplotfh);
 +              player.hitplotfh = -1;
 +      }
 +}
index 75cf5b1d4c8fa016a07c4cabc6426a6253a9b9da,0000000000000000000000000000000000000000..755ab59e593e4906319debced03fd205fb16ca8e
mode 100644,000000..100644
--- /dev/null
@@@ -1,462 -1,0 +1,470 @@@
 +// this function calculates w_shotorg and w_shotdir based on the weapon model
 +// offset, trueaim and antilag, and won't put w_shotorg inside a wall.
 +// make sure you call makevectors first (FIXME?)
 +void W_SetupShot_Dir_ProjectileSize_Range(entity ent, vector s_forward, vector mi, vector ma, float antilag, float recoil, string snd, float chan, float maxdamage, float range)
 +{
 +      float nudge = 1; // added to traceline target and subtracted from result  TOOD(divVerent): do we still need this? Doesn't the engine do this now for us?
 +      float oldsolid;
 +      vector vecs, dv;
 +      oldsolid = ent.dphitcontentsmask;
 +      if(ent.weapon == WEP_RIFLE)
 +              ent.dphitcontentsmask = DPCONTENTS_BODY | DPCONTENTS_CORPSE;
 +      else
 +              ent.dphitcontentsmask = DPCONTENTS_SOLID | DPCONTENTS_BODY | DPCONTENTS_CORPSE;
 +      if(antilag)
 +              WarpZone_traceline_antilag(world, ent.origin + ent.view_ofs, ent.origin + ent.view_ofs + s_forward * range, MOVE_NORMAL, ent, ANTILAG_LATENCY(ent));
 +              // passing world, because we do NOT want it to touch dphitcontentsmask
 +      else
 +              WarpZone_TraceLine(ent.origin + ent.view_ofs, ent.origin + ent.view_ofs + s_forward * range, MOVE_NOMONSTERS, ent);
 +      ent.dphitcontentsmask = DPCONTENTS_SOLID | DPCONTENTS_BODY | DPCONTENTS_CORPSE;
 +
 +      vector vf, vr, vu;
 +      vf = v_forward;
 +      vr = v_right;
 +      vu = v_up;
 +      w_shotend = WarpZone_UnTransformOrigin(WarpZone_trace_transform, trace_endpos); // warpzone support
 +      v_forward = vf;
 +      v_right = vr;
 +      v_up = vu;
 +
 +      // un-adjust trueaim if shotend is too close
 +      if(vlen(w_shotend - (ent.origin + ent.view_ofs)) < autocvar_g_trueaim_minrange)
 +              w_shotend = ent.origin + ent.view_ofs + s_forward * autocvar_g_trueaim_minrange;
 +
 +      // track max damage
 +      if(accuracy_canbegooddamage(ent))
 +              accuracy_add(ent, ent.weapon, maxdamage, 0);
 +
 +      W_HitPlotAnalysis(ent, v_forward, v_right, v_up);
 +
 +      if(ent.weaponentity.movedir_x > 0)
 +              vecs = ent.weaponentity.movedir;
 +      else
 +              vecs = '0 0 0';
 +
 +      dv = v_right * -vecs_y + v_up * vecs_z;
 +      w_shotorg = ent.origin + ent.view_ofs + dv;
 +
 +      // now move the shotorg forward as much as requested if possible
 +      if(antilag)
 +      {
 +              if(ent.antilag_debug)
 +                      tracebox_antilag(ent, w_shotorg, mi, ma, w_shotorg + v_forward * (vecs_x + nudge), MOVE_NORMAL, ent, ent.antilag_debug);
 +              else
 +                      tracebox_antilag(ent, w_shotorg, mi, ma, w_shotorg + v_forward * (vecs_x + nudge), MOVE_NORMAL, ent, ANTILAG_LATENCY(ent));
 +      }
 +      else
 +              tracebox(w_shotorg, mi, ma, w_shotorg + v_forward * (vecs_x + nudge), MOVE_NORMAL, ent);
 +      w_shotorg = trace_endpos - v_forward * nudge;
 +      // calculate the shotdir from the chosen shotorg
 +      w_shotdir = normalize(w_shotend - w_shotorg);
 +
 +      //vector prevdir = w_shotdir;
 +      //vector prevorg = w_shotorg;
 +      //vector prevend = w_shotend; 
 +
 +      if (antilag)
 +      if (!ent.cvar_cl_noantilag)
 +      {
 +              if (autocvar_g_antilag == 1) // switch to "ghost" if not hitting original
 +              {
 +                      traceline(w_shotorg, w_shotorg + w_shotdir * range, MOVE_NORMAL, ent);
 +                      if (!trace_ent.takedamage)
 +                      {
 +                              traceline_antilag_force (ent, w_shotorg, w_shotorg + w_shotdir * range, MOVE_NORMAL, ent, ANTILAG_LATENCY(ent));
 +                              if (trace_ent.takedamage && IS_PLAYER(trace_ent))
 +                              {
 +                                      entity e;
 +                                      e = trace_ent;
 +                                      traceline(w_shotorg, e.origin, MOVE_NORMAL, ent);
 +                                      if(trace_ent == e)
 +                                              w_shotdir = normalize(trace_ent.origin - w_shotorg);
 +                              }
 +                      }
 +              }
 +              else if(autocvar_g_antilag == 3) // client side hitscan
 +              {
 +                      // this part MUST use prydon cursor
 +                      if (ent.cursor_trace_ent)                 // client was aiming at someone
 +                      if (ent.cursor_trace_ent != ent)         // just to make sure
 +                      if (ent.cursor_trace_ent.takedamage)      // and that person is killable
 +                      if (IS_PLAYER(ent.cursor_trace_ent)) // and actually a player
 +                      {
 +                              // verify that the shot would miss without antilag
 +                              // (avoids an issue where guns would always shoot at their origin)
 +                              traceline(w_shotorg, w_shotorg + w_shotdir * range, MOVE_NORMAL, ent);
 +                              if (!trace_ent.takedamage)
 +                              {
 +                                      // verify that the shot would hit if altered
 +                                      traceline(w_shotorg, ent.cursor_trace_ent.origin, MOVE_NORMAL, ent);
 +                                      if (trace_ent == ent.cursor_trace_ent)
 +                                              w_shotdir = normalize(ent.cursor_trace_ent.origin - w_shotorg);
 +                                      else
 +                                              print("antilag fail\n");
 +                              }
 +                      }
 +              }
 +      }
 +
 +      ent.dphitcontentsmask = oldsolid; // restore solid type (generally SOLID_SLIDEBOX)
 +
 +      if (!autocvar_g_norecoil)
 +              ent.punchangle_x = recoil * -1;
 +
 +      if (snd != "")
 +      {
 +              sound (ent, chan, snd, VOL_BASE, ATTN_NORM);
 +              W_PlayStrengthSound(ent);
 +      }
 +
 +      // nudge w_shotend so a trace to w_shotend hits
 +      w_shotend = w_shotend + normalize(w_shotend - w_shotorg) * nudge;
 +      //if(w_shotend != prevend) { printf("SERVER: shotEND differs: %s - %s\n", vtos(w_shotend), vtos(prevend)); }
 +      //if(w_shotorg != prevorg) { printf("SERVER: shotORG differs: %s - %s\n", vtos(w_shotorg), vtos(prevorg)); }
 +      //if(w_shotdir != prevdir) { printf("SERVER: shotDIR differs: %s - %s\n", vtos(w_shotdir), vtos(prevdir)); }
 +}
 +
 +vector W_CalculateProjectileVelocity(vector pvelocity, vector mvelocity, float forceAbsolute)
 +{
 +      vector mdirection;
 +      float mspeed;
 +      vector outvelocity;
 +
 +      mvelocity = mvelocity * g_weaponspeedfactor;
 +
 +      mdirection = normalize(mvelocity);
 +      mspeed = vlen(mvelocity);
 +
 +      outvelocity = get_shotvelocity(pvelocity, mdirection, mspeed, (forceAbsolute ? 0 : autocvar_g_projectiles_newton_style), autocvar_g_projectiles_newton_style_2_minfactor, autocvar_g_projectiles_newton_style_2_maxfactor);
 +
 +      return outvelocity;
 +}
 +
 +void W_SetupProjVelocity_Explicit(entity proj, vector dir, vector upDir, float pSpeed, float pUpSpeed, float pZSpeed, float spread, float forceAbsolute)
 +{
 +      if(proj.owner == world)
 +              error("Unowned missile");
 +
 +      dir = dir + upDir * (pUpSpeed / pSpeed);
 +      dir_z += pZSpeed / pSpeed;
 +      pSpeed *= vlen(dir);
 +      dir = normalize(dir);
 +
 +      #if 0
 +      if(autocvar_g_projectiles_spread_style != mspercallsstyle)
 +      {
 +              mspercallsum = mspercallcount = 0;
 +              mspercallsstyle = autocvar_g_projectiles_spread_style;
 +      }
 +      mspercallsum -= gettime(GETTIME_HIRES);
 +      #endif
 +      
 +      dir = W_CalculateSpread(dir, spread, g_weaponspreadfactor, autocvar_g_projectiles_spread_style);
 +      
 +      #if 0
 +      mspercallsum += gettime(GETTIME_HIRES);
 +      mspercallcount += 1;
 +      print("avg: ", ftos(mspercallcount / mspercallsum), " per sec\n");
 +      #endif
 +
 +      proj.velocity = W_CalculateProjectileVelocity(proj.owner.velocity, pSpeed * dir, forceAbsolute);
 +}
 +
 +
 +// ====================
 +//  Ballistics Tracing
 +// ====================
 +
 +void FireRailgunBullet (vector start, vector end, float bdamage, float bforce, float mindist, float maxdist, float halflifedist, float forcehalflifedist, float deathtype)
 +{
 +      vector hitloc, force, endpoint, dir;
 +      entity ent, endent;
 +      float endq3surfaceflags;
 +      float totaldmg;
 +      entity o;
 +
 +      float length;
 +      vector beampos;
 +      string snd;
 +      entity pseudoprojectile;
 +      float f, ffs;
 +
 +      pseudoprojectile = world;
 +
 +      dir = normalize(end - start);
 +      length = vlen(end - start);
 +      force = dir * bforce;
 +
 +      // go a little bit into the wall because we need to hit this wall later
 +      end = end + dir;
 +
 +      totaldmg = 0;
 +
 +      // trace multiple times until we hit a wall, each obstacle will be made
 +      // non-solid so we can hit the next, while doing this we spawn effects and
 +      // note down which entities were hit so we can damage them later
 +      o = self;
 +      while (1)
 +      {
 +              if(self.antilag_debug)
 +                      WarpZone_traceline_antilag (self, start, end, FALSE, o, self.antilag_debug);
 +              else
 +                      WarpZone_traceline_antilag (self, start, end, FALSE, o, ANTILAG_LATENCY(self));
 +              if(o && WarpZone_trace_firstzone)
 +              {
 +                      o = world;
 +                      continue;
 +              }
 +
 +              if(trace_ent.solid == SOLID_BSP || trace_ent.solid == SOLID_SLIDEBOX)
 +                      Damage_DamageInfo(trace_endpos, bdamage, 0, 0, force, deathtype, trace_ent.species, self);
 +
 +              // if it is world we can't hurt it so stop now
 +              if (trace_ent == world || trace_fraction == 1)
 +                      break;
 +
 +              // make the entity non-solid so we can hit the next one
 +              trace_ent.railgunhit = TRUE;
 +              trace_ent.railgunhitloc = end;
 +              trace_ent.railgunhitsolidbackup = trace_ent.solid;
 +              trace_ent.railgundistance = vlen(WarpZone_UnTransformOrigin(WarpZone_trace_transform, trace_endpos) - start);
 +              trace_ent.railgunforce = WarpZone_TransformVelocity(WarpZone_trace_transform, force);
 +
 +              // stop if this is a wall
 +              if (trace_ent.solid == SOLID_BSP)
 +                      break;
 +
 +              // make the entity non-solid
 +              trace_ent.solid = SOLID_NOT;
 +      }
 +
 +      endpoint = trace_endpos;
 +      endent = trace_ent;
 +      endq3surfaceflags = trace_dphitq3surfaceflags;
 +
 +      // find all the entities the railgun hit and restore their solid state
 +      ent = findfloat(world, railgunhit, TRUE);
 +      while (ent)
 +      {
 +              // restore their solid type
 +              ent.solid = ent.railgunhitsolidbackup;
 +              ent = findfloat(ent, railgunhit, TRUE);
 +      }
 +
 +      // spawn a temporary explosion entity for RadiusDamage calls
 +      //explosion = spawn();
 +
 +      // Find all non-hit players the beam passed close by
 +      if(deathtype == WEP_VAPORIZER || deathtype == WEP_VORTEX)
 +      {
 +              FOR_EACH_REALCLIENT(msg_entity)
 +              if(msg_entity != self)
 +              if(!msg_entity.railgunhit)
 +              if(!(IS_SPEC(msg_entity) && msg_entity.enemy == self)) // we use realclient, so spectators can hear the whoosh too
 +              {
 +                      // nearest point on the beam
 +                      beampos = start + dir * bound(0, (msg_entity.origin - start) * dir, length);
 +
 +                      f = bound(0, 1 - vlen(beampos - msg_entity.origin) / 512, 1);
 +                      if(f <= 0)
 +                              continue;
 +
 +                      snd = strcat("weapons/nexwhoosh", ftos(floor(random() * 3) + 1), ".wav");
 +
 +                      if(!pseudoprojectile)
 +                              pseudoprojectile = spawn(); // we need this so the sound uses the "entchannel4" volume
 +                      soundtoat(MSG_ONE, pseudoprojectile, beampos, CH_SHOTS, snd, VOL_BASE * f, ATTEN_NONE);
 +              }
 +
 +              if(pseudoprojectile)
 +                      remove(pseudoprojectile);
 +      }
 +
 +      // find all the entities the railgun hit and hurt them
 +      ent = findfloat(world, railgunhit, TRUE);
 +      while (ent)
 +      {
 +              // get the details we need to call the damage function
 +              hitloc = ent.railgunhitloc;
 +
 +              f = ExponentialFalloff(mindist, maxdist, halflifedist, ent.railgundistance);
 +              ffs = ExponentialFalloff(mindist, maxdist, forcehalflifedist, ent.railgundistance);
 +
 +              if(accuracy_isgooddamage(self.realowner, ent))
 +                      totaldmg += bdamage * f;
 +
 +              // apply the damage
 +              if (ent.takedamage)
 +                      Damage (ent, self, self, bdamage * f, deathtype, hitloc, ent.railgunforce * ffs);
 +
 +              // create a small explosion to throw gibs around (if applicable)
 +              //setorigin (explosion, hitloc);
 +              //RadiusDamage (explosion, self, 10, 0, 50, world, world, 300, deathtype);
 +
 +              ent.railgunhitloc = '0 0 0';
 +              ent.railgunhitsolidbackup = SOLID_NOT;
 +              ent.railgunhit = FALSE;
 +              ent.railgundistance = 0;
 +
 +              // advance to the next entity
 +              ent = findfloat(ent, railgunhit, TRUE);
 +      }
 +
 +      // calculate hits and fired shots for hitscan
 +      accuracy_add(self, self.weapon, 0, min(bdamage, totaldmg));
 +
 +      trace_endpos = endpoint;
 +      trace_ent = endent;
 +      trace_dphitq3surfaceflags = endq3surfaceflags;
 +}
 +
 +void fireBullet_trace_callback(vector start, vector hit, vector end)
 +{
 +      if(vlen(hit - start) > 16)
 +              trailparticles(world, fireBullet_trace_callback_eff, start, hit);
 +      WarpZone_trace_forent = world;
 +      fireBullet_last_hit = world;
 +}
 +
 +void fireBullet(vector start, vector dir, float spread, float max_solid_penetration, float damage, float force, float dtype, float tracereffects)
 +{
 +      vector  end;
 +
 +      dir = normalize(dir + randomvec() * spread);
 +      end = start + dir * MAX_SHOT_DISTANCE;
 +
 +      entity pl;
 +      fireBullet_last_hit = world;
 +      float solid_penetration_left = 1;
 +      float total_damage = 0;
 +
 +      if(tracereffects & EF_RED)
 +              fireBullet_trace_callback_eff = particleeffectnum("tr_rifle");
 +      else if(tracereffects & EF_BLUE)
 +              fireBullet_trace_callback_eff = particleeffectnum("tr_rifle_weak");
 +      else
 +              fireBullet_trace_callback_eff = particleeffectnum("tr_bullet");
 +
 +      float lag = ANTILAG_LATENCY(self);
 +      if(lag < 0.001)
 +              lag = 0;
 +      if (!IS_REAL_CLIENT(self))
 +              lag = 0;
 +      if(autocvar_g_antilag == 0 || self.cvar_cl_noantilag)
 +              lag = 0; // only do hitscan, but no antilag
 +      if(lag)
++      {
 +              FOR_EACH_PLAYER(pl)
 +                      if(pl != self)
 +                              antilag_takeback(pl, time - lag);
++              FOR_EACH_MONSTER(pl)
++                      antilag_takeback(pl, time - lag);
++      }
 +
 +      WarpZone_trace_forent = self;
 +
 +      for (;;)
 +      {
 +              // TODO also show effect while tracing
 +              WarpZone_TraceBox_ThroughZone(start, '0 0 0', '0 0 0', end, FALSE, WarpZone_trace_forent, world, fireBullet_trace_callback);
 +              dir = WarpZone_TransformVelocity(WarpZone_trace_transform, dir);
 +              end = WarpZone_TransformOrigin(WarpZone_trace_transform, end);
 +              start = trace_endpos;
 +              entity hit = trace_ent;
 +
 +              // When hitting sky, stop.
 +              if (pointcontents(start) == CONTENT_SKY)
 +                      break;
 +
 +              if (trace_dphitq3surfaceflags & Q3SURFACEFLAG_NOIMPACT)
 +                      break;
 +
 +              // if we hit "weapclip", bail out
 +              //
 +              // rationale of this check:
 +              //
 +              // any shader that is solid, nodraw AND trans is meant to clip weapon
 +              // shots and players, but has no other effect!
 +              //
 +              // if it is not trans, it is caulk and should not have this side effect
 +              //
 +              // matching shaders:
 +              //   common/weapclip (intended)
 +              //   common/noimpact (is supposed to eat projectiles, but is erased anyway)
 +              float is_weapclip = 0;
 +              if(trace_dphitq3surfaceflags & Q3SURFACEFLAG_NODRAW)
 +              if (!(trace_dphitq3surfaceflags & Q3SURFACEFLAG_NONSOLID))
 +              if (!(trace_dphitcontents & DPCONTENTS_OPAQUE))
 +                      is_weapclip = 1;
 +
 +              if(!hit || hit.solid == SOLID_BSP || hit.solid == SOLID_SLIDEBOX)
 +                      Damage_DamageInfo(start, damage * solid_penetration_left, 0, 0, max(1, force) * dir * solid_penetration_left, dtype, hit.species, self);
 +
 +              if (hit && hit != WarpZone_trace_forent && hit != fireBullet_last_hit)  // Avoid self-damage (except after going through a warp); avoid hitting the same entity twice (engine bug).
 +              {
 +                      fireBullet_last_hit = hit;
 +                      yoda = 0;
 +                      float g = accuracy_isgooddamage(self, hit);
 +                      Damage(hit, self, self, damage * solid_penetration_left, dtype, start, force * dir * solid_penetration_left);
 +                      // calculate hits for ballistic weapons
 +                      if(g)
 +                      {
 +                              // do not exceed 100%
 +                              float added_damage = min(damage - total_damage, damage * solid_penetration_left);
 +                              total_damage += damage * solid_penetration_left;
 +                              accuracy_add(self, self.weapon, 0, added_damage);
 +                      }
 +              }
 +
 +              if (is_weapclip)
 +                      break;
 +
 +              // go through solid!
 +              // outside the world? forget it
 +              if(start_x > world.maxs_x || start_y > world.maxs_y || start_z > world.maxs_z || start_x < world.mins_x || start_y < world.mins_y || start_z < world.mins_z)
 +                      break;
 +
 +              float maxdist;
 +              if(max_solid_penetration < 0)
 +                      break;
 +              else if(hit.ballistics_density < -1)
 +                      break; // -2: no solid penetration, ever
 +              else if(hit.ballistics_density < 0)
 +                      maxdist = vlen(hit.maxs - hit.mins) + 1; // -1: infinite travel distance
 +              else if(hit.ballistics_density == 0)
 +                      maxdist = max_solid_penetration * solid_penetration_left;
 +              else
 +                      maxdist = max_solid_penetration * solid_penetration_left * hit.ballistics_density;
 +
 +              if(maxdist <= autocvar_g_ballistics_mindistance)
 +                      break;
 +
 +              // move the entity along its velocity until it's out of solid, then let it resume
 +              // The previously hit entity is ignored here!
 +              traceline_inverted (start, start + dir * maxdist, MOVE_NORMAL, WarpZone_trace_forent, TRUE, hit);
 +              if(trace_fraction == 1) // 1: we never got out of solid
 +                      break;
 +
 +              float dist_taken = max(autocvar_g_ballistics_mindistance, vlen(trace_endpos - start));
 +              solid_penetration_left *= (dist_taken / maxdist);
 +
 +              // Only show effect when going through a player (invisible otherwise)
 +              if (hit && (hit.solid != SOLID_BSP))
 +                      if(vlen(trace_endpos - start) > 4)
 +                              trailparticles(self, fireBullet_trace_callback_eff, start, trace_endpos);
 +
 +              start = trace_endpos;
 +
 +              if(hit.solid == SOLID_BSP)
 +                      Damage_DamageInfo(start, 0, 0, 0, max(1, force) * normalize(dir) * -solid_penetration_left, dtype, 0, self);
 +      }
 +
 +      if(lag)
++      {
 +              FOR_EACH_PLAYER(pl)
 +                      if(pl != self)
 +                              antilag_restore(pl);
++              FOR_EACH_MONSTER(pl)
++                      antilag_restore(pl);
++      }
 +}