diff --git a/code/__DEFINES/is_helpers.dm b/code/__DEFINES/is_helpers.dm
index c4399a668aadc..fcd6a3db70926 100644
--- a/code/__DEFINES/is_helpers.dm
+++ b/code/__DEFINES/is_helpers.dm
@@ -265,7 +265,7 @@ GLOBAL_LIST_INIT(turfs_pass_meteor, typecacheof(list(
#define ispickedupmob(A) (istype(A, /obj/item/clothing/head/mob_holder)) // Checks if clothing item is actually a held mob
-#define iscash(A) (istype(A, /obj/item/coin) || istype(A, /obj/item/stack/spacecash) || istype(A, /obj/item/holochip))
+#define iscash(A) (istype(A, /obj/item/coin) || istype(A, /obj/item/stack/spacecash) || istype(A, /obj/item/holochip) || istype(A, /obj/item/libre))
#define isbodypart(A) (istype(A, /obj/item/bodypart))
diff --git a/code/game/machinery/bank_machine.dm b/code/game/machinery/bank_machine.dm
index 72de51d034fe8..6d2b7518dcc90 100644
--- a/code/game/machinery/bank_machine.dm
+++ b/code/game/machinery/bank_machine.dm
@@ -51,6 +51,9 @@
else if(istype(weapon, /obj/item/holochip))
var/obj/item/holochip/inserted_holochip = weapon
value = inserted_holochip.credits
+ else if(istype(weapon, /obj/item/libre/bundle)) // DOPPLER EDIT: you can turn holochips into normal money, if you somehow get a hold of that sort of thing after I'm through
+ var/obj/item/libre/bundle/inserted_libre = weapon
+ value = inserted_libre.value
if(value)
if(synced_bank_account)
synced_bank_account.adjust_money(value)
@@ -125,8 +128,8 @@
/obj/machinery/computer/bank_machine/proc/end_siphon()
siphoning = FALSE
unauthorized = FALSE
- if(syphoning_credits > 0)
- new /obj/item/holochip(drop_location(), syphoning_credits) //get the loot
+ if(syphoning_credits > 0) // DOPPLER EDIT: from holocredits to normalcash
+ new /obj/item/libre/bundle(drop_location(), syphoning_credits) //get the loot
syphoning_credits = 0
/obj/machinery/computer/bank_machine/proc/start_siphon(mob/living/carbon/user)
diff --git a/code/game/machinery/slotmachine.dm b/code/game/machinery/slotmachine.dm
index d3266df16f880..db0e36814c3f1 100644
--- a/code/game/machinery/slotmachine.dm
+++ b/code/game/machinery/slotmachine.dm
@@ -11,7 +11,7 @@
#define SPIN_TIME 65 //As always, deciseconds.
#define REEL_DEACTIVATE_DELAY 7
#define JACKPOT_SEVENS FA_ICON_7
-#define HOLOCHIP 1
+#define CASH 1 // DOPPLER EDIT: previously HOLOCHIP. replaced with cash in the great fuckup; far from modular.
#define COIN 2
/obj/machinery/computer/slot_machine
@@ -30,7 +30,7 @@
var/working = FALSE
var/balance = 0 //How much money is in the machine, ready to be CONSUMED.
var/jackpots = 0
- var/paymode = HOLOCHIP //toggles between HOLOCHIP/COIN, defined above
+ var/paymode = CASH // DOPPLER EDIT: toggles between CASH/COIN, defined above
var/cointype = /obj/item/coin/iron //default cointype
/// Icons that can be displayed by the slot machine.
var/static/list/icons = list(
@@ -114,17 +114,17 @@
qdel(inserted_coin)
return ITEM_INTERACT_SUCCESS
else
- balloon_alert(user, "holochips only!")
+ balloon_alert(user, "cash only!") // DOPPLER EDIT
return ITEM_INTERACT_BLOCKING
- if(istype(inserted, /obj/item/holochip))
- if(paymode == HOLOCHIP)
- var/obj/item/holochip/inserted_chip = inserted
- if(!user.temporarilyRemoveItemFromInventory(inserted_chip))
+ if(istype(inserted, /obj/item/libre/bundle))
+ if(paymode == CASH)
+ var/obj/item/libre/bundle/inserted_cash = inserted
+ if(!user.temporarilyRemoveItemFromInventory(inserted_cash))
return ITEM_INTERACT_BLOCKING
- balloon_alert(user, "[inserted_chip.credits] credit[inserted_chip.credits == 1 ? "" : "s"] inserted")
- balance += inserted_chip.credits
- qdel(inserted_chip)
+ balloon_alert(user, "[inserted_cash.value] credit[inserted_cash.value == 1 ? "" : "s"] inserted")
+ balance += inserted_cash.value
+ qdel(inserted_cash) // DOPPLER EDIT ENDS HERE (for a moment)
return ITEM_INTERACT_SUCCESS
else
balloon_alert(user, "coins only!")
@@ -137,12 +137,12 @@
visible_message("[src] says, 'ERROR! Please empty the machine balance before altering paymode'") //Prevents converting coins into holocredits and vice versa
return ITEM_INTERACT_BLOCKING
- if(paymode == HOLOCHIP)
+ if(paymode == CASH) // DOPPLER EDIT: yeah, I thought this was weird too
paymode = COIN
- balloon_alert(user, "now using coins")
+ balloon_alert(user, "now using material coins")
else
- paymode = HOLOCHIP
- balloon_alert(user, "now using holochips")
+ paymode = CASH
+ balloon_alert(user, "now using Libres") // END DOPPLER EDIT (for now)
return ITEM_INTERACT_SUCCESS
/obj/machinery/computer/slot_machine/emag_act(mob/user, obj/item/card/emag/emag_card)
@@ -306,12 +306,12 @@
else if(check_jackpot(JACKPOT_SEVENS))
var/prize = money + JACKPOT
- visible_message("[src] says, 'JACKPOT! You win [prize] credits!'")
+ visible_message("[src] says, 'JACKPOT! You win [prize] Libres!'")
priority_announce("Congratulations to [user ? user.real_name : usrname] for winning the jackpot at the slot machine in [get_area(src)]!")
jackpots += 1
money = 0
- if(paymode == HOLOCHIP)
- new /obj/item/holochip(loc, prize)
+ if(paymode == CASH) // DOPPLER EDIT
+ new /obj/item/libre/bundle(loc, prize)
else
for(var/i in 1 to 5)
cointype = pick(subtypesof(/obj/item/coin))
@@ -321,11 +321,11 @@
sleep(REEL_DEACTIVATE_DELAY)
else if(linelength == 5)
- visible_message("[src] says, 'Big Winner! You win a thousand credits!'")
+ visible_message("[src] says, 'Big Winner! You win a thousand Libres!'")
give_money(BIG_PRIZE)
else if(linelength == 4)
- visible_message("[src] says, 'Winner! You win four hundred credits!'")
+ visible_message("[src] says, 'Winner! You win four hundred Libres!'")
give_money(SMALL_PRIZE)
else if(linelength == 3)
@@ -375,10 +375,10 @@
money -= amount_to_give
balance += surplus
-/// Pay out the specified amount in either coins or holochips
+/// Pay out the specified amount in either coins or (DOPPLER EDIT) cash!
/obj/machinery/computer/slot_machine/proc/give_payout(amount)
- if(paymode == HOLOCHIP)
- cointype = /obj/item/holochip
+ if(paymode == CASH)
+ cointype = /obj/item/libre/bundle
else
cointype = obj_flags & EMAGGED ? /obj/item/coin/iron : /obj/item/coin/silver
@@ -395,11 +395,11 @@
/// Dispense the given amount. If machine is set to use coins, will use the specified coin type.
/// If throwit and target are set, will launch the payment at the target
/obj/machinery/computer/slot_machine/proc/dispense(amount = 0, cointype = /obj/item/coin/silver, throwit = FALSE, mob/living/target)
- if(paymode == HOLOCHIP)
- var/obj/item/holochip/chip = new /obj/item/holochip(loc,amount)
+ if(paymode == CASH)
+ var/obj/item/libre/bundle/payload = new /obj/item/libre/bundle(loc,amount)
if(throwit && target)
- chip.throw_at(target, 3, 10)
+ payload.throw_at(target, 3, 10)
else
var/value = coinvalues["[cointype]"]
if(value <= 0)
@@ -417,7 +417,7 @@
#undef BIG_PRIZE
#undef COIN
-#undef HOLOCHIP
+#undef CASH // DOPPLER EDIT: previously HOLOCHIP
#undef JACKPOT
#undef REEL_DEACTIVATE_DELAY
#undef JACKPOT_SEVENS
diff --git a/code/game/objects/items/cards_ids.dm b/code/game/objects/items/cards_ids.dm
index 2d1a16986fbe8..82f06191aa2a1 100644
--- a/code/game/objects/items/cards_ids.dm
+++ b/code/game/objects/items/cards_ids.dm
@@ -580,23 +580,26 @@
if(ispath(trim))
SSid_access.apply_trim_to_card(src, trim)
-/obj/item/card/id/item_interaction(mob/living/user, obj/item/tool, list/modifiers)
- if(istype(tool, /obj/item/rupee))
- to_chat(user, span_warning("Your ID smartly rejects the strange shard of glass. Who knew, apparently it's not ACTUALLY valuable!"))
+/obj/item/card/id/item_interaction(mob/living/user, obj/item/tool, list/modifiers) // DOPPLER EDIT - REMOVING INSERT_MONEY AND HOLOCHIPS. I also had to remove the rupee interaction, but that doesn't seem a great loss.
+// if(istype(tool, /obj/item/rupee))
+// to_chat(user, span_warning("Your ID smartly rejects the strange shard of glass. Who knew, apparently it's not ACTUALLY valuable!"))
+// return ITEM_INTERACT_BLOCKING
+ if(iscash(tool))
+ to_chat(user, span_notice("You'll need to visit an ATM to get your money into your account."))
return ITEM_INTERACT_BLOCKING
- else if(iscash(tool))
- return insert_money(tool, user) ? ITEM_INTERACT_SUCCESS : ITEM_INTERACT_BLOCKING
- else if(istype(tool, /obj/item/storage/bag/money))
+// return insert_money(tool, user) ? ITEM_INTERACT_SUCCESS : ITEM_INTERACT_BLOCKING
+
+/** else if(istype(tool, /obj/item/storage/bag/money))
var/obj/item/storage/bag/money/money_bag = tool
var/list/money_contained = money_bag.contents
var/money_added = mass_insert_money(money_contained, user)
if(!money_added)
return ITEM_INTERACT_BLOCKING
to_chat(user, span_notice("You stuff the contents into the card! They disappear in a puff of bluespace smoke, adding [money_added] worth of credits to the linked account."))
- return ITEM_INTERACT_SUCCESS
+ return ITEM_INTERACT_SUCCESS [END DOPPLER EDIT SEGMENT] **/
return NONE
-/**
+/** DOPPLER EDIT - REMOVING INSERT_MONEY AND HOLOCHIPS
* Insert credits or coins into the ID card and add their value to the associated bank account.
*
* Returns TRUE if the money was successfully inserted, FALSE otherwise.
@@ -604,7 +607,7 @@
* money - The item to attempt to convert to credits and insert into the card.
* user - The user inserting the item.
* physical_currency - Boolean, whether this is a physical currency such as a coin and not a holochip.
- */
+
/obj/item/card/id/proc/insert_money(obj/item/money, mob/user)
var/physical_currency
if(istype(money, /obj/item/stack/spacecash) || istype(money, /obj/item/coin))
@@ -636,7 +639,7 @@
* money - List of items to attempt to convert to credits and insert into the card.
* user - The user inserting the items.
*/
-/obj/item/card/id/proc/mass_insert_money(list/money, mob/user)
+ /obj/item/card/id/proc/mass_insert_money(list/money, mob/user)
if(!registered_account)
to_chat(user, span_warning("[src] doesn't have a linked account to deposit into!"))
return FALSE
@@ -655,7 +658,7 @@
log_econ("[total] credits were inserted into [src] owned by [src.registered_name]")
QDEL_LIST(money)
- return total
+ return total END DOPPLER EDIT SEGMENT **/
/// Helper proc. Can the user alt-click the ID?
/obj/item/card/id/proc/alt_click_can_use_id(mob/living/user)
@@ -695,7 +698,7 @@
if(!alt_click_can_use_id(user))
return NONE
if(registered_account.account_debt)
- var/choice = tgui_alert(user, "Choose An Action", "Bank Account", list("Withdraw", "Pay Debt"))
+ var/choice = tgui_alert(user, "Choose An Action", "Bank Account", list("Pay Debt"))
if(!choice || QDELETED(user) || QDELETED(src) || !alt_click_can_use_id(user) || loc != user)
return CLICK_ACTION_BLOCKING
if(choice == "Pay Debt")
@@ -714,7 +717,7 @@
if(choice == "Link Account")
set_new_account(user)
return CLICK_ACTION_SUCCESS
- var/amount_to_remove = tgui_input_number(user, "How much do you want to withdraw? (Max: [registered_account.account_balance] cr)", "Withdraw Funds", max_value = registered_account.account_balance)
+/** var/amount_to_remove = tgui_input_number(user, "How much do you want to withdraw? (Max: [registered_account.account_balance] cr)", "Withdraw Funds", max_value = registered_account.account_balance)
if(!amount_to_remove || QDELETED(user) || QDELETED(src) || issilicon(user) || loc != user)
return CLICK_ACTION_BLOCKING
if(!alt_click_can_use_id(user))
@@ -728,7 +731,8 @@
return CLICK_ACTION_SUCCESS
else
var/difference = amount_to_remove - registered_account.account_balance
- registered_account.bank_card_talk(span_warning("ERROR: The linked account requires [difference] more credit\s to perform that withdrawal."), TRUE)
+ registered_account.bank_card_talk(span_warning("ERROR: The linked account requires [difference] more credit\s to perform that withdrawal."), TRUE) **/
+ else
return CLICK_ACTION_BLOCKING
/obj/item/card/id/click_alt_secondary(mob/user)
@@ -763,7 +767,7 @@
. += span_notice("Alt-Right-Click the ID to set the linked bank account.")
if(HAS_TRAIT(user, TRAIT_ID_APPRAISER))
- . += HAS_TRAIT(src, TRAIT_JOB_FIRST_ID_CARD) ? span_boldnotice("Hmm... yes, this ID was issued from Central Command!") : span_boldnotice("This ID was created in this sector, not by Central Command.")
+ . += HAS_TRAIT(src, TRAIT_JOB_FIRST_ID_CARD) ? span_boldnotice("Hmm... yes, this ID was issued by the Port Authority!") : span_boldnotice("This ID was created in this sector, not by the Port Authority.") // DOPPLER EDIT - while I'm here...
if(HAS_TRAIT(src, TRAIT_TASTEFULLY_THICK_ID_CARD) && (user.is_holding(src) || (user.CanReach(src) && user.put_in_hands(src, ignore_animation = FALSE))))
ADD_TRAIT(src, TRAIT_NODROP, "psycho")
. += span_hypnophrase("Look at that subtle coloring... The tasteful thickness of it. Oh my God, it even has a watermark...")
@@ -864,8 +868,8 @@
return trim?.sechud_icon_state || SECHUD_UNKNOWN
/obj/item/card/id/interact_with_atom(atom/interacting_with, mob/living/user, list/modifiers)
- if(iscash(interacting_with))
- return insert_money(interacting_with, user) ? ITEM_INTERACT_SUCCESS : ITEM_INTERACT_BLOCKING
+ //if(iscash(interacting_with)) DOPPLER EDIT - REMOVING INSERT_MONEY AND HOLOCHIPS
+ // return insert_money(interacting_with, user) ? ITEM_INTERACT_SUCCESS : ITEM_INTERACT_BLOCKING
return NONE
/obj/item/card/id/away
diff --git a/code/modules/modular_computers/computers/item/computer.dm b/code/modules/modular_computers/computers/item/computer.dm
index 3f29e3006befa..2f2eab80f3962 100644
--- a/code/modules/modular_computers/computers/item/computer.dm
+++ b/code/modules/modular_computers/computers/item/computer.dm
@@ -822,8 +822,8 @@
if(isidcard(tool))
return InsertID(tool, user) ? ITEM_INTERACT_SUCCESS : ITEM_INTERACT_BLOCKING
- if(iscash(tool))
- return money_act(user, tool)
+ //if(iscash(tool)) DOPPLER EDIT - removing ID money insertion.
+ // return money_act(user, tool)
if(istype(tool, /obj/item/pai_card))
return pai_act(user, tool)
@@ -849,12 +849,12 @@
if(istype(tool, /obj/item/computer_disk))
return computer_disk_act(user, tool)
-/obj/item/modular_computer/proc/money_act(mob/user, obj/item/money)
+/** /obj/item/modular_computer/proc/money_act(mob/user, obj/item/money) DOPPLER EDIT - removing insert_money. Sneaky one, this.
var/obj/item/card/id/inserted_id = computer_id_slot?.GetID()
if(!inserted_id)
balloon_alert(user, "no ID!")
return ITEM_INTERACT_BLOCKING
- return inserted_id.insert_money(money, user) ? ITEM_INTERACT_SUCCESS : ITEM_INTERACT_BLOCKING
+ return inserted_id.insert_money(money, user) ? ITEM_INTERACT_SUCCESS : ITEM_INTERACT_BLOCKING **/
/obj/item/modular_computer/proc/pai_act(mob/user, obj/item/pai_card/card)
if(inserted_pai)
diff --git a/code/modules/modular_computers/computers/item/pda.dm b/code/modules/modular_computers/computers/item/pda.dm
index d21a3e2047559..04b13420956d6 100644
--- a/code/modules/modular_computers/computers/item/pda.dm
+++ b/code/modules/modular_computers/computers/item/pda.dm
@@ -142,8 +142,8 @@
return . || NONE
/obj/item/modular_computer/pda/interact_with_atom(atom/interacting_with, mob/living/user, list/modifiers)
- if(iscash(interacting_with))
- return money_act(user,interacting_with)
+// if(iscash(interacting_with))
+// return money_act(user,interacting_with)
return NONE
/obj/item/modular_computer/pda/item_interaction(mob/living/user, obj/item/tool, list/modifiers)
diff --git a/modular_doppler/dopple_cash/icons/atm.dmi b/modular_doppler/dopple_cash/icons/atm.dmi
new file mode 100644
index 0000000000000..933e04788f817
Binary files /dev/null and b/modular_doppler/dopple_cash/icons/atm.dmi differ
diff --git a/modular_doppler/dopple_cash/icons/money_libre.dmi b/modular_doppler/dopple_cash/icons/money_libre.dmi
new file mode 100644
index 0000000000000..c7c5c08240158
Binary files /dev/null and b/modular_doppler/dopple_cash/icons/money_libre.dmi differ
diff --git a/modular_doppler/dopple_cash/icons/money_orion.dmi b/modular_doppler/dopple_cash/icons/money_orion.dmi
new file mode 100644
index 0000000000000..698b664f9dc2a
Binary files /dev/null and b/modular_doppler/dopple_cash/icons/money_orion.dmi differ
diff --git a/modular_doppler/dopple_cash/icons/money_orions.dmi b/modular_doppler/dopple_cash/icons/money_orions.dmi
new file mode 100644
index 0000000000000..698b664f9dc2a
Binary files /dev/null and b/modular_doppler/dopple_cash/icons/money_orions.dmi differ
diff --git a/modular_doppler/dopple_cash/items/autobank.dm b/modular_doppler/dopple_cash/items/autobank.dm
new file mode 100644
index 0000000000000..104daac0baaa7
--- /dev/null
+++ b/modular_doppler/dopple_cash/items/autobank.dm
@@ -0,0 +1,160 @@
+// THE ATM
+// my oldest friend. my most ancient enemy.
+
+/obj/machinery/autobank
+ name = "banking terminal"
+ desc = "An automatic teller machine, or ATM, connected to the Port Authority Neglible-Loss Transaction Yard, or PANTRY. Capable of dispensing the two most commonly-utilized currencies on the local market; Ori and Libres."
+ icon = 'modular_doppler/dopple_cash/icons/atm.dmi'
+ icon_state = "atm"
+ anchored = TRUE
+ density = TRUE
+ idle_power_usage = BASE_MACHINE_IDLE_CONSUMPTION
+ // current user's bank card
+ var/obj/item/card/id/inserted_scan_id
+ // currently loaded bank account
+ var/datum/bank_account/synced_bank_account
+ // account balance
+ var/balance = 0
+ // amount of credits withdrawn
+ var/withdrawn_credits = 0
+
+/obj/machinery/autobank/Initialize(mapload)
+ . = ..()
+ synced_bank_account = null
+
+/obj/machinery/autobank/examine(mob/user)
+ . = ..()
+
+ . += span_engradio("You could examine closer for more information about banking services...")
+
+/obj/machinery/autobank/examine_more(mob/user)
+ . = ..()
+
+ . += span_notice("You could turn coins, vending machine holochips, and space cash into standardized credits.")
+
+/obj/machinery/autobank/attackby(obj/item/weapon, mob/user, params)
+ var/value = 0
+ if(isidcard(weapon))
+ if(id_insert(user, weapon, inserted_scan_id))
+ inserted_scan_id = weapon
+ return TRUE
+ else if(istype(weapon, /obj/item/libre))
+ var/obj/item/libre/inserted_cash = weapon
+ value = inserted_cash.value
+ else if(istype(weapon, /obj/item/holochip))
+ var/obj/item/holochip/inserted_holochip = weapon
+ value = inserted_holochip.credits
+ else if(istype(weapon, /obj/item/stack/spacecash))
+ var/obj/item/stack/spacecash/inserted_cash = weapon
+ value = inserted_cash.value * inserted_cash.amount
+ else if(istype(weapon, /obj/item/coin))
+ var/obj/item/coin/inserted_coin = weapon
+ value = inserted_coin.value
+ if(value)
+ if(synced_bank_account)
+ synced_bank_account.adjust_money(value)
+ say("Credits deposited! Your account now holds [synced_bank_account.account_balance] credits.")
+ playsound(src, 'sound/effects/cashregister.ogg', 50, TRUE)
+ qdel(weapon)
+ else
+ say("No account loaded! Please present an identification string.")
+ playsound(src, 'sound/machines/uplink/uplinkerror.ogg', 50, TRUE)
+ return
+ return ..()
+
+/obj/machinery/autobank/ui_data(mob/user)
+ . = list()
+
+ synced_bank_account = inserted_scan_id?.registered_account
+ balance = inserted_scan_id?.registered_account?.account_balance
+
+ var/list/data = list()
+ data["current_balance"] = synced_bank_account?.account_balance
+ data["withdrawal_amount"] = 0
+
+
+ return data
+
+/obj/machinery/autobank/ui_interact(mob/user, datum/tgui/ui)
+ ui = SStgui.try_update_ui(user, src, ui)
+ if(!anchored)
+ return
+ if(!ui)
+ ui = new(user, src, "AutoBank", name)
+ ui.open()
+
+/obj/machinery/autobank/ui_act(action, params, datum/tgui/ui, datum/ui_state/state)
+ . = ..()
+ if(.)
+ return
+
+ // we have no card to take money from
+ if(isnull(synced_bank_account))
+ say("No usable account number on file. If you believe this to be in error, please contact 7-001-0451 at extension '9' for customer service!")
+ return
+
+ switch(action)
+ if("withdraw")
+ var/dosh_taken = text2num(params["totalcreds"])
+ if(dosh_taken <= balance)
+ synced_bank_account.adjust_money(-dosh_taken)
+ say("Withdrawal complete! Have a great day!")
+ spawn_libre(dosh_taken, drop_location())
+ playsound(src, 'sound/effects/cashregister.ogg', 50, TRUE)
+ else
+ say("Unable to complete transaction.")
+ playsound(src, 'sound/machines/uplink/uplinkerror.ogg', 50, TRUE)
+ . = TRUE
+
+/obj/machinery/autobank/proc/id_insert(mob/user, obj/item/inserting_item, obj/item/target) //stolen from the bounty pad
+ var/obj/item/card/id/card_to_insert = inserting_item
+ var/holder_item = FALSE
+
+ if(!isidcard(card_to_insert))
+ card_to_insert = inserting_item.RemoveID()
+ holder_item = TRUE
+
+ if(!card_to_insert || !user.transferItemToLoc(card_to_insert, src))
+ return FALSE
+
+ if(target)
+ if(holder_item && inserting_item.InsertID(target))
+ playsound(src, 'sound/machines/terminal/terminal_insert_disc.ogg', 50, FALSE)
+ else
+ id_eject(user, target)
+
+ user.visible_message(span_notice("[user] inserts \the [card_to_insert] into \the [src]."),
+ span_notice("You insert \the [card_to_insert] into \the [src]."))
+ playsound(src, 'sound/machines/terminal/terminal_insert_disc.ogg', 50, FALSE)
+ ui_interact(user)
+ return TRUE
+
+/obj/machinery/autobank/click_alt(mob/user)
+ id_eject(user, inserted_scan_id)
+ return CLICK_ACTION_SUCCESS
+
+/obj/machinery/autobank/proc/id_eject(mob/user, obj/target)
+ if(!target)
+ to_chat(user, span_warning("That slot is empty!"))
+ return FALSE
+ else
+ target.forceMove(drop_location())
+ if(!issilicon(user) && Adjacent(user))
+ user.put_in_hands(target)
+ user.visible_message(span_notice("[user] gets \the [target] from \the [src]."), \
+ span_notice("You get \the [target] from \the [src]."))
+ playsound(src, 'sound/machines/terminal/terminal_insert_disc.ogg', 50, FALSE)
+ inserted_scan_id = null
+ return TRUE
+
+//colony fab version
+/obj/item/flatpacked_machine/atm
+ name = "banking terminal parts kit"
+ icon = 'modular_doppler/dopple_cash/icons/atm.dmi'
+ icon_state = "flatpacked_atm"
+ //type_to_deploy = /obj/machinery/autobank
+ deploy_time = 2 SECONDS
+ custom_materials = list(
+ /datum/material/iron = SHEET_MATERIAL_AMOUNT * 5,
+ /datum/material/glass = SHEET_MATERIAL_AMOUNT * 5,
+ )
diff --git a/modular_doppler/dopple_cash/items/dopplecash.dm b/modular_doppler/dopple_cash/items/dopplecash.dm
new file mode 100644
index 0000000000000..99be5374c336a
--- /dev/null
+++ b/modular_doppler/dopple_cash/items/dopplecash.dm
@@ -0,0 +1,253 @@
+// money... 2!
+// + kinetic. actionable. threatening.
+// + looks cool
+// - not so easily portable. i consider that a benefit
+
+// code from shiptest, who took it from eris, who came from bay...
+
+/obj/item/libre
+ name = "coin?"
+ desc = "But how will it effect the economy?"
+ icon = 'modular_doppler/dopple_cash/icons/money_libre.dmi'
+ icon_state = "libre0"
+ throwforce = 1
+ throw_speed = 2
+ throw_range = 2
+ w_class = WEIGHT_CLASS_TINY
+ resistance_flags = FLAMMABLE
+ var/value = 0
+ grind_results = list(/datum/reagent/iron = 10)
+
+/obj/item/libre/Initialize(mapload, amount)
+ . = ..()
+ if(amount)
+ value = amount
+ update_appearance()
+
+/obj/item/libre/proc/adjust_value(amount)
+ value += amount
+ update_appearance()
+
+/obj/item/libre/proc/transfer_value(amount, obj/item/libre/target)
+ amount = clamp(amount, 0, value)
+ value -= amount
+ target.value += amount
+ target.update_appearance()
+
+ if(value == 0)
+ qdel(src)
+ return
+
+ update_appearance()
+
+/obj/item/libre/attackby(obj/item/W, mob/user)
+ if(istype(W, /obj/item/libre))
+ var/obj/item/libre/bundle/bundle
+ if(istype(W, /obj/item/libre/bundle))
+ bundle = W
+ else
+ var/obj/item/libre/cash = W
+ bundle = new (loc)
+ bundle.value = cash.value
+ cash.value = 0
+ user.dropItemToGround(cash)
+ qdel(cash)
+
+ if(ishuman(user))
+ var/mob/living/carbon/human/H = user
+ H.dropItemToGround(src)
+ H.dropItemToGround(bundle)
+ H.put_in_hands(src)
+ H.put_in_hands(bundle)
+ to_chat(user, "You add [value] libre worth of money to the bundle.
It now holds [bundle.value + value] libre.")
+ bundle.transfer_value(bundle.value, src)
+
+/obj/item/libre/Destroy()
+ . = ..()
+ value = 0 // This does, in fact, help prevent money from being duped endlessly.
+
+/obj/item/libre/bundle
+ icon_state = "libre20"
+
+/obj/item/libre/bundle/update_appearance()
+ icon_state = "nothing"
+ cut_overlays()
+ var/remaining_value = value
+ var/iteration = 0
+ var/coins_only = TRUE
+ var/list/coin_denominations = list(10, 5, 1)
+ var/list/banknote_denominations = list(1000, 500, 200, 100, 50, 20)
+ for(var/i in banknote_denominations)
+ while(remaining_value >= i && iteration < 50)
+ remaining_value -= i
+ iteration++
+ var/image/banknote = image('modular_doppler/dopple_cash/icons/money_libre.dmi', "libre[i]")
+ var/matrix/M = matrix()
+ M.Translate(rand(-6, 6), rand(-4, 8))
+ banknote.transform = M
+ overlays += banknote
+ coins_only = FALSE
+
+ if(remaining_value)
+ for(var/i in coin_denominations)
+ while(remaining_value >= i && iteration < 50)
+ remaining_value -= i
+ iteration++
+ var/image/coin = image('modular_doppler/dopple_cash/icons/money_libre.dmi', "libre[i]")
+ var/matrix/M = matrix()
+ M.Translate(rand(-6, 6), rand(-4, 8))
+ coin.transform = M
+ overlays += coin
+
+ if(coins_only)
+ if(value == 1)
+ name = "one libre coin"
+ desc = "With this, we could build a new Heaven."
+ drop_sound = 'modular_doppler/dopple_cash/sounds/coin_drop.ogg'
+ pickup_sound = 'modular_doppler/dopple_cash/sounds/coin_pickup.ogg'
+ else
+ name = "[value] libre"
+ desc = "The weight of the world by the palmful."
+ drop_sound = 'modular_doppler/dopple_cash/sounds/coin_drop.ogg'
+ pickup_sound = 'modular_doppler/dopple_cash/sounds/coin_pickup.ogg'
+ else
+ name = "[value] libre"
+ desc = "We saw a perfect void, a star-filled sky, and said, 'let's build a shopping mall there, two hundred stories high, and set it on fire, and make it loud enough to wake God'. And so we did."
+ drop_sound = 'modular_doppler/dopple_cash/sounds/dosh_drop.ogg'
+ pickup_sound = 'modular_doppler/dopple_cash/sounds/dosh_pickup.ogg'
+ return ..()
+
+/obj/item/libre/bundle/attack_self()
+ var/cashamount = input(usr, "How many libre do you want to take? (0 to [value])", "Take Money", 20) as num
+ cashamount = round(clamp(cashamount, 0, value))
+ if(!cashamount)
+ return
+
+ else if(!Adjacent(usr))
+ to_chat(usr, "You need to be in arm's reach for that!")
+ return
+
+ var/obj/item/libre/bundle/bundle = new(usr.loc)
+ transfer_value(cashamount, bundle)
+ usr.put_in_hands(bundle)
+ update_appearance()
+
+/obj/item/libre/bundle/click_alt(mob/living/user)
+ var/cashamount = input(user, "How many libre do you want to take? (0 to [value])", "Take Money", 20) as num
+ cashamount = round(clamp(cashamount, 0, value))
+ if(!cashamount)
+ return
+
+ else if(!Adjacent(user))
+ to_chat(user, "You need to be in arm's reach for that!")
+ return
+
+ adjust_value(-cashamount)
+ if(!value)
+ user.dropItemToGround(src)
+ qdel(src)
+
+ var/obj/item/libre/bundle/bundle = new(user.loc, cashamount)
+ user.put_in_hands(bundle)
+
+/obj/item/libre/bundle/Initialize()
+ . = ..()
+ update_appearance()
+
+/obj/item/libre/bundle/c1/Initialize()
+ value = 1
+ . = ..()
+
+/obj/item/libre/bundle/tiny/Initialize() // THANKS, SHIPTEST!!
+ value = rand(10, 100)
+ . = ..()
+
+/obj/item/libre/bundle/small/Initialize()
+ value = rand(100, 500)
+ . = ..()
+
+/obj/item/libre/bundle/medium/Initialize()
+ value = rand(500, 3000)
+ . = ..()
+
+/obj/item/libre/bundle/large/Initialize()
+ value = rand(2500, 6000)
+ . = ..()
+
+/proc/spawn_libre(sum, spawnloc, mob/living/carbon/human/H) // not my brightest coding but that's what i have you guys for :) used for certain transactions
+ var/obj/item/libre/bundle/fundle = new (spawnloc)
+ fundle.value = sum
+ fundle.update_icon()
+ usr.put_in_hands(fundle)
+
+// ORIONS
+// Want to see something REALLY scary?
+
+/obj/item/orion
+ name = "zero orion stick"
+ desc = "A drive for carrying your Ori around. Fabricated by a 4CA Collective Currency and Logistical Local, or 'COLLECTCALL'."
+ icon = 'modular_doppler/dopple_cash/icons/money_orion.dmi'
+ icon_state = "orion0"
+ w_class = WEIGHT_CLASS_TINY
+ var/value = 0
+ var/stick_value = 0
+
+/obj/item/orion/examine(mob/user)
+ . = ..()
+ . += span_notice("There's [value] Orion on the stick.")
+
+/obj/item/orion/attackby(obj/item/attacking_item, mob/user, params)
+ if(!isidcard(attacking_item))
+ return ..()
+ if(value == stick_value)
+ to_chat(user, span_notice("This stick is full."))
+ return ..()
+ var/obj/item/card/id/attacking_id = attacking_item
+ balloon_alert(user, "starting transfer")
+ var/stickamount = input(user, "How much do you want to transfer? ID Balance: [attacking_id.registered_account.account_balance], Stick Maximum Balance: [stick_value]") as num
+ stickamount = round(clamp(stickamount, 0, stick_value))
+ if(!stickamount)
+ return
+ while(stickamount >= 1 && stickamount <= attacking_id.registered_account.account_balance)
+ if(stickamount <= stick_value)
+ attacking_id.registered_account.account_balance -= stickamount
+ value += stickamount
+ to_chat(user, span_notice("You transfer [stickamount] Orion from [attacking_id] to [src], finalizing the stick."))
+ else
+ to_chat(user, span_notice("YOU FUCKED UP JUNIE!!!"))
+ return
+
+/obj/item/orion/c5
+ name = "5 ori stick"
+ icon_state = "orion5"
+ stick_value = 5
+
+/obj/item/orion/c10
+ name = "10 ori stick"
+ icon_state = "orion10"
+ stick_value = 10
+
+/obj/item/orion/c20
+ name = "20 ori stick"
+ icon_state = "orion20"
+ stick_value = 20
+
+/obj/item/orion/c50
+ name = "50 ori stick"
+ icon_state = "orion50"
+ stick_value = 50
+
+/obj/item/orion/c100
+ name = "100 ori stick"
+ icon_state = "orion100"
+ stick_value = 100
+
+/obj/item/orion/c500
+ name = "500 ori stick"
+ icon_state = "orion500"
+ stick_value = 500
+
+/obj/item/orion/c1000
+ name = "1000 ori stick"
+ icon_state = "orion1000"
+ stick_value = 1000
diff --git a/modular_doppler/dopple_cash/sounds/coin_drop.ogg b/modular_doppler/dopple_cash/sounds/coin_drop.ogg
new file mode 100644
index 0000000000000..7d63143b83f78
Binary files /dev/null and b/modular_doppler/dopple_cash/sounds/coin_drop.ogg differ
diff --git a/modular_doppler/dopple_cash/sounds/coin_pickup.ogg b/modular_doppler/dopple_cash/sounds/coin_pickup.ogg
new file mode 100644
index 0000000000000..6dffa6073da6b
Binary files /dev/null and b/modular_doppler/dopple_cash/sounds/coin_pickup.ogg differ
diff --git a/modular_doppler/dopple_cash/sounds/dosh_drop.ogg b/modular_doppler/dopple_cash/sounds/dosh_drop.ogg
new file mode 100644
index 0000000000000..cf7f12b67cf50
Binary files /dev/null and b/modular_doppler/dopple_cash/sounds/dosh_drop.ogg differ
diff --git a/modular_doppler/dopple_cash/sounds/dosh_pickup.ogg b/modular_doppler/dopple_cash/sounds/dosh_pickup.ogg
new file mode 100644
index 0000000000000..af4a061bad4c8
Binary files /dev/null and b/modular_doppler/dopple_cash/sounds/dosh_pickup.ogg differ
diff --git a/tgstation.dme b/tgstation.dme
index 608523d1c467d..b2d94fead338f 100644
--- a/tgstation.dme
+++ b/tgstation.dme
@@ -6546,6 +6546,8 @@
#include "modular_doppler\deforest_medical_items\code\medstation_designs\blood.dm"
#include "modular_doppler\deforest_medical_items\code\medstation_designs\medical.dm"
#include "modular_doppler\disable_suicide\config_entries.dm"
+#include "modular_doppler\dopple_cash\items\autobank.dm"
+#include "modular_doppler\dopple_cash\items\dopplecash.dm"
#include "modular_doppler\dopplerboop\dopplerboops.dm"
#include "modular_doppler\dopplerboop\human.dm"
#include "modular_doppler\emotes\code\emotes.dm"
diff --git a/tgui/packages/tgui/interfaces/AutoBank.tsx b/tgui/packages/tgui/interfaces/AutoBank.tsx
new file mode 100644
index 0000000000000..ad53b3df98c2d
--- /dev/null
+++ b/tgui/packages/tgui/interfaces/AutoBank.tsx
@@ -0,0 +1,55 @@
+import { useBackend } from '../backend';
+import {
+ AnimatedNumber,
+ LabeledList,
+ NoticeBox,
+ NumberInput,
+ Section,
+} from '../components';
+import { formatMoney } from '../format';
+import { Window } from '../layouts';
+
+type Data = {
+ current_balance: number;
+ withdrawal_amount: number;
+ totalcreds: number;
+};
+
+export const AutoBank = (props) => {
+ const { act, data } = useBackend();
+ const { current_balance, withdrawal_amount } = data;
+
+ return (
+
+
+ 997473629173892347294324723. . .
+
+
+
+ act('withdraw', {
+ totalcreds: value,
+ })
+ }
+ />
+ }
+ >
+ formatMoney(value)}
+ />
+ {' cr'}
+
+
+
+
+
+ );
+};