Adds advanced_bullet_dodge_chance, for admin / mob use. Applies it to space combat drones (#25336)

* Adds advanced_bullet_dodge_chance, for admin / mob use

* actually just make it 25

* Apply suggestions from code review

Co-authored-by: 1080pCat <96908085+1080pCat@users.noreply.github.com>
Signed-off-by: Qwertytoforty <52090703+Qwertytoforty@users.noreply.github.com>

---------

Signed-off-by: Qwertytoforty <52090703+Qwertytoforty@users.noreply.github.com>
Co-authored-by: 1080pCat <96908085+1080pCat@users.noreply.github.com>
This commit is contained in:
Qwertytoforty
2024-05-29 09:37:36 -04:00
committed by GitHub
parent 40d03dd669
commit 97d43770f5
4 changed files with 65 additions and 0 deletions
+6
View File
@@ -6,6 +6,8 @@
faction += "\ref[src]"
determine_move_and_pull_forces()
GLOB.mob_living_list += src
if(advanced_bullet_dodge_chance)
RegisterSignal(src, COMSIG_ATOM_PREHIT, PROC_REF(advanced_bullet_dodge))
// Used to determine the forces dependend on the mob size
// Will only change the force if the force was not set in the mob type itself
@@ -51,6 +53,7 @@
QDEL_NULL(middleClickOverride)
if(mind?.current == src)
mind.current = null
UnregisterSignal(src, COMSIG_ATOM_PREHIT)
return ..()
/mob/living/ghostize(can_reenter_corpse = 1)
@@ -1071,6 +1074,9 @@
update_transform()
if("lighting_alpha")
sync_lighting_plane_alpha()
if("advanced_bullet_dodge_chance")
UnregisterSignal(src, COMSIG_ATOM_PREHIT)
RegisterSignal(src, COMSIG_ATOM_PREHIT, PROC_REF(advanced_bullet_dodge))
/mob/living/throw_at(atom/target, range, speed, mob/thrower, spin, diagonals_first, datum/callback/callback, force, dodgeable, block_movement)
stop_pulling()
+27
View File
@@ -51,6 +51,33 @@
check_projectile_dismemberment(P, def_zone)
return P.on_hit(src, armor, def_zone)
/// Tries to dodge incoming bullets if we aren't disabled for any reasons. Advised to overide with advanced effects, this is as basic example admins can apply.
/mob/living/proc/advanced_bullet_dodge(mob/living/source, obj/item/projectile/hitting_projectile)
SIGNAL_HANDLER
if(HAS_TRAIT(source, TRAIT_IMMOBILIZED))
return NONE
if(source.stat != CONSCIOUS)
return NONE
if(!prob(advanced_bullet_dodge_chance))
return NONE
source.visible_message(
"<span class='danger'>[source] [pick("dodges","jumps out of the way of","evades","dives out of the way of")] [hitting_projectile]!</span>",
"<span class='userdanger'>You evade [hitting_projectile]!</span>",
)
playsound(source, pick('sound/weapons/bulletflyby.ogg', 'sound/weapons/bulletflyby2.ogg', 'sound/weapons/bulletflyby3.ogg'), 75, TRUE)
var/dir_to_avoid = angle2dir_cardinal(hitting_projectile.Angle)
var/list/potential_first_directions = list(NORTH, SOUTH, EAST, WEST)
potential_first_directions -= dir_to_avoid
step(source, pick(potential_first_directions))
// Chance to dodge multiple shotgun spreads, but not likely. Mainly: Infinite loop prevention from admins setting it to 100 and doing something stupid.
// If you want to set your dodge chance to 100 on a subtype, no issue: Just make sure the subtype does not step in a direction, otherwise you'll have the mob move a large distance to dodge rubbershot.
if(prob(50))
addtimer(VARSET_CALLBACK(src, advanced_bullet_dodge_chance, advanced_bullet_dodge_chance), 0.25 SECONDS) // Returns fast enough for multiple laser shots.
advanced_bullet_dodge_chance = 0
return ATOM_PREHIT_FAILURE
/mob/living/proc/check_projectile_dismemberment(obj/item/projectile/P, def_zone)
return 0
@@ -100,6 +100,9 @@
/// Famous last words -- if succumbing, what the user's last words were
var/last_words
///This variable is the chance for a mob to automatically dodge a bullet. Useful for admins, and applied to some mobs by default, such as the malfunctioning drone mobs.
var/advanced_bullet_dodge_chance = 0
/*
Taste Vars
*/
@@ -30,6 +30,7 @@
faction = list("malf_drone")
deathmessage = "suddenly breaks apart."
del_on_death = TRUE
advanced_bullet_dodge_chance = 25 // This will be adjusted when active, vs deactivated. Randomises on hit if it is zero.
var/passive_mode = TRUE // if true, don't target anything.
/mob/living/simple_animal/hostile/malf_drone/Initialize(mapload)
@@ -69,6 +70,8 @@
do_sparks(3, 1, src)
passive_mode = FALSE
update_icons()
if(!advanced_bullet_dodge_chance)
advanced_bullet_dodge_chance = 25
. = ..() // this will handle finding a target if there is a valid one nearby
/mob/living/simple_animal/hostile/malf_drone/Life(seconds, times_fired)
@@ -83,12 +86,38 @@
passive_mode = !passive_mode
if(passive_mode)
visible_message("<span class='notice'>[src] retracts several targetting vanes.</span>")
advanced_bullet_dodge_chance = 0
if(target)
LoseTarget()
else
visible_message("<span class='warning'>[src] suddenly lights up, and additional targetting vanes slide into place.</span>")
advanced_bullet_dodge_chance = 25
update_icons()
/// We overide the basic effect, as malfunctioning drones are in space, and use jets to dodge. Also lets us do cool effects.
/mob/living/simple_animal/hostile/malf_drone/advanced_bullet_dodge(mob/living/source, obj/item/projectile/hitting_projectile)
if(HAS_TRAIT(source, TRAIT_IMMOBILIZED))
return NONE
if(source.stat != CONSCIOUS)
return NONE
if(!prob(advanced_bullet_dodge_chance))
return NONE
source.visible_message(
"<span class='danger'>[source]'s jets [pick("boosts", "propels", "pulses", "flares up and moves", "shudders and pushes")] it out of '[hitting_projectile]'s way!</span>",
"<span class='userdanger'>You evade [hitting_projectile]!</span>",
)
playsound(source, pick('sound/weapons/bulletflyby.ogg', 'sound/weapons/bulletflyby2.ogg', 'sound/weapons/bulletflyby3.ogg', 'sound/effects/refill.ogg'), 75, TRUE)
var/dir_to_avoid = angle2dir_cardinal(hitting_projectile.Angle)
var/list/potential_first_directions = list(NORTH, SOUTH, EAST, WEST)
potential_first_directions -= dir_to_avoid
new /obj/effect/temp_visual/decoy/fading(source.loc, source)
step(source, pick(potential_first_directions))
if(prob(50))
addtimer(VARSET_CALLBACK(source, advanced_bullet_dodge_chance, advanced_bullet_dodge_chance), 0.25 SECONDS)
advanced_bullet_dodge_chance = 0
return ATOM_PREHIT_FAILURE
/mob/living/simple_animal/hostile/malf_drone/emp_act(severity)
adjustHealth(100 / severity) // takes the same damage as a mining drone from emp