diff --git a/citadel.dme b/citadel.dme
index 92c188d2167..61be27550de 100644
--- a/citadel.dme
+++ b/citadel.dme
@@ -283,6 +283,7 @@
#include "code\__DEFINES\misc\attack_animations.dm"
#include "code\__DEFINES\misc\message_ranges.dm"
#include "code\__DEFINES\misc\nightshift.dm"
+#include "code\__DEFINES\misc\point_redemption.dm"
#include "code\__DEFINES\misc\posters.dm"
#include "code\__DEFINES\mobs\actions.dm"
#include "code\__DEFINES\mobs\biology.dm"
@@ -1507,6 +1508,14 @@
#include "code\game\machinery\pipe\construction.dm"
#include "code\game\machinery\pipe\pipe_dispenser.dm"
#include "code\game\machinery\pipe\pipe_recipes.dm"
+#include "code\game\machinery\point_redemption_vendor\construction.dm"
+#include "code\game\machinery\point_redemption_vendor\point_redemption_item.dm"
+#include "code\game\machinery\point_redemption_vendor\point_redemption_vendor.dm"
+#include "code\game\machinery\point_redemption_vendor\point_redemption_voucher.dm"
+#include "code\game\machinery\point_redemption_vendor\unsorted_please_sort_these.dm"
+#include "code\game\machinery\point_redemption_vendor\types\engineering.dm"
+#include "code\game\machinery\point_redemption_vendor\types\mining.dm"
+#include "code\game\machinery\point_redemption_vendor\types\survey.dm"
#include "code\game\machinery\suit_storage\suit_cycler.dm"
#include "code\game\machinery\suit_storage\suit_storage_massive.dm"
#include "code\game\machinery\suit_storage\suit_storage_prepared.dm"
@@ -3609,11 +3618,6 @@
#include "code\modules\mining\machinery\sheet_silo_loader.dm"
#include "code\modules\mining\misc\abandonedcrates.dm"
#include "code\modules\mining\misc\abandonedcrates_vr.dm"
-#include "code\modules\mining\ore_redemption_machine\construction.dm"
-#include "code\modules\mining\ore_redemption_machine\engineering_points_vendor.dm"
-#include "code\modules\mining\ore_redemption_machine\equipment_vendor.dm"
-#include "code\modules\mining\ore_redemption_machine\mine_point_items.dm"
-#include "code\modules\mining\ore_redemption_machine\survey_vendor.dm"
#include "code\modules\mining\ores\alloys.dm"
#include "code\modules\mining\ores\ore.dm"
#include "code\modules\mining\ores\ore_datum.dm"
diff --git a/code/__DEFINES/misc/point_redemption.dm b/code/__DEFINES/misc/point_redemption.dm
new file mode 100644
index 00000000000..b7684199539
--- /dev/null
+++ b/code/__DEFINES/misc/point_redemption.dm
@@ -0,0 +1,10 @@
+//* This file is explicitly licensed under the MIT license. *//
+//* Copyright (c) 2025 Citadel Station Developers *//
+
+/**
+ * stupid GBP system for mining / engineering / survey / etc
+ */
+
+#define POINT_REDEMPTION_TYPE_MINING "mining"
+#define POINT_REDEMPTION_TYPE_ENGINEERING "engineering"
+#define POINT_REDEMPTION_TYPE_SURVEY "survey"
diff --git a/code/__DEFINES/procs/clickcode.dm b/code/__DEFINES/procs/clickcode.dm
index 5eaa74894e1..47c11f429ee 100644
--- a/code/__DEFINES/procs/clickcode.dm
+++ b/code/__DEFINES/procs/clickcode.dm
@@ -51,6 +51,8 @@
#define CLICKCHAIN_FLAGS_UNCONDITIONAL_ABORT (CLICKCHAIN_DO_NOT_PROPAGATE)
/// check these for 'abort attack'
#define CLICKCHAIN_FLAGS_ATTACK_ABORT (CLICKCHAIN_DO_NOT_PROPAGATE | CLICKCHAIN_FULL_BLOCKED)
+/// check these for 'abort further interactions'
+#define CLICKCHAIN_FLAGS_INTERACT_ABORT (CLICKCHAIN_DO_NOT_PROPAGATE | CLICKCHAIN_DID_SOMETHING)
//! Reachability Depths - checked from level of DirectAccess and turf adjacency.
/// default reachability depth
diff --git a/code/game/machinery/computer/command/card.dm b/code/game/machinery/computer/command/card.dm
index d306d3bd22d..44135031e65 100644
--- a/code/game/machinery/computer/command/card.dm
+++ b/code/game/machinery/computer/command/card.dm
@@ -27,7 +27,7 @@
return
switch(id)
if("modify")
- return tgui_cardmod.ui_act(action, params, ui)
+ return tgui_cardmod.ui_act(action, params, ui, new /datum/event_args/actor(usr))
/**
* for later use: authorized to change slots
diff --git a/code/modules/mining/ore_redemption_machine/construction.dm b/code/game/machinery/point_redemption_vendor/construction.dm
similarity index 64%
rename from code/modules/mining/ore_redemption_machine/construction.dm
rename to code/game/machinery/point_redemption_vendor/construction.dm
index 77b55ea2e12..014ec78ffb9 100644
--- a/code/modules/mining/ore_redemption_machine/construction.dm
+++ b/code/game/machinery/point_redemption_vendor/construction.dm
@@ -2,19 +2,22 @@
#error T_BOARD macro is not defined but we need it!
#endif
-/obj/item/circuitboard/mining_equipment_vendor
+/obj/item/circuitboard/point_redemption_vendor
+ abstract_type = /obj/item/circuitboard/point_redemption_vendor
+
+/obj/item/circuitboard/point_redemption_vendor/mining
name = T_BOARD("Mining Equipment Vendor")
board_type = new /datum/frame/frame_types/machine
- build_path = /obj/machinery/mineral/equipment_vendor
+ build_path = /obj/machinery/point_redemption_vendor/mining
origin_tech = list(TECH_DATA = 1, TECH_ENGINEERING = 3)
req_components = list(
/obj/item/stock_parts/console_screen = 1,
/obj/item/stock_parts/matter_bin = 3)
-/obj/item/circuitboard/exploration_equipment_vendor
+/obj/item/circuitboard/point_redemption_vendor/survey
name = T_BOARD("Exploration Equipment Vendor")
board_type = new /datum/frame/frame_types/machine
- build_path = /obj/machinery/mineral/equipment_vendor/survey
+ build_path = /obj/machinery/point_redemption_vendor/survey
origin_tech = list(TECH_DATA = 1, TECH_ENGINEERING = 2)
req_components = list(
/obj/item/stock_parts/console_screen = 1,
diff --git a/code/game/machinery/point_redemption_vendor/point_redemption_item.dm b/code/game/machinery/point_redemption_vendor/point_redemption_item.dm
new file mode 100644
index 00000000000..9888e2e1c1e
--- /dev/null
+++ b/code/game/machinery/point_redemption_vendor/point_redemption_item.dm
@@ -0,0 +1,48 @@
+//* This file is explicitly licensed under the MIT license. *//
+//* Copyright (c) 2025 Citadel Station Developers *//
+
+/**
+ * Describes stuff you can get for points in a point redemption vendor.
+ * * Does not store info about the type of points, at time of writing.
+ *
+ * todo: category system
+ */
+/datum/point_redemption_item
+ var/name = "Unknown Item"
+ /**
+ * Description.
+ * * Inferred from path if unspecified.
+ */
+ var/desc = "Some kind of item."
+ var/path = /obj/item/bananapeel
+ var/cost = 1
+
+/datum/point_redemption_item/New(name, path, cost, desc)
+ if(name)
+ src.name = name
+ if(path)
+ src.path = path
+ if(cost)
+ src.cost = cost
+ if(desc)
+ src.desc = desc
+
+ if(!ispath(src.path, /atom/movable))
+ CRASH("invalid path '[src.path]'.")
+
+ if(desc == initial(desc))
+ var/atom/movable/casted = src.path
+ desc = initial(casted.desc)
+
+/**
+ * @return list of entities created
+ */
+/datum/point_redemption_item/proc/instantiate(atom/where, amount = 1) as /list
+ RETURN_TYPE(/list)
+ . = list()
+ var/safety = 50
+ for(var/i in 1 to amount)
+ if(!--safety)
+ CRASH("safety limit hit")
+ var/atom/movable/created = new path(where)
+ . += created
diff --git a/code/game/machinery/point_redemption_vendor/point_redemption_vendor.dm b/code/game/machinery/point_redemption_vendor/point_redemption_vendor.dm
new file mode 100644
index 00000000000..085bd1c7770
--- /dev/null
+++ b/code/game/machinery/point_redemption_vendor/point_redemption_vendor.dm
@@ -0,0 +1,174 @@
+//* This file is explicitly licensed under the MIT license. *//
+//* Copyright (c) 2025 Citadel Station Developers *//
+
+/obj/machinery/point_redemption_vendor
+ name = "point redemption vendor"
+ desc = "An equipment vendor that trades points for various gear. Usually found in the station's departments \
+ and used to incentivize good performance."
+ density = TRUE
+ anchored = TRUE
+
+ /// point type we operate with
+ var/point_type
+
+ /// flick tihs state when denying sometihng
+ var/icon_state_append_deny
+ /// set to this state if panel is open
+ // todo: render at /obj/machinery level
+ var/icon_state_append_open
+ /// set to this state if we're depowered
+ // todo: render at /obj/machinery level
+ var/icon_state_append_off
+ /// flick this state when vending something
+ var/icon_state_append_vend
+ /// set to this state if we're broken
+ var/icon_state_append_broken
+
+ /// The inserted ID, if any
+ var/obj/item/card/id/inserted_id
+
+ /// available items
+ var/list/datum/point_redemption_item/prize_list = list()
+
+/obj/machinery/point_redemption_vendor/update_icon_state()
+ var/icon_base_state = base_icon_state || initial(icon_state)
+ var/is_broken = atom_flags & ATOM_BROKEN
+ if(is_broken && icon_state_append_broken)
+ icon_state = "[icon_base_state][icon_state_append_broken]"
+ else if((!powered() || is_broken) && icon_state_append_off)
+ icon_state = "[icon_base_state][icon_state_append_off]"
+ else if(panel_open)
+ icon_state = "[icon_base_state][icon_state_append_open]"
+ else
+ icon_state = icon_base_state
+ return ..()
+
+/obj/machinery/point_redemption_vendor/power_change()
+ var/old_stat = machine_stat
+ . = ..()
+ // todo: machine-level update icon hook?
+ if(machine_stat != old_stat)
+ update_icon()
+ if(!powered() && inserted_id)
+ visible_message(
+ SPAN_NOTICE("The ID slot indicator light on [src] flickers as it spits out [inserted_id]."),
+ )
+ inserted_id.forceMove(drop_location())
+
+/obj/machinery/point_redemption_vendor/drop_products(method, atom/where)
+ . = ..()
+ if(inserted_id)
+ drop_product(inserted_id, where)
+ inserted_id = null
+
+/obj/machinery/point_redemption_vendor/using_item_on(obj/item/using, datum/event_args/actor/clickchain/e_args, clickchain_flags, datum/callback/reachability_check)
+ . = ..()
+ if(. & CLICKCHAIN_FLAGS_INTERACT_ABORT)
+ return
+ if(handle_id_insertion(using, e_args))
+ // in either case they wouldn't do anything because the id is either not on them anymore
+ // or is not going to touch the machine
+ return CLICKCHAIN_DID_SOMETHING | CLICKCHAIN_DO_NOT_PROPAGATE
+
+/**
+ * @return TRUE if handled
+ */
+/obj/machinery/point_redemption_vendor/proc/handle_id_insertion(obj/item/maybe_id, datum/event_args/actor/actor)
+ if(!istype(maybe_id, /obj/item/card/id))
+ return FALSE
+ if(inserted_id)
+ actor.chat_feedback(
+ SPAN_WARNING("[src] already has an inserted ID."),
+ target = src,
+ )
+ return TRUE
+ if(!actor.performer.attempt_insert_item_for_installation(maybe_id, src))
+ return TRUE
+ actor.chat_feedback(
+ SPAN_NOTICE("You insert [maybe_id] into [src]'s card slot."),
+ target = src,
+ )
+ inserted_id = maybe_id
+ return TRUE
+
+/obj/machinery/point_redemption_vendor/ui_act(action, list/params, datum/tgui/ui, datum/event_args/actor/e_args)
+ . = ..()
+ if(.)
+ return
+
+ switch(action)
+ if("idcard")
+ if(inserted_id)
+ e_args.visible_feedback(
+ target = src,
+ range = MESSAGE_RANGE_INVENTORY_SOFT,
+ visible = SPAN_NOTICE("[e_args.performer] retrieves [inserted_id] from [src]."),
+ )
+ e_args.performer.put_in_hands_or_drop(inserted_id)
+ inserted_id = null
+ else if(!inserted_id)
+ var/obj/item/active_held = e_args.performer.get_active_held_item()
+ handle_id_insertion(active_held, e_args)
+ return TRUE
+ if("vend")
+ if(!inserted_id)
+ return TRUE
+ // double-verify incase entry changed; we don't give them the refs though so
+ // no locate() in list!
+ var/target_index = params["index"]
+ var/target_name = params["name"]
+ if(target_index < 1 || target_index > length(prize_list))
+ update_static_data(hard_refresh = TRUE)
+ return TRUE
+ var/datum/point_redemption_item/resolved = prize_list[target_index]
+ if(resolved.name != target_name)
+ update_static_data(hard_refresh = TRUE)
+ return TRUE
+ if(inserted_id.get_redemption_points(point_type) < resolved.cost)
+ return TRUE
+ inserted_id.adjust_redemption_points(point_type, -resolved.cost)
+ vend_item(resolved)
+ return TRUE
+
+/obj/machinery/point_redemption_vendor/ui_interact(mob/user, datum/tgui/ui, datum/tgui/parent_ui)
+ ui = SStgui.try_update_ui(user, src, ui)
+ if(!ui)
+ ui = new(user, src, "machines/PointRedemptionVendor")
+ ui.set_title(name)
+ ui.open()
+
+/obj/machinery/point_redemption_vendor/ui_static_data(mob/user, datum/tgui/ui)
+ . = ..()
+ .["pointName"] = point_type
+ var/list/serialized_items = list()
+ for(var/datum/point_redemption_item/item in prize_list)
+ serialized_items[++serialized_items.len] = list(
+ "name" = item.name,
+ "desc" = item.desc,
+ "cost" = item.cost,
+ )
+ .["availableItems"] = serialized_items
+
+/obj/machinery/point_redemption_vendor/ui_data(mob/user, datum/tgui/ui)
+ . = ..()
+ .["points"] = inserted_id ? inserted_id.get_redemption_points(point_type) : 0
+ .["insertedId"] = inserted_id ? list(
+ "name" = inserted_id.name,
+ "rank" = inserted_id.rank,
+ "owner" = inserted_id.registered_name,
+ ) : null
+
+/obj/machinery/point_redemption_vendor/proc/vend_item(datum/point_redemption_item/item)
+ item.instantiate(drop_location())
+ flick_vend()
+ return TRUE
+
+/obj/machinery/point_redemption_vendor/proc/flick_deny()
+ if(!icon_state_append_deny)
+ return
+ flick("[base_icon_state || initial(icon_state)][icon_state_append_deny]", src)
+
+/obj/machinery/point_redemption_vendor/proc/flick_vend()
+ if(!icon_state_append_vend)
+ return
+ flick("[base_icon_state || initial(icon_state)][icon_state_append_vend]", src)
diff --git a/code/game/machinery/point_redemption_vendor/point_redemption_voucher.dm b/code/game/machinery/point_redemption_vendor/point_redemption_voucher.dm
new file mode 100644
index 00000000000..e2f54a0c229
--- /dev/null
+++ b/code/game/machinery/point_redemption_vendor/point_redemption_voucher.dm
@@ -0,0 +1,119 @@
+//* This file is explicitly licensed under the MIT license. *//
+//* Copyright (c) 2025 Citadel Station Developers *//
+
+/**
+ * Kinda self explanatory; stores points you can apply to a card.
+ */
+/obj/item/point_redemption_voucher
+ name = "point redemption voucher"
+ desc = "A voucher with redemption points that you can apply to an ID card to use at an equipment vendor."
+ icon = 'icons/obj/card_cit.dmi'
+ icon_state = "generic"
+ w_class = WEIGHT_CLASS_TINY
+ slot_flags = SLOT_ID | SLOT_EARS
+ pickup_sound = 'sound/items/pickup/card.ogg'
+
+ /// stored points
+ var/list/stored_redemption_points
+
+/obj/item/point_redemption_voucher/Initialize(mapload, list/points)
+ . = ..()
+ if(points)
+ src.stored_redemption_points = points.Copy()
+
+/obj/item/point_redemption_voucher/examine(mob/user, dist)
+ . = ..()
+ var/any_found = FALSE
+ for(var/key in stored_redemption_points)
+ var/amount = stored_redemption_points[key]
+ if(!amount)
+ continue
+ any_found = TRUE
+ . += SPAN_NOTICE("There's [amount] [key] equipment redemption point[amount > 1 ? "s" : ""] loaded on this card.")
+ if(!any_found)
+ . += SPAN_NOTICE("There's no equipment redemption points loaded on this voucher.")
+
+/obj/item/point_redemption_voucher/using_as_item(atom/target, datum/event_args/actor/clickchain/e_args, clickchain_flags, datum/callback/reachability_check)
+ . = ..()
+ if(. & CLICKCHAIN_FLAGS_INTERACT_ABORT)
+ return
+ if(istype(target, /obj/item/card/id))
+ transfer_to_card(target, e_args)
+ return CLICKCHAIN_DID_SOMETHING
+
+/obj/item/point_redemption_voucher/using_item_on(obj/item/using, datum/event_args/actor/clickchain/e_args, clickchain_flags, datum/callback/reachability_check)
+ . = ..()
+ if(. & CLICKCHAIN_FLAGS_INTERACT_ABORT)
+ return
+ if(istype(using, /obj/item/card/id))
+ transfer_to_card(using, e_args)
+ return CLICKCHAIN_DID_SOMETHING
+
+/obj/item/point_redemption_voucher/proc/transfer_to_card(obj/item/card/id/to_id_card, datum/event_args/actor/actor)
+ if(!length(stored_redemption_points))
+ actor?.chat_feedback(
+ SPAN_NOTICE("[src] has no stored redemption points."),
+ target = src,
+ )
+ return
+ for(var/key in stored_redemption_points)
+ var/amount = stored_redemption_points[key]
+ to_id_card.adjust_redemption_points(key, amount)
+ actor?.chat_feedback(
+ SPAN_NOTICE("You transfer [amount] [key] points to [to_id_card] from [src]."),
+ )
+ stored_redemption_points = null
+
+//* Presets *//
+
+/obj/item/point_redemption_voucher/preloaded
+
+/obj/item/point_redemption_voucher/preloaded/mining/c500
+ stored_redemption_points = list(
+ POINT_REDEMPTION_TYPE_MINING = 500,
+ )
+
+/obj/item/point_redemption_voucher/preloaded/mining/c1000
+ stored_redemption_points = list(
+ POINT_REDEMPTION_TYPE_MINING = 1000,
+ )
+
+/obj/item/point_redemption_voucher/preloaded/mining/c2000
+ stored_redemption_points = list(
+ POINT_REDEMPTION_TYPE_MINING = 2000,
+ )
+
+/obj/item/point_redemption_voucher/preloaded/mining/c3000
+ stored_redemption_points = list(
+ POINT_REDEMPTION_TYPE_MINING = 3000,
+ )
+
+/obj/item/point_redemption_voucher/preloaded/mining/c50000
+ stored_redemption_points = list(
+ POINT_REDEMPTION_TYPE_MINING = 50000,
+ )
+
+/obj/item/point_redemption_voucher/preloaded/survey/c50
+ stored_redemption_points = list(
+ POINT_REDEMPTION_TYPE_SURVEY = 50,
+ )
+
+/obj/item/point_redemption_voucher/preloaded/survey/c100
+ stored_redemption_points = list(
+ POINT_REDEMPTION_TYPE_SURVEY = 100,
+ )
+
+/obj/item/point_redemption_voucher/preloaded/survey/c200
+ stored_redemption_points = list(
+ POINT_REDEMPTION_TYPE_SURVEY = 200,
+ )
+
+/obj/item/point_redemption_voucher/preloaded/survey/c300
+ stored_redemption_points = list(
+ POINT_REDEMPTION_TYPE_SURVEY = 300,
+ )
+
+/obj/item/point_redemption_voucher/preloaded/engineering/c50
+ stored_redemption_points = list(
+ POINT_REDEMPTION_TYPE_ENGINEERING = 50,
+ )
diff --git a/code/game/machinery/point_redemption_vendor/types/engineering.dm b/code/game/machinery/point_redemption_vendor/types/engineering.dm
new file mode 100644
index 00000000000..57e3cc6ba4f
--- /dev/null
+++ b/code/game/machinery/point_redemption_vendor/types/engineering.dm
@@ -0,0 +1,58 @@
+/obj/machinery/point_redemption_vendor/engineering
+ name = "Engineering Equipment Vendor"
+ desc = "An equipment vendor for engineers, point generated by the crypto miners can be spend here."
+ icon = 'icons/machinery/point_redemption_vendor/engineering.dmi'
+ icon_state = "vendor"
+ icon_state_append_deny = "-deny"
+ icon_state_append_open = "-open"
+ icon_state_append_off = "-off"
+ point_type = POINT_REDEMPTION_TYPE_ENGINEERING
+ prize_list = list(
+ //Mining vendor steals
+ new /datum/point_redemption_item("Vodka", /obj/item/reagent_containers/food/drinks/bottle/vodka, 3),
+ new /datum/point_redemption_item("Cigar", /obj/item/clothing/mask/smokable/cigarette/cigar/havana, 5),
+ new /datum/point_redemption_item("Soap", /obj/item/soap/nanotrasen, 2),
+ new /datum/point_redemption_item("Laser Pointer", /obj/item/laser_pointer, 9),
+ new /datum/point_redemption_item("Plush Toy", /obj/random/plushie, 3),
+ new /datum/point_redemption_item("GPS Device", /obj/item/gps/engineering, 1),
+ new /datum/point_redemption_item("50 Point Transfer Card", /obj/item/point_redemption_voucher/preloaded/engineering/c50, 50),
+ new /datum/point_redemption_item("Umbrella", /obj/item/melee/umbrella/random, 20),
+ new /datum/point_redemption_item("100 Thaler", /obj/item/spacecash/c100, 4),
+ new /datum/point_redemption_item("1000 Thaler", /obj/item/spacecash/c1000, 40),
+ new /datum/point_redemption_item("Hardsuit - Control Module", /obj/item/hardsuit/industrial, 50),
+ new /datum/point_redemption_item("Hardsuit - Plasma Cutter", /obj/item/hardsuit_module/device/plasmacutter, 10),
+ new /datum/point_redemption_item("Hardsuit - Maneuvering Jets", /obj/item/hardsuit_module/maneuvering_jets, 12),
+ new /datum/point_redemption_item("Hardsuit - Intelligence Storage", /obj/item/hardsuit_module/ai_container, 25),
+ new /datum/point_redemption_item("Injector (L) - Panacea", /obj/item/reagent_containers/hypospray/autoinjector/biginjector/purity, 50),
+ //Mining vendor steals - Ends
+ //Power tools like the CE gets, if kev comes crying: https://cdn.discordapp.com/attachments/296237931587305472/956517623519141908/unknown.png
+ new /datum/point_redemption_item("Advanced Hardsuit", /obj/item/hardsuit/ce, 150),
+ new /datum/point_redemption_item("Power Tool - Hand Drill", /obj/item/tool/screwdriver/power, 80),
+ new /datum/point_redemption_item("Power Tool - Jaws of life", /obj/item/tool/crowbar/power, 80),
+ new /datum/point_redemption_item("Power Tool - Experimental Welder", /obj/item/weldingtool/experimental, 80),
+ new /datum/point_redemption_item("Power Tool - Upgraded T-Ray Scanner", /obj/item/t_scanner/upgraded, 80),
+ new /datum/point_redemption_item("Power Tool - Advanced T-Ray Scanner", /obj/item/t_scanner/advanced, 80),
+ new /datum/point_redemption_item("Power Tool - Long Range Atmosphere scanner", /obj/item/atmos_analyzer/longrange, 80),
+ //new /datum/point_redemption_item("Power Tool - Holofan Projector", /obj/item/holosign_creator/combifan, 80),
+ new /datum/point_redemption_item("Superior Welding Goggles", /obj/item/clothing/glasses/welding/superior, 50),
+
+ //Level 2 stock parts, to make engineering kinda self sufficent for minor upgrades but the parts are also kinda expansive
+ new /datum/point_redemption_item("Stock Parts - Advanced Capacitor", /obj/item/stock_parts/capacitor/adv, 20),
+ new /datum/point_redemption_item("Stock Parts - Advanced Scanning Module", /obj/item/stock_parts/scanning_module/adv, 20),
+ new /datum/point_redemption_item("Stock Parts - Nano-Manipulator", /obj/item/stock_parts/manipulator/nano, 20),
+ new /datum/point_redemption_item("Stock Parts - High-Power Micro-Laser", /obj/item/stock_parts/micro_laser/high, 20),
+ new /datum/point_redemption_item("Stock Parts - Advanced Matter Bin", /obj/item/stock_parts/matter_bin/adv, 20),
+
+ //Special Resources which the vendor is the primary source off:
+ new /datum/point_redemption_item("Special Parts - Vimur Tank", /obj/item/tank/vimur, 5),
+ new /datum/point_redemption_item("Special Parts - TEG Voucher", /obj/item/engineering_voucher/teg, 20),
+ new /datum/point_redemption_item("Special Parts - SM Core Voucher", /obj/item/engineering_voucher/smcore, 40),
+ new /datum/point_redemption_item("Special Parts - Fusion Core Voucher", /obj/item/engineering_voucher/fusion_core, 20),
+ new /datum/point_redemption_item("Special Parts - Fuel Injector Voucher", /obj/item/engineering_voucher/fusion_fuel_injector, 10),
+ new /datum/point_redemption_item("Special Parts - Gyrotrons Voucher", /obj/item/engineering_voucher/gyrotrons, 20),
+ new /datum/point_redemption_item("Special Parts - Fuel compressor Voucher", /obj/item/engineering_voucher/fuel_compressor, 10),
+ new /datum/point_redemption_item("Special Parts - Collector Voucher", /obj/item/engineering_voucher/collectors, 10),
+ new /datum/point_redemption_item("Special Parts - Laser Reflector Voucher", /obj/item/engineering_voucher/reflector, 30),
+ //voucher: Solar crate, Vimur canister
+ new /datum/point_redemption_item("???", /obj/item/engineering_mystical_tech, 1000)
+ )
diff --git a/code/game/machinery/point_redemption_vendor/types/mining.dm b/code/game/machinery/point_redemption_vendor/types/mining.dm
new file mode 100644
index 00000000000..90d944b4b3e
--- /dev/null
+++ b/code/game/machinery/point_redemption_vendor/types/mining.dm
@@ -0,0 +1,90 @@
+/obj/machinery/point_redemption_vendor/mining
+ name = "mining equipment vendor"
+ desc = "An equipment vendor for miners, points collected at an ore redemption machine can be spent here."
+ icon = 'icons/machinery/point_redemption_vendor/mining.dmi'
+ icon_state = "vendor"
+ icon_state_append_deny = "-deny"
+ icon_state_append_open = "-open"
+ icon_state_append_off = "-off"
+ point_type = POINT_REDEMPTION_TYPE_MINING
+ circuit = /obj/item/circuitboard/point_redemption_vendor/mining
+ prize_list = list(
+ new /datum/point_redemption_item("1 Marker Beacon", /obj/item/stack/marker_beacon, 10),
+ new /datum/point_redemption_item("10 Marker Beacons", /obj/item/stack/marker_beacon/ten, 100),
+ new /datum/point_redemption_item("30 Marker Beacons", /obj/item/stack/marker_beacon/thirty, 300),
+ new /datum/point_redemption_item("Whiskey", /obj/item/reagent_containers/food/drinks/bottle/whiskey, 125),
+ new /datum/point_redemption_item("Absinthe", /obj/item/reagent_containers/food/drinks/bottle/absinthe, 125),
+ new /datum/point_redemption_item("Hard Root Beer", /obj/item/reagent_containers/food/drinks/bottle/small/alcsassafras, 70),
+ new /datum/point_redemption_item("Special Blend Whiskey", /obj/item/reagent_containers/food/drinks/bottle/specialwhiskey, 250),
+ new /datum/point_redemption_item("Random Booze", /obj/random/alcohol, 125),
+ new /datum/point_redemption_item("Cigar", /obj/item/clothing/mask/smokable/cigarette/cigar/havana, 150),
+ new /datum/point_redemption_item("Root Beer", /obj/item/reagent_containers/food/drinks/bottle/small/sassafras, 50),
+ new /datum/point_redemption_item("Sarsaparilla", /obj/item/reagent_containers/food/drinks/bottle/small/sarsaparilla, 50),
+ new /datum/point_redemption_item("Soap", /obj/item/soap/nanotrasen, 200),
+ new /datum/point_redemption_item("Laser Pointer", /obj/item/laser_pointer, 900),
+ new /datum/point_redemption_item("Geiger Counter", /obj/item/geiger_counter, 750),
+ new /datum/point_redemption_item("Plush Toy", /obj/random/plushie, 300),
+ new /datum/point_redemption_item("GPS Device", /obj/item/gps/mining, 100),
+ new /datum/point_redemption_item("Portable Fuel Can", /obj/item/reagent_containers/portable_fuelcan, 250),
+ // TODO new /datum/point_redemption_item("Advanced Scanner", /obj/item/t_scanner/adv_mining_scanner, 800),
+ new /datum/point_redemption_item("Fulton Beacon", /obj/item/fulton_core, 500),
+ new /datum/point_redemption_item("Shelter Capsule", /obj/item/survivalcapsule, 500),
+ // TODO new /datum/point_redemption_item("Explorer's Webbing", /obj/item/storage/belt/mining, 500),
+ new /datum/point_redemption_item("500 Point Transfer Card", /obj/item/point_redemption_voucher/preloaded/mining/c500, 500),
+ new /datum/point_redemption_item("1000 Point Transfer Card", /obj/item/point_redemption_voucher/preloaded/mining/c1000, 1000),
+ new /datum/point_redemption_item("2000 Point Transfer Card", /obj/item/point_redemption_voucher/preloaded/mining/c2000, 2000),
+ new /datum/point_redemption_item("3000 Point Transfer Card", /obj/item/point_redemption_voucher/preloaded/mining/c3000, 3000),
+ new /datum/point_redemption_item("Umbrella", /obj/item/melee/umbrella/random, 200),
+ new /datum/point_redemption_item("Survival Medipen", /obj/item/reagent_containers/hypospray/autoinjector/miner, 500),
+ new /datum/point_redemption_item("Mini-Translocator", /obj/item/perfect_tele/one_beacon, 1200),
+ // new /datum/point_redemption_item("Kinetic Crusher", /obj/item/twohanded/required/kinetic_crusher, 750),
+ new /datum/point_redemption_item("Kinetic Accelerator", /obj/item/gun/projectile/energy/kinetic_accelerator, 900),
+ new /datum/point_redemption_item("Resonator", /obj/item/resonator, 900),
+ new /datum/point_redemption_item("Fulton Pack", /obj/item/extraction_pack, 1200),
+ new /datum/point_redemption_item("Wormhole Fulton Pack", /obj/item/extraction_pack/wormhole, 1750),
+ new /datum/point_redemption_item("Silver Pickaxe", /obj/item/pickaxe/silver, 1200),
+ new /datum/point_redemption_item("Climbing Pick", /obj/item/pickaxe/icepick, 2200),
+ //new /datum/point_redemption_item("Mining Conscription Kit", /obj/item/storage/backpack/duffelbag/mining_conscript, 1000),
+ new /datum/point_redemption_item("Diamond Pickaxe", /obj/item/pickaxe/diamond, 2000),
+ new /datum/point_redemption_item("Advanced Ore Scanner", /obj/item/mining_scanner/advanced, 2000),
+ new /datum/point_redemption_item("100 Thalers", /obj/item/spacecash/c100, 5000),
+ new /datum/point_redemption_item("1000 Thalers", /obj/item/spacecash/c1000, 50000),
+ new /datum/point_redemption_item("Hardsuit - Control Module", /obj/item/hardsuit/industrial, 2000),
+ new /datum/point_redemption_item("Hardsuit - Plasma Cutter", /obj/item/hardsuit_module/device/plasmacutter, 800),
+ new /datum/point_redemption_item("Hardsuit - Drill", /obj/item/hardsuit_module/device/drill, 5000),
+ new /datum/point_redemption_item("Hardsuit - Ore Scanner", /obj/item/hardsuit_module/device/orescanner, 1000),
+ new /datum/point_redemption_item("Hardsuit - Material Scanner", /obj/item/hardsuit_module/vision/material, 500),
+ new /datum/point_redemption_item("Hardsuit - Maneuvering Jets", /obj/item/hardsuit_module/maneuvering_jets, 1250),
+ new /datum/point_redemption_item("Hardsuit - Intelligence Storage", /obj/item/hardsuit_module/ai_container, 2500),
+ new /datum/point_redemption_item("Hardsuit - Smoke Bomb Deployer", /obj/item/hardsuit_module/grenade_launcher/smoke, 2000),
+ new /datum/point_redemption_item("Industrial Equipment - Phoron Bore", /obj/item/gun/projectile/magnetic/matfed, 3000),
+ new /datum/point_redemption_item("Industrial Equipment - Sheet-Snatcher",/obj/item/storage/bag/sheetsnatcher, 500),
+ new /datum/point_redemption_item("Repurposed Equipment - Mining Carbine", /obj/item/gun/projectile/energy/gun/miningcarbine, 5000),
+ new /datum/point_redemption_item("Digital Tablet - Standard", /obj/item/modular_computer/tablet/preset/custom_loadout/standard, 500),
+ new /datum/point_redemption_item("Digital Tablet - Advanced", /obj/item/modular_computer/tablet/preset/custom_loadout/advanced, 1000),
+ new /datum/point_redemption_item("Super Resonator", /obj/item/resonator/upgraded, 2500),
+ new /datum/point_redemption_item("Jump Boots", /obj/item/clothing/shoes/bhop, 2500),
+ new /datum/point_redemption_item("Luxury Shelter Capsule", /obj/item/survivalcapsule/luxury, 3100),
+ new /datum/point_redemption_item("KA White Tracer Rounds", /obj/item/ka_modkit/tracer, 125),
+ new /datum/point_redemption_item("KA Adjustable Tracer Rounds", /obj/item/ka_modkit/tracer/adjustable, 175),
+ new /datum/point_redemption_item("KA Super Chassis", /obj/item/ka_modkit/chassis_mod, 250),
+ new /datum/point_redemption_item("KA Hyper Chassis", /obj/item/ka_modkit/chassis_mod/orange, 300),
+ new /datum/point_redemption_item("KA Range Increase", /obj/item/ka_modkit/range, 1000),
+ new /datum/point_redemption_item("KA Cooldown Decrease", /obj/item/ka_modkit/cooldown, 1200),
+ new /datum/point_redemption_item("KA Capacity Increase", /obj/item/ka_modkit/capacity, 1500),
+ new /datum/point_redemption_item("KA Holster", /obj/item/clothing/accessory/holster/waist/kinetic_accelerator, 350),
+ new /datum/point_redemption_item("Fine Excavation Kit - Chisels",/obj/item/storage/excavation, 500),
+ new /datum/point_redemption_item("Fine Excavation Kit - Measuring Tape",/obj/item/measuring_tape, 125),
+ new /datum/point_redemption_item("Fine Excavation Kit - Hand Pick",/obj/item/pickaxe/hand, 375),
+ new /datum/point_redemption_item("Explosive Excavation Kit - Plastic Charge",/obj/item/plastique/seismic/locked, 1500),
+ new /datum/point_redemption_item("Injector (L) - Glucose",/obj/item/reagent_containers/hypospray/autoinjector/biginjector/glucose, 500),
+ new /datum/point_redemption_item("Injector (L) - Panacea",/obj/item/reagent_containers/hypospray/autoinjector/biginjector/purity, 500),
+ new /datum/point_redemption_item("Injector (L) - Trauma",/obj/item/reagent_containers/hypospray/autoinjector/biginjector/brute, 500),
+ new /datum/point_redemption_item("Nanopaste Tube", /obj/item/stack/nanopaste, 1000),
+ new /datum/point_redemption_item("Defense Equipment - Smoke Bomb",/obj/item/grenade/smokebomb, 100),
+ new /datum/point_redemption_item("Defense Equipment - Razor Drone Deployer",/obj/item/grenade/spawnergrenade/manhacks/station/locked, 1000),
+ new /datum/point_redemption_item("Defense Equipment - Sentry Drone Deployer",/obj/item/grenade/spawnergrenade/ward, 1500),
+ new /datum/point_redemption_item("Defense Equipment - Plasteel Machete", /obj/item/clothing/accessory/holster/machete/occupied, 500),
+ new /datum/point_redemption_item("Defense Equipment - Kinetic Dagger", /obj/item/kinetic_crusher/dagger, 1200),
+ new /datum/point_redemption_item("Bar Shelter Capsule", /obj/item/survivalcapsule/luxurybar, 10000)
+ )
diff --git a/code/game/machinery/point_redemption_vendor/types/survey.dm b/code/game/machinery/point_redemption_vendor/types/survey.dm
new file mode 100644
index 00000000000..0aad3e4616a
--- /dev/null
+++ b/code/game/machinery/point_redemption_vendor/types/survey.dm
@@ -0,0 +1,66 @@
+/obj/machinery/point_redemption_vendor/survey
+ name = "exploration equipment vendor"
+ desc = "An equipment vendor for explorers, points collected with a survey scanner can be spent here."
+ icon = 'icons/machinery/point_redemption_vendor/survey.dmi'
+ icon_state = "vendor"
+ icon_state_append_deny = "-deny"
+ icon_state_append_open = "-open"
+ icon_state_append_off = "-off"
+ icon_state_append_broken = "-broken"
+ icon_state_append_vend = "-vend"
+ point_type = POINT_REDEMPTION_TYPE_SURVEY
+ circuit = /obj/item/circuitboard/point_redemption_vendor/survey
+ prize_list = list(
+ new /datum/point_redemption_item("1 Marker Beacon", /obj/item/stack/marker_beacon, 1),
+ new /datum/point_redemption_item("10 Marker Beacons", /obj/item/stack/marker_beacon/ten, 10),
+ new /datum/point_redemption_item("GPS Device", /obj/item/gps/explorer, 10),
+ new /datum/point_redemption_item("Defense Equipment - Smoke Bomb",/obj/item/grenade/smokebomb, 10),
+ new /datum/point_redemption_item("Whiskey", /obj/item/reagent_containers/food/drinks/bottle/whiskey, 10),
+ new /datum/point_redemption_item("Absinthe", /obj/item/reagent_containers/food/drinks/bottle/absinthe, 10),
+ new /datum/point_redemption_item("Cigar", /obj/item/clothing/mask/smokable/cigarette/cigar/havana, 15),
+ new /datum/point_redemption_item("Soap", /obj/item/soap/nanotrasen, 20),
+ new /datum/point_redemption_item("Umbrella", /obj/item/melee/umbrella/random, 20),
+ new /datum/point_redemption_item("30 Marker Beacons", /obj/item/stack/marker_beacon/thirty, 30),
+ new /datum/point_redemption_item("Plush Toy", /obj/random/plushie, 30),
+ new /datum/point_redemption_item("Survey Tools - Shovel", /obj/item/shovel, 40),
+ new /datum/point_redemption_item("Survey Tools - Mechanical Trap", /obj/item/beartrap, 50),
+ new /datum/point_redemption_item("Shelter Capsule", /obj/item/survivalcapsule, 50),
+ new /datum/point_redemption_item("Point Transfer Card", /obj/item/point_redemption_voucher/preloaded/survey/c50, 50),
+ new /datum/point_redemption_item("Regular Firstaid Kit", /obj/item/storage/firstaid/regular, 50),
+ // new /datum/point_redemption_item("Advanced Firstaid Kit", /obj/item/storage/firstaid/adv, 50),
+ // new /datum/point_redemption_item("Bone Restoration Medicine", /obj/item/storage/firstaid/bonemed, 50),
+ // new /datum/point_redemption_item("Clotting Kit", /obj/item/storage/firstaid/clotting, 50),
+ new /datum/point_redemption_item("Survival Medipen", /obj/item/reagent_containers/hypospray/autoinjector/miner, 50),
+ new /datum/point_redemption_item("Injector (L) - Glucose", /obj/item/reagent_containers/hypospray/autoinjector/biginjector/glucose, 50),
+ new /datum/point_redemption_item("Injector (L) - Panacea", /obj/item/reagent_containers/hypospray/autoinjector/biginjector/purity, 50),
+ new /datum/point_redemption_item("Injector (L) - Trauma", /obj/item/reagent_containers/hypospray/autoinjector/biginjector/brute, 50),
+ new /datum/point_redemption_item("Digital Tablet - Standard", /obj/item/modular_computer/tablet/preset/custom_loadout/standard, 50),
+ new /datum/point_redemption_item("Geiger Counter", /obj/item/geiger_counter, 75),
+ new /datum/point_redemption_item("Defense Equipment - Steel Machete", /obj/item/material/knife/machete, 75),
+ new /datum/point_redemption_item("Defense Equipment - Kinetic Dagger", /obj/item/kinetic_crusher/dagger, 75),
+ new /datum/point_redemption_item("Laser Pointer", /obj/item/laser_pointer, 90),
+ new /datum/point_redemption_item("Digital Tablet - Advanced", /obj/item/modular_computer/tablet/preset/custom_loadout/advanced, 100),
+ new /datum/point_redemption_item("Nanopaste Tube", /obj/item/stack/nanopaste, 100),
+ new /datum/point_redemption_item("Binoculars", /obj/item/binoculars, 100),
+ new /datum/point_redemption_item("100 Thalers", /obj/item/spacecash/c100, 100),
+ new /datum/point_redemption_item("Defense Equipment - Razor Drone Deployer", /obj/item/grenade/spawnergrenade/manhacks/station/locked, 100),
+ new /datum/point_redemption_item("Mini-Translocator", /obj/item/perfect_tele/one_beacon, 120),
+ new /datum/point_redemption_item("Extraction Equipment - Fulton Pack", /obj/item/extraction_pack, 125),
+ new /datum/point_redemption_item("Defense Equipment - Sentry Drone Deployer", /obj/item/grenade/spawnergrenade/ward, 150),
+ new /datum/point_redemption_item("Holy Crusade Pack", /obj/item/storage/lockbox/crusade, 200),
+ new /datum/point_redemption_item("Maniple Pack", /obj/item/storage/lockbox/maniple, 200),
+ new /datum/point_redemption_item("Jump Boots", /obj/item/clothing/shoes/bhop, 250),
+ new /datum/point_redemption_item("Defense Equipment - AXHS Gun Case", /obj/item/storage/lockbox/axhs, 250),
+ new /datum/point_redemption_item("Conscript Pack", /obj/item/storage/lockbox/russian, 250),
+ new /datum/point_redemption_item("Extraction Equipment - Fulton Beacon", /obj/item/fulton_core, 300),
+ new /datum/point_redemption_item("Industrial Equipment - Phoron Bore", /obj/item/gun/projectile/magnetic/matfed, 300),
+ new /datum/point_redemption_item("Luxury Shelter Capsule", /obj/item/survivalcapsule/luxury, 310),
+ new /datum/point_redemption_item("Colonial Recce Pack", /obj/item/storage/lockbox/colonial, 350),
+ //uav code is cursed new /datum/point_redemption_item("UAV - Recon Skimmer", /obj/item/uav, 400),
+ new /datum/point_redemption_item("Away Team Pack", /obj/item/storage/lockbox/away, 550),
+ new /datum/point_redemption_item("Gateway Guardian Pack", /obj/item/storage/lockbox/gateway, 800),
+ new /datum/point_redemption_item("Cyan Posse Pack", /obj/item/storage/lockbox/cowboy, 800),
+ new /datum/point_redemption_item("Bar Shelter Capsule", /obj/item/survivalcapsule/luxurybar, 1000),
+ new /datum/point_redemption_item("1000 Thalers", /obj/item/spacecash/c1000, 1000),
+ new /datum/point_redemption_item("Defense Equipment - Marksman Box", /obj/item/gunbox/marksman, 1000),
+ )
diff --git a/code/game/machinery/point_redemption_vendor/unsorted_please_sort_these.dm b/code/game/machinery/point_redemption_vendor/unsorted_please_sort_these.dm
new file mode 100644
index 00000000000..9d27f1903c2
--- /dev/null
+++ b/code/game/machinery/point_redemption_vendor/unsorted_please_sort_these.dm
@@ -0,0 +1,113 @@
+// stuff i kicked over from old files that i don't want to deal with. someone deal with them.
+
+/obj/item/tank/vimur
+ name = "Vimur tank"
+ desc = "Contains Vimur. A gas with very high thermal capacity. Probably not so smart to breath."
+ icon = 'icons/obj/tank_vr.dmi'
+ icon_state = "coolant"
+ gauge_icon = null
+ slot_flags = null //they have no straps!
+ volume = 500//Standard tanks have 70, we up that alot, a cannister has 1000, but we want this to be worth our points.
+
+/obj/item/tank/vimur/Initialize(mapload)
+ . = ..()
+ src.air_contents.adjust_gas(GAS_ID_VIMUR, (10*ONE_ATMOSPHERE)*volume/(R_IDEAL_GAS_EQUATION*T20C))
+ return .
+
+/obj/item/engineering_mystical_tech
+ name = "XYE"
+ desc = "???"
+ icon = 'icons/obj/abductor.dmi'
+ icon_state = "circuit"
+ w_class = WEIGHT_CLASS_SMALL
+ origin_tech = list(TECH_PRECURSOR = 1)
+
+// todo: generic supply vouchers
+/obj/item/engineering_voucher
+ name = "equipment voucher"
+ desc = "An used voucher that could be used to be redeemed for something at the cargo console"
+ icon = 'icons/obj/vouchers.dmi'
+ icon_state = "engineering_voucher_used"
+ w_class = WEIGHT_CLASS_SMALL
+ var/datum/supply_pack/redeemable_for = null
+
+/obj/item/engineering_voucher/proc/redeem(var/mob/user)
+ if(!redeemable_for)
+ to_chat(user, SPAN_WARNING("[src] has already been used"))
+ return
+ var/datum/supply_order/order = new /datum/supply_order
+
+ var/idname = "*None Provided*"
+ if(ishuman(user))
+ var/mob/living/carbon/human/H = user
+ idname = H.get_authentification_name()
+ else if(issilicon(user))
+ idname = user.real_name
+
+ order.ordernum = ++SSsupply.ordernum // Ordernum is used to track the order between the playerside list of orders and the adminside list
+ order.index = order.ordernum // Index can be fabricated, or falsified. Ordernum is a permanent marker used to track the order
+ order.object = redeemable_for
+ order.name = redeemable_for.name
+ order.cost = 0
+ order.ordered_by = idname
+ order.comment = "Voucher redemption"
+ order.ordered_at = stationdate2text() + " - " + stationtime2text()
+ order.status = SUP_ORDER_APPROVED //auto approved
+ order.approved_by = "[user]"
+ order.approved_at = stationdate2text() + " - " + stationtime2text()
+
+ SSsupply.order_history += order//tell supply the order exists.
+ SSsupply.adm_order_history += order
+
+ name = "used " + name
+ redeemable_for = null
+ icon_state = "engineering_voucher_used"
+ desc = "An used voucher that was used to redeem for something at the cargo console"
+
+/obj/item/engineering_voucher/teg
+ name = "Thermo-Electric Generator voucher"
+ desc = "A voucher redeemable, at any NT cargo department, for shipment of a Thermo-Electric Generator"
+ icon_state = "engineering_voucher"
+ redeemable_for = new /datum/supply_pack/nanotrasen/engineering/teg
+
+/obj/item/engineering_voucher/collectors
+ name = "Radiation Collector voucher"
+ desc = "A voucher redeemable, at any NT cargo department, for shipment of crate of radiation collectors"
+ icon_state = "engineering_voucher"
+ redeemable_for = new /datum/supply_pack/nanotrasen/engineering/engine/radiation_collector
+
+/obj/item/engineering_voucher/smcore
+ name = "Supermatter Core voucher"
+ desc = "A voucher redeemable, at any NT cargo department, for shipment of a Supermatter core"
+ icon_state = "engineering_voucher"
+ redeemable_for = new /datum/supply_pack/nanotrasen/engineering/engine/supermatter_core
+
+/obj/item/engineering_voucher/fusion_core
+ name = "Fusion Core voucher"
+ desc = "A voucher redeemable, at any NT cargo department, for shipment of a fusion core"
+ icon_state = "engineering_voucher"
+ redeemable_for = new /datum/supply_pack/nanotrasen/engineering/engine/fusion_core
+
+/obj/item/engineering_voucher/fusion_fuel_injector
+ name = "Fuel Injector voucher"
+ desc = "A voucher redeemable, at any NT cargo department, for shipment of a fusion fuel injector"
+ icon_state = "engineering_voucher"
+ redeemable_for = new /datum/supply_pack/nanotrasen/engineering/engine/fusion_fuel_injector
+
+/obj/item/engineering_voucher/gyrotrons
+ name = "Gyrotron voucher"
+ desc = "A voucher redeemable, at any NT cargo department, for shipment of Gyrotrons"
+ icon_state = "engineering_voucher"
+ redeemable_for = new /datum/supply_pack/nanotrasen/engineering/engine/gyrotron
+
+/obj/item/engineering_voucher/fuel_compressor
+ name = "Fuel compressor voucher"
+ desc = "A voucher redeemable, at any NT cargo department, for shipment of a Fuel rod compressor"
+ icon_state = "engineering_voucher"
+ redeemable_for = new /datum/supply_pack/nanotrasen/engineering/engine/fusion_fuel_compressor
+
+/obj/item/engineering_voucher/reflector
+ name = "Laser reflector voucher"
+ desc = "A voucher redeemable, at any NT cargo department, for a single laser reflector."
+ icon_state = "engineering_voucher"
+ redeemable_for = new /datum/supply_pack/nanotrasen/engineering/reflector
diff --git a/code/game/objects/items/id_cards/station_ids.dm b/code/game/objects/items/id_cards/station_ids.dm
index 8a455e75ccc..20a473b093d 100644
--- a/code/game/objects/items/id_cards/station_ids.dm
+++ b/code/game/objects/items/id_cards/station_ids.dm
@@ -37,9 +37,11 @@
var/assignment = null //can be alt title or the actual job
var/rank = null //actual job
- var/mining_points = 0 // For redeeming at mining equipment vendors
- var/survey_points = 0 // For redeeming at explorer equipment vendors.
- var/engineer_points = 0 // For redeeming at engineering equipment vendors
+ //* Point Redemption *//
+
+ /// stored POINT_REDEMPTION_TYPE_* points; enum associated to number
+ /// * lazy list
+ var/list/stored_redemption_points
/obj/item/card/id/Initialize(mapload)
. = ..()
@@ -76,8 +78,11 @@
. = ..()
if(.)
. += " "
- if(mining_points)
- . += "There's [mining_points] mining equipment redemption point\s loaded onto this card."
+ for(var/key in stored_redemption_points)
+ var/amount = stored_redemption_points[key]
+ if(!amount)
+ continue
+ . += "There's [amount] [key] equipment redemption point[amount > 1 ? "s" : ""] loaded on this card."
/obj/item/card/id/update_name()
name = "[registered_name? "[registered_name]'s " : ""]ID Card [assignment? "([assignment])" : ""]"
@@ -216,6 +221,27 @@
var/datum/tgui_module/card_mod/admin/card_vv/mod = new(src)
mod.ui_interact(usr)
+//* Point Redemption *//
+
+/obj/item/card/id/proc/get_redemption_points(point_type)
+ return stored_redemption_points?[point_type] || 0
+
+/obj/item/card/id/proc/set_redemption_points(point_type, amount)
+ LAZYSET(stored_redemption_points, point_type, amount)
+
+/obj/item/card/id/proc/adjust_redemption_points(point_type, amount)
+ LAZYINITLIST(stored_redemption_points)
+ stored_redemption_points[point_type] = max(0, stored_redemption_points[point_type] + amount)
+
+/**
+ * @return TRUE / FALSE on success / fail
+ */
+/obj/item/card/id/proc/use_redemption_points(point_type, amount)
+ if(stored_redemption_points?[point_type] < amount)
+ return FALSE
+ stored_redemption_points[point_type] -= amount
+ return TRUE
+
/obj/item/card/id/silver
name = "command identification card"
desc = "A silver card which shows honour and dedication."
diff --git a/code/game/objects/structures/crates_lockers/closets/secure/explorer.dm b/code/game/objects/structures/crates_lockers/closets/secure/explorer.dm
index 38c6d00eae8..ce4ce245aa8 100644
--- a/code/game/objects/structures/crates_lockers/closets/secure/explorer.dm
+++ b/code/game/objects/structures/crates_lockers/closets/secure/explorer.dm
@@ -152,7 +152,7 @@
/obj/item/clothing/accessory/holster/leg,
/obj/item/reagent_containers/food/snacks/liquid,
/obj/item/reagent_containers/food/snacks/liquid/protein,
- /obj/item/card/mining_point_card/survey/gimmick,
+ /obj/item/point_redemption_voucher/preloaded/survey/c300,
/obj/item/cataloguer/compact/pathfinder,
/obj/item/binoculars)
diff --git a/code/modules/catalogue/cataloguer.dm b/code/modules/catalogue/cataloguer.dm
index 452e3296d28..4676f0f844f 100644
--- a/code/modules/catalogue/cataloguer.dm
+++ b/code/modules/catalogue/cataloguer.dm
@@ -329,7 +329,7 @@ GLOBAL_LIST_EMPTY(all_cataloguers)
busy = TRUE
var/obj/item/card/id/ID = W
if(points_stored)
- ID.survey_points += points_stored
+ ID.adjust_redemption_points(POINT_REDEMPTION_TYPE_SURVEY, points_stored)
points_stored = 0
to_chat(user, "You swipe the id over \the [src].")
else
diff --git a/code/modules/mining/machinery/machine_processing.dm b/code/modules/mining/machinery/machine_processing.dm
index 950f9b19713..5adfbb47f14 100644
--- a/code/modules/mining/machinery/machine_processing.dm
+++ b/code/modules/mining/machinery/machine_processing.dm
@@ -74,7 +74,7 @@
data["unclaimedPoints"] = machine.points
if(inserted_id)
data["idName"] = inserted_id.registered_name
- data["idPoints"] = inserted_id.mining_points
+ data["idPoints"] = inserted_id.get_redemption_points(POINT_REDEMPTION_TYPE_MINING)
else
data["idName"] = ""
data["idPoints"] = 0
@@ -114,7 +114,7 @@
return TRUE
if("claim_points")
if(istype(inserted_id))
- inserted_id.mining_points += machine.points
+ inserted_id.adjust_redemption_points(POINT_REDEMPTION_TYPE_MINING, machine.points)
machine.points = 0
playsound(src.loc, 'sound/machines/ping.ogg', clickvol, 0)
return TRUE
diff --git a/code/modules/mining/ore_redemption_machine/engineering_points_vendor.dm b/code/modules/mining/ore_redemption_machine/engineering_points_vendor.dm
deleted file mode 100644
index f2ad1e9bebe..00000000000
--- a/code/modules/mining/ore_redemption_machine/engineering_points_vendor.dm
+++ /dev/null
@@ -1,235 +0,0 @@
-/*****************************
- * Points vendor for engineers
- * Points are aquired via crypto miners.
- *****************************/
-
-/obj/machinery/mineral/equipment_vendor/engineering
- name = "Engineering Equipment Vendor"
- desc = "An equipment vendor for engineers, point generated by the crypto miners can be spend here."
- icon_state = "engineering"
- icon_deny = "engineering-deny"
- child = TRUE
- //circuit = /obj/item/circuitboard/engineering_equip
- prize_list = list(
- //Mining vendor steals
- new /datum/data/mining_equipment("Vodka", /obj/item/reagent_containers/food/drinks/bottle/vodka, 3),
- new /datum/data/mining_equipment("Cigar", /obj/item/clothing/mask/smokable/cigarette/cigar/havana, 5),
- new /datum/data/mining_equipment("Soap", /obj/item/soap/nanotrasen, 2),
- new /datum/data/mining_equipment("Laser Pointer", /obj/item/laser_pointer, 9),
- new /datum/data/mining_equipment("Plush Toy", /obj/random/plushie, 3),
- new /datum/data/mining_equipment("GPS Device", /obj/item/gps/engineering, 1),
- new /datum/data/mining_equipment("50 Point Transfer Card", /obj/item/card/mining_point_card/engineering, 50),
- new /datum/data/mining_equipment("Umbrella", /obj/item/melee/umbrella/random, 20),
- new /datum/data/mining_equipment("100 Thaler", /obj/item/spacecash/c100, 4),
- new /datum/data/mining_equipment("1000 Thaler", /obj/item/spacecash/c1000, 40),
- new /datum/data/mining_equipment("Hardsuit - Control Module", /obj/item/hardsuit/industrial, 50),
- new /datum/data/mining_equipment("Hardsuit - Plasma Cutter", /obj/item/hardsuit_module/device/plasmacutter, 10),
- new /datum/data/mining_equipment("Hardsuit - Maneuvering Jets", /obj/item/hardsuit_module/maneuvering_jets, 12),
- new /datum/data/mining_equipment("Hardsuit - Intelligence Storage", /obj/item/hardsuit_module/ai_container, 25),
- new /datum/data/mining_equipment("Injector (L) - Panacea", /obj/item/reagent_containers/hypospray/autoinjector/biginjector/purity, 50),
- //Mining vendor steals - Ends
- //Power tools like the CE gets, if kev comes crying: https://cdn.discordapp.com/attachments/296237931587305472/956517623519141908/unknown.png
- new /datum/data/mining_equipment("Advanced Hardsuit", /obj/item/hardsuit/ce, 150),
- new /datum/data/mining_equipment("Power Tool - Hand Drill", /obj/item/tool/screwdriver/power, 80),
- new /datum/data/mining_equipment("Power Tool - Jaws of life", /obj/item/tool/crowbar/power, 80),
- new /datum/data/mining_equipment("Power Tool - Experimental Welder", /obj/item/weldingtool/experimental, 80),
- new /datum/data/mining_equipment("Power Tool - Upgraded T-Ray Scanner", /obj/item/t_scanner/upgraded, 80),
- new /datum/data/mining_equipment("Power Tool - Advanced T-Ray Scanner", /obj/item/t_scanner/advanced, 80),
- new /datum/data/mining_equipment("Power Tool - Long Range Atmosphere scanner", /obj/item/atmos_analyzer/longrange, 80),
- //new /datum/data/mining_equipment("Power Tool - Holofan Projector", /obj/item/holosign_creator/combifan, 80),
- new /datum/data/mining_equipment("Superior Welding Goggles", /obj/item/clothing/glasses/welding/superior, 50),
-
- //Level 2 stock parts, to make engineering kinda self sufficent for minor upgrades but the parts are also kinda expansive
- new /datum/data/mining_equipment("Stock Parts - Advanced Capacitor", /obj/item/stock_parts/capacitor/adv, 20),
- new /datum/data/mining_equipment("Stock Parts - Advanced Scanning Module", /obj/item/stock_parts/scanning_module/adv, 20),
- new /datum/data/mining_equipment("Stock Parts - Nano-Manipulator", /obj/item/stock_parts/manipulator/nano, 20),
- new /datum/data/mining_equipment("Stock Parts - High-Power Micro-Laser", /obj/item/stock_parts/micro_laser/high, 20),
- new /datum/data/mining_equipment("Stock Parts - Advanced Matter Bin", /obj/item/stock_parts/matter_bin/adv, 20),
-
- //Special Resources which the vendor is the primary source off:
- new /datum/data/mining_equipment("Special Parts - Vimur Tank", /obj/item/tank/vimur, 5),
- new /datum/data/mining_equipment("Special Parts - TEG Voucher", /obj/item/engineering_voucher/teg, 20),
- new /datum/data/mining_equipment("Special Parts - SM Core Voucher", /obj/item/engineering_voucher/smcore, 40),
- new /datum/data/mining_equipment("Special Parts - Fusion Core Voucher", /obj/item/engineering_voucher/fusion_core, 20),
- new /datum/data/mining_equipment("Special Parts - Fuel Injector Voucher", /obj/item/engineering_voucher/fusion_fuel_injector, 10),
- new /datum/data/mining_equipment("Special Parts - Gyrotrons Voucher", /obj/item/engineering_voucher/gyrotrons, 20),
- new /datum/data/mining_equipment("Special Parts - Fuel compressor Voucher", /obj/item/engineering_voucher/fuel_compressor, 10),
- new /datum/data/mining_equipment("Special Parts - Collector Voucher", /obj/item/engineering_voucher/collectors, 10),
- new /datum/data/mining_equipment("Special Parts - Laser Reflector Voucher", /obj/item/engineering_voucher/reflector, 30),
- //voucher: Solar crate, Vimur canister
- new /datum/data/mining_equipment("???", /obj/item/engineering_mystical_tech, 1000)
- )
-
-/obj/machinery/mineral/equipment_vendor/engineering/interact(mob/user)
- user.set_machine(src)
-
- var/dat
- dat +="
"
- if(istype(inserted_id))
- dat += "You have [inserted_id.engineer_points] engineering points collected. Eject ID. "
- else
- dat += "No ID inserted. Insert ID. "
- dat += "
"
- dat += " Equipment point cost list:
"
- for(var/datum/data/mining_equipment/prize in prize_list)
- dat += "
"
- var/datum/browser/popup = new(user, "miningvendor", "Engineering Equipment Vendor", 400, 600)
- popup.set_content(dat)
- popup.open()
-
-/obj/machinery/mineral/equipment_vendor/engineering/Topic(href, href_list)
- if(..())
- return 1
-
- if(href_list["choice"])
- if(istype(inserted_id))
- if(href_list["choice"] == "eject")
- to_chat(usr, "You eject the ID from [src]'s card slot.")
- if(ishuman(usr))
- usr.put_in_hands_or_drop(inserted_id)
- inserted_id = null
- else
- inserted_id.forceMove(get_turf(src))
- inserted_id = null
- else if(href_list["choice"] == "insert")
- var/obj/item/card/id/I = usr.get_active_held_item()
- if(istype(I) && !inserted_id)
- if(!usr.attempt_insert_item_for_installation(I, src))
- return
- inserted_id = I
- interact(usr)
- to_chat(usr, "You insert the ID into [src]'s card slot.")
- else
- to_chat(usr, "No valid ID.")
- flick(icon_deny, src)
-
- if(href_list["purchase"])
- if(istype(inserted_id))
- var/datum/data/mining_equipment/prize = locate(href_list["purchase"])
- if (!prize || !(prize in prize_list))
- to_chat(usr, "Error: Invalid choice!")
- flick(icon_deny, src)
- return
- if(prize.cost > inserted_id.engineer_points)
- to_chat(usr, "Error: Insufficent points for [prize.equipment_name]!")
- flick(icon_deny, src)
- else
- inserted_id.engineer_points -= prize.cost
- to_chat(usr, "[src] clanks to life briefly before vending [prize.equipment_name]!")
- new prize.equipment_path(drop_location())
- else
- to_chat(usr, "Error: Please insert a valid ID!")
- flick(icon_deny, src)
- updateUsrDialog()
-
-/obj/item/tank/vimur
- name = "Vimur tank"
- desc = "Contains Vimur. A gas with very high thermal capacity. Probably not so smart to breath."
- icon = 'icons/obj/tank_vr.dmi'
- icon_state = "coolant"
- gauge_icon = null
- slot_flags = null //they have no straps!
- volume = 500//Standard tanks have 70, we up that alot, a cannister has 1000, but we want this to be worth our points.
-
-/obj/item/tank/vimur/Initialize(mapload)
- . = ..()
- src.air_contents.adjust_gas(GAS_ID_VIMUR, (10*ONE_ATMOSPHERE)*volume/(R_IDEAL_GAS_EQUATION*T20C))
- return .
-
-/obj/item/engineering_voucher
- name = "equipment voucher"
- desc = "An used voucher that could be used to be redeemed for something at the cargo console"
- icon = 'icons/obj/vouchers.dmi'
- icon_state = "engineering_voucher_used"
- w_class = WEIGHT_CLASS_SMALL
- var/datum/supply_pack/redeemable_for = null
-
-/obj/item/engineering_voucher/proc/redeem(var/mob/user)
- if(!redeemable_for)
- to_chat(user, SPAN_WARNING("[src] has already been used"))
- return
- var/datum/supply_order/order = new /datum/supply_order
-
- var/idname = "*None Provided*"
- if(ishuman(user))
- var/mob/living/carbon/human/H = user
- idname = H.get_authentification_name()
- else if(issilicon(user))
- idname = user.real_name
-
- order.ordernum = ++SSsupply.ordernum // Ordernum is used to track the order between the playerside list of orders and the adminside list
- order.index = order.ordernum // Index can be fabricated, or falsified. Ordernum is a permanent marker used to track the order
- order.object = redeemable_for
- order.name = redeemable_for.name
- order.cost = 0
- order.ordered_by = idname
- order.comment = "Voucher redemption"
- order.ordered_at = stationdate2text() + " - " + stationtime2text()
- order.status = SUP_ORDER_APPROVED //auto approved
- order.approved_by = "[user]"
- order.approved_at = stationdate2text() + " - " + stationtime2text()
-
- SSsupply.order_history += order//tell supply the order exists.
- SSsupply.adm_order_history += order
-
- name = "used " + name
- redeemable_for = null
- icon_state = "engineering_voucher_used"
- desc = "An used voucher that was used to redeem for something at the cargo console"
-
-/obj/item/engineering_voucher/teg
- name = "Thermo-Electric Generator voucher"
- desc = "A voucher redeemable, at any NT cargo department, for shipment of a Thermo-Electric Generator"
- icon_state = "engineering_voucher"
- redeemable_for = new /datum/supply_pack/nanotrasen/engineering/teg
-
-/obj/item/engineering_voucher/collectors
- name = "Radiation Collector voucher"
- desc = "A voucher redeemable, at any NT cargo department, for shipment of crate of radiation collectors"
- icon_state = "engineering_voucher"
- redeemable_for = new /datum/supply_pack/nanotrasen/engineering/engine/radiation_collector
-
-/obj/item/engineering_voucher/smcore
- name = "Supermatter Core voucher"
- desc = "A voucher redeemable, at any NT cargo department, for shipment of a Supermatter core"
- icon_state = "engineering_voucher"
- redeemable_for = new /datum/supply_pack/nanotrasen/engineering/engine/supermatter_core
-
-/obj/item/engineering_voucher/fusion_core
- name = "Fusion Core voucher"
- desc = "A voucher redeemable, at any NT cargo department, for shipment of a fusion core"
- icon_state = "engineering_voucher"
- redeemable_for = new /datum/supply_pack/nanotrasen/engineering/engine/fusion_core
-
-/obj/item/engineering_voucher/fusion_fuel_injector
- name = "Fuel Injector voucher"
- desc = "A voucher redeemable, at any NT cargo department, for shipment of a fusion fuel injector"
- icon_state = "engineering_voucher"
- redeemable_for = new /datum/supply_pack/nanotrasen/engineering/engine/fusion_fuel_injector
-
-/obj/item/engineering_voucher/gyrotrons
- name = "Gyrotron voucher"
- desc = "A voucher redeemable, at any NT cargo department, for shipment of Gyrotrons"
- icon_state = "engineering_voucher"
- redeemable_for = new /datum/supply_pack/nanotrasen/engineering/engine/gyrotron
-
-/obj/item/engineering_voucher/fuel_compressor
- name = "Fuel compressor voucher"
- desc = "A voucher redeemable, at any NT cargo department, for shipment of a Fuel rod compressor"
- icon_state = "engineering_voucher"
- redeemable_for = new /datum/supply_pack/nanotrasen/engineering/engine/fusion_fuel_compressor
-
-/obj/item/engineering_voucher/reflector
- name = "Laser reflector voucher"
- desc = "A voucher redeemable, at any NT cargo department, for a single laser reflector."
- icon_state = "engineering_voucher"
- redeemable_for = new /datum/supply_pack/nanotrasen/engineering/reflector
-
-/obj/item/engineering_mystical_tech
- name = "XYE"
- desc = "???"
- icon = 'icons/obj/abductor.dmi'
- icon_state = "circuit"
- w_class = WEIGHT_CLASS_SMALL
- origin_tech = list(TECH_PRECURSOR = 1)
diff --git a/code/modules/mining/ore_redemption_machine/equipment_vendor.dm b/code/modules/mining/ore_redemption_machine/equipment_vendor.dm
deleted file mode 100644
index c6294d6f77d..00000000000
--- a/code/modules/mining/ore_redemption_machine/equipment_vendor.dm
+++ /dev/null
@@ -1,250 +0,0 @@
-/**********************Mining Equipment Locker**************************/
-
-/obj/machinery/mineral/equipment_vendor
- name = "mining equipment vendor"
- desc = "An equipment vendor for miners, points collected at an ore redemption machine can be spent here."
- icon = 'icons/obj/machines/mining_machines.dmi'
- icon_state = "mining"
- density = TRUE
- anchored = TRUE
- circuit = /obj/item/circuitboard/mining_equipment_vendor
- var/icon_deny = "mining-deny"
- var/obj/item/card/id/inserted_id
- var/child = FALSE//To tell topic() to bypass this iteration of it
- var/list/prize_list = list(
- new /datum/data/mining_equipment("1 Marker Beacon", /obj/item/stack/marker_beacon, 10),
- new /datum/data/mining_equipment("10 Marker Beacons", /obj/item/stack/marker_beacon/ten, 100),
- new /datum/data/mining_equipment("30 Marker Beacons", /obj/item/stack/marker_beacon/thirty, 300),
- new /datum/data/mining_equipment("Whiskey", /obj/item/reagent_containers/food/drinks/bottle/whiskey, 125),
- new /datum/data/mining_equipment("Absinthe", /obj/item/reagent_containers/food/drinks/bottle/absinthe, 125),
- new /datum/data/mining_equipment("Hard Root Beer", /obj/item/reagent_containers/food/drinks/bottle/small/alcsassafras, 70),
- new /datum/data/mining_equipment("Special Blend Whiskey", /obj/item/reagent_containers/food/drinks/bottle/specialwhiskey, 250),
- new /datum/data/mining_equipment("Random Booze", /obj/random/alcohol, 125),
- new /datum/data/mining_equipment("Cigar", /obj/item/clothing/mask/smokable/cigarette/cigar/havana, 150),
- new /datum/data/mining_equipment("Root Beer", /obj/item/reagent_containers/food/drinks/bottle/small/sassafras, 50),
- new /datum/data/mining_equipment("Sarsaparilla", /obj/item/reagent_containers/food/drinks/bottle/small/sarsaparilla, 50),
- new /datum/data/mining_equipment("Soap", /obj/item/soap/nanotrasen, 200),
- new /datum/data/mining_equipment("Laser Pointer", /obj/item/laser_pointer, 900),
- new /datum/data/mining_equipment("Geiger Counter", /obj/item/geiger_counter, 750),
- new /datum/data/mining_equipment("Plush Toy", /obj/random/plushie, 300),
- new /datum/data/mining_equipment("GPS Device", /obj/item/gps/mining, 100),
- new /datum/data/mining_equipment("Portable Fuel Can", /obj/item/reagent_containers/portable_fuelcan, 250),
- // TODO new /datum/data/mining_equipment("Advanced Scanner", /obj/item/t_scanner/adv_mining_scanner, 800),
- new /datum/data/mining_equipment("Fulton Beacon", /obj/item/fulton_core, 500),
- new /datum/data/mining_equipment("Shelter Capsule", /obj/item/survivalcapsule, 500),
- // TODO new /datum/data/mining_equipment("Explorer's Webbing", /obj/item/storage/belt/mining, 500),
- new /datum/data/mining_equipment("500 Point Transfer Card", /obj/item/card/mining_point_card, 500),
- new /datum/data/mining_equipment("1000 Point Transfer Card", /obj/item/card/mining_point_card/onethou, 1000),
- new /datum/data/mining_equipment("2000 Point Transfer Card", /obj/item/card/mining_point_card/twothou, 2000),
- new /datum/data/mining_equipment("3000 Point Transfer Card", /obj/item/card/mining_point_card/threethou, 3000),
- new /datum/data/mining_equipment("Umbrella", /obj/item/melee/umbrella/random, 200),
- new /datum/data/mining_equipment("Survival Medipen", /obj/item/reagent_containers/hypospray/autoinjector/miner, 500),
- new /datum/data/mining_equipment("Mini-Translocator", /obj/item/perfect_tele/one_beacon, 1200),
- // new /datum/data/mining_equipment("Kinetic Crusher", /obj/item/twohanded/required/kinetic_crusher, 750),
- new /datum/data/mining_equipment("Kinetic Accelerator", /obj/item/gun/projectile/energy/kinetic_accelerator, 900),
- new /datum/data/mining_equipment("Resonator", /obj/item/resonator, 900),
- new /datum/data/mining_equipment("Fulton Pack", /obj/item/extraction_pack, 1200),
- new /datum/data/mining_equipment("Wormhole Fulton Pack", /obj/item/extraction_pack/wormhole, 1750),
- new /datum/data/mining_equipment("Silver Pickaxe", /obj/item/pickaxe/silver, 1200),
- new /datum/data/mining_equipment("Climbing Pick", /obj/item/pickaxe/icepick, 2200),
- //new /datum/data/mining_equipment("Mining Conscription Kit", /obj/item/storage/backpack/duffelbag/mining_conscript, 1000),
- new /datum/data/mining_equipment("Diamond Pickaxe", /obj/item/pickaxe/diamond, 2000),
- new /datum/data/mining_equipment("Advanced Ore Scanner", /obj/item/mining_scanner/advanced, 2000),
- new /datum/data/mining_equipment("100 Thalers", /obj/item/spacecash/c100, 20000),
- new /datum/data/mining_equipment("1000 Thalers", /obj/item/spacecash/c1000, 200000),
- new /datum/data/mining_equipment("Hardsuit - Control Module", /obj/item/hardsuit/industrial, 2000),
- new /datum/data/mining_equipment("Hardsuit - Plasma Cutter", /obj/item/hardsuit_module/device/plasmacutter, 800),
- new /datum/data/mining_equipment("Hardsuit - Drill", /obj/item/hardsuit_module/device/drill, 5000),
- new /datum/data/mining_equipment("Hardsuit - Ore Scanner", /obj/item/hardsuit_module/device/orescanner, 1000),
- new /datum/data/mining_equipment("Hardsuit - Material Scanner", /obj/item/hardsuit_module/vision/material, 500),
- new /datum/data/mining_equipment("Hardsuit - Maneuvering Jets", /obj/item/hardsuit_module/maneuvering_jets, 1250),
- new /datum/data/mining_equipment("Hardsuit - Intelligence Storage", /obj/item/hardsuit_module/ai_container, 2500),
- new /datum/data/mining_equipment("Hardsuit - Smoke Bomb Deployer", /obj/item/hardsuit_module/grenade_launcher/smoke, 2000),
- new /datum/data/mining_equipment("Industrial Equipment - Phoron Bore", /obj/item/gun/projectile/magnetic/matfed, 3000),
- new /datum/data/mining_equipment("Industrial Equipment - Sheet-Snatcher",/obj/item/storage/bag/sheetsnatcher, 500),
- new /datum/data/mining_equipment("Repurposed Equipment - Mining Carbine", /obj/item/gun/projectile/energy/gun/miningcarbine, 5000),
- new /datum/data/mining_equipment("Digital Tablet - Standard", /obj/item/modular_computer/tablet/preset/custom_loadout/standard, 500),
- new /datum/data/mining_equipment("Digital Tablet - Advanced", /obj/item/modular_computer/tablet/preset/custom_loadout/advanced, 1000),
- new /datum/data/mining_equipment("Super Resonator", /obj/item/resonator/upgraded, 2500),
- new /datum/data/mining_equipment("Jump Boots", /obj/item/clothing/shoes/bhop, 2500),
- new /datum/data/mining_equipment("Luxury Shelter Capsule", /obj/item/survivalcapsule/luxury, 3100),
- new /datum/data/mining_equipment("KA White Tracer Rounds", /obj/item/ka_modkit/tracer, 125),
- new /datum/data/mining_equipment("KA Adjustable Tracer Rounds", /obj/item/ka_modkit/tracer/adjustable, 175),
- new /datum/data/mining_equipment("KA Super Chassis", /obj/item/ka_modkit/chassis_mod, 250),
- new /datum/data/mining_equipment("KA Hyper Chassis", /obj/item/ka_modkit/chassis_mod/orange, 300),
- new /datum/data/mining_equipment("KA Range Increase", /obj/item/ka_modkit/range, 1000),
- new /datum/data/mining_equipment("KA Cooldown Decrease", /obj/item/ka_modkit/cooldown, 1200),
- new /datum/data/mining_equipment("KA Capacity Increase", /obj/item/ka_modkit/capacity, 1500),
- new /datum/data/mining_equipment("KA Holster", /obj/item/clothing/accessory/holster/waist/kinetic_accelerator, 350),
- new /datum/data/mining_equipment("Fine Excavation Kit - Chisels",/obj/item/storage/excavation, 500),
- new /datum/data/mining_equipment("Fine Excavation Kit - Measuring Tape",/obj/item/measuring_tape, 125),
- new /datum/data/mining_equipment("Fine Excavation Kit - Hand Pick",/obj/item/pickaxe/hand, 375),
- new /datum/data/mining_equipment("Explosive Excavation Kit - Plastic Charge",/obj/item/plastique/seismic/locked, 1500),
- new /datum/data/mining_equipment("Injector (L) - Glucose",/obj/item/reagent_containers/hypospray/autoinjector/biginjector/glucose, 500),
- new /datum/data/mining_equipment("Injector (L) - Panacea",/obj/item/reagent_containers/hypospray/autoinjector/biginjector/purity, 500),
- new /datum/data/mining_equipment("Injector (L) - Trauma",/obj/item/reagent_containers/hypospray/autoinjector/biginjector/brute, 500),
- new /datum/data/mining_equipment("Nanopaste Tube", /obj/item/stack/nanopaste, 1000),
- new /datum/data/mining_equipment("Defense Equipment - Smoke Bomb",/obj/item/grenade/smokebomb, 100),
- new /datum/data/mining_equipment("Defense Equipment - Razor Drone Deployer",/obj/item/grenade/spawnergrenade/manhacks/station/locked, 1000),
- new /datum/data/mining_equipment("Defense Equipment - Sentry Drone Deployer",/obj/item/grenade/spawnergrenade/ward, 1500),
- new /datum/data/mining_equipment("Defense Equipment - Plasteel Machete", /obj/item/clothing/accessory/holster/machete/occupied, 500),
- new /datum/data/mining_equipment("Defense Equipment - Kinetic Dagger", /obj/item/kinetic_crusher/dagger, 1200),
- new /datum/data/mining_equipment("Bar Shelter Capsule", /obj/item/survivalcapsule/luxurybar, 10000)
- )
-
-/datum/data/mining_equipment
- var/equipment_name = "generic"
- var/equipment_path = null
- var/cost = 0
-
-/datum/data/mining_equipment/New(name, path, cost)
- src.equipment_name = name
- src.equipment_path = path
- src.cost = cost
-
-/obj/machinery/mineral/equipment_vendor/power_change()
- var/old_stat = machine_stat
- ..()
- if(old_stat != machine_stat)
- update_icon()
- if(inserted_id && !powered())
- visible_message("The ID slot indicator light flickers on \the [src] as it spits out a card before powering down.")
- inserted_id.forceMove(get_turf(src))
-
-/obj/machinery/mineral/equipment_vendor/update_icon()
- if(panel_open)
- icon_state = "[initial(icon_state)]-open"
- else if(powered())
- icon_state = initial(icon_state)
- else
- icon_state = "[initial(icon_state)]-off"
-
-/obj/machinery/mineral/equipment_vendor/attack_hand(mob/user, datum/event_args/actor/clickchain/e_args)
- if(..())
- return
- interact(user)
-
-/obj/machinery/mineral/equipment_vendor/attack_ghost(mob/user)
- . = ..()
- interact(user)
-
-/obj/machinery/mineral/equipment_vendor/interact(mob/user)
- user.set_machine(src)
-
- var/dat
- dat +="
"
- if(istype(inserted_id))
- dat += "You have [inserted_id.mining_points] mining points collected. Eject ID. "
- else
- dat += "No ID inserted. Insert ID. "
- dat += "
"
- dat += " Equipment point cost list:
"
- for(var/datum/data/mining_equipment/prize in prize_list)
- dat += "
"
- var/datum/browser/popup = new(user, "miningvendor", "Mining Equipment Vendor", 400, 600)
- popup.set_content(dat)
- popup.open()
-
-/obj/machinery/mineral/equipment_vendor/Topic(href, href_list)
- if(..())
- return 1
- if(child)
- return 0
- if(href_list["choice"])
- if(istype(inserted_id))
- if(href_list["choice"] == "eject")
- to_chat(usr, "You eject the ID from [src]'s card slot.")
- if(ishuman(usr))
- usr.put_in_hands_or_drop(inserted_id)
- inserted_id = null
- else
- inserted_id.forceMove(get_turf(src))
- inserted_id = null
- else if(href_list["choice"] == "insert")
- var/obj/item/card/id/I = usr.get_active_held_item()
- if(istype(I) && !inserted_id)
- if(!usr.attempt_insert_item_for_installation(I, src))
- return
- inserted_id = I
- interact(usr)
- to_chat(usr, "You insert the ID into [src]'s card slot.")
- else
- to_chat(usr, "No valid ID.")
- flick(icon_deny, src)
-
- if(href_list["purchase"])
- if(istype(inserted_id))
- var/datum/data/mining_equipment/prize = locate(href_list["purchase"])
- if (!prize || !(prize in prize_list))
- to_chat(usr, "Error: Invalid choice!")
- flick(icon_deny, src)
- return
- if(prize.cost > inserted_id.mining_points)
- to_chat(usr, "Error: Insufficent points for [prize.equipment_name]!")
- flick(icon_deny, src)
- else
- inserted_id.mining_points -= prize.cost
- to_chat(usr, "[src] clanks to life briefly before vending [prize.equipment_name]!")
- new prize.equipment_path(drop_location())
- else
- to_chat(usr, "Error: Please insert a valid ID!")
- flick(icon_deny, src)
- updateUsrDialog()
-
-/obj/machinery/mineral/equipment_vendor/attackby(obj/item/I, mob/user, params)
- if(default_deconstruction_screwdriver(user, I))
- updateUsrDialog()
- return CLICKCHAIN_DO_NOT_PROPAGATE
- if(default_part_replacement(user, I))
- return CLICKCHAIN_DO_NOT_PROPAGATE
- if(default_deconstruction_crowbar(user, I))
- return CLICKCHAIN_DO_NOT_PROPAGATE
- if(istype(I, /obj/item/mining_voucher))
- if(!powered())
- return
- RedeemVoucher(I, user)
- return CLICKCHAIN_DO_NOT_PROPAGATE
- if(istype(I,/obj/item/card/id))
- if(!powered())
- return CLICKCHAIN_DO_NOT_PROPAGATE
- else if(!inserted_id)
- if(!user.attempt_insert_item_for_installation(I, src))
- return
- inserted_id = I
- interact(user)
- return CLICKCHAIN_DO_NOT_PROPAGATE
- ..()
-
-/obj/machinery/mineral/equipment_vendor/drop_products(method, atom/where)
- . = ..()
- inserted_id?.forceMove(where)
- inserted_id = null
-
-/obj/machinery/mineral/equipment_vendor/proc/RedeemVoucher(obj/item/mining_voucher/voucher, mob/redeemer)
- var/selection = input(redeemer, "Pick your equipment", "Mining Voucher Redemption") as null|anything in list("Kinetic Accelerator", "Resonator", "Mining Drone", "Advanced Scanner", "Crusher")
- if(!selection || !Adjacent(redeemer) || voucher.loc != redeemer)
- return
- var/drop_location = drop_location()
- switch(selection)
- if("Kinetic Accelerator")
- new /obj/item/gun/projectile/energy/kinetic_accelerator(drop_location)
- if("Resonator")
- new /obj/item/resonator(drop_location)
- qdel(voucher)
-
-/obj/machinery/mineral/equipment_vendor/proc/new_prize(var/name, var/path, var/cost) // Generic proc for adding new entries. Good for abusing for FUN and PROFIT.
- if(!cost)
- cost = 100
- if(!path)
- path = /obj/item/stack/marker_beacon
- if(!name)
- name = "Generic Entry"
- prize_list += new /datum/data/mining_equipment(name, path, cost)
-
-/obj/machinery/mineral/equipment_vendor/legacy_ex_act(severity, target)
- var/datum/effect_system/spark_spread/s = new /datum/effect_system/spark_spread
- s.set_up(5, 1, src)
- s.start()
- if(prob(50 / severity) && severity < 3)
- qdel(src)
diff --git a/code/modules/mining/ore_redemption_machine/mine_point_items.dm b/code/modules/mining/ore_redemption_machine/mine_point_items.dm
deleted file mode 100644
index fe4dd1f39d5..00000000000
--- a/code/modules/mining/ore_redemption_machine/mine_point_items.dm
+++ /dev/null
@@ -1,75 +0,0 @@
-/**********************Mining Equipment Locker Items**************************/
-
-/**********************Mining Equipment Voucher**********************/
-
-/obj/item/mining_voucher
- name = "mining voucher"
- desc = "A token to redeem a piece of equipment. Use it on a mining equipment vendor."
- icon = 'icons/obj/mining.dmi'
- icon_state = "mining_voucher"
- w_class = WEIGHT_CLASS_TINY
-
-/**********************Mining Point Card**********************/
-
-/obj/item/card/mining_point_card
- name = "mining point card"
- desc = "A small card preloaded with mining points. Swipe your ID card over it to transfer the points, then discard."
- icon_state = "data"
- var/mine_points = 500
- var/survey_points = 0
- var/engineering_points
-
-/obj/item/card/mining_point_card/attackby(obj/item/I, mob/user, params)
- if(istype(I, /obj/item/card/id))
- var/obj/item/card/id/C = I
- if(mine_points)
- C.mining_points += mine_points
- to_chat(user, "You transfer [mine_points] excavation points to [C].")
- mine_points = 0
- else
- to_chat(user, "There's no excavation points left on [src].")
-
- if(survey_points)
- C.survey_points += survey_points
- to_chat(user, "You transfer [survey_points] survey points to [C].")
- survey_points = 0
- else
- to_chat(user, "There's no survey points left on [src].")
-
- if(engineering_points)
- C.engineer_points += engineering_points
- to_chat(user, "You transfer [engineering_points] engineering points to [C].")
- engineering_points = 0
- else
- to_chat(user, "There's no engineering points left on [src].")
- ..()
-
-/obj/item/card/mining_point_card/examine(mob/user, dist)
- . = ..()
- . += "There's [mine_points] excavation points on the card."
- . += "There's [survey_points] survey points on the card."
-
-/obj/item/card/mining_point_card/onethou
- name = "deluxe mining point card"
- mine_points = 1000
-
-/obj/item/card/mining_point_card/twothou
- name = "deluxe mining point card"
- mine_points = 2000
-
-/obj/item/card/mining_point_card/threethou
- name = "deluxe mining point card"
- mine_points = 3000
-
-/obj/item/card/mining_point_card/survey
- mine_points = 0
- survey_points = 50
-
-/obj/item/card/mining_point_card/survey/gimmick
- name = "exploration equipment voucher"
- mine_points = 0
- survey_points = 300
-
-/obj/item/card/mining_point_card/engineering
- mine_points = 0
- engineering_points = 50
diff --git a/code/modules/mining/ore_redemption_machine/survey_vendor.dm b/code/modules/mining/ore_redemption_machine/survey_vendor.dm
deleted file mode 100644
index 1c8e8bc280f..00000000000
--- a/code/modules/mining/ore_redemption_machine/survey_vendor.dm
+++ /dev/null
@@ -1,124 +0,0 @@
-/obj/machinery/mineral/equipment_vendor/survey
- name = "exploration equipment vendor"
- desc = "An equipment vendor for explorers, points collected with a survey scanner can be spent here."
- icon = 'icons/obj/machines/mining_machines.dmi'
- icon_state = "exploration"
- density = TRUE
- anchored = TRUE
- circuit = /obj/item/circuitboard/exploration_equipment_vendor
- icon_deny = "exploration-deny"
- var/icon_vend = "exploration-vend"
- child = TRUE
- prize_list = list(
- new /datum/data/mining_equipment("1 Marker Beacon", /obj/item/stack/marker_beacon, 1),
- new /datum/data/mining_equipment("10 Marker Beacons", /obj/item/stack/marker_beacon/ten, 10),
- new /datum/data/mining_equipment("GPS Device", /obj/item/gps/explorer, 10),
- new /datum/data/mining_equipment("Defense Equipment - Smoke Bomb",/obj/item/grenade/smokebomb, 10),
- new /datum/data/mining_equipment("Whiskey", /obj/item/reagent_containers/food/drinks/bottle/whiskey, 10),
- new /datum/data/mining_equipment("Absinthe", /obj/item/reagent_containers/food/drinks/bottle/absinthe, 10),
- new /datum/data/mining_equipment("Cigar", /obj/item/clothing/mask/smokable/cigarette/cigar/havana, 15),
- new /datum/data/mining_equipment("Soap", /obj/item/soap/nanotrasen, 20),
- new /datum/data/mining_equipment("Umbrella", /obj/item/melee/umbrella/random, 20),
- new /datum/data/mining_equipment("30 Marker Beacons", /obj/item/stack/marker_beacon/thirty, 30),
- new /datum/data/mining_equipment("Plush Toy", /obj/random/plushie, 30),
- new /datum/data/mining_equipment("Survey Tools - Shovel", /obj/item/shovel, 40),
- new /datum/data/mining_equipment("Survey Tools - Mechanical Trap", /obj/item/beartrap, 50),
- new /datum/data/mining_equipment("Shelter Capsule", /obj/item/survivalcapsule, 50),
- new /datum/data/mining_equipment("Point Transfer Card", /obj/item/card/mining_point_card/survey, 50),
- new /datum/data/mining_equipment("Regular Firstaid Kit", /obj/item/storage/firstaid/regular, 50),
- // new /datum/data/mining_equipment("Advanced Firstaid Kit", /obj/item/storage/firstaid/adv, 50),
- // new /datum/data/mining_equipment("Bone Restoration Medicine", /obj/item/storage/firstaid/bonemed, 50),
- // new /datum/data/mining_equipment("Clotting Kit", /obj/item/storage/firstaid/clotting, 50),
- new /datum/data/mining_equipment("Survival Medipen", /obj/item/reagent_containers/hypospray/autoinjector/miner, 50),
- new /datum/data/mining_equipment("Injector (L) - Glucose", /obj/item/reagent_containers/hypospray/autoinjector/biginjector/glucose, 50),
- new /datum/data/mining_equipment("Injector (L) - Panacea", /obj/item/reagent_containers/hypospray/autoinjector/biginjector/purity, 50),
- new /datum/data/mining_equipment("Injector (L) - Trauma", /obj/item/reagent_containers/hypospray/autoinjector/biginjector/brute, 50),
- new /datum/data/mining_equipment("Digital Tablet - Standard", /obj/item/modular_computer/tablet/preset/custom_loadout/standard, 50),
- new /datum/data/mining_equipment("Geiger Counter", /obj/item/geiger_counter, 75),
- new /datum/data/mining_equipment("Defense Equipment - Steel Machete", /obj/item/material/knife/machete, 75),
- new /datum/data/mining_equipment("Defense Equipment - Kinetic Dagger", /obj/item/kinetic_crusher/dagger, 75),
- new /datum/data/mining_equipment("Laser Pointer", /obj/item/laser_pointer, 90),
- new /datum/data/mining_equipment("Digital Tablet - Advanced", /obj/item/modular_computer/tablet/preset/custom_loadout/advanced, 100),
- new /datum/data/mining_equipment("Nanopaste Tube", /obj/item/stack/nanopaste, 100),
- new /datum/data/mining_equipment("Binoculars", /obj/item/binoculars, 100),
- new /datum/data/mining_equipment("100 Thalers", /obj/item/spacecash/c100, 100),
- new /datum/data/mining_equipment("Defense Equipment - Razor Drone Deployer", /obj/item/grenade/spawnergrenade/manhacks/station/locked, 100),
- new /datum/data/mining_equipment("Mini-Translocator", /obj/item/perfect_tele/one_beacon, 120),
- new /datum/data/mining_equipment("Extraction Equipment - Fulton Pack", /obj/item/extraction_pack, 125),
- new /datum/data/mining_equipment("Defense Equipment - Sentry Drone Deployer", /obj/item/grenade/spawnergrenade/ward, 150),
- new /datum/data/mining_equipment("Holy Crusade Pack", /obj/item/storage/lockbox/crusade, 200),
- new /datum/data/mining_equipment("Maniple Pack", /obj/item/storage/lockbox/maniple, 200),
- new /datum/data/mining_equipment("Jump Boots", /obj/item/clothing/shoes/bhop, 250),
- new /datum/data/mining_equipment("Defense Equipment - AXHS Gun Case", /obj/item/storage/lockbox/axhs, 250),
- new /datum/data/mining_equipment("Conscript Pack", /obj/item/storage/lockbox/russian, 250),
- new /datum/data/mining_equipment("Extraction Equipment - Fulton Beacon", /obj/item/fulton_core, 300),
- new /datum/data/mining_equipment("Industrial Equipment - Phoron Bore", /obj/item/gun/projectile/magnetic/matfed, 300),
- new /datum/data/mining_equipment("Luxury Shelter Capsule", /obj/item/survivalcapsule/luxury, 310),
- new /datum/data/mining_equipment("Colonial Recce Pack", /obj/item/storage/lockbox/colonial, 350),
- //uav code is cursed new /datum/data/mining_equipment("UAV - Recon Skimmer", /obj/item/uav, 400),
- new /datum/data/mining_equipment("Away Team Pack", /obj/item/storage/lockbox/away, 550),
- new /datum/data/mining_equipment("Gateway Guardian Pack", /obj/item/storage/lockbox/gateway, 800),
- new /datum/data/mining_equipment("Cyan Posse Pack", /obj/item/storage/lockbox/cowboy, 800),
- new /datum/data/mining_equipment("Bar Shelter Capsule", /obj/item/survivalcapsule/luxurybar, 1000),
- new /datum/data/mining_equipment("1000 Thalers", /obj/item/spacecash/c1000, 1000),
- new /datum/data/mining_equipment("Defense Equipment - Marksman Box", /obj/item/gunbox/marksman, 1000),
- )
-/obj/machinery/mineral/equipment_vendor/survey/interact(mob/user)
- user.set_machine(src)
-
- var/dat
- dat +="
"
- if(istype(inserted_id))
- dat += "You have [inserted_id.survey_points] survey points collected. Eject ID. "
- else
- dat += "No ID inserted. Insert ID. "
- dat += "
"
- dat += " Equipment point cost list:
"
- for(var/datum/data/mining_equipment/prize in prize_list)
- dat += "