mirror of
https://github.com/VOREStation/VOREStation.git
synced 2026-07-19 11:05:50 +01:00
Disposal Connector Component (#18431)
* looks like we're just recoding disposals entirely lol * wip * fixes * doc * code cleanup * define use * use doafter * disposal flooring breaks now properly drop floor sheets * Moved disposal mail tag to packet init instead of before it * modernization * cleans up overrides that shouldn't exist * more cleanup * Update code/modules/recycling/disposal_holder.dm Co-authored-by: Cameron Lennox <killer65311@gmail.com> * Update code/modules/recycling/disposal_holder.dm Co-authored-by: Cameron Lennox <killer65311@gmail.com> * Update code/modules/recycling/disposal_machines.dm Co-authored-by: Cameron Lennox <killer65311@gmail.com> --------- Co-authored-by: Cameron Lennox <killer65311@gmail.com>
This commit is contained in:
@@ -0,0 +1,56 @@
|
||||
/obj/item/destTagger
|
||||
name = "destination tagger"
|
||||
desc = "Used to set the destination of properly wrapped packages."
|
||||
icon = 'icons/obj/device.dmi'
|
||||
icon_state = "dest_tagger"
|
||||
var/currTag = 0
|
||||
|
||||
w_class = ITEMSIZE_SMALL
|
||||
item_state = "electronic"
|
||||
slot_flags = SLOT_BELT
|
||||
pickup_sound = 'sound/items/pickup/device.ogg'
|
||||
drop_sound = 'sound/items/drop/device.ogg'
|
||||
|
||||
/obj/item/destTagger/tgui_state(mob/user)
|
||||
return GLOB.tgui_inventory_state
|
||||
|
||||
/obj/item/destTagger/tgui_interact(mob/user, datum/tgui/ui)
|
||||
ui = SStgui.try_update_ui(user, src, ui)
|
||||
if(!ui)
|
||||
ui = new(user, src, "DestinationTagger", name)
|
||||
ui.open()
|
||||
|
||||
/obj/item/destTagger/tgui_static_data(mob/user)
|
||||
var/list/data = ..()
|
||||
var/list/taggers = list()
|
||||
var/list/tagger_levels = list()
|
||||
for(var/tag in GLOB.tagger_locations)
|
||||
var/z_level = GLOB.tagger_locations[tag]
|
||||
taggers += list(list("tag" = tag, "level" = z_level))
|
||||
tagger_levels += list(list("z" = z_level, "location" = using_map.get_zlevel_name(z_level)))
|
||||
data["taggerLevels"] = tagger_levels
|
||||
data["taggerLocs"] = taggers
|
||||
|
||||
return data
|
||||
|
||||
/obj/item/destTagger/tgui_data(mob/user, datum/tgui/ui)
|
||||
var/list/data = ..()
|
||||
|
||||
data["currTag"] = currTag
|
||||
|
||||
return data
|
||||
|
||||
/obj/item/destTagger/attack_self(mob/user as mob)
|
||||
tgui_interact(user)
|
||||
|
||||
/obj/item/destTagger/tgui_act(action, params, datum/tgui/ui)
|
||||
if(..())
|
||||
return TRUE
|
||||
add_fingerprint(ui.user)
|
||||
switch(action)
|
||||
if("set_tag")
|
||||
var/new_tag = params["tag"]
|
||||
if(!(new_tag in GLOB.tagger_locations))
|
||||
return FALSE
|
||||
currTag = new_tag
|
||||
. = TRUE
|
||||
@@ -17,7 +17,7 @@
|
||||
var/dpdir = 0 // directions as disposalpipe
|
||||
var/base_state = "pipe-s"
|
||||
|
||||
/obj/structure/disposalconstruct/Initialize(mapload, var/newtype, var/newdir, var/flipped, var/newsubtype)
|
||||
/obj/structure/disposalconstruct/Initialize(mapload, newtype, newdir, flipped, newsubtype)
|
||||
. = ..()
|
||||
ptype = newtype
|
||||
dir = newdir
|
||||
@@ -114,7 +114,7 @@
|
||||
|
||||
// hide called by levelupdate if turf intact status changes
|
||||
// change visibility status and force update of icon
|
||||
/obj/structure/disposalconstruct/hide(var/intact)
|
||||
/obj/structure/disposalconstruct/hide(intact)
|
||||
invisibility = (intact && level==1) ? INVISIBILITY_ABSTRACT: INVISIBILITY_NONE // hide if floor is intact
|
||||
update()
|
||||
|
||||
@@ -224,7 +224,7 @@
|
||||
// attackby item
|
||||
// wrench: (un)anchor
|
||||
// weldingtool: convert to real pipe
|
||||
/obj/structure/disposalconstruct/attackby(var/obj/item/I, var/mob/user)
|
||||
/obj/structure/disposalconstruct/attackby(obj/item/I, mob/user)
|
||||
var/nicetype = "pipe"
|
||||
var/ispipe = 0 // Indicates if we should change the level of this pipe
|
||||
src.add_fingerprint(user)
|
||||
@@ -338,9 +338,6 @@
|
||||
var/obj/structure/disposaloutlet/P = new /obj/structure/disposaloutlet(src.loc)
|
||||
src.transfer_fingerprints_to(P)
|
||||
P.set_dir(dir)
|
||||
P.target = get_ranged_target_turf(src, dir, 10) //TODO: replace this with a proc parameter or other cleaner
|
||||
var/obj/structure/disposalpipe/trunk/Trunk = CP
|
||||
Trunk.linked = P
|
||||
|
||||
else if(ptype==DISPOSAL_PIPE_CHUTE)
|
||||
var/obj/machinery/disposal/deliveryChute/P = new /obj/machinery/disposal/deliveryChute(src.loc)
|
||||
|
||||
+46
-1172
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,153 @@
|
||||
// virtual disposal object
|
||||
// travels through pipes in lieu of actual items
|
||||
// contents will be items flushed by the disposal
|
||||
// this allows the gas flushed to be tracked
|
||||
|
||||
/obj/structure/disposalholder
|
||||
invisibility = INVISIBILITY_ABSTRACT
|
||||
var/datum/gas_mixture/gas = null // gas used to flush, will appear at exit point
|
||||
var/active = FALSE // true if the holder is moving, otherwise inactive
|
||||
var/count = 2048 //*** can travel 2048 steps before going inactive (in case of loops)
|
||||
var/destinationTag = "" // changes if contains a delivery container
|
||||
var/hasmob = FALSE //If it contains a mob
|
||||
var/partialTag = "" //set by a partial tagger the first time round, then put in destinationTag if it goes through again.
|
||||
dir = 0
|
||||
|
||||
// initialize a holder from the contents of a disposal unit
|
||||
/obj/structure/disposalholder/proc/init(list/flush_list, datum/gas_mixture/flush_gas)
|
||||
gas = flush_gas// transfer gas resv. into holder object -- let's be explicit about the data this proc consumes, please.
|
||||
|
||||
//Check for any living mobs trigger hasmob.
|
||||
//hasmob effects whether the package goes to cargo or its tagged destination.
|
||||
for(var/mob/living/M in flush_list)
|
||||
if(M.stat != DEAD && !istype(M,/mob/living/silicon/robot/drone))
|
||||
hasmob = TRUE
|
||||
if(M.client)
|
||||
M.client.perspective = EYE_PERSPECTIVE
|
||||
M.client.eye = src
|
||||
|
||||
//Checks 1 contents level deep. This means that players can be sent through disposals...
|
||||
//...but it should require a second person to open the package. (i.e. person inside a wrapped locker)
|
||||
for(var/obj/O in flush_list)
|
||||
if(!O.contents)
|
||||
continue
|
||||
for(var/mob/living/M in O.contents)
|
||||
if(M && M.stat != DEAD && !istype(M,/mob/living/silicon/robot/drone))
|
||||
hasmob = TRUE
|
||||
|
||||
// now everything inside the disposal gets put into the holder
|
||||
// note AM since can contain mobs or objs
|
||||
for(var/atom/movable/AM in flush_list)
|
||||
AM.forceMove(src)
|
||||
// Mail will use it's sorting tag if dropped into disposals
|
||||
if(istype(AM, /obj/structure/bigDelivery) && !hasmob)
|
||||
var/obj/structure/bigDelivery/T = AM
|
||||
src.destinationTag = T.sortTag
|
||||
if(istype(AM, /obj/item/smallDelivery) && !hasmob)
|
||||
var/obj/item/smallDelivery/T = AM
|
||||
src.destinationTag = T.sortTag
|
||||
if(istype(AM, /obj/item/mail) && !hasmob)
|
||||
var/obj/item/mail/T = AM
|
||||
src.destinationTag = T.sortTag
|
||||
// Drones can mail themselves through maint.
|
||||
if(istype(AM, /mob/living/silicon/robot/drone))
|
||||
var/mob/living/silicon/robot/drone/drone = AM
|
||||
src.destinationTag = drone.mail_destination
|
||||
|
||||
// movement process, persists while holder is moving through pipes
|
||||
/obj/structure/disposalholder/proc/move()
|
||||
if(!active)
|
||||
return
|
||||
|
||||
// Clonk n' bonk
|
||||
if(hasmob && prob(3))
|
||||
for(var/mob/living/H in src)
|
||||
if(!istype(H,/mob/living/silicon/robot/drone)) //Drones use the mailing code to move through the disposal system,
|
||||
H.take_overall_damage(20, 0, "Blunt Trauma")//horribly maim any living creature jumping down disposals. c'est la vie
|
||||
|
||||
// Transfer to next segment
|
||||
var/obj/structure/disposalpipe/last = loc
|
||||
var/obj/structure/disposalpipe/curr = last.transfer(src)
|
||||
if(!active)
|
||||
return // Handled by a machine connected to a trunk during transfer()
|
||||
if(!curr)
|
||||
last.expel(src, get_turf(loc), dir)
|
||||
return
|
||||
|
||||
// Onto the next segment
|
||||
if(!(count--))
|
||||
active = FALSE
|
||||
return
|
||||
addtimer(CALLBACK(src, PROC_REF(move)), 1, TIMER_DELETE_ME)
|
||||
|
||||
|
||||
// find the turf which should contain the next pipe
|
||||
/obj/structure/disposalholder/proc/nextloc()
|
||||
return get_step(loc,dir)
|
||||
|
||||
// find a matching pipe on a turf
|
||||
/obj/structure/disposalholder/proc/findpipe(turf/T)
|
||||
if(!T)
|
||||
return null
|
||||
var/fdir = turn(dir, 180) // flip the movement direction
|
||||
for(var/obj/structure/disposalpipe/P in T)
|
||||
if(fdir & P.dpdir) // find pipe direction mask that matches flipped dir
|
||||
return P
|
||||
// if no matching pipe, return null
|
||||
return null
|
||||
|
||||
// merge two holder objects
|
||||
// used when a a holder meets a stuck holder
|
||||
/obj/structure/disposalholder/proc/merge(obj/structure/disposalholder/other)
|
||||
for(var/atom/movable/AM in other)
|
||||
AM.forceMove(src) // move everything in other holder to this one
|
||||
if(ismob(AM))
|
||||
var/mob/M = AM
|
||||
if(M.client) // if a client mob, update eye to follow this holder
|
||||
M.client.eye = src
|
||||
qdel(other)
|
||||
|
||||
/obj/structure/disposalholder/proc/settag(new_tag)
|
||||
destinationTag = new_tag
|
||||
|
||||
/obj/structure/disposalholder/proc/setpartialtag(new_tag)
|
||||
if(partialTag == new_tag)
|
||||
destinationTag = new_tag
|
||||
partialTag = ""
|
||||
else
|
||||
partialTag = new_tag
|
||||
|
||||
|
||||
// called when player tries to move while in a pipe
|
||||
/obj/structure/disposalholder/relaymove(mob/living/user)
|
||||
if(!isliving(user))
|
||||
return
|
||||
|
||||
if(user.stat || user.last_special <= world.time)
|
||||
return
|
||||
user.last_special = world.time+100
|
||||
|
||||
if(QDELETED(src))
|
||||
return
|
||||
|
||||
for(var/mob/M in hearers(get_turf(src)))
|
||||
to_chat(M, "<FONT size=[max(0, 5 - get_dist(src, M))]>CLONG, clong!</FONT>")
|
||||
playsound(src, 'sound/effects/clang.ogg', 50, 0, 0)
|
||||
|
||||
// called to vent all gas in holder to a location
|
||||
/obj/structure/disposalholder/proc/vent_gas(atom/location)
|
||||
location.assume_air(gas) // vent all gas to turf
|
||||
return
|
||||
|
||||
/obj/structure/disposalholder/Destroy()
|
||||
QDEL_NULL(gas)
|
||||
if(contents.len)
|
||||
var/turf/qdelloc = get_turf(src)
|
||||
if(qdelloc)
|
||||
for(var/atom/movable/AM in contents)
|
||||
AM.forceMove(qdelloc)
|
||||
else
|
||||
log_and_message_admins("A disposal holder was deleted with contents in nullspace") //ideally, this should never happen
|
||||
|
||||
active = FALSE
|
||||
return ..()
|
||||
@@ -0,0 +1,197 @@
|
||||
/obj/structure/disposalpipe/junction/yjunction
|
||||
icon_state = "pipe-y"
|
||||
|
||||
//a three-way junction with dir being the dominant direction
|
||||
/obj/structure/disposalpipe/junction
|
||||
icon_state = "pipe-j1"
|
||||
|
||||
/obj/structure/disposalpipe/junction/Initialize(mapload)
|
||||
. = ..()
|
||||
if(icon_state == "pipe-j1")
|
||||
dpdir = dir | turn(dir, -90) | turn(dir,180)
|
||||
else if(icon_state == "pipe-j2")
|
||||
dpdir = dir | turn(dir, 90) | turn(dir,180)
|
||||
else // pipe-y
|
||||
dpdir = dir | turn(dir,90) | turn(dir, -90)
|
||||
update()
|
||||
return
|
||||
|
||||
|
||||
// next direction to move
|
||||
// if coming in from secondary dirs, then next is primary dir
|
||||
// if coming in from primary dir, then next is equal chance of other dirs
|
||||
|
||||
/obj/structure/disposalpipe/junction/nextdir(fromdir)
|
||||
var/flipdir = turn(fromdir, 180)
|
||||
if(flipdir != dir) // came from secondary dir
|
||||
return dir // so exit through primary
|
||||
else // came from primary
|
||||
// so need to choose either secondary exit
|
||||
var/mask = ..(fromdir)
|
||||
|
||||
// find a bit which is set
|
||||
var/setbit = 0
|
||||
if(mask & NORTH)
|
||||
setbit = NORTH
|
||||
else if(mask & SOUTH)
|
||||
setbit = SOUTH
|
||||
else if(mask & EAST)
|
||||
setbit = EAST
|
||||
else
|
||||
setbit = WEST
|
||||
|
||||
if(prob(50)) // 50% chance to choose the found bit or the other one
|
||||
return setbit
|
||||
else
|
||||
return mask & (~setbit)
|
||||
|
||||
//a three-way junction that sorts objects
|
||||
/obj/structure/disposalpipe/sortjunction
|
||||
name = "sorting junction"
|
||||
icon_state = "pipe-j1s"
|
||||
desc = "An underfloor disposal pipe with a package sorting mechanism."
|
||||
|
||||
var/sortdir = 0
|
||||
|
||||
var/last_sort = FALSE
|
||||
var/sort_scan = TRUE
|
||||
var/panel_open = FALSE
|
||||
var/datum/wires/wires = null // ...Why isnt this defined on /atom...
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/proc/updatedesc()
|
||||
desc = initial(desc)
|
||||
if(sortType)
|
||||
desc += "\nIt's filtering objects with the '[sortType]' tag."
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/proc/updatename()
|
||||
if(sortType)
|
||||
name = "[initial(name)] ([sortType])"
|
||||
else
|
||||
name = initial(name)
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/Destroy()
|
||||
QDEL_NULL(wires)
|
||||
. = ..()
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/proc/updatedir()
|
||||
var/negdir = turn(dir, 180)
|
||||
|
||||
if(icon_state == "pipe-j1s")
|
||||
sortdir = turn(dir, -90)
|
||||
else if(icon_state == "pipe-j2s")
|
||||
sortdir = turn(dir, 90)
|
||||
|
||||
dpdir = sortdir | dir | negdir
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/Initialize(mapload)
|
||||
. = ..()
|
||||
if(sortType) GLOB.tagger_locations |= list("[sortType]" = get_z(src))
|
||||
|
||||
wires = new /datum/wires/disposals(src)
|
||||
|
||||
updatedir()
|
||||
updatename()
|
||||
updatedesc()
|
||||
update()
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/attackby(obj/item/I, mob/user)
|
||||
if(..())
|
||||
return
|
||||
|
||||
if(I.has_tool_quality(TOOL_SCREWDRIVER)) //Who is screwdriver_act()?
|
||||
panel_open = !panel_open
|
||||
playsound(src, I.usesound, 100, 1)
|
||||
to_chat(user, span_notice("You [panel_open ? "open" : "close"] the wire panel."))
|
||||
update_icon()
|
||||
return
|
||||
|
||||
if(panel_open && is_wire_tool(I))
|
||||
wires.Interact(user)
|
||||
return TRUE
|
||||
|
||||
if(istype(I, /obj/item/destTagger))
|
||||
var/obj/item/destTagger/O = I
|
||||
|
||||
if(O.currTag)// Tag set
|
||||
sortType = O.currTag
|
||||
playsound(src, 'sound/machines/twobeep.ogg', 100, 1)
|
||||
to_chat(user, span_blue("Changed filter to '[sortType]'."))
|
||||
updatename()
|
||||
updatedesc()
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/proc/divert_check(checkTag)
|
||||
return sortType == checkTag
|
||||
|
||||
// next direction to move
|
||||
// if coming in from negdir then next is primary dir or sortdir
|
||||
// if coming in from dir, Then next is negdir or sortdir
|
||||
// if coming in from sortdir, always go to posdir
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/nextdir(fromdir, sortTag)
|
||||
if(sort_scan)
|
||||
if(divert_check(sortTag))
|
||||
if(!wires.is_cut(WIRE_SORT_SIDE))
|
||||
last_sort = TRUE
|
||||
else
|
||||
if(!wires.is_cut(WIRE_SORT_FORWARD))
|
||||
last_sort = FALSE
|
||||
if(fromdir != sortdir && last_sort)
|
||||
return sortdir
|
||||
// so go with the flow to positive direction
|
||||
return dir
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/proc/reset_scan()
|
||||
if(!wires.is_cut(WIRE_SORT_SCAN))
|
||||
sort_scan = TRUE
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/transfer(obj/structure/disposalholder/H)
|
||||
var/nextdir = nextdir(H.dir, H.destinationTag)
|
||||
H.set_dir(nextdir)
|
||||
var/turf/T = H.nextloc()
|
||||
var/obj/structure/disposalpipe/P = H.findpipe(T)
|
||||
|
||||
if(P)
|
||||
// find other holder in next loc, if inactive merge it with current
|
||||
var/obj/structure/disposalholder/H2 = locate() in P
|
||||
if(H2 && !H2.active)
|
||||
H.merge(H2)
|
||||
|
||||
H.forceMove(P)
|
||||
else // if wasn't a pipe, then set loc to turf
|
||||
H.forceMove(T)
|
||||
return null
|
||||
|
||||
return P
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/update_icon()
|
||||
cut_overlays()
|
||||
. = ..()
|
||||
if(panel_open)
|
||||
add_overlay("[icon_state]-open")
|
||||
|
||||
//a three-way junction that filters all wrapped and tagged items
|
||||
/obj/structure/disposalpipe/sortjunction/wildcard
|
||||
name = "wildcard sorting junction"
|
||||
desc = "An underfloor disposal pipe which filters all wrapped and tagged items."
|
||||
subtype = 1
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/wildcard/divert_check(checkTag)
|
||||
return checkTag != ""
|
||||
|
||||
//junction that filters all untagged items
|
||||
/obj/structure/disposalpipe/sortjunction/untagged
|
||||
name = "untagged sorting junction"
|
||||
desc = "An underfloor disposal pipe which filters all untagged items."
|
||||
subtype = 2
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/untagged/divert_check(checkTag)
|
||||
return checkTag == ""
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/flipped //for easier and cleaner mapping
|
||||
icon_state = "pipe-j2s"
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/wildcard/flipped
|
||||
icon_state = "pipe-j2s"
|
||||
|
||||
/obj/structure/disposalpipe/sortjunction/untagged/flipped
|
||||
icon_state = "pipe-j2s"
|
||||
@@ -0,0 +1,492 @@
|
||||
// Disposal bin
|
||||
// Holds items for disposal into pipe system
|
||||
// Draws air from turf, gradually charges internal reservoir
|
||||
// Once full (~1 atm), uses air resv to flush items into the pipes
|
||||
// Automatically recharges air (unless off), will flush when ready if pre-set
|
||||
// Can hold items and human size things, no other draggables
|
||||
// Toilets are a type of disposal bin for small objects only and work on magic. By magic, I mean torque rotation
|
||||
#define SEND_PRESSURE (0.05 + ONE_ATMOSPHERE) //kPa - assume the inside of a dispoal pipe is 1 atm, so that needs to be added.
|
||||
#define PRESSURE_TANK_VOLUME 150 //L
|
||||
#define PUMP_MAX_FLOW_RATE 11.25 //L/s - 4 m/s using a 15 cm by 15 cm inlet //NOTE: I reduced the send pressure from 801 to 101.05 which is about 1/8 there was originally, and this was 90 before that. 90/8 is about 11.25, so that's the new value. -Reo
|
||||
#define DISPOSALMODE_EJECTONLY -1
|
||||
#define DISPOSALMODE_OFF 0
|
||||
#define DISPOSALMODE_CHARGING 1
|
||||
#define DISPOSALMODE_CHARGED 2
|
||||
|
||||
/obj/machinery/disposal
|
||||
name = "disposal unit"
|
||||
desc = "A pneumatic waste disposal unit."
|
||||
icon = 'icons/obj/pipes/disposal.dmi'
|
||||
icon_state = "disposal"
|
||||
anchored = TRUE
|
||||
density = TRUE
|
||||
var/datum/gas_mixture/air_contents // internal reservoir
|
||||
var/mode = DISPOSALMODE_CHARGING
|
||||
var/flush = FALSE // true if flush handle is pulled
|
||||
var/flushing = FALSE // true if flushing in progress
|
||||
var/flush_every_ticks = 30 //Every 30 ticks it will look whether it is ready to flush
|
||||
var/flush_count = 0 //this var adds 1 once per tick. When it reaches flush_every_ticks it resets and tries to flush.
|
||||
active_power_usage = 2200 //the pneumatic pump power. 3 HP ~ 2200W
|
||||
idle_power_usage = 100
|
||||
var/stat_tracking = TRUE
|
||||
|
||||
// create a new disposal
|
||||
// find the attached trunk (if present) and init gas resvr.
|
||||
/obj/machinery/disposal/Initialize(mapload)
|
||||
. = ..()
|
||||
|
||||
var/obj/structure/disposalpipe/trunk/trunk = locate() in loc
|
||||
if(!trunk)
|
||||
mode = DISPOSALMODE_OFF
|
||||
flush = FALSE
|
||||
|
||||
air_contents = new(PRESSURE_TANK_VOLUME)
|
||||
update()
|
||||
AddComponent(/datum/component/disposal_system_connection)
|
||||
|
||||
/obj/machinery/disposal/Destroy()
|
||||
eject()
|
||||
return ..()
|
||||
|
||||
// attack by item places it in to disposal
|
||||
/obj/machinery/disposal/attackby(obj/item/I, mob/user)
|
||||
if(stat & BROKEN || !I || !user)
|
||||
return
|
||||
|
||||
add_fingerprint(user)
|
||||
if(mode <= DISPOSALMODE_OFF) // It's off
|
||||
if(I.has_tool_quality(TOOL_SCREWDRIVER))
|
||||
if(contents.len > 0)
|
||||
to_chat(user, "Eject the items first!")
|
||||
return
|
||||
if(mode == DISPOSALMODE_OFF) // It's off but still not unscrewed
|
||||
mode = DISPOSALMODE_EJECTONLY // Set it to doubleoff l0l
|
||||
playsound(src, I.usesound, 50, 1)
|
||||
to_chat(user, "You remove the screws around the power connection.")
|
||||
return
|
||||
else if(mode == DISPOSALMODE_EJECTONLY)
|
||||
mode = DISPOSALMODE_OFF
|
||||
playsound(src, I.usesound, 50, 1)
|
||||
to_chat(user, "You attach the screws around the power connection.")
|
||||
return
|
||||
else if(I.has_tool_quality(TOOL_WELDER) && mode == DISPOSALMODE_EJECTONLY)
|
||||
if(contents.len > 0)
|
||||
to_chat(user, "Eject the items first!")
|
||||
return
|
||||
var/obj/item/weldingtool/W = I.get_welder()
|
||||
if(W.remove_fuel(0,user))
|
||||
playsound(src, W.usesound, 100, 1)
|
||||
to_chat(user, "You start slicing the floorweld off the disposal unit.")
|
||||
|
||||
if(do_after(user, 2 SECONDS * W.toolspeed, target = src))
|
||||
if(!src || !W.isOn()) return
|
||||
to_chat(user, "You sliced the floorweld off the disposal unit.")
|
||||
var/obj/structure/disposalconstruct/C = new (get_turf(src))
|
||||
transfer_fingerprints_to(C)
|
||||
C.ptype = 6 // 6 = disposal unit
|
||||
C.anchored = TRUE
|
||||
C.density = TRUE
|
||||
C.update()
|
||||
qdel(src)
|
||||
return
|
||||
else
|
||||
to_chat(user, "You need more welding fuel to complete this task.")
|
||||
return
|
||||
|
||||
|
||||
if(istype(I, /obj/item/storage/bag/trash))
|
||||
var/obj/item/storage/bag/trash/T = I
|
||||
to_chat(user, span_blue("You empty the bag."))
|
||||
for(var/obj/item/O in T.contents)
|
||||
T.remove_from_storage(O,src)
|
||||
T.update_icon()
|
||||
update()
|
||||
return
|
||||
|
||||
if(istype(I, /obj/item/material/ashtray))
|
||||
var/obj/item/material/ashtray/A = I
|
||||
if(A.contents.len > 0)
|
||||
user.visible_message(span_infoplain(span_bold("\The [user]") + " empties \the [A] into [src]."))
|
||||
for(var/obj/item/O in A.contents)
|
||||
O.forceMove(src)
|
||||
A.update_icon()
|
||||
update()
|
||||
return
|
||||
|
||||
var/obj/item/grab/G = I
|
||||
if(istype(G)) // handle grabbed mob
|
||||
if(ismob(G.affecting))
|
||||
var/mob/GM = G.affecting
|
||||
for (var/mob/V in viewers(user))
|
||||
V.show_message("[user] starts putting [GM.name] into the disposal.", 3)
|
||||
if(do_after(user, 2 SECONDS, target = src))
|
||||
if (GM.client)
|
||||
GM.client.perspective = EYE_PERSPECTIVE
|
||||
GM.client.eye = src
|
||||
GM.forceMove(src)
|
||||
for (var/mob/C in viewers(src))
|
||||
C.show_message(span_red("[GM.name] has been placed in the [src] by [user]."), 3)
|
||||
qdel(G)
|
||||
|
||||
add_attack_logs(user,GM,"Disposals dunked")
|
||||
return
|
||||
|
||||
if(isrobot(user))
|
||||
return
|
||||
if(!I || I.anchored || !I.canremove)
|
||||
return
|
||||
|
||||
user.drop_item()
|
||||
if(I)
|
||||
if(istype(I, /obj/item/holder))
|
||||
var/obj/item/holder/holder = I
|
||||
var/mob/victim = holder.held_mob
|
||||
if(ishuman(victim) || victim.client)
|
||||
log_and_message_admins("placed [victim] inside \the [src]", user)
|
||||
victim.forceMove(src)
|
||||
|
||||
I.forceMove(src)
|
||||
|
||||
user.visible_message("[user] places \the [I] into the [src].", "You place \the [I] into the [src].","Ca-Clunk")
|
||||
update()
|
||||
|
||||
// mouse drop another mob or self
|
||||
//
|
||||
/obj/machinery/disposal/MouseDrop_T(mob/target, mob/user)
|
||||
if(user.stat || !user.canmove || !istype(target))
|
||||
return
|
||||
if(target.buckled || get_dist(user, src) > 1 || get_dist(user, target) > 1)
|
||||
return
|
||||
|
||||
//animals cannot put mobs other than themselves into disposal
|
||||
if(isanimal(user) && target != user)
|
||||
return
|
||||
|
||||
add_fingerprint(user)
|
||||
var/target_loc = target.loc
|
||||
var/msg
|
||||
for (var/mob/V in viewers(user))
|
||||
if(target == user && !user.stat && !user.weakened && !user.stunned && !user.paralysis)
|
||||
V.show_message("[user] starts climbing into the disposal.", 3)
|
||||
if(target != user && !user.restrained() && !user.stat && !user.weakened && !user.stunned && !user.paralysis)
|
||||
if(target.anchored) return
|
||||
V.show_message("[user] starts stuffing [target.name] into the disposal.", 3)
|
||||
if(!do_after(user, 2 SECONDS, target))
|
||||
return
|
||||
if(target_loc != target.loc)
|
||||
return
|
||||
if(target == user && !user.stat && !user.weakened && !user.stunned && !user.paralysis) // if drop self, then climbed in
|
||||
// must be awake, not stunned or whatever
|
||||
msg = "[user.name] climbs into the [src]."
|
||||
to_chat(user, "You climb into the [src].")
|
||||
log_and_message_admins("climbed into disposals!", user)
|
||||
else if(target != user && !user.restrained() && !user.stat && !user.weakened && !user.stunned && !user.paralysis)
|
||||
msg = "[user.name] stuffs [target.name] into the [src]!"
|
||||
to_chat(user, "You stuff [target.name] into the [src]!")
|
||||
|
||||
add_attack_logs(user,target,"Disposals dunked")
|
||||
else
|
||||
return
|
||||
if (target.client)
|
||||
target.client.perspective = EYE_PERSPECTIVE
|
||||
target.client.eye = src
|
||||
|
||||
target.forceMove(src)
|
||||
|
||||
for (var/mob/C in viewers(src))
|
||||
if(C == user)
|
||||
continue
|
||||
C.show_message(msg, 3)
|
||||
|
||||
update()
|
||||
return
|
||||
|
||||
// attempt to move while inside
|
||||
/obj/machinery/disposal/relaymove(mob/user)
|
||||
if(user.stat || flushing)
|
||||
return
|
||||
if(user.loc == src)
|
||||
go_out(user)
|
||||
return
|
||||
|
||||
// leave the disposal
|
||||
/obj/machinery/disposal/proc/go_out(mob/user)
|
||||
if (user.client)
|
||||
user.client.eye = user.client.mob
|
||||
user.client.perspective = MOB_PERSPECTIVE
|
||||
user.forceMove(get_turf(src))
|
||||
update()
|
||||
return
|
||||
|
||||
// ai as human but can't flush
|
||||
/obj/machinery/disposal/attack_ai(mob/user)
|
||||
add_hiddenprint(user)
|
||||
tgui_interact(user)
|
||||
|
||||
// human interact with machine
|
||||
/obj/machinery/disposal/attack_hand(mob/user)
|
||||
if(stat & BROKEN)
|
||||
return
|
||||
|
||||
if(user && user.loc == src)
|
||||
to_chat(user, span_red("You cannot reach the controls from inside."))
|
||||
return
|
||||
|
||||
// Clumsy folks can only flush it.
|
||||
if(user.IsAdvancedToolUser(1))
|
||||
tgui_interact(user)
|
||||
else
|
||||
flush = !flush
|
||||
update()
|
||||
return
|
||||
|
||||
// user interaction
|
||||
/obj/machinery/disposal/tgui_interact(mob/user, datum/tgui/ui = null)
|
||||
ui = SStgui.try_update_ui(user, src, ui)
|
||||
if(!ui)
|
||||
ui = new(user, src, "DisposalBin")
|
||||
ui.open()
|
||||
|
||||
/obj/machinery/disposal/tgui_data(mob/user)
|
||||
var/list/data = list()
|
||||
|
||||
data["isAI"] = isAI(user)
|
||||
data["flushing"] = flush
|
||||
data["mode"] = mode
|
||||
data["pressure"] = round(clamp(100* air_contents.return_pressure() / (SEND_PRESSURE), 0, 100),1)
|
||||
|
||||
return data
|
||||
|
||||
/obj/machinery/disposal/tgui_act(action, list/params, datum/tgui/ui, datum/tgui_state/state)
|
||||
if(..())
|
||||
return
|
||||
|
||||
if(ui.user.loc == src)
|
||||
to_chat(ui.user, span_warning("You cannot reach the controls from inside."))
|
||||
return TRUE
|
||||
|
||||
if(mode == DISPOSALMODE_EJECTONLY && action != "eject") // If the mode is -1, only allow ejection
|
||||
to_chat(ui.user, span_warning("The disposal units power is disabled."))
|
||||
return
|
||||
|
||||
if(stat & BROKEN)
|
||||
return
|
||||
|
||||
add_fingerprint(ui.user)
|
||||
|
||||
if(flushing)
|
||||
return
|
||||
|
||||
if(isturf(loc))
|
||||
if(action == "pumpOn")
|
||||
mode = DISPOSALMODE_CHARGING
|
||||
update()
|
||||
if(action == "pumpOff")
|
||||
mode = DISPOSALMODE_OFF
|
||||
update()
|
||||
|
||||
if(action == "engageHandle")
|
||||
flush = TRUE
|
||||
update()
|
||||
if(action == "disengageHandle")
|
||||
flush = FALSE
|
||||
update()
|
||||
|
||||
if(action == "eject")
|
||||
eject()
|
||||
|
||||
return TRUE
|
||||
|
||||
// eject the contents of the disposal unit
|
||||
|
||||
/obj/machinery/disposal/verb/force_eject()
|
||||
set src in oview(1)
|
||||
set category = "Object"
|
||||
set name = "Force Eject"
|
||||
if(flushing)
|
||||
return
|
||||
eject()
|
||||
|
||||
/obj/machinery/disposal/proc/eject()
|
||||
for(var/atom/movable/AM in src)
|
||||
AM.forceMove(get_turf(src))
|
||||
AM.pipe_eject(0)
|
||||
update()
|
||||
|
||||
// update the icon & overlays to reflect mode & status
|
||||
/obj/machinery/disposal/proc/update()
|
||||
cut_overlays()
|
||||
if(stat & BROKEN)
|
||||
icon_state = "disposal-broken"
|
||||
mode = DISPOSALMODE_OFF
|
||||
flush = 0
|
||||
return
|
||||
|
||||
// flush handle
|
||||
if(flush)
|
||||
add_overlay("[initial(icon_state)]-handle")
|
||||
|
||||
// only handle is shown if no power
|
||||
if(stat & NOPOWER || mode == DISPOSALMODE_EJECTONLY)
|
||||
return
|
||||
|
||||
// check for items in disposal - occupied light
|
||||
if(contents.len > 0)
|
||||
add_overlay("[initial(icon_state)]-full")
|
||||
|
||||
// charging and ready light
|
||||
if(mode == DISPOSALMODE_CHARGING)
|
||||
add_overlay("[initial(icon_state)]-charge")
|
||||
else if(mode == DISPOSALMODE_CHARGED)
|
||||
add_overlay("[initial(icon_state)]-ready")
|
||||
|
||||
// timed process
|
||||
// charge the gas reservoir and perform flush if ready
|
||||
/obj/machinery/disposal/process()
|
||||
if(!air_contents || (stat & BROKEN)) // nothing can happen if broken
|
||||
update_use_power(USE_POWER_OFF)
|
||||
return
|
||||
|
||||
flush_count++
|
||||
if( flush_count >= flush_every_ticks )
|
||||
if( contents.len )
|
||||
if(mode == DISPOSALMODE_CHARGED)
|
||||
spawn(0)
|
||||
feedback_inc("disposal_auto_flush",1)
|
||||
flush()
|
||||
flush_count = 0
|
||||
|
||||
if(flush && air_contents.return_pressure() >= SEND_PRESSURE ) // flush can happen even without power
|
||||
flush()
|
||||
|
||||
if(mode != DISPOSALMODE_CHARGING) //if off or ready, no need to charge
|
||||
update_use_power(USE_POWER_IDLE)
|
||||
else if(air_contents.return_pressure() >= SEND_PRESSURE)
|
||||
mode = DISPOSALMODE_CHARGED //if full enough, switch to ready mode
|
||||
update()
|
||||
else
|
||||
pressurize() //otherwise charge
|
||||
|
||||
/obj/machinery/disposal/proc/pressurize()
|
||||
if(stat & NOPOWER) // won't charge if no power
|
||||
update_use_power(USE_POWER_OFF)
|
||||
return
|
||||
|
||||
var/atom/L = loc // recharging from loc turf
|
||||
var/datum/gas_mixture/env = L.return_air()
|
||||
|
||||
var/power_draw = -1
|
||||
if(env && env.temperature > 0)
|
||||
var/transfer_moles = (PUMP_MAX_FLOW_RATE/env.volume)*env.total_moles //group_multiplier is divided out here
|
||||
power_draw = pump_gas(src, env, air_contents, transfer_moles, active_power_usage)
|
||||
|
||||
if (power_draw > 0)
|
||||
use_power(power_draw)
|
||||
|
||||
// perform a flush
|
||||
/obj/machinery/disposal/proc/flush()
|
||||
if(flushing)
|
||||
return
|
||||
|
||||
flushing = TRUE
|
||||
flick("[icon_state]-flush", src)
|
||||
// wait for animation to finish
|
||||
addtimer(CALLBACK(src, PROC_REF(flush_animation)), 1 SECOND, TIMER_DELETE_ME)
|
||||
|
||||
/obj/machinery/disposal/proc/flush_animation()
|
||||
PROTECTED_PROC(TRUE)
|
||||
// wait for animation to finish
|
||||
playsound(src, 'sound/machines/disposalflush.ogg', 50, 0, 0)
|
||||
addtimer(CALLBACK(src, PROC_REF(flush_resolve)), 0.5 SECOND, TIMER_DELETE_ME)
|
||||
|
||||
/obj/machinery/disposal/proc/flush_resolve()
|
||||
SEND_SIGNAL(src,COMSIG_DISPOSAL_FLUSH,air_contents)
|
||||
air_contents = new(PRESSURE_TANK_VOLUME) // new empty gas resv. Disposal packet takes ownership of the original one!
|
||||
if(stat_tracking)
|
||||
GLOB.disposals_flush_shift_roundstat++
|
||||
flushing = FALSE
|
||||
|
||||
// now reset disposal state
|
||||
flush = FALSE
|
||||
if(mode == DISPOSALMODE_CHARGED) // if was ready,
|
||||
mode = DISPOSALMODE_CHARGING // switch to charging
|
||||
update()
|
||||
return
|
||||
|
||||
// called when area power changes
|
||||
/obj/machinery/disposal/power_change()
|
||||
..() // do default setting/reset of stat NOPOWER bit
|
||||
update() // update icon
|
||||
return
|
||||
|
||||
/obj/machinery/disposal/hitby(atom/movable/AM)
|
||||
. = ..()
|
||||
if(istype(AM, /obj/item) && !istype(AM, /obj/item/projectile))
|
||||
if(prob(75))
|
||||
AM.forceMove(src)
|
||||
visible_message("\The [AM] lands in \the [src].")
|
||||
else
|
||||
visible_message("\The [AM] bounces off of \the [src]'s rim!")
|
||||
|
||||
if(istype(AM,/mob/living))
|
||||
if(prob(75))
|
||||
var/mob/living/to_be_dunked = AM
|
||||
if(ishuman(AM) ||to_be_dunked.client)
|
||||
log_and_message_admins("[AM] was thrown into \the [src]", null)
|
||||
AM.forceMove(src)
|
||||
visible_message("\The [AM] lands in \the [src].")
|
||||
|
||||
/obj/machinery/disposal/wall
|
||||
name = "inset disposal unit"
|
||||
icon_state = "wall"
|
||||
|
||||
density = FALSE
|
||||
|
||||
/obj/machinery/disposal/wall/update()
|
||||
..()
|
||||
|
||||
switch(dir)
|
||||
if(1)
|
||||
pixel_x = 0
|
||||
pixel_y = -32
|
||||
if(2)
|
||||
pixel_x = 0
|
||||
pixel_y = 32
|
||||
if(4)
|
||||
pixel_x = -32
|
||||
pixel_y = 0
|
||||
if(8)
|
||||
pixel_x = 32
|
||||
pixel_y = 0
|
||||
|
||||
|
||||
// Cleaner subtype
|
||||
/obj/machinery/disposal/wall/cleaner
|
||||
name = "resleeving equipment deposit"
|
||||
desc = "Automatically cleans and transports items to the local resleeving facilities."
|
||||
icon_state = "bluewall"
|
||||
|
||||
/obj/machinery/disposal/wall/cleaner/flush()
|
||||
if(flushing)
|
||||
return
|
||||
|
||||
// Clean items before sending them
|
||||
for(var/obj/item/flushed_item in src)
|
||||
if(istype(flushed_item, /obj/item/storage))
|
||||
var/obj/item/storage/storage_flushed = flushed_item
|
||||
var/list/storage_items = storage_flushed.return_inv()
|
||||
for(var/obj/item/item in storage_items)
|
||||
item.wash(CLEAN_WASH)
|
||||
continue
|
||||
if(istype(flushed_item, /obj/item))
|
||||
flushed_item.wash(CLEAN_WASH)
|
||||
|
||||
. = ..()
|
||||
|
||||
#undef DISPOSALMODE_EJECTONLY
|
||||
#undef DISPOSALMODE_OFF
|
||||
#undef DISPOSALMODE_CHARGING
|
||||
#undef DISPOSALMODE_CHARGED
|
||||
#undef SEND_PRESSURE
|
||||
#undef PRESSURE_TANK_VOLUME
|
||||
#undef PUMP_MAX_FLOW_RATE
|
||||
@@ -0,0 +1,230 @@
|
||||
/obj/structure/bigDelivery
|
||||
desc = "A big wrapped package."
|
||||
name = "large parcel"
|
||||
icon = 'icons/obj/storage_vr.dmi' //VOREStation Edit
|
||||
icon_state = "deliverycloset"
|
||||
var/obj/wrapped = null
|
||||
density = TRUE
|
||||
var/sortTag = null
|
||||
flags = NOBLUDGEON
|
||||
mouse_drag_pointer = MOUSE_ACTIVE_POINTER
|
||||
var/examtext = null
|
||||
var/nameset = 0
|
||||
var/label_y
|
||||
var/label_x
|
||||
var/tag_x
|
||||
|
||||
/obj/structure/bigDelivery/attack_hand(mob/user as mob)
|
||||
unwrap()
|
||||
|
||||
/obj/structure/bigDelivery/proc/unwrap()
|
||||
playsound(src, 'sound/items/package_unwrap.ogg', 50, 1)
|
||||
// Destroy will drop our wrapped object on the turf, so let it.
|
||||
qdel(src)
|
||||
|
||||
/obj/structure/bigDelivery/attackby(obj/item/W as obj, mob/user as mob)
|
||||
if(istype(W, /obj/item/destTagger))
|
||||
var/obj/item/destTagger/O = W
|
||||
if(O.currTag)
|
||||
if(src.sortTag != O.currTag)
|
||||
to_chat(user, span_notice("You have labeled the destination as [O.currTag]."))
|
||||
if(!src.sortTag)
|
||||
src.sortTag = O.currTag
|
||||
update_icon()
|
||||
else
|
||||
src.sortTag = O.currTag
|
||||
playsound(src, 'sound/machines/twobeep.ogg', 50, 1)
|
||||
else
|
||||
to_chat(user, span_warning("The package is already labeled for [O.currTag]."))
|
||||
else
|
||||
to_chat(user, span_warning("You need to set a destination first!"))
|
||||
|
||||
else if(istype(W, /obj/item/pen))
|
||||
switch(tgui_alert(user, "What would you like to alter?","Select Alteration",list("Title","Description","Cancel")))
|
||||
if("Title")
|
||||
var/str = sanitizeSafe(tgui_input_text(user,"Label text?","Set label","", MAX_NAME_LEN, encode = FALSE), MAX_NAME_LEN)
|
||||
if(!str || !length(str))
|
||||
to_chat(user, span_warning(" Invalid text."))
|
||||
return
|
||||
user.visible_message("\The [user] titles \the [src] with \a [W], marking down: \"[str]\"",\
|
||||
span_notice("You title \the [src]: \"[str]\""),\
|
||||
"You hear someone scribbling a note.")
|
||||
playsound(src, pick('sound/bureaucracy/pen1.ogg','sound/bureaucracy/pen2.ogg'), 20)
|
||||
name = "[name] ([str])"
|
||||
if(!examtext && !nameset)
|
||||
nameset = 1
|
||||
update_icon()
|
||||
else
|
||||
nameset = 1
|
||||
if("Description")
|
||||
var/str = tgui_input_text(user,"Label text?","Set label","", MAX_MESSAGE_LEN)
|
||||
if(!str || !length(str))
|
||||
to_chat(user, span_red("Invalid text."))
|
||||
return
|
||||
if(!examtext && !nameset)
|
||||
examtext = str
|
||||
update_icon()
|
||||
else
|
||||
examtext = str
|
||||
user.visible_message("\The [user] labels \the [src] with \a [W], scribbling down: \"[examtext]\"",\
|
||||
span_notice("You label \the [src]: \"[examtext]\""),\
|
||||
"You hear someone scribbling a note.")
|
||||
playsound(src, pick('sound/bureaucracy/pen1.ogg','sound/bureaucracy/pen2.ogg'), 20)
|
||||
return
|
||||
|
||||
/obj/structure/bigDelivery/update_icon()
|
||||
cut_overlays()
|
||||
if(nameset || examtext)
|
||||
var/image/I = new/image('icons/obj/storage.dmi',"delivery_label")
|
||||
if(icon_state == "deliverycloset")
|
||||
I.pixel_x = 2
|
||||
if(label_y == null)
|
||||
label_y = rand(-6, 11)
|
||||
I.pixel_y = label_y
|
||||
else if(icon_state == "deliverycrate")
|
||||
if(label_x == null)
|
||||
label_x = rand(-8, 6)
|
||||
I.pixel_x = label_x
|
||||
I.pixel_y = -3
|
||||
add_overlay(I)
|
||||
if(src.sortTag)
|
||||
var/image/I = new/image('icons/obj/storage.dmi',"delivery_tag")
|
||||
if(icon_state == "deliverycloset")
|
||||
if(tag_x == null)
|
||||
tag_x = rand(-2, 3)
|
||||
I.pixel_x = tag_x
|
||||
I.pixel_y = 9
|
||||
else if(icon_state == "deliverycrate")
|
||||
if(tag_x == null)
|
||||
tag_x = rand(-8, 6)
|
||||
I.pixel_x = tag_x
|
||||
I.pixel_y = -3
|
||||
add_overlay(I)
|
||||
|
||||
/obj/structure/bigDelivery/examine(mob/user)
|
||||
. = ..()
|
||||
if(get_dist(user, src) <= 4)
|
||||
if(sortTag)
|
||||
. += span_notice("It is labeled \"[sortTag]\"")
|
||||
if(examtext)
|
||||
. += span_notice("It has a note attached which reads, \"[examtext]\"")
|
||||
|
||||
/obj/structure/bigDelivery/Destroy()
|
||||
if(wrapped) //sometimes items can disappear. For example, bombs. --rastaf0
|
||||
wrapped.forceMove(get_turf(src))
|
||||
if(istype(wrapped, /obj/structure/closet))
|
||||
var/obj/structure/closet/O = wrapped
|
||||
O.sealed = 0
|
||||
wrapped = null
|
||||
var/turf/T = get_turf(src)
|
||||
for(var/atom/movable/AM in contents)
|
||||
AM.forceMove(T)
|
||||
return ..()
|
||||
|
||||
/obj/item/smallDelivery
|
||||
desc = "A small wrapped package."
|
||||
name = "small parcel"
|
||||
icon = 'icons/obj/storage_vr.dmi' //VOREStation Edit
|
||||
icon_state = "deliverycrate3"
|
||||
drop_sound = 'sound/items/drop/cardboardbox.ogg'
|
||||
pickup_sound = 'sound/items/pickup/cardboardbox.ogg'
|
||||
var/obj/item/wrapped = null
|
||||
var/sortTag = null
|
||||
var/examtext = null
|
||||
var/nameset = 0
|
||||
var/tag_x
|
||||
|
||||
/obj/item/smallDelivery/attack_self(mob/user as mob)
|
||||
if (src.wrapped) //sometimes items can disappear. For example, bombs. --rastaf0
|
||||
wrapped.loc = user.loc
|
||||
if(ishuman(user))
|
||||
user.put_in_hands(wrapped)
|
||||
else
|
||||
wrapped.loc = get_turf(src)
|
||||
|
||||
qdel(src)
|
||||
return
|
||||
|
||||
/obj/item/smallDelivery/attackby(obj/item/W as obj, mob/user as mob)
|
||||
if(istype(W, /obj/item/destTagger))
|
||||
var/obj/item/destTagger/O = W
|
||||
if(O.currTag)
|
||||
if(src.sortTag != O.currTag)
|
||||
to_chat(user, span_notice("You have labeled the destination as [O.currTag]."))
|
||||
if(!src.sortTag)
|
||||
src.sortTag = O.currTag
|
||||
update_icon()
|
||||
else
|
||||
src.sortTag = O.currTag
|
||||
playsound(src, 'sound/machines/twobeep.ogg', 50, 1)
|
||||
else
|
||||
to_chat(user, span_warning("The package is already labeled for [O.currTag]."))
|
||||
else
|
||||
to_chat(user, span_warning("You need to set a destination first!"))
|
||||
|
||||
else if(istype(W, /obj/item/pen))
|
||||
switch(tgui_alert(user, "What would you like to alter?","Select Alteration",list("Title","Description","Cancel")))
|
||||
if("Title")
|
||||
var/str = sanitizeSafe(tgui_input_text(user,"Label text?","Set label","", MAX_NAME_LEN, encode = FALSE), MAX_NAME_LEN)
|
||||
if(!str || !length(str))
|
||||
to_chat(user, span_warning(" Invalid text."))
|
||||
return
|
||||
user.visible_message("\The [user] titles \the [src] with \a [W], marking down: \"[str]\"",\
|
||||
span_notice("You title \the [src]: \"[str]\""),\
|
||||
"You hear someone scribbling a note.")
|
||||
playsound(src, pick('sound/bureaucracy/pen1.ogg','sound/bureaucracy/pen2.ogg'), 20)
|
||||
name = "[name] ([str])"
|
||||
if(!examtext && !nameset)
|
||||
nameset = 1
|
||||
update_icon()
|
||||
else
|
||||
nameset = 1
|
||||
|
||||
if("Description")
|
||||
var/str = tgui_input_text(user,"Label text?","Set label","", MAX_MESSAGE_LEN)
|
||||
if(!str || !length(str))
|
||||
to_chat(user, span_red("Invalid text."))
|
||||
return
|
||||
if(!examtext && !nameset)
|
||||
examtext = str
|
||||
update_icon()
|
||||
else
|
||||
examtext = str
|
||||
user.visible_message("\The [user] labels \the [src] with \a [W], scribbling down: \"[examtext]\"",\
|
||||
span_notice("You label \the [src]: \"[examtext]\""),\
|
||||
"You hear someone scribbling a note.")
|
||||
playsound(src, pick('sound/bureaucracy/pen1.ogg','sound/bureaucracy/pen2.ogg'), 20)
|
||||
return
|
||||
|
||||
/obj/item/smallDelivery/update_icon()
|
||||
cut_overlays()
|
||||
if((nameset || examtext) && icon_state != "deliverycrate1")
|
||||
var/image/I = new/image('icons/obj/storage.dmi',"delivery_label")
|
||||
if(icon_state == "deliverycrate5")
|
||||
I.pixel_y = -1
|
||||
add_overlay(I)
|
||||
if(src.sortTag)
|
||||
var/image/I = new/image('icons/obj/storage.dmi',"delivery_tag")
|
||||
switch(icon_state)
|
||||
if("deliverycrate1")
|
||||
I.pixel_y = -5
|
||||
if("deliverycrate2")
|
||||
I.pixel_y = -2
|
||||
if("deliverycrate3")
|
||||
I.pixel_y = 0
|
||||
if("deliverycrate4")
|
||||
if(tag_x == null)
|
||||
tag_x = rand(0,5)
|
||||
I.pixel_x = tag_x
|
||||
I.pixel_y = 3
|
||||
if("deliverycrate5")
|
||||
I.pixel_y = -3
|
||||
add_overlay(I)
|
||||
|
||||
/obj/item/smallDelivery/examine(mob/user)
|
||||
. = ..()
|
||||
if(get_dist(user, src) <= 4)
|
||||
if(sortTag)
|
||||
. += span_notice("It is labeled \"[sortTag]\"")
|
||||
if(examtext)
|
||||
. += span_notice("It has a note attached which reads, \"[examtext]\"")
|
||||
@@ -0,0 +1,49 @@
|
||||
// the disposal outlet machine
|
||||
/obj/structure/disposaloutlet
|
||||
name = "disposal outlet"
|
||||
desc = "An outlet for the pneumatic disposal system."
|
||||
icon = 'icons/obj/pipes/disposal.dmi'
|
||||
icon_state = "outlet"
|
||||
density = TRUE
|
||||
anchored = TRUE
|
||||
var/active = 0
|
||||
var/mode = 0
|
||||
|
||||
/obj/structure/disposaloutlet/Initialize(mapload)
|
||||
. = ..()
|
||||
AddComponent(/datum/component/disposal_system_connection/disposaloutlet) // Special subtype for directional tossing and it's animation/buzzer
|
||||
|
||||
/obj/structure/disposaloutlet/attackby(obj/item/I, mob/user)
|
||||
if(!I || !user)
|
||||
return
|
||||
src.add_fingerprint(user)
|
||||
if(I.has_tool_quality(TOOL_SCREWDRIVER))
|
||||
if(mode==0)
|
||||
mode=1
|
||||
to_chat(user, "You remove the screws around the power connection.")
|
||||
playsound(src, I.usesound, 50, 1)
|
||||
return
|
||||
else if(mode==1)
|
||||
mode=0
|
||||
to_chat(user, "You attach the screws around the power connection.")
|
||||
playsound(src, I.usesound, 50, 1)
|
||||
return
|
||||
else if(I.has_tool_quality(TOOL_WELDER) && mode==1)
|
||||
var/obj/item/weldingtool/W = I.get_welder()
|
||||
if(W.remove_fuel(0,user))
|
||||
playsound(src, W.usesound, 100, 1)
|
||||
to_chat(user, "You start slicing the floorweld off the disposal outlet.")
|
||||
if(do_after(user, 2 SECONDS * W.toolspeed, target = src))
|
||||
if(!src || !W.isOn()) return
|
||||
to_chat(user, "You sliced the floorweld off the disposal outlet.")
|
||||
var/obj/structure/disposalconstruct/C = new (src.loc)
|
||||
src.transfer_fingerprints_to(C)
|
||||
C.ptype = 7 // 7 = outlet
|
||||
C.update()
|
||||
C.anchored = TRUE
|
||||
C.density = TRUE
|
||||
qdel(src)
|
||||
return
|
||||
else
|
||||
to_chat(user, "You need more welding fuel to complete this task.")
|
||||
return
|
||||
@@ -0,0 +1,51 @@
|
||||
/obj/structure/disposalpipe/tagger
|
||||
name = "package tagger"
|
||||
icon_state = "pipe-tagger"
|
||||
var/sort_tag = ""
|
||||
var/partial = 0
|
||||
|
||||
/obj/structure/disposalpipe/tagger/proc/updatedesc()
|
||||
desc = initial(desc)
|
||||
if(sort_tag)
|
||||
desc += "\nIt's tagging objects with the '[sort_tag]' tag."
|
||||
|
||||
/obj/structure/disposalpipe/tagger/proc/updatename()
|
||||
if(sort_tag)
|
||||
name = "[initial(name)] ([sort_tag])"
|
||||
else
|
||||
name = initial(name)
|
||||
|
||||
/obj/structure/disposalpipe/tagger/Initialize(mapload)
|
||||
. = ..()
|
||||
dpdir = dir | turn(dir, 180)
|
||||
if(sort_tag) GLOB.tagger_locations |= list("[sort_tag]" = get_z(src))
|
||||
updatename()
|
||||
updatedesc()
|
||||
update()
|
||||
|
||||
/obj/structure/disposalpipe/tagger/attackby(obj/item/I, mob/user)
|
||||
if(..())
|
||||
return
|
||||
|
||||
if(istype(I, /obj/item/destTagger))
|
||||
var/obj/item/destTagger/O = I
|
||||
|
||||
if(O.currTag)// Tag set
|
||||
sort_tag = O.currTag
|
||||
playsound(src, 'sound/machines/twobeep.ogg', 100, 1)
|
||||
to_chat(user, span_blue("Changed tag to '[sort_tag]'."))
|
||||
updatename()
|
||||
updatedesc()
|
||||
|
||||
/obj/structure/disposalpipe/tagger/transfer(obj/structure/disposalholder/H)
|
||||
if(sort_tag)
|
||||
if(partial)
|
||||
H.setpartialtag(sort_tag)
|
||||
else
|
||||
H.settag(sort_tag)
|
||||
return ..()
|
||||
|
||||
/obj/structure/disposalpipe/tagger/partial //needs two passes to tag
|
||||
name = "partial package tagger"
|
||||
icon_state = "pipe-tagger-partial"
|
||||
partial = 1
|
||||
@@ -0,0 +1,62 @@
|
||||
//a trunk joining to a disposal bin or outlet on the same turf
|
||||
/obj/structure/disposalpipe/trunk
|
||||
icon_state = "pipe-t"
|
||||
|
||||
/obj/structure/disposalpipe/trunk/Initialize(mapload)
|
||||
..()
|
||||
dpdir = dir
|
||||
return INITIALIZE_HINT_LATELOAD
|
||||
|
||||
/obj/structure/disposalpipe/trunk/LateInitialize()
|
||||
update()
|
||||
|
||||
// Override attackby so we disallow trunkremoval when somethings ontop
|
||||
/obj/structure/disposalpipe/trunk/attackby(obj/item/I, mob/user)
|
||||
//Disposal constructors
|
||||
var/turf/T = get_turf(src)
|
||||
var/obj/structure/disposalconstruct/C = locate() in T
|
||||
if(C && C.anchored)
|
||||
return
|
||||
|
||||
if(!T.is_plating())
|
||||
return // prevent interaction with T-scanner revealed pipes
|
||||
add_fingerprint(user)
|
||||
if(I.has_tool_quality(TOOL_WELDER))
|
||||
var/obj/item/weldingtool/W = I.get_welder()
|
||||
|
||||
if(W.remove_fuel(0,user))
|
||||
playsound(src, W.usesound, 100, 1)
|
||||
to_chat(user, "Slicing the disposal pipe.")
|
||||
if(do_after(user, 3 SECONDS * W.toolspeed, target = src))
|
||||
if(!src || !W.isOn()) return
|
||||
welded()
|
||||
else
|
||||
to_chat(user, "You must stay still while welding the pipe.")
|
||||
else
|
||||
to_chat(user, "You need more welding fuel to cut the pipe.")
|
||||
|
||||
// would transfer to next pipe segment, but we are in a trunk
|
||||
// if not entering from disposal bin,
|
||||
// transfer to linked object (outlet or bin)
|
||||
/obj/structure/disposalpipe/trunk/transfer(obj/structure/disposalholder/H)
|
||||
if(H.dir == DOWN) // we just entered from a disposer
|
||||
return ..() // so do base transfer proc
|
||||
|
||||
// Find a disposal handler component. First come first serve.
|
||||
var/transfered = FALSE
|
||||
var/turf/T = get_turf(src)
|
||||
for(var/obj/O in T)
|
||||
if(SEND_SIGNAL(O,COMSIG_DISPOSAL_RECEIVING,H))
|
||||
transfered = TRUE
|
||||
break
|
||||
if(!transfered) // Check if anything handled it, will be deleted if so.
|
||||
expel(H, T, 0) // expel at turf if nothing handled it
|
||||
|
||||
return null
|
||||
|
||||
// nextdir
|
||||
/obj/structure/disposalpipe/trunk/nextdir(fromdir)
|
||||
if(fromdir == DOWN)
|
||||
return dir
|
||||
else
|
||||
return 0
|
||||
@@ -1,19 +0,0 @@
|
||||
/obj/machinery/disposal/wall/cleaner
|
||||
name = "resleeving equipment deposit"
|
||||
desc = "Automatically cleans and transports items to the local resleeving facilities."
|
||||
icon = 'icons/obj/pipes/disposal_vr.dmi'
|
||||
icon_state = "bluewall"
|
||||
|
||||
/obj/machinery/disposal/wall/cleaner/flush()
|
||||
flick("[icon_state]-flush", src)
|
||||
for(var/obj/item/storage/i in src)
|
||||
if(istype(i, /obj/item/storage))
|
||||
var/list/storage_items = i.return_inv()
|
||||
|
||||
for(var/obj/item/item in storage_items)
|
||||
item.wash(CLEAN_WASH)
|
||||
|
||||
for(var/obj/item/i in src)
|
||||
if(istype(i, /obj/item))
|
||||
i.wash(CLEAN_WASH)
|
||||
. = ..()
|
||||
@@ -0,0 +1,97 @@
|
||||
/obj/item/packageWrap
|
||||
name = "package wrapper"
|
||||
desc = "Like wrapping paper, but less festive."
|
||||
icon = 'icons/obj/items.dmi'
|
||||
icon_state = "deliveryPaper"
|
||||
w_class = ITEMSIZE_NORMAL
|
||||
var/amount = 25.0
|
||||
drop_sound = 'sound/items/drop/wrapper.ogg'
|
||||
|
||||
/obj/item/packageWrap/afterattack(obj/target, mob/user, proximity)
|
||||
if(!proximity) return
|
||||
if(!istype(target)) //this really shouldn't be necessary (but it is). -Pete
|
||||
return
|
||||
if(istype(target, /obj/item/smallDelivery) || istype(target,/obj/structure/bigDelivery) \
|
||||
|| istype(target, /obj/item/gift) || istype(target, /obj/item/evidencebag))
|
||||
return
|
||||
if(target.anchored)
|
||||
return
|
||||
if(!isturf(target.loc)) //no wrapping things inside other things, just breaks things, put it on the ground first.
|
||||
return
|
||||
if(user in target) //no wrapping closets that you are inside - it's not physically possible
|
||||
return
|
||||
|
||||
user.attack_log += text("\[[time_stamp()]\] [span_blue("Has used [src.name] on \ref[target]")]")
|
||||
|
||||
if (istype(target, /obj/item) && !(istype(target, /obj/item/storage) && !istype(target,/obj/item/storage/box)))
|
||||
var/obj/item/O = target
|
||||
if (src.amount > 1)
|
||||
var/obj/item/smallDelivery/P = new /obj/item/smallDelivery(get_turf(O.loc)) //Aaannd wrap it up!
|
||||
if(!istype(O.loc, /turf))
|
||||
if(user.client)
|
||||
user.client.screen -= O
|
||||
P.wrapped = O
|
||||
O.forceMove(P)
|
||||
P.w_class = O.w_class
|
||||
var/i = round(O.w_class)
|
||||
if(i in list(1,2,3,4,5))
|
||||
P.icon_state = "deliverycrate[i]"
|
||||
switch(i)
|
||||
if(1) P.name = "tiny parcel"
|
||||
if(3) P.name = "normal-sized parcel"
|
||||
if(4) P.name = "large parcel"
|
||||
if(5) P.name = "huge parcel"
|
||||
if(i < 1)
|
||||
P.icon_state = "deliverycrate1"
|
||||
P.name = "tiny parcel"
|
||||
if(i > 5)
|
||||
P.icon_state = "deliverycrate5"
|
||||
P.name = "huge parcel"
|
||||
P.add_fingerprint(user)
|
||||
O.add_fingerprint(user)
|
||||
src.add_fingerprint(user)
|
||||
src.amount -= 1
|
||||
user.visible_message("\The [user] wraps \a [target] with \a [src].",\
|
||||
span_notice("You wrap \the [target], leaving [amount] units of paper on \the [src]."),\
|
||||
"You hear someone taping paper around a small object.")
|
||||
playsound(src, 'sound/items/package_wrap.ogg', 50, 1)
|
||||
else if (istype(target, /obj/structure/closet/crate))
|
||||
var/obj/structure/closet/crate/O = target
|
||||
if (src.amount > 3 && !O.opened)
|
||||
var/obj/structure/bigDelivery/P = new /obj/structure/bigDelivery(get_turf(O.loc))
|
||||
P.icon_state = "deliverycrate"
|
||||
P.wrapped = O
|
||||
O.loc = P
|
||||
src.amount -= 3
|
||||
user.visible_message("\The [user] wraps \a [target] with \a [src].",\
|
||||
span_notice("You wrap \the [target], leaving [amount] units of paper on \the [src]."),\
|
||||
"You hear someone taping paper around a large object.")
|
||||
playsound(src, 'sound/items/package_wrap.ogg', 50, 1)
|
||||
else if(src.amount < 3)
|
||||
to_chat(user, span_warning("You need more paper."))
|
||||
else if (istype (target, /obj/structure/closet))
|
||||
var/obj/structure/closet/O = target
|
||||
if (src.amount > 3 && !O.opened)
|
||||
var/obj/structure/bigDelivery/P = new /obj/structure/bigDelivery(get_turf(O.loc))
|
||||
P.wrapped = O
|
||||
O.sealed = 1
|
||||
O.loc = P
|
||||
src.amount -= 3
|
||||
user.visible_message("\The [user] wraps \a [target] with \a [src].",\
|
||||
span_notice("You wrap \the [target], leaving [amount] units of paper on \the [src]."),\
|
||||
"You hear someone taping paper around a large object.")
|
||||
playsound(src, 'sound/items/package_wrap.ogg', 50, 1)
|
||||
else if(src.amount < 3)
|
||||
to_chat(user, span_warning("You need more paper."))
|
||||
else
|
||||
to_chat(user, span_blue("The object you are trying to wrap is unsuitable for the sorting machinery!"))
|
||||
if (src.amount <= 0)
|
||||
new /obj/item/c_tube( src.loc )
|
||||
qdel(src)
|
||||
return
|
||||
return
|
||||
|
||||
/obj/item/packageWrap/examine(mob/user)
|
||||
. = ..()
|
||||
if(get_dist(user, src) <= 0)
|
||||
. += span_blue("There are [amount] units of package wrap left!")
|
||||
@@ -1,404 +1,10 @@
|
||||
/obj/structure/bigDelivery
|
||||
desc = "A big wrapped package."
|
||||
name = "large parcel"
|
||||
icon = 'icons/obj/storage_vr.dmi' //VOREStation Edit
|
||||
icon_state = "deliverycloset"
|
||||
var/obj/wrapped = null
|
||||
density = TRUE
|
||||
var/sortTag = null
|
||||
flags = NOBLUDGEON
|
||||
mouse_drag_pointer = MOUSE_ACTIVE_POINTER
|
||||
var/examtext = null
|
||||
var/nameset = 0
|
||||
var/label_y
|
||||
var/label_x
|
||||
var/tag_x
|
||||
|
||||
/obj/structure/bigDelivery/attack_hand(mob/user as mob)
|
||||
unwrap()
|
||||
|
||||
/obj/structure/bigDelivery/proc/unwrap()
|
||||
playsound(src, 'sound/items/package_unwrap.ogg', 50, 1)
|
||||
// Destroy will drop our wrapped object on the turf, so let it.
|
||||
qdel(src)
|
||||
|
||||
/obj/structure/bigDelivery/attackby(obj/item/W as obj, mob/user as mob)
|
||||
if(istype(W, /obj/item/destTagger))
|
||||
var/obj/item/destTagger/O = W
|
||||
if(O.currTag)
|
||||
if(src.sortTag != O.currTag)
|
||||
to_chat(user, span_notice("You have labeled the destination as [O.currTag]."))
|
||||
if(!src.sortTag)
|
||||
src.sortTag = O.currTag
|
||||
update_icon()
|
||||
else
|
||||
src.sortTag = O.currTag
|
||||
playsound(src, 'sound/machines/twobeep.ogg', 50, 1)
|
||||
else
|
||||
to_chat(user, span_warning("The package is already labeled for [O.currTag]."))
|
||||
else
|
||||
to_chat(user, span_warning("You need to set a destination first!"))
|
||||
|
||||
else if(istype(W, /obj/item/pen))
|
||||
switch(tgui_alert(user, "What would you like to alter?","Select Alteration",list("Title","Description","Cancel")))
|
||||
if("Title")
|
||||
var/str = sanitizeSafe(tgui_input_text(user,"Label text?","Set label","", MAX_NAME_LEN, encode = FALSE), MAX_NAME_LEN)
|
||||
if(!str || !length(str))
|
||||
to_chat(user, span_warning(" Invalid text."))
|
||||
return
|
||||
user.visible_message("\The [user] titles \the [src] with \a [W], marking down: \"[str]\"",\
|
||||
span_notice("You title \the [src]: \"[str]\""),\
|
||||
"You hear someone scribbling a note.")
|
||||
playsound(src, pick('sound/bureaucracy/pen1.ogg','sound/bureaucracy/pen2.ogg'), 20)
|
||||
name = "[name] ([str])"
|
||||
if(!examtext && !nameset)
|
||||
nameset = 1
|
||||
update_icon()
|
||||
else
|
||||
nameset = 1
|
||||
if("Description")
|
||||
var/str = tgui_input_text(user,"Label text?","Set label","", MAX_MESSAGE_LEN)
|
||||
if(!str || !length(str))
|
||||
to_chat(user, span_red("Invalid text."))
|
||||
return
|
||||
if(!examtext && !nameset)
|
||||
examtext = str
|
||||
update_icon()
|
||||
else
|
||||
examtext = str
|
||||
user.visible_message("\The [user] labels \the [src] with \a [W], scribbling down: \"[examtext]\"",\
|
||||
span_notice("You label \the [src]: \"[examtext]\""),\
|
||||
"You hear someone scribbling a note.")
|
||||
playsound(src, pick('sound/bureaucracy/pen1.ogg','sound/bureaucracy/pen2.ogg'), 20)
|
||||
return
|
||||
|
||||
/obj/structure/bigDelivery/update_icon()
|
||||
cut_overlays()
|
||||
if(nameset || examtext)
|
||||
var/image/I = new/image('icons/obj/storage.dmi',"delivery_label")
|
||||
if(icon_state == "deliverycloset")
|
||||
I.pixel_x = 2
|
||||
if(label_y == null)
|
||||
label_y = rand(-6, 11)
|
||||
I.pixel_y = label_y
|
||||
else if(icon_state == "deliverycrate")
|
||||
if(label_x == null)
|
||||
label_x = rand(-8, 6)
|
||||
I.pixel_x = label_x
|
||||
I.pixel_y = -3
|
||||
add_overlay(I)
|
||||
if(src.sortTag)
|
||||
var/image/I = new/image('icons/obj/storage.dmi',"delivery_tag")
|
||||
if(icon_state == "deliverycloset")
|
||||
if(tag_x == null)
|
||||
tag_x = rand(-2, 3)
|
||||
I.pixel_x = tag_x
|
||||
I.pixel_y = 9
|
||||
else if(icon_state == "deliverycrate")
|
||||
if(tag_x == null)
|
||||
tag_x = rand(-8, 6)
|
||||
I.pixel_x = tag_x
|
||||
I.pixel_y = -3
|
||||
add_overlay(I)
|
||||
|
||||
/obj/structure/bigDelivery/examine(mob/user)
|
||||
. = ..()
|
||||
if(get_dist(user, src) <= 4)
|
||||
if(sortTag)
|
||||
. += span_notice("It is labeled \"[sortTag]\"")
|
||||
if(examtext)
|
||||
. += span_notice("It has a note attached which reads, \"[examtext]\"")
|
||||
|
||||
/obj/item/smallDelivery
|
||||
desc = "A small wrapped package."
|
||||
name = "small parcel"
|
||||
icon = 'icons/obj/storage_vr.dmi' //VOREStation Edit
|
||||
icon_state = "deliverycrate3"
|
||||
drop_sound = 'sound/items/drop/cardboardbox.ogg'
|
||||
pickup_sound = 'sound/items/pickup/cardboardbox.ogg'
|
||||
var/obj/item/wrapped = null
|
||||
var/sortTag = null
|
||||
var/examtext = null
|
||||
var/nameset = 0
|
||||
var/tag_x
|
||||
|
||||
/obj/item/smallDelivery/attack_self(mob/user as mob)
|
||||
if (src.wrapped) //sometimes items can disappear. For example, bombs. --rastaf0
|
||||
wrapped.loc = user.loc
|
||||
if(ishuman(user))
|
||||
user.put_in_hands(wrapped)
|
||||
else
|
||||
wrapped.loc = get_turf(src)
|
||||
|
||||
qdel(src)
|
||||
return
|
||||
|
||||
/obj/item/smallDelivery/attackby(obj/item/W as obj, mob/user as mob)
|
||||
if(istype(W, /obj/item/destTagger))
|
||||
var/obj/item/destTagger/O = W
|
||||
if(O.currTag)
|
||||
if(src.sortTag != O.currTag)
|
||||
to_chat(user, span_notice("You have labeled the destination as [O.currTag]."))
|
||||
if(!src.sortTag)
|
||||
src.sortTag = O.currTag
|
||||
update_icon()
|
||||
else
|
||||
src.sortTag = O.currTag
|
||||
playsound(src, 'sound/machines/twobeep.ogg', 50, 1)
|
||||
else
|
||||
to_chat(user, span_warning("The package is already labeled for [O.currTag]."))
|
||||
else
|
||||
to_chat(user, span_warning("You need to set a destination first!"))
|
||||
|
||||
else if(istype(W, /obj/item/pen))
|
||||
switch(tgui_alert(user, "What would you like to alter?","Select Alteration",list("Title","Description","Cancel")))
|
||||
if("Title")
|
||||
var/str = sanitizeSafe(tgui_input_text(user,"Label text?","Set label","", MAX_NAME_LEN, encode = FALSE), MAX_NAME_LEN)
|
||||
if(!str || !length(str))
|
||||
to_chat(user, span_warning(" Invalid text."))
|
||||
return
|
||||
user.visible_message("\The [user] titles \the [src] with \a [W], marking down: \"[str]\"",\
|
||||
span_notice("You title \the [src]: \"[str]\""),\
|
||||
"You hear someone scribbling a note.")
|
||||
playsound(src, pick('sound/bureaucracy/pen1.ogg','sound/bureaucracy/pen2.ogg'), 20)
|
||||
name = "[name] ([str])"
|
||||
if(!examtext && !nameset)
|
||||
nameset = 1
|
||||
update_icon()
|
||||
else
|
||||
nameset = 1
|
||||
|
||||
if("Description")
|
||||
var/str = tgui_input_text(user,"Label text?","Set label","", MAX_MESSAGE_LEN)
|
||||
if(!str || !length(str))
|
||||
to_chat(user, span_red("Invalid text."))
|
||||
return
|
||||
if(!examtext && !nameset)
|
||||
examtext = str
|
||||
update_icon()
|
||||
else
|
||||
examtext = str
|
||||
user.visible_message("\The [user] labels \the [src] with \a [W], scribbling down: \"[examtext]\"",\
|
||||
span_notice("You label \the [src]: \"[examtext]\""),\
|
||||
"You hear someone scribbling a note.")
|
||||
playsound(src, pick('sound/bureaucracy/pen1.ogg','sound/bureaucracy/pen2.ogg'), 20)
|
||||
return
|
||||
|
||||
/obj/item/smallDelivery/update_icon()
|
||||
cut_overlays()
|
||||
if((nameset || examtext) && icon_state != "deliverycrate1")
|
||||
var/image/I = new/image('icons/obj/storage.dmi',"delivery_label")
|
||||
if(icon_state == "deliverycrate5")
|
||||
I.pixel_y = -1
|
||||
add_overlay(I)
|
||||
if(src.sortTag)
|
||||
var/image/I = new/image('icons/obj/storage.dmi',"delivery_tag")
|
||||
switch(icon_state)
|
||||
if("deliverycrate1")
|
||||
I.pixel_y = -5
|
||||
if("deliverycrate2")
|
||||
I.pixel_y = -2
|
||||
if("deliverycrate3")
|
||||
I.pixel_y = 0
|
||||
if("deliverycrate4")
|
||||
if(tag_x == null)
|
||||
tag_x = rand(0,5)
|
||||
I.pixel_x = tag_x
|
||||
I.pixel_y = 3
|
||||
if("deliverycrate5")
|
||||
I.pixel_y = -3
|
||||
add_overlay(I)
|
||||
|
||||
/obj/item/smallDelivery/examine(mob/user)
|
||||
. = ..()
|
||||
if(get_dist(user, src) <= 4)
|
||||
if(sortTag)
|
||||
. += span_notice("It is labeled \"[sortTag]\"")
|
||||
if(examtext)
|
||||
. += span_notice("It has a note attached which reads, \"[examtext]\"")
|
||||
|
||||
/obj/item/packageWrap
|
||||
name = "package wrapper"
|
||||
desc = "Like wrapping paper, but less festive."
|
||||
icon = 'icons/obj/items.dmi'
|
||||
icon_state = "deliveryPaper"
|
||||
w_class = ITEMSIZE_NORMAL
|
||||
var/amount = 25.0
|
||||
drop_sound = 'sound/items/drop/wrapper.ogg'
|
||||
|
||||
|
||||
/obj/item/packageWrap/afterattack(var/obj/target as obj, mob/user as mob, proximity)
|
||||
if(!proximity) return
|
||||
if(!istype(target)) //this really shouldn't be necessary (but it is). -Pete
|
||||
return
|
||||
if(istype(target, /obj/item/smallDelivery) || istype(target,/obj/structure/bigDelivery) \
|
||||
|| istype(target, /obj/item/gift) || istype(target, /obj/item/evidencebag))
|
||||
return
|
||||
if(target.anchored)
|
||||
return
|
||||
if(!isturf(target.loc)) //no wrapping things inside other things, just breaks things, put it on the ground first.
|
||||
return
|
||||
if(user in target) //no wrapping closets that you are inside - it's not physically possible
|
||||
return
|
||||
|
||||
user.attack_log += text("\[[time_stamp()]\] [span_blue("Has used [src.name] on \ref[target]")]")
|
||||
|
||||
|
||||
if (istype(target, /obj/item) && !(istype(target, /obj/item/storage) && !istype(target,/obj/item/storage/box)))
|
||||
var/obj/item/O = target
|
||||
if (src.amount > 1)
|
||||
var/obj/item/smallDelivery/P = new /obj/item/smallDelivery(get_turf(O.loc)) //Aaannd wrap it up!
|
||||
if(!istype(O.loc, /turf))
|
||||
if(user.client)
|
||||
user.client.screen -= O
|
||||
P.wrapped = O
|
||||
O.forceMove(P)
|
||||
P.w_class = O.w_class
|
||||
var/i = round(O.w_class)
|
||||
if(i in list(1,2,3,4,5))
|
||||
P.icon_state = "deliverycrate[i]"
|
||||
switch(i)
|
||||
if(1) P.name = "tiny parcel"
|
||||
if(3) P.name = "normal-sized parcel"
|
||||
if(4) P.name = "large parcel"
|
||||
if(5) P.name = "huge parcel"
|
||||
if(i < 1)
|
||||
P.icon_state = "deliverycrate1"
|
||||
P.name = "tiny parcel"
|
||||
if(i > 5)
|
||||
P.icon_state = "deliverycrate5"
|
||||
P.name = "huge parcel"
|
||||
P.add_fingerprint(user)
|
||||
O.add_fingerprint(user)
|
||||
src.add_fingerprint(user)
|
||||
src.amount -= 1
|
||||
user.visible_message("\The [user] wraps \a [target] with \a [src].",\
|
||||
span_notice("You wrap \the [target], leaving [amount] units of paper on \the [src]."),\
|
||||
"You hear someone taping paper around a small object.")
|
||||
playsound(src, 'sound/items/package_wrap.ogg', 50, 1)
|
||||
else if (istype(target, /obj/structure/closet/crate))
|
||||
var/obj/structure/closet/crate/O = target
|
||||
if (src.amount > 3 && !O.opened)
|
||||
var/obj/structure/bigDelivery/P = new /obj/structure/bigDelivery(get_turf(O.loc))
|
||||
P.icon_state = "deliverycrate"
|
||||
P.wrapped = O
|
||||
O.loc = P
|
||||
src.amount -= 3
|
||||
user.visible_message("\The [user] wraps \a [target] with \a [src].",\
|
||||
span_notice("You wrap \the [target], leaving [amount] units of paper on \the [src]."),\
|
||||
"You hear someone taping paper around a large object.")
|
||||
playsound(src, 'sound/items/package_wrap.ogg', 50, 1)
|
||||
else if(src.amount < 3)
|
||||
to_chat(user, span_warning("You need more paper."))
|
||||
else if (istype (target, /obj/structure/closet))
|
||||
var/obj/structure/closet/O = target
|
||||
if (src.amount > 3 && !O.opened)
|
||||
var/obj/structure/bigDelivery/P = new /obj/structure/bigDelivery(get_turf(O.loc))
|
||||
P.wrapped = O
|
||||
O.sealed = 1
|
||||
O.loc = P
|
||||
src.amount -= 3
|
||||
user.visible_message("\The [user] wraps \a [target] with \a [src].",\
|
||||
span_notice("You wrap \the [target], leaving [amount] units of paper on \the [src]."),\
|
||||
"You hear someone taping paper around a large object.")
|
||||
playsound(src, 'sound/items/package_wrap.ogg', 50, 1)
|
||||
else if(src.amount < 3)
|
||||
to_chat(user, span_warning("You need more paper."))
|
||||
else
|
||||
to_chat(user, span_blue("The object you are trying to wrap is unsuitable for the sorting machinery!"))
|
||||
if (src.amount <= 0)
|
||||
new /obj/item/c_tube( src.loc )
|
||||
qdel(src)
|
||||
return
|
||||
return
|
||||
|
||||
/obj/item/packageWrap/examine(mob/user)
|
||||
. = ..()
|
||||
if(get_dist(user, src) <= 0)
|
||||
. += span_blue("There are [amount] units of package wrap left!")
|
||||
|
||||
/obj/structure/bigDelivery/Destroy()
|
||||
if(wrapped) //sometimes items can disappear. For example, bombs. --rastaf0
|
||||
wrapped.forceMove(get_turf(src))
|
||||
if(istype(wrapped, /obj/structure/closet))
|
||||
var/obj/structure/closet/O = wrapped
|
||||
O.sealed = 0
|
||||
wrapped = null
|
||||
var/turf/T = get_turf(src)
|
||||
for(var/atom/movable/AM in contents)
|
||||
AM.forceMove(T)
|
||||
return ..()
|
||||
|
||||
/obj/item/destTagger
|
||||
name = "destination tagger"
|
||||
desc = "Used to set the destination of properly wrapped packages."
|
||||
icon = 'icons/obj/device.dmi'
|
||||
icon_state = "dest_tagger"
|
||||
var/currTag = 0
|
||||
|
||||
w_class = ITEMSIZE_SMALL
|
||||
item_state = "electronic"
|
||||
slot_flags = SLOT_BELT
|
||||
pickup_sound = 'sound/items/pickup/device.ogg'
|
||||
drop_sound = 'sound/items/drop/device.ogg'
|
||||
|
||||
/obj/item/destTagger/tgui_state(mob/user)
|
||||
return GLOB.tgui_inventory_state
|
||||
|
||||
/obj/item/destTagger/tgui_interact(mob/user, datum/tgui/ui)
|
||||
ui = SStgui.try_update_ui(user, src, ui)
|
||||
if(!ui)
|
||||
ui = new(user, src, "DestinationTagger", name)
|
||||
ui.open()
|
||||
|
||||
/obj/item/destTagger/tgui_static_data(mob/user)
|
||||
var/list/data = ..()
|
||||
var/list/taggers = list()
|
||||
var/list/tagger_levels = list()
|
||||
for(var/tag in GLOB.tagger_locations)
|
||||
var/z_level = GLOB.tagger_locations[tag]
|
||||
taggers += list(list("tag" = tag, "level" = z_level))
|
||||
tagger_levels += list(list("z" = z_level, "location" = using_map.get_zlevel_name(z_level)))
|
||||
data["taggerLevels"] = tagger_levels
|
||||
data["taggerLocs"] = taggers
|
||||
|
||||
return data
|
||||
|
||||
/obj/item/destTagger/tgui_data(mob/user, datum/tgui/ui)
|
||||
var/list/data = ..()
|
||||
|
||||
data["currTag"] = currTag
|
||||
|
||||
return data
|
||||
|
||||
/obj/item/destTagger/attack_self(mob/user as mob)
|
||||
tgui_interact(user)
|
||||
|
||||
/obj/item/destTagger/tgui_act(action, params, datum/tgui/ui)
|
||||
if(..())
|
||||
return TRUE
|
||||
add_fingerprint(ui.user)
|
||||
switch(action)
|
||||
if("set_tag")
|
||||
var/new_tag = params["tag"]
|
||||
if(!(new_tag in GLOB.tagger_locations))
|
||||
return FALSE
|
||||
currTag = new_tag
|
||||
. = TRUE
|
||||
|
||||
/obj/machinery/disposal/deliveryChute
|
||||
name = "Delivery chute"
|
||||
desc = "A chute for big and small packages alike!"
|
||||
density = TRUE
|
||||
icon_state = "intake"
|
||||
|
||||
var/c_mode = 0
|
||||
|
||||
/obj/machinery/disposal/deliveryChute/Initialize(mapload)
|
||||
. = ..()
|
||||
trunk = locate() in src.loc
|
||||
if(trunk)
|
||||
trunk.linked = src // link the pipe trunk to self
|
||||
stat_tracking = FALSE
|
||||
var/c_mode = FALSE
|
||||
|
||||
/obj/machinery/disposal/deliveryChute/interact()
|
||||
return
|
||||
@@ -418,13 +24,9 @@
|
||||
if(WEST)
|
||||
if(AM.loc.x != src.loc.x-1) return
|
||||
|
||||
if(istype(AM, /obj))
|
||||
var/obj/O = AM
|
||||
O.loc = src
|
||||
else if(istype(AM, /mob))
|
||||
var/mob/M = AM
|
||||
M.loc = src
|
||||
src.flush()
|
||||
if(isobj(AM) || ismob(AM))
|
||||
AM.forceMove(src)
|
||||
flush()
|
||||
|
||||
/obj/machinery/disposal/deliveryChute/hitby(atom/movable/AM)
|
||||
if(!QDELETED(AM) || (istype(AM, /obj/item) || istype(AM, /mob/living)) && !istype(AM, /obj/item/projectile))
|
||||
@@ -438,29 +40,7 @@
|
||||
if(WEST)
|
||||
if(AM.loc.x != src.loc.x-1) return ..()
|
||||
AM.forceMove(src)
|
||||
src.flush()
|
||||
|
||||
/obj/machinery/disposal/deliveryChute/flush()
|
||||
flushing = 1
|
||||
flick("intake-closing", src)
|
||||
var/obj/structure/disposalholder/H = new() // virtual holder object which actually
|
||||
// travels through the pipes.
|
||||
air_contents = new() // new empty gas resv.
|
||||
|
||||
sleep(10)
|
||||
playsound(src, 'sound/machines/disposalflush.ogg', 50, 0, 0)
|
||||
sleep(5) // wait for animation to finish
|
||||
|
||||
H.init(src) // copy the contents of disposer to holder
|
||||
|
||||
H.start(src) // start the holder processing movement
|
||||
flushing = 0
|
||||
// now reset disposal state
|
||||
flush = 0
|
||||
if(mode == 2) // if was ready,
|
||||
mode = 1 // switch to charging
|
||||
update()
|
||||
return
|
||||
flush()
|
||||
|
||||
/obj/machinery/disposal/deliveryChute/attackby(var/obj/item/I, var/mob/user)
|
||||
if(!I || !user)
|
||||
@@ -471,7 +51,7 @@
|
||||
playsound(src, I.usesound, 50, 1)
|
||||
to_chat(user, "You [c_mode ? "remove" : "attach"] the screws around the power connection.")
|
||||
return
|
||||
if(I.has_tool_quality(TOOL_WELDER) && c_mode==1)
|
||||
if(I.has_tool_quality(TOOL_WELDER) && c_mode == TRUE)
|
||||
var/obj/item/weldingtool/W = I.get_welder()
|
||||
if(!W.remove_fuel(0,user))
|
||||
to_chat(user, "You need more welding fuel to complete this task.")
|
||||
@@ -488,8 +68,3 @@
|
||||
C.density = TRUE
|
||||
qdel(src)
|
||||
return
|
||||
|
||||
/obj/machinery/disposal/deliveryChute/Destroy()
|
||||
if(trunk)
|
||||
trunk.linked = null
|
||||
. = ..()
|
||||
|
||||
Reference in New Issue
Block a user