[MIRROR] Autounlock techwebs are shared between machines that use them. [MDB IGNORE] (#18734)

* Autounlock techwebs are shared between machines that use them. (#72515)

## About The Pull Request

Did you know that for every Autolathe, Limbgrower, Biogenerator, ORM,
and Smelter that was built, an entire new techweb was made? The average
round has 2 ORMs (smelters count) if not more from ORM deconstruction
objective, 2 biogenerators, several autolathes and generally 0-1
limbgrower, I think there's more techwebs being created than we need.

Creating a whole techweb was a pretty terrible way to optimize this, so
I made a global list that stores these techwebs. Created on demand,
these autounlocking techwebs now share between the machines that use
them. It also generate all hacked nodes which will be visible if the
machine is hacked, instead of 'researching' them for each hacked
individual machine.

The 'specialized' techweb subtype was removed because its sole purpose
was to allow autounlocking to be a subtype of it. Now autounlocking is
just the direct subtype. I also removed mechfab autounlocking type
because it wasn't used, mechfabs use techwebs directly.

Autolathes and Limbgrowers now locally store 'imported designs' which
are things uploaded from technology disks. Outside of this, the
autounlocking techweb subtype now stores 'hacked designs' which unlocks
when the machine is emagged.
While doing this, I saw ORMs and Biogenerators had disks you can insert
into them, but I did not find anything that can actually be uploaded to
them (I saw Alien Alloys as a possibility, but there's no such disk to
allow uploading this alloy to the machine, and I didn't think an entire
system for 1 single alloy was worth keeping around), so I removed this
unused feature from both machines.

I merged 'Hacked' and 'Emagged' categories because they served the same
purpose, 'hacked' being on hacked autolathes and 'emagged' being on
hacked (emagged) limbgrowers.

Tech disk techwebs (which is created every time a disk is made, however
I hope to change this in the future) into it's own subtype, so admins
understand where its from when looking in VV panel (because I was
confused when I saw them at first).

``autolathe_crafted`` proc was removed because it was entirely unused
too.

Now it looks like this, which I consider an improvement:

![image](https://user-images.githubusercontent.com/53777086/211052875-9215a84d-fb04-450b-a120-4d0316cec6ff.png)

## Why It's Good For The Game

We no longer initialize a brand new techweb for no reason whatsoever.
Each techweb made is making entire lists of experiments and research
papers, all of which is never to be seen in-game and is completely
useless to the player. Cutting down on these techwebs is a good first
step to this needless initializing.

## Changelog

🆑
qol: Removed the tech disk part of the ORM's UI as it was entirely
unused, now it's a little more compact with less scrolling needed.
refactor: Autolathes, Limb growers, Biogenerators, ORMs and Smelters now
share techwebs with other machines of their types, rather than all make
new techwebs each time. This means they only build their nodes once,
including hacked ones. Instead of researching nodes on hacking the
machine, they now show hacked ones depending on if it's hacked.
/🆑

Co-authored-by: Zephyr <12817816+ZephyrTFA@ users.noreply.github.com>

* Autounlock techwebs are shared between machines that use them.

Co-authored-by: John Willard <53777086+JohnFulpWillard@users.noreply.github.com>
Co-authored-by: Zephyr <12817816+ZephyrTFA@ users.noreply.github.com>
This commit is contained in:
SkyratBot
2023-01-14 18:54:19 -08:00
committed by GitHub
co-authored by Zephyr John Willard
parent 0087464bde
commit 27492ff60d
14 changed files with 176 additions and 277 deletions
@@ -190,5 +190,4 @@
// Meta categories
#define RND_CATEGORY_INITIAL "initial"
#define RND_CATEGORY_HACKED "hacked"
#define RND_CATEGORY_EMAGGED "emagged"
#define RND_CATEGORY_IMPORTED "/Imported Designs"
+13 -24
View File
@@ -16,15 +16,18 @@
var/creation_efficiency = 1.6
var/datum/design/being_built
var/datum/techweb/stored_research
var/datum/techweb/autounlocking/stored_research
///Designs imported from technology disks that we can print.
var/list/imported_designs = list()
/obj/machinery/autolathe/Initialize(mapload)
AddComponent(/datum/component/material_container, SSmaterials.materials_by_category[MAT_CATEGORY_ITEM_MATERIAL], 0, MATCONTAINER_EXAMINE, _after_insert = CALLBACK(src, PROC_REF(AfterMaterialInsert)))
. = ..()
wires = new /datum/wires/autolathe(src)
stored_research = new /datum/techweb/specialized/autounlocking/autolathe
if(!GLOB.autounlock_techwebs[/datum/techweb/autounlocking/autolathe])
GLOB.autounlock_techwebs[/datum/techweb/autounlocking/autolathe] = new /datum/techweb/autounlocking/autolathe
stored_research = GLOB.autounlock_techwebs[/datum/techweb/autounlocking/autolathe]
/obj/machinery/autolathe/Destroy()
QDEL_NULL(wires)
@@ -47,6 +50,10 @@
var/list/data = list()
data["designs"] = handle_designs(stored_research.researched_designs)
if(imported_designs.len)
data["designs"] += handle_designs(imported_designs)
if(hacked)
data["designs"] += handle_designs(stored_research.hacked_designs)
return data
@@ -141,17 +148,15 @@
/obj/machinery/autolathe/ui_act(action, list/params)
. = ..()
if(.)
return
if(action == "make")
var/design_id = params["id"]
if(!istext(design_id))
return
if(!stored_research.isDesignResearchedID(design_id))
if(!stored_research.researched_designs.Find(design_id) && !imported_designs.Find(design_id))
return
var/datum/design/design = SSresearch.techweb_design_by_id(design_id)
@@ -161,7 +166,6 @@
if (busy)
to_chat(usr, span_alert("The autolathe is busy. Please wait for completion of previous operation."))
return
being_built = design
@@ -258,7 +262,7 @@
if(!blueprint)
continue
if(blueprint.build_type & AUTOLATHE)
stored_research.add_design(blueprint)
imported_designs += blueprint.id
else
LAZYADD(not_imported, blueprint.name)
if(not_imported)
@@ -318,11 +322,9 @@
if(is_stack)
var/obj/item/stack/N = new being_built.build_path(A, multiplier, FALSE)
N.update_appearance()
N.autolathe_crafted(src)
else
for(var/i in 1 to multiplier)
var/obj/item/new_item = new being_built.build_path(A)
new_item.autolathe_crafted(src)
if(length(picked_materials))
new_item.set_custom_materials(picked_materials, 1 / multiplier) //Ensure we get the non multiplied amount
@@ -411,21 +413,8 @@
/obj/machinery/autolathe/proc/adjust_hacked(state)
hacked = state
for(var/id in SSresearch.techweb_designs)
var/datum/design/D = SSresearch.techweb_design_by_id(id)
if((D.build_type & AUTOLATHE) && (RND_CATEGORY_HACKED in D.category))
if(hacked)
stored_research.add_design(D)
else
stored_research.remove_design(D)
update_static_data_for_all_viewers()
/obj/machinery/autolathe/hacked/Initialize(mapload)
. = ..()
adjust_hacked(TRUE)
//Called when the object is constructed by an autolathe
//Has a reference to the autolathe so you can do !!FUN!! things with hacked lathes
/obj/item/proc/autolathe_crafted(obj/machinery/autolathe/A)
return
+30 -25
View File
@@ -19,16 +19,28 @@
/// The design we're printing currently.
var/datum/design/being_built
/// Our internal techweb for limbgrower designs.
var/datum/techweb/stored_research
var/datum/techweb/autounlocking/stored_research
/// All the categories of organs we can print.
var/list/categories = list(SPECIES_HUMAN, SPECIES_LIZARD, SPECIES_MOTH, SPECIES_PLASMAMAN, SPECIES_ETHEREAL, RND_CATEGORY_LIMBS_OTHER, RND_CATEGORY_LIMBS_DIGITIGRADE)
///Designs imported from technology disks that we can print.
var/list/imported_designs = list()
/obj/machinery/limbgrower/Initialize(mapload)
create_reagents(100, OPENCONTAINER)
stored_research = new /datum/techweb/specialized/autounlocking/limbgrower
if(!GLOB.autounlock_techwebs[/datum/techweb/autounlocking/limbgrower])
GLOB.autounlock_techwebs[/datum/techweb/autounlocking/limbgrower] = new /datum/techweb/autounlocking/limbgrower
stored_research = GLOB.autounlock_techwebs[/datum/techweb/autounlocking/limbgrower]
. = ..()
AddComponent(/datum/component/plumbing/simple_demand)
/// Emagging a limbgrower allows you to build synthetic armblades.
/obj/machinery/limbgrower/emag_act(mob/user)
if(obj_flags & EMAGGED)
return
. = ..()
obj_flags |= EMAGGED
update_static_data(user)
/obj/machinery/limbgrower/ui_interact(mob/user, datum/tgui/ui)
. = ..()
ui = SStgui.try_update_ui(user, src, ui)
@@ -63,7 +75,14 @@
var/species_categories = categories.Copy()
for(var/species in species_categories)
species_categories[species] = list()
for(var/design_id in stored_research.researched_designs)
var/list/available_nodes = stored_research.researched_designs.Copy()
if(imported_designs.len)
available_nodes += imported_designs
if(obj_flags & EMAGGED)
available_nodes += stored_research.hacked_designs
for(var/design_id in available_nodes)
var/datum/design/limb_design = SSresearch.techweb_design_by_id(design_id)
for(var/found_category in species_categories)
if(found_category in limb_design.category)
@@ -98,7 +117,7 @@
/obj/machinery/limbgrower/on_deconstruction()
for(var/obj/item/reagent_containers/cup/our_beaker in component_parts)
reagents.trans_to(our_beaker, our_beaker.reagents.maximum_volume)
..()
return ..()
/obj/machinery/limbgrower/attackby(obj/item/user_item, mob/living/user, params)
if (busy)
@@ -113,7 +132,7 @@
var/obj/item/disk/design_disk/limbs/limb_design_disk = user_item
if(do_after(user, 2 SECONDS, target = src))
for(var/datum/design/found_design in limb_design_disk.blueprints)
stored_research.add_design(found_design)
imported_designs[found_design.id] = TRUE
update_static_data(user)
busy = FALSE
return
@@ -144,10 +163,9 @@
. = TRUE
if("make_limb")
being_built = stored_research.isDesignResearchedID(params["design_id"])
if(!being_built)
CRASH("[src] was passed an invalid design id!")
var/design_id = params["design_id"]
if(!stored_research.researched_designs.Find(design_id) && !imported_designs.Find(design_id))
return
/// All the reagents we're using to make our organ.
var/list/consumed_reagents_list = being_built.reagents_list.Copy()
/// The amount of power we're going to use, based on how much reagent we use.
@@ -164,7 +182,7 @@
busy = TRUE
use_power(power)
flick("limbgrower_fill",src)
flick("limbgrower_fill", src)
icon_state = "limbgrower_idleon"
selected_category = params["active_tab"]
addtimer(CALLBACK(src, PROC_REF(build_item), consumed_reagents_list), production_speed * production_coefficient)
@@ -261,7 +279,6 @@
/obj/machinery/limbgrower/fullupgrade //Inherently cheaper organ production. This is to NEVER be inherently emagged, no valids.
desc = "It grows new limbs using Synthflesh. This alien model seems more efficient."
obj_flags = CAN_BE_HIT
flags_1 = NODECONSTRUCT_1
circuit = /obj/item/circuitboard/machine/limbgrower/fullupgrade
@@ -269,17 +286,5 @@
. = ..()
for(var/id in SSresearch.techweb_designs)
var/datum/design/found_design = SSresearch.techweb_design_by_id(id)
if((found_design.build_type & LIMBGROWER) && !(RND_CATEGORY_EMAGGED in found_design.category))
stored_research.add_design(found_design)
/// Emagging a limbgrower allows you to build synthetic armblades.
/obj/machinery/limbgrower/emag_act(mob/user)
if(obj_flags & EMAGGED)
return
for(var/design_id in SSresearch.techweb_designs)
var/datum/design/found_design = SSresearch.techweb_design_by_id(design_id)
if((found_design.build_type & LIMBGROWER) && (RND_CATEGORY_EMAGGED in found_design.category))
stored_research.add_design(found_design)
to_chat(user, span_warning("Safety overrides have been deactivated!"))
obj_flags |= EMAGGED
update_static_data(user)
if((found_design.build_type & LIMBGROWER) && !(RND_CATEGORY_HACKED in found_design.category))
imported_designs += found_design.id
+3 -22
View File
@@ -45,19 +45,18 @@
/// The sound loop that can be heard when the generator is processing.
var/datum/looping_sound/generator/soundloop
/obj/machinery/biogenerator/Initialize(mapload)
. = ..()
stored_research = new /datum/techweb/specialized/autounlocking/biogenerator
if(!GLOB.autounlock_techwebs[/datum/techweb/autounlocking/biogenerator])
GLOB.autounlock_techwebs[/datum/techweb/autounlocking/biogenerator] = new /datum/techweb/autounlocking/biogenerator
stored_research = GLOB.autounlock_techwebs[/datum/techweb/autounlocking/biogenerator]
soundloop = new(src, processing)
/obj/machinery/biogenerator/Destroy()
QDEL_NULL(beaker)
QDEL_NULL(soundloop)
return ..()
/obj/machinery/biogenerator/contents_explosion(severity, target)
. = ..()
if(!beaker)
@@ -71,7 +70,6 @@
if(EXPLODE_LIGHT)
SSexplosions.low_mov_atom += beaker
/obj/machinery/biogenerator/handle_atom_del(atom/deleting_atom)
. = ..()
@@ -218,23 +216,6 @@
return TRUE //no afterattack
else if (istype(attacking_item, /obj/item/disk/design_disk))
user.visible_message(
span_notice("[user] begins to load \the [attacking_item] in \the [src]..."),
span_notice("You begin to load a design from \the [attacking_item]..."),
span_hear("You hear the chatter of a floppy drive.")
)
processing = TRUE
var/obj/item/disk/design_disk/design_disk = attacking_item
if(do_after(user, 1 SECONDS, target = src))
for(var/blueprint in design_disk.blueprints)
if(blueprint)
stored_research.add_design(blueprint)
processing = FALSE
return TRUE
else
to_chat(user, span_warning("You cannot put \the [attacking_item] in \the [src]!"))
+4 -2
View File
@@ -153,12 +153,14 @@
/datum/material/bluespace,
)
AddComponent(/datum/component/material_container, allowed_materials, INFINITY, MATCONTAINER_EXAMINE|BREAKDOWN_FLAGS_ORE_PROCESSOR, allowed_items=/obj/item/stack)
stored_research = new /datum/techweb/specialized/autounlocking/smelter
if(!GLOB.autounlock_techwebs[/datum/techweb/autounlocking/smelter])
GLOB.autounlock_techwebs[/datum/techweb/autounlocking/smelter] = new /datum/techweb/autounlocking/smelter
stored_research = GLOB.autounlock_techwebs[/datum/techweb/autounlocking/smelter]
selected_material = GET_MATERIAL_REF(/datum/material/iron)
/obj/machinery/mineral/processing_unit/Destroy()
mineral_machine = null
QDEL_NULL(stored_research)
stored_research = null
return ..()
/obj/machinery/mineral/processing_unit/proc/process_ore(obj/item/stack/ore/O)
+8 -56
View File
@@ -22,16 +22,17 @@
/// Variable that holds a timer which is used for callbacks to `send_console_message()`. Used for preventing multiple calls to this proc while the ORM is eating a stack of ores.
var/console_notify_timer
var/datum/techweb/stored_research
var/obj/item/disk/design_disk/inserted_disk
var/datum/component/remote_materials/materials
/obj/machinery/mineral/ore_redemption/Initialize(mapload)
. = ..()
stored_research = new /datum/techweb/specialized/autounlocking/smelter
if(!GLOB.autounlock_techwebs[/datum/techweb/autounlocking/smelter])
GLOB.autounlock_techwebs[/datum/techweb/autounlocking/smelter] = new /datum/techweb/autounlocking/smelter
stored_research = GLOB.autounlock_techwebs[/datum/techweb/autounlocking/smelter]
materials = AddComponent(/datum/component/remote_materials, "orm", mapload, mat_container_flags=BREAKDOWN_FLAGS_ORM)
/obj/machinery/mineral/ore_redemption/Destroy()
QDEL_NULL(stored_research)
stored_research = null
materials = null
return ..()
@@ -172,14 +173,9 @@
if(!powered())
return ..()
if(istype(W, /obj/item/disk/design_disk))
if(user.transferItemToLoc(W, src))
inserted_disk = W
return TRUE
var/obj/item/stack/ore/O = W
if(istype(O))
if(O.refined_type == null)
if(isnull(O.refined_type))
to_chat(user, span_warning("[O] has already been refined!"))
return
@@ -230,16 +226,6 @@
else if (materials.on_hold())
data["disconnected"] = "mineral withdrawal is on hold"
data["diskDesigns"] = list()
data["hasDisk"] = FALSE
if(inserted_disk)
data["hasDisk"] = TRUE
if(inserted_disk.blueprints.len)
var/index = 1
for (var/datum/design/thisdesign in inserted_disk.blueprints)
if(thisdesign)
data["diskDesigns"] += list(list("name" = thisdesign.name, "index" = index, "canupload" = thisdesign.build_type&SMELTER))
index++
return data
/obj/machinery/mineral/ore_redemption/ui_act(action, params)
@@ -277,18 +263,11 @@
return
var/stored_amount = CEILING(amount / MINERAL_MATERIAL_AMOUNT, 0.1)
if(!stored_amount)
return
var/desired = 0
if (params["sheets"])
desired = text2num(params["sheets"])
else
desired = tgui_input_number(usr, "How many sheets would you like to smelt?", "Smelt", max_value = stored_amount)
if(!desired || QDELETED(usr) || QDELETED(src) || !usr.canUseTopic(src, be_close = TRUE, no_dexterity = FALSE, no_tk = TRUE))
return
var/sheets_to_remove = round(min(desired,50,stored_amount))
var/desired = text2num(params["sheets"])
var/sheets_to_remove = round(min(desired, 50, stored_amount))
var/count = mat_container.retrieve_sheets(sheets_to_remove, mat, get_step(src, output_dir))
var/list/mats = list()
@@ -296,25 +275,6 @@
materials.silo_log(src, "released", -count, "sheets", mats)
//Logging deleted for quick coding
return TRUE
if("diskInsert")
var/obj/item/disk/design_disk/disk = usr.get_active_held_item()
if(istype(disk))
if(!usr.transferItemToLoc(disk,src))
return
inserted_disk = disk
else
to_chat(usr, span_warning("Not a valid Design Disk!"))
return TRUE
if("diskEject")
if(inserted_disk)
usr.put_in_hands(inserted_disk)
inserted_disk = null
return TRUE
if("diskUpload")
var/n = text2num(params["design"])
if(inserted_disk && inserted_disk.blueprints && inserted_disk.blueprints[n])
stored_research.add_design(inserted_disk.blueprints[n])
return TRUE
if("Smelt")
if(!mat_container)
return
@@ -328,15 +288,7 @@
var/mob/living/user = usr
user_id_card = user.get_idcard(TRUE)
if((check_access(user_id_card) || allowed(usr)) && alloy)
var/smelt_amount = can_smelt_alloy(alloy)
var/desired = 0
if (params["sheets"])
desired = text2num(params["sheets"])
else
desired = tgui_input_number(usr, "How many sheets would you like to smelt?", "Smelt", max_value = smelt_amount)
if(!desired || QDELETED(usr) || QDELETED(src) || !usr.canUseTopic(src, be_close = TRUE, no_dexterity = FALSE, no_tk = TRUE))
return
var/amount = round(min(desired,50,smelt_amount))
var/amount = round(min(text2num(params["sheets"]), 50, can_smelt_alloy(alloy)))
if(amount < 1) //no negative mats
return
mat_container.use_materials(alloy.materials, amount)
@@ -212,7 +212,7 @@
build_type = LIMBGROWER
reagents_list = list(/datum/reagent/medicine/c2/synthflesh = 75)
build_path = /obj/item/melee/synthetic_arm_blade
category = list(RND_CATEGORY_LIMBS_OTHER, RND_CATEGORY_EMAGGED)
category = list(RND_CATEGORY_LIMBS_OTHER, RND_CATEGORY_HACKED)
/// Design disks and designs - for adding limbs and organs to the limbgrower.
/obj/item/disk/design_disk/limbs
@@ -76,7 +76,7 @@
name = "Alien Alloy"
desc = "A sheet of reverse-engineered alien alloy."
id = "alienalloy"
build_type = PROTOLATHE | AWAY_LATHE | SMELTER
build_type = SMELTER | PROTOLATHE | AWAY_LATHE
materials = list(/datum/material/iron = 4000, /datum/material/plasma = 4000)
build_path = /obj/item/stack/sheet/mineral/abductor
category = list(
+1 -1
View File
@@ -9,7 +9,7 @@
/obj/item/disk/tech_disk/Initialize(mapload)
. = ..()
if(!stored_research)
stored_research = new /datum/techweb
stored_research = new /datum/techweb/disk
pixel_x = base_pixel_x + rand(-5, 5)
pixel_y = base_pixel_y + rand(-5, 5)
+18 -81
View File
@@ -69,30 +69,6 @@
initialize_published_papers()
return ..()
/datum/techweb/admin
id = "ADMIN"
organization = "CentCom"
/datum/techweb/admin/New() //All unlocked.
. = ..()
for(var/i in SSresearch.techweb_nodes)
var/datum/techweb_node/TN = SSresearch.techweb_nodes[i]
research_node(TN, TRUE, TRUE, FALSE)
for(var/i in SSresearch.point_types)
research_points[i] = INFINITY
hidden_nodes = list()
/datum/techweb/bepis/New(remove_tech = TRUE)
. = ..()
var/bepis_id = pick(SSresearch.techweb_nodes_experimental) //To add a new tech to the BEPIS, add the ID to this pick list.
var/datum/techweb_node/BN = (SSresearch.techweb_node_by_id(bepis_id))
hidden_nodes -= BN.id //Has to be removed from hidden nodes
research_node(BN, TRUE, FALSE, FALSE)
update_node_status(BN)
if(remove_tech)
SSresearch.techweb_nodes_experimental -= bepis_id
log_research("[BN.display_name] has been removed from experimental nodes through the BEPIS techweb's \"remove tech\" feature.")
/datum/techweb/Destroy()
researched_nodes = null
researched_designs = null
@@ -201,16 +177,30 @@
research_points[type] = max(0, research_points[type] - amount)
return TRUE
/datum/techweb/proc/add_design_by_id(id, custom = FALSE)
return add_design(SSresearch.techweb_design_by_id(id), custom)
/**
* add_design_by_id
* The main way to add add designs to techweb
* Uses the techweb node's ID
* Args:
* id - the ID of the techweb node to research
* custom - Boolean on whether the node should also be added to custom_designs
* add_to - A custom list to add the node to, overwriting research_designs.
*/
/datum/techweb/proc/add_design_by_id(id, custom = FALSE, list/add_to)
return add_design(SSresearch.techweb_design_by_id(id), custom, add_to)
/datum/techweb/proc/add_design(datum/design/design, custom = FALSE)
/datum/techweb/proc/add_design(datum/design/design, custom = FALSE, list/add_to)
if(!istype(design))
return FALSE
SEND_SIGNAL(src, COMSIG_TECHWEB_ADD_DESIGN, design, custom)
researched_designs[design.id] = TRUE
if(custom)
custom_designs[design.id] = TRUE
if(add_to)
add_to[design.id] = TRUE
else
researched_designs[design.id] = TRUE
return TRUE
/datum/techweb/proc/remove_design_by_id(id, custom = FALSE)
@@ -449,46 +439,6 @@
/datum/techweb/proc/isNodeAvailableID(id)
return available_nodes[id]? SSresearch.techweb_node_by_id(id) : FALSE
/datum/techweb/specialized
var/allowed_buildtypes = ALL
/datum/techweb/specialized/add_design(datum/design/D)
if(!(D.build_type & allowed_buildtypes))
return FALSE
return ..()
/datum/techweb/specialized/autounlocking
var/design_autounlock_buildtypes = NONE
/datum/techweb/specialized/autounlocking/New()
..()
autounlock()
/datum/techweb/specialized/autounlocking/proc/autounlock()
for(var/id in SSresearch.techweb_designs)
var/datum/design/design = SSresearch.techweb_designs[id]
if((design.build_type & design_autounlock_buildtypes) && (RND_CATEGORY_INITIAL in design.category))
add_design_by_id(id)
/datum/techweb/specialized/autounlocking/autolathe
design_autounlock_buildtypes = AUTOLATHE
allowed_buildtypes = AUTOLATHE
/datum/techweb/specialized/autounlocking/limbgrower
design_autounlock_buildtypes = LIMBGROWER
allowed_buildtypes = LIMBGROWER
/datum/techweb/specialized/autounlocking/biogenerator
design_autounlock_buildtypes = BIOGENERATOR
allowed_buildtypes = BIOGENERATOR
/datum/techweb/specialized/autounlocking/smelter
design_autounlock_buildtypes = SMELTER
allowed_buildtypes = SMELTER
/datum/techweb/specialized/autounlocking/exofab
allowed_buildtypes = MECHFAB
/// Fill published_papers with nulls.
/datum/techweb/proc/initialize_published_papers()
published_papers = list()
@@ -526,16 +476,3 @@
handler.announce_message_to_all("The [experiment.name] has been completed!")
return TRUE
/datum/techweb/science //Global science techweb for RND consoles.
id = "SCIENCE"
organization = "Nanotrasen"
/datum/techweb/science/research_node(datum/techweb_node/node, force = FALSE, auto_adjust_cost = TRUE, get_that_dosh = TRUE) //When something is researched, triggers the proc for this techweb only
. = ..()
if(.)
node.on_research()
/datum/techweb/bepis //Should contain only 1 BEPIS tech selected at random.
id = "EXPERIMENTAL"
organization = "Nanotrasen R&D"
@@ -2381,26 +2381,3 @@
research_costs = list(TECHWEB_POINT_TYPE_GENERIC = 2500)
hidden = TRUE
experimental = TRUE
//Helpers for debugging/balancing the techweb in its entirety!
/proc/total_techweb_points()
var/list/datum/techweb_node/processing = list()
for(var/i in subtypesof(/datum/techweb_node))
processing += new i
var/datum/techweb/TW = new
TW.research_points = list()
for(var/i in processing)
var/datum/techweb_node/TN = i
TW.add_point_list(TN.research_costs)
return TW.research_points
/proc/total_techweb_points_printout()
var/list/datum/techweb_node/processing = list()
for(var/i in subtypesof(/datum/techweb_node))
processing += new i
var/datum/techweb/TW = new
TW.research_points = list()
for(var/i in processing)
var/datum/techweb_node/TN = i
TW.add_point_list(TN.research_costs)
return TW.printout_points()
@@ -0,0 +1,95 @@
/**
* Global Science techweb for RND consoles
*/
/datum/techweb/science
id = "SCIENCE"
organization = "Nanotrasen"
//When something is researched, triggers the proc for this techweb only
/datum/techweb/science/research_node(datum/techweb_node/node, force = FALSE, auto_adjust_cost = TRUE, get_that_dosh = TRUE)
. = ..()
if(.)
node.on_research()
/**
* Admin techweb that has everything unlocked by default
*/
/datum/techweb/admin
id = "ADMIN"
organization = "CentCom"
/datum/techweb/admin/New()
. = ..()
for(var/i in SSresearch.techweb_nodes)
var/datum/techweb_node/TN = SSresearch.techweb_nodes[i]
research_node(TN, TRUE, TRUE, FALSE)
for(var/i in SSresearch.point_types)
research_points[i] = INFINITY
hidden_nodes = list()
/**
* Techweb made through BEPIS machine
* Should only contain 1 BEPIS tech at random.
*/
/datum/techweb/bepis
id = "EXPERIMENTAL"
organization = "Nanotrasen R&D"
/datum/techweb/bepis/New(remove_tech = TRUE)
. = ..()
var/bepis_id = pick(SSresearch.techweb_nodes_experimental) //To add a new tech to the BEPIS, add the ID to this pick list.
var/datum/techweb_node/BN = (SSresearch.techweb_node_by_id(bepis_id))
hidden_nodes -= BN.id //Has to be removed from hidden nodes
research_node(BN, TRUE, FALSE, FALSE)
update_node_status(BN)
if(remove_tech)
SSresearch.techweb_nodes_experimental -= bepis_id
log_research("[BN.display_name] has been removed from experimental nodes through the BEPIS techweb's \"remove tech\" feature.")
/**
* Techweb made through tech disks
* Contains nothing, subtype mostly meant to make it easy for admins to see.
*/
/datum/techweb/disk
id = "D1SK"
GLOBAL_LIST_EMPTY(autounlock_techwebs)
/**
* Techweb node that automatically unlocks a given buildtype.
* Saved in GLOB.autounlock_techwebs and used to prevent
* creating new ones each time it's needed.
*/
/datum/techweb/autounlocking
///The buildtype we will automatically unlock.
var/allowed_buildtypes = ALL
///Designs that are only available when the printer is hacked.
var/list/hacked_designs = list()
/datum/techweb/autounlocking/New()
. = ..()
for(var/id in SSresearch.techweb_designs)
var/datum/design/design = SSresearch.techweb_designs[id]
if(!(design.build_type & allowed_buildtypes))
continue
if(RND_CATEGORY_INITIAL in design.category)
add_design_by_id(id)
if(RND_CATEGORY_HACKED in design.category)
add_design_by_id(id, add_to = hacked_designs)
/datum/techweb/autounlocking/add_design(datum/design/design, custom = FALSE, list/add_to)
if(!(design.build_type & allowed_buildtypes))
return FALSE
return ..()
/datum/techweb/autounlocking/autolathe
allowed_buildtypes = AUTOLATHE
/datum/techweb/autounlocking/limbgrower
allowed_buildtypes = LIMBGROWER
/datum/techweb/autounlocking/biogenerator
allowed_buildtypes = BIOGENERATOR
/datum/techweb/autounlocking/smelter
allowed_buildtypes = SMELTER
+1
View File
@@ -4553,6 +4553,7 @@
#include "code\modules\research\techweb\_techweb.dm"
#include "code\modules\research\techweb\_techweb_node.dm"
#include "code\modules\research\techweb\all_nodes.dm"
#include "code\modules\research\techweb\techweb_types.dm"
#include "code\modules\research\xenobiology\xenobio_camera.dm"
#include "code\modules\research\xenobiology\xenobiology.dm"
#include "code\modules\research\xenobiology\crossbreeding\__corecross.dm"
@@ -5,7 +5,7 @@ import { Window } from '../layouts';
export const OreRedemptionMachine = (props, context) => {
const { act, data } = useBackend(context);
const { unclaimedPoints, materials, alloys, diskDesigns, hasDisk } = data;
const { unclaimedPoints, materials, alloys } = data;
return (
<Window title="Ore Redemption Machine" width={440} height={550}>
<Window.Content scrollable>
@@ -28,45 +28,6 @@ export const OreRedemptionMachine = (props, context) => {
/>
</Box>
</Section>
<Section>
{(hasDisk && (
<>
<Box mb={1}>
<Button
icon="eject"
content="Eject design disk"
onClick={() => act('diskEject')}
/>
</Box>
<Table>
{diskDesigns.map((design) => (
<Table.Row key={design.index}>
<Table.Cell>
File {design.index}: {design.name}
</Table.Cell>
<Table.Cell collapsing>
<Button
disabled={!design.canupload}
content="Upload"
onClick={() =>
act('diskUpload', {
design: design.index,
})
}
/>
</Table.Cell>
</Table.Row>
))}
</Table>
</>
)) || (
<Button
icon="save"
content="Insert design disk"
onClick={() => act('diskInsert')}
/>
)}
</Section>
<Section title="Materials">
<Table>
{materials.map((material) => (