Fixed machine processing for ores going in the negatives for alloying (#18781)

Fixed a runtime found on mechs.
Fixed machine processing for ores going in the negatives for alloying.
Some more optimizations, DMdocs, turned a var into a global one, some
defines added and made into bitflags, yada yada you know the usual deal.
This commit is contained in:
Fluffy
2024-04-04 12:45:07 +02:00
committed by GitHub
parent 55e724e5d4
commit 6e3ee53783
3 changed files with 103 additions and 25 deletions
+56 -22
View File
@@ -1,3 +1,9 @@
//Modes the smelter can work with, bitflags
#define SMELTER_MODE_IDLE BITFLAG(0)
#define SMELTER_MODE_ALLOYING BITFLAG(1)
#define SMELTER_MODE_COMPRESSING BITFLAG(2)
#define SMELTER_MODE_SMELTING BITFLAG(3)
/obj/machinery/mineral
var/id //used for linking machines to consoles
@@ -117,14 +123,14 @@
if(!O)
continue
var/processing_type = ""
switch(machine.ores_processing[ore])
if(0)
switch(machine.ores_processing[ore]) //Yes we could use bitflags, but I don't care enough about it here
if(SMELTER_MODE_IDLE)
processing_type = "Idle"
if(1)
if(SMELTER_MODE_SMELTING)
processing_type = "Smelt"
if(2)
if(SMELTER_MODE_COMPRESSING)
processing_type = "Compress"
if(3)
if(SMELTER_MODE_ALLOYING)
processing_type = "Alloy"
ore_list += list(list("name" = capitalize_first_letters(O.display_name), "processing" = processing_type, "stored" = machine.ores_stored[ore], "ore" = ore))
data["oreList"] = ore_list
@@ -158,13 +164,13 @@
switch(choice)
if("Nothing")
choice = 0
choice = SMELTER_MODE_IDLE
if("Smelting")
choice = 1
choice = SMELTER_MODE_SMELTING
if("Compressing")
choice = 2
choice = SMELTER_MODE_COMPRESSING
if("Alloying")
choice = 3
choice = SMELTER_MODE_ALLOYING
machine.ores_processing[ore_name] = choice
return TRUE
@@ -278,6 +284,10 @@
/**********************Mineral processing unit**************************/
/**
* A list containing alloy data, initialized only once by the first `/obj/machinery/mineral/processing_unit` that initializes
*/
GLOBAL_LIST_EMPTY_TYPED(alloy_data, /datum/alloy)
/obj/machinery/mineral/processing_unit
name = "industrial smelter" //This isn't actually a goddamn furnace, we're in space and it's processing platinum and flammable phoron... //lol fuk u bay it is //i'm gay // based and redpilled
@@ -296,9 +306,24 @@
///How many sheets in a second this smelter can make (more or less, rounded up depending on ticklag)
var/sheets_per_second = 50
/**
* An associative list
*
* Key is a string, representing the ore name (eg. uranium, diamond, gold)
*
* Value is a bitflag, representing the operation mode for said ore, see `SMELTER_MODE_*` defines
*/
var/list/ores_processing[0]
/**
* An associative list
*
* Key is a string, representing the ore name (eg. uranium, diamond, gold)
*
* Value is a number, representing how many ores are stored in the device for said ore type
*/
var/list/ores_stored[0]
var/static/list/alloy_data
var/active = 0
idle_power_usage = 15
active_power_usage = 150
@@ -314,14 +339,13 @@
/obj/machinery/mineral/processing_unit/Initialize()
. = ..()
// initialize static alloy_data list
if(!alloy_data)
alloy_data = list()
// initialize static alloy_data list, if it's not already initialized
if(!length(GLOB.alloy_data))
for(var/alloytype in subtypesof(/datum/alloy))
alloy_data += new alloytype()
GLOB.alloy_data += new alloytype()
for(var/O in GLOB.ore_data)
ores_processing[O] = 0
ores_processing[O] = SMELTER_MODE_IDLE
ores_stored[O] = 0
return INITIALIZE_HINT_LATELOAD
@@ -361,6 +385,8 @@
RegisterSignal(console, COMSIG_QDELETING, PROC_REF(handle_console_deletion))
/obj/machinery/mineral/processing_unit/proc/handle_console_deletion()
SIGNAL_HANDLER
console = null
/obj/machinery/mineral/processing_unit/attackby(obj/item/attacking_item, mob/user)
@@ -408,13 +434,14 @@
if(sheets >= ROUND_UP(sheets_per_second*seconds_per_tick))
break
if(ores_stored[metal] > 0 && ores_processing[metal] != 0)
if(ores_stored[metal] > 0 && ores_processing[metal] != SMELTER_MODE_IDLE)
var/ore/O = GLOB.ore_data[metal]
if(!O)
continue
if(ores_processing[metal] == 3 && O.alloy) //Alloying.
for(var/datum/alloy/A in alloy_data)
//Alloying materials
if(ores_processing[metal] & SMELTER_MODE_ALLOYING && O.alloy)
for(var/datum/alloy/A in GLOB.alloy_data)
if(A.metaltag in tick_alloys)
continue
@@ -427,7 +454,7 @@
for(var/needs_metal in A.requires)
//Check if we're alloying the needed metal and have it stored.
if(ores_processing[needs_metal] != 3 || ores_stored[needs_metal] < A.requires[needs_metal])
if(!(ores_processing[needs_metal] & SMELTER_MODE_ALLOYING) || ores_stored[needs_metal] < A.requires[needs_metal])
enough_metal = FALSE
break
@@ -450,7 +477,8 @@
console.alloy_mats[A] = console.alloy_mats[A] + 1
new A.product(output)
else if(ores_processing[metal] == 2 && O.compresses_to) //Compressing.
//Compressing materials
else if(ores_processing[metal] & SMELTER_MODE_COMPRESSING && O.compresses_to)
var/can_make = Clamp(ores_stored[metal], 0, ROUND_UP(sheets_per_second*seconds_per_tick) - sheets)
if(can_make % 2 > 0)
can_make--
@@ -460,7 +488,7 @@
if(!istype(M) || !can_make || ores_stored[metal] < 1)
continue
for(var/_ in 1 to (can_make*2))
for(var/_ in 1 to (can_make/2))
if(console)
console.points += O.worth * 2
use_power_oneoff(300)
@@ -469,7 +497,8 @@
console.output_mats[M] += 1
new M.stack_type(output)
else if(ores_processing[metal] == 1 && O.smelts_to) //Smelting.
//Smelting materials
else if(ores_processing[metal] & SMELTER_MODE_SMELTING && O.smelts_to)
var/can_make = Clamp(ores_stored[metal], 0, ROUND_UP(sheets_per_second*seconds_per_tick) - sheets)
var/material/M = SSmaterials.get_material_by_name(O.smelts_to)
@@ -514,3 +543,8 @@
laser_rating += P.rating
sheets_per_second += scan_rating + cap_rating + laser_rating
#undef SMELTER_MODE_IDLE
#undef SMELTER_MODE_ALLOYING
#undef SMELTER_MODE_COMPRESSING
#undef SMELTER_MODE_SMELTING