diff --git a/code/__HELPERS/mob_helpers.dm b/code/__HELPERS/mob_helpers.dm
index 659c379453d..cda36557525 100644
--- a/code/__HELPERS/mob_helpers.dm
+++ b/code/__HELPERS/mob_helpers.dm
@@ -392,7 +392,7 @@
* This will create progress bar that lasts for 5 seconds. If the user doesn't move or otherwise do something that would cause the checks to fail in those 5 seconds, do_stuff() would execute.
* The Proc returns TRUE upon success (the progress bar reached the end), or FALSE upon failure (the user moved or some other check failed)
*/
-/proc/do_after(mob/user, delay, needhand = 1, atom/target = null, progress = 1, list/extra_checks = list(), use_default_checks = TRUE)
+/proc/do_after(mob/user, delay, needhand = 1, atom/target = null, progress = 1, allow_moving = 0, must_be_held = 0, list/extra_checks = list(), use_default_checks = TRUE)
if(!user)
return FALSE
var/atom/Tloc = null
@@ -402,8 +402,9 @@
var/atom/Uloc = user.loc
var/drifting = FALSE
- if(!user.Process_Spacemove(0) && user.inertia_dir)
- drifting = TRUE
+ if(!allow_moving)
+ if(!user.Process_Spacemove(0) && user.inertia_dir)
+ drifting = TRUE
var/holding = user.get_active_hand()
@@ -429,12 +430,15 @@
sleep(1)
if(progress)
progbar.update(world.time - starttime)
+ if(!allow_moving)
+ if(drifting && !user.inertia_dir)
+ drifting = FALSE
+ Uloc = user.loc
+ if((!drifting && user.loc != Uloc))
+ . = FALSE
+ break
- if(drifting && !user.inertia_dir)
- drifting = FALSE
- Uloc = user.loc
-
- if(!user || user.stat || (!drifting && user.loc != Uloc) || check_for_true_callbacks(extra_checks))
+ if(!user || user.stat || check_for_true_callbacks(extra_checks))
. = FALSE
break
@@ -442,6 +446,11 @@
. = FALSE
break
+ if(must_be_held)
+ if(target.loc != user)
+ . = FALSE
+ break
+
if(needhand)
//This might seem like an odd check, but you can still need a hand even when it's empty
//i.e the hand is used to pull some item/tool out of the construction
@@ -456,7 +465,7 @@
qdel(progbar)
/// A version of do_after that will not get cancelled by a mob moving, for situations when signals are not viable
-/proc/moving_do_after(mob/user, delay, needhand = TRUE, atom/target = null, progress = TRUE, list/extra_checks = list(), use_default_checks = TRUE, must_be_held = TRUE)
+/proc/moving_do_after(mob/user, delay, needhand = TRUE, atom/target = null, progress = TRUE, allow_moving = 0, list/extra_checks = list(), use_default_checks = TRUE, must_be_held = TRUE)
if(!istype(user))
return FALSE
var/atom/target_loc = null
@@ -514,7 +523,7 @@
#define DOAFTERONCE_MAGIC "Magic~~"
GLOBAL_LIST_INIT(do_after_once_tracker, list())
-/proc/do_after_once(mob/user, delay, needhand = 1, atom/target = null, progress = 1, attempt_cancel_message = "Attempt cancelled.")
+/proc/do_after_once(mob/user, delay, needhand = 1, atom/target = null, progress = 1, allow_moving, must_be_held, attempt_cancel_message = "Attempt cancelled.")
if(!user || !target)
return
@@ -524,7 +533,7 @@ GLOBAL_LIST_INIT(do_after_once_tracker, list())
to_chat(user, "[attempt_cancel_message]")
return FALSE
GLOB.do_after_once_tracker[cache_key] = TRUE
- . = do_after(user, delay, needhand, target, progress, extra_checks = list(CALLBACK(GLOBAL_PROC, GLOBAL_PROC_REF(do_after_once_checks), cache_key)))
+ . = do_after(user, delay, needhand, target, progress, allow_moving, must_be_held, extra_checks = list(CALLBACK(GLOBAL_PROC, GLOBAL_PROC_REF(do_after_once_checks), cache_key)))
GLOB.do_after_once_tracker[cache_key] = FALSE
/proc/do_after_once_checks(cache_key)
diff --git a/code/modules/projectiles/ammunition.dm b/code/modules/projectiles/ammunition.dm
index 85f116e7faf..a0d25ee80a1 100644
--- a/code/modules/projectiles/ammunition.dm
+++ b/code/modules/projectiles/ammunition.dm
@@ -50,8 +50,10 @@
return
/obj/item/ammo_casing/attackby(obj/item/I as obj, mob/user as mob, params)
- if(istype(I, /obj/item/ammo_box) && !istype(I, /obj/item/ammo_box/magazine/wt550m9))
+ if(istype(I, /obj/item/ammo_box))
var/obj/item/ammo_box/box = I
+ if(box.slow_loading)
+ return
if(isturf(loc))
var/boolets = 0
for(var/obj/item/ammo_casing/bullet in loc)
@@ -127,9 +129,10 @@
var/multi_sprite_step = AMMO_MULTI_SPRITE_STEP_NONE // see update_icon_state() for details
var/caliber
var/multiload = 1
+ var/slow_loading = 0
var/list/initial_mats //For calculating refund values.
-/obj/item/ammo_box/New()
+/obj/item/ammo_box/Initialize(mapload)
..()
for(var/i in 1 to max_ammo)
stored_ammo += new ammo_type(src)
diff --git a/code/modules/projectiles/ammunition/magazines.dm b/code/modules/projectiles/ammunition/magazines.dm
index 334e3ddfc44..8d027d3ba42 100644
--- a/code/modules/projectiles/ammunition/magazines.dm
+++ b/code/modules/projectiles/ammunition/magazines.dm
@@ -154,7 +154,7 @@
max_ammo = 6
multiload = 0
-/obj/item/ammo_box/magazine/internal/rus357/New()
+/obj/item/ammo_box/magazine/internal/rus357/Initialize(mapload)
..()
stored_ammo.Cut() // We only want 1 bullet in there
stored_ammo += new ammo_type(src)
@@ -259,6 +259,7 @@
max_ammo = 20
multi_sprite_step = 4
multiload = 0
+ slow_loading = 1
w_class = WEIGHT_CLASS_NORMAL
///A var to check if the mag is being loaded
var/being_loaded = FALSE
@@ -275,29 +276,19 @@
if(istype(A, /obj/item/ammo_box/wt550) || istype(A, /obj/item/ammo_box/magazine/wt550m9))
to_chat(user, "You begin to load the magazine with [A].")
var/obj/item/ammo_box/AB = A
- if(being_loaded == TRUE && double_loaded == FALSE)
- double_loaded = TRUE //This will cancel ongoing reloads if made true by someone trying to do two reload processes at once
- to_chat(user, "You're already loading the magazine!.")
- to_chat(user, "You stop loading the magazine with [A].")
- being_loaded = TRUE
for(var/obj/item/ammo_casing/AC in AB.stored_ammo)
- if(double_loaded == FALSE)// checks to make sure double_loaded hasn't been made true while an ongoing reload is already ongoing
- to_chat(user, "You stop loading the magazine with [A].")
- double_loaded = FALSE
- break
if(length(stored_ammo) >= max_ammo)
to_chat(user, "You stop loading the magazine with [A].")
break
- if(!moving_do_after(user, 0.5 SECONDS, target = src, use_default_checks = TRUE))
- to_chat(user, "You stop loading the magazine with [A].")
+ if(do_after_once(user, 0.5 SECONDS, target = src, allow_moving = TRUE, must_be_held = TRUE, attempt_cancel_message = "You stop loading the magazine with [A]."))
+ src.give_round(AC)
+ AB.stored_ammo -= AC
+ update_mat_value()
+ update_appearance(UPDATE_DESC|UPDATE_ICON_STATE)
+ AB.update_appearance(UPDATE_DESC|UPDATE_ICON_STATE)
+ playsound(src, 'sound/weapons/gun_interactions/bulletinsert.ogg', 50, 1)
+ else
break
- src.give_round(AC)
- AB.stored_ammo -= AC
- update_mat_value()
- update_appearance(UPDATE_DESC|UPDATE_ICON_STATE)
- AB.update_appearance(UPDATE_DESC|UPDATE_ICON_STATE)
- playsound(src, 'sound/weapons/gun_interactions/bulletinsert.ogg', 50, 1)
- being_loaded = FALSE
/obj/item/ammo_box/magazine/wt550m9/wtap
name = "wt550 magazine (Armour Piercing 4.6x30mm)"
@@ -319,9 +310,9 @@
icon_state = "46x30mmt"
ammo_type = /obj/item/ammo_casing/c46x30mm
-/obj/item/ammo_box/magazine/wt550m9/empty/New()
+/obj/item/ammo_box/magazine/wt550m9/empty/Initialize(mapload)
. = ..()
- stored_ammo = list()
+ stored_ammo.Cut()
update_appearance(UPDATE_DESC|UPDATE_ICON)
/obj/item/ammo_box/magazine/uzim9mm