diff --git a/code/modules/hydroponics/grown.dm b/code/modules/hydroponics/grown.dm
index 15456c1e34..dadf077c8a 100644
--- a/code/modules/hydroponics/grown.dm
+++ b/code/modules/hydroponics/grown.dm
@@ -146,7 +146,7 @@
/obj/item/reagent_containers/food/snacks/grown/on_grind()
var/nutriment = reagents.get_reagent_amount("nutriment")
- if(grind_results.len)
+ if(grind_results&&grind_results.len)
for(var/i in 1 to grind_results.len)
grind_results[grind_results[i]] = nutriment
reagents.del_reagent("nutriment")
@@ -154,7 +154,7 @@
/obj/item/reagent_containers/food/snacks/grown/on_juice()
var/nutriment = reagents.get_reagent_amount("nutriment")
- if(juice_results.len)
+ if(juice_results&&juice_results.len)
for(var/i in 1 to juice_results.len)
juice_results[juice_results[i]] = nutriment
reagents.del_reagent("nutriment")
diff --git a/code/modules/integrated_electronics/core/assemblies.dm b/code/modules/integrated_electronics/core/assemblies.dm
index 805cf787f7..637c3bfcee 100644
--- a/code/modules/integrated_electronics/core/assemblies.dm
+++ b/code/modules/integrated_electronics/core/assemblies.dm
@@ -20,6 +20,8 @@
var/charge_tick = FALSE
var/charge_delay = 4
var/use_cyborg_cell = TRUE
+ max_integrity = 50
+ armor = list(melee = 50, bullet = 70, laser = 70, energy = 100, bomb = 10, bio = 100, rad = 100, fire = 0, acid = 0)
/obj/item/device/electronic_assembly/proc/check_interactivity(mob/user)
return user.canUseTopic(src,be_close = TRUE)
@@ -30,8 +32,6 @@
START_PROCESSING(SScircuit, src)
materials[MAT_METAL] = round((max_complexity + max_components) / 4) * SScircuit.cost_multiplier
-
-
/obj/item/device/electronic_assembly/Destroy()
STOP_PROCESSING(SScircuit, src)
return ..()
@@ -273,22 +273,9 @@
/obj/item/device/electronic_assembly/afterattack(atom/target, mob/user, proximity)
- for(var/obj/item/integrated_circuit/input/sensor/S in assembly_components)
- if(!proximity)
- if(istype(S,/obj/item/integrated_circuit/input/sensor/ranged)||(!user))
- if(user.client)
- if(!(target in view(user.client)))
- continue
- else
- if(!(target in view(user)))
- continue
- else
- continue
- S.set_pin_data(IC_OUTPUT, 1, WEAKREF(target))
- S.check_then_do_work()
- S.scan(target)
-
- visible_message(" [user] waves [src] around [target].")
+ for(var/obj/item/integrated_circuit/input/S in assembly_components)
+ if(S.sense(target,user,proximity))
+ visible_message(" [user] waves [src] around [target].")
/obj/item/device/electronic_assembly/screwdriver_act(mob/living/user, obj/item/S)
@@ -326,8 +313,11 @@
interact(user)
return TRUE
else
+ for(var/obj/item/integrated_circuit/input/S in assembly_components)
+ S.attackby_react(I,user,user.a_intent)
return ..()
+
/obj/item/device/electronic_assembly/attack_self(mob/user)
if(!check_interactivity(user))
return
@@ -391,7 +381,6 @@
/obj/item/device/electronic_assembly/proc/get_object()
return src
-
// Returns the location to be used for dropping items.
// Same as the regular drop_location(), but with checks being run on acting_object if necessary.
/obj/item/integrated_circuit/drop_location()
@@ -406,6 +395,7 @@
/obj/item/device/electronic_assembly/default //The /default electronic_assemblys are to allow the introduction of the new naming scheme without breaking old saves.
name = "type-a electronic assembly"
+
/obj/item/device/electronic_assembly/calc
name = "type-b electronic assembly"
icon_state = "setup_small_calc"
@@ -507,4 +497,4 @@
/obj/item/device/electronic_assembly/drone/arms
name = "type-b electronic drone"
icon_state = "setup_drone_arms"
- desc = "It's a case, for building mobile electronics with. This one is armed and dangerous."
\ No newline at end of file
+ desc = "It's a case, for building mobile electronics with. This one is armed and dangerous."
diff --git a/code/modules/integrated_electronics/core/debugger.dm b/code/modules/integrated_electronics/core/debugger.dm
index ac6f5c1a1e..666fcf00d6 100644
--- a/code/modules/integrated_electronics/core/debugger.dm
+++ b/code/modules/integrated_electronics/core/debugger.dm
@@ -56,7 +56,7 @@
data_to_show = A.name
to_chat(user, "You write '[data_to_write ? data_to_show : "NULL"]' to the '[io]' pin of \the [io.holder].")
else if(io.io_type == PULSE_CHANNEL)
- io.holder.check_then_do_work(ignore_power = TRUE)
+ io.holder.check_then_do_work(io.ord,ignore_power = TRUE)
to_chat(user, "You pulse \the [io.holder]'s [io].")
io.holder.interact(user) // This is to update the UI.
diff --git a/code/modules/integrated_electronics/core/helpers.dm b/code/modules/integrated_electronics/core/helpers.dm
index e84823f201..773c4f0684 100644
--- a/code/modules/integrated_electronics/core/helpers.dm
+++ b/code/modules/integrated_electronics/core/helpers.dm
@@ -15,9 +15,9 @@
io_type_override = io_list_copy[io_entry]
if(io_type_override)
- io_list.Add(new io_type_override(src, io_entry, default_data, pin_type))
+ io_list.Add(new io_type_override(src, io_entry, default_data, pin_type,i))
else
- io_list.Add(new io_type(src, io_entry, default_data, pin_type))
+ io_list.Add(new io_type(src, io_entry, default_data, pin_type,i))
/obj/item/integrated_circuit/proc/set_pin_data(pin_type, pin_number, datum/new_data)
diff --git a/code/modules/integrated_electronics/core/integrated_circuit.dm b/code/modules/integrated_electronics/core/integrated_circuit.dm
index 069ca4245c..0c1a2fdad5 100644
--- a/code/modules/integrated_electronics/core/integrated_circuit.dm
+++ b/code/modules/integrated_electronics/core/integrated_circuit.dm
@@ -58,6 +58,12 @@ a creative player the means to solve many problems. Circuits are held inside an
/obj/item/integrated_circuit/proc/any_examine(mob/user)
return
+/obj/item/integrated_circuit/proc/attackby_react(var/atom/movable/A,mob/user)
+ return
+
+/obj/item/integrated_circuit/proc/sense(var/atom/movable/A,mob/user,prox)
+ return
+
/obj/item/integrated_circuit/proc/check_interactivity(mob/user)
if(assembly)
return assembly.check_interactivity(user)
@@ -291,17 +297,18 @@ a creative player the means to solve many problems. Circuits are held inside an
return TRUE // Battery has enough.
return FALSE // Not enough power.
-/obj/item/integrated_circuit/proc/check_then_do_work(var/ignore_power = FALSE)
+/obj/item/integrated_circuit/proc/check_then_do_work(ord,var/ignore_power = FALSE)
if(world.time < next_use) // All intergrated circuits have an internal cooldown, to protect from spam.
- return
+ return FALSE
if(power_draw_per_use && !ignore_power)
if(!check_power())
power_fail()
- return
+ return FALSE
next_use = world.time + cooldown_per_use
- do_work()
+ do_work(ord)
+ return TRUE
-/obj/item/integrated_circuit/proc/do_work()
+/obj/item/integrated_circuit/proc/do_work(ord)
return
/obj/item/integrated_circuit/proc/disconnect_all()
@@ -369,4 +376,3 @@ a creative player the means to solve many problems. Circuits are held inside an
return TRUE
return FALSE
-
diff --git a/code/modules/integrated_electronics/core/pins.dm b/code/modules/integrated_electronics/core/pins.dm
index bff96b713c..528281c3b7 100644
--- a/code/modules/integrated_electronics/core/pins.dm
+++ b/code/modules/integrated_electronics/core/pins.dm
@@ -25,14 +25,16 @@ D [1]/ ||
var/list/linked = list()
var/io_type = DATA_CHANNEL
var/pin_type // IC_INPUT, IC_OUTPUT, IC_ACTIVATOR - used in saving assembly wiring
+ var/ord
-
-/datum/integrated_io/New(loc, _name, _data, _pin_type)
+/datum/integrated_io/New(loc, _name, _data, _pin_type,_ord)
name = _name
if(_data)
data = _data
if(_pin_type)
pin_type = _pin_type
+ if(_ord)
+ ord = _ord
holder = loc
@@ -148,7 +150,7 @@ D [1]/ ||
/datum/integrated_io/activate/push_data()
for(var/k in 1 to linked.len)
var/datum/integrated_io/io = linked[k]
- io.holder.check_then_do_work()
+ io.holder.check_then_do_work(io.ord)
/datum/integrated_io/proc/pull_data()
for(var/k in 1 to linked.len)
@@ -207,7 +209,7 @@ D [1]/ ||
write_data_to_pin(new_data)
/datum/integrated_io/activate/ask_for_pin_data(mob/user) // This just pulses the pin.
- holder.check_then_do_work(ignore_power = TRUE)
+ holder.check_then_do_work(ord,ignore_power = TRUE)
to_chat(user, "You pulse \the [holder]'s [src] pin.")
/datum/integrated_io/activate
diff --git a/code/modules/integrated_electronics/core/special_pins/index_pin.dm b/code/modules/integrated_electronics/core/special_pins/index_pin.dm
index 51b12a0f3a..06267eec61 100644
--- a/code/modules/integrated_electronics/core/special_pins/index_pin.dm
+++ b/code/modules/integrated_electronics/core/special_pins/index_pin.dm
@@ -1,4 +1,4 @@
-// These pins can only contain integer numbers between 1 and IC_MAX_LIST_LENGTH. Null is not allowed.
+// These pins can only contain integer numbers between 0 and IC_MAX_LIST_LENGTH. Null is allowed.
/datum/integrated_io/index
name = "index pin"
data = 1
@@ -11,10 +11,10 @@
/datum/integrated_io/index/write_data_to_pin(new_data)
if(isnull(new_data))
- new_data = 1
+ new_data = 0
if(isnum(new_data))
- data = CLAMP(round(new_data), 1, IC_MAX_LIST_LENGTH)
+ data = CLAMP(round(new_data), 0, IC_MAX_LIST_LENGTH)
holder.on_data_written()
/datum/integrated_io/index/display_pin_type()
diff --git a/code/modules/integrated_electronics/subtypes/arithmetic.dm b/code/modules/integrated_electronics/subtypes/arithmetic.dm
index 7dec779f83..e491a34a69 100644
--- a/code/modules/integrated_electronics/subtypes/arithmetic.dm
+++ b/code/modules/integrated_electronics/subtypes/arithmetic.dm
@@ -30,10 +30,9 @@
/obj/item/integrated_circuit/arithmetic/addition/do_work()
var/result = 0
for(var/k in 1 to inputs.len)
- var/datum/integrated_io/I = inputs[k]
- I.pull_data()
- if(isnum(I.data))
- result = result + I.data
+ var/I = get_pin_data(IC_INPUT, k)
+ if(isnum(I))
+ result += I
set_pin_data(IC_OUTPUT, 1, result)
push_data()
@@ -56,13 +55,10 @@
return
var/result = A.data
- for(var/k in 1 to inputs.len)
- var/datum/integrated_io/I = inputs[k]
- if(I == A)
- continue
- I.pull_data()
- if(isnum(I.data))
- result = result - I.data
+ for(var/k in 2 to inputs.len)
+ var/I = get_pin_data(IC_INPUT, k)
+ if(isnum(I))
+ result -= I
set_pin_data(IC_OUTPUT, 1, result)
push_data()
@@ -85,13 +81,10 @@
if(!isnum(A.data))
return
var/result = A.data
- for(var/k in 1 to inputs.len)
- var/datum/integrated_io/I = inputs[k]
- if(I == A)
- continue
- I.pull_data()
- if(isnum(I.data))
- result = result * I.data
+ for(var/k in 2 to inputs.len)
+ var/I = get_pin_data(IC_INPUT, k)
+ if(isnum(I))
+ result *= I
set_pin_data(IC_OUTPUT, 1, result)
push_data()
@@ -114,13 +107,12 @@
return
var/result = A.data
- for(var/k in 1 to inputs.len)
- var/datum/integrated_io/I = inputs[k]
- if(I == A)
- continue
- I.pull_data()
- if(isnum(I.data) && I.data != 0) //No runtimes here.
- result = result / I.data
+
+ for(var/k in 2 to inputs.len)
+ var/I = get_pin_data(IC_INPUT, k)
+ if(isnum(I) && (I != 0))
+ result /= I
+
set_pin_data(IC_OUTPUT, 1, result)
push_data()
@@ -228,12 +220,11 @@
/obj/item/integrated_circuit/arithmetic/average/do_work()
var/result = 0
var/inputs_used = 0
- for(var/k in 1 to inputs.len)
- var/datum/integrated_io/I = inputs[k]
- I.pull_data()
- if(isnum(I.data))
+ for(var/k in 2 to inputs.len)
+ var/I = get_pin_data(IC_INPUT, k)
+ if(isnum(I))
inputs_used++
- result = result + I.data
+ result += I
if(inputs_used)
result = result / inputs_used
@@ -288,11 +279,10 @@
/obj/item/integrated_circuit/arithmetic/square_root/do_work()
var/result = 0
- for(var/k in 1 to inputs.len)
- var/datum/integrated_io/I = inputs[k]
- I.pull_data()
- if(isnum(I.data))
- result = sqrt(I.data)
+ for(var/k in 2 to inputs.len)
+ var/I = get_pin_data(IC_INPUT, k)
+ if(isnum(I))
+ result += sqrt(I)
set_pin_data(IC_OUTPUT, 1, result)
push_data()
diff --git a/code/modules/integrated_electronics/subtypes/converters.dm b/code/modules/integrated_electronics/subtypes/converters.dm
index d622ea8ca9..cd9306d0da 100644
--- a/code/modules/integrated_electronics/subtypes/converters.dm
+++ b/code/modules/integrated_electronics/subtypes/converters.dm
@@ -160,10 +160,10 @@
/obj/item/integrated_circuit/converter/concatenator/do_work()
var/result = null
- for(var/datum/integrated_io/I in inputs)
- I.pull_data()
- if(!isnull(I.data))
- result = result + I.data
+ for(var/k in 1 to inputs.len)
+ var/I = get_pin_data(IC_INPUT, k)
+ if(!isnull(I))
+ result = result + I
set_pin_data(IC_OUTPUT, 1, result)
push_data()
diff --git a/code/modules/integrated_electronics/subtypes/input.dm b/code/modules/integrated_electronics/subtypes/input.dm
index c39cfeac44..91b4b437e3 100644
--- a/code/modules/integrated_electronics/subtypes/input.dm
+++ b/code/modules/integrated_electronics/subtypes/input.dm
@@ -128,7 +128,7 @@
var/mob/living/carbon/human/H = get_pin_data_as_type(IC_INPUT, 1, /mob/living/carbon/human)
if(!istype(H)) //Invalid input
return
- if(H in view(get_turf(H))) // Like medbot's analyzer it can be used in range..
+ if(H in view(get_turf(src))) // Like medbot's analyzer it can be used in range..
var/total_health = round(H.health/H.getMaxHealth(), 0.01)*100
var/missing_health = H.getMaxHealth() - H.health
@@ -143,6 +143,49 @@
push_data()
activate_pin(2)
+/obj/item/integrated_circuit/input/slime_scanner
+ name = "slime_scanner"
+ desc = "A very small version of the xenobio analyser. This allows the machine to know every needed properties of slime."
+ icon_state = "medscan_adv"
+ complexity = 12
+ inputs = list("\[ target")
+ outputs = list(
+ "colour" = IC_PINTYPE_STRING,
+ "adult" = IC_PINTYPE_BOOLEAN,
+ "nutrition" = IC_PINTYPE_NUMBER,
+ "charge" = IC_PINTYPE_NUMBER,
+ "health" = IC_PINTYPE_NUMBER,
+ "possible mutation" = IC_PINTYPE_LIST,
+ "genetic destability"= IC_PINTYPE_NUMBER,
+ "slime core amount" = IC_PINTYPE_NUMBER,
+ "Growth progress" = IC_PINTYPE_NUMBER,
+ )
+ activators = list("scan" = IC_PINTYPE_PULSE_IN, "on scanned" = IC_PINTYPE_PULSE_OUT)
+ spawn_flags = IC_SPAWN_RESEARCH
+ power_draw_per_use = 80
+
+/obj/item/integrated_circuit/input/slime_scanner/do_work()
+ var/mob/living/simple_animal/slime/T = get_pin_data_as_type(IC_INPUT, 1, /mob/living/simple_animal/slime)
+ if(!isslime(T)) //Invalid input
+ return
+ if(T in view(get_turf(src))) // Like medbot's analyzer it can be used in range..
+
+ set_pin_data(IC_OUTPUT, 1, T.colour)
+ set_pin_data(IC_OUTPUT, 2, T.is_adult)
+ set_pin_data(IC_OUTPUT, 3, T.nutrition/T.get_max_nutrition())
+ set_pin_data(IC_OUTPUT, 4, T.powerlevel)
+ set_pin_data(IC_OUTPUT, 5, round(T.health/T.maxHealth,0.01)*100)
+ set_pin_data(IC_OUTPUT, 6, uniqueList(T.slime_mutation))
+ set_pin_data(IC_OUTPUT, 7, T.mutation_chance)
+ set_pin_data(IC_OUTPUT, 8, T.cores)
+ set_pin_data(IC_OUTPUT, 9, T.amount_grown/SLIME_EVOLUTION_THRESHOLD)
+
+
+ push_data()
+ activate_pin(2)
+
+
+
/obj/item/integrated_circuit/input/plant_scanner
name = "integrated plant analyzer"
desc = "A very small version of the plant analyser. This allows the machine to know all valuable params of plants in trays. \
@@ -180,7 +223,7 @@
return
for(var/i=1, i<=outputs.len, i++)
set_pin_data(IC_OUTPUT, i, null)
- if(H in view(get_turf(H))) // Like medbot's analyzer it can be used in range..
+ if(H in view(get_turf(src))) // Like medbot's analyzer it can be used in range..
if(H.myseed)
set_pin_data(IC_OUTPUT, 1, H.myseed.plantname)
set_pin_data(IC_OUTPUT, 2, H.age)
@@ -228,7 +271,7 @@
return
for(var/i=1, i<=outputs.len, i++)
set_pin_data(IC_OUTPUT, i, null)
- if(H in view(get_turf(H))) // Like medbot's analyzer it can be used in range..
+ if(H in view(get_turf(src))) // Like medbot's analyzer it can be used in range..
if(H.myseed)
for(var/datum/plant_gene/reagent/G in H.myseed.genes)
greagents.Add(G.get_name())
@@ -671,12 +714,15 @@
spawn_flags = IC_SPAWN_DEFAULT|IC_SPAWN_RESEARCH
power_draw_per_use = 120
-/obj/item/integrated_circuit/input/sensor/proc/scan(var/atom/A)
+/obj/item/integrated_circuit/input/sensor/sense(var/atom/A,mob/user,prox)
+ if(!prox)
+ return FALSE
+ if(!check_then_do_work())
+ return FALSE
var/ignore_bags = get_pin_data(IC_INPUT, 1)
if(ignore_bags)
if(istype(A, /obj/item/storage))
return FALSE
-
set_pin_data(IC_OUTPUT, 1, WEAKREF(A))
push_data()
activate_pin(1)
@@ -694,6 +740,52 @@
spawn_flags = IC_SPAWN_DEFAULT|IC_SPAWN_RESEARCH
power_draw_per_use = 120
+/obj/item/integrated_circuit/input/sensor/ranged/sense(var/atom/A,mob/user)
+ if(!user)
+ return FALSE
+ if(user.client)
+ if(!(A in view(user.client)))
+ return FALSE
+ else
+ if(!(A in view(user)))
+ return FALSE
+ if(!check_then_do_work())
+ return FALSE
+ var/ignore_bags = get_pin_data(IC_INPUT, 1)
+ if(ignore_bags)
+ if(istype(A, /obj/item/storage))
+ return FALSE
+ set_pin_data(IC_OUTPUT, 1, WEAKREF(A))
+ push_data()
+ activate_pin(1)
+ return TRUE
+
+/obj/item/integrated_circuit/input/objscaner
+ name = "scaner"
+ desc = "Scans and obtains a reference for any objects you use on assembly."
+ extended_desc = "If 'put down' pin is set to true, assembly will take scanned object from your hands to it's location.\
+ useful for interaction with grabber. Scaner works only with help intent."
+ icon_state = "recorder"
+ complexity = 4
+ inputs = list("put down" = IC_PINTYPE_BOOLEAN)
+ outputs = list("scanned" = IC_PINTYPE_REF)
+ activators = list("on scanned" = IC_PINTYPE_PULSE_OUT)
+ spawn_flags = IC_SPAWN_DEFAULT|IC_SPAWN_RESEARCH
+ power_draw_per_use = 20
+
+/obj/item/integrated_circuit/input/objscaner/attackby_react(var/atom/A,var/mob/user,intent)
+ if(intent!=INTENT_HELP)
+ return FALSE
+ if(!check_then_do_work())
+ return FALSE
+ var/pu = get_pin_data(IC_INPUT, 1)
+ if(pu)
+ user.transferItemToLoc(A,drop_location())
+ set_pin_data(IC_OUTPUT, 1, WEAKREF(A))
+ push_data()
+ activate_pin(1)
+ return TRUE
+
/obj/item/integrated_circuit/input/internalbm
name = "internal battery monitor"
desc = "This monitors the charge level of an internal battery."
@@ -760,3 +852,38 @@
activate_pin(2)
push_data()
return
+
+/obj/item/integrated_circuit/input/ntnetsc
+ name = "NTnet scaner"
+ desc = "This can return NTnet id of component insi given object, if there is any."
+ icon_state = "signalsc"
+ w_class = WEIGHT_CLASS_TINY
+ complexity = 2
+ inputs = list("target" = IC_PINTYPE_REF)
+ outputs = list(
+ "id" = IC_PINTYPE_STRING
+ )
+ activators = list("read" = IC_PINTYPE_PULSE_IN, "found" = IC_PINTYPE_PULSE_OUT,"not found" = IC_PINTYPE_PULSE_OUT)
+ spawn_flags = IC_SPAWN_DEFAULT|IC_SPAWN_RESEARCH
+ power_draw_per_use = 1
+
+/obj/item/integrated_circuit/input/ntnetsc/do_work()
+
+ var/atom/AM = get_pin_data_as_type(IC_INPUT, 1, /atom)
+ var/list/processing_list = list(AM)
+ var/datum/component/ntnet_interface/net = null
+ set_pin_data(IC_OUTPUT, 1, null)
+ while(processing_list.len && !net)
+ var/atom/A = processing_list[1]
+ processing_list.Cut(1, 2)
+ //Byond does not allow things to be in multiple contents, or double parent-child hierarchies, so only += is needed
+ //This is also why we don't need to check against assembled as we go along
+ processing_list += A.contents
+ net = A.GetComponent(/datum/component/ntnet_interface)
+ if(net)
+ set_pin_data(IC_OUTPUT, 1, net.hardware_id)
+ activate_pin(2)
+ else
+ activate_pin(3)
+ push_data()
+ return
diff --git a/code/modules/integrated_electronics/subtypes/logic.dm b/code/modules/integrated_electronics/subtypes/logic.dm
index 627301ef10..f8e858ef94 100644
--- a/code/modules/integrated_electronics/subtypes/logic.dm
+++ b/code/modules/integrated_electronics/subtypes/logic.dm
@@ -2,7 +2,7 @@
name = "logic gate"
desc = "This tiny chip will decide for you!"
extended_desc = "Logic circuits will treat a null, 0, and a \"\" string value as FALSE and anything else as TRUE."
- complexity = 3
+ complexity = 1
outputs = list("result")
activators = list("compare" = IC_PINTYPE_PULSE_IN)
category_text = "Logic"
diff --git a/code/modules/integrated_electronics/subtypes/manipulation.dm b/code/modules/integrated_electronics/subtypes/manipulation.dm
index f32f414fbb..5099547197 100644
--- a/code/modules/integrated_electronics/subtypes/manipulation.dm
+++ b/code/modules/integrated_electronics/subtypes/manipulation.dm
@@ -155,9 +155,11 @@
if(isnum(wanted_dir.data))
if(step(assembly, wanted_dir.data))
activate_pin(2)
+ return
else
activate_pin(3)
return FALSE
+ return FALSE
/obj/item/integrated_circuit/manipulation/grenade
name = "grenade primer"
@@ -247,9 +249,14 @@
/obj/item/integrated_circuit/manipulation/plant_module/do_work()
..()
var/turf/T = get_turf(src)
- var/obj/machinery/hydroponics/AM = get_pin_data_as_type(IC_INPUT, 1, /obj/machinery/hydroponics)
- if(!istype(AM)) //Invalid input
+ var/obj/OM = get_pin_data_as_type(IC_INPUT, 1, /obj)
+ if(istype(OM,/obj/structure/spacevine) && get_pin_data(IC_INPUT, 2) == 2)
+ qdel(OM)
+ activate_pin(2)
return
+ var/obj/machinery/hydroponics/AM = OM
+ if(!istype(AM)) //Invalid input
+ return FALSE
var/mob/living/M = get_turf(AM)
if(!M.Adjacent(T))
return //Can't reach
@@ -276,6 +283,7 @@
qdel(AM.myseed)
AM.myseed = null
AM.weedlevel = 0 //Has a side effect of cleaning up those nasty weeds
+ AM.dead = 0
AM.update_icon()
else
activate_pin(2)
@@ -284,7 +292,7 @@
/obj/item/integrated_circuit/manipulation/grabber
name = "grabber"
- desc = "A circuit with it's own inventory for small/medium items, used to grab and store things."
+ desc = "A circuit with it's own inventory for tiny/small items, used to grab and store things."
icon_state = "grabber"
extended_desc = "The circuit accepts a reference to thing to be grabbed. It can store up to 10 things. Modes: 1 for grab. 0 for eject the first thing. -1 for eject all."
w_class = WEIGHT_CLASS_SMALL
@@ -307,7 +315,7 @@
var/mode = get_pin_data(IC_INPUT, 2)
if(mode == 1)
- if(check_target(AM, exclude_contents = TRUE))
+ if(check_target(AM))
if((contents.len < max_items) && (!max_w_class || AM.w_class <= max_w_class))
AM.forceMove(src)
if(mode == 0)
diff --git a/code/modules/integrated_electronics/subtypes/reagents.dm b/code/modules/integrated_electronics/subtypes/reagents.dm
index 33f92c3646..0c66c3a943 100644
--- a/code/modules/integrated_electronics/subtypes/reagents.dm
+++ b/code/modules/integrated_electronics/subtypes/reagents.dm
@@ -9,6 +9,11 @@
. = ..()
if(volume)
create_reagents(volume)
+ push_vol()
+
+/obj/item/integrated_circuit/reagent/proc/push_vol()
+ set_pin_data(IC_OUTPUT, 1, reagents.total_volume)
+ push_data()
/obj/item/integrated_circuit/reagent/smoke
name = "smoke generator"
@@ -29,7 +34,8 @@
)
activators = list(
"create smoke" = IC_PINTYPE_PULSE_IN,
- "on smoked" = IC_PINTYPE_PULSE_OUT
+ "on smoked" = IC_PINTYPE_PULSE_OUT,
+ "push ref" = IC_PINTYPE_PULSE_IN
)
spawn_flags = IC_SPAWN_RESEARCH
power_draw_per_use = 20
@@ -40,24 +46,27 @@
//reset warning only if we have reagents now
if(changetype == ADD_REAGENT)
notified = FALSE
- set_pin_data(IC_OUTPUT, 1, reagents.total_volume)
- push_data()
+ push_vol()
-/obj/item/integrated_circuit/reagent/smoke/do_work()
- if(!reagents || (reagents.total_volume < IC_SMOKE_REAGENTS_MINIMUM_UNITS))
- return
- var/location = get_turf(src)
- var/datum/effect_system/smoke_spread/chem/S = new
- S.attach(location)
- playsound(location, 'sound/effects/smoke.ogg', 50, 1, -3)
- if(S)
- S.set_up(reagents, smoke_radius, location, notified)
- if(!notified)
- notified = TRUE
- S.start()
-
- reagents.clear_reagents()
- activate_pin(2)
+/obj/item/integrated_circuit/reagent/smoke/do_work(ord)
+ switch(ord)
+ if(1)
+ if(!reagents || (reagents.total_volume < IC_SMOKE_REAGENTS_MINIMUM_UNITS))
+ return
+ var/location = get_turf(src)
+ var/datum/effect_system/smoke_spread/chem/S = new
+ S.attach(location)
+ playsound(location, 'sound/effects/smoke.ogg', 50, 1, -3)
+ if(S)
+ S.set_up(reagents, smoke_radius, location, notified)
+ if(!notified)
+ notified = TRUE
+ S.start()
+ reagents.clear_reagents()
+ activate_pin(2)
+ if(3)
+ set_pin_data(IC_OUTPUT, 2, WEAKREF(src))
+ push_data()
/obj/item/integrated_circuit/reagent/injector
name = "integrated hypo-injector"
@@ -85,7 +94,9 @@
activators = list(
"inject" = IC_PINTYPE_PULSE_IN,
"on injected" = IC_PINTYPE_PULSE_OUT,
- "on fail" = IC_PINTYPE_PULSE_OUT
+ "on fail" = IC_PINTYPE_PULSE_OUT,
+ "push ref" = IC_PINTYPE_PULSE_IN
+
)
spawn_flags = IC_SPAWN_DEFAULT|IC_SPAWN_RESEARCH
power_draw_per_use = 15
@@ -93,15 +104,8 @@
var/transfer_amount = 10
var/busy = FALSE
-/obj/item/integrated_circuit/reagent/injector/interact(mob/user)
- set_pin_data(IC_OUTPUT, 2, WEAKREF(src))
- push_data()
- ..()
-
-
/obj/item/integrated_circuit/reagent/injector/on_reagent_change(changetype)
- set_pin_data(IC_OUTPUT, 1, reagents.total_volume)
- push_data()
+ push_vol()
/obj/item/integrated_circuit/reagent/injector/on_data_written()
var/new_amount = get_pin_data(IC_INPUT, 2)
@@ -127,7 +131,15 @@
temp_reagents.clear_reagents()
qdel(temp_reagents)
-/obj/item/integrated_circuit/reagent/injector/do_work()
+/obj/item/integrated_circuit/reagent/injector/do_work(ord)
+ switch(ord)
+ if(1)
+ inject()
+ if(4)
+ set_pin_data(IC_OUTPUT, 2, WEAKREF(src))
+ push_data()
+
+/obj/item/integrated_circuit/reagent/injector/proc/inject()
set waitfor = FALSE // Don't sleep in a proc that is called by a processor without this set, otherwise it'll delay the entire thing
var/atom/movable/AM = get_pin_data_as_type(IC_INPUT, 1, /atom/movable)
var/atom/movable/acting_object = get_object()
@@ -281,17 +293,15 @@
"volume used" = IC_PINTYPE_NUMBER,
"self reference" = IC_PINTYPE_REF
)
- activators = list()
+ activators = list("push ref" = IC_PINTYPE_PULSE_OUT)
spawn_flags = IC_SPAWN_DEFAULT|IC_SPAWN_RESEARCH
-/obj/item/integrated_circuit/reagent/storage/interact(mob/user)
+/obj/item/integrated_circuit/reagent/storage/do_work()
set_pin_data(IC_OUTPUT, 2, WEAKREF(src))
push_data()
- ..()
/obj/item/integrated_circuit/reagent/storage/on_reagent_change(changetype)
- set_pin_data(IC_OUTPUT, 1, reagents.total_volume)
- push_data()
+ push_vol()
/obj/item/integrated_circuit/reagent/storage/cryo
name = "cryo reagent storage"
@@ -306,6 +316,7 @@
. = ..()
reagents.set_reacting(FALSE)
+
/obj/item/integrated_circuit/reagent/storage/big
name = "big reagent storage"
desc = "Stores liquid inside, and away from electrical components. Can store up to 180u."
@@ -317,6 +328,99 @@
complexity = 16
spawn_flags = IC_SPAWN_RESEARCH
+/obj/item/integrated_circuit/reagent/storage/grinder
+ name = "reagent grinder"
+ desc = "This is reagent grinder.It accepts ref to something and refines it into reagents. Can store up to 100u."
+ icon_state = "blender"
+ extended_desc = ""
+ inputs = list(
+ "target" = IC_PINTYPE_REF,
+ )
+ outputs = list(
+ "volume used" = IC_PINTYPE_NUMBER,
+ "self reference" = IC_PINTYPE_REF
+ )
+ activators = list(
+ "grind" = IC_PINTYPE_PULSE_IN,
+ "on grind" = IC_PINTYPE_PULSE_OUT,
+ "on fail" = IC_PINTYPE_PULSE_OUT,
+ "push ref" = IC_PINTYPE_PULSE_IN
+ )
+ volume = 100
+ power_draw_per_use = 150
+ complexity = 16
+ spawn_flags = IC_SPAWN_RESEARCH
+
+
+/obj/item/integrated_circuit/reagent/storage/grinder/do_work(ord)
+ switch(ord)
+ if(1)
+ grind()
+ if(4)
+ set_pin_data(IC_OUTPUT, 2, WEAKREF(src))
+ push_data()
+
+/obj/item/integrated_circuit/reagent/storage/grinder/proc/grind()
+ if(reagents.total_volume >= reagents.maximum_volume)
+ activate_pin(3)
+ return FALSE
+ var/obj/item/I = get_pin_data_as_type(IC_INPUT, 1, /obj/item)
+ if(istype(I)&&(I.grind_results)&&check_target(I)&&(I.on_grind(src) != -1))
+ reagents.add_reagent_list(I.grind_results)
+ if(I.reagents)
+ I.reagents.trans_to(src, I.reagents.total_volume)
+ qdel(I)
+ activate_pin(2)
+ return TRUE
+ activate_pin(3)
+ return FALSE
+
+obj/item/integrated_circuit/reagent/storage/juicer
+ name = "reagent juicer"
+ desc = "This is reagent juicer.It accepts ref to something and refines it into reagents. Can store up to 100u."
+ icon_state = "blender"
+ extended_desc = ""
+ inputs = list(
+ "target" = IC_PINTYPE_REF,
+ )
+ outputs = list(
+ "volume used" = IC_PINTYPE_NUMBER,
+ "self reference" = IC_PINTYPE_REF
+ )
+ activators = list(
+ "juice" = IC_PINTYPE_PULSE_IN,
+ "on juice" = IC_PINTYPE_PULSE_OUT,
+ "on fail" = IC_PINTYPE_PULSE_OUT,
+ "push ref" = IC_PINTYPE_PULSE_IN
+ )
+ volume = 100
+ power_draw_per_use = 150
+ complexity = 16
+ spawn_flags = IC_SPAWN_RESEARCH
+
+/obj/item/integrated_circuit/reagent/storage/juicer/do_work(ord)
+ switch(ord)
+ if(1)
+ juice()
+ if(4)
+ set_pin_data(IC_OUTPUT, 2, WEAKREF(src))
+ push_data()
+
+/obj/item/integrated_circuit/reagent/storage/juicer/proc/juice()
+ if(reagents.total_volume >= reagents.maximum_volume)
+ activate_pin(3)
+ return FALSE
+ var/obj/item/I = get_pin_data_as_type(IC_INPUT, 1, /obj/item)
+ if(istype(I)&&check_target(I)&&(I.juice_results)&&(I.on_juice() != -1))
+ reagents.add_reagent_list(I.juice_results)
+ qdel(I)
+ activate_pin(2)
+ return TRUE
+ activate_pin(3)
+ return FALSE
+
+
+
/obj/item/integrated_circuit/reagent/storage/scan
name = "reagent scanner"
desc = "Stores liquid inside, and away from electrical components. Can store up to 60u. On pulse this beaker will send list of contained reagents."
@@ -330,17 +434,22 @@
"list of reagents" = IC_PINTYPE_LIST
)
activators = list(
- "scan" = IC_PINTYPE_PULSE_IN
+ "scan" = IC_PINTYPE_PULSE_IN,
+ "push ref" = IC_PINTYPE_PULSE_IN
)
spawn_flags = IC_SPAWN_RESEARCH
-/obj/item/integrated_circuit/reagent/storage/scan/do_work()
- var/cont[0]
- for(var/datum/reagent/RE in reagents.reagent_list)
- cont += RE.id
- set_pin_data(IC_OUTPUT, 3, cont)
- push_data()
-
+/obj/item/integrated_circuit/reagent/storage/scan/do_work(ord)
+ switch(ord)
+ if(1)
+ var/cont[0]
+ for(var/datum/reagent/RE in reagents.reagent_list)
+ cont += RE.id
+ set_pin_data(IC_OUTPUT, 3, cont)
+ push_data()
+ if(2)
+ set_pin_data(IC_OUTPUT, 2, WEAKREF(src))
+ push_data()
/obj/item/integrated_circuit/reagent/filter
name = "reagent filter"
@@ -394,7 +503,8 @@
if(!source.reagents || !target.reagents)
return
- if(!source.is_drainable() || !target.is_refillable())
+ // FALSE in those procs makes mobs invalid targets.
+ if(!source.is_drawable(FALSE) || !target.is_injectable(FALSE))
return
if(target.reagents.maximum_volume - target.reagents.total_volume <= 0)
@@ -410,3 +520,45 @@
activate_pin(2)
push_data()
+/obj/item/integrated_circuit/reagent/storage/heater
+ name = "chemical heater"
+ desc = "Stores liquid inside, and away from electrical components. Can store up to 60u. Will heat or freeze reagents \
+ to target temperature, when turned on."
+ icon_state = "heater"
+ container_type = OPENCONTAINER
+ complexity = 8
+ inputs = list(
+ "target temperature" = IC_PINTYPE_NUMBER,
+ "on" = IC_PINTYPE_BOOLEAN
+ )
+ inputs_default = list("1" = 300)
+ outputs = list("volume used" = IC_PINTYPE_NUMBER,"self reference" = IC_PINTYPE_REF,"temperature" = IC_PINTYPE_NUMBER)
+ spawn_flags = IC_SPAWN_RESEARCH
+ var/heater_coefficient = 0.1
+
+/obj/item/integrated_circuit/reagent/storage/heater/on_data_written()
+ if(get_pin_data(IC_INPUT, 2))
+ power_draw_idle = 30
+ else
+ power_draw_idle = 0
+
+/obj/item/integrated_circuit/reagent/storage/heater/Initialize()
+ .=..()
+ START_PROCESSING(SScircuit, src)
+
+/obj/item/integrated_circuit/reagent/storage/heater/Destroy()
+ STOP_PROCESSING(SScircuit, src)
+ return ..()
+
+/obj/item/integrated_circuit/reagent/storage/heater/process()
+ if(power_draw_idle)
+ var/target_temperature = get_pin_data(IC_INPUT, 1)
+ if(reagents.chem_temp > target_temperature)
+ reagents.chem_temp += min(-1, (target_temperature - reagents.chem_temp) * heater_coefficient)
+ if(reagents.chem_temp < target_temperature)
+ reagents.chem_temp += max(1, (target_temperature - reagents.chem_temp) * heater_coefficient)
+
+ reagents.chem_temp = round(reagents.chem_temp)
+ reagents.handle_reactions()
+ set_pin_data(IC_OUTPUT, 3, reagents.chem_temp)
+ push_data()
diff --git a/code/modules/integrated_electronics/subtypes/smart.dm b/code/modules/integrated_electronics/subtypes/smart.dm
index ec59c3cab1..37a38677b0 100644
--- a/code/modules/integrated_electronics/subtypes/smart.dm
+++ b/code/modules/integrated_electronics/subtypes/smart.dm
@@ -27,6 +27,6 @@
push_data()
return // Can't see the target.
- set_pin_data(IC_OUTPUT, 1, get_dir(get_turf(src), get_turf(A)))
+ set_pin_data(IC_OUTPUT, 1, get_dir(get_turf(src), get_step_towards2(get_turf(src),A)))
push_data()
activate_pin(2)
diff --git a/icons/obj/assemblies/electronic_components.dmi b/icons/obj/assemblies/electronic_components.dmi
index 1852079e73..a9dac06d6b 100644
Binary files a/icons/obj/assemblies/electronic_components.dmi and b/icons/obj/assemblies/electronic_components.dmi differ
]