diff --git a/code/game/objects/items/circuitboards/machine_circuitboards.dm b/code/game/objects/items/circuitboards/machine_circuitboards.dm
index a26301693f..82c307d8e5 100644
--- a/code/game/objects/items/circuitboards/machine_circuitboards.dm
+++ b/code/game/objects/items/circuitboards/machine_circuitboards.dm
@@ -599,8 +599,8 @@
/obj/item/stock_parts/capacitor = 6)
/obj/item/circuitboard/machine/chem_dispenser
- name = "Portable Chem Dispenser (Machine Board)"
- build_path = /obj/machinery/chem_dispenser/constructable
+ name = "Chem Dispenser (Machine Board)"
+ build_path = /obj/machinery/chem_dispenser
req_components = list(
/obj/item/stock_parts/matter_bin = 2,
/obj/item/stock_parts/capacitor = 1,
diff --git a/code/modules/reagents/chemistry/machinery/chem_dispenser.dm b/code/modules/reagents/chemistry/machinery/chem_dispenser.dm
index 3b06b4c71e..f280b4f171 100644
--- a/code/modules/reagents/chemistry/machinery/chem_dispenser.dm
+++ b/code/modules/reagents/chemistry/machinery/chem_dispenser.dm
@@ -9,15 +9,17 @@
idle_power_usage = 40
interact_offline = TRUE
resistance_flags = FIRE_PROOF | ACID_PROOF
+ circuit = /obj/item/circuitboard/machine/chem_dispenser
var/cell_type = /obj/item/stock_parts/cell/high
var/obj/item/stock_parts/cell/cell
- var/powerefficiency = 0.01
+ var/powerefficiency = 0.1
var/amount = 30
var/recharged = 0
var/recharge_delay = 5
var/mutable_appearance/beaker_overlay
var/working_state = "dispenser_working"
var/nopower_state = "dispenser_nopower"
+ var/macrotier = 1
var/obj/item/reagent_containers/beaker = null
var/list/dispensable_reagents = list(
"hydrogen",
@@ -199,7 +201,7 @@ obj/machinery/chem_dispenser/update_icon()
var/actual = min(amount, (cell.charge * powerefficiency)*10, free)
R.add_reagent(reagent, actual)
- cell.use((actual / 10) / powerefficiency)
+ cell.use(actual / powerefficiency)
work_animation()
. = TRUE
if("remove")
@@ -219,16 +221,17 @@ obj/machinery/chem_dispenser/update_icon()
if("dispense_recipe")
var/recipe_to_use = params["recipe"]
var/list/chemicals_to_dispense = process_recipe_list(recipe_to_use)
+ var/res = get_macro_resolution()
for(var/key in chemicals_to_dispense) // i suppose you could edit the list locally before passing it
var/list/keysplit = splittext(key," ")
var/r_id = keysplit[1]
if(beaker && dispensable_reagents.Find(r_id)) // but since we verify we have the reagent, it'll be fine
var/datum/reagents/R = beaker.reagents
var/free = R.maximum_volume - R.total_volume
- var/actual = min(chemicals_to_dispense[key], (cell.charge * powerefficiency)*10, free)
+ var/actual = min(round(chemicals_to_dispense[key], res), (cell.charge * powerefficiency)*10, free)
if(actual)
R.add_reagent(r_id, actual)
- cell.use((actual / 10) / powerefficiency)
+ cell.use(actual / powerefficiency)
work_animation()
if("clear_recipes")
var/yesno = alert("Clear all recipes?",, "Yes","No")
@@ -241,21 +244,35 @@ obj/machinery/chem_dispenser/update_icon()
var/list/first_process = splittext(recipe, ";")
if(!LAZYLEN(first_process))
return
+ var/res = get_macro_resolution()
+ var/resmismatch = FALSE
for(var/reagents in first_process)
- var/list/fuck = splittext(reagents, "=")
- if(dispensable_reagents.Find(fuck[1]))
+ var/list/reagent = splittext(reagents, "=")
+ if(dispensable_reagents.Find(reagent[1]))
+ if (!resmismatch && !check_macro_part(reagents, res))
+ resmismatch = TRUE
continue
else
- var/temp = fuck[1]
+ var/chemid = reagent[1]
visible_message("[src] buzzes.", "You hear a faint buzz.")
- to_chat(usr, "[src] cannot find Chemical ID: [temp]!")
+ to_chat(usr, "[src] cannot find Chemical ID: [chemid]!")
playsound(src, "sound/machines/buzz-two.ogg", 50, 1)
return
+ if (resmismatch && alert("[src] is not yet capable of replicating this recipe with the precision it needs, do you want to save it anyway?",, "Yes","No") == "No")
+ return
saved_recipes += list(list("recipe_name" = name, "contents" = recipe))
/obj/machinery/chem_dispenser/attackby(obj/item/I, mob/user, params)
if(default_unfasten_wrench(user, I))
return
+ if(default_deconstruction_screwdriver(user, "dispenser-o", "dispenser", I))
+ return
+
+ if(exchange_parts(user, I))
+ return
+
+ if(default_deconstruction_crowbar(I))
+ return
if(istype(I, /obj/item/reagent_containers) && !(I.flags_1 & ABSTRACT_1) && I.is_open_container())
var/obj/item/reagent_containers/B = I
. = 1 //no afterattack
@@ -294,92 +311,48 @@ obj/machinery/chem_dispenser/update_icon()
visible_message("[src] malfunctions, spraying chemicals everywhere!")
..()
-/obj/machinery/chem_dispenser/constructable
- name = "portable chem dispenser"
- icon = 'icons/obj/chemical.dmi'
- icon_state = "minidispenser"
- powerefficiency = 0.001
- amount = 5
- recharge_delay = 20
- dispensable_reagents = list()
- circuit = /obj/item/circuitboard/machine/chem_dispenser
- working_state = "minidispenser_working"
- nopower_state = "minidispenser_nopower"
- var/static/list/dispensable_reagent_tiers = list(
- list(
- "hydrogen",
- "oxygen",
- "silicon",
- "phosphorus",
- "sulfur",
- "carbon",
- "nitrogen",
- "water"
- ),
- list(
- "lithium",
- "sugar",
- "sacid",
- "copper",
- "mercury",
- "sodium",
- "iodine",
- "bromine"
- ),
- list(
- "ethanol",
- "chlorine",
- "potassium",
- "aluminium",
- "radium",
- "fluorine",
- "iron",
- "welding_fuel",
- "silver",
- "stable_plasma"
- ),
- list(
- "oil",
- "ash",
- "acetone",
- "saltpetre",
- "ammonia",
- "diethylamine"
- )
- )
-/obj/machinery/chem_dispenser/constructable/RefreshParts()
+/obj/machinery/chem_dispenser/RefreshParts()
var/time = 0
- var/i
+ var/newpowereff = 0.0666666
for(var/obj/item/stock_parts/cell/P in component_parts)
cell = P
for(var/obj/item/stock_parts/matter_bin/M in component_parts)
- time += M.rating
+ newpowereff += 0.0166666666*M.rating
for(var/obj/item/stock_parts/capacitor/C in component_parts)
time += C.rating
recharge_delay = 30/(time/2) //delay between recharges, double the usual time on lowest 50% less than usual on highest
for(var/obj/item/stock_parts/manipulator/M in component_parts)
- for(i=1, i<=M.rating, i++)
- dispensable_reagents |= dispensable_reagent_tiers[i]
- dispensable_reagents = sortList(dispensable_reagents)
+ if (M.rating > macrotier)
+ macrotier = M.rating
+ powerefficiency = round(newpowereff, 0.01)
-/obj/machinery/chem_dispenser/constructable/attackby(obj/item/I, mob/user, params)
- if(default_deconstruction_screwdriver(user, "minidispenser-o", "minidispenser", I))
- return
- if(exchange_parts(user, I))
- return
- if(default_deconstruction_crowbar(I))
- return
- return ..()
-
-/obj/machinery/chem_dispenser/constructable/on_deconstruction()
+/obj/machinery/chem_dispenser/on_deconstruction()
if(beaker)
beaker.forceMove(drop_location())
beaker = null
return ..()
+/obj/machinery/chem_dispenser/proc/get_macro_resolution()
+ . = 5
+ if (macrotier > 1)
+ . -= macrotier // 5 for tier1, 3 for 2, 2 for 3, 1 for 4.
+
+/obj/machinery/chem_dispenser/proc/check_macro(var/macro)
+ var/res = get_macro_resolution()
+ for (var/reagent in splittext(macro, ";"))
+ if (!check_macro_part(reagent, res))
+ return FALSE
+ return TRUE
+
+/obj/machinery/chem_dispenser/proc/check_macro_part(var/part, var/res = get_macro_resolution())
+ var/detail = splittext(part, "=")
+ if (round(text2num(detail[2]), res) != text2num(detail[2]))
+ return FALSE
+ return TRUE
+
/obj/machinery/chem_dispenser/proc/process_recipe_list(var/fucking_hell)
var/list/key_list = list()
var/list/final_list = list()
@@ -389,12 +362,6 @@ obj/machinery/chem_dispenser/update_icon()
final_list += list(avoid_assoc_duplicate_keys(fuck[1],key_list) = text2num(fuck[2]))
return final_list
-/obj/machinery/chem_dispenser/constructable/display_beaker()
- var/mutable_appearance/b_o = beaker_overlay || mutable_appearance(icon, "disp_beaker")
- b_o.pixel_y = -4
- b_o.pixel_x = -4
- return b_o
-
/obj/machinery/chem_dispenser/drinks/display_beaker()
var/mutable_appearance/b_o = beaker_overlay || mutable_appearance(icon, "disp_beaker")
switch(dir)