From 1e1463a9b10363f59c4c337e4f63c6de3e91dc17 Mon Sep 17 00:00:00 2001 From: Timothy Teakettle <59849408+timothyteakettle@users.noreply.github.com> Date: Thu, 11 Jun 2020 23:50:55 +0100 Subject: [PATCH] attempted ricochet fix --- code/__DEFINES/dcs/signals.dm | 1 + code/modules/projectiles/projectile.dm | 26 +++++++++++--------------- 2 files changed, 12 insertions(+), 15 deletions(-) diff --git a/code/__DEFINES/dcs/signals.dm b/code/__DEFINES/dcs/signals.dm index 34cc7ad41d..141f5626b2 100644 --- a/code/__DEFINES/dcs/signals.dm +++ b/code/__DEFINES/dcs/signals.dm @@ -323,6 +323,7 @@ #define COMSIG_PROJECTILE_SELF_ON_HIT "projectile_self_on_hit" // from base of /obj/item/projectile/proc/on_hit(): (atom/movable/firer, atom/target, Angle) #define COMSIG_PROJECTILE_ON_HIT "projectile_on_hit" // from base of /obj/item/projectile/proc/on_hit(): (atom/movable/firer, atom/target, Angle) #define COMSIG_PROJECTILE_BEFORE_FIRE "projectile_before_fire" // from base of /obj/item/projectile/proc/fire(): (obj/item/projectile, atom/original_target) +#define COMSIG_PROJECTILE_FIRE "projectile_fire" ///from the base of /obj/projectile/proc/fire(): () #define COMSIG_PROJECTILE_RANGE_OUT "projectile_range_out" // sent to targets during the process_hit proc of projectiles #define COMSIG_EMBED_TRY_FORCE "item_try_embed" // sent when trying to force an embed (mainly for projectiles, only used in the embed element) #define COMSIG_PROJECTILE_PREHIT "com_proj_prehit" ///sent to targets during the process_hit proc of projectiles diff --git a/code/modules/projectiles/projectile.dm b/code/modules/projectiles/projectile.dm index 404ba376b9..b46e6f5ead 100644 --- a/code/modules/projectiles/projectile.dm +++ b/code/modules/projectiles/projectile.dm @@ -284,27 +284,22 @@ /obj/item/projectile/proc/on_ricochet(atom/A) if(!ricochet_auto_aim_angle || !ricochet_auto_aim_range) - message_admins("not an autoaim ricochet") return - var/mob/living/unlucky_sob var/best_angle = ricochet_auto_aim_angle if(firer && HAS_TRAIT(firer, TRAIT_NICE_SHOT)) best_angle += NICE_SHOT_RICOCHET_BONUS for(var/mob/living/L in range(ricochet_auto_aim_range, src.loc)) - message_admins("yeah lets have a look at [L]") if(L.stat == DEAD || !isInSight(src, L)) - message_admins("they were not suitable, try again.") continue - var/our_angle = abs(closer_angle_difference(Angle, Get_Angle(src.loc, L.loc))) + var/our_angle = abs(closer_angle_difference(Angle, get_projectile_angle(src.loc, L.loc))) if(our_angle < best_angle) best_angle = our_angle unlucky_sob = L if(unlucky_sob) - message_admins("yeah fuck that guy get him") - setAngle(Get_Angle(src, unlucky_sob.loc)) + setAngle(get_projectile_angle(src, unlucky_sob.loc)) /obj/item/projectile/proc/store_hitscan_collision(datum/point/pcache) beam_segments[beam_index] = pcache @@ -314,7 +309,7 @@ /obj/item/projectile/Bump(atom/A) var/datum/point/pcache = trajectory.copy_to() var/turf/T = get_turf(A) - if(ricochets < ricochets_max && check_ricochet_flag(A) && check_ricochet(A)) + if(trajectory && ricochets < ricochets_max && check_ricochet_flag(A) && check_ricochet(A)) ricochets++ if(A.handle_ricochet(src)) on_ricochet(A) @@ -328,13 +323,15 @@ return TRUE var/distance = get_dist(T, starting) // Get the distance between the turf shot from and the mob we hit and use that for the calculations. - def_zone = ran_zone(def_zone, max(100-(7*distance), 5)) //Lower accurancy/longer range tradeoff. 7 is a balanced number to use. + if(def_zone && check_zone(def_zone) != BODY_ZONE_CHEST) + def_zone = ran_zone(def_zone, max(100-(7*distance), 5) * zone_accuracy_factor) //Lower accurancy/longer range tradeoff. 7 is a balanced number to use. if(isturf(A) && hitsound_wall) var/volume = clamp(vol_by_damage() + 20, 0, 100) if(suppressed) volume = 5 - playsound(loc, hitsound_wall, volume, TRUE, -1) + playsound(loc, hitsound_wall, volume, 1, -1) + return process_hit(T, select_target(T, A)) #define QDEL_SELF 1 //Delete if we're not UNSTOPPABLE flagged non-temporarily @@ -343,25 +340,24 @@ /obj/item/projectile/proc/process_hit(turf/T, atom/target, qdel_self, hit_something = FALSE) //probably needs to be reworked entirely when pixel movement is done. if(QDELETED(src) || !T || !target) //We're done, nothing's left. - if((qdel_self == FORCE_QDEL) || ((qdel_self == QDEL_SELF) && !temporary_unstoppable_movement && !(movement_type & UNSTOPPABLE))) + if((qdel_self == FORCE_QDEL) || ((qdel_self == QDEL_SELF) && !temporary_unstoppable_movement && !CHECK_BITFIELD(movement_type, UNSTOPPABLE))) qdel(src) return hit_something permutated |= target //Make sure we're never hitting it again. If we ever run into weirdness with piercing projectiles needing to hit something multiple times.. well.. that's a to-do. if(!prehit(target)) return process_hit(T, select_target(T), qdel_self, hit_something) //Hit whatever else we can since that didn't work. - SEND_SIGNAL(target, COMSIG_PROJECTILE_PREHIT, args) var/result = target.bullet_act(src, def_zone) if(result == BULLET_ACT_FORCE_PIERCE) - if(!(movement_type & UNSTOPPABLE)) + if(!CHECK_BITFIELD(movement_type, UNSTOPPABLE)) temporary_unstoppable_movement = TRUE - movement_type |= UNSTOPPABLE + ENABLE_BITFIELD(movement_type, UNSTOPPABLE) return process_hit(T, select_target(T), qdel_self, TRUE) //Hit whatever else we can since we're piercing through but we're still on the same tile. else if(result == BULLET_ACT_TURF) //We hit the turf but instead we're going to also hit something else on it. return process_hit(T, select_target(T), QDEL_SELF, TRUE) else //Whether it hit or blocked, we're done! qdel_self = QDEL_SELF hit_something = TRUE - if((qdel_self == FORCE_QDEL) || ((qdel_self == QDEL_SELF) && !temporary_unstoppable_movement && !(movement_type & UNSTOPPABLE))) + if((qdel_self == FORCE_QDEL) || ((qdel_self == QDEL_SELF) && !temporary_unstoppable_movement && !CHECK_BITFIELD(movement_type, UNSTOPPABLE))) qdel(src) return hit_something