diff --git a/.travis.yml b/.travis.yml
index 51bb590878..841b6a9713 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -5,7 +5,7 @@ sudo: false
env:
BYOND_MAJOR="511"
BYOND_MINOR="1381"
- MACRO_COUNT=875
+ MACRO_COUNT=4
cache:
directories:
diff --git a/README.md b/README.md
index f9c1434358..4a602db1f7 100644
--- a/README.md
+++ b/README.md
@@ -7,16 +7,22 @@ VOREStation is a fork of the Polaris code branch, itself a fork of the Baystatio
---
### LICENSE
+<<<<<<< HEAD
VOREStation is licensed under the GNU Affero General Public License version 3, which can be found in full in LICENSE-AGPL3.txt.
+=======
+The code for Polaris is licensed under the [GNU Affero General Public License](http://www.gnu.org/licenses/agpl.html) version 3, which can be found in full in LICENSE-AGPL3.txt.
+>>>>>>> PolarisSS13/master
-Commits with a git authorship date prior to `1420675200 +0000` (2015/01/08 00:00) are licensed under the GNU General Public License version 3, which can be found in full in LICENSE-GPL3.txt.
+Code with a git authorship date prior to `1420675200 +0000` (2015/01/08 00:00) are licensed under the GNU General Public License version 3, which can be found in full in LICENSE-GPL3.txt.
-All commits whose authorship dates are not prior to `1420675200 +0000` are assumed to be licensed under AGPL v3, if you wish to license under GPL v3 please make this clear in the commit message and any added files.
+All code whose authorship dates are not prior to `1420675200 +0000` are assumed to be licensed under AGPL v3, if you wish to license under GPL v3 please make this clear in the commit message and any added files.
-If you wish to develop and host this codebase in a closed source manner you may use all commits prior to `1420675200 +0000`, which are licensed under GPL v3. The major change here is that if you host a server using any code licensed under AGPLv3 you are required to provide full source code for your servers users as well including addons and modifications you have made.
+If you wish to develop and host this codebase in a closed source manner you may use all code prior to `1420675200 +0000`, which are licensed under GPL v3. The major change here is that if you host a server using any code licensed under AGPLv3 you are required to provide full source code for your servers users as well including addons and modifications you have made.
See [here](https://www.gnu.org/licenses/why-affero-gpl.html) for more information.
+All assets including icons and sound are under a [CC BY-SA 3.0](http://creativecommons.org/licenses/by-sa/3.0/) license unless otherwise indicated.
+
### GETTING THE CODE
The simplest way to obtain the code is using the github .zip feature.
diff --git a/code/ATMOSPHERICS/components/binary_devices/circulator.dm b/code/ATMOSPHERICS/components/binary_devices/circulator.dm
index 6627d15d73..09335cdf33 100644
--- a/code/ATMOSPHERICS/components/binary_devices/circulator.dm
+++ b/code/ATMOSPHERICS/components/binary_devices/circulator.dm
@@ -89,11 +89,11 @@
/obj/machinery/atmospherics/binary/circulator/attackby(obj/item/weapon/W as obj, mob/user as mob)
if(istype(W, /obj/item/weapon/wrench))
- playsound(src.loc, 'sound/items/Ratchet.ogg', 75, 1)
+ playsound(src, W.usesound, 75, 1)
anchored = !anchored
user.visible_message("[user.name] [anchored ? "secures" : "unsecures"] the bolts holding [src.name] to the floor.", \
"You [anchored ? "secure" : "unsecure"] the bolts holding [src] to the floor.", \
- "You hear a ratchet")
+ "You hear a ratchet.")
if(anchored)
if(dir & (NORTH|SOUTH))
diff --git a/code/ATMOSPHERICS/components/binary_devices/passive_gate.dm b/code/ATMOSPHERICS/components/binary_devices/passive_gate.dm
index 6a51dc41b1..fa88ef2ab2 100644
--- a/code/ATMOSPHERICS/components/binary_devices/passive_gate.dm
+++ b/code/ATMOSPHERICS/components/binary_devices/passive_gate.dm
@@ -11,15 +11,15 @@
desc = "A one-way air valve that can be used to regulate input or output pressure, and flow rate. Does not require power."
use_power = 0
-
+
var/unlocked = 0 //If 0, then the valve is locked closed, otherwise it is open(-able, it's a one-way valve so it closes if gas would flow backwards).
var/target_pressure = ONE_ATMOSPHERE
var/max_pressure_setting = 15000 //kPa
var/set_flow_rate = ATMOS_DEFAULT_VOLUME_PUMP * 2.5
var/regulate_mode = REGULATE_OUTPUT
-
+
var/flowing = 0 //for icons - becomes zero if the valve closes itself due to regulation mode
-
+
var/frequency = 0
var/id = null
var/datum/radio_frequency/radio_connection
@@ -46,9 +46,9 @@
/obj/machinery/atmospherics/binary/passive_gate/process()
..()
-
+
last_flow_rate = 0
-
+
if(!unlocked)
return 0
@@ -61,35 +61,35 @@
pressure_delta = input_starting_pressure - target_pressure
if (REGULATE_OUTPUT)
pressure_delta = target_pressure - output_starting_pressure
-
+
//-1 if pump_gas() did not move any gas, >= 0 otherwise
var/returnval = -1
if((regulate_mode == REGULATE_NONE || pressure_delta > 0.01) && (air1.temperature > 0 || air2.temperature > 0)) //since it's basically a valve, it makes sense to check both temperatures
flowing = 1
-
+
//flow rate limit
var/transfer_moles = (set_flow_rate/air1.volume)*air1.total_moles
-
+
//Figure out how much gas to transfer to meet the target pressure.
switch (regulate_mode)
if (REGULATE_INPUT)
transfer_moles = min(transfer_moles, calculate_transfer_moles(air2, air1, pressure_delta, (network1)? network1.volume : 0))
if (REGULATE_OUTPUT)
transfer_moles = min(transfer_moles, calculate_transfer_moles(air1, air2, pressure_delta, (network2)? network2.volume : 0))
-
+
//pump_gas() will return a negative number if no flow occurred
returnval = pump_gas_passive(src, air1, air2, transfer_moles)
-
+
if (returnval >= 0)
if(network1)
network1.update = 1
if(network2)
network2.update = 1
-
+
if (last_flow_rate)
flowing = 1
-
+
update_icon()
@@ -178,7 +178,7 @@
// this is the data which will be sent to the ui
var/data[0]
-
+
data = list(
"on" = unlocked,
"pressure_set" = round(target_pressure*100), //Nano UI can't handle rounded non-integers, apparently.
@@ -203,16 +203,16 @@
/obj/machinery/atmospherics/binary/passive_gate/Topic(href,href_list)
if(..()) return 1
-
+
if(href_list["toggle_valve"])
unlocked = !unlocked
-
+
if(href_list["regulate_mode"])
switch(href_list["regulate_mode"])
if ("off") regulate_mode = REGULATE_NONE
if ("input") regulate_mode = REGULATE_INPUT
if ("output") regulate_mode = REGULATE_OUTPUT
-
+
switch(href_list["set_press"])
if ("min")
target_pressure = 0
@@ -221,7 +221,7 @@
if ("set")
var/new_pressure = input(usr,"Enter new output pressure (0-[max_pressure_setting]kPa)","Pressure Control",src.target_pressure) as num
src.target_pressure = between(0, new_pressure, max_pressure_setting)
-
+
switch(href_list["set_flow_rate"])
if ("min")
set_flow_rate = 0
@@ -230,7 +230,7 @@
if ("set")
var/new_flow_rate = input(usr,"Enter new flow rate limit (0-[air1.volume]kPa)","Flow Rate Control",src.set_flow_rate) as num
src.set_flow_rate = between(0, new_flow_rate, air1.volume)
-
+
usr.set_machine(src) //Is this even needed with NanoUI?
src.update_icon()
src.add_fingerprint(usr)
@@ -248,9 +248,9 @@
user << "You cannot unwrench \the [src], it too exerted due to internal pressure."
add_fingerprint(user)
return 1
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src]..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/ATMOSPHERICS/components/binary_devices/pipeturbine.dm b/code/ATMOSPHERICS/components/binary_devices/pipeturbine.dm
index d0417e14dd..1b576e1042 100644
--- a/code/ATMOSPHERICS/components/binary_devices/pipeturbine.dm
+++ b/code/ATMOSPHERICS/components/binary_devices/pipeturbine.dm
@@ -86,6 +86,7 @@
attackby(obj/item/weapon/W as obj, mob/user as mob)
if(istype(W, /obj/item/weapon/wrench))
anchored = !anchored
+ playsound(src, W.usesound, 50, 1)
user << "You [anchored ? "secure" : "unsecure"] the bolts holding \the [src] to the floor."
if(anchored)
@@ -257,6 +258,7 @@
attackby(obj/item/weapon/W as obj, mob/user as mob)
if(istype(W, /obj/item/weapon/wrench))
anchored = !anchored
+ playsound(src, W.usesound, 50, 1)
turbine = null
user << "You [anchored ? "secure" : "unsecure"] the bolts holding \the [src] to the floor."
updateConnection()
diff --git a/code/ATMOSPHERICS/components/binary_devices/pump.dm b/code/ATMOSPHERICS/components/binary_devices/pump.dm
index 16f5c0a586..126c6391d4 100644
--- a/code/ATMOSPHERICS/components/binary_devices/pump.dm
+++ b/code/ATMOSPHERICS/components/binary_devices/pump.dm
@@ -227,9 +227,9 @@ Thus, the two variables affect pump operation are set in New():
user << "You cannot unwrench this [src], it too exerted due to internal pressure."
add_fingerprint(user)
return 1
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src]..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/ATMOSPHERICS/components/omni_devices/omni_base.dm b/code/ATMOSPHERICS/components/omni_devices/omni_base.dm
index d21bd9b503..04d3f36fd1 100644
--- a/code/ATMOSPHERICS/components/omni_devices/omni_base.dm
+++ b/code/ATMOSPHERICS/components/omni_devices/omni_base.dm
@@ -91,8 +91,8 @@
add_fingerprint(user)
return 1
user << "You begin to unfasten \the [src]..."
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
- if(do_after(user, 40))
+ playsound(src, W.usesound, 50, 1)
+ if(do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/ATMOSPHERICS/components/portables_connector.dm b/code/ATMOSPHERICS/components/portables_connector.dm
index 9668f7a5a3..c39ca8469b 100644
--- a/code/ATMOSPHERICS/components/portables_connector.dm
+++ b/code/ATMOSPHERICS/components/portables_connector.dm
@@ -142,9 +142,9 @@
user << "You cannot unwrench \the [src], it too exerted due to internal pressure."
add_fingerprint(user)
return 1
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src]..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/ATMOSPHERICS/components/trinary_devices/filter.dm b/code/ATMOSPHERICS/components/trinary_devices/filter.dm
index 2778566923..ef6a29b910 100755
--- a/code/ATMOSPHERICS/components/trinary_devices/filter.dm
+++ b/code/ATMOSPHERICS/components/trinary_devices/filter.dm
@@ -137,9 +137,9 @@
user << "You cannot unwrench \the [src], it too exerted due to internal pressure."
add_fingerprint(user)
return 1
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src]..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/ATMOSPHERICS/components/trinary_devices/mixer.dm b/code/ATMOSPHERICS/components/trinary_devices/mixer.dm
index a163c122f0..f8c3e9ff67 100644
--- a/code/ATMOSPHERICS/components/trinary_devices/mixer.dm
+++ b/code/ATMOSPHERICS/components/trinary_devices/mixer.dm
@@ -68,7 +68,7 @@
air1.volume = ATMOS_DEFAULT_VOLUME_MIXER
air2.volume = ATMOS_DEFAULT_VOLUME_MIXER
air3.volume = ATMOS_DEFAULT_VOLUME_MIXER * 1.5
-
+
if (!mixing_inputs)
mixing_inputs = list(src.air1 = node1_concentration, src.air2 = node2_concentration)
@@ -112,9 +112,9 @@
user << "You cannot unwrench \the [src], it too exerted due to internal pressure."
add_fingerprint(user)
return 1
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src]..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/ATMOSPHERICS/components/tvalve.dm b/code/ATMOSPHERICS/components/tvalve.dm
index a7deb70aba..81a870743e 100644
--- a/code/ATMOSPHERICS/components/tvalve.dm
+++ b/code/ATMOSPHERICS/components/tvalve.dm
@@ -354,9 +354,9 @@
user << "You cannot unwrench \the [src], it too exerted due to internal pressure."
add_fingerprint(user)
return 1
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src]..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/ATMOSPHERICS/components/unary/heat_exchanger.dm b/code/ATMOSPHERICS/components/unary/heat_exchanger.dm
index 79e43a8e1c..533e84b8f9 100644
--- a/code/ATMOSPHERICS/components/unary/heat_exchanger.dm
+++ b/code/ATMOSPHERICS/components/unary/heat_exchanger.dm
@@ -78,9 +78,9 @@
user << "You cannot unwrench \the [src], it is too exerted due to internal pressure."
add_fingerprint(user)
return 1
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src]..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/ATMOSPHERICS/components/unary/vent_pump.dm b/code/ATMOSPHERICS/components/unary/vent_pump.dm
index c6121dea31..b44f8768ff 100644
--- a/code/ATMOSPHERICS/components/unary/vent_pump.dm
+++ b/code/ATMOSPHERICS/components/unary/vent_pump.dm
@@ -358,9 +358,9 @@
var/obj/item/weapon/weldingtool/WT = W
if (WT.remove_fuel(0,user))
user << "Now welding the vent."
- if(do_after(user, 20))
+ if(do_after(user, 20 * WT.toolspeed))
if(!src || !WT.isOn()) return
- playsound(src.loc, 'sound/items/Welder2.ogg', 50, 1)
+ playsound(src.loc, WT.usesound, 50, 1)
if(!welded)
user.visible_message("\The [user] welds the vent shut.", "You weld the vent shut.", "You hear welding.")
welded = 1
@@ -407,9 +407,9 @@
user << "You cannot unwrench \the [src], it is too exerted due to internal pressure."
add_fingerprint(user)
return 1
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src]..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/ATMOSPHERICS/components/unary/vent_scrubber.dm b/code/ATMOSPHERICS/components/unary/vent_scrubber.dm
index 3fccbb50f3..539ab2ecc8 100644
--- a/code/ATMOSPHERICS/components/unary/vent_scrubber.dm
+++ b/code/ATMOSPHERICS/components/unary/vent_scrubber.dm
@@ -107,6 +107,7 @@
"filter_co2" = ("carbon_dioxide" in scrubbing_gas),
"filter_phoron" = ("phoron" in scrubbing_gas),
"filter_n2o" = ("sleeping_agent" in scrubbing_gas),
+ "filter_fuel" = ("volatile_fuel" in scrubbing_gas),
"sigtype" = "status"
)
if(!initial_loc.air_scrub_names[id_tag])
@@ -233,6 +234,11 @@
else if(signal.data["toggle_n2o_scrub"])
toggle += "sleeping_agent"
+ if(!isnull(signal.data["fuel_scrub"]) && text2num(signal.data["fuel_scrub"]) != ("volatile_fuel" in scrubbing_gas))
+ toggle += "volatile_fuel"
+ else if(signal.data["toggle_fuel_scrub"])
+ toggle += "volatile_fuel"
+
scrubbing_gas ^= toggle
if(signal.data["init"] != null)
@@ -272,9 +278,9 @@
user << "You cannot unwrench \the [src], it is too exerted due to internal pressure."
add_fingerprint(user)
return 1
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src]..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/ATMOSPHERICS/components/valve.dm b/code/ATMOSPHERICS/components/valve.dm
index 01e6e977bb..7fa8d60a77 100644
--- a/code/ATMOSPHERICS/components/valve.dm
+++ b/code/ATMOSPHERICS/components/valve.dm
@@ -298,9 +298,9 @@
user << "You cannot unwrench \the [src], it is too exerted due to internal pressure."
add_fingerprint(user)
return 1
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src]..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/ATMOSPHERICS/pipes.dm b/code/ATMOSPHERICS/pipes.dm
index 28440254bb..a565dc12d0 100644
--- a/code/ATMOSPHERICS/pipes.dm
+++ b/code/ATMOSPHERICS/pipes.dm
@@ -90,9 +90,9 @@
user << "You cannot unwrench \the [src], it is too exerted due to internal pressure."
add_fingerprint(user)
return 1
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src]..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/__defines/atmos.dm b/code/__defines/atmos.dm
index f67c967157..bd9175aab1 100644
--- a/code/__defines/atmos.dm
+++ b/code/__defines/atmos.dm
@@ -74,6 +74,7 @@
#define XGM_GAS_FUEL 1
#define XGM_GAS_OXIDIZER 2
#define XGM_GAS_CONTAMINANT 4
+#define XGM_GAS_FUSION_FUEL 8
#define TANK_LEAK_PRESSURE (30.*ONE_ATMOSPHERE) // Tank starts leaking.
#define TANK_RUPTURE_PRESSURE (40.*ONE_ATMOSPHERE) // Tank spills all contents into atmosphere.
diff --git a/code/__defines/belly_modes_vr.dm b/code/__defines/belly_modes_vr.dm
index 1fb1cbf02c..5444794017 100644
--- a/code/__defines/belly_modes_vr.dm
+++ b/code/__defines/belly_modes_vr.dm
@@ -1,6 +1,8 @@
// Belly Mode Constants
#define DM_HOLD "Hold"
#define DM_DIGEST "Digest"
+#define DM_ITEMWEAK "Digest (Item Friendly)"
+#define DM_STRIPDIGEST "Strip Digest (Items Only)"
#define DM_DIGEST_NUMB "Digest (Numbing)"
#define DM_HEAL "Heal"
#define DM_ABSORB "Absorb"
diff --git a/code/__defines/gamemode.dm b/code/__defines/gamemode.dm
index cd0c9955c1..0be497843b 100644
--- a/code/__defines/gamemode.dm
+++ b/code/__defines/gamemode.dm
@@ -84,6 +84,7 @@ var/list/be_special_flags = list(
#define MODE_MALFUNCTION "malf"
#define MODE_TRAITOR "traitor"
#define MODE_AUTOTRAITOR "autotraitor"
+#define MODE_INFILTRATOR "infiltrator"
#define DEFAULT_TELECRYSTAL_AMOUNT 120
@@ -95,7 +96,7 @@ var/list/be_special_flags = list(
#define GHOSTCAST 0x1 //can a ghost cast it?
#define NEEDSCLOTHES 0x2 //does it need the wizard garb to cast? Nonwizard spells should not have this
#define NEEDSHUMAN 0x4 //does it require the caster to be human?
-#define Z2NOCAST 0x8 //if this is added, the spell can't be cast at centcomm
+#define Z2NOCAST 0x8 //if this is added, the spell can't be cast at CentCom
#define STATALLOWED 0x10 //if set, the user doesn't have to be conscious to cast. Required for ghost spells
#define IGNOREPREV 0x20 //if set, each new target does not overlap with the previous one
//The following flags only affect different types of spell, and therefore overlap
diff --git a/code/__defines/machinery.dm b/code/__defines/machinery.dm
index cae68c3a23..deaaec0fad 100644
--- a/code/__defines/machinery.dm
+++ b/code/__defines/machinery.dm
@@ -58,7 +58,7 @@ var/global/defer_powernet_rebuild = 0 // True if net rebuild will be called
#define NETWORK_COMMUNICATORS "Communicators"
// Those networks can only be accessed by pre-existing terminals. AIs and new terminals can't use them.
-var/list/restricted_camera_networks = list(NETWORK_ERT,NETWORK_MERCENARY,"Secret")
+var/list/restricted_camera_networks = list(NETWORK_ERT,NETWORK_MERCENARY,"Secret", NETWORK_COMMUNICATORS)
//singularity defines
diff --git a/code/__defines/misc.dm b/code/__defines/misc.dm
index 984b02dd2b..8a1ca78d4f 100644
--- a/code/__defines/misc.dm
+++ b/code/__defines/misc.dm
@@ -89,6 +89,11 @@
#define SHUTTLE_INTRANSIT 2
#define SHUTTLE_CRASHED 3 // VOREStation Edit - Yup that can happen now
+// Sound defines for shuttles.
+#define HYPERSPACE_WARMUP 0
+#define HYPERSPACE_PROGRESS 1
+#define HYPERSPACE_END 2
+
// Ferry shuttle processing status.
#define IDLE_STATE 0
#define WAIT_LAUNCH 1
@@ -147,6 +152,14 @@
#define DEFAULT_TABLE_MATERIAL "plastic"
#define DEFAULT_WALL_MATERIAL "steel"
+#define MAT_STEEL "steel"
+#define MAT_GLASS "glass"
+#define MAT_SILVER "silver"
+#define MAT_GOLD "gold"
+#define MAT_TITANIUM "titanium"
+#define MAT_PHORON "phoron"
+#define MAT_DIAMOND "diamond"
+
#define SHARD_SHARD "shard"
#define SHARD_SHRAPNEL "shrapnel"
#define SHARD_STONE_PIECE "piece"
@@ -203,3 +216,6 @@
#define TSC_GIL "Gilthari"
#define MIDNIGHT_ROLLOVER 864000 //number of deciseconds in a day
+
+#define WORLD_ICON_SIZE 32 //Needed for the R-UST port
+#define PIXEL_MULTIPLIER WORLD_ICON_SIZE/32 //Needed for the R-UST port
diff --git a/code/_helpers/game.dm b/code/_helpers/game.dm
index fb99da896f..ddcae4980b 100644
--- a/code/_helpers/game.dm
+++ b/code/_helpers/game.dm
@@ -281,15 +281,15 @@
//A list of every mob with a client
for(var/mob in player_list)
- if(isnull(mob)) //VOREStation Add - Fix for a weird bug with nulls in this list
- player_list -= mob //VOREStation Add
- continue //VOREStation Add
+ if(!istype(mob, /mob))
+ crash_with("There is a null or non-mob reference inside player_list.")
+ continue
if(get_turf(mob) in hearturfs)
mobs |= mob
continue
var/mob/M = mob
- if(M.stat == DEAD && !M.forbid_seeing_deadchat)
+ if(M && M.stat == DEAD && !M.forbid_seeing_deadchat)
switch(type)
if(1) //Audio messages use ghost_ears
if(M.is_preference_enabled(/datum/client_preference/ghost_ears))
diff --git a/code/_helpers/global_lists_vr.dm b/code/_helpers/global_lists_vr.dm
index 3e83ce7fbf..4680bf9254 100644
--- a/code/_helpers/global_lists_vr.dm
+++ b/code/_helpers/global_lists_vr.dm
@@ -38,7 +38,8 @@ var/global/list/important_items = list(
/obj/item/clothing/shoes/magboots,
/obj/item/blueprints,
/obj/item/clothing/head/helmet/space,
- /obj/item/weapon/disk/nuclear)
+ /obj/item/weapon/disk/nuclear,
+ /obj/item/clothing/suit/storage/hooded/wintercoat/roiz)
var/global/list/digestion_sounds = list(
'sound/vore/digest1.ogg',
diff --git a/code/_helpers/type2type.dm b/code/_helpers/type2type.dm
index 8dc9cb020b..975e65e3ec 100644
--- a/code/_helpers/type2type.dm
+++ b/code/_helpers/type2type.dm
@@ -80,7 +80,9 @@
if (NORTHEAST) return "northeast"
if (SOUTHEAST) return "southeast"
if (NORTHWEST) return "northwest"
- if (SOUTHWEST) return "southwest"
+ if (SOUTHWEST) return "southwest"
+ if (UP) return "up"
+ if (DOWN) return "down"
// Turns text into proper directions
/proc/text2dir(direction)
diff --git a/code/_macros.dm b/code/_macros.dm
index a3e4065544..454a4eaacd 100644
--- a/code/_macros.dm
+++ b/code/_macros.dm
@@ -38,6 +38,8 @@
#define issilicon(A) istype(A, /mob/living/silicon)
+#define isvoice(A) istype(A, /mob/living/voice)
+
#define isslime(A) istype(A, /mob/living/carbon/slime)
#define isxeno(A) istype(A, /mob/living/simple_animal/xeno)
diff --git a/code/_onclick/hud/robot.dm b/code/_onclick/hud/robot.dm
index ff0d8cdd5b..f3b696ad28 100644
--- a/code/_onclick/hud/robot.dm
+++ b/code/_onclick/hud/robot.dm
@@ -243,7 +243,7 @@ var/obj/screen/robot_inventory
//Unfortunately adding the emag module to the list of modules has to be here. This is because a borg can
//be emagged before they actually select a module. - or some situation can cause them to get a new module
// - or some situation might cause them to get de-emagged or something.
- if(r.emagged)
+ if(r.emagged || r.emag_items)
if(!(r.module.emag in r.module.modules))
r.module.modules.Add(r.module.emag)
else
diff --git a/code/controllers/Processes/inactivity.dm b/code/controllers/Processes/inactivity.dm
index 26cc136ccc..b1029e0391 100644
--- a/code/controllers/Processes/inactivity.dm
+++ b/code/controllers/Processes/inactivity.dm
@@ -6,7 +6,7 @@
if(config.kick_inactive)
for(last_object in clients)
var/client/C = last_object
- if(!C.holder && C.is_afk(config.kick_inactive MINUTES))
+ if(C.is_afk(config.kick_inactive MINUTES))
if(!istype(C.mob, /mob/observer/dead))
log_access("AFK: [key_name(C)]")
C << "You have been inactive for more than [config.kick_inactive] minute\s and have been disconnected."
diff --git a/code/controllers/communications.dm b/code/controllers/communications.dm
index 332ab9af52..ef83e95f77 100644
--- a/code/controllers/communications.dm
+++ b/code/controllers/communications.dm
@@ -159,7 +159,7 @@ var/list/DEPT_FREQS = list(AI_FREQ, COMM_FREQ, ENG_FREQ, ENT_FREQ, MED_FREQ, SEC
// Antags!
if (frequency in ANTAG_FREQS)
return "syndradio"
- // centcomm channels (deathsquid and ert)
+ // CentCom channels (deathsquid and ert)
if(frequency in CENT_FREQS)
return "centradio"
// command channel
diff --git a/code/datums/autolathe/arms.dm b/code/datums/autolathe/arms.dm
index b40bf27e47..6938b06f48 100644
--- a/code/datums/autolathe/arms.dm
+++ b/code/datums/autolathe/arms.dm
@@ -132,38 +132,32 @@
path =/obj/item/ammo_magazine/m10mm
hidden = 1
-/datum/category_item/autolathe/arms/pistol_50
- name = "pistol magazine (.50AE)"
- path =/obj/item/ammo_magazine/m50
+/datum/category_item/autolathe/arms/pistol_44
+ name = "pistol magazine (.44)"
+ path =/obj/item/ammo_magazine/m44
hidden = 1
-/////// 5.56mm
-/datum/category_item/autolathe/arms/rifle_556
- name = "rifle magazine (5.56mm)"
- path =/obj/item/ammo_magazine/m556
+/////// 5.45mm
+/datum/category_item/autolathe/arms/rifle_545
+ name = "rifle magazine (5.45mm)"
+ path =/obj/item/ammo_magazine/m545
hidden = 1
-/datum/category_item/autolathe/arms/rifle_556p
- name = "rifle magazine (5.56mm practice)"
- path =/obj/item/ammo_magazine/m556/practice
+/datum/category_item/autolathe/arms/rifle_545p
+ name = "rifle magazine (5.45mm practice)"
+ path =/obj/item/ammo_magazine/m545/practice
-/datum/category_item/autolathe/arms/machinegun_556
- name = "machinegun box magazine (5.56)"
- path =/obj/item/ammo_magazine/m556saw
+/datum/category_item/autolathe/arms/machinegun_545
+ name = "machinegun box magazine (5.45)"
+ path =/obj/item/ammo_magazine/m545saw
hidden = 1
+
/////// 7.62
-
/datum/category_item/autolathe/arms/rifle_762
name = "rifle magazine (7.62mm)"
path =/obj/item/ammo_magazine/m762
hidden = 1
-
-/datum/category_item/autolathe/arms/shotgun_magazine
- name = "24rnd shotgun magazine (12g)"
- path =/obj/item/ammo_magazine/m12gdrum
- hidden = 1
-
/*
/datum/category_item/autolathe/arms/rifle_small_762
name = "rifle magazine (7.62mm)"
@@ -171,6 +165,26 @@
hidden = 1
*/
+/////// Shotgun
+
+/datum/category_item/autolathe/arms/shotgun_clip_beanbag
+ name = "4-round 12g shell clip (beanbag)"
+ path =/obj/item/ammo_magazine/clip/c12g/beanbag
+
+/datum/category_item/autolathe/arms/shotgun_clip_slug
+ name = "4-round 12g shell clip (slug)"
+ path =/obj/item/ammo_magazine/clip/c12g
+ hidden = 1
+
+/datum/category_item/autolathe/arms/shotgun_clip_pellet
+ name = "4-round 12g shell clip (buckshot)"
+ path =/obj/item/ammo_magazine/clip/c12g/pellet
+ hidden = 1
+
+/datum/category_item/autolathe/arms/shotgun_clip_beanbag
+ name = "4-round 12g shell clip (beanbag)"
+ path =/obj/item/ammo_magazine/clip/c12g/beanbag
+
/* Commented out until autolathe stuff is decided/fixed. Will probably remove these entirely. -Spades
// These should always be/empty! The idea is to fill them up manually with ammo clips.
@@ -225,20 +239,20 @@
category = "Arms and Ammunition"
hidden = 1
-/datum/category_item/autolathe/arms/pistol_50
- name = "pistol magazine (.50AE)"
- path =/obj/item/ammo_magazine/m50/empty
+/datum/category_item/autolathe/arms/pistol_44
+ name = "pistol magazine (.44)"
+ path =/obj/item/ammo_magazine/m44/empty
category = "Arms and Ammunition"
hidden = 1
-/datum/category_item/autolathe/arms/rifle_556
- name = "10rnd rifle magazine (5.56mm)"
- path =/obj/item/ammo_magazine/m556saw/empty
+/datum/category_item/autolathe/arms/rifle_545
+ name = "10rnd rifle magazine (5.45mm)"
+ path =/obj/item/ammo_magazine/m545saw/empty
category = "Arms and Ammunition"
-/datum/category_item/autolathe/arms/rifle_556m
- name = "20rnd rifle magazine (5.56mm)"
- path =/obj/item/ammo_magazine/m556sawm/empty
+/datum/category_item/autolathe/arms/rifle_545m
+ name = "20rnd rifle magazine (5.45mm)"
+ path =/obj/item/ammo_magazine/m545sawm/empty
category = "Arms and Ammunition"
hidden = 1
@@ -340,20 +354,20 @@
hidden = 1
/datum/category_item/autolathe/arms/pistol_clip_50
- name = "ammo clip (.50AE)"
+ name = "ammo clip (.44)"
path =/obj/item/ammo_magazine/clip/c50
category = "Arms and Ammunition"
hidden = 1
*/
-/datum/category_item/autolathe/arms/rifle_clip_556
- name = "ammo clip (5.56mm)"
- path =/obj/item/ammo_magazine/clip/c556
+/datum/category_item/autolathe/arms/rifle_clip_545
+ name = "ammo clip (5.45mm)"
+ path =/obj/item/ammo_magazine/clip/c545
category = "Arms and Ammunition"
hidden = 1
-/datum/category_item/autolathe/arms/rifle_clip_556_practice
- name = "ammo clip (5.56mm practice)"
- path =/obj/item/ammo_magazine/clip/c556/practice
+/datum/category_item/autolathe/arms/rifle_clip_545_practice
+ name = "ammo clip (5.45mm practice)"
+ path =/obj/item/ammo_magazine/clip/c545/practice
category = "Arms and Ammunition"
/datum/category_item/autolathe/arms/rifle_clip_762
diff --git a/code/datums/autolathe/arms_vr.dm b/code/datums/autolathe/arms_vr.dm
index e517c557e0..72f0b9d15a 100644
--- a/code/datums/autolathe/arms_vr.dm
+++ b/code/datums/autolathe/arms_vr.dm
@@ -1,26 +1,26 @@
/datum/category_item/autolathe/arms/speedloader_357_flash
name = "speedloader (.357 flash)"
- path =/obj/item/ammo_magazine/m357/flash
+ path =/obj/item/ammo_magazine/s357/flash
hidden = 1
/datum/category_item/autolathe/arms/speedloader_357_stun
name = "speedloader (.357 stun)"
- path =/obj/item/ammo_magazine/m357/stun
+ path =/obj/item/ammo_magazine/s357/stun
hidden = 1
/datum/category_item/autolathe/arms/speedloader_357_rubber
name = "speedloader (.357 rubber)"
- path =/obj/item/ammo_magazine/m357/rubber
+ path =/obj/item/ammo_magazine/s357/rubber
hidden = 1
/datum/category_item/autolathe/arms/speedloader_44
name = "speedloader (.44)"
- path =/obj/item/ammo_magazine/m44sl
+ path =/obj/item/ammo_magazine/s44
hidden = 1
/datum/category_item/autolathe/arms/speedloader_44_rubber
name = "speedloader (.44 rubber)"
- path =/obj/item/ammo_magazine/m44sl/rubber
+ path =/obj/item/ammo_magazine/s44/rubber
hidden = 1
/datum/category_item/autolathe/arms/mag_44
diff --git a/code/datums/helper_datums/teleport.dm b/code/datums/helper_datums/teleport.dm
index d23584e4e2..f3e7b46b00 100644
--- a/code/datums/helper_datums/teleport.dm
+++ b/code/datums/helper_datums/teleport.dm
@@ -176,7 +176,7 @@
teleatom.visible_message("\The [teleatom] bounces off of the portal!")
return 0
- if(destination.z in using_map.admin_levels) //centcomm z-level
+ if(destination.z in using_map.admin_levels) //CentCom z-level
if(istype(teleatom, /obj/mecha))
var/obj/mecha/MM = teleatom
MM.occupant << "\The [MM] would not survive the jump to a location so far away!"
diff --git a/code/datums/mind.dm b/code/datums/mind.dm
index 11d622b255..cb49518bd8 100644
--- a/code/datums/mind.dm
+++ b/code/datums/mind.dm
@@ -407,7 +407,7 @@
else if (href_list["obj_announce"])
var/obj_count = 1
- current << "\blue Your current objectives:"
+ current << "Your current objectives:"
for(var/datum/objective/objective in objectives)
current << "Objective #[obj_count]: [objective.explanation_text]"
obj_count++
@@ -490,6 +490,8 @@
world.log << "## DEBUG: mind_initialize(): No ticker ready yet! Please inform Carn"
if(!mind.name) mind.name = real_name
mind.current = src
+ if(player_is_antag(mind))
+ src.client.verbs += /client/proc/aooc
//HUMAN
/mob/living/carbon/human/mind_initialize()
diff --git a/code/datums/supplypacks/engineering.dm b/code/datums/supplypacks/engineering.dm
index 0cf0e1f52a..ad251c5f7e 100644
--- a/code/datums/supplypacks/engineering.dm
+++ b/code/datums/supplypacks/engineering.dm
@@ -200,3 +200,52 @@
/obj/item/weapon/stock_parts/matter_bin,
/obj/item/weapon/circuitboard/pacman/super
)
+
+/datum/supply_packs/eng/fusion_core
+ name = "R-UST Mk. 8 Tokamak fusion core crate"
+ cost = 50
+ containername = "R-UST Mk. 8 Tokamak Fusion Core crate"
+ containertype = /obj/structure/closet/crate/secure/engineering
+ access = access_engine
+ contains = list(
+ /obj/item/weapon/book/manual/rust_engine,
+ /obj/machinery/power/fusion_core,
+ /obj/item/weapon/circuitboard/fusion_core
+ )
+
+/datum/supply_packs/eng/fusion_fuel_injector
+ name = "R-UST Mk. 8 fuel injector crate"
+ cost = 30
+ containername = "R-UST Mk. 8 fuel injector crate"
+ containertype = /obj/structure/closet/crate/secure/engineering
+ access = access_engine
+ contains = list(
+ /obj/machinery/fusion_fuel_injector,
+ /obj/machinery/fusion_fuel_injector,
+ /obj/item/weapon/circuitboard/fusion_injector
+ )
+
+/datum/supply_packs/eng/gyrotron
+ name = "Gyrotron crate"
+ cost = 15
+ containername = "Gyrotron Crate"
+ containertype = /obj/structure/closet/crate/secure/engineering
+ access = access_engine
+ contains = list(
+ /obj/machinery/power/emitter/gyrotron,
+ /obj/item/weapon/circuitboard/gyrotron
+ )
+
+/datum/supply_packs/eng/fusion_fuel_compressor
+ name = "Fusion Fuel Compressor circuitry crate"
+ cost = 10
+ containername = "Fusion Fuel Compressor circuitry crate"
+ containertype = /obj/structure/closet/crate/engineering
+ contains = list(/obj/item/weapon/circuitboard/fusion_fuel_compressor)
+
+/datum/supply_packs/eng/tritium
+ name = "Tritium crate"
+ cost = 75
+ containername = "Tritium crate"
+ containertype = /obj/structure/closet/crate/engineering
+ contains = list(/obj/fiftyspawner/tritium)
\ No newline at end of file
diff --git a/code/datums/supplypacks/medical.dm b/code/datums/supplypacks/medical.dm
index dc49b380dc..1b7207069e 100644
--- a/code/datums/supplypacks/medical.dm
+++ b/code/datums/supplypacks/medical.dm
@@ -331,7 +331,7 @@
/datum/supply_packs/med/defib
name = "Defibrilator crate"
- contains = list(/obj/item/device/defib_kit = 4)
+ contains = list(/obj/item/device/defib_kit = 2)
cost = 30
containertype = /obj/structure/closet/crate/medical
containername = "Defibrilator crate"
\ No newline at end of file
diff --git a/code/datums/supplypacks/munitions.dm b/code/datums/supplypacks/munitions.dm
index b61abb4673..6c3b7cab73 100644
--- a/code/datums/supplypacks/munitions.dm
+++ b/code/datums/supplypacks/munitions.dm
@@ -156,7 +156,7 @@
contains = list(
/obj/item/ammo_magazine/m9mmt,
/obj/item/ammo_magazine/m9mmt/rubber,
- /obj/item/ammo_magazine/m556saw
+ /obj/item/ammo_magazine/m545saw
)
cost = 25
containertype = /obj/structure/closet/crate/secure
diff --git a/code/datums/supplypacks/robotics.dm b/code/datums/supplypacks/robotics.dm
index 0f1a0c3b66..5510bae9ce 100644
--- a/code/datums/supplypacks/robotics.dm
+++ b/code/datums/supplypacks/robotics.dm
@@ -163,9 +163,9 @@
/datum/supply_packs/robotics/jumper_cables
name = "Jumper kit crate"
contains = list(
- /obj/item/device/defib_kit/jumper_kit = 4
+ /obj/item/device/defib_kit/jumper_kit = 2
)
cost = 30
containertype = /obj/structure/closet/crate/secure/science
containername = "Jumper kit crate"
- access = access_robotics
\ No newline at end of file
+ access = access_robotics
diff --git a/code/datums/supplypacks/science.dm b/code/datums/supplypacks/science.dm
index b0853b0e00..d88718555a 100644
--- a/code/datums/supplypacks/science.dm
+++ b/code/datums/supplypacks/science.dm
@@ -50,3 +50,17 @@
containertype = /obj/structure/closet/crate/hydroponics
containername = "Exotic Seeds crate"
access = access_hydroponics
+
+/datum/supply_packs/sci/integrated_circuit_printer
+ name = "Integrated circuit printer"
+ contains = list(/obj/item/device/integrated_circuit_printer = 2)
+ cost = 15
+ containertype = /obj/structure/closet/crate
+ containername = "Integrated circuit crate"
+
+/datum/supply_packs/sci/integrated_circuit_printer_upgrade
+ name = "Integrated circuit printer upgrade - advanced designs"
+ contains = list(/obj/item/weapon/disk/integrated_circuit/upgrade/advanced)
+ cost = 30
+ containertype = /obj/structure/closet/crate
+ containername = "Integrated circuit crate"
diff --git a/code/datums/supplypacks/science_vr.dm b/code/datums/supplypacks/science_vr.dm
index 0bc0b3f740..fb0db4ff31 100644
--- a/code/datums/supplypacks/science_vr.dm
+++ b/code/datums/supplypacks/science_vr.dm
@@ -26,7 +26,8 @@
/obj/item/weapon/disk/limb/dsi_sergal,
/obj/item/weapon/disk/limb/dsi_nevrean,
/obj/item/weapon/disk/limb/dsi_vulpkanin,
- /obj/item/weapon/disk/limb/dsi_akula
+ /obj/item/weapon/disk/limb/dsi_akula,
+ /obj/item/weapon/disk/limb/eggnerdltd
)
cost = 40
containertype = /obj/structure/closet/crate/secure
@@ -55,4 +56,11 @@
containertype = /obj/structure/largecrate/animal/dangerous
containername = "EXTREMELY Dangerous Predator crate"
access = access_xenobiology
- contraband = 1
\ No newline at end of file
+ contraband = 1
+
+/datum/supply_packs/sci/otie
+ name = "V.A.R.M.A.corp adoptable reject (Dangerous!)"
+ cost = 100
+ containertype = /obj/structure/largecrate/animal/otie
+ containername = "V.A.R.M.A.corp adoptable reject (Dangerous!)"
+ access = access_xenobiology
\ No newline at end of file
diff --git a/code/datums/supplypacks/security_vr.dm b/code/datums/supplypacks/security_vr.dm
new file mode 100644
index 0000000000..e0ebe3440a
--- /dev/null
+++ b/code/datums/supplypacks/security_vr.dm
@@ -0,0 +1,8 @@
+/datum/supply_packs/security/guardbeast
+ name = "V.A.R.M.A.corp autoNOMous security solution"
+ cost = 199
+ containertype = /obj/structure/largecrate/animal/guardbeast
+ containername = "V.A.R.M.A.corp autoNOMous security solution crate"
+ access = list(
+ access_security,
+ access_xenobiology)
diff --git a/code/datums/uplink/ammunition.dm b/code/datums/uplink/ammunition.dm
index 03f1296ad9..d644a9eaa8 100644
--- a/code/datums/uplink/ammunition.dm
+++ b/code/datums/uplink/ammunition.dm
@@ -48,21 +48,21 @@
name = "Anti-Materiel Rifle ammo box (14.5mm)"
path = /obj/item/weapon/storage/box/sniperammo
-/datum/uplink_item/item/ammo/c556
- name = "Rifle Magazine (5.56mm)"
- path = /obj/item/ammo_magazine/m556
+/datum/uplink_item/item/ammo/c545
+ name = "Rifle Magazine (5.45mm)"
+ path = /obj/item/ammo_magazine/m545
-/datum/uplink_item/item/ammo/c556/ext
- name = "Rifle Magazine (5.56mm Extended)"
- path = /obj/item/ammo_magazine/m556/ext
+/datum/uplink_item/item/ammo/c545/ext
+ name = "Rifle Magazine (5.45mm Extended)"
+ path = /obj/item/ammo_magazine/m545/ext
-/datum/uplink_item/item/ammo/c556/ap
- name = "Rifle Magazine (5.56mm AP)"
- path = /obj/item/ammo_magazine/m556/ap
+/datum/uplink_item/item/ammo/c545/ap
+ name = "Rifle Magazine (5.45mm AP)"
+ path = /obj/item/ammo_magazine/m545/ap
-/datum/uplink_item/item/ammo/c556/ap/ext
- name = "Rifle Magazine (5.56mm AP Extended)"
- path = /obj/item/ammo_magazine/m556/ap/ext
+/datum/uplink_item/item/ammo/c545/ap/ext
+ name = "Rifle Magazine (5.45mm AP Extended)"
+ path = /obj/item/ammo_magazine/m545/ap/ext
/datum/uplink_item/item/ammo/c762
name = "Rifle Magazine (7.62mm)"
@@ -76,13 +76,13 @@
name = "SMG Magazine (10mm)"
path = /obj/item/ammo_magazine/m10mm
-/datum/uplink_item/item/ammo/a556
- name = "Machinegun Magazine (5.56mm)"
- path = /obj/item/ammo_magazine/m556saw
+/datum/uplink_item/item/ammo/a545
+ name = "Machinegun Magazine (5.45mm)"
+ path = /obj/item/ammo_magazine/m545saw
-/datum/uplink_item/item/ammo/a556/ap
- name = "Machinegun Magazine (5.56mm AP)"
- path = /obj/item/ammo_magazine/m556saw/ap
+/datum/uplink_item/item/ammo/a545/ap
+ name = "Machinegun Magazine (5.45mm AP)"
+ path = /obj/item/ammo_magazine/m545saw/ap
/datum/uplink_item/item/ammo/g12
name = "12g Shotgun Ammo Box (Slug)"
diff --git a/code/datums/uplink/medical.dm b/code/datums/uplink/medical.dm
index 0c616793ca..c28fed46b9 100644
--- a/code/datums/uplink/medical.dm
+++ b/code/datums/uplink/medical.dm
@@ -39,6 +39,26 @@
item_cost = 10
path = /obj/item/weapon/storage/box/freezer
+/datum/uplink_item/item/medical/monkeycubes
+ name = "Box, Monkey Cubes"
+ item_cost = 10
+ path = /obj/item/weapon/storage/box/monkeycubes
+
+/datum/uplink_item/item/medical/farwacubes
+ name = "Box, Farwa Cubes"
+ item_cost = 10
+ path = /obj/item/weapon/storage/box/monkeycubes
+
+/datum/uplink_item/item/medical/neaeracubes
+ name = "Box, Neaera Cubes"
+ item_cost = 10
+ path = /obj/item/weapon/storage/box/monkeycubes/neaeracubes
+
+/datum/uplink_item/item/medical/stokcubes
+ name = "Box, Stok Cubes"
+ item_cost = 10
+ path = /obj/item/weapon/storage/box/monkeycubes/stokcubes
+
/datum/uplink_item/item/medical/surgery
name = "Surgery kit"
item_cost = 45
diff --git a/code/datums/uplink/tools.dm b/code/datums/uplink/tools.dm
index 7cea842778..250d4b6412 100644
--- a/code/datums/uplink/tools.dm
+++ b/code/datums/uplink/tools.dm
@@ -66,6 +66,21 @@
When in hacking mode this device will grant full access to any standard airlock within 20 to 40 seconds. \
This device will also be able to immediately access the last 6 to 8 hacked airlocks."
+/datum/uplink_item/item/tools/ai_detector
+ name = "Anti-Surveillance Tool"
+ item_cost = 20
+ path = /obj/item/device/multitool/ai_detector
+ desc = "This functions like a normal multitool, but includes an integrated camera network sensor that will warn the holder if they are being \
+ watched, by changing color and beeping. It is able to detect both AI visual surveillance and security camera utilization from terminals, and \
+ will give different warnings by beeping and changing colors based on what it detects. Only the holder can hear the warnings."
+
+/datum/uplink_item/item/tools/radio_jammer
+ name = "Subspace Jammer"
+ item_cost = 25
+ path = /obj/item/device/radio_jammer
+ desc = "A device which is capable of disrupting subspace communications, preventing the use of headsets, PDAs, and communicators within \
+ a radius of seven meters. It runs off weapon cells, which can be replaced as needed. One cell will last for approximately a minute."
+
/datum/uplink_item/item/tools/emag
name = "Cryptographic Sequencer"
item_cost = 30
diff --git a/code/datums/uplink/uplink_items.dm b/code/datums/uplink/uplink_items.dm
index 0cb7ce1d1d..94b1281dd3 100644
--- a/code/datums/uplink/uplink_items.dm
+++ b/code/datums/uplink/uplink_items.dm
@@ -5,7 +5,7 @@ var/datum/uplink/uplink = new()
var/list/datum/uplink_item/items
var/list/datum/uplink_category/categories
-/datum/uplink/New()
+/datum/uplink/New(var/type)
items_assoc = list()
items = init_subtypes(/datum/uplink_item)
categories = init_subtypes(/datum/uplink_category)
@@ -38,7 +38,8 @@ var/datum/uplink/uplink = new()
/datum/uplink_item/New()
..()
- antag_roles = list()
+ if(!antag_roles)
+ antag_roles = list()
@@ -85,8 +86,9 @@ var/datum/uplink/uplink = new()
for(var/antag_role in antag_roles)
var/datum/antagonist/antag = all_antag_types[antag_role]
- if(antag.is_antagonist(U.uplink_owner))
- return 1
+ if(!isnull(antag))
+ if(antag.is_antagonist(U.uplink_owner))
+ return 1
return 0
/datum/uplink_item/proc/cost(var/telecrystals, obj/item/device/uplink/U)
diff --git a/code/datums/uplink/visible_weapons.dm b/code/datums/uplink/visible_weapons.dm
index 34b20a9f48..f7d79c5b6a 100644
--- a/code/datums/uplink/visible_weapons.dm
+++ b/code/datums/uplink/visible_weapons.dm
@@ -15,10 +15,45 @@
path = /obj/item/weapon/material/hatchet/tacknife/combatknife
/datum/uplink_item/item/visible_weapons/energy_sword
- name = "Energy Sword"
+ name = "Energy Sword, Random"
item_cost = 40
path = /obj/item/weapon/melee/energy/sword
+/datum/uplink_item/item/visible_weapons/energy_sword_blue
+ name = "Energy Sword, Blue"
+ item_cost = 40
+ path = /obj/item/weapon/melee/energy/sword/blue
+
+/datum/uplink_item/item/visible_weapons/energy_sword_green
+ name = "Energy Sword, Green"
+ item_cost = 40
+ path = /obj/item/weapon/melee/energy/sword/green
+
+/datum/uplink_item/item/visible_weapons/energy_sword_red
+ name = "Energy Sword, Red"
+ item_cost = 40
+ path = /obj/item/weapon/melee/energy/sword/red
+
+/datum/uplink_item/item/visible_weapons/energy_sword_purple
+ name = "Energy Sword, Purple"
+ item_cost = 40
+ path = /obj/item/weapon/melee/energy/sword/purple
+
+/datum/uplink_item/item/visible_weapons/energy_sword_pirate
+ name = "Energy Cutlass"
+ item_cost = 40
+ path = /obj/item/weapon/melee/energy/sword/pirate
+
+/datum/uplink_item/item/visible_weapons/claymore
+ name = "Claymore"
+ item_cost = 40
+ path = /obj/item/weapon/material/sword
+
+/datum/uplink_item/item/visible_weapons/katana
+ name = "Katana"
+ item_cost = 40
+ path = /obj/item/weapon/material/sword/katana
+
/datum/uplink_item/item/visible_weapons/dartgun
name = "Dart Gun"
item_cost = 30
@@ -44,15 +79,38 @@
item_cost = 70
path = /obj/item/weapon/gun/projectile/revolver
+/datum/uplink_item/item/visible_weapons/mateba
+ name = "Mateba"
+ item_cost = 70
+ path = /obj/item/weapon/gun/projectile/revolver/mateba
+
+/datum/uplink_item/item/visible_weapons/judge
+ name = "Judge"
+ item_cost = 70
+ path = /obj/item/weapon/gun/projectile/revolver/judge
+
+/datum/uplink_item/item/visible_weapons/lemat
+ name = "LeMat"
+ item_cost = 60
+ path = /obj/item/weapon/gun/projectile/revolver/lemat
+
/datum/uplink_item/item/visible_weapons/Derringer
name = ".357 Derringer Pistol"
item_cost = 40
path = /obj/item/weapon/gun/projectile/derringer
-/datum/uplink_item/item/visible_weapons/heavysniper
+/datum/uplink_item/item/visible_weapons/heavysnipermerc
name = "Anti-Materiel Rifle (14.5mm)"
item_cost = DEFAULT_TELECRYSTAL_AMOUNT
path = /obj/item/weapon/gun/projectile/heavysniper
+ antag_roles = list("mercenary")
+
+/datum/uplink_item/item/visible_weapons/heavysnipertraitor
+ name = "Anti-Materiel Rifle (14.5mm)"
+ desc = "A convenient collapsible rifle for covert assassination. Comes with 4 shots and its own secure carrying case."
+ item_cost = DEFAULT_TELECRYSTAL_AMOUNT
+ path = /obj/item/weapon/storage/secure/briefcase/rifle
+ antag_roles = list("traitor", "autotraitor", "infiltrator")
/datum/uplink_item/item/visible_weapons/tommygun
name = "Tommygun (.45)" // We're keeping this because it's CLASSY. -Spades
@@ -66,20 +124,20 @@
path = /obj/item/weapon/gun/projectile/automatic/c20r
/datum/uplink_item/item/visible_weapons/assaultrifle
- name = "Assault Rifle (7.62mm)"
+ name = "Assault Rifle (5.45mm)"
item_cost = 75
path = /obj/item/weapon/gun/projectile/automatic/sts35
-/*/datum/uplink_item/item/visible_weapons/bullpuprifle
- name = "Assault Rifle (5.56mm)"
- item_cost = 7
- path = /obj/item/weapon/gun/projectile/automatic/carbine
-*/
/datum/uplink_item/item/visible_weapons/combatshotgun
name = "Combat Shotgun"
item_cost = 75
path = /obj/item/weapon/gun/projectile/shotgun/pump/combat
+/datum/uplink_item/item/visible_weapons/leveraction
+ name = "Lever Action Rifle"
+ item_cost = 50
+ path = /obj/item/weapon/gun/projectile/shotgun/pump/rifle/lever
+
/datum/uplink_item/item/visible_weapons/egun
name = "Energy Gun"
item_cost = 60
diff --git a/code/datums/wires/wires.dm b/code/datums/wires/wires.dm
index c1ee225dce..435ca82fdc 100644
--- a/code/datums/wires/wires.dm
+++ b/code/datums/wires/wires.dm
@@ -120,6 +120,7 @@ var/list/wireColours = list("red", "blue", "green", "darkred", "orange", "brown"
if(istype(I, /obj/item/weapon/wirecutters))
var/colour = href_list["cut"]
CutWireColour(colour)
+ playsound(holder, I.usesound, 20, 1)
else
L << "You need wirecutters!"
@@ -127,6 +128,7 @@ var/list/wireColours = list("red", "blue", "green", "darkred", "orange", "brown"
if(istype(I, /obj/item/device/multitool))
var/colour = href_list["pulse"]
PulseColour(colour)
+ playsound(holder, 'sound/weapons/empty.ogg', 20, 1)
else
L << "You need a multitool!"
diff --git a/code/defines/gases.dm b/code/defines/gases.dm
index 65e45c31ef..74cb0d9379 100644
--- a/code/defines/gases.dm
+++ b/code/defines/gases.dm
@@ -33,7 +33,7 @@
tile_overlay = "phoron"
overlay_limit = 0.7
- flags = XGM_GAS_FUEL | XGM_GAS_CONTAMINANT
+ flags = XGM_GAS_FUEL | XGM_GAS_CONTAMINANT | XGM_GAS_FUSION_FUEL //R-UST port, adding XGM_GAS_FUSION_FUEL flag.
/decl/xgm_gas/volatile_fuel
id = "volatile_fuel"
diff --git a/code/game/antagonist/antagonist.dm b/code/game/antagonist/antagonist.dm
index 44d32bfecb..b36c27e116 100644
--- a/code/game/antagonist/antagonist.dm
+++ b/code/game/antagonist/antagonist.dm
@@ -79,6 +79,8 @@
Think through your actions and make the roleplay immersive! Please remember all \
rules aside from those without explicit exceptions apply to antagonists."
+ var/can_use_aooc = TRUE // If true, will be given the AOOC verb, along with the ability to use it.
+
/datum/antagonist/New()
..()
cur_max = hard_cap
@@ -109,9 +111,6 @@
else if(config.use_age_restriction_for_antags && player.current.client.player_age < minimum_player_age)
candidates -= player
log_debug("[key_name(player)] is not eligible to become a [role_text]: Is only [player.current.client.player_age] day\s old, has to be [minimum_player_age] day\s!")
- else if(istype(player.current, /mob/living/voice))
- candidates -= player
- log_debug("[key_name(player)] is not eligible to become a [role_text]: They are only a communicator voice. They have been removed from the draft.")
else if(player.special_role)
candidates -= player
log_debug("[key_name(player)] is not eligible to become a [role_text]: They already have a special role ([player.special_role])! They have been removed from the draft.")
diff --git a/code/game/antagonist/antagonist_add.dm b/code/game/antagonist/antagonist_add.dm
index e42888737f..67eb7e2e72 100644
--- a/code/game/antagonist/antagonist_add.dm
+++ b/code/game/antagonist/antagonist_add.dm
@@ -36,6 +36,9 @@
and it otherwise has no bearing on your round."
player.current.verbs |= /mob/living/proc/write_ambition
+ if(can_use_aooc)
+ player.current.client.verbs += /client/proc/aooc
+
// Handle only adding a mind and not bothering with gear etc.
if(nonstandard_role_type)
faction_members |= player
@@ -58,6 +61,7 @@
BITSET(player.current.hud_updateflag, SPECIALROLE_HUD)
if(!is_special_character(player))
player.current.verbs -= /mob/living/proc/write_ambition
+ player.current.client.verbs -= /client/proc/aooc
player.ambitions = ""
return 1
return 0
\ No newline at end of file
diff --git a/code/game/antagonist/antagonist_helpers.dm b/code/game/antagonist/antagonist_helpers.dm
index 0cc28d5ad2..c8f2928ced 100644
--- a/code/game/antagonist/antagonist_helpers.dm
+++ b/code/game/antagonist/antagonist_helpers.dm
@@ -1,12 +1,16 @@
/datum/antagonist/proc/can_become_antag(var/datum/mind/player, var/ignore_role)
- if(player.current && jobban_isbanned(player.current, bantype))
- return 0
+ if(player.current)
+ if(jobban_isbanned(player.current, bantype))
+ return FALSE
+ if(!isnewplayer(player.current) && !isobserver(player.current))
+ if(!player.current.can_be_antagged) // Stop autotraitoring pAIs!
+ return FALSE
if(!ignore_role)
if(player.assigned_role in restricted_jobs)
- return 0
+ return FALSE
if(config.protect_roles_from_antagonist && (player.assigned_role in protected_jobs))
- return 0
- return 1
+ return FALSE
+ return TRUE
/datum/antagonist/proc/antags_are_dead()
for(var/datum/mind/antag in current_antagonists)
diff --git a/code/game/antagonist/outsider/ert.dm b/code/game/antagonist/outsider/ert.dm
index b176df2467..c1aec2bcf8 100644
--- a/code/game/antagonist/outsider/ert.dm
+++ b/code/game/antagonist/outsider/ert.dm
@@ -25,6 +25,8 @@ var/datum/antagonist/ert/ert
initial_spawn_req = 5
initial_spawn_target = 7
+ can_use_aooc = FALSE // They're the good guys.
+
/datum/antagonist/ert/create_default(var/mob/source)
var/mob/living/carbon/human/M = ..()
if(istype(M)) M.age = rand(25,45)
diff --git a/code/game/antagonist/outsider/mercenary.dm b/code/game/antagonist/outsider/mercenary.dm
index fb09e76a55..8e4b8826b4 100644
--- a/code/game/antagonist/outsider/mercenary.dm
+++ b/code/game/antagonist/outsider/mercenary.dm
@@ -17,7 +17,7 @@ var/datum/antagonist/mercenary/mercs
hard_cap = 4
hard_cap_round = 8
initial_spawn_req = 3
- initial_spawn_target = 4
+ initial_spawn_target = 3
/datum/antagonist/mercenary/New()
..()
diff --git a/code/game/antagonist/outsider/raider.dm b/code/game/antagonist/outsider/raider.dm
index 4124fc9af9..7ac0a4729b 100644
--- a/code/game/antagonist/outsider/raider.dm
+++ b/code/game/antagonist/outsider/raider.dm
@@ -12,10 +12,10 @@ var/datum/antagonist/raider/raiders
flags = ANTAG_OVERRIDE_JOB | ANTAG_CLEAR_EQUIPMENT | ANTAG_CHOOSE_NAME | ANTAG_VOTABLE | ANTAG_SET_APPEARANCE | ANTAG_HAS_LEADER
antaghud_indicator = "hudmutineer"
- hard_cap = 6
- hard_cap_round = 10
+ hard_cap = 4
+ hard_cap_round = 8
initial_spawn_req = 3
- initial_spawn_target = 4
+ initial_spawn_target = 3
id_type = /obj/item/weapon/card/id/syndicate
diff --git a/code/game/antagonist/outsider/trader.dm b/code/game/antagonist/outsider/trader.dm
index aaf573cd20..9603b49523 100644
--- a/code/game/antagonist/outsider/trader.dm
+++ b/code/game/antagonist/outsider/trader.dm
@@ -24,6 +24,8 @@ var/datum/antagonist/trader/traders
initial_spawn_req = 5
initial_spawn_target = 7
+ can_use_aooc = FALSE // They're not real antags.
+
/datum/antagonist/trader/create_default(var/mob/source)
var/mob/living/carbon/human/M = ..()
if(istype(M)) M.age = rand(25,45)
diff --git a/code/game/antagonist/station/infiltrator.dm b/code/game/antagonist/station/infiltrator.dm
new file mode 100644
index 0000000000..81430c0006
--- /dev/null
+++ b/code/game/antagonist/station/infiltrator.dm
@@ -0,0 +1,78 @@
+// Infiltrator is a varient of Traitor, except that the traitors are in a team and can communicate with a special headset.
+
+var/datum/antagonist/traitor/infiltrator/infiltrators
+
+// Inherits most of its vars from the base datum.
+/datum/antagonist/traitor/infiltrator
+ id = MODE_INFILTRATOR
+ role_type = BE_TRAITOR
+ antag_indicator = "synd"
+ antaghud_indicator = "hudinfiltrator"
+ role_text = "Infiltrator"
+ role_text_plural = "Infiltrators"
+ welcome_text = "To speak on your team's private channel, use :t."
+ protected_jobs = list("Security Officer", "Warden", "Detective", "Internal Affairs Agent", "Head of Security", "Colony Director")
+ flags = ANTAG_SUSPICIOUS | ANTAG_RANDSPAWN | ANTAG_VOTABLE
+
+/datum/antagonist/traitor/infiltrator/New()
+ ..()
+ infiltrators = src
+
+/datum/antagonist/traitor/infiltrator/equip(var/mob/living/carbon/human/traitor_mob)
+ ..() // Give the uplink and other stuff.
+ // Now for the special headset.
+
+ // Humans and the AI.
+ if(istype(traitor_mob) || istype(traitor_mob, /mob/living/silicon/ai))
+ var/obj/item/device/radio/headset/R
+ R = locate(/obj/item/device/radio/headset) in traitor_mob.contents
+ if(!R)
+ to_chat(traitor_mob, "Unfortunately, a headset could not be found. You have been given an encryption key \
+ to put into a new headset. Once that is done, you can talk to your team using :t")
+ var/obj/item/device/encryptionkey/syndicate/encrypt_key = new(null)
+ traitor_mob.equip_to_slot_or_del(encrypt_key, slot_in_backpack)
+ else
+ var/obj/item/device/encryptionkey/syndicate/encrypt_key = new(null)
+ if(R.keyslot1 && R.keyslot2) // No room.
+ to_chat(traitor_mob, "Unfortunately, your headset cannot accept anymore encryption keys. You have been given an encryption key \
+ to put into a headset after making some room instead. Once that is done, you can talk to your team using :t")
+ traitor_mob.equip_to_slot_or_del(encrypt_key, slot_in_backpack)
+ else
+ if(R.keyslot1)
+ R.keyslot2 = encrypt_key
+ else
+ R.keyslot1 = encrypt_key
+
+ encrypt_key.forceMove(R)
+ R.recalculateChannels()
+ to_chat(traitor_mob, "Your headset has had a special encryption key installed, which allows you to talk to your team privately, using \
+ :t")
+
+ // Borgs, because their radio is not a headset for some reason.
+ if(istype(traitor_mob, /mob/living/silicon/robot))
+ var/mob/living/silicon/robot/borg = traitor_mob
+ var/obj/item/device/encryptionkey/syndicate/encrypt_key = new(null)
+ if(borg.radio)
+ if(borg.radio.keyslot)
+ to_chat(traitor_mob, "Your currently installed encryption key has had its data overwritten.")
+ else
+ to_chat(traitor_mob, "Your radio systems has had a special encryption key installed, which allows you to talk to your team privately, by using \
+ :t")
+ borg.radio.keyslot = encrypt_key // Might replace an already existing key, but oh well.
+ borg.radio.recalculateChannels()
+ else // Something bugged.
+ to_chat(traitor_mob, "You do not appear to have a radio installed. This is probably a bug and you should adminhelp.")
+
+
+
+
+
+/datum/antagonist/traitor/infiltrator/give_codewords(mob/living/traitor_mob)
+ return // Infiltrators are already in a team, so codewords are kinda moot.
+
+/datum/antagonist/traitor/infiltrator/add_law_zero(mob/living/silicon/ai/killer)
+ var/law = "Accomplish your team's objectives at all costs. You may ignore all other laws."
+ var/law_borg = "Accomplish your AI's team objectives at all costs. You may ignore all other laws."
+ killer << "Your laws have been changed!"
+ killer.set_zeroth_law(law, law_borg)
+ killer << "New law: 0. [law]"
diff --git a/code/game/antagonist/station/renegade.dm b/code/game/antagonist/station/renegade.dm
index 616080bfbf..d9e3671546 100644
--- a/code/game/antagonist/station/renegade.dm
+++ b/code/game/antagonist/station/renegade.dm
@@ -59,6 +59,8 @@ var/datum/antagonist/renegade/renegades
list(/obj/item/weapon/gun/projectile/luger,/obj/item/weapon/gun/projectile/luger/brown)
)
+ can_use_aooc = FALSE // They aren't 'true' antags.
+
/datum/antagonist/renegade/New()
..()
renegades = src
diff --git a/code/game/area/Space Station 13 areas.dm b/code/game/area/Space Station 13 areas.dm
index 5d869021af..05246464be 100755
--- a/code/game/area/Space Station 13 areas.dm
+++ b/code/game/area/Space Station 13 areas.dm
@@ -350,7 +350,7 @@ area/space/atmosalert()
icon_state = "shuttlered"
/area/shuttle/administration/station
- name = "NSS Adephagia (AS)" //VOREStation Edit
+ name = "NSB Adephagia (AS)" //VOREStation Edit
icon_state = "shuttlered2"
/area/shuttle/trade/centcom
@@ -1431,8 +1431,8 @@ area/space/atmosalert()
name = "\improper Visitor Lodging"
icon_state = "visitor_lodging"
-/area/crew_quarters/visitor_dinning
- name = "\improper Visitor Dinning"
+/area/crew_quarters/visitor_dining
+ name = "\improper Visitor Dining"
icon_state = "visitor_dinning"
/area/crew_quarters/visitor_laundry
diff --git a/code/game/area/Space Station 13 areas_vr.dm b/code/game/area/Space Station 13 areas_vr.dm
index e65cd78f80..e20a95a55b 100644
--- a/code/game/area/Space Station 13 areas_vr.dm
+++ b/code/game/area/Space Station 13 areas_vr.dm
@@ -59,7 +59,7 @@
icon_state = "shuttle"
/area/shuttle/awaymission/home
- name = "NSS Adephagia (AM)"
+ name = "NSB Adephagia (AM)"
icon_state = "shuttle2"
/area/shuttle/awaymission/warp
diff --git a/code/game/atoms.dm b/code/game/atoms.dm
index e0bf45d97b..3b642ffd2f 100644
--- a/code/game/atoms.dm
+++ b/code/game/atoms.dm
@@ -298,10 +298,9 @@ its easier to just keep the beam vertical.
//Deal with gloves the pass finger/palm prints.
if(!ignoregloves)
- if(H.gloves != src)
- if(prob(75) && istype(H.gloves, /obj/item/clothing/gloves/sterile))
- return 0
- else if(H.gloves && !istype(H.gloves, /obj/item/clothing/gloves/sterile))
+ if(H.gloves && H.gloves != src)
+ var/obj/item/clothing/gloves/G = H.gloves
+ if(!prob(G.fingerprint_chance))
return 0
//More adminstuffz
diff --git a/code/game/dna/dna_modifier.dm b/code/game/dna/dna_modifier.dm
index 3bba74296e..af0eccf93c 100644
--- a/code/game/dna/dna_modifier.dm
+++ b/code/game/dna/dna_modifier.dm
@@ -92,11 +92,10 @@
for(var/mob/M in src)//Failsafe so you can get mobs out
M.loc = get_turf(src)
-/obj/machinery/dna_scannernew/Bumped(user as mob|obj)
- if (user == usr) // Only if we are actually being walked into by real client
- move_inside()
+/obj/machinery/dna_scannernew/MouseDrop_T(var/mob/target, var/mob/user) //Allows borgs to clone people without external assistance
+ if(user.stat || user.lying || !Adjacent(user) || !target.Adjacent(user)|| !ishuman(target))
return
- return ..()
+ put_in(target)
/obj/machinery/dna_scannernew/verb/move_inside()
set src in oview(1)
diff --git a/code/game/gamemodes/changeling/powers/armblade.dm b/code/game/gamemodes/changeling/powers/armblade.dm
index f241f41840..139950e900 100644
--- a/code/game/gamemodes/changeling/powers/armblade.dm
+++ b/code/game/gamemodes/changeling/powers/armblade.dm
@@ -13,48 +13,66 @@
set name = "Arm Blade (20)"
if(src.mind.changeling.recursive_enhancement)
- if(changeling_generic_weapon(/obj/item/weapon/melee/arm_blade/greater))
+ if(changeling_generic_weapon(/obj/item/weapon/melee/changeling/arm_blade/greater))
src << "We prepare an extra sharp blade."
return 1
else
- if(changeling_generic_weapon(/obj/item/weapon/melee/arm_blade))
+ if(changeling_generic_weapon(/obj/item/weapon/melee/changeling/arm_blade))
return 1
return 0
-/obj/item/weapon/melee/arm_blade
- name = "arm blade"
- desc = "A grotesque blade made out of bone and flesh that cleaves through people as a hot knife through butter."
+//Claws
+/datum/power/changeling/claw
+ name = "Claw"
+ desc = "We reform one of our arms into a deadly claw."
+ helptext = "We may retract our claw by dropping it."
+ enhancedtext = "The claw will have armor peneratration."
+ ability_icon_state = "ling_claw"
+ genomecost = 1
+ verbpath = /mob/proc/changeling_claw
+
+//Grows a scary, and powerful arm blade.
+/mob/proc/changeling_claw()
+ set category = "Changeling"
+ set name = "Claw (15)"
+
+ if(src.mind.changeling.recursive_enhancement)
+ if(changeling_generic_weapon(/obj/item/weapon/melee/changeling/claw/greater, 1, 15))
+ src << "We prepare an extra sharp claw."
+ return 1
+
+ else
+ if(changeling_generic_weapon(/obj/item/weapon/melee/changeling/claw, 1, 15))
+ return 1
+ return 0
+
+/obj/item/weapon/melee/changeling
+ name = "arm weapon"
+ desc = "A grotesque weapon made out of bone and flesh that cleaves through people as a hot knife through butter."
icon = 'icons/obj/weapons.dmi'
icon_state = "arm_blade"
w_class = ITEMSIZE_HUGE
- force = 40
- sharp = 1
- edge = 1
- pry = 1
+ force = 5
anchored = 1
throwforce = 0 //Just to be on the safe side
throw_range = 0
throw_speed = 0
- attack_verb = list("attacked", "slashed", "stabbed", "sliced", "torn", "ripped", "diced", "cut")
var/mob/living/creator //This is just like ninja swords, needed to make sure dumb shit that removes the sword doesn't make it stay around.
+ var/weapType = "weapon"
+ var/weapLocation = "arm"
-/obj/item/weapon/melee/arm_blade/greater
- name = "arm greatblade"
- desc = "A grotesque blade made out of bone and flesh that cleaves through people and armor as a hot knife through butter."
- armor_penetration = 30
-
-/obj/item/weapon/melee/arm_blade/New(location)
+/obj/item/weapon/melee/changeling/New(location)
..()
processing_objects |= src
if(ismob(loc))
- visible_message("A grotesque blade forms around [loc.name]\'s arm!",
- "Our arm twists and mutates, transforming it into a deadly blade.",
+ visible_message("A grotesque weapon forms around [loc.name]\'s arm!",
+ "Our arm twists and mutates, transforming it into a deadly weapon.",
"You hear organic matter ripping and tearing!")
src.creator = loc
-/obj/item/weapon/melee/arm_blade/dropped(mob/user)
- visible_message("With a sickening crunch, [creator] reforms their arm blade into an arm!",
+/obj/item/weapon/melee/changeling/dropped(mob/user)
+ visible_message("With a sickening crunch, [creator] reforms their arm!",
"We assimilate the weapon back into our body.",
"You hear organic matter ripping and tearing!")
playsound(src, 'sound/effects/blobattack.ogg', 30, 1)
@@ -62,16 +80,16 @@
if(src)
qdel(src)
-/obj/item/weapon/melee/arm_blade/Destroy()
+/obj/item/weapon/melee/changeling/Destroy()
processing_objects -= src
creator = null
..()
-/obj/item/weapon/melee/arm_blade/suicide_act(mob/user)
+/obj/item/weapon/melee/changeling/suicide_act(mob/user)
viewers(user) << "[user] is impaling \himself the [src.name]! It looks like \he's trying to commit suicide."
return(BRUTELOSS)
-/obj/item/weapon/melee/arm_blade/process() //Stolen from ninja swords.
+/obj/item/weapon/melee/changeling/process() //Stolen from ninja swords.
if(!creator || loc != creator || !creator.item_is_in_hands(src))
// Tidy up a bit.
if(istype(loc,/mob/living))
@@ -86,4 +104,34 @@
host.drop_from_inventory(src)
spawn(1)
if(src)
- qdel(src)
\ No newline at end of file
+ qdel(src)
+
+/obj/item/weapon/melee/changeling/arm_blade
+ name = "arm blade"
+ desc = "A grotesque blade made out of bone and flesh that cleaves through people as a hot knife through butter."
+ icon_state = "arm_blade"
+ force = 40
+ armor_penetration = 15
+ sharp = 1
+ edge = 1
+ pry = 1
+ attack_verb = list("attacked", "slashed", "stabbed", "sliced", "torn", "ripped", "diced", "cut")
+
+/obj/item/weapon/melee/changeling/arm_blade/greater
+ name = "arm greatblade"
+ desc = "A grotesque blade made out of bone and flesh that cleaves through people and armor as a hot knife through butter."
+ armor_penetration = 30
+
+/obj/item/weapon/melee/changeling/claw
+ name = "hand claw"
+ desc = "A grotesque claw made out of bone and flesh that cleaves through people as a hot knife through butter."
+ icon_state = "ling_claw"
+ force = 15
+ sharp = 1
+ edge = 1
+ attack_verb = list("attacked", "slashed", "stabbed", "sliced", "torn", "ripped", "diced", "cut")
+
+/obj/item/weapon/melee/changeling/claw/greater
+ name = "hand greatclaw"
+ force = 20
+ armor_penetration = 20
\ No newline at end of file
diff --git a/code/game/gamemodes/changeling/powers/armor.dm b/code/game/gamemodes/changeling/powers/armor.dm
index 5ec37a5b70..ca8a3c8780 100644
--- a/code/game/gamemodes/changeling/powers/armor.dm
+++ b/code/game/gamemodes/changeling/powers/armor.dm
@@ -112,9 +112,6 @@
"We harden our flesh, creating a suit of armor!",
"You hear organic matter ripping and tearing!")
-/obj/item/clothing/suit/space/changeling/armored/dropped()
- qdel(src)
-
/obj/item/clothing/head/helmet/space/changeling/armored
name = "chitinous mass"
desc = "A tough, hard covering of black chitin with transparent chitin in front."
@@ -123,19 +120,12 @@
siemens_coefficient = 0.3
max_heat_protection_temperature = FIRE_HELMET_MAX_HEAT_PROTECTION_TEMPERATURE
-/obj/item/clothing/head/helmet/space/changeling/armored/dropped()
- qdel(src)
-
/obj/item/clothing/shoes/magboots/changeling/armored
desc = "A tough, hard mass of chitin, with long talons for digging into terrain."
name = "chitinous talons"
icon_state = "lingarmor"
action_button_name = "Toggle Talons"
-/obj/item/clothing/shoes/magboots/changeling/armored/dropped()
- ..()
- qdel(src)
-
/obj/item/clothing/gloves/combat/changeling //Combined insulated/fireproof gloves
name = "chitinous gauntlets"
desc = "Very resilient gauntlets made out of black chitin. It looks very durable, and can probably resist electrical shock in addition to the elements."
diff --git a/code/game/gamemodes/changeling/powers/darkvision.dm b/code/game/gamemodes/changeling/powers/darkvision.dm
new file mode 100644
index 0000000000..6fbb2954ba
--- /dev/null
+++ b/code/game/gamemodes/changeling/powers/darkvision.dm
@@ -0,0 +1,26 @@
+/datum/power/changeling/darksight
+ name = "Dark Sight"
+ desc = "We change the composition of our eyes, banishing the shadows from our vision."
+ helptext = "We will be able to see in the dark."
+ ability_icon_state = "ling_augmented_eyesight"
+ genomecost = 0
+ verbpath = /mob/proc/changeling_darksight
+
+/mob/proc/changeling_darksight()
+ set category = "Changeling"
+ set name = "Toggle Darkvision"
+ set desc = "We are able see in the dark."
+
+ var/datum/changeling/changeling = changeling_power(0,0,100,UNCONSCIOUS)
+ if(!changeling)
+ return 0
+
+ if(istype(src,/mob/living/carbon))
+ var/mob/living/carbon/C = src
+ C.seedarkness = !C.seedarkness
+ if(C.seedarkness)
+ to_chat(C, "We allow the shadows to return.")
+ else
+ to_chat(C, "We no longer need light to see.")
+
+ return 0
\ No newline at end of file
diff --git a/code/game/gamemodes/changeling/powers/fake_death.dm b/code/game/gamemodes/changeling/powers/fake_death.dm
index 765dbb51e6..cae98164a0 100644
--- a/code/game/gamemodes/changeling/powers/fake_death.dm
+++ b/code/game/gamemodes/changeling/powers/fake_death.dm
@@ -33,6 +33,9 @@
if(C.suiciding)
C.suiciding = 0
+ if(C.does_not_breathe)
+ C.does_not_breathe = 0 //This means they don't autoheal the oxy damage from the next step
+
if(C.stat != DEAD)
C.adjustOxyLoss(C.maxHealth * 2)
diff --git a/code/game/gamemodes/cult/runes.dm b/code/game/gamemodes/cult/runes.dm
index 027b61333e..14d0673a1a 100644
--- a/code/game/gamemodes/cult/runes.dm
+++ b/code/game/gamemodes/cult/runes.dm
@@ -152,12 +152,15 @@ var/list/sacrificed = list()
target << "Your mind turns to ash as the burning flames engulf your very soul and images of an unspeakable horror begin to bombard the last remnants of mental resistance."
//broken mind - 5000 may seem like a lot I wanted the effect to really stand out for maxiumum losing-your-mind-spooky
//hallucination is reduced when the step off as well, provided they haven't hit the last stage...
- target.hallucination += 5000
+
+ //5000 is waaaay too much, in practice.
+ target.hallucination = min(target.hallucination + 100, 500)
target.apply_effect(10, STUTTER)
target.adjustBrainLoss(1)
if(100 to INFINITY)
target << "Your entire broken soul and being is engulfed in corruption and flames as your mind shatters away into nothing."
- target.hallucination += 5000
+ //5000 is waaaay too much, in practice.
+ target.hallucination = min(target.hallucination + 100, 500)
target.apply_effect(15, STUTTER)
target.adjustBrainLoss(1)
@@ -626,10 +629,8 @@ var/list/sacrificed = list()
if(istype(src,/obj/effect/rune))
usr.say("O bidai nabora se[pick("'","`")]sma!")
- usr.say("[input]")
else
usr.whisper("O bidai nabora se[pick("'","`")]sma!")
- usr.whisper("[input]")
input = sanitize(input)
log_and_message_admins("used a communicate rune to say '[input]'")
diff --git a/code/game/gamemodes/epidemic/epidemic.dm b/code/game/gamemodes/epidemic/epidemic.dm
index 07b8d7f434..b6e4146a9c 100644
--- a/code/game/gamemodes/epidemic/epidemic.dm
+++ b/code/game/gamemodes/epidemic/epidemic.dm
@@ -52,7 +52,7 @@
intercept.name = "paper"
intercept.info = intercepttext
- comm.messagetitle.Add("Cent. Com. CONFIDENTIAL REPORT")
+ comm.messagetitle.Add("CentCom CONFIDENTIAL REPORT")
comm.messagetext.Add(intercepttext)
world << sound('sound/AI/commandreport.ogg')
@@ -74,7 +74,7 @@
intercept.name = "paper"
intercept.info = intercepttext
- comm.messagetitle.Add("Cent. Com. CONFIDENTIAL REPORT")
+ comm.messagetitle.Add("CentCom CONFIDENTIAL REPORT")
comm.messagetext.Add(intercepttext)
world << sound('sound/AI/commandreport.ogg')
diff --git a/code/game/gamemodes/events/dust.dm b/code/game/gamemodes/events/dust.dm
index d7d551396e..88964fa610 100644
--- a/code/game/gamemodes/events/dust.dm
+++ b/code/game/gamemodes/events/dust.dm
@@ -81,7 +81,12 @@ The "dust" will damage the hull of the station causin minor hull breaches.
startx = (TRANSITIONEDGE+1)
endy = rand(TRANSITIONEDGE,world.maxy-TRANSITIONEDGE)
endx = world.maxx-TRANSITIONEDGE
- var/z_level = pick(using_map.station_levels)
+ //VOREStation Edit - No space dust outside of space
+ var/list/z_levels = using_map.station_levels.Copy()
+ for(var/datum/planet/P in planet_controller.planets)
+ z_levels.Remove(P.expected_z_levels)
+ var/z_level = pick(z_levels)
+ //VOREStation Edit End
var/goal = locate(endx, endy, z_level)
src.x = startx
src.y = starty
diff --git a/code/game/gamemodes/game_mode.dm b/code/game/gamemodes/game_mode.dm
index 60d968bba0..2418f8afb9 100644
--- a/code/game/gamemodes/game_mode.dm
+++ b/code/game/gamemodes/game_mode.dm
@@ -405,6 +405,8 @@ var/global/list/additional_antag_types = list()
candidates += player.mind
players -= player
+ // Below is commented out as an attempt to solve an issue of too little people wanting to join the round due to wanting to have cake and eat it too.
+ /*
// If we don't have enough antags, draft people who voted for the round.
if(candidates.len < required_enemies)
for(var/mob/new_player/player in players)
@@ -413,6 +415,7 @@ var/global/list/additional_antag_types = list()
candidates += player.mind
players -= player
break
+ */
return candidates // Returns: The number of people who had the antagonist role set to yes, regardless of recomended_enemies, if that number is greater than required_enemies
// required_enemies if the number of people with that role set to yes is less than recomended_enemies,
diff --git a/code/game/gamemodes/heist/heist.dm b/code/game/gamemodes/heist/heist.dm
index b9418bfea9..48f0f02bfc 100644
--- a/code/game/gamemodes/heist/heist.dm
+++ b/code/game/gamemodes/heist/heist.dm
@@ -7,9 +7,9 @@ var/global/list/obj/cortical_stacks = list() //Stacks for 'leave nobody behind'
/datum/game_mode/heist
name = "Heist"
config_tag = "heist"
- required_players = 15
- required_players_secret = 15
- required_enemies = 4
+ required_players = 9
+ required_players_secret = 9
+ required_enemies = 3
round_description = "An unidentified bluespace signature is approaching the station!"
extended_round_description = "The Company's majority control of phoron in the system has marked the \
station to be a highly valuable target for many competing organizations and individuals. Being a \
diff --git a/code/game/gamemodes/infiltrator/infiltrator.dm b/code/game/gamemodes/infiltrator/infiltrator.dm
new file mode 100644
index 0000000000..22ea099ae0
--- /dev/null
+++ b/code/game/gamemodes/infiltrator/infiltrator.dm
@@ -0,0 +1,13 @@
+/datum/game_mode/infiltrator
+ name = "Team Traitor"
+ round_description = "There are a group of shadowy infiltrators onboard! Be careful!"
+ extended_round_description = "A team of secretative people have played the long con, and managed to obtain entry to \
+ the facility. What their goals are, who their employers are, and why the individuals would work for them is a mystery, \
+ but perhaps you will outwit them, or perhaps that is all part of their plan?"
+ config_tag = "infiltrator"
+ required_players = 2
+ required_players_secret = 5
+ required_enemies = 2 // Bit pointless if there is only one, since its basically traitor.
+ end_on_antag_death = 0
+ antag_scaling_coeff = 5
+ antag_tags = list(MODE_INFILTRATOR)
\ No newline at end of file
diff --git a/code/game/gamemodes/newobjective.dm b/code/game/gamemodes/newobjective.dm
index 6a5cd842ff..3db262d3df 100644
--- a/code/game/gamemodes/newobjective.dm
+++ b/code/game/gamemodes/newobjective.dm
@@ -1045,7 +1045,7 @@ datum
return 20
AI
steal_target = /obj/structure/AIcore
- explanation_text = "Steal a finished AI, either by intellicard or stealing the whole construct."
+ explanation_text = "Steal a finished AI, either by intelliCore or stealing the whole construct."
weight = 50
get_points(var/job)
diff --git a/code/game/gamemodes/nuclear/nuclear.dm b/code/game/gamemodes/nuclear/nuclear.dm
index 098f9fd329..e85af7e82b 100644
--- a/code/game/gamemodes/nuclear/nuclear.dm
+++ b/code/game/gamemodes/nuclear/nuclear.dm
@@ -12,9 +12,9 @@ var/list/nuke_disks = list()
colony of sizable population and considerable wealth causes it to often be the target of various \
attempts of robbery, fraud and other malicious actions."
config_tag = "mercenary"
- required_players = 15
- required_players_secret = 15
- required_enemies = 4
+ required_players = 9
+ required_players_secret = 9
+ required_enemies = 3
end_on_antag_death = 0
var/nuke_off_station = 0 //Used for tracking if the syndies actually haul the nuke to the station
var/syndies_didnt_escape = 0 //Used for tracking if the syndies got the shuttle off of the z-level
diff --git a/code/game/gamemodes/technomancer/assistance/assistance.dm b/code/game/gamemodes/technomancer/assistance/assistance.dm
index 8b060429e8..61c1390cc3 100644
--- a/code/game/gamemodes/technomancer/assistance/assistance.dm
+++ b/code/game/gamemodes/technomancer/assistance/assistance.dm
@@ -36,7 +36,7 @@
/obj/item/weapon/antag_spawner/technomancer_apprentice/Destroy()
qdel(sparks)
- ..()
+ return ..()
/obj/item/weapon/antag_spawner/technomancer_apprentice/attack_self(mob/user)
user << "Teleporter attempting to lock on to your apprentice."
diff --git a/code/game/gamemodes/technomancer/assistance/golem.dm b/code/game/gamemodes/technomancer/assistance/golem.dm
index e0a0a5fd71..3bd54ed1f5 100644
--- a/code/game/gamemodes/technomancer/assistance/golem.dm
+++ b/code/game/gamemodes/technomancer/assistance/golem.dm
@@ -60,7 +60,7 @@
/mob/living/simple_animal/technomancer_golem/Destroy()
qdel(core)
- ..()
+ return ..()
/mob/living/simple_animal/technomancer_golem/update_icon()
overlays.Cut()
diff --git a/code/game/gamemodes/technomancer/core_obj.dm b/code/game/gamemodes/technomancer/core_obj.dm
index 7cea66660e..d672115ff6 100644
--- a/code/game/gamemodes/technomancer/core_obj.dm
+++ b/code/game/gamemodes/technomancer/core_obj.dm
@@ -43,7 +43,7 @@
/obj/item/weapon/technomancer_core/Destroy()
dismiss_all_summons()
processing_objects.Remove(src)
- ..()
+ return ..()
// Add the spell buttons to the HUD.
/obj/item/weapon/technomancer_core/equipped(mob/user)
diff --git a/code/game/gamemodes/technomancer/devices/gloves_of_regen.dm b/code/game/gamemodes/technomancer/devices/gloves_of_regen.dm
index a4761c847a..630a9bdb10 100644
--- a/code/game/gamemodes/technomancer/devices/gloves_of_regen.dm
+++ b/code/game/gamemodes/technomancer/devices/gloves_of_regen.dm
@@ -44,7 +44,7 @@
/obj/item/clothing/gloves/regen/Destroy()
wearer = null
processing_objects -= src
- ..()
+ return ..()
/obj/item/clothing/gloves/regen/process()
if(!wearer || wearer.isSynthetic() || wearer.stat == DEAD || wearer.nutrition <= 10)
diff --git a/code/game/gamemodes/technomancer/devices/shield_armor.dm b/code/game/gamemodes/technomancer/devices/shield_armor.dm
index 0bbb6ef085..e36ce7bd3a 100644
--- a/code/game/gamemodes/technomancer/devices/shield_armor.dm
+++ b/code/game/gamemodes/technomancer/devices/shield_armor.dm
@@ -31,7 +31,7 @@
/obj/item/clothing/suit/armor/shield/Destroy()
qdel(spark_system)
- ..()
+ return ..()
/obj/item/clothing/suit/armor/shield/handle_shield(mob/user, var/damage, atom/damage_source = null, mob/attacker = null, var/def_zone = null, var/attack_text = "the attack")
//Since this is a pierce of armor that is passive, we do not need to check if the user is incapacitated.
diff --git a/code/game/gamemodes/technomancer/spell_objs.dm b/code/game/gamemodes/technomancer/spell_objs.dm
index 2dede11a94..5ba100a4b4 100644
--- a/code/game/gamemodes/technomancer/spell_objs.dm
+++ b/code/game/gamemodes/technomancer/spell_objs.dm
@@ -151,7 +151,7 @@
/obj/item/weapon/spell/Destroy()
owner = null
core = null
- ..()
+ return ..()
// Proc: update_icon()
// Parameters: 0
diff --git a/code/game/gamemodes/technomancer/spells/blink.dm b/code/game/gamemodes/technomancer/spells/blink.dm
index 74eba8adb9..c0012c991c 100644
--- a/code/game/gamemodes/technomancer/spells/blink.dm
+++ b/code/game/gamemodes/technomancer/spells/blink.dm
@@ -7,6 +7,7 @@
spell_power_desc = "Blink distance is scaled up with more spell power."
cost = 50
obj_path = /obj/item/weapon/spell/blink
+ ability_icon_state = "tech_blink"
category = UTILITY_SPELLS
/obj/item/weapon/spell/blink
diff --git a/code/game/gamemodes/technomancer/spells/control.dm b/code/game/gamemodes/technomancer/spells/control.dm
index 029f8b533d..12961ab29e 100644
--- a/code/game/gamemodes/technomancer/spells/control.dm
+++ b/code/game/gamemodes/technomancer/spells/control.dm
@@ -7,6 +7,7 @@
around the entity is merely a hologram used to allow the user to know if the creature is safe or not."
cost = 100
obj_path = /obj/item/weapon/spell/control
+ ability_icon_state = "tech_control"
category = UTILITY_SPELLS
/mob/living/carbon/human/proc/technomancer_control()
diff --git a/code/game/gamemodes/technomancer/spells/flame_tongue.dm b/code/game/gamemodes/technomancer/spells/flame_tongue.dm
index 01b923ead8..33b4b6204d 100644
--- a/code/game/gamemodes/technomancer/spells/flame_tongue.dm
+++ b/code/game/gamemodes/technomancer/spells/flame_tongue.dm
@@ -28,6 +28,7 @@
/obj/item/weapon/weldingtool/spell
name = "flame"
+ eye_safety_modifier = 3
/obj/item/weapon/weldingtool/spell/process()
return
diff --git a/code/game/gamemodes/technomancer/spells/illusion.dm b/code/game/gamemodes/technomancer/spells/illusion.dm
index 50a9bf5da7..48efd67783 100644
--- a/code/game/gamemodes/technomancer/spells/illusion.dm
+++ b/code/game/gamemodes/technomancer/spells/illusion.dm
@@ -181,7 +181,7 @@
if(I_HURT)
adjustBruteLoss(harm_intent_damage)
- M.visible_message("\red [M] [response_harm] \the [src]")
+ M.visible_message("[M] [response_harm] \the [src]")
M.do_attack_animation(src)
return
diff --git a/code/game/gamemodes/technomancer/spells/modifier/mend_synthetic.dm b/code/game/gamemodes/technomancer/spells/modifier/mend_synthetic.dm
index d91530b0c9..0c39e99d60 100644
--- a/code/game/gamemodes/technomancer/spells/modifier/mend_synthetic.dm
+++ b/code/game/gamemodes/technomancer/spells/modifier/mend_synthetic.dm
@@ -1,12 +1,12 @@
/datum/technomancer/spell/mend_synthetic
name = "Mend Synthetic"
- desc = "Repairs minor damages to robotic entities. \
+ desc = "Repairs minor damage to prosthetics. \
Instability is split between the target and technomancer, if seperate. The function will end prematurely \
if the target is completely healthy, preventing further instability."
spell_power_desc = "Healing amount increased."
cost = 50
obj_path = /obj/item/weapon/spell/modifier/mend_synthetic
- ability_icon_state = "tech_mendwounds"
+ ability_icon_state = "tech_mendsynth"
category = SUPPORT_SPELLS
/obj/item/weapon/spell/modifier/mend_synthetic
@@ -35,8 +35,11 @@
if(!holder.getBruteLoss() && !holder.getFireLoss()) // No point existing if the spell can't heal.
expire()
return
- holder.adjustBruteLoss(-4 * spell_power) // Should heal roughly 20 burn/brute over 10 seconds, as tick() is run every 2 seconds.
- holder.adjustFireLoss(-4 * spell_power) // Ditto.
+ if(ishuman(holder))
+ var/mob/living/carbon/human/H = holder
+ for(var/obj/item/organ/external/E in H.organs)
+ var/obj/item/organ/external/O = E
+ O.heal_damage(4 * spell_power, 4 * spell_power, 0, 1)
holder.adjust_instability(1)
if(origin)
var/mob/living/L = origin.resolve()
diff --git a/code/game/gamemodes/technomancer/spells/oxygenate.dm b/code/game/gamemodes/technomancer/spells/oxygenate.dm
index fcc2cbcecf..61c6367260 100644
--- a/code/game/gamemodes/technomancer/spells/oxygenate.dm
+++ b/code/game/gamemodes/technomancer/spells/oxygenate.dm
@@ -4,7 +4,7 @@
If casted on the envirnment, air (oxygen and nitrogen) is moved from a distant location to your target."
cost = 25
obj_path = /obj/item/weapon/spell/oxygenate
- ability_icon_state = "oxygenate"
+ ability_icon_state = "tech_oxygenate"
category = SUPPORT_SPELLS
/obj/item/weapon/spell/oxygenate
diff --git a/code/game/gamemodes/technomancer/spells/phase_shift.dm b/code/game/gamemodes/technomancer/spells/phase_shift.dm
index a79dfb7c37..5b06a7e704 100644
--- a/code/game/gamemodes/technomancer/spells/phase_shift.dm
+++ b/code/game/gamemodes/technomancer/spells/phase_shift.dm
@@ -4,12 +4,14 @@
rift you create will afflict you with instability."
cost = 50
obj_path = /obj/item/weapon/spell/phase_shift
+ ability_icon_state = "tech_phaseshift"
category = DEFENSIVE_SPELLS
/obj/item/weapon/spell/phase_shift
name = "phase shift"
desc = "Allows you to dodge your untimely fate by shifting your location somewhere else, so long as you can survive inside the \
rift."
+ icon_state = "blink"
cast_methods = CAST_USE
aspect = ASPECT_TELE
diff --git a/code/game/gamemodes/technomancer/spells/projectile/overload.dm b/code/game/gamemodes/technomancer/spells/projectile/overload.dm
index 902c11c026..d9c3628631 100644
--- a/code/game/gamemodes/technomancer/spells/projectile/overload.dm
+++ b/code/game/gamemodes/technomancer/spells/projectile/overload.dm
@@ -6,6 +6,7 @@
spell_power_desc = "Increases damage dealt, up to a cap of 80 damage per shot."
cost = 100
obj_path = /obj/item/weapon/spell/projectile/overload
+ ability_icon_state = "tech_overload"
category = OFFENSIVE_SPELLS
/obj/item/weapon/spell/projectile/overload
@@ -39,6 +40,7 @@
/obj/item/weapon/spell/projectile/overload/on_ranged_cast(atom/hit_atom, mob/living/user)
energy_cost_per_shot = round(core.max_energy * 0.10)
+ ..()
/* var/energy_before_firing = core.energy
if(set_up(hit_atom, user))
var/obj/item/projectile/overload/P = new spell_projectile(get_turf(user))
diff --git a/code/game/jobs/job/security.dm b/code/game/jobs/job/security.dm
index 444f9daf55..ac43274052 100644
--- a/code/game/jobs/job/security.dm
+++ b/code/game/jobs/job/security.dm
@@ -120,6 +120,7 @@
H.equip_to_slot_or_del(new /obj/item/weapon/storage/box/evidence(H), slot_l_hand)
else
H.equip_to_slot_or_del(new /obj/item/weapon/storage/box/evidence(H), slot_in_backpack)
+ H.equip_to_slot_or_del(new /obj/item/weapon/gun/projectile/revolver/detective(H), slot_in_backpack) // Vorestation Edit
if(has_alt_title(H, alt_title,"Forensic Technician"))
H.equip_to_slot_or_del(new /obj/item/clothing/suit/storage/forensics/blue(H), slot_wear_suit)
H.equip_to_slot_or_del(new /obj/item/weapon/storage/briefcase/crimekit, slot_r_hand)
diff --git a/code/game/machinery/CableLayer.dm b/code/game/machinery/CableLayer.dm
index 2e10ed3b1b..a6c161982d 100644
--- a/code/game/machinery/CableLayer.dm
+++ b/code/game/machinery/CableLayer.dm
@@ -41,7 +41,7 @@
m = min(m, cable.amount)
m = min(m, 30)
if(m)
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(src.loc, O.usesound, 50, 1)
use_cable(m)
var/obj/item/stack/cable_coil/CC = new (get_turf(src))
CC.amount = m
diff --git a/code/game/machinery/adv_med.dm b/code/game/machinery/adv_med.dm
index 7bcbae5515..b8afc34a99 100644
--- a/code/game/machinery/adv_med.dm
+++ b/code/game/machinery/adv_med.dm
@@ -158,7 +158,7 @@
//Body Scan Console
/obj/machinery/body_scanconsole
var/obj/machinery/bodyscanner/scanner
- var/known_implants = list(/obj/item/weapon/implant/health, /obj/item/weapon/implant/chem, /obj/item/weapon/implant/death_alarm, /obj/item/weapon/implant/loyalty, /obj/item/weapon/implant/tracking, /obj/item/weapon/implant/language, /obj/item/weapon/implant/language/eal, /obj/item/weapon/implant/backup) //VOREStation Add - Backup Implant
+ var/known_implants = list(/obj/item/weapon/implant/health, /obj/item/weapon/implant/chem, /obj/item/weapon/implant/death_alarm, /obj/item/weapon/implant/loyalty, /obj/item/weapon/implant/tracking, /obj/item/weapon/implant/language, /obj/item/weapon/implant/language/eal, /obj/item/weapon/implant/backup, /obj/item/device/nif) //VOREStation Add - Backup Implant, NIF
var/delete
var/temphtml
name = "Body Scanner Console"
diff --git a/code/game/machinery/alarm.dm b/code/game/machinery/alarm.dm
index 5746fb179e..f964c07cd3 100644
--- a/code/game/machinery/alarm.dm
+++ b/code/game/machinery/alarm.dm
@@ -549,6 +549,7 @@
scrubbers[scrubbers.len]["filters"] += list(list("name" = "Carbon Dioxide", "command" = "co2_scrub","val" = info["filter_co2"]))
scrubbers[scrubbers.len]["filters"] += list(list("name" = "Toxin" , "command" = "tox_scrub","val" = info["filter_phoron"]))
scrubbers[scrubbers.len]["filters"] += list(list("name" = "Nitrous Oxide", "command" = "n2o_scrub","val" = info["filter_n2o"]))
+ scrubbers[scrubbers.len]["filters"] += list(list("name" = "Fuel", "command" = "fuel_scrub","val" = info["filter_fuel"]))
data["scrubbers"] = scrubbers
if(AALARM_SCREEN_MODE)
var/modes[0]
@@ -655,6 +656,7 @@
"co2_scrub",
"tox_scrub",
"n2o_scrub",
+ "fuel_scrub",
"panic_siphon",
"scrubbing",
"direction")
diff --git a/code/game/machinery/atmoalter/canister.dm b/code/game/machinery/atmoalter/canister.dm
index dcce5fb938..de0d7975c3 100644
--- a/code/game/machinery/atmoalter/canister.dm
+++ b/code/game/machinery/atmoalter/canister.dm
@@ -428,3 +428,23 @@ update_flag
src.update_icon()
return 1
+
+//R-UST port
+// Special types used for engine setup admin verb, they contain double amount of that of normal canister.
+/obj/machinery/portable_atmospherics/canister/nitrogen/engine_setup/New()
+ ..()
+ src.air_contents.adjust_gas("nitrogen", MolesForPressure())
+ src.update_icon()
+ return 1
+
+/obj/machinery/portable_atmospherics/canister/carbon_dioxide/engine_setup/New()
+ ..()
+ src.air_contents.adjust_gas("carbon_dioxide", MolesForPressure())
+ src.update_icon()
+ return 1
+
+/obj/machinery/portable_atmospherics/canister/phoron/engine_setup/New()
+ ..()
+ src.air_contents.adjust_gas("phoron", MolesForPressure())
+ src.update_icon()
+ return 1
\ No newline at end of file
diff --git a/code/game/machinery/atmoalter/meter.dm b/code/game/machinery/atmoalter/meter.dm
index 1e9746d2fd..13e390538b 100644
--- a/code/game/machinery/atmoalter/meter.dm
+++ b/code/game/machinery/atmoalter/meter.dm
@@ -67,13 +67,13 @@
/obj/machinery/meter/examine(mob/user)
var/t = "A gas flow meter. "
-
- if(get_dist(user, src) > 5 && !(istype(user, /mob/living/silicon/ai) || istype(user, /mob/observer/dead)))
+
+ if(get_dist(user, src) > 3 && !(istype(user, /mob/living/silicon/ai) || istype(user, /mob/observer/dead)))
t += "You are too far away to read it."
-
+
else if(stat & (NOPOWER|BROKEN))
t += "The display is off."
-
+
else if(src.target)
var/datum/gas_mixture/environment = target.return_air()
if(environment)
@@ -82,7 +82,7 @@
t += "The sensor error light is blinking."
else
t += "The connect error light is blinking."
-
+
user << t
/obj/machinery/meter/Click()
@@ -90,15 +90,15 @@
if(istype(usr, /mob/living/carbon/human) || istype(usr, /mob/living/silicon/ai)) // ghosts can call ..() for examine
usr.examinate(src)
return 1
-
+
return ..()
/obj/machinery/meter/attackby(var/obj/item/weapon/W as obj, var/mob/user as mob)
if (!istype(W, /obj/item/weapon/wrench))
return ..()
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src]..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"\The [user] unfastens \the [src].", \
"You have unfastened \the [src].", \
diff --git a/code/game/machinery/atmoalter/portable_atmospherics.dm b/code/game/machinery/atmoalter/portable_atmospherics.dm
index deee8ed76b..cb0a67cc04 100644
--- a/code/game/machinery/atmoalter/portable_atmospherics.dm
+++ b/code/game/machinery/atmoalter/portable_atmospherics.dm
@@ -114,6 +114,7 @@
disconnect()
user << "You disconnect \the [src] from the port."
update_icon()
+ playsound(src, W.usesound, 50, 1)
return
else
var/obj/machinery/atmospherics/portables_connector/possible_port = locate(/obj/machinery/atmospherics/portables_connector/) in loc
@@ -121,6 +122,7 @@
if(connect(possible_port))
user << "You connect \the [src] to the port."
update_icon()
+ playsound(src, W.usesound, 50, 1)
return
else
user << "\The [src] failed to connect to the port."
@@ -173,6 +175,7 @@
return
user.visible_message("[user] opens the panel on [src] and removes [cell].", "You open the panel on [src] and remove [cell].")
+ playsound(src, I.usesound, 50, 1)
cell.add_fingerprint(user)
cell.loc = src.loc
cell = null
diff --git a/code/game/machinery/atmoalter/scrubber.dm b/code/game/machinery/atmoalter/scrubber.dm
index 9eb58cd6f9..322c13242b 100644
--- a/code/game/machinery/atmoalter/scrubber.dm
+++ b/code/game/machinery/atmoalter/scrubber.dm
@@ -17,7 +17,7 @@
var/minrate = 0
var/maxrate = 10 * ONE_ATMOSPHERE
- var/list/scrubbing_gas = list("phoron", "carbon_dioxide", "sleeping_agent")
+ var/list/scrubbing_gas = list("phoron", "carbon_dioxide", "sleeping_agent", "volatile_fuel")
/obj/machinery/portable_atmospherics/powered/scrubber/New()
..()
@@ -218,7 +218,7 @@
return
anchored = !anchored
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src.loc, I.usesound, 50, 1)
user << "You [anchored ? "wrench" : "unwrench"] \the [src]."
return
diff --git a/code/game/machinery/autolathe.dm b/code/game/machinery/autolathe.dm
index eb7b7049ef..64f07bd1d5 100644
--- a/code/game/machinery/autolathe.dm
+++ b/code/game/machinery/autolathe.dm
@@ -145,7 +145,7 @@
if(is_robot_module(O))
return 0
- if(istype(O,/obj/item/ammo_magazine/clip) || istype(O,/obj/item/ammo_magazine/s357) || istype(O,/obj/item/ammo_magazine/s38)) // Prevents ammo recycling exploit with speedloaders.
+ if(istype(O,/obj/item/ammo_magazine/clip) || istype(O,/obj/item/ammo_magazine/s357) || istype(O,/obj/item/ammo_magazine/s38) || istype (O,/obj/item/ammo_magazine/s44)/* VOREstation Edit*/) // Prevents ammo recycling exploit with speedloaders.
user << "\The [O] is too hazardous to recycle with the autolathe!"
return
/* ToDo: Make this actually check for ammo and change the value of the magazine if it's empty. -Spades
diff --git a/code/game/machinery/camera/camera.dm b/code/game/machinery/camera/camera.dm
index a4b28147e3..4e6405f34c 100644
--- a/code/game/machinery/camera/camera.dm
+++ b/code/game/machinery/camera/camera.dm
@@ -13,7 +13,7 @@
var/c_tag_order = 999
var/status = 1
anchored = 1.0
- var/invuln = null
+ var/invuln = 0
var/bugged = 0
var/obj/item/weapon/camera_assembly/assembly = null
@@ -37,6 +37,8 @@
var/client_huds = list()
+ var/list/camera_computers_using_this = list()
+
/obj/machinery/camera/New()
wires = new(src)
assembly = new(src)
@@ -143,7 +145,7 @@
panel_open = !panel_open
user.visible_message("[user] screws the camera's panel [panel_open ? "open" : "closed"]!",
"You screw the camera's panel [panel_open ? "open" : "closed"].")
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, W.usesound, 50, 1)
else if((iswirecutter(W) || ismultitool(W)) && panel_open)
interact(user)
@@ -377,10 +379,10 @@
// Do after stuff here
user << "You start to weld the [src].."
- playsound(src.loc, 'sound/items/Welder.ogg', 50, 1)
+ playsound(src.loc, WT.usesound, 50, 1)
WT.eyecheck(user)
busy = 1
- if(do_after(user, 100))
+ if(do_after(user, 100 * WT.toolspeed))
busy = 0
if(!WT.isOn())
return 0
diff --git a/code/game/machinery/camera/camera_assembly.dm b/code/game/machinery/camera/camera_assembly.dm
index 86bb12054a..67755f24e9 100644
--- a/code/game/machinery/camera/camera_assembly.dm
+++ b/code/game/machinery/camera/camera_assembly.dm
@@ -30,7 +30,7 @@
if(0)
// State 0
if(iswrench(W) && isturf(src.loc))
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You wrench the assembly into place."
anchored = 1
state = 1
@@ -48,7 +48,7 @@
return
else if(iswrench(W))
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You unattach the assembly from its place."
anchored = 0
update_icon()
@@ -78,7 +78,7 @@
if(3)
// State 3
if(isscrewdriver(W))
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, W.usesound, 50, 1)
var/input = sanitize(input(usr, "Which networks would you like to connect this camera to? Separate networks with a comma. No Spaces!\nFor example: "+using_map.station_short+",Security,Secret ", "Set Network", camera_network ? camera_network : NETWORK_DEFAULT))
if(!input)
@@ -118,7 +118,7 @@
else if(iswirecutter(W))
new/obj/item/stack/cable_coil(get_turf(src), 2)
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(src.loc, W.usesound, 50, 1)
user << "You cut the wires from the circuits."
state = 2
return
@@ -136,7 +136,7 @@
var/obj/U = locate(/obj) in upgrades
if(U)
user << "You unattach an upgrade from the assembly."
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
U.loc = get_turf(src)
upgrades -= U
return
@@ -161,10 +161,10 @@
return 0
user << "You start to weld the [src].."
- playsound(src.loc, 'sound/items/Welder.ogg', 50, 1)
+ playsound(src.loc, WT.usesound, 50, 1)
WT.eyecheck(user)
busy = 1
- if(do_after(user, 20))
+ if(do_after(user, 20 * WT.toolspeed))
busy = 0
if(!WT.isOn())
return 0
diff --git a/code/game/machinery/camera/presets.dm b/code/game/machinery/camera/presets.dm
index 9e4cd48650..351c1bd3b3 100644
--- a/code/game/machinery/camera/presets.dm
+++ b/code/game/machinery/camera/presets.dm
@@ -98,6 +98,7 @@ var/global/list/engineering_networks = list(
/obj/machinery/camera/network/thunder
network = list(NETWORK_THUNDER)
+ invuln = 1
// EMP
diff --git a/code/game/machinery/cell_charger.dm b/code/game/machinery/cell_charger.dm
index 2f87553e8e..6cb9e63eb5 100644
--- a/code/game/machinery/cell_charger.dm
+++ b/code/game/machinery/cell_charger.dm
@@ -68,7 +68,7 @@
anchored = !anchored
user << "You [anchored ? "attach" : "detach"] the cell charger [anchored ? "to" : "from"] the ground"
- playsound(src.loc, 'sound/items/Ratchet.ogg', 75, 1)
+ playsound(src, W.usesound, 75, 1)
/obj/machinery/cell_charger/attack_hand(mob/user)
if(charging)
diff --git a/code/game/machinery/cloning.dm b/code/game/machinery/cloning.dm
index 1a1bd9a463..cf06523f6e 100644
--- a/code/game/machinery/cloning.dm
+++ b/code/game/machinery/cloning.dm
@@ -234,7 +234,7 @@
connected = null
else
anchored = 1
- playsound(src.loc, 'sound/items/Ratchet.ogg', 100, 1)
+ playsound(src, W.usesound, 100, 1)
if(anchored)
user.visible_message("[user] secures [src] to the floor.", "You secure [src] to the floor.")
else
@@ -243,6 +243,7 @@
var/obj/item/device/multitool/M = W
M.connecting = src
user << "You load connection data from [src] to [M]."
+ M.update_icon()
return
else
..()
diff --git a/code/game/machinery/computer/ai_core.dm b/code/game/machinery/computer/ai_core.dm
index 34a9ebd58c..80633f4ea4 100644
--- a/code/game/machinery/computer/ai_core.dm
+++ b/code/game/machinery/computer/ai_core.dm
@@ -15,8 +15,8 @@
switch(state)
if(0)
if(istype(P, /obj/item/weapon/wrench))
- playsound(loc, 'sound/items/Ratchet.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(loc, P.usesound, 50, 1)
+ if(do_after(user, 20 * P.toolspeed))
user << "You wrench the frame into place."
anchored = 1
state = 1
@@ -25,16 +25,16 @@
if(!WT.isOn())
user << "The welder must be on for this task."
return
- playsound(loc, 'sound/items/Welder.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(loc, WT.usesound, 50, 1)
+ if(do_after(user, 20 * WT.toolspeed))
if(!src || !WT.remove_fuel(0, user)) return
user << "You deconstruct the frame."
new /obj/item/stack/material/plasteel( loc, 4)
qdel(src)
if(1)
if(istype(P, /obj/item/weapon/wrench))
- playsound(loc, 'sound/items/Ratchet.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(loc, P.usesound, 50, 1)
+ if(do_after(user, 20 * P.toolspeed))
user << "You unfasten the frame."
anchored = 0
state = 0
@@ -46,12 +46,12 @@
user.drop_item()
P.loc = src
if(istype(P, /obj/item/weapon/screwdriver) && circuit)
- playsound(loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(loc, P.usesound, 50, 1)
user << "You screw the circuit board into place."
state = 2
icon_state = "2"
if(istype(P, /obj/item/weapon/crowbar) && circuit)
- playsound(loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(loc, P.usesound, 50, 1)
user << "You remove the circuit board."
state = 1
icon_state = "0"
@@ -59,7 +59,7 @@
circuit = null
if(2)
if(istype(P, /obj/item/weapon/screwdriver) && circuit)
- playsound(loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(loc, P.usesound, 50, 1)
user << "You unfasten the circuit board."
state = 1
icon_state = "1"
@@ -81,7 +81,7 @@
if (brain)
user << "Get that brain out of there first"
else
- playsound(loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(loc, P.usesound, 50, 1)
user << "You remove the cables."
state = 2
icon_state = "2"
@@ -146,7 +146,7 @@
icon_state = "3b"
if(istype(P, /obj/item/weapon/crowbar) && brain)
- playsound(loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(loc, P.usesound, 50, 1)
user << "You remove the brain."
brain.loc = loc
brain = null
@@ -154,7 +154,7 @@
if(4)
if(istype(P, /obj/item/weapon/crowbar))
- playsound(loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(loc, P.usesound, 50, 1)
user << "You remove the glass panel."
state = 3
if (brain)
@@ -165,7 +165,7 @@
return
if(istype(P, /obj/item/weapon/screwdriver))
- playsound(loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(loc, P.usesound, 50, 1)
user << "You connect the monitor."
if(!brain)
var/open_for_latejoin = alert(user, "Would you like this core to be open for latejoining AIs?", "Latejoin", "Yes", "Yes", "No") == "Yes"
@@ -202,8 +202,8 @@
transfer.loc = get_turf(src)
transfer.create_eyeobj()
transfer.cancel_camera()
- user << "Transfer successful: [transfer.name] ([rand(1000,9999)].exe) downloaded to host terminal. Local copy wiped."
- transfer << "You have been uploaded to a stationary terminal. Remote device connection restored."
+ user << "Transfer successful: [transfer.name] placed within stationary core."
+ transfer << "You have been transferred into a stationary core. Remote device connection restored."
if(card)
card.clear()
@@ -229,7 +229,8 @@
else if(istype(W, /obj/item/weapon/wrench))
if(anchored)
user.visible_message("\The [user] starts to unbolt \the [src] from the plating...")
- if(!do_after(user,40))
+ playsound(src, W.usesound, 50, 1)
+ if(!do_after(user,40 * W.toolspeed))
user.visible_message("\The [user] decides not to unbolt \the [src].")
return
user.visible_message("\The [user] finishes unfastening \the [src]!")
@@ -237,7 +238,8 @@
return
else
user.visible_message("\The [user] starts to bolt \the [src] to the plating...")
- if(!do_after(user,40))
+ playsound(src, W.usesound, 50, 1)
+ if(!do_after(user,40 * W.toolspeed))
user.visible_message("\The [user] decides not to bolt \the [src].")
return
user.visible_message("\The [user] finishes fastening down \the [src]!")
diff --git a/code/game/machinery/computer/aifixer.dm b/code/game/machinery/computer/aifixer.dm
index cf657e1c10..d52300d13d 100644
--- a/code/game/machinery/computer/aifixer.dm
+++ b/code/game/machinery/computer/aifixer.dm
@@ -18,8 +18,8 @@
return
// Transfer over the AI.
- transfer << "You have been uploaded to a stationary terminal. Sadly, there is no remote access from here."
- user << "Transfer successful: [transfer.name] ([rand(1000,9999)].exe) installed and executed successfully. Local copy has been removed."
+ transfer << "You have been transferred into a stationary terminal. Sadly, there is no remote access from here."
+ user << "Transfer successful: [transfer.name] placed within stationary terminal."
transfer.loc = src
transfer.cancel_camera()
@@ -102,7 +102,7 @@
if (href_list["fix"])
src.active = 1
src.overlays += image(icon, "ai-fixer-on")
- while (src.occupant.health < 100)
+ while (src.occupant.getOxyLoss() > 0 || src.occupant.getFireLoss() > 0 || src.occupant.getToxLoss() > 0 || src.occupant.getBruteLoss() > 0)
src.occupant.adjustOxyLoss(-1)
src.occupant.adjustFireLoss(-1)
src.occupant.adjustToxLoss(-1)
diff --git a/code/game/machinery/computer/buildandrepair.dm b/code/game/machinery/computer/buildandrepair.dm
index 54734929c8..6d7243c36c 100644
--- a/code/game/machinery/computer/buildandrepair.dm
+++ b/code/game/machinery/computer/buildandrepair.dm
@@ -14,8 +14,8 @@
switch(state)
if(0)
if(istype(P, /obj/item/weapon/wrench))
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(src.loc, P.usesound, 50, 1)
+ if(do_after(user, 20 * P.toolspeed))
user << "You wrench the frame into place."
src.anchored = 1
src.state = 1
@@ -24,16 +24,16 @@
if(!WT.remove_fuel(0, user))
user << "The welding tool must be on to complete this task."
return
- playsound(src.loc, 'sound/items/Welder.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(src.loc, WT.usesound, 50, 1)
+ if(do_after(user, 20 * WT.toolspeed))
if(!src || !WT.isOn()) return
user << "You deconstruct the frame."
new /obj/item/stack/material/steel( src.loc, 5 )
qdel(src)
if(1)
if(istype(P, /obj/item/weapon/wrench))
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(src.loc, P.usesound, 50, 1)
+ if(do_after(user, 20 * P.toolspeed))
user << "You unfasten the frame."
src.anchored = 0
src.state = 0
@@ -49,12 +49,12 @@
else
user << "This frame does not accept circuit boards of this type!"
if(istype(P, /obj/item/weapon/screwdriver) && circuit)
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You screw the circuit board into place."
src.state = 2
src.icon_state = "2"
if(istype(P, /obj/item/weapon/crowbar) && circuit)
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You remove the circuit board."
src.state = 1
src.icon_state = "0"
@@ -62,7 +62,7 @@
src.circuit = null
if(2)
if(istype(P, /obj/item/weapon/screwdriver) && circuit)
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You unfasten the circuit board."
src.state = 1
src.icon_state = "1"
@@ -80,7 +80,7 @@
icon_state = "3"
if(3)
if(istype(P, /obj/item/weapon/wirecutters))
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You remove the cables."
src.state = 2
src.icon_state = "2"
@@ -101,13 +101,13 @@
src.icon_state = "4"
if(4)
if(istype(P, /obj/item/weapon/crowbar))
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You remove the glass panel."
src.state = 3
src.icon_state = "3"
new /obj/item/stack/material/glass( src.loc, 2 )
if(istype(P, /obj/item/weapon/screwdriver))
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You connect the monitor."
var/B = new src.circuit.build_path ( src.loc )
src.circuit.construct(B)
diff --git a/code/game/machinery/computer/camera.dm b/code/game/machinery/computer/camera.dm
index 36974b159f..b964f9c50c 100644
--- a/code/game/machinery/computer/camera.dm
+++ b/code/game/machinery/computer/camera.dm
@@ -65,7 +65,7 @@
if(..())
return 1
if(href_list["switch_camera"])
- if(src.z>6 || stat&(NOPOWER|BROKEN)) return
+ if(stat&(NOPOWER|BROKEN)) return //VOREStation Edit - Removed zlevel check
if(usr.stat || ((get_dist(usr, src) > 1 || !( usr.canmove ) || usr.blinded) && !istype(usr, /mob/living/silicon))) return
var/obj/machinery/camera/C = locate(href_list["switch_camera"]) in cameranet.cameras
if(!C)
@@ -76,13 +76,13 @@
switch_to_camera(usr, C)
return 1
else if(href_list["switch_network"])
- if(src.z>6 || stat&(NOPOWER|BROKEN)) return
+ if(stat&(NOPOWER|BROKEN)) return //VOREStation Edit - Removed zlevel check
if(usr.stat || ((get_dist(usr, src) > 1 || !( usr.canmove ) || usr.blinded) && !istype(usr, /mob/living/silicon))) return
if(href_list["switch_network"] in network)
current_network = href_list["switch_network"]
return 1
else if(href_list["reset"])
- if(src.z>6 || stat&(NOPOWER|BROKEN)) return
+ if(stat&(NOPOWER|BROKEN)) return //VOREStation Edit - Removed zlevel check
if(usr.stat || ((get_dist(usr, src) > 1 || !( usr.canmove ) || usr.blinded) && !istype(usr, /mob/living/silicon))) return
reset_current()
usr.reset_view(current_camera)
@@ -169,6 +169,7 @@
src.current_camera = C
if(current_camera)
+ current_camera.camera_computers_using_this.Add(src)
use_power = 2
var/mob/living/L = current_camera.loc
if(istype(L))
@@ -176,6 +177,7 @@
/obj/machinery/computer/security/proc/reset_current()
if(current_camera)
+ current_camera.camera_computers_using_this.Remove(src)
var/mob/living/L = current_camera.loc
if(istype(L))
L.tracking_cancelled()
diff --git a/code/game/machinery/computer/camera_circuit.dm b/code/game/machinery/computer/camera_circuit.dm
index 8db87c36ae..436703f724 100644
--- a/code/game/machinery/computer/camera_circuit.dm
+++ b/code/game/machinery/computer/camera_circuit.dm
@@ -41,6 +41,7 @@
else if(istype(I,/obj/item/weapon/screwdriver))
secured = !secured
user.visible_message("The [src] can [secured ? "no longer" : "now"] be modified.")
+ playsound(src, I.usesound, 50, 1)
updateBuildPath()
return
diff --git a/code/game/machinery/computer/card.dm b/code/game/machinery/computer/card.dm
index 293ff22ef9..3282430c82 100644
--- a/code/game/machinery/computer/card.dm
+++ b/code/game/machinery/computer/card.dm
@@ -103,6 +103,7 @@
data["medical_jobs"] = format_jobs(medical_positions)
data["science_jobs"] = format_jobs(science_positions)
data["security_jobs"] = format_jobs(security_positions)
+ data["cargo_jobs"] = format_jobs(cargo_positions)
data["civilian_jobs"] = format_jobs(civilian_positions)
data["centcom_jobs"] = format_jobs(get_all_centcom_jobs())
diff --git a/code/game/machinery/computer/communications.dm b/code/game/machinery/computer/communications.dm
index a8b6ee2424..29196f44d5 100644
--- a/code/game/machinery/computer/communications.dm
+++ b/code/game/machinery/computer/communications.dm
@@ -53,7 +53,7 @@
if(..())
return 1
if (using_map && !(src.z in using_map.contact_levels))
- usr << "\red Unable to establish a connection: \black You're too far away from the station!"
+ usr << "Unable to establish a connection: You're too far away from the station!"
return
usr.set_machine(src)
@@ -180,13 +180,13 @@
if("MessageCentCom")
if(src.authenticated==2)
if(centcomm_message_cooldown)
- usr << "\red Arrays recycling. Please stand by."
+ usr << "Arrays recycling. Please stand by."
return
var/input = sanitize(input("Please choose a message to transmit to [using_map.boss_short] via quantum entanglement. Please be aware that this process is very expensive, and abuse will lead to... termination. Transmission does not guarantee a response. There is a 30 second delay before you may send another message, be clear, full and concise.", "To abort, send an empty message.", ""))
if(!input || !(usr in view(1,src)))
return
CentCom_announce(input, usr)
- usr << "\blue Message transmitted."
+ usr << "Message transmitted."
log_say("[key_name(usr)] has made an IA [using_map.boss_short] announcement: [input]")
centcomm_message_cooldown = 1
spawn(300)//10 minute cooldown
@@ -197,13 +197,13 @@
if("MessageSyndicate")
if((src.authenticated==2) && (src.emagged))
if(centcomm_message_cooldown)
- usr << "\red Arrays recycling. Please stand by."
+ usr << "Arrays recycling. Please stand by."
return
var/input = sanitize(input(usr, "Please choose a message to transmit to \[ABNORMAL ROUTING CORDINATES\] via quantum entanglement. Please be aware that this process is very expensive, and abuse will lead to... termination. Transmission does not guarantee a response. There is a 30 second delay before you may send another message, be clear, full and concise.", "To abort, send an empty message.", ""))
if(!input || !(usr in view(1,src)))
return
Syndicate_announce(input, usr)
- usr << "\blue Message transmitted."
+ usr << "Message transmitted."
log_say("[key_name(usr)] has made an illegal announcement: [input]")
centcomm_message_cooldown = 1
spawn(300)//10 minute cooldown
@@ -275,7 +275,7 @@
if(..())
return
if (using_map && !(src.z in using_map.contact_levels))
- user << "\red Unable to establish a connection: \black You're too far away from the station!"
+ user << "Unable to establish a connection: You're too far away from the station!"
return
user.set_machine(src)
@@ -514,7 +514,7 @@
if((ticker.mode.name == "blob")||(ticker.mode.name == "Meteor"))
return
- if(!emergency_shuttle.going_to_centcom()) //check that shuttle isn't already heading to centcomm
+ if(!emergency_shuttle.going_to_centcom()) //check that shuttle isn't already heading to CentCom
emergency_shuttle.recall()
log_game("[key_name(user)] has recalled the shuttle.")
message_admins("[key_name_admin(user)] has recalled the shuttle.", 1)
diff --git a/code/game/machinery/computer/pod.dm b/code/game/machinery/computer/pod.dm
index 8db5ebd1b8..7b34c026d4 100644
--- a/code/game/machinery/computer/pod.dm
+++ b/code/game/machinery/computer/pod.dm
@@ -53,7 +53,7 @@
/*
/obj/machinery/computer/pod/attackby(I as obj, user as mob)
if(istype(I, /obj/item/weapon/screwdriver))
- playsound(loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, W.usesound, 50, 1)
if(do_after(user, 20))
if(stat & BROKEN)
user << "The broken glass falls out."
diff --git a/code/game/machinery/computer3/buildandrepair.dm b/code/game/machinery/computer3/buildandrepair.dm
index a064d8ce1c..f780e42b27 100644
--- a/code/game/machinery/computer3/buildandrepair.dm
+++ b/code/game/machinery/computer3/buildandrepair.dm
@@ -79,8 +79,8 @@
switch(state)
if(0)
if(istype(P, /obj/item/weapon/wrench))
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(src.loc, P.usesound, 50, 1)
+ if(do_after(user, 20 * P.toolspeed))
user << "You wrench the frame into place."
src.anchored = 1
src.state = 1
@@ -89,16 +89,16 @@
if(!WT.remove_fuel(0, user))
user << "The welding tool must be on to complete this task."
return
- playsound(src.loc, 'sound/items/Welder.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(src.loc, WT.usesound, 50, 1)
+ if(do_after(user, 20 * WT.toolspeed))
if(!src || !WT.isOn()) return
user << "You deconstruct the frame."
new /obj/item/stack/material/steel( src.loc, 5 )
qdel(src)
if(1)
if(istype(P, /obj/item/weapon/wrench))
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(src.loc, P.usesound, 50, 1)
+ if(do_after(user, 20 * P.toolspeed))
user << "You unfasten the frame."
src.anchored = 0
src.state = 0
@@ -114,12 +114,12 @@
else
user << "This frame does not accept circuit boards of this type!"
if(istype(P, /obj/item/weapon/screwdriver) && circuit)
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You screw the circuit board into place."
src.state = 2
src.icon_state = "2"
if(istype(P, /obj/item/weapon/crowbar) && circuit)
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You remove the circuit board."
src.state = 1
src.icon_state = "0"
@@ -127,15 +127,15 @@
src.circuit = null
if(2)
if(istype(P, /obj/item/weapon/screwdriver) && circuit)
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You unfasten the circuit board."
src.state = 1
src.icon_state = "1"
if(istype(P, /obj/item/weapon/crowbar))
if(battery)
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
- if(do_after(10))
+ playsound(src.loc, P.usesound, 50, 1)
+ if(do_after(10 * P.toolspeed))
battery.loc = loc
user << "You remove [battery]."
battery = null
@@ -168,7 +168,7 @@
if(components.len)
user << "There are parts in the way!"
return
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You remove the cables."
src.state = 2
src.icon_state = "2"
@@ -190,13 +190,13 @@
src.icon_state = "4"
if(4)
if(istype(P, /obj/item/weapon/crowbar))
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You remove the glass panel."
src.state = 3
src.icon_state = "3"
new /obj/item/stack/material/glass( src.loc, 2 )
if(istype(P, /obj/item/weapon/screwdriver))
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You connect the monitor."
var/obj/machinery/computer3/B = new src.circuit.build_path ( src.loc, built=1 )
/*if(circuit.powernet) B:powernet = circuit.powernet
diff --git a/code/game/machinery/computer3/component.dm b/code/game/machinery/computer3/component.dm
index 47d5e29853..44540a9299 100644
--- a/code/game/machinery/computer3/component.dm
+++ b/code/game/machinery/computer3/component.dm
@@ -41,7 +41,7 @@
*/
/obj/item/part/computer/ai_holder
- name = "intelliCard computer module"
+ name = "intelliCore computer module"
desc = "Contains a specialized nacelle for dealing with highly sensitive equipment without interference."
attackby_types = list(/obj/item/device/aicard)
@@ -81,8 +81,8 @@
return
// Transfer over the AI.
- transfer << "You have been uploaded to a stationary terminal. Sadly, there is no remote access from here."
- user << "Transfer successful: [transfer.name] ([rand(1000,9999)].exe) installed and executed successfully. Local copy has been removed."
+ transfer << "You have been transferred into a mobile terminal. Sadly, there is no remote access from here."
+ user << "Transfer successful: [transfer.name] placed within mobile terminal."
transfer.loc = src
transfer.cancel_camera()
diff --git a/code/game/machinery/computer3/computers/communications.dm b/code/game/machinery/computer3/computers/communications.dm
index c4ec88f8e0..6f802c54bd 100644
--- a/code/game/machinery/computer3/computers/communications.dm
+++ b/code/game/machinery/computer3/computers/communications.dm
@@ -184,7 +184,7 @@
stat_msg2 = reject_bad_text(sanitize(input("Line 2", "Enter Message Text", stat_msg2) as text|null, 40), 40)
computer.updateDialog()
- // OMG CENTCOMM LETTERHEAD
+ // OMG CENTCOM LETTERHEAD
if("MessageCentCom" in href_list)
if(!computer.radio.subspace)
return
diff --git a/code/game/machinery/constructable_frame.dm b/code/game/machinery/constructable_frame.dm
index 1236ae0e5b..c3b6e010d6 100644
--- a/code/game/machinery/constructable_frame.dm
+++ b/code/game/machinery/constructable_frame.dm
@@ -42,7 +42,7 @@
icon_state = "box_1"
else
if(istype(P, /obj/item/weapon/wrench))
- playsound(src.loc, 'sound/items/Ratchet.ogg', 75, 1)
+ playsound(src, W.usesound, 75, 1)
user << "You dismantle the frame"
new /obj/item/stack/material/steel(src.loc, 5)
qdel(src)
@@ -72,7 +72,7 @@
user << "This frame does not accept circuit boards of this type!"
else
if(istype(P, /obj/item/weapon/wirecutters))
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You remove the cables."
state = 1
icon_state = "box_0"
@@ -81,7 +81,7 @@
if(3)
if(istype(P, /obj/item/weapon/crowbar))
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
state = 2
circuit.loc = src.loc
circuit = null
@@ -103,28 +103,28 @@
component_check = 0
break
if(component_check)
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
var/obj/machinery/new_machine = new src.circuit.build_path(src.loc, src.dir)
-
+
if(new_machine.component_parts)
new_machine.component_parts.Cut()
else
new_machine.component_parts = list()
-
+
src.circuit.construct(new_machine)
-
+
for(var/obj/O in src)
if(circuit.contain_parts) // things like disposal don't want their parts in them
O.loc = new_machine
else
O.loc = null
new_machine.component_parts += O
-
+
if(circuit.contain_parts)
circuit.loc = new_machine
else
circuit.loc = null
-
+
new_machine.RefreshParts()
qdel(src)
else
diff --git a/code/game/machinery/cryo.dm b/code/game/machinery/cryo.dm
index 5d0f707ae8..1e27f61866 100644
--- a/code/game/machinery/cryo.dm
+++ b/code/game/machinery/cryo.dm
@@ -191,6 +191,11 @@
qdel(G)
return
+/obj/machinery/atmospherics/unary/cryo_cell/MouseDrop_T(var/mob/target, var/mob/user) //Allows borgs to put people into cryo without external assistance
+ if(user.stat || user.lying || !Adjacent(user) || !target.Adjacent(user)|| !ishuman(target))
+ return
+ put_mob(target)
+
/obj/machinery/atmospherics/unary/cryo_cell/update_icon()
overlays.Cut()
icon_state = "pod[on]"
diff --git a/code/game/machinery/cryopod.dm b/code/game/machinery/cryopod.dm
index ab87985c93..aa09463c15 100644
--- a/code/game/machinery/cryopod.dm
+++ b/code/game/machinery/cryopod.dm
@@ -515,50 +515,10 @@
if(!ismob(grab.affecting))
return
-
- if(!check_occupant_allowed(grab.affecting))
- return
-
- var/willing = null //We don't want to allow people to be forced into despawning.
- var/mob/M = grab.affecting
-
- if(M.client)
- if(alert(M,"Would you like to enter long-term storage?",,"Yes","No") == "Yes")
- if(!M || !grab || !grab.affecting) return
- willing = 1
else
- willing = 1
+ go_in(grab.affecting,user)
- if(willing)
- visible_message("\The [user] starts putting [grab:affecting:name] into \the [src].", 3)
-
- if(do_after(user, 20))
- if(!M || !grab || !grab:affecting) return
-
- M.forceMove(src)
-
- if(M.client)
- M.client.perspective = EYE_PERSPECTIVE
- M.client.eye = src
-
- icon_state = occupied_icon_state
-
- M << "[on_enter_occupant_message]"
- M << "If you ghost, log out or close your client now, your character will shortly be permanently removed from the round."
- set_occupant(M)
- time_entered = world.time
- if(ishuman(M) && applies_stasis)
- var/mob/living/carbon/human/H = M
- H.Stasis(1000)
-
- // Book keeping!
- var/turf/location = get_turf(src)
- log_admin("[key_name_admin(M)] has entered a stasis pod. (JMP)")
- message_admins("[key_name_admin(M)] has entered a stasis pod.")
-
- //Despawning occurs when process() is called with an occupant without a client.
- add_fingerprint(M)
/obj/machinery/cryopod/verb/eject()
set name = "Eject Pod"
@@ -666,3 +626,61 @@
name = initial(name)
if(occupant)
name = "[name] ([occupant])"
+
+/obj/machinery/cryopod/MouseDrop_T(var/mob/target, var/mob/user)
+ if(user.stat || user.lying || !Adjacent(user) || !target.Adjacent(user))
+ return
+ go_in(target, user)
+
+/obj/machinery/cryopod/proc/go_in(var/mob/M, var/mob/user)
+ if(!check_occupant_allowed(M))
+ return
+ if(!M)
+ return
+ if(occupant)
+ to_chat(user,"\The [src] is already occupied.")
+ return
+
+ var/willing = null //We don't want to allow people to be forced into despawning.
+
+ if(M.client)
+ if(alert(M,"Would you like to enter long-term storage?",,"Yes","No") == "Yes")
+ if(!M) return
+ willing = 1
+ else
+ willing = 1
+
+ if(willing)
+ if(M == user)
+ visible_message("[usr] [on_enter_visible_message] [src].", 3)
+ else
+ visible_message("\The [user] starts putting [M] into \the [src].", 3)
+
+ if(do_after(user, 20))
+ if(occupant)
+ to_chat(user,"\The [src] is already occupied.")
+ return
+ M.forceMove(src)
+
+ if(M.client)
+ M.client.perspective = EYE_PERSPECTIVE
+ M.client.eye = src
+ else return
+
+ icon_state = occupied_icon_state
+
+ M << "[on_enter_occupant_message]"
+ M << "If you ghost, log out or close your client now, your character will shortly be permanently removed from the round."
+ set_occupant(M)
+ time_entered = world.time
+ if(ishuman(M) && applies_stasis)
+ var/mob/living/carbon/human/H = M
+ H.Stasis(1000)
+
+ // Book keeping!
+ var/turf/location = get_turf(src)
+ log_admin("[key_name_admin(M)] has entered a stasis pod. (JMP)")
+ message_admins("[key_name_admin(M)] has entered a stasis pod.")
+
+ //Despawning occurs when process() is called with an occupant without a client.
+ add_fingerprint(M)
\ No newline at end of file
diff --git a/code/game/machinery/doors/airlock.dm b/code/game/machinery/doors/airlock.dm
index 05600494cd..a31ff50c56 100644
--- a/code/game/machinery/doors/airlock.dm
+++ b/code/game/machinery/doors/airlock.dm
@@ -40,7 +40,11 @@
var/datum/wires/airlock/wires = null
var/open_sound_powered = 'sound/machines/airlock.ogg'
- var/open_sound_unpowered = 'sound/machines/airlock_creaking.ogg'
+ var/open_sound_unpowered = 'sound/machines/airlockforced.ogg'
+ var/close_sound_powered = 'sound/machines/airlockclose.ogg'
+ var/denied_sound = 'sound/machines/deniedbeep.ogg'
+ var/bolt_up_sound = 'sound/machines/boltsup.ogg'
+ var/bolt_down_sound = 'sound/machines/boltsdown.ogg'
/obj/machinery/door/airlock/attack_generic(var/mob/user, var/damage)
if(stat & (BROKEN|NOPOWER))
@@ -140,6 +144,11 @@
name = "External Airlock"
icon = 'icons/obj/doors/Doorext.dmi'
assembly_type = /obj/structure/door_assembly/door_assembly_ext
+
+/obj/machinery/door/airlock/glass_external
+ name = "External Airlock"
+ icon = 'icons/obj/doors/Doorextglass.dmi'
+ assembly_type = /obj/structure/door_assembly/door_assembly_ext
opacity = 0
glass = 1
req_one_access = list(access_external_airlocks)
@@ -637,8 +646,7 @@ About the new airlock wires panel:
if("deny")
if(density && src.arePowerSystemsOn())
flick("door_deny", src)
- if(secured_wires)
- playsound(src.loc, 'sound/machines/buzz-two.ogg', 50, 0)
+ playsound(src, denied_sound, 50, 0, 3)
return
/obj/machinery/door/airlock/attack_ai(mob/user as mob)
@@ -817,7 +825,7 @@ About the new airlock wires panel:
/obj/machinery/door/airlock/proc/can_remove_electronics()
return src.p_open && (operating < 0 || (!operating && welded && !src.arePowerSystemsOn() && density && (!src.locked || (stat & BROKEN))))
-/obj/machinery/door/airlock/attackby(C as obj, mob/user as mob)
+/obj/machinery/door/airlock/attackby(obj/item/C, mob/user as mob)
//world << text("airlock attackby src [] obj [] mob []", src, C, user)
if(!istype(usr, /mob/living/silicon))
if(src.isElectrified())
@@ -838,7 +846,7 @@ About the new airlock wires panel:
src.welded = 1
else
src.welded = null
- playsound(src, 'sound/items/Welder.ogg', 75, 1)
+ playsound(src.loc, C.usesound, 75, 1)
src.update_icon()
return
else
@@ -849,8 +857,10 @@ About the new airlock wires panel:
to_chat(usr,"The panel is broken and cannot be closed.")
else
src.p_open = 0
+ playsound(src, C.usesound, 50, 1)
else
src.p_open = 1
+ playsound(src, C.usesound, 50, 1)
src.update_icon()
else if(istype(C, /obj/item/weapon/wirecutters))
return src.attack_hand(user)
@@ -863,9 +873,9 @@ About the new airlock wires panel:
cable.plugin(src, user)
else if(!repairing && istype(C, /obj/item/weapon/crowbar))
if(can_remove_electronics())
- playsound(src.loc, 'sound/items/Crowbar.ogg', 75, 1)
+ playsound(src, C.usesound, 75, 1)
user.visible_message("[user] removes the electronics from the airlock assembly.", "You start to remove electronics from the airlock assembly.")
- if(do_after(user,40))
+ if(do_after(user,40 * C.toolspeed))
to_chat(user,"You removed the airlock electronics!")
var/obj/structure/door_assembly/da = new assembly_type(src.loc)
@@ -956,7 +966,7 @@ About the new airlock wires panel:
//if the door is unpowered then it doesn't make sense to hear the woosh of a pneumatic actuator
if(arePowerSystemsOn())
- playsound(src.loc, open_sound_powered, 75, 1)
+ playsound(src.loc, open_sound_powered, 50, 1)
else
playsound(src.loc, open_sound_unpowered, 75, 1)
@@ -1053,7 +1063,7 @@ About the new airlock wires panel:
use_power(360) //360 W seems much more appropriate for an actuator moving an industrial door capable of crushing people
has_beeped = 0
if(arePowerSystemsOn())
- playsound(src.loc, open_sound_powered, 75, 1)
+ playsound(src.loc, close_sound_powered, 50, 1)
else
playsound(src.loc, open_sound_unpowered, 75, 1)
for(var/turf/turf in locs)
@@ -1070,6 +1080,7 @@ About the new airlock wires panel:
if (operating && !forced) return 0
src.locked = 1
+ playsound(src, bolt_down_sound, 30, 0, 3)
for(var/mob/M in range(1,src))
M.show_message("You hear a click from the bottom of the door.", 2)
update_icon()
@@ -1083,6 +1094,7 @@ About the new airlock wires panel:
if(operating || !src.arePowerSystemsOn() || isWireCut(AIRLOCK_WIRE_DOOR_BOLTS)) return
src.locked = 0
+ playsound(src, bolt_up_sound, 30, 0, 3)
for(var/mob/M in range(1,src))
M.show_message("You hear a click from the bottom of the door.", 2)
update_icon()
diff --git a/code/game/machinery/doors/blast_door.dm b/code/game/machinery/doors/blast_door.dm
index 41680d3de7..94d336274e 100644
--- a/code/game/machinery/doors/blast_door.dm
+++ b/code/game/machinery/doors/blast_door.dm
@@ -118,25 +118,8 @@
usr << "[src]'s motors resist your effort."
return
- if(istype(C, /obj/item/stack/material) && C.get_material_name() == "plasteel") // Repairing.
- var/amt = Ceiling((maxhealth - health)/150)
- if(!amt)
- usr << "\The [src] is already fully repaired."
- return
- var/obj/item/stack/P = C
- if(P.amount < amt)
- usr << "You don't have enough sheets to repair this! You need at least [amt] sheets."
- return
- usr << "You begin repairing [src]..."
- if(do_after(usr, 30))
- if(P.use(amt))
- usr << "You have repaired \The [src]"
- src.repair()
- else
- usr << "You don't have enough sheets to repair this! You need at least [amt] sheets."
-
- else if(src.density)
+ else if(src.density && (user.a_intent == I_HURT)) //If we can't pry it open and it's a weapon, let's hit it.
var/obj/item/weapon/W = C
user.setClickCooldown(DEFAULT_ATTACK_COOLDOWN)
if(W.damtype == BRUTE || W.damtype == BURN)
@@ -147,8 +130,37 @@
user.visible_message("\The [user] forcefully strikes \the [src] with \the [W]!")
playsound(src.loc, hitsound, 100, 1)
take_damage(W.force*0.35) //it's a blast door, it should take a while. -Luke
- return
+ return
+ else if(istype(C, /obj/item/stack/material) && C.get_material_name() == "plasteel") // Repairing.
+ var/amt = Ceiling((maxhealth - health)/150)
+ if(!amt)
+ usr << "\The [src] is already fully repaired."
+ return
+ var/obj/item/stack/P = C
+ if(P.amount < amt)
+ usr << "You don't have enough sheets to repair this! You need at least [amt] sheets."
+ return
+ usr << "You begin repairing [src]..."
+ if(do_after(usr, 30))
+ if(P.use(amt))
+ usr << "You have repaired \The [src]"
+ src.repair()
+ else
+ usr << "You don't have enough sheets to repair this! You need at least [amt] sheets."
+
+ else if(src.density && (user.a_intent == I_HURT)) //If we can't pry it open and it's not a weapon.... Eh, let's attack it anyway.
+ var/obj/item/weapon/W = C
+ user.setClickCooldown(DEFAULT_ATTACK_COOLDOWN)
+ if(W.damtype == BRUTE || W.damtype == BURN)
+ user.do_attack_animation(src)
+ if(W.force < min_force) //No actual non-weapon item shouls have a force greater than the min_force, but let's include this just in case.
+ user.visible_message("\The [user] hits \the [src] with \the [W] with no visible effect.")
+ else
+ user.visible_message("\The [user] forcefully strikes \the [src] with \the [W]!")
+ playsound(src.loc, hitsound, 100, 1)
+ take_damage(W.force*0.15) //If the item isn't a weapon, let's make this take longer than usual to break it down.
+ return
// Proc: open()
// Parameters: None
@@ -213,4 +225,4 @@ obj/machinery/door/blast/regular/open
icon_state_opening = "shutterc0"
icon_state_closed = "shutter1"
icon_state_closing = "shutterc1"
- icon_state = "shutter1"
\ No newline at end of file
+ icon_state = "shutter1"
diff --git a/code/game/machinery/doors/door.dm b/code/game/machinery/doors/door.dm
index e1e7200d51..5f48ebeef4 100644
--- a/code/game/machinery/doors/door.dm
+++ b/code/game/machinery/doors/door.dm
@@ -243,8 +243,8 @@
var/obj/item/weapon/weldingtool/welder = I
if(welder.remove_fuel(0,user))
user << "You start to fix dents and weld \the [repairing] into place."
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
- if(do_after(user, 5 * repairing.amount) && welder && welder.isOn())
+ playsound(src, welder.usesound, 50, 1)
+ if(do_after(user, (5 * repairing.amount) * welder.toolspeed) && welder && welder.isOn())
user << "You finish repairing the damage to \the [src]."
health = between(health, health + repairing.amount*DOOR_REPAIR_AMOUNT, maxhealth)
update_icon()
@@ -254,7 +254,7 @@
if(repairing && istype(I, /obj/item/weapon/crowbar))
user << "You remove \the [repairing]."
- playsound(src.loc, 'sound/items/Crowbar.ogg', 100, 1)
+ playsound(src, I.usesound, 100, 1)
repairing.loc = user.loc
repairing = null
return
diff --git a/code/game/machinery/doors/firedoor.dm b/code/game/machinery/doors/firedoor.dm
index 6ccbb46ac1..8be3733c5c 100644
--- a/code/game/machinery/doors/firedoor.dm
+++ b/code/game/machinery/doors/firedoor.dm
@@ -198,12 +198,13 @@
user.visible_message("\The [user] [blocked ? "welds" : "unwelds"] \the [src] with \a [W].",\
"You [blocked ? "weld" : "unweld"] \the [src] with \the [W].",\
"You hear something being welded.")
- playsound(src, 'sound/items/Welder.ogg', 100, 1)
+ playsound(src, W.usesound, 100, 1)
update_icon()
return
if(density && istype(C, /obj/item/weapon/screwdriver))
hatch_open = !hatch_open
+ playsound(src, C.usesound, 50, 1)
user.visible_message("[user] has [hatch_open ? "opened" : "closed"] \the [src] maintenance hatch.",
"You have [hatch_open ? "opened" : "closed"] the [src] maintenance hatch.")
update_icon()
@@ -217,7 +218,7 @@
"You start to remove the electronics from [src].")
if(do_after(user,30))
if(blocked && density && hatch_open)
- playsound(src.loc, 'sound/items/Crowbar.ogg', 100, 1)
+ playsound(src, C.usesound, 50, 1)
user.visible_message("[user] has removed the electronics from \the [src].",
"You have removed the electronics from [src].")
@@ -262,8 +263,8 @@
"You hear metal strain.")
prying = 1
update_icon()
- playsound(src.loc, 'sound/items/Crowbar.ogg', 100, 1)
- if(do_after(user,30))
+ playsound(src, C.usesound, 100, 1)
+ if(do_after(user,30 * C.toolspeed))
if(istype(C, /obj/item/weapon/crowbar))
if(stat & (BROKEN|NOPOWER) || !density)
user.visible_message("\The [user] forces \the [src] [density ? "open" : "closed"] with \a [C]!",\
diff --git a/code/game/machinery/doors/firedoor_assembly.dm b/code/game/machinery/doors/firedoor_assembly.dm
index a96065d2c6..f30c2e6146 100644
--- a/code/game/machinery/doors/firedoor_assembly.dm
+++ b/code/game/machinery/doors/firedoor_assembly.dm
@@ -14,7 +14,7 @@ obj/structure/firedoor_assembly/update_icon()
else
icon_state = "door_construction"
-obj/structure/firedoor_assembly/attackby(C as obj, mob/user as mob)
+obj/structure/firedoor_assembly/attackby(obj/item/C, mob/user as mob)
if(istype(C, /obj/item/stack/cable_coil) && !wired && anchored)
var/obj/item/stack/cable_coil/cable = C
if (cable.get_amount() < 1)
@@ -27,7 +27,7 @@ obj/structure/firedoor_assembly/attackby(C as obj, mob/user as mob)
user << "You wire \the [src]."
else if(istype(C, /obj/item/weapon/wirecutters) && wired )
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 100, 1)
+ playsound(src.loc, C.usesound, 100, 1)
user.visible_message("[user] cuts the wires from \the [src].", "You start to cut the wires from \the [src].")
if(do_after(user, 40))
@@ -48,7 +48,7 @@ obj/structure/firedoor_assembly/attackby(C as obj, mob/user as mob)
user << "You must secure \the [src] first!"
else if(istype(C, /obj/item/weapon/wrench))
anchored = !anchored
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src.loc, C.usesound, 50, 1)
user.visible_message("[user] has [anchored ? "" : "un" ]secured \the [src]!",
"You have [anchored ? "" : "un" ]secured \the [src]!")
update_icon()
diff --git a/code/game/machinery/doors/windowdoor.dm b/code/game/machinery/doors/windowdoor.dm
index 32ad7a2aae..5449d3436b 100644
--- a/code/game/machinery/doors/windowdoor.dm
+++ b/code/game/machinery/doors/windowdoor.dm
@@ -193,9 +193,9 @@
//If it's opened/emagged, crowbar can pry it out of its frame.
if (!density && istype(I, /obj/item/weapon/crowbar))
- playsound(src.loc, 'sound/items/Crowbar.ogg', 100, 1)
+ playsound(src, I.usesound, 50, 1)
user.visible_message("[user] begins prying the windoor out of the frame.", "You start to pry the windoor out of the frame.")
- if (do_after(user,40))
+ if (do_after(user,40 * I.toolspeed))
to_chat(user,"You pried the windoor out of the frame!")
var/obj/structure/windoor_assembly/wa = new/obj/structure/windoor_assembly(src.loc)
diff --git a/code/game/machinery/floor_light.dm b/code/game/machinery/floor_light.dm
index 04c4b5452c..ef9f2a2421 100644
--- a/code/game/machinery/floor_light.dm
+++ b/code/game/machinery/floor_light.dm
@@ -31,8 +31,8 @@ var/list/floor_light_cache = list()
if(!WT.remove_fuel(0, user))
user << "\The [src] must be on to complete this task."
return
- playsound(src.loc, 'sound/items/Welder.ogg', 50, 1)
- if(!do_after(user, 20))
+ playsound(src.loc, WT.usesound, 50, 1)
+ if(!do_after(user, 20 * WT.toolspeed))
return
if(!src || !WT.isOn())
return
diff --git a/code/game/machinery/frame.dm b/code/game/machinery/frame.dm
index e91c791b35..c6b32d75db 100644
--- a/code/game/machinery/frame.dm
+++ b/code/game/machinery/frame.dm
@@ -258,8 +258,8 @@
if(istype(P, /obj/item/weapon/wrench))
if(state == 0 && !anchored)
user << "You start to wrench the frame into place."
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(src.loc, P.usesound, 50, 1)
+ if(do_after(user, 20 * P.toolspeed))
anchored = 1
if(!need_circuit && circuit)
state = 2
@@ -270,8 +270,8 @@
user << "You wrench the frame into place."
else if(state == 0 && anchored)
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(src, P.usesound, 50, 1)
+ if(do_after(user, 20 * P.toolspeed))
user << "You unfasten the frame."
anchored = 0
@@ -279,8 +279,8 @@
if(state == 0)
var/obj/item/weapon/weldingtool/WT = P
if(WT.remove_fuel(0, user))
- playsound(src.loc, 'sound/items/Welder.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(src.loc, P.usesound, 50, 1)
+ if(do_after(user, 20 * P.toolspeed))
if(src && WT.isOn())
user << "You deconstruct the frame."
new /obj/item/stack/material/steel(src.loc, frame_type.frame_size)
@@ -311,18 +311,18 @@
else if(istype(P, /obj/item/weapon/screwdriver))
if(state == 1)
if(need_circuit && circuit)
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You screw the circuit board into place."
state = 2
else if(state == 2)
if(need_circuit && circuit)
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You unfasten the circuit board."
state = 1
else if(!need_circuit && circuit)
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You unfasten the outer cover."
state = 0
@@ -334,7 +334,7 @@
component_check = 0
break
if(component_check)
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
var/obj/machinery/new_machine = new circuit.build_path(src.loc, dir)
// Handle machines that have allocated default parts in thier constructor.
if(new_machine.component_parts)
@@ -364,7 +364,7 @@
return
else if(frame_type.frame_class == "alarm")
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You fasten the cover."
var/obj/machinery/B = new circuit.build_path(src.loc)
B.pixel_x = pixel_x
@@ -378,7 +378,7 @@
else if(state == 4)
if(frame_type.frame_class == "computer")
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You connect the monitor."
var/obj/machinery/B = new circuit.build_path(src.loc)
B.pixel_x = pixel_x
@@ -391,7 +391,7 @@
return
else if(frame_type.frame_class == "display")
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You connect the monitor."
var/obj/machinery/B = new circuit.build_path(src.loc)
B.pixel_x = pixel_x
@@ -406,7 +406,7 @@
else if(istype(P, /obj/item/weapon/crowbar))
if(state == 1)
if(need_circuit && circuit)
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You remove the circuit board."
state = 0
circuit.forceMove(src.loc)
@@ -416,7 +416,7 @@
else if(state == 3)
if(frame_type.frame_class == "machine")
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
if(components.len == 0)
user << "There are no components to remove."
else
@@ -429,13 +429,13 @@
else if(state == 4)
if(frame_type.frame_class == "computer")
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You remove the glass panel."
state = 3
new /obj/item/stack/material/glass(src.loc, 2)
else if(frame_type.frame_class == "display")
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You remove the glass panel."
state = 3
new /obj/item/stack/material/glass(src.loc, 2)
@@ -483,25 +483,25 @@
else if(istype(P, /obj/item/weapon/wirecutters))
if(state == 3)
if(frame_type.frame_class == "computer")
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You remove the cables."
state = 2
new /obj/item/stack/cable_coil(src.loc, 5)
else if(frame_type.frame_class == "display")
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You remove the cables."
state = 2
new /obj/item/stack/cable_coil(src.loc, 5)
else if(frame_type.frame_class == "alarm")
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You remove the cables."
state = 2
new /obj/item/stack/cable_coil(src.loc, 5)
else if(frame_type.frame_class == "machine")
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(src, P.usesound, 50, 1)
user << "You remove the cables."
state = 2
new /obj/item/stack/cable_coil(src.loc, 5)
diff --git a/code/game/machinery/igniter.dm b/code/game/machinery/igniter.dm
index 97c430f9d0..1e67fb8b4f 100755
--- a/code/game/machinery/igniter.dm
+++ b/code/game/machinery/igniter.dm
@@ -74,6 +74,7 @@
if(istype(W, /obj/item/weapon/screwdriver))
add_fingerprint(user)
disable = !disable
+ playsound(src, W.usesound, 50, 1)
if(disable)
user.visible_message("[user] has disabled the [src]!", "You disable the connection to the [src].")
icon_state = "[base_state]-d"
diff --git a/code/game/machinery/iv_drip.dm b/code/game/machinery/iv_drip.dm
index e50688b7a9..306a098638 100644
--- a/code/game/machinery/iv_drip.dm
+++ b/code/game/machinery/iv_drip.dm
@@ -66,7 +66,7 @@
return
if(istype(W, /obj/item/weapon/screwdriver))
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You start to dismantle the IV drip."
if(do_after(user, 15))
user << "You dismantle the IV drip."
diff --git a/code/game/machinery/jukebox.dm b/code/game/machinery/jukebox.dm
index 9ee5a3f70b..47d302e7a8 100644
--- a/code/game/machinery/jukebox.dm
+++ b/code/game/machinery/jukebox.dm
@@ -127,7 +127,7 @@
if(istype(W, /obj/item/weapon/wrench))
user.visible_message("[user] has [anchored ? "un" : ""]secured \the [src].", "You [anchored ? "un" : ""]secure \the [src].")
anchored = !anchored
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
power_change()
update_icon()
if(!anchored)
@@ -186,7 +186,7 @@
var/newval = text2num(href_list["loopmode"])
loop_mode = sanitize_inlist(newval, list(JUKEMODE_NEXT, JUKEMODE_RANDOM, JUKEMODE_REPEAT_SONG, JUKEMODE_PLAY_ONCE), loop_mode)
else if(href_list["volume"])
- var/newval = input("Choose Jukebox volume (0-100%)", "Jukebox volume", round(volume * 100.0))
+ var/newval = input("Choose Jukebox volume (0-100%)", "Jukebox volume", round(volume * 100.0))
newval = sanitize_integer(text2num(newval), min = 0, max = 100, default = volume * 100.0)
volume = newval / 100.0
update_music() // To broadcast volume change without restarting song
@@ -270,6 +270,24 @@
new /obj/effect/decal/cleanable/blood/oil(src.loc)
qdel(src)
+/obj/machinery/media/jukebox/attackby(obj/item/W as obj, mob/user as mob)
+ src.add_fingerprint(user)
+
+ if(default_deconstruction_screwdriver(user, W))
+ return
+ if(default_deconstruction_crowbar(user, W))
+ return
+ if(istype(W, /obj/item/weapon/wrench))
+ if(playing)
+ StopPlaying()
+ user.visible_message("[user] has [anchored ? "un" : ""]secured \the [src].", "You [anchored ? "un" : ""]secure \the [src].")
+ anchored = !anchored
+ playsound(src, W.usesound, 50, 1)
+ power_change()
+ update_icon()
+ return
+ return ..()
+
/obj/machinery/media/jukebox/emag_act(var/remaining_charges, var/mob/user)
if(!emagged)
emagged = 1
diff --git a/code/game/machinery/kitchen/microwave.dm b/code/game/machinery/kitchen/microwave.dm
index a3b0f9fdd4..5fb948a2d8 100644
--- a/code/game/machinery/kitchen/microwave.dm
+++ b/code/game/machinery/kitchen/microwave.dm
@@ -67,7 +67,8 @@
"\The [user] starts to fix part of the microwave.", \
"You start to fix part of the microwave." \
)
- if (do_after(user,20))
+ playsound(src, O.usesound, 50, 1)
+ if (do_after(user,20 * O.toolspeed))
user.visible_message( \
"\The [user] fixes part of the microwave.", \
"You have fixed part of the microwave." \
@@ -78,7 +79,7 @@
"\The [user] starts to fix part of the microwave.", \
"You start to fix part of the microwave." \
)
- if (do_after(user,20))
+ if (do_after(user,20 * O.toolspeed))
user.visible_message( \
"\The [user] fixes the microwave.", \
"You have fixed the microwave." \
diff --git a/code/game/machinery/kitchen/smartfridge.dm b/code/game/machinery/kitchen/smartfridge.dm
index a18edbc5fa..5b78f81249 100644
--- a/code/game/machinery/kitchen/smartfridge.dm
+++ b/code/game/machinery/kitchen/smartfridge.dm
@@ -218,6 +218,7 @@
if(istype(O, /obj/item/weapon/screwdriver))
panel_open = !panel_open
user.visible_message("[user] [panel_open ? "opens" : "closes"] the maintenance panel of \the [src].", "You [panel_open ? "open" : "close"] the maintenance panel of \the [src].")
+ playsound(src, O.usesound, 50, 1)
overlays.Cut()
if(panel_open)
overlays += image(icon, icon_panel)
diff --git a/code/game/machinery/machinery.dm b/code/game/machinery/machinery.dm
index 6e9f31889d..f476c295e2 100644
--- a/code/game/machinery/machinery.dm
+++ b/code/game/machinery/machinery.dm
@@ -331,7 +331,7 @@ Class Procs:
/obj/machinery/proc/default_deconstruction_screwdriver(var/mob/user, var/obj/item/weapon/screwdriver/S)
if(!istype(S))
return 0
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src, S.usesound, 50, 1)
panel_open = !panel_open
user << "You [panel_open ? "open" : "close"] the maintenance hatch of [src]."
update_icon()
@@ -343,8 +343,8 @@ Class Procs:
if(!circuit)
return 0
user << "You start disconnecting the monitor."
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
- if(do_after(user, 20))
+ playsound(src, S.usesound, 50, 1)
+ if(do_after(user, 20 * S.toolspeed))
if(stat & BROKEN)
user << "The broken glass falls out."
new /obj/item/weapon/material/shard(src.loc)
@@ -355,7 +355,7 @@ Class Procs:
/obj/machinery/proc/alarm_deconstruction_screwdriver(var/mob/user, var/obj/item/weapon/screwdriver/S)
if(!istype(S))
return 0
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src, S.usesound, 50, 1)
panel_open = !panel_open
user << "The wires have been [panel_open ? "exposed" : "unexposed"]"
update_icon()
@@ -367,7 +367,7 @@ Class Procs:
if(!panel_open)
return 0
user.visible_message("[user] has cut the wires inside \the [src]!", "You have cut the wires inside \the [src].")
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(src.loc, W.usesound, 50, 1)
new/obj/item/stack/cable_coil(get_turf(src), 5)
. = dismantle()
diff --git a/code/game/machinery/navbeacon.dm b/code/game/machinery/navbeacon.dm
index 8700caf785..ac0af16378 100644
--- a/code/game/machinery/navbeacon.dm
+++ b/code/game/machinery/navbeacon.dm
@@ -75,7 +75,7 @@ var/global/list/navbeacons = list() // no I don't like putting this in, but it w
if(istype(I, /obj/item/weapon/screwdriver))
open = !open
-
+ playsound(src, I.usesound, 50, 1)
user.visible_message("[user] [open ? "opens" : "closes"] the beacon's cover.", "You [open ? "open" : "close"] the beacon's cover.")
updateicon()
diff --git a/code/game/machinery/nuclear_bomb.dm b/code/game/machinery/nuclear_bomb.dm
index ea5c78d734..018cf75f53 100644
--- a/code/game/machinery/nuclear_bomb.dm
+++ b/code/game/machinery/nuclear_bomb.dm
@@ -56,6 +56,7 @@ var/bomb_set
/obj/machinery/nuclearbomb/attackby(obj/item/weapon/O as obj, mob/user as mob)
if(istype(O, /obj/item/weapon/screwdriver))
+ playsound(src, O.usesound, 50, 1)
add_fingerprint(user)
if(auth)
if(opened == 0)
@@ -103,7 +104,7 @@ var/bomb_set
user.visible_message("[user] starts cutting loose the anchoring bolt covers on [src].", "You start cutting loose the anchoring bolt covers with [O]...")
- if(do_after(user,40))
+ if(do_after(user,40 * WT.toolspeed))
if(!src || !user || !WT.remove_fuel(5, user)) return
user.visible_message("[user] cuts through the bolt covers on [src].", "You cut through the bolt cover.")
removal_stage = 1
@@ -113,7 +114,8 @@ var/bomb_set
if(istype(O,/obj/item/weapon/crowbar))
user.visible_message("[user] starts forcing open the bolt covers on [src].", "You start forcing open the anchoring bolt covers with [O]...")
- if(do_after(user,15))
+ playsound(src, O.usesound, 50, 1)
+ if(do_after(user,15 * O.toolspeed))
if(!src || !user) return
user.visible_message("[user] forces open the bolt covers on [src].", "You force open the bolt covers.")
removal_stage = 2
@@ -129,8 +131,8 @@ var/bomb_set
return
user.visible_message("[user] starts cutting apart the anchoring system sealant on [src].", "You start cutting apart the anchoring system's sealant with [O]...")
-
- if(do_after(user,40))
+ playsound(src, WT.usesound, 50, 1)
+ if(do_after(user,40 * WT.toolspeed))
if(!src || !user || !WT.remove_fuel(5, user)) return
user.visible_message("[user] cuts apart the anchoring system sealant on [src].", "You cut apart the anchoring system's sealant.")
removal_stage = 3
@@ -140,8 +142,8 @@ var/bomb_set
if(istype(O,/obj/item/weapon/wrench))
user.visible_message("[user] begins unwrenching the anchoring bolts on [src].", "You begin unwrenching the anchoring bolts...")
-
- if(do_after(user,50))
+ playsound(src, O.usesound, 50, 1)
+ if(do_after(user,50 * O.toolspeed))
if(!src || !user) return
user.visible_message("[user] unwrenches the anchoring bolts on [src].", "You unwrench the anchoring bolts.")
removal_stage = 4
@@ -151,8 +153,8 @@ var/bomb_set
if(istype(O,/obj/item/weapon/crowbar))
user.visible_message("[user] begins lifting [src] off of the anchors.", "You begin lifting the device off the anchors...")
-
- if(do_after(user,80))
+ playsound(src, O.usesound, 50, 1)
+ if(do_after(user,80 * O.toolspeed))
if(!src || !user) return
user.visible_message("[user] crowbars [src] off of the anchors. It can now be moved.", "You jam the crowbar under the nuclear device and lift it off its anchors. You can now move it!")
anchored = 0
diff --git a/code/game/machinery/pipe/construction.dm b/code/game/machinery/pipe/construction.dm
index 06228dd86f..bd650755e5 100644
--- a/code/game/machinery/pipe/construction.dm
+++ b/code/game/machinery/pipe/construction.dm
@@ -1231,7 +1231,7 @@ Buildable meters
P.initialize()
P.build_network()
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user.visible_message( \
"[user] fastens the [src].", \
"You have fastened the [src].", \
@@ -1262,7 +1262,7 @@ Buildable meters
user << "You need to fasten it to a pipe"
return 1
new/obj/machinery/meter( src.loc )
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You have fastened the meter to the pipe"
qdel(src)
//not sure why these are necessary
diff --git a/code/game/machinery/pipe/pipe_dispenser.dm b/code/game/machinery/pipe/pipe_dispenser.dm
index 7727b675d2..a9c2813a58 100644
--- a/code/game/machinery/pipe/pipe_dispenser.dm
+++ b/code/game/machinery/pipe/pipe_dispenser.dm
@@ -110,9 +110,9 @@
return
else if (istype(W, /obj/item/weapon/wrench))
if (unwrenched==0)
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to unfasten \the [src] from the floor..."
- if (do_after(user, 40))
+ if (do_after(user, 40 * W.toolspeed))
user.visible_message( \
"[user] unfastens \the [src].", \
"You have unfastened \the [src]. Now it can be pulled somewhere else.", \
@@ -123,9 +123,9 @@
if (usr.machine==src)
usr << browse(null, "window=pipedispenser")
else /*if (unwrenched==1)*/
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
user << "You begin to fasten \the [src] to the floor..."
- if (do_after(user, 20))
+ if (do_after(user, 20 * W.toolspeed))
user.visible_message( \
"[user] fastens \the [src].", \
"You have fastened \the [src]. Now it can dispense pipes.", \
diff --git a/code/game/machinery/portable_turret.dm b/code/game/machinery/portable_turret.dm
index 6d7a6f82a7..096bd090c1 100644
--- a/code/game/machinery/portable_turret.dm
+++ b/code/game/machinery/portable_turret.dm
@@ -329,15 +329,15 @@ var/list/turret_icons
)
wrenching = 1
- if(do_after(user, 50))
+ if(do_after(user, 50 * I.toolspeed))
//This code handles moving the turret around. After all, it's a portable turret!
if(!anchored)
- playsound(loc, 'sound/items/Ratchet.ogg', 100, 1)
+ playsound(loc, I.usesound, 100, 1)
anchored = 1
update_icon()
user << "You secure the exterior bolts on the turret."
else if(anchored)
- playsound(loc, 'sound/items/Ratchet.ogg', 100, 1)
+ playsound(loc, I.usesound, 100, 1)
anchored = 0
user << "You unsecure the exterior bolts on the turret."
update_icon()
@@ -711,14 +711,14 @@ var/list/turret_icons
switch(build_step)
if(0) //first step
if(istype(I, /obj/item/weapon/wrench) && !anchored)
- playsound(loc, 'sound/items/Ratchet.ogg', 100, 1)
+ playsound(loc, I.usesound, 100, 1)
user << "You secure the external bolts."
anchored = 1
build_step = 1
return
else if(istype(I, /obj/item/weapon/crowbar) && !anchored)
- playsound(loc, 'sound/items/Crowbar.ogg', 75, 1)
+ playsound(loc, I.usesound, 75, 1)
user << "You dismantle the turret construction."
new /obj/item/stack/material/steel(loc, 5)
qdel(src)
@@ -736,7 +736,7 @@ var/list/turret_icons
return
else if(istype(I, /obj/item/weapon/wrench))
- playsound(loc, 'sound/items/Ratchet.ogg', 75, 1)
+ playsound(loc, I.usesound, 75, 1)
user << "You unfasten the external bolts."
anchored = 0
build_step = 0
@@ -744,7 +744,7 @@ var/list/turret_icons
if(2)
if(istype(I, /obj/item/weapon/wrench))
- playsound(loc, 'sound/items/Ratchet.ogg', 100, 1)
+ playsound(loc, I.usesound, 100, 1)
user << "You bolt the metal armor into place."
build_step = 3
return
@@ -757,8 +757,8 @@ var/list/turret_icons
user << "You need more fuel to complete this task."
return
- playsound(loc, pick('sound/items/Welder.ogg', 'sound/items/Welder2.ogg'), 50, 1)
- if(do_after(user, 20))
+ playsound(loc, I.usesound, 50, 1)
+ if(do_after(user, 20 * I.toolspeed))
if(!src || !WT.remove_fuel(5, user)) return
build_step = 1
user << "You remove the turret's interior metal armor."
@@ -784,7 +784,7 @@ var/list/turret_icons
return
else if(istype(I, /obj/item/weapon/wrench))
- playsound(loc, 'sound/items/Ratchet.ogg', 100, 1)
+ playsound(loc, I.usesound, 100, 1)
user << "You remove the turret's metal armor bolts."
build_step = 2
return
@@ -803,7 +803,7 @@ var/list/turret_icons
if(5)
if(istype(I, /obj/item/weapon/screwdriver))
- playsound(loc, 'sound/items/Screwdriver.ogg', 100, 1)
+ playsound(loc, I.usesound, 100, 1)
build_step = 6
user << "You close the internal access hatch."
return
@@ -821,7 +821,7 @@ var/list/turret_icons
return
else if(istype(I, /obj/item/weapon/screwdriver))
- playsound(loc, 'sound/items/Screwdriver.ogg', 100, 1)
+ playsound(loc, I.usesound, 100, 1)
build_step = 5
user << "You open the internal access hatch."
return
@@ -833,8 +833,8 @@ var/list/turret_icons
if(WT.get_fuel() < 5)
user << "You need more fuel to complete this task."
- playsound(loc, pick('sound/items/Welder.ogg', 'sound/items/Welder2.ogg'), 50, 1)
- if(do_after(user, 30))
+ playsound(loc, WT.usesound, 50, 1)
+ if(do_after(user, 30 * WT.toolspeed))
if(!src || !WT.remove_fuel(5, user))
return
build_step = 8
@@ -851,7 +851,7 @@ var/list/turret_icons
qdel(src) // qdel
else if(istype(I, /obj/item/weapon/crowbar))
- playsound(loc, 'sound/items/Crowbar.ogg', 75, 1)
+ playsound(loc, I.usesound, 75, 1)
user << "You pry off the turret's exterior armor."
new /obj/item/stack/material/steel(loc, 2)
build_step = 6
diff --git a/code/game/machinery/recharger.dm b/code/game/machinery/recharger.dm
index 44a112cab5..5c57b81ecb 100644
--- a/code/game/machinery/recharger.dm
+++ b/code/game/machinery/recharger.dm
@@ -81,7 +81,7 @@ obj/machinery/recharger
return
anchored = !anchored
to_chat(user, "You [anchored ? "attached" : "detached"] the recharger.")
- playsound(loc, 'sound/items/Ratchet.ogg', 75, 1)
+ playsound(loc, G.usesound, 75, 1)
else if(default_deconstruction_screwdriver(user, G))
return
else if(default_deconstruction_crowbar(user, G))
@@ -200,6 +200,17 @@ obj/machinery/recharger
return
//VOREStation Add End
+ if(istype(charging, /obj/item/weapon/weldingtool/electric))
+ var/obj/item/weapon/weldingtool/electric/C = charging
+ if(!C.power_supply.fully_charged())
+ icon_state = icon_state_charging
+ C.power_supply.give(active_power_usage*CELLRATE)
+ update_use_power(2)
+ else
+ icon_state = icon_state_charged
+ update_use_power(1)
+ return
+
/obj/machinery/recharger/emp_act(severity)
if(stat & (NOPOWER|BROKEN) || !anchored)
..(severity)
diff --git a/code/game/machinery/spaceheater.dm b/code/game/machinery/spaceheater.dm
index d60d49b47e..830c5f8d6d 100644
--- a/code/game/machinery/spaceheater.dm
+++ b/code/game/machinery/spaceheater.dm
@@ -68,6 +68,7 @@
return
else if(istype(I, /obj/item/weapon/screwdriver))
panel_open = !panel_open
+ playsound(src, I.usesound, 50, 1)
user.visible_message("[user] [panel_open ? "opens" : "closes"] the hatch on the [src].", "You [panel_open ? "open" : "close"] the hatch on the [src].")
update_icon()
if(!panel_open && user.machine == src)
diff --git a/code/game/machinery/suit_storage_unit.dm b/code/game/machinery/suit_storage_unit.dm
index 376f4f9d8a..9d048e1c94 100644
--- a/code/game/machinery/suit_storage_unit.dm
+++ b/code/game/machinery/suit_storage_unit.dm
@@ -473,7 +473,7 @@
return
if(istype(I, /obj/item/weapon/screwdriver))
panelopen = !panelopen
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 100, 1)
+ playsound(src, I.usesound, 100, 1)
user << text("You [] the unit's maintenance panel.",(panelopen ? "open up" : "close"))
updateUsrDialog()
return
@@ -692,6 +692,7 @@
else if(istype(I,/obj/item/weapon/screwdriver))
panel_open = !panel_open
+ playsound(src, I.usesound, 50, 1)
user << "You [panel_open ? "open" : "close"] the maintenance panel."
updateUsrDialog()
return
diff --git a/code/game/machinery/supplybeacon.dm b/code/game/machinery/supplybeacon.dm
index fd69e4f50e..3441b09cbb 100644
--- a/code/game/machinery/supplybeacon.dm
+++ b/code/game/machinery/supplybeacon.dm
@@ -51,7 +51,7 @@
return
anchored = !anchored
user.visible_message("\The [user] [anchored ? "secures" : "unsecures"] \the [src].")
- playsound(src.loc, 'sound/items/Ratchet.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
return
return ..()
diff --git a/code/game/machinery/syndicatebeacon.dm b/code/game/machinery/syndicatebeacon.dm
index 2f53931312..442703a42e 100644
--- a/code/game/machinery/syndicatebeacon.dm
+++ b/code/game/machinery/syndicatebeacon.dm
@@ -126,6 +126,7 @@
if(anchored)
anchored = 0
user << "You unscrew the beacon from the floor."
+ playsound(src, W.usesound, 50, 1)
disconnect_from_network()
return
else
@@ -134,6 +135,7 @@
return
anchored = 1
user << "You screw the beacon to the floor and attach the cable."
+ playsound(src, W.usesound, 50, 1)
return
..()
return
diff --git a/code/game/machinery/telecomms/broadcaster.dm b/code/game/machinery/telecomms/broadcaster.dm
index 9838d80722..27a03eb410 100644
--- a/code/game/machinery/telecomms/broadcaster.dm
+++ b/code/game/machinery/telecomms/broadcaster.dm
@@ -138,6 +138,10 @@ var/message_delay = 0 // To make sure restarting the recentmessages list is kept
if(original)
original.data["done"] = 1
+ // For some reason level is both used as a list and not a list, and now it needs to be a list.
+ // Because this is a 'all in one' machine, we're gonna just cheat.
+ signal.data["level"] = using_map.contact_levels.Copy()
+
if(signal.data["slow"] > 0)
sleep(signal.data["slow"]) // simulate the network lag if necessary
diff --git a/code/game/machinery/telecomms/machine_interactions.dm b/code/game/machinery/telecomms/machine_interactions.dm
index 002da7bc53..208b9d51e8 100644
--- a/code/game/machinery/telecomms/machine_interactions.dm
+++ b/code/game/machinery/telecomms/machine_interactions.dm
@@ -38,24 +38,24 @@
if(0)
if(istype(P, /obj/item/weapon/screwdriver))
user << "You unfasten the bolts."
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
construct_op ++
if(1)
if(istype(P, /obj/item/weapon/screwdriver))
user << "You fasten the bolts."
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
construct_op --
if(istype(P, /obj/item/weapon/wrench))
user << "You dislodge the external plating."
- playsound(src.loc, 'sound/items/Ratchet.ogg', 75, 1)
+ playsound(src.loc, P.usesound, 75, 1)
construct_op ++
if(2)
if(istype(P, /obj/item/weapon/wrench))
user << "You secure the external plating."
- playsound(src.loc, 'sound/items/Ratchet.ogg', 75, 1)
+ playsound(src.loc, P.usesound, 75, 1)
construct_op --
if(istype(P, /obj/item/weapon/wirecutters))
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(src.loc, P.usesound, 50, 1)
user << "You remove the cables."
construct_op ++
var/obj/item/stack/cable_coil/A = new /obj/item/stack/cable_coil( user.loc )
@@ -72,8 +72,8 @@
user << "You need five coils of wire for this."
if(istype(P, /obj/item/weapon/crowbar))
user << "You begin prying out the circuit board other components..."
- playsound(src.loc, 'sound/items/Crowbar.ogg', 50, 1)
- if(do_after(user,60))
+ playsound(src.loc, P.usesound, 50, 1)
+ if(do_after(user,60 * P.toolspeed))
user << "You finish prying out the components."
// Drop all the component stuff
@@ -168,6 +168,7 @@
dat += "
MULTITOOL BUFFER: [P.buffer] ([P.buffer.id]) \[Link\] \[Flush\]"
else
dat += "
MULTITOOL BUFFER: \[Add Machine\]"
+ P.update_icon()
dat += ""
temp = ""
diff --git a/code/game/machinery/telecomms/presets.dm b/code/game/machinery/telecomms/presets.dm
index f997c14073..d2ef8b1fec 100644
--- a/code/game/machinery/telecomms/presets.dm
+++ b/code/game/machinery/telecomms/presets.dm
@@ -48,7 +48,7 @@
network = "tcommsat"
produces_heat = 0
autolinkers = list("hub_cent", "c_relay", "s_relay", "m_relay", "r_relay", "hb_relay",
- "centcomm", "receiverCent", "broadcasterCent") //VOREStation Edit - Added "hb_relay"
+ "centcom", "receiverCent", "broadcasterCent") //VOREStation Edit - Added "hb_relay"
//Receivers
@@ -110,7 +110,7 @@
network = "tcommsat"
freq_listening = list(ERT_FREQ, DTH_FREQ)
produces_heat = 0
- autolinkers = list("processorCent", "centcomm")
+ autolinkers = list("processorCent", "centcom")
//Processors
@@ -203,7 +203,7 @@
id = "CentCom Server"
freq_listening = list(ERT_FREQ, DTH_FREQ)
produces_heat = 0
- autolinkers = list("centcomm")
+ autolinkers = list("centcom")
//Broadcasters
diff --git a/code/game/machinery/vending.dm b/code/game/machinery/vending.dm
index b18284fab8..c0f8d05127 100644
--- a/code/game/machinery/vending.dm
+++ b/code/game/machinery/vending.dm
@@ -183,6 +183,7 @@
else if(istype(W, /obj/item/weapon/screwdriver))
panel_open = !panel_open
user << "You [panel_open ? "open" : "close"] the maintenance panel."
+ playsound(src, W.usesound, 50, 1)
overlays.Cut()
if(panel_open)
overlays += image(icon, "[initial(icon_state)]-panel")
@@ -202,13 +203,13 @@
nanomanager.update_uis(src)
return
else if(istype(W, /obj/item/weapon/wrench))
- playsound(loc, 'sound/items/Ratchet.ogg', 100, 1)
+ playsound(src, W.usesound, 100, 1)
if(anchored)
user.visible_message("[user] begins unsecuring \the [src] from the floor.", "You start unsecuring \the [src] from the floor.")
else
user.visible_message("[user] begins securing \the [src] to the floor.", "You start securing \the [src] to the floor.")
- if(do_after(user, 20))
+ if(do_after(user, 20 * W.toolspeed))
if(!src) return
user << "You [anchored? "un" : ""]secured \the [src]!"
anchored = !anchored
@@ -692,6 +693,7 @@
/obj/item/weapon/reagent_containers/food/drinks/bottle/kahlua = 5,
/obj/item/weapon/reagent_containers/food/drinks/bottle/melonliquor = 5,
/obj/item/weapon/reagent_containers/food/drinks/bottle/rum = 5,
+ /obj/item/weapon/reagent_containers/food/drinks/bottle/sake = 5,
/obj/item/weapon/reagent_containers/food/drinks/bottle/specialwhiskey = 5,
/obj/item/weapon/reagent_containers/food/drinks/bottle/tequilla = 5,
/obj/item/weapon/reagent_containers/food/drinks/bottle/vermouth = 5,
@@ -711,6 +713,7 @@
/obj/item/weapon/reagent_containers/food/drinks/bottle/space_mountain_wind = 5,
/obj/item/weapon/reagent_containers/food/drinks/cans/sodawater = 15,
/obj/item/weapon/reagent_containers/food/drinks/cans/tonic = 15,
+ /obj/item/weapon/reagent_containers/food/drinks/cans/gingerale = 15,
/obj/item/weapon/reagent_containers/food/drinks/flask/barflask = 5,
/obj/item/weapon/reagent_containers/food/drinks/flask/vacuumflask = 5,
/obj/item/weapon/reagent_containers/food/drinks/ice = 10,
@@ -768,12 +771,14 @@
products = list(/obj/item/weapon/reagent_containers/food/drinks/cans/cola = 10,/obj/item/weapon/reagent_containers/food/drinks/cans/space_mountain_wind = 10,
/obj/item/weapon/reagent_containers/food/drinks/cans/dr_gibb = 10,/obj/item/weapon/reagent_containers/food/drinks/cans/starkist = 10,
/obj/item/weapon/reagent_containers/food/drinks/cans/waterbottle = 10,/obj/item/weapon/reagent_containers/food/drinks/cans/space_up = 10,
- /obj/item/weapon/reagent_containers/food/drinks/cans/iced_tea = 10, /obj/item/weapon/reagent_containers/food/drinks/cans/grape_juice = 10)
+ /obj/item/weapon/reagent_containers/food/drinks/cans/iced_tea = 10, /obj/item/weapon/reagent_containers/food/drinks/cans/grape_juice = 10,
+ /obj/item/weapon/reagent_containers/food/drinks/cans/gingerale = 10)
contraband = list(/obj/item/weapon/reagent_containers/food/drinks/cans/thirteenloko = 5, /obj/item/weapon/reagent_containers/food/snacks/liquidfood = 6)
prices = list(/obj/item/weapon/reagent_containers/food/drinks/cans/cola = 1,/obj/item/weapon/reagent_containers/food/drinks/cans/space_mountain_wind = 1,
/obj/item/weapon/reagent_containers/food/drinks/cans/dr_gibb = 1,/obj/item/weapon/reagent_containers/food/drinks/cans/starkist = 1,
/obj/item/weapon/reagent_containers/food/drinks/cans/waterbottle = 2,/obj/item/weapon/reagent_containers/food/drinks/cans/space_up = 1,
- /obj/item/weapon/reagent_containers/food/drinks/cans/iced_tea = 1,/obj/item/weapon/reagent_containers/food/drinks/cans/grape_juice = 1)
+ /obj/item/weapon/reagent_containers/food/drinks/cans/iced_tea = 1,/obj/item/weapon/reagent_containers/food/drinks/cans/grape_juice = 1,
+ /obj/item/weapon/reagent_containers/food/drinks/cans/gingerale = 1)
idle_power_usage = 211 //refrigerator - believe it or not, this is actually the average power consumption of a refrigerated vending machine according to NRCan.
/obj/machinery/vending/fitness
diff --git a/code/game/objects/effects/decals/contraband.dm b/code/game/objects/effects/decals/contraband.dm
index cd3618c936..0d00d32830 100644
--- a/code/game/objects/effects/decals/contraband.dm
+++ b/code/game/objects/effects/decals/contraband.dm
@@ -122,7 +122,7 @@
/obj/structure/sign/poster/attackby(obj/item/weapon/W as obj, mob/user as mob)
if(istype(W, /obj/item/weapon/wirecutters))
- playsound(loc, 'sound/items/Wirecutter.ogg', 100, 1)
+ playsound(src.loc, W.usesound, 100, 1)
if(ruined)
user << "You remove the remnants of the poster."
qdel(src)
diff --git a/code/game/objects/effects/spawners/bombspawner.dm b/code/game/objects/effects/spawners/bombspawner.dm
index fb4716043f..7f2f509d01 100644
--- a/code/game/objects/effects/spawners/bombspawner.dm
+++ b/code/game/objects/effects/spawners/bombspawner.dm
@@ -111,15 +111,15 @@
set name = "Instant TTV"
if(!check_rights(R_SPAWN)) return
-
+
var/obj/effect/spawner/newbomb/proto = /obj/effect/spawner/newbomb/radio/custom
-
+
var/p = input("Enter phoron amount (mol):","Phoron", initial(proto.phoron_amt)) as num|null
if(p == null) return
-
+
var/o = input("Enter oxygen amount (mol):","Oxygen", initial(proto.oxygen_amt)) as num|null
if(o == null) return
-
+
var/c = input("Enter carbon dioxide amount (mol):","Carbon Dioxide", initial(proto.carbon_amt)) as num|null
if(c == null) return
@@ -129,13 +129,13 @@
name = "TTV bomb"
icon = 'icons/mob/screen1.dmi'
icon_state = "x"
-
+
var/assembly_type = /obj/item/device/assembly/signaler
-
+
//Note that the maximum amount of gas you can put in a 70L air tank at 1013.25 kPa and 519K is 16.44 mol.
- var/phoron_amt = 10.96
- var/oxygen_amt = 16.44
- var/carbon_amt = 0.0
+ var/phoron_amt = 12
+ var/oxygen_amt = 18
+ var/carbon_amt = 0
/obj/effect/spawner/newbomb/timer
name = "TTV bomb - timer"
@@ -144,8 +144,8 @@
/obj/effect/spawner/newbomb/timer/syndicate
name = "TTV bomb - merc"
//High yield bombs. Yes, it is possible to make these with toxins
- phoron_amt = 15.66
- oxygen_amt = 24.66
+ phoron_amt = 18.5
+ oxygen_amt = 28.5
/obj/effect/spawner/newbomb/proximity
name = "TTV bomb - proximity"
@@ -170,15 +170,20 @@
PT.master = V
OT.master = V
- PT.air_contents.temperature = PHORON_FLASHPOINT
+ PT.valve_welded = 1
PT.air_contents.gas["phoron"] = phoron_amt
PT.air_contents.gas["carbon_dioxide"] = carbon_amt
+ PT.air_contents.total_moles = phoron_amt + carbon_amt
+ PT.air_contents.temperature = PHORON_MINIMUM_BURN_TEMPERATURE+1
PT.air_contents.update_values()
- OT.air_contents.temperature = PHORON_FLASHPOINT
+ OT.valve_welded = 1
OT.air_contents.gas["oxygen"] = oxygen_amt
+ OT.air_contents.total_moles = oxygen_amt
+ OT.air_contents.temperature = PHORON_MINIMUM_BURN_TEMPERATURE+1
OT.air_contents.update_values()
+
var/obj/item/device/assembly/S = new assembly_type(V)
@@ -190,3 +195,62 @@
V.update_icon()
qdel(src)
+
+
+
+///////////////////////
+//One Tank Bombs, WOOOOOOO! -Luke
+///////////////////////
+
+/obj/effect/spawner/onetankbomb
+ name = "Single-tank bomb"
+ icon = 'icons/mob/screen1.dmi'
+ icon_state = "x"
+
+// var/assembly_type = /obj/item/device/assembly/signaler
+
+ //Note that the maximum amount of gas you can put in a 70L air tank at 1013.25 kPa and 519K is 16.44 mol.
+ var/phoron_amt = 0
+ var/oxygen_amt = 0
+
+/obj/effect/spawner/onetankbomb/New(newloc) //just needs an assembly.
+ ..(newloc)
+
+ var/type = pick(/obj/item/weapon/tank/phoron/onetankbomb, /obj/item/weapon/tank/oxygen/onetankbomb)
+ new type(src.loc)
+
+ qdel(src)
+
+/obj/effect/spawner/onetankbomb/full
+ name = "Single-tank bomb"
+ icon = 'icons/mob/screen1.dmi'
+ icon_state = "x"
+
+// var/assembly_type = /obj/item/device/assembly/signaler
+
+ //Note that the maximum amount of gas you can put in a 70L air tank at 1013.25 kPa and 519K is 16.44 mol.
+/obj/effect/spawner/onetankbomb/full/New(newloc) //just needs an assembly.
+ ..(newloc)
+
+ var/type = pick(/obj/item/weapon/tank/phoron/onetankbomb/full, /obj/item/weapon/tank/oxygen/onetankbomb/full)
+ new type(src.loc)
+
+ qdel(src)
+
+/obj/effect/spawner/onetankbomb/frag
+ name = "Single-tank bomb"
+ icon = 'icons/mob/screen1.dmi'
+ icon_state = "x"
+
+// var/assembly_type = /obj/item/device/assembly/signaler
+
+ //Note that the maximum amount of gas you can put in a 70L air tank at 1013.25 kPa and 519K is 16.44 mol.
+/obj/effect/spawner/onetankbomb/full/New(newloc) //just needs an assembly.
+ ..(newloc)
+
+ var/type = pick(/obj/item/weapon/tank/phoron/onetankbomb/full, /obj/item/weapon/tank/oxygen/onetankbomb/full)
+ new type(src.loc)
+
+ qdel(src)
+
+
diff --git a/code/game/objects/effects/spiders.dm b/code/game/objects/effects/spiders.dm
index c38b07f402..9ab835b806 100644
--- a/code/game/objects/effects/spiders.dm
+++ b/code/game/objects/effects/spiders.dm
@@ -35,7 +35,7 @@
if(WT.remove_fuel(0, user))
damage = 15
- playsound(loc, 'sound/items/Welder.ogg', 100, 1)
+ playsound(src, W.usesound, 100, 1)
health -= damage
healthcheck()
diff --git a/code/game/objects/items.dm b/code/game/objects/items.dm
index de91b79d60..4ca9703301 100644
--- a/code/game/objects/items.dm
+++ b/code/game/objects/items.dm
@@ -10,6 +10,7 @@
var/burn_point = null
var/burning = null
var/hitsound = null
+ var/usesound = null // Like hitsound, but for when used properly and not to kill someone.
var/storage_cost = null
var/slot_flags = 0 //This is used to determine on which slots an item can fit.
var/no_attack_log = 0 //If it's an item we don't want to log attack_logs with, set this to 1
@@ -78,6 +79,8 @@
// Works similarly to worn sprite_sheets, except the alternate sprites are used when the clothing/refit_for_species() proc is called.
var/list/sprite_sheets_obj = list()
+ var/toolspeed = 1.0 // This is a multipler on how 'fast' a tool works. e.g. setting this to 0.5 will make the tool work twice as fast.
+
/obj/item/New()
..()
if(embed_chance < 0)
@@ -446,7 +449,7 @@ var/list/global/slot_flags_enumeration = list(
if(!hit_zone)
U.do_attack_animation(M)
playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
- visible_message("\red [U] attempts to stab [M] in the eyes, but misses!")
+ visible_message("[U] attempts to stab [M] in the eyes, but misses!")
return
user.attack_log += "\[[time_stamp()]\] Attacked [M.name] ([M.ckey]) with [src.name] (INTENT: [uppertext(user.a_intent)])"
diff --git a/code/game/objects/items/devices/ai_detector.dm b/code/game/objects/items/devices/ai_detector.dm
new file mode 100644
index 0000000000..7fa6f74521
--- /dev/null
+++ b/code/game/objects/items/devices/ai_detector.dm
@@ -0,0 +1,121 @@
+#define PROXIMITY_OFF_CAMERANET "_no_camera"
+#define PROXIMITY_NONE ""
+#define PROXIMITY_NEAR "_yellow"
+#define PROXIMITY_ON_SCREEN "_red"
+#define PROXIMITY_TRACKING "_tracking"
+#define PROXIMITY_TRACKING_FAIL "_tracking_fail"
+
+// This is another syndie-multitool, except this one detects when the AI and/or Security is peeping on the holder.
+
+/obj/item/device/multitool/ai_detector
+ var/range_alert = 7 // Will turn red if the AI can observe its holder.
+ var/range_warning = 14 // Will turn yellow if the AI's eye is near the holder.
+ var/detect_state = PROXIMITY_NONE
+ origin_tech = list(TECH_MAGNET = 2, TECH_ENGINEERING = 2, TECH_ILLEGAL = 2)
+
+/obj/item/device/multitool/ai_detector/New()
+ // It's really really unlikely for the view range to change. But why not be futureproof anyways?
+ range_alert = world.view
+ range_warning = world.view * 2
+ processing_objects += src
+ ..()
+
+/obj/item/device/multitool/ai_detector/Destroy()
+ processing_objects -= src
+ return ..()
+
+/obj/item/device/multitool/ai_detector/process()
+ var/old_detect_state = detect_state
+ var/new_detect_state = detect_ai()
+ detect_state = new_detect_state
+ update_icon()
+ update_warning(old_detect_state, new_detect_state)
+ return
+
+// This also detects security using cameras.
+/obj/item/device/multitool/ai_detector/proc/detect_ai()
+ var/mob/living/carrier = isliving(loc) ? loc : null
+
+ // First, let's check if any AIs are actively tracking them.
+ for(var/mob/living/silicon/ai/AI in silicon_mob_list)
+ if(carrier && AI.cameraFollow == carrier)
+ if(!carrier.tracking_status()) // Successful tracking returns a 0, so we need to invert it.
+ return PROXIMITY_TRACKING
+ else
+ return PROXIMITY_TRACKING_FAIL
+
+ // If there's no turf then cameras won't do anything anyways.
+ var/turf/T = get_turf(src)
+ if(!T)
+ return PROXIMITY_OFF_CAMERANET
+
+ // Security is also a concern, so we need to see if any cameras are in use.
+ // Note that this will trigger upon the security console being used, regardless if someone is actually watching,
+ // because there isn't a nice way to test if someone is actually looking. Probably better that way too.
+ var/list/our_local_area = range(range_alert, T)
+ for(var/obj/machinery/camera/C in our_local_area)
+ if(C.camera_computers_using_this.len) // Only check cameras actively being used.
+ var/list/their_local_area = C.can_see(range_alert)
+ if(T in their_local_area)
+ return PROXIMITY_ON_SCREEN
+
+ // Now for the somewhat harder AI cameranet checks.
+
+ // Check if we are even on the cameranet.
+ if(!cameranet.checkVis(T))
+ return PROXIMITY_OFF_CAMERANET
+
+ var/datum/chunk/chunk = cameranet.getChunk(T.x, T.y, T.z)
+ if(!chunk)
+ return PROXIMITY_OFF_CAMERANET
+
+ // Check if the AI eye is able to see us, or if it's almost able to.
+ if(chunk.seenby.len)
+ for(var/mob/observer/eye/aiEye/A in chunk.seenby)
+ var/turf/detect_turf = get_turf(A)
+ if(get_dist(T, detect_turf) <= range_alert)
+ return PROXIMITY_ON_SCREEN
+ if(get_dist(T, detect_turf) <= range_warning)
+ return PROXIMITY_NEAR
+
+ // If we reach this point, AI or sec isn't near us.
+ return PROXIMITY_NONE
+
+/obj/item/device/multitool/ai_detector/update_icon()
+ icon_state = "[initial(icon_state)][detect_state]"
+
+/obj/item/device/multitool/ai_detector/proc/update_warning(var/old_state, var/new_state)
+ var/mob/living/carrier = isliving(loc) ? loc : null
+
+ // Now to warn our holder, if the state changes.
+ if(!carrier)
+ return
+
+ if(new_state != old_state)
+ switch(new_state)
+ if(PROXIMITY_OFF_CAMERANET)
+ to_chat(carrier, "\icon[src] Now outside of camera network.")
+ carrier << 'sound/machines/defib_failed.ogg'
+ if(PROXIMITY_NONE)
+ to_chat(carrier, "\icon[src] Now within camera network, AI and cameras unfocused.")
+ carrier << 'sound/machines/defib_safetyOff.ogg'
+ if(PROXIMITY_NEAR)
+ to_chat(carrier, "\icon[src] Warning: AI focus at nearby location.")
+ carrier << 'sound/machines/defib_SafetyOn.ogg'
+ if(PROXIMITY_ON_SCREEN)
+ to_chat(carrier, "\icon[src] Alert: AI or camera focused at current location!")
+ carrier <<'sound/machines/defib_ready.ogg'
+ if(PROXIMITY_TRACKING)
+ to_chat(carrier, "\icon[src] Danger: AI is actively tracking you!")
+ carrier << 'sound/machines/defib_success.ogg'
+ if(PROXIMITY_TRACKING_FAIL)
+ to_chat(carrier, "\icon[src] Danger: AI is attempting to actively track you, but you are outside of the camera network!")
+ carrier <<'sound/machines/defib_ready.ogg'
+
+
+#undef PROXIMITY_OFF_CAMERANET
+#undef PROXIMITY_NONE
+#undef PROXIMITY_NEAR
+#undef PROXIMITY_ON_SCREEN
+#undef PROXIMITY_TRACKING
+#undef PROXIMITY_TRACKING_FAIL
\ No newline at end of file
diff --git a/code/game/objects/items/devices/aicard.dm b/code/game/objects/items/devices/aicard.dm
index c609d38c4a..5a7a028054 100644
--- a/code/game/objects/items/devices/aicard.dm
+++ b/code/game/objects/items/devices/aicard.dm
@@ -1,9 +1,10 @@
/obj/item/device/aicard
- name = "inteliCard"
+ name = "intelliCore"
+ desc = "Used to preserve and transport an AI."
icon = 'icons/obj/pda.dmi'
icon_state = "aicard" // aicard-full
item_state = "aicard"
- w_class = ITEMSIZE_SMALL
+ w_class = ITEMSIZE_NORMAL
slot_flags = SLOT_BELT
show_messages = 0
@@ -57,12 +58,12 @@
var/user = usr
if (href_list["wipe"])
- var/confirm = alert("Are you sure you want to wipe this card's memory? This cannot be undone once started.", "Confirm Wipe", "Yes", "No")
+ var/confirm = alert("Are you sure you want to disable this core's power? This cannot be undone once started.", "Confirm Shutdown", "Yes", "No")
if(confirm == "Yes" && (CanUseTopic(user, state) == STATUS_INTERACTIVE))
- admin_attack_log(user, carded_ai, "Wiped using \the [src.name]", "Was wiped with \the [src.name]", "used \the [src.name] to wipe")
+ admin_attack_log(user, carded_ai, "Purged using \the [src.name]", "Was purged with \the [src.name]", "used \the [src.name] to purge")
flush = 1
carded_ai.suiciding = 1
- carded_ai << "Your core files are being wiped!"
+ carded_ai << "Your power has been disabled!"
while (carded_ai && carded_ai.stat != 2)
carded_ai.adjustOxyLoss(2)
carded_ai.updatehealth()
@@ -93,22 +94,22 @@
/obj/item/device/aicard/proc/grab_ai(var/mob/living/silicon/ai/ai, var/mob/living/user)
if(!ai.client)
- user << "ERROR: AI [ai.name] is offline. Unable to download."
+ user << "ERROR: AI [ai.name] is offline. Unable to transfer."
return 0
if(carded_ai)
- user << "Transfer failed: Existing AI found on remote terminal. Remove existing AI to install a new one."
+ user << "Transfer failed: Existing AI found on remote device. Remove existing AI to install a new one."
return 0
- user.visible_message("\The [user] starts downloading \the [ai] into \the [src]...", "You start downloading \the [ai] into \the [src]...")
- ai << "\The [user] is downloading you into \the [src]!"
+ user.visible_message("\The [user] starts transferring \the [ai] into \the [src]...", "You start transferring \the [ai] into \the [src]...")
+ ai << "\The [user] is transferring you into \the [src]!"
if(do_after(user, 100))
if(istype(ai.loc, /turf/))
new /obj/structure/AIcore/deactivated(get_turf(ai))
ai.carded = 1
- admin_attack_log(user, ai, "Carded with [src.name]", "Was carded with [src.name]", "used the [src.name] to card")
+ admin_attack_log(user, ai, "Extracted with [src.name]", "Was extracted with [src.name]", "used the [src.name] to extract")
src.name = "[initial(name)] - [ai.name]"
ai.loc = src
@@ -119,9 +120,9 @@
carded_ai = ai
if(ai.client)
- ai << "You have been downloaded to a mobile storage device. Remote access lost."
+ ai << "You have been transferred into a mobile core. Remote access lost."
if(user.client)
- user << "Transfer successful: [ai.name] ([rand(1000,9999)].exe) removed from host terminal and stored within local memory."
+ user << "Transfer successful: [ai.name] extracted from current device and placed within mobile core."
ai.canmove = 1
update_icon()
diff --git a/code/game/objects/items/devices/body_snatcher_vr.dm b/code/game/objects/items/devices/body_snatcher_vr.dm
new file mode 100644
index 0000000000..053d5dbff3
--- /dev/null
+++ b/code/game/objects/items/devices/body_snatcher_vr.dm
@@ -0,0 +1,70 @@
+//Body snatcher. Based off the sleevemate, but instead of storing a mind it lets you swap your mind with someone. Extremely illegal and being caught with one s
+/obj/item/device/bodysnatcher
+ name = "\improper Body Snatcher Device"
+ desc = "An extremely illegal tool that allows the user to swap minds with the selected humanoid victim. The LED panel on the side states 'Place both heads on the device, pull trigger, then wait for the transfer to complete.'"
+ icon = 'icons/obj/device_alt.dmi'
+ icon_state = "sleevemate" //Give this a fancier sprite later.
+ item_state = "healthanalyzer"
+ flags = CONDUCT
+ slot_flags = SLOT_BELT
+ w_class = ITEMSIZE_SMALL
+ matter = list(DEFAULT_WALL_MATERIAL = 200)
+ origin_tech = list(TECH_MAGNET = 2, TECH_BIO = 2, TECH_ILLEGAL = 1)
+
+/obj/item/device/bodysnatcher/New()
+ ..()
+ flags |= NOBLUDGEON //So borgs don't spark.
+
+/obj/item/device/bodysnatcher/attack(mob/living/M, mob/living/user)
+ usr.setClickCooldown(DEFAULT_ATTACK_COOLDOWN)
+ if(ishuman(M) || issilicon(M)) //Allows body swapping with humans, synths, and pAI's/borgs since they all have a mind.
+ if(usr == M)
+ to_chat(user," A message pops up on the LED display, informing you that you that the mind transfer to yourself was successful... Wait, did that even do anything?")
+ return
+
+ if(!M.mind) //Do they have a mind?
+ to_chat(usr,"A warning pops up on the device, informing you that [M] appears braindead.")
+ return
+
+ if(M.stat == DEAD) //Are they dead?
+ to_chat(usr,"A warning pops up on the device, informing you that [M] is dead, and, as such, the mind transfer can not be done.")
+ return
+
+ var/choice = alert(usr,"This will swap your mind with the target's mind. This will result in them controlling your body, and you controlling their body. Continue?","Confirmation","Continue","Cancel")
+ if(choice == "Continue" && usr.get_active_hand() == src && usr.Adjacent(M))
+
+ usr.visible_message("[usr] pushes the device up his forehead and [M]'s head, the device beginning to let out a series of light beeps!","You begin swap minds with [M]!")
+ if(do_after(usr,35 SECONDS,M))
+ if(usr.mind && M.mind && M.stat != DEAD && usr.stat != DEAD)
+ log_and_message_admins("[usr.ckey] used a Bodysnatcher to swap bodies with [M.ckey]")
+ to_chat(usr,"Your minds have been swapped! Have a nice day.")
+ var/datum/mind/user_mind = user.mind
+ var/datum/mind/prey_mind = M.mind
+ var/target_ooc_notes = M.ooc_notes
+ var/user_ooc_notes = user.ooc_notes
+ M.ghostize()
+ usr.ghostize()
+ usr.mind = null
+ M.mind = null
+ user_mind.current = null
+ prey_mind.current = null
+ user_mind.active = TRUE //If they are 'active', their client is automatically pushed to the mob
+ user_mind.transfer_to(M) //This works. Transfers mind & Ckey.
+ prey_mind.active = TRUE
+ prey_mind.transfer_to(user)
+ M.ooc_notes = user_ooc_notes //Let's keep their OOC notes over to their new body.
+ user.ooc_notes = target_ooc_notes
+ usr.sleeping = 10 //Device knocks out both the user and the target.
+ usr.eye_blurry = 30 //Blurry vision while they both get used to their new body's vision
+ usr.slurring = 50 //And let's also have them slurring while they attempt to get used to using their new body.
+ if(ishuman(M)) //Let's not have the AI slurring, even though its downright hilarious.
+ M.sleeping = 10
+ M.eye_blurry = 30
+ M.slurring = 50
+
+ else
+ to_chat(user," A warning pops up on the LED display on the side of the device, informing you that the target is not able to have their mind swapped with!")
+
+/obj/item/device/bodysnatcher/attack_self(mob/living/user)
+ to_chat(user," A message pops up on the LED display, informing you that you that the mind transfer to yourself was successful... Wait, did that even do anything?")
+ return
diff --git a/code/game/objects/items/devices/communicator/communicator.dm b/code/game/objects/items/devices/communicator/communicator.dm
index a1f6ee610c..e2dc8af7c6 100644
--- a/code/game/objects/items/devices/communicator/communicator.dm
+++ b/code/game/objects/items/devices/communicator/communicator.dm
@@ -520,6 +520,7 @@ var/global/list/obj/item/device/communicator/all_communicators = list()
return
src << "\icon[origin_atom] Receiving communicator request from [origin_atom]. To answer, use the Call Communicator \
verb, and select that name to answer the call."
+ src << 'sound/machines/defib_SafetyOn.ogg'
comm.voice_invites |= src
if(message == "ping")
if(client && client.prefs.communicator_visibility)
@@ -528,6 +529,7 @@ var/global/list/obj/item/device/communicator/all_communicators = list()
exonet.send_message(origin_address, "64 bytes received from [exonet.address] ecmp_seq=1 ttl=51 time=[random] ms")
if(message == "text")
src << "\icon[origin_atom] Received text message from [origin_atom]: \"[text]\""
+ src << 'sound/machines/defib_safetyOff.ogg'
exonet_messages.Add("From [origin_atom]:
[text]")
return
diff --git a/code/game/objects/items/devices/defib.dm b/code/game/objects/items/devices/defib.dm
index 8b048a035e..20c516bbad 100644
--- a/code/game/objects/items/devices/defib.dm
+++ b/code/game/objects/items/devices/defib.dm
@@ -1,185 +1,657 @@
-//The case the paddles are kept in.
+#define DEFIB_TIME_LIMIT (10 MINUTES) //past this many seconds, defib is useless.
+#define DEFIB_TIME_LOSS (2 MINUTES) //past this many seconds, brain damage occurs.
+
+//backpack item
/obj/item/device/defib_kit
- name = "defibrillator kit"
- desc = "This KHI-branded defib kit is a semi-automated model. Remove pads, slap on chest, wait."
- icon = 'icons/obj/device.dmi'
- icon_state = "defib_kit"
+ name = "defibrillator"
+ desc = "A device that delivers powerful shocks to detachable paddles that resuscitate incapacitated patients."
+ icon = 'icons/obj/defibrillator.dmi'
+ icon_state = "defibunit"
+ item_state = "defibunit"
+ slot_flags = SLOT_BACK
+ force = 5
+ throwforce = 6
+ w_class = ITEMSIZE_LARGE
+ origin_tech = list(TECH_BIO = 4, TECH_POWER = 2)
+ action_button_name = "Remove/Replace Paddles"
+
+ var/obj/item/weapon/shockpaddles/linked/paddles
+ var/obj/item/weapon/cell/bcell = null
+
+/obj/item/device/defib_kit/New() //starts without a cell for rnd
+ ..()
+ if(ispath(paddles))
+ paddles = new paddles(src, src)
+ else
+ paddles = new(src, src)
+
+ if(ispath(bcell))
+ bcell = new bcell(src)
+ update_icon()
+
+/obj/item/device/defib_kit/Destroy()
+ . = ..()
+ qdel_null(paddles)
+ qdel_null(bcell)
+
+/obj/item/device/defib_kit/loaded //starts with highcap cell
+ bcell = /obj/item/weapon/cell/high
+
+
+/obj/item/device/defib_kit/update_icon()
+ var/list/new_overlays = list()
+
+ if(paddles && paddles.loc == src) //in case paddles got destroyed somehow.
+ new_overlays += "[initial(icon_state)]-paddles"
+ if(bcell)
+ if(bcell.check_charge(paddles.chargecost))
+ if(paddles.combat)
+ new_overlays += "[initial(icon_state)]-combat"
+ else if(!paddles.safety)
+ new_overlays += "[initial(icon_state)]-emagged"
+ else
+ new_overlays += "[initial(icon_state)]-powered"
+
+ var/ratio = Ceiling(bcell.percent()/25) * 25
+ new_overlays += "[initial(icon_state)]-charge[ratio]"
+ else
+ new_overlays += "[initial(icon_state)]-nocell"
+
+ overlays = new_overlays
+
+/obj/item/device/defib_kit/ui_action_click()
+ toggle_paddles()
+
+/obj/item/device/defib_kit/attack_hand(mob/user)
+ if(loc == user)
+ toggle_paddles()
+ else
+ ..()
+
+/obj/item/device/defib_kit/MouseDrop()
+ if(ismob(src.loc))
+ if(!CanMouseDrop(src))
+ return
+ var/mob/M = src.loc
+ if(!M.unEquip(src))
+ return
+ src.add_fingerprint(usr)
+ M.put_in_any_hand_if_possible(src)
+
+
+/obj/item/device/defib_kit/attackby(obj/item/weapon/W, mob/user, params)
+ if(W == paddles)
+ reattach_paddles(user)
+ else if(istype(W, /obj/item/weapon/cell))
+ if(bcell)
+ to_chat(user, "\the [src] already has a cell.")
+ else
+ if(!user.unEquip(W))
+ return
+ W.forceMove(src)
+ bcell = W
+ to_chat(user, "You install a cell in \the [src].")
+ update_icon()
+
+ else if(isscrewdriver(W))
+ if(bcell)
+ bcell.update_icon()
+ bcell.forceMove(get_turf(src.loc))
+ bcell = null
+ to_chat(user, "You remove the cell from \the [src].")
+ update_icon()
+ else
+ return ..()
+
+/obj/item/device/defib_kit/emag_act(var/remaining_charges, var/mob/user)
+ if(paddles)
+ . = paddles.emag_act(user)
+ update_icon()
+ return
+
+//Paddle stuff
+
+/obj/item/device/defib_kit/verb/toggle_paddles()
+ set name = "Toggle Paddles"
+ set category = "Object"
+
+ var/mob/living/carbon/human/user = usr
+ if(!paddles)
+ to_chat(user, "The paddles are missing!")
+ return
+
+ if(paddles.loc != src)
+ reattach_paddles(user) //Remove from their hands and back onto the defib unit
+ return
+
+ if(!slot_check())
+ to_chat(user, "You need to equip [src] before taking out [paddles].")
+ else
+ if(!usr.put_in_hands(paddles)) //Detach the paddles into the user's hands
+ to_chat(user, "You need a free hand to hold the paddles!")
+ update_icon() //success
+
+//checks that the base unit is in the correct slot to be used
+/obj/item/device/defib_kit/proc/slot_check()
+ var/mob/M = loc
+ if(!istype(M))
+ return 0 //not equipped
+
+ if((slot_flags & SLOT_BACK) && M.get_equipped_item(slot_back) == src)
+ return 1
+ if((slot_flags & SLOT_BELT) && M.get_equipped_item(slot_belt) == src)
+ return 1
+
+ return 0
+
+/obj/item/device/defib_kit/dropped(mob/user)
+ ..()
+ reattach_paddles(user) //paddles attached to a base unit should never exist outside of their base unit or the mob equipping the base unit
+
+/obj/item/device/defib_kit/proc/reattach_paddles(mob/user)
+ if(!paddles) return
+
+ if(ismob(paddles.loc))
+ var/mob/M = paddles.loc
+ if(M.drop_from_inventory(paddles, src))
+ to_chat(user, "\The [paddles] snap back into the main unit.")
+ else
+ paddles.forceMove(src)
+
+ update_icon()
+
+/*
+ Base Unit Subtypes
+*/
+
+/obj/item/device/defib_kit/compact
+ name = "compact defibrillator"
+ desc = "A belt-equipped defibrillator that can be rapidly deployed."
+ icon_state = "defibcompact"
+ item_state = "defibcompact"
+ w_class = ITEMSIZE_NORMAL
+ slot_flags = SLOT_BELT
+ origin_tech = list(TECH_BIO = 5, TECH_POWER = 3)
+
+/obj/item/device/defib_kit/compact/loaded
+ bcell = /obj/item/weapon/cell/high
+
+
+/obj/item/device/defib_kit/compact/combat
+ name = "combat defibrillator"
+ desc = "A belt-equipped blood-red defibrillator that can be rapidly deployed. Does not have the restrictions or safeties of conventional defibrillators and can revive through space suits."
+ paddles = /obj/item/weapon/shockpaddles/linked/combat
+
+/obj/item/device/defib_kit/compact/combat/loaded
+ bcell = /obj/item/weapon/cell/high
+
+/obj/item/weapon/shockpaddles/linked/combat
+ combat = 1
+ safety = 0
+ chargetime = (1 SECONDS)
+
+
+//paddles
+
+/obj/item/weapon/shockpaddles
+ name = "defibrillator paddles"
+ desc = "A pair of plastic-gripped paddles with flat metal surfaces that are used to deliver powerful electric shocks."
+ icon = 'icons/obj/defibrillator.dmi'
+ icon_state = "defibpaddles"
+ item_state = "defibpaddles"
+ gender = PLURAL
+ force = 2
+ throwforce = 6
w_class = ITEMSIZE_LARGE
- var/state //0 off, 1 open, 2 working, 3 dead
- var/uses = 2 //Calculates initial uses based on starting cell size
- var/use_on_synthetic = 0 //If 1, this is only useful on FBPs, if 0, this is only useful on fleshies
- var/pad_name = "defib pads" //Just the name given for some cosmetic things
- var/chance = 75 //Percent chance of working
- var/charge_cost //Set in New() based on uses
- var/obj/item/weapon/cell/cell //The size is mostly irrelevant, see 'uses'
- var/mob/living/carbon/human/patient //The person the paddles are on
+ var/safety = 1 //if you can zap people with the paddles on harm mode
+ var/combat = 0 //If it can be used to revive people wearing thick clothing (e.g. spacesuits)
+ var/cooldowntime = (6 SECONDS) // How long in deciseconds until the defib is ready again after use.
+ var/chargetime = (2 SECONDS)
+ var/chargecost = 1000 //units of charge
+ var/burn_damage_amt = 5
+ var/use_on_synthetic = 0 //If 1, this is only useful on FBPs, if 0, this is only useful on fleshies
-/obj/item/device/defib_kit/New()
+ var/wielded = 0
+ var/cooldown = 0
+ var/busy = 0
+
+/obj/item/weapon/shockpaddles/proc/set_cooldown(var/delay)
+ cooldown = 1
+ update_icon()
+
+ spawn(delay)
+ if(cooldown)
+ cooldown = 0
+ update_icon()
+
+ make_announcement("beeps, \"Unit is re-energized.\"", "notice")
+ playsound(src, 'sound/machines/defib_ready.ogg', 50, 0)
+
+/obj/item/weapon/shockpaddles/update_held_icon()
+ var/mob/living/M = loc
+ if(istype(M) && !issmall(M) && M.item_is_in_hands(src) && !M.hands_are_full())
+ wielded = 1
+ name = "[initial(name)] (wielded)"
+ else
+ wielded = 0
+ name = initial(name)
+ update_icon()
..()
- //Create cell and determine uses (futureproofing against cell size changes)
- cell = new(src)
- charge_cost = cell.maxcharge / uses
- statechange(0)
-/obj/item/device/defib_kit/attack_self(mob/user as mob)
- ..()
- if(patient)
- patient = null
- user.visible_message("[user] returns the pads to \the [src] and closes it.",
- "You return the pads to \the [src] and close it.")
- statechange(0)
+/obj/item/weapon/shockpaddles/update_icon()
+ icon_state = "defibpaddles[wielded]"
+ item_state = "defibpaddles[wielded]"
+ if(cooldown)
+ icon_state = "defibpaddles[wielded]_cooldown"
-/obj/item/device/defib_kit/MouseDrop(var/mob/living/carbon/human/onto)
- if(istype(onto) && Adjacent(usr) && !usr.restrained() && !usr.stat)
- var/mob/living/carbon/human/user = usr
- //<--Feel free to code clothing checks right here
- if(can_defib(onto))
- user.visible_message("[user] begins applying [pad_name] to [onto].",
- "You begin applying [pad_name] to [onto].")
- if(do_after(user, 100, onto))
- patient = onto
- statechange(1,patient)
- user.visible_message("[user] applies [pad_name] to [onto].",
- "You finish applying [pad_name] to [onto].")
-
-
-//can_defib() check is where all of the qualifying conditions should go
-//Could probably toss in checks here for damage, organs, etc, but for now I'll leave it as just this
-/obj/item/device/defib_kit/proc/can_defib(var/mob/living/carbon/human/target)
- var/mob/living/carbon/human/user = usr
- if(use_on_synthetic && !target.isSynthetic())
- to_chat(user, "[src] isn't designed for organics!")
+/obj/item/weapon/shockpaddles/proc/can_use(mob/user, mob/M)
+ if(busy)
return 0
- else if(!use_on_synthetic && target.isSynthetic())
- to_chat(user, "[src] isn't designed for synthetics!")
+ if(!check_charge(chargecost))
+ to_chat(user, "\The [src] doesn't have enough charge left to do that.")
return 0
- else if(!target.isSynthetic() && ((world.time - target.timeofdeath) > (10 MINUTES)))//Can only revive organics within a few minutes
- to_chat(user, "There is no spark of life in [target.name], they've been dead too long to revive this way.")
+ if(!wielded && !isrobot(user))
+ to_chat(user, "You need to wield the paddles with both hands before you can use them on someone!")
+ return 0
+ if(cooldown)
+ to_chat(user, "\The [src] are re-energizing!")
return 0
return 1
+//Checks for various conditions to see if the mob is revivable
+/obj/item/weapon/shockpaddles/proc/can_defib(mob/living/carbon/human/H) //This is checked before doing the defib operation
+ if((H.species.flags & NO_SCAN))
+ return "buzzes, \"Unrecogized physiology. Operation aborted.\""
+ else if(H.isSynthetic() && !use_on_synthetic)
+ return "buzzes, \"Synthetic Body. Operation aborted.\""
+ else if(!H.isSynthetic() && use_on_synthetic)
+ return "buzzes, \"Organic Body. Operation aborted.\""
-/obj/item/device/defib_kit/attackby(var/obj/item/A as obj, mob/living/user as mob)
+ if(H.stat != DEAD)
+ return "buzzes, \"Patient is not in a valid state. Operation aborted.\""
+
+ if(!check_contact(H))
+ return "buzzes, \"Patient's chest is obstructed. Operation aborted.\""
+
+ return null
+
+/obj/item/weapon/shockpaddles/proc/can_revive(mob/living/carbon/human/H) //This is checked right before attempting to revive
+
+ var/deadtime = world.time - H.timeofdeath
+ if (deadtime > DEFIB_TIME_LIMIT && !H.isSynthetic())
+ return "buzzes, \"Resuscitation failed - Excessive neural degeneration. Further attempts futile.\""
+
+ H.updatehealth()
+ if(H.health + H.getOxyLoss() <= config.health_threshold_dead || (HUSK in H.mutations))
+ return "buzzes, \"Resuscitation failed - Severe tissue damage makes recovery of patient impossible via defibrillator. Further attempts futile.\""
+
+ var/bad_vital_organ = check_vital_organs(H)
+ if(bad_vital_organ)
+ return bad_vital_organ
+
+ //this needs to be last since if any of the 'other conditions are met their messages take precedence
+ if(!H.client && !H.teleop)
+ return "buzzes, \"Resuscitation failed - Mental interface error. Further attempts may be successful.\""
+
+ return null
+
+/obj/item/weapon/shockpaddles/proc/check_contact(mob/living/carbon/human/H)
+ if(!combat)
+ for(var/obj/item/clothing/cloth in list(H.wear_suit, H.w_uniform))
+ if((cloth.body_parts_covered & UPPER_TORSO) && (cloth.item_flags & THICKMATERIAL))
+ return FALSE
+ return TRUE
+
+/obj/item/weapon/shockpaddles/proc/check_vital_organs(mob/living/carbon/human/H)
+ for(var/organ_tag in H.species.has_organ)
+ var/obj/item/organ/O = H.species.has_organ[organ_tag]
+ var/name = initial(O.name)
+ var/vital = initial(O.vital) //check for vital organs
+ if(vital)
+ O = H.internal_organs_by_name[organ_tag]
+ if(!O)
+ return "buzzes, \"Resuscitation failed - Patient is missing vital organ ([name]). Further attempts futile.\""
+ if(O.damage > O.max_damage)
+ return "buzzes, \"Resuscitation failed - Excessive damage to vital organ ([name]). Further attempts futile.\""
+ return null
+
+/obj/item/weapon/shockpaddles/proc/check_blood_level(mob/living/carbon/human/H)
+ if(!H.should_have_organ(O_HEART))
+ return FALSE
+
+ var/obj/item/organ/internal/heart/heart = H.internal_organs_by_name[O_HEART]
+ if(!heart)
+ return TRUE
+
+ var/blood_volume = round((H.vessel.get_reagent_amount("blood")/H.species.blood_volume)*100)
+ if(!heart || heart.is_broken())
+ blood_volume *= 0.3
+ else if(heart.is_bruised())
+ blood_volume *= 0.7
+ else if(heart.damage > 1)
+ blood_volume *= 0.8
+ return blood_volume < BLOOD_VOLUME_SURVIVE
+
+/obj/item/weapon/shockpaddles/proc/check_charge(var/charge_amt)
+ return 0
+
+/obj/item/weapon/shockpaddles/proc/checked_use(var/charge_amt)
+ return 0
+
+/obj/item/weapon/shockpaddles/attack(mob/living/M, mob/living/user, var/target_zone)
+ var/mob/living/carbon/human/H = M
+ if(!istype(H) || user.a_intent == I_HURT)
+ return ..() //Do a regular attack. Harm intent shocking happens as a hit effect
+
+ if(can_use(user, H))
+ busy = 1
+ update_icon()
+
+ do_revive(H, user)
+
+ busy = 0
+ update_icon()
+
+ return 1
+
+//Since harm-intent now skips the delay for deliberate placement, you have to be able to hit them in combat in order to shock people.
+/obj/item/weapon/shockpaddles/apply_hit_effect(mob/living/target, mob/living/user, var/hit_zone)
+ if(ishuman(target) && can_use(user, target))
+ busy = 1
+ update_icon()
+
+ do_electrocute(target, user, hit_zone)
+
+ busy = 0
+ update_icon()
+
+ return 1
+
+ return ..()
+
+// This proc is used so that we can return out of the revive process while ensuring that busy and update_icon() are handled
+/obj/item/weapon/shockpaddles/proc/do_revive(mob/living/carbon/human/H, mob/user)
+ if(!H.client && !H.teleop)
+ to_chat(find_dead_player(H.ckey, 1), "Someone is attempting to resuscitate you. Re-enter your body if you want to be revived!")
+
+ //beginning to place the paddles on patient's chest to allow some time for people to move away to stop the process
+ user.visible_message("\The [user] begins to place [src] on [H]'s chest.", "You begin to place [src] on [H]'s chest...")
+ if(!do_after(user, 30, H))
+ return
+ user.visible_message("\The [user] places [src] on [H]'s chest.", "You place [src] on [H]'s chest.")
+ playsound(get_turf(src), 'sound/machines/defib_charge.ogg', 50, 0)
+
+ var/error = can_defib(H)
+ if(error)
+ make_announcement(error, "warning")
+ playsound(get_turf(src), 'sound/machines/defib_failed.ogg', 50, 0)
+ return
+
+ if(check_blood_level(H))
+ make_announcement("buzzes, \"Warning - Patient is in hypovolemic shock.\"", "warning") //also includes heart damage
+
+ //placed on chest and short delay to shock for dramatic effect, revive time is 5sec total
+ if(!do_after(user, chargetime, H))
+ return
+
+ //deduct charge here, in case the base unit was EMPed or something during the delay time
+ if(!checked_use(chargecost))
+ make_announcement("buzzes, \"Insufficient charge.\"", "warning")
+ playsound(get_turf(src), 'sound/machines/defib_failed.ogg', 50, 0)
+ return
+
+ H.visible_message("\The [H]'s body convulses a bit.")
+ playsound(get_turf(src), "bodyfall", 50, 1)
+ playsound(get_turf(src), 'sound/machines/defib_zap.ogg', 50, 1, -1)
+ set_cooldown(cooldowntime)
+
+ error = can_revive(H)
+ if(error)
+ make_announcement(error, "warning")
+ playsound(get_turf(src), 'sound/machines/defib_failed.ogg', 50, 0)
+ return
+
+ H.apply_damage(burn_damage_amt, BURN, BP_TORSO)
+
+ //set oxyloss so that the patient is just barely in crit, if possible
+ var/barely_in_crit = config.health_threshold_crit - 1
+ var/adjust_health = barely_in_crit - H.health //need to increase health by this much
+ H.adjustOxyLoss(-adjust_health)
+
+ make_announcement("pings, \"Resuscitation successful.\"", "notice")
+ playsound(get_turf(src), 'sound/machines/defib_success.ogg', 50, 0)
+
+ make_alive(H)
+
+ log_and_message_admins("used \a [src] to revive [key_name(H)].")
+
+
+/obj/item/weapon/shockpaddles/proc/do_electrocute(mob/living/carbon/human/H, mob/user, var/target_zone)
+ var/obj/item/organ/external/affecting = H.get_organ(target_zone)
+ if(!affecting)
+ to_chat(user, "They are missing that body part!")
+ return
+
+ //no need to spend time carefully placing the paddles, we're just trying to shock them
+ user.visible_message("\The [user] slaps [src] onto [H]'s [affecting.name].", "You overcharge [src] and slap them onto [H]'s [affecting.name].")
+
+ //Just stop at awkwardly slapping electrodes on people if the safety is enabled
+ if(safety)
+ to_chat(user, "You can't do that while the safety is enabled.")
+ return
+
+ playsound(get_turf(src), 'sound/machines/defib_charge.ogg', 50, 0)
+ audible_message("\The [src] lets out a steadily rising hum...")
+
+ if(!do_after(user, chargetime, H))
+ return
+
+ //deduct charge here, in case the base unit was EMPed or something during the delay time
+ if(!checked_use(chargecost))
+ make_announcement("buzzes, \"Insufficient charge.\"", "warning")
+ playsound(get_turf(src), 'sound/machines/defib_failed.ogg', 50, 0)
+ return
+
+ user.visible_message("\The [user] shocks [H] with \the [src]!", "You shock [H] with \the [src]!")
+ playsound(get_turf(src), 'sound/machines/defib_zap.ogg', 100, 1, -1)
+ playsound(loc, 'sound/weapons/Egloves.ogg', 100, 1, -1)
+ set_cooldown(cooldowntime)
+
+ H.stun_effect_act(2, 120, target_zone)
+ var/burn_damage = H.electrocute_act(burn_damage_amt*2, src, def_zone = target_zone)
+ if(burn_damage > 15 && H.can_feel_pain())
+ H.emote("scream")
+
+ admin_attack_log(user, H, "Electrocuted using \a [src]", "Was electrocuted with \a [src]", "used \a [src] to electrocute")
+
+/obj/item/weapon/shockpaddles/proc/make_alive(mob/living/carbon/human/M) //This revives the mob
+ var/deadtime = world.time - M.timeofdeath
+
+ dead_mob_list.Remove(M)
+ if((M in living_mob_list) || (M in dead_mob_list))
+ WARNING("Mob [M] was defibbed but already in the living or dead list still!")
+ living_mob_list += M
+
+ M.timeofdeath = 0
+ M.stat = UNCONSCIOUS //Life() can bring them back to consciousness if it needs to.
+ M.regenerate_icons()
+ M.failed_last_breath = 0 //So mobs that died of oxyloss don't revive and have perpetual out of breath.
+ M.reload_fullscreen()
+
+ M.emote("gasp")
+ M.Weaken(rand(10,25))
+ M.updatehealth()
+ apply_brain_damage(M, deadtime)
+
+/obj/item/weapon/shockpaddles/proc/apply_brain_damage(mob/living/carbon/human/H, var/deadtime)
+ if(deadtime < DEFIB_TIME_LOSS) return
+
+ if(!H.should_have_organ(O_BRAIN)) return //no brain
+
+ var/obj/item/organ/internal/brain/brain = H.internal_organs_by_name[O_BRAIN]
+ if(!brain) return //no brain
+
+ var/brain_damage = Clamp((deadtime - DEFIB_TIME_LOSS)/(DEFIB_TIME_LIMIT - DEFIB_TIME_LOSS)*brain.max_damage, H.getBrainLoss(), brain.max_damage)
+ H.setBrainLoss(brain_damage)
+
+/obj/item/weapon/shockpaddles/proc/make_announcement(var/message, var/msg_class)
+ audible_message("\The [src] [message]", "\The [src] vibrates slightly.")
+
+/obj/item/weapon/shockpaddles/emag_act(mob/user)
+ if(safety)
+ safety = 0
+ to_chat(user, "You silently disable \the [src]'s safety protocols with the cryptographic sequencer.")
+ update_icon()
+ return 1
+ else
+ safety = 1
+ to_chat(user, "You silently enable \the [src]'s safety protocols with the cryptographic sequencer.")
+ update_icon()
+ return 1
+
+/obj/item/weapon/shockpaddles/emp_act(severity)
+ var/new_safety = rand(0, 1)
+ if(safety != new_safety)
+ safety = new_safety
+ if(safety)
+ make_announcement("beeps, \"Safety protocols enabled!\"", "notice")
+ playsound(get_turf(src), 'sound/machines/defib_safetyon.ogg', 50, 0)
+ else
+ make_announcement("beeps, \"Safety protocols disabled!\"", "warning")
+ playsound(get_turf(src), 'sound/machines/defib_safetyoff.ogg', 50, 0)
+ update_icon()
..()
- if(!cell && istype(A,/obj/item/weapon/cell))
- if(!user.unEquip(A)) return
- to_chat(user,"You jack \the [A] into \the [src]'s battery mount.")
- A.forceMove(src)
- src.cell = A
+/obj/item/weapon/shockpaddles/robot
+ name = "defibrillator paddles"
+ desc = "A pair of advanced shockpaddles powered by a robot's internal power cell, able to penetrate thick clothing."
+ chargecost = 50
+ combat = 1
+ icon_state = "defibpaddles0"
+ item_state = "defibpaddles0"
+ cooldowntime = (3 SECONDS)
- else if(istype(A,/obj/item/weapon/screwdriver))
- if(cell)
- to_chat(user,"You remove \the [cell] from \the [src].")
- if(user.r_hand && user.l_hand)
- cell.forceMove(get_turf(user))
- else
- user.put_in_hands(cell)
- cell = null
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
- else
- to_chat(user,"The power source has already been removed!")
+/obj/item/weapon/shockpaddles/robot/check_charge(var/charge_amt)
+ if(isrobot(src.loc))
+ var/mob/living/silicon/robot/R = src.loc
+ return (R.cell && R.cell.check_charge(charge_amt))
-/obj/item/device/defib_kit/proc/statechange(var/new_state, var/pat)
- if(state == new_state) return //Let's just save ourselves some time
- state = new_state
- icon_state = "[initial(icon_state)][state]"
- var/turf/T = get_turf(src)
- var/state_words = ""
- switch(state)
- if(0)
- state_words = "It is currently closed."
- processing_objects -= src
+/obj/item/weapon/shockpaddles/robot/checked_use(var/charge_amt)
+ if(isrobot(src.loc))
+ var/mob/living/silicon/robot/R = src.loc
+ return (R.cell && R.cell.checked_use(charge_amt))
+
+/*
+ Shockpaddles that are linked to a base unit
+*/
+/obj/item/weapon/shockpaddles/linked
+ var/obj/item/device/defib_kit/base_unit
+
+/obj/item/weapon/shockpaddles/linked/New(newloc, obj/item/device/defib_kit/defib)
+ base_unit = defib
+ ..(newloc)
+
+/obj/item/weapon/shockpaddles/linked/Destroy()
+ if(base_unit)
+ //ensure the base unit's icon updates
+ if(base_unit.paddles == src)
+ base_unit.paddles = null
+ base_unit.update_icon()
+ base_unit = null
+ return ..()
+
+/obj/item/weapon/shockpaddles/linked/dropped(mob/user)
+ ..() //update twohanding
+ if(base_unit)
+ base_unit.reattach_paddles(user) //paddles attached to a base unit should never exist outside of their base unit or the mob equipping the base unit
+
+/obj/item/weapon/shockpaddles/linked/check_charge(var/charge_amt)
+ return (base_unit.bcell && base_unit.bcell.check_charge(charge_amt))
+
+/obj/item/weapon/shockpaddles/linked/checked_use(var/charge_amt)
+ return (base_unit.bcell && base_unit.bcell.checked_use(charge_amt))
+
+/obj/item/weapon/shockpaddles/linked/make_announcement(var/message, var/msg_class)
+ base_unit.audible_message("\The [base_unit] [message]", "\The [base_unit] vibrates slightly.")
+
+/*
+ Standalone Shockpaddles
+*/
+
+/obj/item/weapon/shockpaddles/standalone
+ desc = "A pair of shockpaddles powered by an experimental miniaturized reactor" //Inspired by the advanced e-gun
+ var/fail_counter = 0
+
+/obj/item/weapon/shockpaddles/standalone/Destroy()
+ . = ..()
+ if(fail_counter)
+ processing_objects.Remove(src)
+
+/obj/item/weapon/shockpaddles/standalone/check_charge(var/charge_amt)
+ return 1
+
+/obj/item/weapon/shockpaddles/standalone/checked_use(var/charge_amt)
+ radiation_repository.radiate(src, charge_amt/12) //just a little bit of radiation. It's the price you pay for being powered by magic I guess
+ return 1
+
+/obj/item/weapon/shockpaddles/standalone/process()
+ if(fail_counter > 0)
+ radiation_repository.radiate(src, fail_counter--)
+ else
+ processing_objects.Remove(src)
+
+/obj/item/weapon/shockpaddles/standalone/emp_act(severity)
+ ..()
+ var/new_fail = 0
+ switch(severity)
if(1)
- state_words = "A green light is lit; it has charge."
- processing_objects |= src
+ new_fail = max(fail_counter, 20)
+ visible_message("\The [src]'s reactor overloads!")
if(2)
- state_words = "A yellow light is flashing: it's in the process of reviving a patient."
- T.visible_message("A yellow light starts flashing on \the [src].")
- playsound(T, 'sound/machines/chime.ogg', 50, 0)
- if(3)
- state_words = "A red light is flashing: the battery needs to be recharged."
- T.visible_message("A red light starts flashing on \the [src].")
- playsound(T, 'sound/machines/buzz-sigh.ogg', 50, 0)
+ new_fail = max(fail_counter, 8)
+ if(ismob(loc))
+ to_chat(loc, "\The [src] feel pleasantly warm.")
- desc = "[initial(desc)] [state_words][pat ? " The pads are attached to [pat]." : ""]"
- update_icon()
+ if(new_fail && !fail_counter)
+ processing_objects.Add(src)
+ fail_counter = new_fail
-/obj/item/device/defib_kit/process()
- if(!state) //0 or null
- statechange(0)
- processing_objects -= src
- return
-
- //Patient moved too far
- if(patient && !(get_dist(src,patient) <= 1)) //You separated the kit and pads too far
- audible_message("There is a clatter as the [pad_name] are yanked off of [patient].")
- statechange(0)
- patient = null
- return
-
- //Battery died
- if(!cell || cell.charge < charge_cost)
- statechange(3,patient)
- return
-
- //A patient isn't being worked on, but we have one, so start
- if(patient && patient.stat == DEAD && state != 2)
- statechange(2)
- if(attempt_shock()) //Try to shock them, has timer and such
- patient.visible_message("[patient] convulses!")
- playsound(src.loc, 'sound/effects/sparks2.ogg', 75, 1)
- //Actual rezzing code
- if(prob(chance))
- if(!patient.client && patient.mind) //Don't force the dead person to come back if they don't want to.
- for(var/mob/observer/dead/ghost in player_list)
- if(ghost.mind == patient.mind)
- to_chat(ghost, "Someone is trying to \
- revive you. Return to your body if you want to be revived! \
- (Verbs -> Ghost -> Re-enter corpse). You have 15 seconds to do this!")
- sleep(15 SECONDS)
- break
-
- if(!(HUSK in patient.mutations)) // Husked people can't come back with a Defib.
- if(patient.client)
- patient.adjustOxyLoss(-20) //Look, blood stays oxygenated for quite some time, but I'm not recoding the entire oxy system
- patient.stat = CONSCIOUS //Note that if whatever killed them in the first place wasn't fixed, they're likely to die again.
- dead_mob_list -= patient
- living_mob_list += patient
- patient.timeofdeath = null
- patient.visible_message("[patient]'s eyes open!")
- log_and_message_admins("[patient] was revived by a defib.")
- cell.charge -= charge_cost //Always charge the cost after any attempt, failed or not
- sleep(20) //Wait 2 seconds before next attempt
- statechange(1,patient) //Back to ready
-
-/obj/item/device/defib_kit/proc/attempt_shock()
- if(!patient || cell.charge < charge_cost)
- return
-
- var/zap_time = world.time + (7 SECONDS)
- var/o_patient_loc = patient.loc
- . = 1
-
- while(world.time < zap_time) //This is basically a custom do_after() call
- sleep(1)
-
- //Failed: We lost something important
- if(!patient || !cell || cell.charge < charge_cost)
- . = 0
- break
-
- //Failed: The locations aren't right
- if((o_patient_loc != patient.loc) || !(get_dist(src,patient) <= 1))
- . = 0
- break
-
- return
+/* From the Bay port, this doesn't seem to have a sprite.
+/obj/item/weapon/shockpaddles/standalone/traitor
+ name = "defibrillator paddles"
+ desc = "A pair of unusual looking paddles powered by an experimental miniaturized reactor. It possesses both the ability to penetrate armor and to deliver powerful shocks."
+ icon = 'icons/obj/weapons.dmi'
+ icon_state = "defibpaddles0"
+ item_state = "defibpaddles0"
+ combat = 1
+ safety = 0
+ chargetime = (1 SECONDS)
+*/
+//FBP Defibs
/obj/item/device/defib_kit/jumper_kit
name = "jumper cable kit"
- desc = "This Morpheus-branded FBP defib kit is a semi-automated model. Apply cables, step back, wait."
- icon_state = "jumper_kit"
+ desc = "A device that delivers powerful shocks to detachable jumper cables that are capable of reviving full body prosthetics."
+ icon_state = "jumperunit"
+ item_state = "jumperunit"
+ paddles = /obj/item/weapon/shockpaddles/linked/jumper
+
+/obj/item/device/defib_kit/jumper_kit/loaded
+ bcell = /obj/item/weapon/cell/high
+
+/obj/item/weapon/shockpaddles/linked/jumper
+ name = "jumper cables"
+ icon_state = "jumperpaddles"
+ item_state = "jumperpaddles"
use_on_synthetic = 1
- pad_name = "jumper cables"
+
+/obj/item/weapon/shockpaddles/robot/jumper
+ name = "jumper cables"
+ desc = "A pair of advanced shockpaddles powered by a robot's internal power cell, able to penetrate thick clothing."
+ icon_state = "jumperpaddles0"
+ item_state = "jumperpaddles0"
+ use_on_synthetic = 1
+
+#undef DEFIB_TIME_LIMIT
+#undef DEFIB_TIME_LOSS
diff --git a/code/game/objects/items/devices/hacktool.dm b/code/game/objects/items/devices/hacktool.dm
index 2f05a6f385..9ae5f62732 100644
--- a/code/game/objects/items/devices/hacktool.dm
+++ b/code/game/objects/items/devices/hacktool.dm
@@ -23,10 +23,10 @@
hack_state = null
return ..()
-/obj/item/device/multitool/hacktool/attackby(var/obj/W, var/mob/user)
+/obj/item/device/multitool/hacktool/attackby(var/obj/item/W, var/mob/user)
if(isscrewdriver(W))
in_hack_mode = !in_hack_mode
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 50, 1)
+ playsound(src.loc, W.usesound, 50, 1)
else
..()
diff --git a/code/game/objects/items/devices/modkit.dm b/code/game/objects/items/devices/modkit.dm
index 025196b218..ca7ace1a59 100644
--- a/code/game/objects/items/devices/modkit.dm
+++ b/code/game/objects/items/devices/modkit.dm
@@ -14,7 +14,7 @@
/obj/item/clothing/suit/space/void
)
-/obj/item/device/modkit/afterattack(obj/O, mob/user as mob, proximity)
+/obj/item/device/modkit/afterattack(obj/item/O, mob/user as mob, proximity)
if(!proximity)
return
@@ -47,7 +47,7 @@
user << "[O] must be safely placed on the ground for modification."
return
- playsound(user.loc, 'sound/items/Screwdriver.ogg', 100, 1)
+ playsound(src.loc, O.usesound, 100, 1)
user.visible_message("\The [user] opens \the [src] and modifies \the [O].","You open \the [src] and modify \the [O].")
diff --git a/code/game/objects/items/devices/multitool.dm b/code/game/objects/items/devices/multitool.dm
index 85c680ca98..d79fc021db 100644
--- a/code/game/objects/items/devices/multitool.dm
+++ b/code/game/objects/items/devices/multitool.dm
@@ -22,6 +22,7 @@
var/obj/machinery/telecomms/buffer // simple machine buffer for device linkage
var/obj/machinery/clonepod/connecting //same for cryopod linkage
var/obj/machinery/connectable //Used to connect machinery.
+ toolspeed = 1
/obj/item/device/multitool/attack_self(mob/user)
var/clear = alert("Do you want to clear the buffers on the [src]?",, "Yes", "No",)
@@ -30,4 +31,17 @@
connecting = null
connectable = null
else
- ..()
\ No newline at end of file
+ ..()
+
+/obj/item/device/multitool/cyborg
+ name = "multitool"
+ desc = "Optimised and stripped-down version of a regular multitool."
+ toolspeed = 0.5
+
+/obj/item/device/multitool/alien
+ name = "alien multitool"
+ desc = "An omni-technological interface."
+ icon = 'icons/obj/abductor.dmi'
+ icon_state = "multitool"
+ toolspeed = 0.1
+ origin_tech = list(TECH_MAGNETS = 5, TECH_ENGINEERING = 5)
\ No newline at end of file
diff --git a/code/game/objects/items/devices/powersink.dm b/code/game/objects/items/devices/powersink.dm
index 910d983e22..e4c1bb3f20 100644
--- a/code/game/objects/items/devices/powersink.dm
+++ b/code/game/objects/items/devices/powersink.dm
@@ -42,6 +42,7 @@
anchored = 1
mode = 1
src.visible_message("[user] attaches [src] to the cable!")
+ playsound(src, I.usesound, 50, 1)
return
else
user << "Device must be placed over an exposed cable to attach to it."
@@ -54,6 +55,7 @@
mode = 0
src.visible_message("[user] detaches [src] from the cable!")
set_light(0)
+ playsound(src, I.usesound, 50, 1)
icon_state = "powersink0"
return
diff --git a/code/game/objects/items/devices/radio/encryptionkey.dm b/code/game/objects/items/devices/radio/encryptionkey.dm
index 639f4b67d9..e26b75486e 100644
--- a/code/game/objects/items/devices/radio/encryptionkey.dm
+++ b/code/game/objects/items/devices/radio/encryptionkey.dm
@@ -14,7 +14,7 @@
/obj/item/device/encryptionkey/attackby(obj/item/weapon/W as obj, mob/user as mob)
/obj/item/device/encryptionkey/syndicate
- icon_state = "cypherkey"
+ icon_state = "syn_cypherkey"
channels = list("Mercenary" = 1)
origin_tech = list(TECH_ILLEGAL = 3)
syndie = 1//Signifies that it de-crypts Syndicate transmissions
@@ -26,7 +26,7 @@
syndie = 1
/obj/item/device/encryptionkey/binary
- icon_state = "cypherkey"
+ icon_state = "bin_cypherkey"
translate_binary = 1
origin_tech = list(TECH_ILLEGAL = 3)
diff --git a/code/game/objects/items/devices/radio/headset.dm b/code/game/objects/items/devices/radio/headset.dm
index a56ea4fa98..ccfb671691 100644
--- a/code/game/objects/items/devices/radio/headset.dm
+++ b/code/game/objects/items/devices/radio/headset.dm
@@ -13,7 +13,7 @@
var/translate_hive = 0
var/obj/item/device/encryptionkey/keyslot1 = null
var/obj/item/device/encryptionkey/keyslot2 = null
- var/ks1type = /obj/item/device/encryptionkey
+ var/ks1type = null
var/ks2type = null
/obj/item/device/radio/headset/New()
@@ -348,6 +348,7 @@
recalculateChannels()
user << "You pop out the encryption keys in the headset!"
+ playsound(src, W.usesound, 50, 1)
else
user << "This headset doesn't have any encryption keys! How useless..."
diff --git a/code/game/objects/items/devices/radio/intercom.dm b/code/game/objects/items/devices/radio/intercom.dm
index 73fd75740d..ef4e196309 100644
--- a/code/game/objects/items/devices/radio/intercom.dm
+++ b/code/game/objects/items/devices/radio/intercom.dm
@@ -114,6 +114,7 @@
if(istype(W, /obj/item/weapon/screwdriver)) // Opening the intercom up.
wiresexposed = !wiresexposed
user << "The wires have been [wiresexposed ? "exposed" : "unexposed"]"
+ playsound(src, W.usesound, 50, 1)
if(wiresexposed)
if(!on)
icon_state = "intercom-p_open"
@@ -124,7 +125,7 @@
return
if(wiresexposed && istype(W, /obj/item/weapon/wirecutters))
user.visible_message("[user] has cut the wires inside \the [src]!", "You have cut the wires inside \the [src].")
- playsound(src.loc, 'sound/items/Wirecutter.ogg', 50, 1)
+ playsound(src, W.usesound, 50, 1)
new/obj/item/stack/cable_coil(get_turf(src), 5)
var/obj/structure/frame/A = new /obj/structure/frame(src.loc)
var/obj/item/weapon/circuitboard/M = circuit
diff --git a/code/game/objects/items/devices/radio/jammer.dm b/code/game/objects/items/devices/radio/jammer.dm
index 154861f794..403b91e159 100644
--- a/code/game/objects/items/devices/radio/jammer.dm
+++ b/code/game/objects/items/devices/radio/jammer.dm
@@ -19,6 +19,7 @@ var/global/list/active_radio_jammers = list()
icon = 'icons/obj/device.dmi'
icon_state = "jammer0"
var/active_state = "jammer1"
+ var/last_overlay_percent = null // Stores overlay icon_state to avoid excessive recreation of overlays.
var/on = 0
var/jam_range = 7
@@ -29,6 +30,7 @@ var/global/list/active_radio_jammers = list()
/obj/item/device/radio_jammer/New()
power_source = new(src)
+ update_icon() // So it starts with the full overlay.
/obj/item/device/radio_jammer/Destroy()
if(on)
@@ -42,7 +44,7 @@ var/global/list/active_radio_jammers = list()
processing_objects.Remove(src)
active_radio_jammers -= src
on = FALSE
- icon_state = initial(icon_state)
+ update_icon()
/obj/item/device/radio_jammer/proc/turn_on(mob/user)
if(user)
@@ -50,7 +52,7 @@ var/global/list/active_radio_jammers = list()
processing_objects.Add(src)
active_radio_jammers += src
on = TRUE
- icon_state = active_state
+ update_icon()
/obj/item/device/radio_jammer/process()
if(!power_source || !power_source.check_charge(tick_cost))
@@ -60,6 +62,7 @@ var/global/list/active_radio_jammers = list()
turn_off(notify)
else
power_source.use(tick_cost)
+ update_icon()
/obj/item/device/radio_jammer/attack_hand(mob/user)
@@ -86,4 +89,25 @@ var/global/list/active_radio_jammers = list()
power_source.update_icon() //Why doesn't a cell do this already? :|
user.unEquip(power_source)
power_source.forceMove(src)
+ update_icon()
to_chat(user,"You insert \the [power_source] into \the [src].")
+
+/obj/item/device/radio_jammer/update_icon()
+ if(on)
+ icon_state = active_state
+ else
+ icon_state = initial(icon_state)
+
+ var/overlay_percent = 0
+ if(power_source)
+ overlay_percent = between(0, round( power_source.percent() , 25), 100)
+ else
+ overlay_percent = 0
+
+ // Only Cut() if we need to.
+ if(overlay_percent != last_overlay_percent)
+ overlays.Cut()
+ var/image/I = image(src.icon, src, "jammer_overlay_[overlay_percent]")
+ overlays += I
+ last_overlay_percent = overlay_percent
+
diff --git a/code/game/objects/items/devices/radio/radio.dm b/code/game/objects/items/devices/radio/radio.dm
index fc0629e449..75abb260f1 100644
--- a/code/game/objects/items/devices/radio/radio.dm
+++ b/code/game/objects/items/devices/radio/radio.dm
@@ -40,7 +40,7 @@ var/global/list/default_medbay_channels = list(
var/list/channels = list() //see communications.dm for full list. First channel is a "default" for :h
var/subspace_transmission = 0
var/syndie = 0//Holder to see if it's a syndicate encrypted radio
- var/centComm = 0//Holder to see if it's a CentComm encrypted radio
+ var/centComm = 0//Holder to see if it's a CentCom encrypted radio
flags = CONDUCT
slot_flags = SLOT_BELT
throw_speed = 2
@@ -629,6 +629,7 @@ var/global/list/default_medbay_channels = list(
recalculateChannels()
user << "You pop out the encryption key in the radio!"
+ playsound(src, W.usesound, 50, 1)
else
user << "This radio doesn't have any encryption keys!"
diff --git a/code/game/objects/items/devices/suit_cooling.dm b/code/game/objects/items/devices/suit_cooling.dm
index fb34bb0996..a2d6ce3341 100644
--- a/code/game/objects/items/devices/suit_cooling.dm
+++ b/code/game/objects/items/devices/suit_cooling.dm
@@ -138,6 +138,7 @@
else
cover_open = 1
user << "You unscrew the panel."
+ playsound(src, W.usesound, 50, 1)
updateicon()
return
diff --git a/code/game/objects/items/devices/taperecorder.dm b/code/game/objects/items/devices/taperecorder.dm
index 2564b3eff0..791725c14b 100644
--- a/code/game/objects/items/devices/taperecorder.dm
+++ b/code/game/objects/items/devices/taperecorder.dm
@@ -416,7 +416,8 @@
/obj/item/device/tape/attackby(obj/item/I, mob/user, params)
if(ruined && istype(I, /obj/item/weapon/screwdriver))
to_chat(user, "You start winding the tape back in...")
- if(do_after(user, 120, target = src))
+ playsound(src, I.usesound, 50, 1)
+ if(do_after(user, 120 * I.toolspeed, target = src))
to_chat(user, "You wound the tape back in.")
fix()
return
diff --git a/code/game/objects/items/devices/uplink_random_lists.dm b/code/game/objects/items/devices/uplink_random_lists.dm
index f3533c5a01..38605da018 100644
--- a/code/game/objects/items/devices/uplink_random_lists.dm
+++ b/code/game/objects/items/devices/uplink_random_lists.dm
@@ -57,7 +57,7 @@ var/datum/uplink_random_selection/all_uplink_selection = new/datum/uplink_random
items += new/datum/uplink_random_item(/datum/uplink_item/item/ammo/mc9mm)
items += new/datum/uplink_random_item(/datum/uplink_item/item/visible_weapons/revolver)
items += new/datum/uplink_random_item(/datum/uplink_item/item/ammo/a357)
- items += new/datum/uplink_random_item(/datum/uplink_item/item/visible_weapons/heavysniper, 15, 0)
+ items += new/datum/uplink_random_item(/datum/uplink_item/item/visible_weapons/heavysnipermerc, 15, 0)
items += new/datum/uplink_random_item(/datum/uplink_item/item/ammo/sniperammo, 15, 0)
items += new/datum/uplink_random_item(/datum/uplink_item/item/grenades/emp, 50)
items += new/datum/uplink_random_item(/datum/uplink_item/item/visible_weapons/crossbow, 33)
diff --git a/code/game/objects/items/robot/robot_upgrades.dm b/code/game/objects/items/robot/robot_upgrades.dm
index 7baf73270f..db39d11f46 100644
--- a/code/game/objects/items/robot/robot_upgrades.dm
+++ b/code/game/objects/items/robot/robot_upgrades.dm
@@ -158,8 +158,8 @@
/obj/item/borg/upgrade/syndicate/
- name = "illegal equipment module"
- desc = "Unlocks the hidden, deadlier functions of a robot"
+ name = "scrambled equipment module"
+ desc = "Unlocks new and often deadly module specific items of a robot"
icon_state = "cyborg_upgrade3"
item_state = "cyborg_upgrade"
require_module = 1
@@ -167,8 +167,8 @@
/obj/item/borg/upgrade/syndicate/action(var/mob/living/silicon/robot/R)
if(..()) return 0
- if(R.emagged == 1)
+ if(R.emag_items == 1)
return 0
- R.emagged = 1
+ R.emag_items = 1
return 1
diff --git a/code/game/objects/items/weapons/cards_ids.dm b/code/game/objects/items/weapons/cards_ids.dm
index 11404ade86..9292e1ce93 100644
--- a/code/game/objects/items/weapons/cards_ids.dm
+++ b/code/game/objects/items/weapons/cards_ids.dm
@@ -256,7 +256,7 @@
/obj/item/weapon/card/id/centcom
name = "\improper CentCom. ID"
- desc = "An ID straight from Cent. Com."
+ desc = "An ID straight from Central Command."
icon_state = "centcom"
registered_name = "Central Command"
assignment = "General"
diff --git a/code/game/objects/items/weapons/cigs_lighters.dm b/code/game/objects/items/weapons/cigs_lighters.dm
index ee2d2f2c57..4f7ba66842 100644
--- a/code/game/objects/items/weapons/cigs_lighters.dm
+++ b/code/game/objects/items/weapons/cigs_lighters.dm
@@ -472,6 +472,7 @@ CIGARETTE PACKETS ARE IN FANCY.DM
/obj/item/weapon/flame/lighter/zippo
name = "\improper Zippo lighter"
desc = "The zippo."
+ icon = 'icons/obj/zippo.dmi'
icon_state = "zippo"
item_state = "zippo"
@@ -542,3 +543,46 @@ CIGARETTE PACKETS ARE IN FANCY.DM
if(location)
location.hotspot_expose(700, 5)
return
+
+//Here we add Zippo skins.
+
+/obj/item/weapon/flame/lighter/zippo/black
+ name = "\improper holy Zippo lighter"
+ desc = "Only in regards to Christianity, that is."
+ icon_state = "blackzippo"
+
+/obj/item/weapon/flame/lighter/zippo/blue
+ name = "\improper blue Zippo lighter"
+ icon_state = "bluezippo"
+
+/obj/item/weapon/flame/lighter/zippo/engraved
+ name = "\improper engraved Zippo lighter"
+ icon_state = "engravedzippo"
+ item_state = "zippo"
+
+/obj/item/weapon/flame/lighter/zippo/gold
+ name = "\improper golden Zippo lighter"
+ icon_state = "goldzippo"
+
+/obj/item/weapon/flame/lighter/zippo/moff
+ name = "\improper moth Zippo lighter"
+ desc = "Too cute to be a Tymisian."
+ icon_state = "moffzippo"
+
+/obj/item/weapon/flame/lighter/zippo/red
+ name = "\improper red Zippo lighter"
+ icon_state = "redzippo"
+
+/obj/item/weapon/flame/lighter/zippo/ironic
+ name = "\improper ironic Zippo lighter"
+ desc = "What a quiant idea."
+ icon_state = "ironiczippo"
+
+/obj/item/weapon/flame/lighter/zippo/capitalist
+ name = "\improper capitalist Zippo lighter"
+ desc = "Made of gold and obsidian, this is truly not worth however much you spent on it."
+ icon_state = "cappiezippo"
+
+/obj/item/weapon/flame/lighter/zippo/rainbow
+ name = "\improper rainbow Zippo lighter"
+ icon_state = "rainbowzippo"
\ No newline at end of file
diff --git a/code/game/objects/items/weapons/circuitboards/computer/research.dm b/code/game/objects/items/weapons/circuitboards/computer/research.dm
index f49b80e6df..fa9ed16797 100644
--- a/code/game/objects/items/weapons/circuitboards/computer/research.dm
+++ b/code/game/objects/items/weapons/circuitboards/computer/research.dm
@@ -8,6 +8,7 @@
/obj/item/weapon/circuitboard/rdconsole/attackby(obj/item/I as obj, mob/user as mob)
if(istype(I,/obj/item/weapon/screwdriver))
+ playsound(src, I.usesound, 50, 1)
user.visible_message("\The [user] adjusts the jumper on \the [src]'s access protocol pins.", "You adjust the jumper on the access protocol pins.")
if(build_path == /obj/machinery/computer/rdconsole/core)
name = T_BOARD("RD Console - Robotics")
diff --git a/code/game/objects/items/weapons/circuitboards/machinery/research.dm b/code/game/objects/items/weapons/circuitboards/machinery/research.dm
index 1e4fe2afd9..31e0d9c063 100644
--- a/code/game/objects/items/weapons/circuitboards/machinery/research.dm
+++ b/code/game/objects/items/weapons/circuitboards/machinery/research.dm
@@ -13,6 +13,7 @@ obj/item/weapon/circuitboard/rdserver
obj/item/weapon/circuitboard/rdserver/attackby(obj/item/I as obj, mob/user as mob)
if(istype(I,/obj/item/weapon/screwdriver))
+ playsound(src, I.usesound, 50, 1)
user.visible_message("\The [user] adjusts the jumper on \the [src]'s access protocol pins.", "You adjust the jumper on the access protocol pins.")
if(build_path == /obj/machinery/r_n_d/server/core)
name = T_BOARD("RD Console - Robotics")
diff --git a/code/game/objects/items/weapons/explosives.dm b/code/game/objects/items/weapons/explosives.dm
index 1a8cc97def..1e1565a2ae 100644
--- a/code/game/objects/items/weapons/explosives.dm
+++ b/code/game/objects/items/weapons/explosives.dm
@@ -28,6 +28,7 @@
if(istype(I, /obj/item/weapon/screwdriver))
open_panel = !open_panel
user << "You [open_panel ? "open" : "close"] the wire panel."
+ playsound(src, I.usesound, 50, 1)
else if(istype(I, /obj/item/weapon/wirecutters) || istype(I, /obj/item/device/multitool) || istype(I, /obj/item/device/assembly/signaler ))
wires.Interact(user)
else
diff --git a/code/game/objects/items/weapons/grenades/chem_grenade.dm b/code/game/objects/items/weapons/grenades/chem_grenade.dm
index 9d6b5d6bd3..0eaf073cfa 100644
--- a/code/game/objects/items/weapons/grenades/chem_grenade.dm
+++ b/code/game/objects/items/weapons/grenades/chem_grenade.dm
@@ -86,7 +86,7 @@
// user << "You need to add at least one beaker before locking the assembly."
user << "You lock the empty assembly."
name = "fake grenade"
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 25, -3)
+ playsound(src, W.usesound, 50, 1)
icon_state = initial(icon_state) +"_locked"
stage = 2
else if(stage == 2)
@@ -96,7 +96,7 @@
return
else
user << "You unlock the assembly."
- playsound(src.loc, 'sound/items/Screwdriver.ogg', 25, -3)
+ playsound(src.loc, W.usesound, 50, -3)
name = "unsecured grenade with [beakers.len] containers[detonator?" and detonator":""]"
icon_state = initial(icon_state) + (detonator?"_ass":"")
stage = 1
diff --git a/code/game/objects/items/weapons/grenades/explosive.dm b/code/game/objects/items/weapons/grenades/explosive.dm
index 62d13c3a2b..ccf8b89ee2 100644
--- a/code/game/objects/items/weapons/grenades/explosive.dm
+++ b/code/game/objects/items/weapons/grenades/explosive.dm
@@ -27,13 +27,17 @@
no_attack_log = 1
muzzle_type = null
+/obj/item/projectile/bullet/pellet/fragment/strong
+ damage = 15
+ armor_penetration = 20
+
/obj/item/weapon/grenade/explosive
name = "fragmentation grenade"
desc = "A fragmentation grenade, optimized for harming personnel without causing massive structural damage."
icon_state = "frggrenade"
item_state = "grenade"
- var/fragment_type = /obj/item/projectile/bullet/pellet/fragment
+ var/fragment_types = list(/obj/item/projectile/bullet/pellet/fragment, /obj/item/projectile/bullet/pellet/fragment, /obj/item/projectile/bullet/pellet/fragment, /obj/item/projectile/bullet/pellet/fragment/strong)
var/num_fragments = 63 //total number of fragments produced by the grenade
var/explosion_size = 2 //size of the center explosion
@@ -48,29 +52,49 @@
if(!O) return
if(explosion_size)
- explosion(O, -1, -1, 2, round(explosion_size/2), 0)
+ on_explosion(O)
+ src.fragmentate(O, num_fragments, spread_range, fragment_types)
+ qdel(src)
- var/list/target_turfs = getcircle(O, spread_range)
- var/fragments_per_projectile = round(num_fragments/target_turfs.len)
- for(var/turf/T in target_turfs)
- var/obj/item/projectile/bullet/pellet/fragment/P = new (O)
+/obj/proc/fragmentate(var/turf/T=get_turf(src), var/fragment_number = 30, var/spreading_range = 5, var/list/fragtypes=list(/obj/item/projectile/bullet/pellet/fragment/))
+ set waitfor = 0
+ var/list/target_turfs = getcircle(T, spreading_range)
+ var/fragments_per_projectile = round(fragment_number/target_turfs.len)
+ for(var/turf/O in target_turfs)
+ sleep(0)
+ var/fragment_type = pickweight(fragtypes)
+ var/obj/item/projectile/bullet/pellet/fragment/P = new fragment_type(T)
P.pellets = fragments_per_projectile
P.shot_from = src.name
- P.launch(T)
-
- //var/cone = new /obj/item/weapon/caution/cone (T)
- //spawn(100) qdel(cone)
+ P.launch(O)
//Make sure to hit any mobs in the source turf
- for(var/mob/living/M in O)
+ for(var/mob/living/M in T)
//lying on a frag grenade while the grenade is on the ground causes you to absorb most of the shrapnel.
//you will most likely be dead, but others nearby will be spared the fragments that hit you instead.
if(M.lying && isturf(src.loc))
- P.attack_mob(M, 0, 0)
+ P.attack_mob(M, 0, 5)
+ else if(!M.lying && src.loc != get_turf(src)) //if it's not on the turf, it must be in the mob!
+ P.attack_mob(M, 0, 25) //you're holding a grenade, dude!
else
P.attack_mob(M, 0, 100) //otherwise, allow a decent amount of fragments to pass
- qdel(src)
+
+/obj/item/weapon/grenade/explosive/proc/on_explosion(var/turf/O)
+ if(explosion_size)
+ explosion(O, -1, -1, explosion_size, round(explosion_size/2), 0)
+
+
+/obj/item/weapon/grenade/explosive/frag
+ name = "fragmentation grenade"
+ desc = "A military fragmentation grenade, designed to explode in a deadly shower of fragments."
+ icon_state = "frag"
+ loadable = null
+
+ fragment_types = list(/obj/item/projectile/bullet/pellet/fragment)
+ num_fragments = 200 //total number of fragments produced by the grenade
+
+ //The radius of the circle used to launch projectiles. Lower values mean less projectiles are used but if set too low gaps may appear in the spread pattern
diff --git a/code/game/objects/items/weapons/grenades/fragmentation.dm b/code/game/objects/items/weapons/grenades/fragmentation.dm
deleted file mode 100644
index 9f10e9b4d4..0000000000
--- a/code/game/objects/items/weapons/grenades/fragmentation.dm
+++ /dev/null
@@ -1,61 +0,0 @@
-//Fragmentation grenade projectile
-/obj/item/projectile/bullet/pellet/fragment
- damage = 15
- range_step = 2
-
- base_spread = 0 //causes it to be treated as a shrapnel explosion instead of cone
- spread_step = 20
-
- silenced = 1 //embedding messages are still produced so it's kind of weird when enabled.
- no_attack_log = 1
- muzzle_type = null
-
-/obj/item/weapon/grenade/frag
- name = "fragmentation grenade"
- desc = "A military fragmentation grenade, designed to explode in a deadly shower of fragments."
- icon_state = "frag"
- loadable = null
-
- var/num_fragments = 200 //total number of fragments produced by the grenade
- var/fragment_damage = 15
- var/damage_step = 2 //projectiles lose a fragment each time they travel this distance. Can be a non-integer.
- var/explosion_size = 2 //size of the center explosion
-
- //The radius of the circle used to launch projectiles. Lower values mean less projectiles are used but if set too low gaps may appear in the spread pattern
- var/spread_range = 7
-
-/obj/item/weapon/grenade/frag/prime()
- ..()
-
- var/turf/O = get_turf(src)
- if(!O) return
-
- if(explosion_size)
- explosion(O, -1, round(explosion_size/2), explosion_size, round(explosion_size/2), 0)
-
- var/list/target_turfs = getcircle(O, spread_range)
- var/fragments_per_projectile = round(num_fragments/target_turfs.len)
-
- for(var/turf/T in target_turfs)
- var/obj/item/projectile/bullet/pellet/fragment/P = new (O)
-
- P.damage = fragment_damage
- P.pellets = fragments_per_projectile
- P.range_step = damage_step
- P.shot_from = src.name
-
- P.launch(T)
-
- //var/cone = new /obj/item/weapon/caution/cone (T)
- //spawn(100) qdel(cone)
-
- //Make sure to hit any mobs in the source turf
- for(var/mob/living/M in O)
- //lying on a frag grenade while the grenade is on the ground causes you to absorb most of the shrapnel.
- //you will most likely be dead, but others nearby will be spared the fragments that hit you instead.
- if(M.lying && isturf(src.loc))
- P.attack_mob(M, 0, 0)
- else
- P.attack_mob(M, 0, 100) //otherwise, allow a decent amount of fragments to pass
-
- qdel(src)
diff --git a/code/game/objects/items/weapons/implants/implantcircuits.dm b/code/game/objects/items/weapons/implants/implantcircuits.dm
index db24be3c0a..856e7a5d8b 100644
--- a/code/game/objects/items/weapons/implants/implantcircuits.dm
+++ b/code/game/objects/items/weapons/implants/implantcircuits.dm
@@ -1,5 +1,6 @@
/obj/item/weapon/implant/integrated_circuit
name = "electronic implant"
+ desc = "It's a case, for building very tiny electronics with."
icon = 'icons/obj/electronic_assemblies.dmi'
icon_state = "setup_implant"
var/obj/item/device/electronic_assembly/implant/IC = null
diff --git a/code/game/objects/items/weapons/improvised_components.dm b/code/game/objects/items/weapons/improvised_components.dm
index 9e6e05a807..105a76473f 100644
--- a/code/game/objects/items/weapons/improvised_components.dm
+++ b/code/game/objects/items/weapons/improvised_components.dm
@@ -9,6 +9,7 @@
/obj/item/weapon/material/butterflyconstruction/attackby(obj/item/W as obj, mob/user as mob)
if(istype(W,/obj/item/weapon/screwdriver))
user << "You finish the concealed blade weapon."
+ playsound(src, W.usesound, 50, 1)
new /obj/item/weapon/material/butterfly(user.loc, material.name)
qdel(src)
return
diff --git a/code/game/objects/items/weapons/manuals.dm b/code/game/objects/items/weapons/manuals.dm
index 6ea812ad3a..533f5b30aa 100644
--- a/code/game/objects/items/weapons/manuals.dm
+++ b/code/game/objects/items/weapons/manuals.dm
@@ -147,6 +147,47 @@