Files
Batrachophreno 8111a8489b Restore many missing inhand sprites for items, add/port others (#21831)
Many, many, many items have inhand sprites in their .dmis but for
whatever reasons do not display them in-game. This PR:

1. Updates many item definitions to point to their already-existing
inhands correctly. This consists largely of held tools, but also gas
tanks and jetpacks mounted in the suit storage slot.

2. Adds a few codersprites made by me for objects with either missing
inhands or poorly matching mishands (IE, the tape recorder, which has a
black case, reused the white inhand sprites of the health analyzer). The
new sprites are modified or recolored variations of other inhand sprites
from our repo, except for circuitboards which are new.
<img width="444" height="400" alt="image"
src="https://github.com/user-attachments/assets/7f107b9a-fe24-4e31-8f16-4d34768ee117"
/>


3. Adds inhand sprites for Inflatables and Inflatable Boxes made by
Tomixcomics.
<img width="424" height="101" alt="image"
src="https://github.com/user-attachments/assets/434107c4-8577-49a2-a58e-d6b014c03933"
/>

4. Ports inhand sprites for the Hydraulic Rescue Tool from tg's Jaws of
Life.
<img width="224" height="94" alt="Screenshot 2026-02-07 172931"
src="https://github.com/user-attachments/assets/070c7956-f6a8-4fb5-870f-10c64afcc8b3"
/>

5. Some additional cleanup while in the area. The 'analyzer' has been
renamed the 'gas analyzer' to be consistent with the other analyzer
objects, standardized icon_state naming conventions where I saw
oddballs, updated code docs to use DMDocs when in the area, etc.

### Asset Licenses
The following assets that **have not** been created by myself are
included in this PR:

| Path | Original Author | License |
| --- | --- | --- |
| icons/obj/item/hydraulic_rescue_tool.dmi | [SomeAngryMiner (bee
station)](https://github.com/BeeStation/BeeStation-Hornet/pull/2487),
[maxymax
(/tg/station)](https://github.com/tgstation/tgstation/pull/58616) |
CC-BY-SA |
| icons/obj/item/inflatables.dmi |
[Tomixcomics](https://github.com/tomixcomics) | CC-BY-SA |
2026-02-17 17:51:22 +00:00

102 lines
3.8 KiB
Plaintext

/obj/item/paper_scanner
name = "paper scanner"
desc = "A simple device that can be used to scan paper or paper bundles in order to digitize them."
icon = 'icons/obj/item/scanner.dmi'
icon_state = "paperscanner"
item_state = "paperscanner"
contained_sprite = TRUE
var/obj/item/computer_hardware/hard_drive/portable/drive
/obj/item/paper_scanner/mechanics_hints(mob/user, distance, is_adjacent)
. += ..()
. += "Click paper or a paper bundle with it to digitize it and store it in the inserted drive."
. += "ALT-click it while it's in one of your hands to eject the portable drive."
/obj/item/paper_scanner/Initialize(mapload, ...)
. = ..()
drive = new /obj/item/computer_hardware/hard_drive/portable(src)
update_icon()
/obj/item/paper_scanner/update_icon()
ClearOverlays()
if(drive)
AddOverlays("paperscanner-drive")
/obj/item/paper_scanner/AltClick(mob/living/user)
if(!drive)
to_chat(user, SPAN_WARNING("\The [src] doesn't have a drive installed."))
return
if(!istype(user))
to_chat(user, SPAN_WARNING("You're too simple to work \the [src]."))
return
if(user.l_hand == src || user.r_hand == src || issilicon(user))
to_chat(user, SPAN_NOTICE("You eject \the [drive]."))
user.put_in_hands(drive)
drive = null
update_icon()
else
to_chat(user, SPAN_WARNING("You must be holding \the [src] in one of your hands before you can eject a drive."))
/obj/item/paper_scanner/attackby(obj/item/attacking_item, mob/user)
if(istype(attacking_item, /obj/item/computer_hardware/hard_drive/portable))
if(drive)
to_chat(user, SPAN_WARNING("\The [src] already has a drive installed!"))
return TRUE
to_chat(user, SPAN_NOTICE("You insert \the [attacking_item] into \the [src]."))
user.drop_from_inventory(attacking_item, src)
drive = attacking_item
update_icon()
return TRUE
else
return ..()
/obj/item/paper_scanner/afterattack(atom/target, mob/user, proximity_flag, click_parameters)
if(proximity_flag && (istype(target, /obj/item/paper) || istype(target, /obj/item/paper_bundle)))
do_scan(target, user)
/obj/item/paper_scanner/proc/do_scan(var/obj/item/target, var/mob/user)
if(!drive)
to_chat(user, SPAN_WARNING("\The [src] doesn't have a drive installed."))
return
var/list/pages_to_scan = list()
var/obj/item/paper/P = target
var/obj/item/paper_bundle/PB = target
if(istype(P))
if(!P.info)
to_chat(user, SPAN_WARNING("\The [P] doesn't have any information on it."))
return
pages_to_scan += P
else if(istype(PB))
var/has_info = FALSE
for(var/obj/item/paper/page in PB.pages)
if(page.info)
pages_to_scan += page
has_info = TRUE
if(!has_info)
to_chat(user, SPAN_WARNING("\The [PB] doesn't have any information in it."))
return
if(!length(pages_to_scan))
return
user.visible_message("<b>[user]</b> starts making a scan of \the [target]...", SPAN_NOTICE("You start making a scan of \the [target]..."), range = 3)
if(do_after(user, 30 * length(pages_to_scan), target))
if(!drive)
to_chat(user, SPAN_WARNING("\The [src] doesn't have a drive installed."))
return
user.visible_message("<b>[user]</b> makes a scan of \the [target].", SPAN_NOTICE("You make a scan of \the [target]."), range = 3)
var/datum/computer_file/data/F = new /datum/computer_file/data(drive)
F.filename = target.name != initial(target.name) ? "[target.name] ([worldtime2text()] - [time2text(world.time, "Month DD")])" : "Digital Paper ([worldtime2text()] - [time2text(world.time, "Month DD")])"
F.filetype = "TXT"
var/data_to_save = ""
for(var/thing in pages_to_scan)
var/obj/item/paper/page = thing
var/p_info = html2pencode(page.info)
data_to_save += strip_html_properly(p_info)
data_to_save += "\[br\]"
F.stored_data = data_to_save
if(!drive.store_file(F))
to_chat(user, SPAN_WARNING("\The [drive] does not have enough space to store the latest scanned file."))