mirror of
https://github.com/ParadiseSS13/Paradise.git
synced 2026-08-22 03:27:05 +01:00
Merge branch 'master' of https://github.com/ParadiseSS13/Paradise into turfs
# Conflicts: # code/game/objects/items.dm # code/modules/power/cable.dm # icons/mob/inhands/items_lefthand.dmi # icons/mob/inhands/items_righthand.dmi # icons/obj/lighting.dmi # paradise.dme
This commit is contained in:
@@ -100,6 +100,10 @@ var/global/image/fire_overlay = image("icon" = 'icons/goonstation/effects/fire.d
|
||||
var/trip_walksafe = TRUE
|
||||
var/trip_tiles = 0
|
||||
|
||||
//Tooltip vars
|
||||
var/in_inventory = FALSE //is this item equipped into an inventory slot or hand of a mob?
|
||||
var/tip_timer = 0
|
||||
|
||||
/obj/item/New()
|
||||
..()
|
||||
for(var/path in actions_types)
|
||||
@@ -340,11 +344,13 @@ var/global/image/fire_overlay = image("icon" = 'icons/goonstation/effects/fire.d
|
||||
A.Remove(user)
|
||||
if(flags & DROPDEL)
|
||||
qdel(src)
|
||||
in_inventory = FALSE
|
||||
SEND_SIGNAL(src, COMSIG_ITEM_DROPPED,user)
|
||||
|
||||
// called just as an item is picked up (loc is not yet changed)
|
||||
/obj/item/proc/pickup(mob/user)
|
||||
SEND_SIGNAL(src, COMSIG_ITEM_PICKUP, user)
|
||||
in_inventory = TRUE
|
||||
return TRUE
|
||||
|
||||
// called when this item is removed from a storage item, which is passed on as S. The loc variable is already set to the new destination before this is called.
|
||||
@@ -374,6 +380,7 @@ var/global/image/fire_overlay = image("icon" = 'icons/goonstation/effects/fire.d
|
||||
var/datum/action/A = X
|
||||
if(item_action_slot_check(slot, user)) //some items only give their actions buttons when in a specific slot.
|
||||
A.Grant(user)
|
||||
in_inventory = TRUE
|
||||
|
||||
/obj/item/proc/item_action_slot_check(slot, mob/user)
|
||||
return 1
|
||||
@@ -532,6 +539,7 @@ var/global/image/fire_overlay = image("icon" = 'icons/goonstation/effects/fire.d
|
||||
if(callback) //call the original callback
|
||||
. = callback.Invoke()
|
||||
throw_speed = initial(throw_speed) //explosions change this.
|
||||
in_inventory = FALSE
|
||||
|
||||
/obj/item/proc/pwr_drain()
|
||||
return 0 // Process Kill
|
||||
@@ -585,3 +593,16 @@ var/global/image/fire_overlay = image("icon" = 'icons/goonstation/effects/fire.d
|
||||
return
|
||||
var/mob/owner = loc
|
||||
owner.regenerate_icons()
|
||||
|
||||
/obj/item/proc/openTip(location, control, params, user)
|
||||
openToolTip(user, src, params, title = name, content = "[desc]", theme = "")
|
||||
|
||||
/obj/item/MouseEntered(location, control, params)
|
||||
if(in_inventory)
|
||||
var/timedelay = 5
|
||||
var/user = usr
|
||||
tip_timer = addtimer(CALLBACK(src, .proc/openTip, location, control, params, user), timedelay, TIMER_STOPPABLE)
|
||||
|
||||
/obj/item/MouseExited()
|
||||
deltimer(tip_timer) //delete any in-progress timer if the mouse is moved off the item before it finishes
|
||||
closeToolTip(usr)
|
||||
|
||||
@@ -307,6 +307,9 @@
|
||||
brightness_on = 7
|
||||
icon_state = "torch"
|
||||
item_state = "torch"
|
||||
lefthand_file = 'icons/mob/inhands/items_lefthand.dmi'
|
||||
righthand_file = 'icons/mob/inhands/items_righthand.dmi'
|
||||
light_color = LIGHT_COLOR_ORANGE
|
||||
on_damage = 10
|
||||
|
||||
/obj/item/flashlight/slime
|
||||
|
||||
@@ -1,3 +1,7 @@
|
||||
#define DISCONNECTED 0
|
||||
#define CLAMPED_OFF 1
|
||||
#define OPERATING 2
|
||||
|
||||
// Powersink - used to drain station power
|
||||
|
||||
/obj/item/powersink
|
||||
@@ -13,28 +17,55 @@
|
||||
throw_range = 2
|
||||
materials = list(MAT_METAL=750)
|
||||
origin_tech = "powerstorage=5;syndicate=5"
|
||||
var/drain_rate = 1600000 // amount of power to drain per tick
|
||||
var/apc_drain_rate = 50 // Max. amount drained from single APC. In Watts.
|
||||
var/dissipation_rate = 20000 // Passive dissipation of drained power. In Watts.
|
||||
var/power_drained = 0 // Amount of power drained.
|
||||
var/max_power = 1e10 // Detonation point.
|
||||
var/mode = 0 // 0 = off, 1=clamped (off), 2=operating
|
||||
var/drained_this_tick = 0 // This is unfortunately necessary to ensure we process powersinks BEFORE other machinery such as APCs.
|
||||
var/admins_warned = 0 // stop spam, only warn the admins once that we are about to go boom
|
||||
var/drain_rate = 2000000 // amount of power to drain per tick
|
||||
var/power_drained = 0 // has drained this much power
|
||||
var/max_power = 6e8 // maximum power that can be drained before exploding
|
||||
var/mode = 0 // 0 = off, 1=clamped (off), 2=operating
|
||||
var/admins_warned = FALSE // stop spam, only warn the admins once that we are about to boom
|
||||
|
||||
var/datum/powernet/PN // Our powernet
|
||||
var/obj/structure/cable/attached // the attached cable
|
||||
|
||||
/obj/item/powersink/Destroy()
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
GLOB.processing_power_items.Remove(src)
|
||||
PN = null
|
||||
attached = null
|
||||
return ..()
|
||||
|
||||
/obj/item/powersink/attackby(var/obj/item/I, var/mob/user)
|
||||
if(istype(I, /obj/item/screwdriver))
|
||||
if(mode == 0)
|
||||
/obj/item/powersink/update_icon()
|
||||
icon_state = "powersink[mode == OPERATING]"
|
||||
|
||||
/obj/item/powersink/proc/set_mode(value)
|
||||
if(value == mode)
|
||||
return
|
||||
switch(value)
|
||||
if(DISCONNECTED)
|
||||
attached = null
|
||||
if(mode == OPERATING)
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
anchored = FALSE
|
||||
density = FALSE
|
||||
|
||||
if(CLAMPED_OFF)
|
||||
if(!attached)
|
||||
return
|
||||
if(mode == OPERATING)
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
anchored = TRUE
|
||||
density = TRUE
|
||||
|
||||
if(OPERATING)
|
||||
if(!attached)
|
||||
return
|
||||
START_PROCESSING(SSobj, src)
|
||||
anchored = TRUE
|
||||
density = TRUE
|
||||
|
||||
mode = value
|
||||
update_icon()
|
||||
set_light(0)
|
||||
|
||||
/obj/item/powersink/attackby(obj/item/I, mob/user)
|
||||
if(isscrewdriver(I))
|
||||
if(mode == DISCONNECTED)
|
||||
var/turf/T = loc
|
||||
if(isturf(T) && !T.intact)
|
||||
attached = locate() in T
|
||||
@@ -42,98 +73,81 @@
|
||||
to_chat(user, "No exposed cable here to attach to.")
|
||||
return
|
||||
else
|
||||
anchored = 1
|
||||
mode = 1
|
||||
src.visible_message("<span class='notice'>[user] attaches [src] to the cable!</span>")
|
||||
set_mode(CLAMPED_OFF)
|
||||
visible_message("<span class='notice'>[user] attaches [src] to the cable!</span>")
|
||||
message_admins("Power sink activated by [key_name_admin(user)] at ([x],[y],[z] - <A HREF='?_src_=holder;adminplayerobservecoodjump=1;X=[x];Y=[y];Z=[z]'>JMP</a>)")
|
||||
log_game("Power sink activated by [key_name(user)] at ([x],[y],[z])")
|
||||
return
|
||||
else
|
||||
to_chat(user, "Device must be placed over an exposed cable to attach to it.")
|
||||
return
|
||||
else
|
||||
if(mode == 2)
|
||||
STOP_PROCESSING(SSobj, src) // Now the power sink actually stops draining the station's power if you unhook it. --NeoFite
|
||||
GLOB.processing_power_items.Remove(src)
|
||||
anchored = 0
|
||||
mode = 0
|
||||
set_mode(DISCONNECTED)
|
||||
src.visible_message("<span class='notice'>[user] detaches [src] from the cable!</span>")
|
||||
set_light(0)
|
||||
icon_state = "powersink0"
|
||||
|
||||
return
|
||||
else
|
||||
..()
|
||||
return ..()
|
||||
|
||||
/obj/item/powersink/attack_ai()
|
||||
return
|
||||
|
||||
/obj/item/powersink/attack_hand(var/mob/user)
|
||||
switch(mode)
|
||||
if(0)
|
||||
if(DISCONNECTED)
|
||||
..()
|
||||
if(1)
|
||||
src.visible_message("<span class='notice'>[user] activates [src]!</span>")
|
||||
mode = 2
|
||||
icon_state = "powersink1"
|
||||
START_PROCESSING(SSobj, src)
|
||||
GLOB.processing_power_items.Add(src)
|
||||
if(2) //This switch option wasn't originally included. It exists now. --NeoFite
|
||||
src.visible_message("<span class='notice'>[user] deactivates [src]!</span>")
|
||||
mode = 1
|
||||
set_light(0)
|
||||
icon_state = "powersink0"
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
GLOB.processing_power_items.Remove(src)
|
||||
|
||||
/obj/item/powersink/pwr_drain()
|
||||
if(!attached)
|
||||
return 0
|
||||
|
||||
if(drained_this_tick)
|
||||
return 1
|
||||
drained_this_tick = 1
|
||||
|
||||
var/drained = 0
|
||||
|
||||
if(!PN)
|
||||
return 1
|
||||
|
||||
set_light(12)
|
||||
PN.trigger_warning()
|
||||
// found a powernet, so drain up to max power from it
|
||||
drained = PN.draw_power(drain_rate)
|
||||
// if tried to drain more than available on powernet
|
||||
// now look for APCs and drain their cells
|
||||
if(drained < drain_rate)
|
||||
for(var/obj/machinery/power/terminal/T in PN.nodes)
|
||||
// Enough power drained this tick, no need to torture more APCs
|
||||
if(drained >= drain_rate)
|
||||
break
|
||||
if(istype(T.master, /obj/machinery/power/apc))
|
||||
var/obj/machinery/power/apc/A = T.master
|
||||
if(A.operating && A.cell)
|
||||
A.cell.charge = max(0, A.cell.charge - apc_drain_rate)
|
||||
drained += apc_drain_rate
|
||||
if(A.charging == 2) // If the cell was full
|
||||
A.charging = 1 // It's no longer full
|
||||
power_drained += drained
|
||||
return 1
|
||||
if(CLAMPED_OFF)
|
||||
user.visible_message( \
|
||||
"[user] activates \the [src]!", \
|
||||
"<span class='notice'>You activate \the [src].</span>",
|
||||
"<span class='italics'>You hear a click.</span>")
|
||||
message_admins("Power sink activated by [ADMIN_LOOKUPFLW(user)] at [ADMIN_VERBOSEJMP(src)]")
|
||||
log_game("Power sink activated by [key_name(user)] at [AREACOORD(src)]")
|
||||
set_mode(OPERATING)
|
||||
|
||||
if(OPERATING)
|
||||
user.visible_message( \
|
||||
"[user] deactivates \the [src]!", \
|
||||
"<span class='notice'>You deactivate \the [src].</span>",
|
||||
"<span class='italics'>You hear a click.</span>")
|
||||
set_mode(CLAMPED_OFF)
|
||||
|
||||
/obj/item/powersink/process()
|
||||
drained_this_tick = 0
|
||||
power_drained -= min(dissipation_rate, power_drained)
|
||||
if(!attached)
|
||||
set_mode(DISCONNECTED)
|
||||
return
|
||||
|
||||
var/datum/powernet/PN = attached.powernet
|
||||
if(PN)
|
||||
set_light(5)
|
||||
|
||||
// found a powernet, so drain up to max power from it
|
||||
|
||||
var/drained = min (drain_rate, attached.newavail())
|
||||
attached.add_delayedload(drained)
|
||||
power_drained += drained
|
||||
|
||||
// if tried to drain more than available on powernet
|
||||
// now look for APCs and drain their cells
|
||||
if(drained < drain_rate)
|
||||
for(var/obj/machinery/power/terminal/T in PN.nodes)
|
||||
if(istype(T.master, /obj/machinery/power/apc))
|
||||
var/obj/machinery/power/apc/A = T.master
|
||||
if(A.operating && A.cell)
|
||||
A.cell.charge = max(0, A.cell.charge - 50)
|
||||
power_drained += 50
|
||||
if(A.charging == 2) // If the cell was full
|
||||
A.charging = 1 // It's no longer full
|
||||
if(drained >= drain_rate)
|
||||
break
|
||||
|
||||
if(power_drained > max_power * 0.98)
|
||||
if(!admins_warned)
|
||||
admins_warned = 1
|
||||
if (!admins_warned)
|
||||
admins_warned = TRUE
|
||||
message_admins("Power sink at ([x],[y],[z] - <A HREF='?_src_=holder;adminplayerobservecoodjump=1;X=[x];Y=[y];Z=[z]'>JMP</a>) is 95% full. Explosion imminent.")
|
||||
playsound(src, 'sound/effects/screech.ogg', 100, 1, 1)
|
||||
|
||||
if(power_drained >= max_power)
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
explosion(src.loc, 4,8,16,32)
|
||||
qdel(src)
|
||||
return
|
||||
if(attached && attached.powernet)
|
||||
PN = attached.powernet
|
||||
else
|
||||
PN = null
|
||||
|
||||
#undef DISCONNECTED
|
||||
#undef CLAMPED_OFF
|
||||
#undef OPERATING
|
||||
@@ -54,7 +54,7 @@
|
||||
to_chat(user, "There are [amount] [singular_name]\s in the stack.")
|
||||
else
|
||||
to_chat(user, "There are [amount] [name]\s in the stack.")
|
||||
to_chat(user,"<span class='notice'>Ctrl-Shift-click to take a custom amount.</span>")
|
||||
to_chat(user,"<span class='notice'>Alt-click to take a custom amount.</span>")
|
||||
|
||||
/obj/item/stack/proc/add(newamount)
|
||||
amount += newamount
|
||||
@@ -263,7 +263,7 @@
|
||||
else
|
||||
..()
|
||||
|
||||
/obj/item/stack/CtrlShiftClick(mob/living/user)
|
||||
/obj/item/stack/AltClick(mob/living/user)
|
||||
if(!istype(user) || user.incapacitated())
|
||||
to_chat(user, "<span class='warning'>You can't do that right now!</span>")
|
||||
return
|
||||
@@ -276,7 +276,7 @@
|
||||
//get amount from user
|
||||
var/min = 0
|
||||
var/max = get_amount()
|
||||
var/stackmaterial = round(input(user, "How many sheets do you wish to take out of this stack? (Maximum: [max])") as num)
|
||||
var/stackmaterial = round(input(user, "How many sheets do you wish to take out of this stack? (Maximum: [max])") as null|num)
|
||||
if(stackmaterial == null || stackmaterial <= min || stackmaterial > get_amount())
|
||||
return
|
||||
change_stack(user,stackmaterial)
|
||||
|
||||
@@ -98,6 +98,8 @@
|
||||
//alt titles are handled a bit weirdly in order to unobtrusively integrate into existing ID system
|
||||
var/assignment = null //can be alt title or the actual job
|
||||
var/rank = null //actual job
|
||||
var/owner_uid
|
||||
var/owner_ckey
|
||||
var/dorm = 0 // determines if this ID has claimed a dorm already
|
||||
|
||||
var/sex
|
||||
@@ -195,6 +197,19 @@
|
||||
jobnamedata += " (" + assignment + ")"
|
||||
return jobnamedata
|
||||
|
||||
/obj/item/card/id/proc/getPlayer()
|
||||
if(owner_uid)
|
||||
var/mob/living/carbon/human/H = locateUID(owner_uid)
|
||||
if(istype(H) && H.ckey == owner_ckey)
|
||||
return H
|
||||
owner_uid = null
|
||||
if(owner_ckey)
|
||||
for(var/mob/M in GLOB.player_list)
|
||||
if(M.ckey && M.ckey == owner_ckey)
|
||||
owner_uid = M.UID()
|
||||
return M
|
||||
owner_ckey = null
|
||||
|
||||
/obj/item/card/id/proc/is_untrackable()
|
||||
return untrackable
|
||||
|
||||
|
||||
@@ -112,10 +112,9 @@
|
||||
/obj/item/dice/attack_self(mob/user as mob)
|
||||
diceroll(user)
|
||||
|
||||
/obj/item/dice/throw_at(atom/target, range, speed, mob/thrower, spin=1, diagonals_first = 0, datum/callback/callback)
|
||||
if(!..())
|
||||
return
|
||||
diceroll(thrower)
|
||||
/obj/item/dice/throw_impact(atom/target)
|
||||
diceroll(thrownby)
|
||||
. = ..()
|
||||
|
||||
/obj/item/dice/proc/diceroll(mob/user)
|
||||
result = rand(1, sides)
|
||||
|
||||
@@ -152,8 +152,14 @@
|
||||
breakouttime = 35//easy to apply, easy to break out of
|
||||
gender = NEUTER
|
||||
origin_tech = "engineering=3;combat=1"
|
||||
hitsound = 'sound/effects/snap.ogg'
|
||||
var/weaken = 0
|
||||
|
||||
/obj/item/restraints/legcuffs/bola/throw_at(atom/target, range, speed, mob/thrower, spin=1, diagonals_first = 0, datum/callback/callback)
|
||||
playsound(loc,'sound/weapons/bolathrow.ogg', 50, TRUE)
|
||||
if(!..())
|
||||
return
|
||||
|
||||
/obj/item/restraints/legcuffs/bola/throw_impact(atom/hit_atom)
|
||||
if(..() || !iscarbon(hit_atom))//if it gets caught or the target can't be cuffed,
|
||||
return//abort
|
||||
@@ -166,6 +172,7 @@
|
||||
feedback_add_details("handcuffs","B")
|
||||
to_chat(C, "<span class='userdanger'>[src] ensnares you!</span>")
|
||||
C.Weaken(weaken)
|
||||
playsound(loc, hitsound, 50, TRUE)
|
||||
|
||||
/obj/item/restraints/legcuffs/bola/tactical //traitor variant
|
||||
name = "reinforced bola"
|
||||
|
||||
@@ -28,6 +28,22 @@
|
||||
else
|
||||
has_extinguisher = new/obj/item/extinguisher
|
||||
|
||||
/obj/structure/extinguisher_cabinet/examine(mob/user)
|
||||
..()
|
||||
to_chat(user, "<span class='notice'>Alt-click to [opened ? "close":"open"] it.</span>")
|
||||
|
||||
/obj/structure/extinguisher_cabinet/AltClick(mob/living/user)
|
||||
if(!istype(user) || user.incapacitated())
|
||||
to_chat(user, "<span class='warning'>You can't do that right now!</span>")
|
||||
return
|
||||
if(!in_range(src, user))
|
||||
return
|
||||
if(!iscarbon(usr))
|
||||
return
|
||||
playsound(loc, 'sound/machines/click.ogg', 15, TRUE, -3)
|
||||
opened = !opened
|
||||
update_icon()
|
||||
|
||||
/obj/structure/extinguisher_cabinet/Destroy()
|
||||
QDEL_NULL(has_extinguisher)
|
||||
return ..()
|
||||
@@ -37,11 +53,16 @@
|
||||
return
|
||||
if(istype(O, /obj/item/extinguisher))
|
||||
if(!has_extinguisher && opened)
|
||||
if(!user.drop_item())
|
||||
return
|
||||
user.drop_item(O)
|
||||
contents += O
|
||||
has_extinguisher = O
|
||||
update_icon()
|
||||
to_chat(user, "<span class='notice'>You place [O] in [src].</span>")
|
||||
return TRUE
|
||||
else
|
||||
playsound(loc, 'sound/machines/click.ogg', 15, TRUE, -3)
|
||||
opened = !opened
|
||||
else if(istype(O, /obj/item/weldingtool))
|
||||
if(has_extinguisher)
|
||||
@@ -65,6 +86,7 @@
|
||||
new material_drop(T)
|
||||
qdel(src)
|
||||
else
|
||||
playsound(loc, 'sound/machines/click.ogg', 15, TRUE, -3)
|
||||
opened = !opened
|
||||
update_icon()
|
||||
|
||||
@@ -81,21 +103,27 @@
|
||||
to_chat(user, "<span class='notice'>You try to move your [temp.name], but cannot!")
|
||||
return
|
||||
if(has_extinguisher)
|
||||
if(icon_state == "extinguisher_closed")
|
||||
playsound(loc, 'sound/machines/click.ogg', 15, TRUE, -3)
|
||||
user.put_in_hands(has_extinguisher)
|
||||
to_chat(user, "<span class='notice'>You take [has_extinguisher] from [src].</span>")
|
||||
has_extinguisher = null
|
||||
opened = 1
|
||||
else
|
||||
playsound(loc, 'sound/machines/click.ogg', 15, TRUE, -3)
|
||||
opened = !opened
|
||||
update_icon()
|
||||
|
||||
/obj/structure/extinguisher_cabinet/attack_tk(mob/user)
|
||||
if(has_extinguisher)
|
||||
if(icon_state == "extinguisher_closed")
|
||||
playsound(loc, 'sound/machines/click.ogg', 15, TRUE, -3)
|
||||
has_extinguisher.loc = loc
|
||||
to_chat(user, "<span class='notice'>You telekinetically remove [has_extinguisher] from [src].</span>")
|
||||
has_extinguisher = null
|
||||
opened = 1
|
||||
else
|
||||
playsound(loc, 'sound/machines/click.ogg', 15, TRUE, -3)
|
||||
opened = !opened
|
||||
update_icon()
|
||||
|
||||
|
||||
@@ -273,8 +273,8 @@
|
||||
var/obj/structure/cable/C = T.get_cable_node()
|
||||
if(C)
|
||||
playsound(loc, 'sound/magic/lightningshock.ogg', 100, 1, extrarange = 5)
|
||||
tesla_zap(src, 3, C.powernet.avail * 0.01) //Zap for 1/100 of the amount of power. At a million watts in the grid, it will be as powerful as a tesla revolver shot.
|
||||
C.powernet.load += C.powernet.avail * 0.0375 // you can gain up to 3.5 via the 4x upgrades power is halved by the pole so thats 2x then 1X then .5X for 3.5x the 3 bounces shock.
|
||||
tesla_zap(src, 3, C.newavail() * 0.01) //Zap for 1/100 of the amount of power. At a million watts in the grid, it will be as powerful as a tesla revolver shot.
|
||||
C.add_delayedload(C.newavail() * 0.0375) // you can gain up to 3.5 via the 4x upgrades power is halved by the pole so thats 2x then 1X then .5X for 3.5x the 3 bounces shock.
|
||||
return ..()
|
||||
|
||||
/obj/structure/grille/broken // Pre-broken grilles for map placement
|
||||
|
||||
Reference in New Issue
Block a user