diff --git a/code/datums/components/remote_view.dm b/code/datums/components/remote_view.dm index 0b08010692..bfbba19568 100644 --- a/code/datums/components/remote_view.dm +++ b/code/datums/components/remote_view.dm @@ -62,13 +62,10 @@ /** * If an item is coordinating this view (scopes/binoculars) * Handles remote views that are managed by a held item. The held item must remain in the mob's - * inventory, and will call zoom() and unzoom() when it starts and ends. Optionally showing a message. + * inventory, and will call unzoom() when it ends. Optionally showing a message. */ if(isitem(managing_item)) host_item = managing_item - // Unfortunately too many things read this to control item state for me to remove this. - // Oh well! better than GetComponent() everywhere. Lets just manage item/zoom in this component though... - host_item.zoom = TRUE // Feedback show_message = show_visible_messages if(show_message) @@ -96,7 +93,7 @@ /datum/component/remote_view/Destroy(force) // Clear item if(host_item) - host_item.zoom(host_mob) + host_item.unzoom(host_mob) // Feedback if(show_message) host_mob.visible_message(span_filter_notice("[host_item.zoomdevicename ? "[host_mob] looks up from the [host_item.name]" : "[host_mob] lowers the [host_item.name]"].")) @@ -246,6 +243,9 @@ SIGNAL_HANDLER SHOULD_NOT_OVERRIDE(TRUE) PRIVATE_PROC(TRUE) + // Don't forward movement to ourselves if we're using a spyglass or something + if(host_mob == remote_view_target) + return // I'd move this into the config datum if it didn't require the component to also be passed too. Lets avoid GetComponent on a hotpath. return settings.handle_relay_movement(src, host_mob, direction) diff --git a/code/game/objects/items.dm b/code/game/objects/items.dm index a759851154..5e48e6adbb 100644 --- a/code/game/objects/items.dm +++ b/code/game/objects/items.dm @@ -61,7 +61,7 @@ var/list/allowed = null //suit storage stuff. var/obj/item/uplink/hidden/hidden_uplink = null // All items can have an uplink hidden inside, just remember to add the triggers. var/zoomdevicename = null //name used for message when binoculars/scope is used - var/zoom = 0 //1 if item is actively being used to zoom. For scoped guns and binoculars. + var/zoom = FALSE // if the item is currently zoomed in with a remote view, do not set manually. Handled by remote_view component. var/embed_chance = -1 //0 won't embed, and 100 will always embed @@ -841,19 +841,18 @@ GLOBAL_LIST_EMPTY(blood_overlays_by_type) if(I && !I.abstract) I.showoff(src) -/// For zooming with scope or binoculars. Uses remote_view/item component for disabling when you move or drop the item -/obj/item/proc/zoom(mob/living/M, tileoffset = 14,viewsize = 9) //tileoffset is client view offset in the direction the user is facing. viewsize is how far out this thing zooms. 7 is normal view +/// For zooming with scope or binoculars. Starts a remote_view when called, which calls unzoom when called again or dropped +/obj/item/proc/toggle_zoom(mob/living/user, tileoffset = 14,viewsize = 9) //tileoffset is client view offset in the direction the user is facing. viewsize is how far out this thing zooms. 7 is normal view + SHOULD_CALL_PARENT(TRUE) SIGNAL_HANDLER - if(isliving(usr)) //Always prefer usr if set - M = usr - if(!M.client) + if(!user.client) return FALSE - if(!isliving(M)) + if(!isliving(user)) return FALSE - if(isbelly(M.loc) || istype(M.loc,/obj/item/dogborg/sleeper)) + if(isbelly(user.loc) || istype(user.loc,/obj/item/dogborg/sleeper)) return FALSE - if(M.is_remote_viewing()) - to_chat(M, span_warning("You are too distracted to do that.")) + if(user.is_remote_viewing()) + to_chat(user, span_warning("You are too distracted to do that.")) return FALSE var/devicename @@ -863,22 +862,28 @@ GLOBAL_LIST_EMPTY(blood_overlays_by_type) devicename = src.name var/can_zoom = TRUE - if((M.stat && !zoom) || !(ishuman(M))) - to_chat(M, span_filter_notice("You are unable to focus through the [devicename].")) + if((user.stat && !zoom) || !(ishuman(user))) + to_chat(user, span_filter_notice("You are unable to focus through the [devicename].")) can_zoom = FALSE - else if(!zoom && (GLOB.global_hud.darkMask[1] in M.client.screen)) - to_chat(M, span_filter_notice("Your visor gets in the way of looking through the [devicename].")) + else if(!zoom && (GLOB.global_hud.darkMask[1] in user.client.screen)) + to_chat(user, span_filter_notice("Your visor gets in the way of looking through the [devicename].")) can_zoom = FALSE - else if(!zoom && M.get_active_hand() != src) - to_chat(M, span_filter_notice("You are too distracted to look through the [devicename], perhaps if it was in your active hand this might work better.")) + else if(!zoom && user.get_active_hand() != src) + to_chat(user, span_filter_notice("You are too distracted to look through the [devicename], perhaps if it was in your active hand this might work better.")) can_zoom = FALSE if(!zoom && can_zoom) - M.AddComponent(/datum/component/remote_view, focused_on = M, vconfig_path = /datum/remote_view_config/zoomed_item, managing_item = src, viewsize = viewsize, tileoffset = tileoffset, show_visible_messages = TRUE) + user.AddComponent(/datum/component/remote_view, focused_on = user, vconfig_path = /datum/remote_view_config/zoomed_item, managing_item = src, viewsize = viewsize, tileoffset = tileoffset, show_visible_messages = TRUE) + zoom = TRUE return - zoom = FALSE SEND_SIGNAL(src,COMSIG_REMOTE_VIEW_CLEAR) +/// Called by remote view when the view is ended. Do not call manually. +/obj/item/proc/unzoom(mob/user) + SHOULD_CALL_PARENT(TRUE) + SIGNAL_HANDLER + zoom = FALSE + /obj/item/proc/pwr_drain() return 0 // Process Kill diff --git a/code/game/objects/items/devices/binoculars.dm b/code/game/objects/items/devices/binoculars.dm index 66d31ae46b..071630f2cb 100644 --- a/code/game/objects/items/devices/binoculars.dm +++ b/code/game/objects/items/devices/binoculars.dm @@ -17,7 +17,7 @@ . = ..(user) if(.) return TRUE - zoom() + toggle_zoom(user) /obj/item/binoculars/spyglass name = "spyglass" diff --git a/code/modules/projectiles/gun.dm b/code/modules/projectiles/gun.dm index 1ebba63838..c5d5f74489 100644 --- a/code/modules/projectiles/gun.dm +++ b/code/modules/projectiles/gun.dm @@ -739,25 +739,24 @@ handle_click_empty(user) return -/obj/item/gun/proc/toggle_scope(zoom_amount=2.0) +/obj/item/gun/proc/toggle_scope(mob/user, zoom_amount=2.0) //looking through a scope limits your periphereal vision //still, increase the view size by a tiny amount so that sniping isn't too restricted to NSEW var/zoom_offset = round(world.view * zoom_amount) var/view_size = round(world.view + zoom_amount) var/scoped_accuracy_mod = zoom_offset - zoom(zoom_offset, view_size) - if(zoom) + toggle_zoom(user, zoom_offset, view_size) + if(zoom) // If zoom in was successful accuracy = scoped_accuracy + scoped_accuracy_mod if(recoil) recoil = round(recoil*zoom_amount+1) //recoil is worse when looking through a scope -//make sure accuracy and recoil are reset regardless of how the item is unzoomed. -/obj/item/gun/zoom() - ..() - if(!zoom) - accuracy = initial(accuracy) - recoil = initial(recoil) +/obj/item/gun/unzoom() + . = ..() + //make sure accuracy and recoil are reset regardless of how the item is unzoomed. + accuracy = initial(accuracy) + recoil = initial(recoil) /obj/item/gun/examine(mob/user) . = ..() diff --git a/code/modules/projectiles/guns/energy/laser.dm b/code/modules/projectiles/guns/energy/laser.dm index 33fc238767..ac607e049c 100644 --- a/code/modules/projectiles/guns/energy/laser.dm +++ b/code/modules/projectiles/guns/energy/laser.dm @@ -330,7 +330,7 @@ set name = "Use Scope" set popup_menu = 1 - toggle_scope(2.0) + toggle_scope(usr, 2.0) /* * Laser Scattergun (proof of concept) @@ -428,7 +428,7 @@ set name = "Aim Down Sights" set popup_menu = 1 - toggle_scope(scope_multiplier) + toggle_scope(usr, scope_multiplier) /obj/item/gun/energy/monorifle/combat name = "combat mono-rifle" diff --git a/code/modules/projectiles/guns/energy/pump.dm b/code/modules/projectiles/guns/energy/pump.dm index c1b764dcf0..c180517ac8 100644 --- a/code/modules/projectiles/guns/energy/pump.dm +++ b/code/modules/projectiles/guns/energy/pump.dm @@ -205,7 +205,7 @@ set name = "Use Scope" set popup_menu = 1 - toggle_scope(2.0) + toggle_scope(usr, 2.0) /obj/item/gun/energy/locked/frontier/rifle/update_icon() if(recharging) diff --git a/code/modules/projectiles/guns/projectile/sniper.dm b/code/modules/projectiles/guns/projectile/sniper.dm index 9ff162cde6..a6dc3e24de 100644 --- a/code/modules/projectiles/guns/projectile/sniper.dm +++ b/code/modules/projectiles/guns/projectile/sniper.dm @@ -73,7 +73,7 @@ set name = "Use Scope" set popup_menu = 1 - toggle_scope(2.0) + toggle_scope(usr, 2.0) ////////////// Dragunov Sniper Rifle ////////////// @@ -111,4 +111,4 @@ set name = "Use Scope" set popup_menu = 1 - toggle_scope(2.0) + toggle_scope(usr, 2.0)