mirror of
https://github.com/Bubberstation/Bubberstation.git
synced 2026-07-14 17:45:02 +01:00
[MANUAL MIRROR] Refactors Admin Setups on Forced Events + Refactors Vending Sentience (#19068)
* Refactors Admin Setups on Forced Events + Refactors Vending Sentience + Refactors Shuttle Loans (#72998) - [x] TEST EVERYTHING tested: - Pirates - Vending Machines - Shuttle Catastrophe - Anomalies - Immovable Rod - Sandstorms - Scrubber Overflow - Stray Meteor - Madness - Department Revolt (Well obviously, it is my super robust code after all) - Shuttle Loan - Mass Hallucination - Heart Attack - False Alarm Disease Outbreak is probably fine aha... It correctly reports that there are no candidates before aborting. allow you to let the game decide where previously you had to choose! I need to refactor and datumize how admins set up special conditions on forced events, so I did! Now `/datum/event_admin_setup` handles admin settings, with a few prototypes to make it easier to give events admin options in the future. This was exhausting and what 90% of the pr is. The code was so bad I could not datumize the admin part of it so I cleaned it up, making a lot of things in the event get decided in `setup()` where they should. The code was so bad I could not datumize the admin part of it so I cleaned it up AS WELL, by datumizing the shuttle loans. Should be easier to add more types in the future, actually kinda stoked. This is preparation for a tgui change to ForceEvent.ts an admin has requested. Phew! 🆑 refactor: Refactored a bunch of admin-related event code, hopefully you won't notice much admin: ... But you specifically may notice some minor differences. Raw inputs changed into tgui ones, minor soul removal, etc. /🆑 * remove override * merge conflict * dm update * merge conflict --------- Co-authored-by: tralezab <40974010+tralezab@users.noreply.github.com>
This commit is contained in:
@@ -88,7 +88,7 @@
|
||||
var/datum/round_event_control/event = locate(event_to_run_type) in SSevents.control
|
||||
if(!event)
|
||||
return
|
||||
if(event.admin_setup(usr) == ADMIN_CANCEL_EVENT)
|
||||
if(event.admin_setup && event.admin_setup.prompt_admins() == ADMIN_CANCEL_EVENT)
|
||||
return
|
||||
var/always_announce_chance = 100
|
||||
var/no_announce_chance = 0
|
||||
|
||||
@@ -83,31 +83,6 @@
|
||||
else message_admins("[key_name_admin(usr)] FAILED to create '[href_list["makeAntag"]]' with a parameter of '[opt]'.")
|
||||
// SKYRAT EDIT END -- ONE CLICK ANTAG
|
||||
|
||||
else if(href_list["forceevent"])
|
||||
if(!check_rights(R_FUN))
|
||||
return
|
||||
var/datum/round_event_control/E = locate(href_list["forceevent"]) in SSevents.control
|
||||
if(E)
|
||||
E.admin_setup(usr)
|
||||
var/datum/round_event/event = E.runEvent()
|
||||
if(event.cancel_event)
|
||||
return
|
||||
if(event.announce_when>0)
|
||||
event.processing = FALSE
|
||||
var/prompt = tgui_alert(usr, "Would you like to alert the crew?", "Alert", list("Yes", "No", "Cancel"))
|
||||
switch(prompt)
|
||||
if("Yes")
|
||||
event.announce_chance = 100
|
||||
if("Cancel")
|
||||
event.kill()
|
||||
return
|
||||
if("No")
|
||||
event.announce_chance = 0
|
||||
event.processing = TRUE
|
||||
message_admins("[key_name_admin(usr)] has triggered an event. ([E.name])")
|
||||
log_admin("[key_name(usr)] has triggered an event. ([E.name])")
|
||||
return
|
||||
|
||||
else if(href_list["editrightsbrowser"])
|
||||
edit_admin_permissions(0)
|
||||
|
||||
|
||||
@@ -7,30 +7,19 @@
|
||||
dynamic_should_hijack = TRUE
|
||||
category = EVENT_CATEGORY_INVASION
|
||||
description = "The crew will either pay up, or face a pirate assault."
|
||||
///admin chosen pirate team
|
||||
var/datum/pirate_gang/chosen_gang
|
||||
|
||||
/datum/round_event_control/pirates/admin_setup(mob/admin)
|
||||
var/list/gang_choices = list("Random")
|
||||
|
||||
for(var/datum/pirate_gang/possible_gang as anything in GLOB.pirate_gangs)
|
||||
gang_choices[possible_gang.name] = possible_gang
|
||||
|
||||
var/chosen = tgui_input_list(usr, "Select pirate gang", "TICKETS TO THE SPONGEBOB MOVIE!!", gang_choices)
|
||||
if(!chosen)
|
||||
return ADMIN_CANCEL_EVENT
|
||||
if(chosen == "Random")
|
||||
return //still do the event, but chosen_gang is still null, so it will pick from the choices
|
||||
chosen_gang = gang_choices[chosen]
|
||||
admin_setup = /datum/event_admin_setup/pirates
|
||||
|
||||
/datum/round_event_control/pirates/preRunEvent()
|
||||
if (!SSmapping.empty_space)
|
||||
return EVENT_CANT_RUN
|
||||
return ..()
|
||||
|
||||
/datum/round_event/pirates
|
||||
///admin chosen pirate team
|
||||
var/datum/pirate_gang/chosen_gang
|
||||
|
||||
/datum/round_event/pirates/start()
|
||||
var/datum/round_event_control/pirates/pirate_control = control
|
||||
send_pirate_threat(pirate_control.chosen_gang)
|
||||
send_pirate_threat(chosen_gang)
|
||||
|
||||
/proc/send_pirate_threat(datum/pirate_gang/chosen_gang)
|
||||
if(!chosen_gang)
|
||||
@@ -91,43 +80,25 @@
|
||||
|
||||
priority_announce("Unidentified armed ship detected near the station.")
|
||||
|
||||
//Shuttle equipment
|
||||
/datum/event_admin_setup/pirates
|
||||
///admin chosen pirate team
|
||||
var/datum/pirate_gang/chosen_gang
|
||||
|
||||
/obj/machinery/shuttle_scrambler
|
||||
name = "Data Siphon"
|
||||
desc = "This heap of machinery steals credits and data from unprotected systems and locks down cargo shuttles."
|
||||
icon = 'icons/obj/machines/dominator.dmi'
|
||||
icon_state = "dominator"
|
||||
density = TRUE
|
||||
var/active = FALSE
|
||||
var/credits_stored = 0
|
||||
var/siphon_per_tick = 5
|
||||
/datum/event_admin_setup/pirates/prompt_admins()
|
||||
|
||||
/obj/machinery/shuttle_scrambler/Initialize(mapload)
|
||||
. = ..()
|
||||
update_appearance()
|
||||
var/list/gang_choices = list("Random")
|
||||
|
||||
/obj/machinery/shuttle_scrambler/process()
|
||||
if(active)
|
||||
if(is_station_level(z))
|
||||
var/datum/bank_account/D = SSeconomy.get_dep_account(ACCOUNT_CAR)
|
||||
if(D)
|
||||
var/siphoned = min(D.account_balance,siphon_per_tick)
|
||||
D.adjust_money(-siphoned)
|
||||
credits_stored += siphoned
|
||||
interrupt_research()
|
||||
else
|
||||
return
|
||||
else
|
||||
STOP_PROCESSING(SSobj,src)
|
||||
for(var/datum/pirate_gang/possible_gang as anything in GLOB.pirate_gangs)
|
||||
gang_choices[possible_gang.name] = possible_gang
|
||||
|
||||
/obj/machinery/shuttle_scrambler/proc/toggle_on(mob/user)
|
||||
SSshuttle.registerTradeBlockade(src)
|
||||
AddComponent(/datum/component/gps, "Nautical Signal")
|
||||
active = TRUE
|
||||
to_chat(user,span_notice("You toggle [src] [active ? "on":"off"]."))
|
||||
to_chat(user,span_warning("The scrambling signal can be now tracked by GPS."))
|
||||
START_PROCESSING(SSobj,src)
|
||||
var/chosen = tgui_input_list(usr, "Select pirate gang", "TICKETS TO THE SPONGEBOB MOVIE!!", gang_choices)
|
||||
if(!chosen)
|
||||
return ADMIN_CANCEL_EVENT
|
||||
if(chosen == "Random")
|
||||
return //still do the event, but chosen_gang is still null, so it will pick from the choices
|
||||
chosen_gang = gang_choices[chosen]
|
||||
|
||||
/datum/event_admin_setup/pirates/apply_to_event(datum/round_event/pirates/event)
|
||||
|
||||
/obj/machinery/shuttle_scrambler/interact(mob/user)
|
||||
if(active)
|
||||
@@ -142,30 +113,6 @@
|
||||
update_appearance()
|
||||
send_notification()
|
||||
|
||||
//interrupt_research
|
||||
/obj/machinery/shuttle_scrambler/proc/interrupt_research()
|
||||
for(var/obj/machinery/rnd/server/S as anything in SSresearch.science_tech.techweb_servers)
|
||||
if(S.machine_stat & (NOPOWER|BROKEN))
|
||||
continue
|
||||
S.emp_act()
|
||||
new /obj/effect/temp_visual/emp(get_turf(S))
|
||||
|
||||
/obj/machinery/shuttle_scrambler/proc/dump_loot(mob/user)
|
||||
if(credits_stored) // Prevents spamming empty holochips
|
||||
new /obj/item/holochip(drop_location(), credits_stored)
|
||||
to_chat(user,span_notice("You retrieve the siphoned credits!"))
|
||||
credits_stored = 0
|
||||
else
|
||||
to_chat(user,span_notice("There's nothing to withdraw."))
|
||||
|
||||
/obj/machinery/shuttle_scrambler/proc/send_notification()
|
||||
priority_announce("Data theft signal detected, source registered on local gps units.")
|
||||
|
||||
/obj/machinery/shuttle_scrambler/proc/toggle_off(mob/user)
|
||||
SSshuttle.clearTradeBlockade(src)
|
||||
active = FALSE
|
||||
STOP_PROCESSING(SSobj,src)
|
||||
|
||||
/obj/machinery/shuttle_scrambler/update_icon_state()
|
||||
icon_state = active ? "dominator-Blue" : "dominator"
|
||||
return ..()
|
||||
@@ -211,15 +158,6 @@
|
||||
mask_type = /obj/item/clothing/mask/breath
|
||||
storage_type = /obj/item/tank/internals/oxygen
|
||||
|
||||
/obj/machinery/loot_locator
|
||||
name = "Booty Locator"
|
||||
desc = "This sophisticated machine scans the nearby space for items of value."
|
||||
icon = 'icons/obj/machines/research.dmi'
|
||||
icon_state = "tdoppler"
|
||||
density = TRUE
|
||||
var/cooldown = 300
|
||||
var/next_use = 0
|
||||
|
||||
/obj/machinery/loot_locator/interact(mob/user)
|
||||
if(world.time <= next_use)
|
||||
to_chat(user,span_warning("[src] is recharging."))
|
||||
@@ -231,33 +169,6 @@
|
||||
else
|
||||
say("Located: [AM.name] at [get_area_name(AM)]")
|
||||
|
||||
/obj/machinery/loot_locator/proc/find_random_loot()
|
||||
if(!GLOB.exports_list.len)
|
||||
setupExports()
|
||||
var/list/possible_loot = list()
|
||||
for(var/datum/export/pirate/E in GLOB.exports_list)
|
||||
possible_loot += E
|
||||
var/datum/export/pirate/P
|
||||
var/atom/movable/AM
|
||||
while(!AM && possible_loot.len)
|
||||
P = pick_n_take(possible_loot)
|
||||
AM = P.find_loot()
|
||||
return AM
|
||||
|
||||
//Pad & Pad Terminal
|
||||
/obj/machinery/piratepad
|
||||
name = "cargo hold pad"
|
||||
icon = 'icons/obj/telescience.dmi'
|
||||
icon_state = "lpad-idle-off"
|
||||
///This is the icon_state that this telepad uses when it's not in use.
|
||||
var/idle_state = "lpad-idle-off"
|
||||
///This is the icon_state that this telepad uses when it's warming up for goods teleportation.
|
||||
var/warmup_state = "lpad-idle"
|
||||
///This is the icon_state to flick when the goods are being sent off by the telepad.
|
||||
var/sending_state = "lpad-beam"
|
||||
///This is the cargo hold ID used by the piratepad_control. Match these two to link them together.
|
||||
var/cargo_hold_id
|
||||
|
||||
/obj/machinery/piratepad/multitool_act(mob/living/user, obj/item/multitool/I)
|
||||
. = ..()
|
||||
if (istype(I))
|
||||
@@ -275,27 +186,6 @@
|
||||
default_deconstruction_crowbar(tool)
|
||||
return TRUE
|
||||
|
||||
/obj/machinery/computer/piratepad_control
|
||||
name = "cargo hold control terminal"
|
||||
///Message to display on the TGUI window.
|
||||
var/status_report = "Ready for delivery."
|
||||
///Reference to the specific pad that the control computer is linked up to.
|
||||
var/datum/weakref/pad_ref
|
||||
///How long does it take to warmup the pad to teleport?
|
||||
var/warmup_time = 100
|
||||
///Is the teleport pad/computer sending something right now? TRUE/FALSE
|
||||
var/sending = FALSE
|
||||
///For the purposes of space pirates, how many points does the control pad have collected.
|
||||
var/points = 0
|
||||
///Reference to the export report totaling all sent objects and mobs.
|
||||
var/datum/export_report/total_report
|
||||
///Callback holding the sending timer for sending the goods after a delay.
|
||||
var/sending_timer
|
||||
///This is the cargo hold ID used by the piratepad machine. Match these two to link them together.
|
||||
var/cargo_hold_id
|
||||
///Interface name for the ui_interact call for different subtypes.
|
||||
var/interface_type = "CargoHoldTerminal"
|
||||
|
||||
/obj/machinery/computer/piratepad_control/Initialize(mapload)
|
||||
..()
|
||||
return INITIALIZE_HINT_LATELOAD
|
||||
@@ -351,10 +241,6 @@
|
||||
stop_sending()
|
||||
. = TRUE
|
||||
|
||||
/obj/machinery/computer/piratepad_control/proc/recalc()
|
||||
if(sending)
|
||||
return
|
||||
|
||||
status_report = "Predicted value: "
|
||||
var/value = 0
|
||||
var/datum/export_report/ex = new
|
||||
@@ -362,10 +248,6 @@
|
||||
for(var/atom/movable/AM in get_turf(pad))
|
||||
if(AM == pad)
|
||||
continue
|
||||
//SKYRAT EDIT ADDITION - NO MOBS!
|
||||
if(ismob(AM))
|
||||
continue
|
||||
//SKYRAT EDIT END
|
||||
export_item_and_contents(AM, apply_elastic = FALSE, dry_run = TRUE, external_report = ex)
|
||||
|
||||
for(var/datum/export/E in ex.total_amount)
|
||||
@@ -376,85 +258,6 @@
|
||||
if(!value)
|
||||
status_report += "0"
|
||||
|
||||
/obj/machinery/computer/piratepad_control/proc/send()
|
||||
if(!sending)
|
||||
return
|
||||
|
||||
var/datum/export_report/ex = new
|
||||
var/obj/machinery/piratepad/pad = pad_ref?.resolve()
|
||||
|
||||
for(var/atom/movable/AM in get_turf(pad))
|
||||
if(AM == pad)
|
||||
continue
|
||||
//SKYRAT EDIT ADDITION - NO MOBS!
|
||||
if(ismob(AM))
|
||||
continue
|
||||
//SKYRAT EDIT END
|
||||
export_item_and_contents(AM, EXPORT_PIRATE | EXPORT_CARGO | EXPORT_CONTRABAND | EXPORT_EMAG, apply_elastic = FALSE, delete_unsold = FALSE, external_report = ex)
|
||||
|
||||
status_report = "Sold: "
|
||||
var/value = 0
|
||||
for(var/datum/export/E in ex.total_amount)
|
||||
var/export_text = E.total_printout(ex,notes = FALSE) //Don't want nanotrasen messages, makes no sense here.
|
||||
if(!export_text)
|
||||
continue
|
||||
|
||||
status_report += export_text
|
||||
status_report += " "
|
||||
value += ex.total_value[E]
|
||||
|
||||
if(!total_report)
|
||||
total_report = ex
|
||||
else
|
||||
total_report.exported_atoms += ex.exported_atoms
|
||||
for(var/datum/export/E in ex.total_amount)
|
||||
total_report.total_amount[E] += ex.total_amount[E]
|
||||
total_report.total_value[E] += ex.total_value[E]
|
||||
playsound(loc, 'sound/machines/wewewew.ogg', 70, TRUE)
|
||||
|
||||
points += value
|
||||
|
||||
if(!value)
|
||||
status_report += "Nothing"
|
||||
|
||||
pad.visible_message(span_notice("[pad] activates!"))
|
||||
flick(pad.sending_state,pad)
|
||||
pad.icon_state = pad.idle_state
|
||||
sending = FALSE
|
||||
|
||||
/obj/machinery/computer/piratepad_control/proc/start_sending()
|
||||
var/obj/machinery/piratepad/pad = pad_ref?.resolve()
|
||||
if(!pad)
|
||||
status_report = "No pad detected. Build or link a pad."
|
||||
pad.audible_message(span_notice("[pad] beeps."))
|
||||
return
|
||||
if(pad?.panel_open)
|
||||
status_report = "Please screwdrive pad closed to send. "
|
||||
pad.audible_message(span_notice("[pad] beeps."))
|
||||
return
|
||||
if(sending)
|
||||
return
|
||||
sending = TRUE
|
||||
status_report = "Sending... "
|
||||
pad.visible_message(span_notice("[pad] starts charging up."))
|
||||
pad.icon_state = pad.warmup_state
|
||||
sending_timer = addtimer(CALLBACK(src, PROC_REF(send)),warmup_time, TIMER_STOPPABLE)
|
||||
|
||||
/obj/machinery/computer/piratepad_control/proc/stop_sending(custom_report)
|
||||
if(!sending)
|
||||
return
|
||||
sending = FALSE
|
||||
status_report = "Ready for delivery."
|
||||
if(custom_report)
|
||||
status_report = custom_report
|
||||
var/obj/machinery/piratepad/pad = pad_ref?.resolve()
|
||||
pad.icon_state = pad.idle_state
|
||||
deltimer(sending_timer)
|
||||
|
||||
//Attempts to find the thing on station
|
||||
/datum/export/pirate/proc/find_loot()
|
||||
return
|
||||
|
||||
/datum/export/pirate/ransom
|
||||
cost = 3000
|
||||
unit_name = "hostage"
|
||||
|
||||
@@ -0,0 +1,408 @@
|
||||
//Shuttle equipment
|
||||
|
||||
/obj/machinery/shuttle_scrambler
|
||||
name = "Data Siphon"
|
||||
desc = "This heap of machinery steals credits and data from unprotected systems and locks down cargo shuttles."
|
||||
icon = 'icons/obj/machines/dominator.dmi'
|
||||
icon_state = "dominator"
|
||||
density = TRUE
|
||||
var/active = FALSE
|
||||
var/credits_stored = 0
|
||||
var/siphon_per_tick = 5
|
||||
|
||||
/obj/machinery/shuttle_scrambler/Initialize(mapload)
|
||||
. = ..()
|
||||
update_appearance()
|
||||
|
||||
/obj/machinery/shuttle_scrambler/process()
|
||||
if(active)
|
||||
if(is_station_level(z))
|
||||
var/datum/bank_account/D = SSeconomy.get_dep_account(ACCOUNT_CAR)
|
||||
if(D)
|
||||
var/siphoned = min(D.account_balance,siphon_per_tick)
|
||||
D.adjust_money(-siphoned)
|
||||
credits_stored += siphoned
|
||||
interrupt_research()
|
||||
else
|
||||
return
|
||||
else
|
||||
STOP_PROCESSING(SSobj,src)
|
||||
|
||||
/obj/machinery/shuttle_scrambler/proc/toggle_on(mob/user)
|
||||
SSshuttle.registerTradeBlockade(src)
|
||||
AddComponent(/datum/component/gps, "Nautical Signal")
|
||||
active = TRUE
|
||||
to_chat(user,span_notice("You toggle [src] [active ? "on":"off"]."))
|
||||
to_chat(user,span_warning("The scrambling signal can be now tracked by GPS."))
|
||||
START_PROCESSING(SSobj,src)
|
||||
|
||||
/obj/machinery/shuttle_scrambler/interact(mob/user)
|
||||
if(active)
|
||||
dump_loot(user)
|
||||
return
|
||||
var/scramble_response = tgui_alert(user, "Turning the scrambler on will make the shuttle trackable by GPS. Are you sure you want to do it?", "Scrambler", list("Yes", "Cancel"))
|
||||
if(scramble_response != "Yes")
|
||||
return
|
||||
if(active || !user.canUseTopic(src, be_close = TRUE))
|
||||
return
|
||||
toggle_on(user)
|
||||
update_appearance()
|
||||
send_notification()
|
||||
|
||||
//interrupt_research
|
||||
/obj/machinery/shuttle_scrambler/proc/interrupt_research()
|
||||
for(var/obj/machinery/rnd/server/S as anything in SSresearch.science_tech.techweb_servers)
|
||||
if(S.machine_stat & (NOPOWER|BROKEN))
|
||||
continue
|
||||
S.emp_act()
|
||||
new /obj/effect/temp_visual/emp(get_turf(S))
|
||||
|
||||
/obj/machinery/shuttle_scrambler/proc/dump_loot(mob/user)
|
||||
if(credits_stored) // Prevents spamming empty holochips
|
||||
new /obj/item/holochip(drop_location(), credits_stored)
|
||||
to_chat(user,span_notice("You retrieve the siphoned credits!"))
|
||||
credits_stored = 0
|
||||
else
|
||||
to_chat(user,span_notice("There's nothing to withdraw."))
|
||||
|
||||
/obj/machinery/shuttle_scrambler/proc/send_notification()
|
||||
priority_announce("Data theft signal detected, source registered on local gps units.")
|
||||
|
||||
/obj/machinery/shuttle_scrambler/proc/toggle_off(mob/user)
|
||||
SSshuttle.clearTradeBlockade(src)
|
||||
active = FALSE
|
||||
STOP_PROCESSING(SSobj,src)
|
||||
|
||||
/obj/machinery/shuttle_scrambler/update_icon_state()
|
||||
icon_state = active ? "dominator-Blue" : "dominator"
|
||||
return ..()
|
||||
|
||||
/obj/machinery/shuttle_scrambler/Destroy()
|
||||
toggle_off()
|
||||
return ..()
|
||||
|
||||
/obj/machinery/computer/shuttle/pirate
|
||||
name = "pirate shuttle console"
|
||||
shuttleId = "pirate"
|
||||
icon_screen = "syndishuttle"
|
||||
icon_keyboard = "syndie_key"
|
||||
light_color = COLOR_SOFT_RED
|
||||
possible_destinations = "pirate_away;pirate_home;pirate_custom"
|
||||
|
||||
/obj/machinery/computer/camera_advanced/shuttle_docker/syndicate/pirate
|
||||
name = "pirate shuttle navigation computer"
|
||||
desc = "Used to designate a precise transit location for the pirate shuttle."
|
||||
shuttleId = "pirate"
|
||||
lock_override = CAMERA_LOCK_STATION
|
||||
shuttlePortId = "pirate_custom"
|
||||
x_offset = 9
|
||||
y_offset = 0
|
||||
see_hidden = FALSE
|
||||
|
||||
/obj/machinery/computer/camera_advanced/shuttle_docker/syndicate/pirate/psyker
|
||||
name = "psyker navigation warper"
|
||||
desc = "Used to designate a precise transit location for the psyker shuttle, using sent out brainwaves as detailed sight."
|
||||
icon_screen = "recharge_comp_on"
|
||||
interaction_flags_machine = INTERACT_MACHINE_ALLOW_SILICON | INTERACT_MACHINE_SET_MACHINE //blind friendly
|
||||
x_offset = 0
|
||||
y_offset = 11
|
||||
|
||||
/obj/docking_port/mobile/pirate
|
||||
name = "pirate shuttle"
|
||||
shuttle_id = "pirate"
|
||||
rechargeTime = 3 MINUTES
|
||||
|
||||
/obj/machinery/suit_storage_unit/pirate
|
||||
suit_type = /obj/item/clothing/suit/space
|
||||
helmet_type = /obj/item/clothing/head/helmet/space
|
||||
mask_type = /obj/item/clothing/mask/breath
|
||||
storage_type = /obj/item/tank/internals/oxygen
|
||||
|
||||
/obj/machinery/loot_locator
|
||||
name = "Booty Locator"
|
||||
desc = "This sophisticated machine scans the nearby space for items of value."
|
||||
icon = 'icons/obj/machines/research.dmi'
|
||||
icon_state = "tdoppler"
|
||||
density = TRUE
|
||||
var/cooldown = 300
|
||||
var/next_use = 0
|
||||
|
||||
/obj/machinery/loot_locator/interact(mob/user)
|
||||
if(world.time <= next_use)
|
||||
to_chat(user,span_warning("[src] is recharging."))
|
||||
return
|
||||
next_use = world.time + cooldown
|
||||
var/atom/movable/AM = find_random_loot()
|
||||
if(!AM)
|
||||
say("No valuables located. Try again later.")
|
||||
else
|
||||
say("Located: [AM.name] at [get_area_name(AM)]")
|
||||
|
||||
/obj/machinery/loot_locator/proc/find_random_loot()
|
||||
if(!GLOB.exports_list.len)
|
||||
setupExports()
|
||||
var/list/possible_loot = list()
|
||||
for(var/datum/export/pirate/E in GLOB.exports_list)
|
||||
possible_loot += E
|
||||
var/datum/export/pirate/P
|
||||
var/atom/movable/AM
|
||||
while(!AM && possible_loot.len)
|
||||
P = pick_n_take(possible_loot)
|
||||
AM = P.find_loot()
|
||||
return AM
|
||||
|
||||
//Pad & Pad Terminal
|
||||
/obj/machinery/piratepad
|
||||
name = "cargo hold pad"
|
||||
icon = 'icons/obj/telescience.dmi'
|
||||
icon_state = "lpad-idle-off"
|
||||
///This is the icon_state that this telepad uses when it's not in use.
|
||||
var/idle_state = "lpad-idle-off"
|
||||
///This is the icon_state that this telepad uses when it's warming up for goods teleportation.
|
||||
var/warmup_state = "lpad-idle"
|
||||
///This is the icon_state to flick when the goods are being sent off by the telepad.
|
||||
var/sending_state = "lpad-beam"
|
||||
///This is the cargo hold ID used by the piratepad_control. Match these two to link them together.
|
||||
var/cargo_hold_id
|
||||
|
||||
/obj/machinery/piratepad/multitool_act(mob/living/user, obj/item/multitool/I)
|
||||
. = ..()
|
||||
if (istype(I))
|
||||
to_chat(user, span_notice("You register [src] in [I]s buffer."))
|
||||
I.buffer = src
|
||||
return TRUE
|
||||
|
||||
/obj/machinery/piratepad/screwdriver_act_secondary(mob/living/user, obj/item/screwdriver/screw)
|
||||
. = ..()
|
||||
if(!.)
|
||||
return default_deconstruction_screwdriver(user, "lpad-idle-open", "lpad-idle-off", screw)
|
||||
|
||||
/obj/machinery/piratepad/crowbar_act_secondary(mob/living/user, obj/item/tool)
|
||||
. = ..()
|
||||
default_deconstruction_crowbar(tool)
|
||||
return TRUE
|
||||
|
||||
/obj/machinery/computer/piratepad_control
|
||||
name = "cargo hold control terminal"
|
||||
///Message to display on the TGUI window.
|
||||
var/status_report = "Ready for delivery."
|
||||
///Reference to the specific pad that the control computer is linked up to.
|
||||
var/datum/weakref/pad_ref
|
||||
///How long does it take to warmup the pad to teleport?
|
||||
var/warmup_time = 100
|
||||
///Is the teleport pad/computer sending something right now? TRUE/FALSE
|
||||
var/sending = FALSE
|
||||
///For the purposes of space pirates, how many points does the control pad have collected.
|
||||
var/points = 0
|
||||
///Reference to the export report totaling all sent objects and mobs.
|
||||
var/datum/export_report/total_report
|
||||
///Callback holding the sending timer for sending the goods after a delay.
|
||||
var/sending_timer
|
||||
///This is the cargo hold ID used by the piratepad machine. Match these two to link them together.
|
||||
var/cargo_hold_id
|
||||
///Interface name for the ui_interact call for different subtypes.
|
||||
var/interface_type = "CargoHoldTerminal"
|
||||
|
||||
/obj/machinery/computer/piratepad_control/Initialize(mapload)
|
||||
..()
|
||||
return INITIALIZE_HINT_LATELOAD
|
||||
|
||||
/obj/machinery/computer/piratepad_control/multitool_act(mob/living/user, obj/item/multitool/I)
|
||||
. = ..()
|
||||
if (istype(I) && istype(I.buffer,/obj/machinery/piratepad))
|
||||
to_chat(user, span_notice("You link [src] with [I.buffer] in [I] buffer."))
|
||||
pad_ref = WEAKREF(I.buffer)
|
||||
return TRUE
|
||||
|
||||
/obj/machinery/computer/piratepad_control/LateInitialize()
|
||||
. = ..()
|
||||
if(cargo_hold_id)
|
||||
for(var/obj/machinery/piratepad/P in GLOB.machines)
|
||||
if(P.cargo_hold_id == cargo_hold_id)
|
||||
pad_ref = WEAKREF(P)
|
||||
return
|
||||
else
|
||||
var/obj/machinery/piratepad/pad = locate() in range(4, src)
|
||||
pad_ref = WEAKREF(pad)
|
||||
|
||||
/obj/machinery/computer/piratepad_control/ui_interact(mob/user, datum/tgui/ui)
|
||||
. = ..()
|
||||
ui = SStgui.try_update_ui(user, src, ui)
|
||||
if(!ui)
|
||||
ui = new(user, src, interface_type, name)
|
||||
ui.open()
|
||||
|
||||
/obj/machinery/computer/piratepad_control/ui_data(mob/user)
|
||||
var/list/data = list()
|
||||
data["points"] = points
|
||||
data["pad"] = pad_ref?.resolve() ? TRUE : FALSE
|
||||
data["sending"] = sending
|
||||
data["status_report"] = status_report
|
||||
return data
|
||||
|
||||
/obj/machinery/computer/piratepad_control/ui_act(action, params)
|
||||
. = ..()
|
||||
if(.)
|
||||
return
|
||||
if(!pad_ref?.resolve())
|
||||
return
|
||||
|
||||
switch(action)
|
||||
if("recalc")
|
||||
recalc()
|
||||
. = TRUE
|
||||
if("send")
|
||||
start_sending()
|
||||
. = TRUE
|
||||
if("stop")
|
||||
stop_sending()
|
||||
. = TRUE
|
||||
|
||||
/obj/machinery/computer/piratepad_control/proc/recalc()
|
||||
if(sending)
|
||||
return
|
||||
|
||||
status_report = "Predicted value: "
|
||||
var/value = 0
|
||||
var/datum/export_report/ex = new
|
||||
var/obj/machinery/piratepad/pad = pad_ref?.resolve()
|
||||
for(var/atom/movable/AM in get_turf(pad))
|
||||
if(AM == pad)
|
||||
continue
|
||||
export_item_and_contents(AM, apply_elastic = FALSE, dry_run = TRUE, external_report = ex)
|
||||
|
||||
for(var/datum/export/E in ex.total_amount)
|
||||
status_report += E.total_printout(ex,notes = FALSE)
|
||||
status_report += " "
|
||||
value += ex.total_value[E]
|
||||
|
||||
if(!value)
|
||||
status_report += "0"
|
||||
|
||||
/obj/machinery/computer/piratepad_control/proc/send()
|
||||
if(!sending)
|
||||
return
|
||||
|
||||
var/datum/export_report/ex = new
|
||||
var/obj/machinery/piratepad/pad = pad_ref?.resolve()
|
||||
|
||||
for(var/atom/movable/AM in get_turf(pad))
|
||||
if(AM == pad)
|
||||
continue
|
||||
export_item_and_contents(AM, EXPORT_PIRATE | EXPORT_CARGO | EXPORT_CONTRABAND | EXPORT_EMAG, apply_elastic = FALSE, delete_unsold = FALSE, external_report = ex)
|
||||
|
||||
status_report = "Sold: "
|
||||
var/value = 0
|
||||
for(var/datum/export/E in ex.total_amount)
|
||||
var/export_text = E.total_printout(ex,notes = FALSE) //Don't want nanotrasen messages, makes no sense here.
|
||||
if(!export_text)
|
||||
continue
|
||||
|
||||
status_report += export_text
|
||||
status_report += " "
|
||||
value += ex.total_value[E]
|
||||
|
||||
if(!total_report)
|
||||
total_report = ex
|
||||
else
|
||||
total_report.exported_atoms += ex.exported_atoms
|
||||
for(var/datum/export/E in ex.total_amount)
|
||||
total_report.total_amount[E] += ex.total_amount[E]
|
||||
total_report.total_value[E] += ex.total_value[E]
|
||||
playsound(loc, 'sound/machines/wewewew.ogg', 70, TRUE)
|
||||
|
||||
points += value
|
||||
|
||||
if(!value)
|
||||
status_report += "Nothing"
|
||||
|
||||
pad.visible_message(span_notice("[pad] activates!"))
|
||||
flick(pad.sending_state,pad)
|
||||
pad.icon_state = pad.idle_state
|
||||
sending = FALSE
|
||||
|
||||
/obj/machinery/computer/piratepad_control/proc/start_sending()
|
||||
var/obj/machinery/piratepad/pad = pad_ref?.resolve()
|
||||
if(!pad)
|
||||
status_report = "No pad detected. Build or link a pad."
|
||||
pad.audible_message(span_notice("[pad] beeps."))
|
||||
return
|
||||
if(pad?.panel_open)
|
||||
status_report = "Please screwdrive pad closed to send. "
|
||||
pad.audible_message(span_notice("[pad] beeps."))
|
||||
return
|
||||
if(sending)
|
||||
return
|
||||
sending = TRUE
|
||||
status_report = "Sending... "
|
||||
pad.visible_message(span_notice("[pad] starts charging up."))
|
||||
pad.icon_state = pad.warmup_state
|
||||
sending_timer = addtimer(CALLBACK(src, PROC_REF(send)),warmup_time, TIMER_STOPPABLE)
|
||||
|
||||
/obj/machinery/computer/piratepad_control/proc/stop_sending(custom_report)
|
||||
if(!sending)
|
||||
return
|
||||
sending = FALSE
|
||||
status_report = "Ready for delivery."
|
||||
if(custom_report)
|
||||
status_report = custom_report
|
||||
var/obj/machinery/piratepad/pad = pad_ref?.resolve()
|
||||
pad.icon_state = pad.idle_state
|
||||
deltimer(sending_timer)
|
||||
|
||||
//Attempts to find the thing on station
|
||||
/datum/export/pirate/proc/find_loot()
|
||||
return
|
||||
|
||||
/datum/export/pirate/ransom
|
||||
cost = 3000
|
||||
unit_name = "hostage"
|
||||
export_types = list(/mob/living/carbon/human)
|
||||
|
||||
/datum/export/pirate/ransom/find_loot()
|
||||
var/list/head_minds = SSjob.get_living_heads()
|
||||
var/list/head_mobs = list()
|
||||
for(var/datum/mind/M as anything in head_minds)
|
||||
head_mobs += M.current
|
||||
if(head_mobs.len)
|
||||
return pick(head_mobs)
|
||||
|
||||
/datum/export/pirate/ransom/get_cost(atom/movable/AM)
|
||||
var/mob/living/carbon/human/H = AM
|
||||
if(H.stat != CONSCIOUS || !H.mind) //mint condition only
|
||||
return 0
|
||||
else if("pirate" in H.faction) //can't ransom your fellow pirates to CentCom!
|
||||
return 0
|
||||
else if(H.mind.assigned_role.departments_bitflags & DEPARTMENT_BITFLAG_COMMAND)
|
||||
return 3000
|
||||
else
|
||||
return 1000
|
||||
|
||||
/datum/export/pirate/parrot
|
||||
cost = 2000
|
||||
unit_name = "alive parrot"
|
||||
export_types = list(/mob/living/simple_animal/parrot)
|
||||
|
||||
/datum/export/pirate/parrot/find_loot()
|
||||
for(var/mob/living/simple_animal/parrot/P in GLOB.alive_mob_list)
|
||||
var/turf/T = get_turf(P)
|
||||
if(T && is_station_level(T.z))
|
||||
return P
|
||||
|
||||
/datum/export/pirate/cash
|
||||
cost = 1
|
||||
unit_name = "bills"
|
||||
export_types = list(/obj/item/stack/spacecash)
|
||||
|
||||
/datum/export/pirate/cash/get_amount(obj/O)
|
||||
var/obj/item/stack/spacecash/C = O
|
||||
return ..() * C.amount * C.value
|
||||
|
||||
/datum/export/pirate/holochip
|
||||
cost = 1
|
||||
unit_name = "holochip"
|
||||
export_types = list(/obj/item/holochip)
|
||||
|
||||
/datum/export/pirate/holochip/get_cost(atom/movable/AM)
|
||||
var/obj/item/holochip/H = AM
|
||||
return H.credits
|
||||
@@ -30,10 +30,16 @@
|
||||
/// Whether or not dynamic should hijack this event
|
||||
var/dynamic_should_hijack = FALSE
|
||||
|
||||
/// Datum that will handle admin options for forcing the event.
|
||||
/// If there are no options, just leave it null.
|
||||
var/datum/event_admin_setup/admin_setup = null
|
||||
|
||||
/datum/round_event_control/New()
|
||||
if(config && !wizardevent) // Magic is unaffected by configs
|
||||
earliest_start = CEILING(earliest_start * CONFIG_GET(number/events_min_time_mul), 1)
|
||||
min_players = CEILING(min_players * CONFIG_GET(number/events_min_players_mul), 1)
|
||||
if(admin_setup)
|
||||
admin_setup = new admin_setup(src)
|
||||
|
||||
/datum/round_event_control/wizard
|
||||
category = EVENT_CATEGORY_WIZARD
|
||||
@@ -122,22 +128,25 @@ Runs the event
|
||||
* * In the worst case scenario we can still recall a event which we cancelled by accident, which is much better then to have a unwanted event
|
||||
*/
|
||||
UnregisterSignal(SSdcs, COMSIG_GLOB_RANDOM_EVENT)
|
||||
var/datum/round_event/E = new typepath(TRUE, src)
|
||||
E.current_players = get_active_player_count(alive_check = 1, afk_check = 1, human_check = 1)
|
||||
var/datum/round_event/round_event = new typepath(TRUE, src)
|
||||
if(admin_forced && admin_setup)
|
||||
admin_setup.apply_to_event(round_event)
|
||||
round_event.setup()
|
||||
round_event.current_players = get_active_player_count(alive_check = 1, afk_check = 1, human_check = 1)
|
||||
occurrences++
|
||||
|
||||
SSevents.previously_run += src //SKYRAT EDIT ADDITION
|
||||
|
||||
if(announce_chance_override != null)
|
||||
E.announce_chance = announce_chance_override
|
||||
round_event.announce_chance = announce_chance_override
|
||||
|
||||
testing("[time2text(world.time, "hh:mm:ss")] [E.type]")
|
||||
testing("[time2text(world.time, "hh:mm:ss")] [round_event.type]")
|
||||
triggering = TRUE
|
||||
|
||||
if(!triggering)
|
||||
RegisterSignal(SSdcs, COMSIG_GLOB_RANDOM_EVENT, PROC_REF(stop_random_event))
|
||||
E.cancel_event = TRUE
|
||||
return E
|
||||
round_event.cancel_event = TRUE
|
||||
return round_event
|
||||
|
||||
triggering = FALSE
|
||||
if(random)
|
||||
@@ -146,8 +155,8 @@ Runs the event
|
||||
if(alert_observers)
|
||||
announce_deadchat(random)
|
||||
|
||||
SSblackbox.record_feedback("tally", "event_ran", 1, "[E]")
|
||||
return E
|
||||
SSblackbox.record_feedback("tally", "event_ran", 1, "[round_event]")
|
||||
return round_event
|
||||
|
||||
///Annouces the event name to deadchat, override this if what an event should show to deadchat is different to its event name.
|
||||
/datum/round_event_control/proc/announce_deadchat(random)
|
||||
@@ -158,12 +167,6 @@ Runs the event
|
||||
SIGNAL_HANDLER
|
||||
return CANCEL_RANDOM_EVENT
|
||||
|
||||
/// Any special things admins can do while triggering this event to "improve" it.
|
||||
/// Return [ADMIN_CANCEL_EVENT] to stop the event from actually happening after all
|
||||
/datum/round_event_control/proc/admin_setup(mob/admin)
|
||||
SHOULD_CALL_PARENT(FALSE)
|
||||
return
|
||||
|
||||
/datum/round_event //NOTE: Times are measured in master controller ticks!
|
||||
var/processing = TRUE
|
||||
var/datum/round_event_control/control
|
||||
@@ -194,12 +197,14 @@ Runs the event
|
||||
//It will only have been overridden by the time we get to announce() start() tick() or end() (anything but setup basically).
|
||||
//This is really only for setting defaults which can be overridden later when New() finishes.
|
||||
/datum/round_event/proc/setup()
|
||||
SHOULD_CALL_PARENT(FALSE)
|
||||
return
|
||||
|
||||
//Called when the tick is equal to the start_when variable.
|
||||
//Allows you to start before announcing or vice versa.
|
||||
//Only called once.
|
||||
/datum/round_event/proc/start()
|
||||
SHOULD_CALL_PARENT(FALSE)
|
||||
return
|
||||
|
||||
//Called after something followable has been spawned by an event
|
||||
@@ -285,7 +290,6 @@ Runs the event
|
||||
//Sets up the event then adds the event to the the list of running events
|
||||
/datum/round_event/New(my_processing = TRUE, datum/round_event_control/event_controller)
|
||||
control = event_controller
|
||||
setup()
|
||||
processing = my_processing
|
||||
SSevents.running += src
|
||||
return ..()
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
/// Datum that holds a proc for additional options when running an event.
|
||||
/// Prototypes are declared here, non-prototypes on the event files.
|
||||
/datum/event_admin_setup
|
||||
/// event control that owns this.
|
||||
var/datum/round_event_control/event_control
|
||||
|
||||
/datum/event_admin_setup/New(event_control)
|
||||
src.event_control = event_control
|
||||
|
||||
/datum/event_admin_setup/proc/prompt_admins()
|
||||
SHOULD_CALL_PARENT(FALSE)
|
||||
CRASH("Unimplemented prompt_admins() on [event_control]'s admin setup.")
|
||||
|
||||
/datum/event_admin_setup/proc/apply_to_event(datum/round_event/event)
|
||||
SHOULD_CALL_PARENT(FALSE)
|
||||
CRASH("Unimplemented apply_to_event() on [event_control]'s admin setup.")
|
||||
|
||||
/// A very common pattern is picking from a tgui list input, so this does that.
|
||||
/// Supply a list in `get_list` and prompt admins will have the admin pick from it or cancel.
|
||||
/datum/event_admin_setup/listed_options
|
||||
/// Text to ask the user, for example "What deal would you like to offer the crew?"
|
||||
var/input_text = "Unset Text"
|
||||
/// If set, picking this will be the same as running the event without admin setup.
|
||||
var/normal_run_option
|
||||
/// Picked list option to be applied.
|
||||
var/chosen
|
||||
|
||||
/datum/event_admin_setup/listed_options/proc/get_list()
|
||||
SHOULD_CALL_PARENT(FALSE)
|
||||
CRASH("Unimplemented get_list() on [event_control]'s admin setup.")
|
||||
|
||||
/datum/event_admin_setup/listed_options/prompt_admins()
|
||||
var/list/options = get_list()
|
||||
if(normal_run_option)
|
||||
options.Insert(1, normal_run_option)
|
||||
chosen = tgui_input_list(usr, input_text, event_control.name, options)
|
||||
if(!chosen)
|
||||
return ADMIN_CANCEL_EVENT
|
||||
if(normal_run_option && chosen == normal_run_option)
|
||||
chosen = null //no admin pick = runs as normal
|
||||
|
||||
/// For admin setups that want a custom string. Suggests what the event would have picked normally.
|
||||
/datum/event_admin_setup/text_input
|
||||
/// Text to ask the user, for example "What horrifying truth will you reveal?"
|
||||
var/input_text = "Unset Text"
|
||||
/// Picked string to be applied.
|
||||
var/chosen
|
||||
|
||||
/// Returns a string to suggest to the admin, which would be what the event would have chosen.
|
||||
/// No suggestion if an empty string, which is default behavior.
|
||||
/datum/event_admin_setup/text_input/proc/get_text_suggestion()
|
||||
return ""
|
||||
|
||||
/datum/event_admin_setup/text_input/prompt_admins()
|
||||
var/suggestion = get_text_suggestion()
|
||||
chosen = tgui_input_text(usr, input_text, event_control.name, suggestion)
|
||||
if(!chosen)
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
/// Some events are not always a good idea when a game state is in a certain situation.
|
||||
/// This runs a check and warns the admin.
|
||||
/datum/event_admin_setup/warn_admin
|
||||
/// Warning text shown to admin on the alert.
|
||||
var/warning_text = "Unset warning text"
|
||||
/// Message sent to other admins. Example: "has forced a shuttle catastrophe while a shuttle was already docked."
|
||||
var/snitch_text = "Unset snitching text (be mad at coders AND the admin responsible)"
|
||||
|
||||
/datum/event_admin_setup/warn_admin/prompt_admins()
|
||||
if(!should_warn())
|
||||
return
|
||||
var/mob/admin = usr
|
||||
if(tgui_alert(usr, "WARNING: [warning_text]", event_control.name, list("Yes", "No")) == "Yes")
|
||||
message_admins("[admin.ckey] [snitch_text]")
|
||||
else
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
/// Returns whether the admin should get an alert.
|
||||
/datum/event_admin_setup/warn_admin/proc/should_warn()
|
||||
SHOULD_CALL_PARENT(FALSE)
|
||||
CRASH("Unimplemented should_warn() on [event_control]'s admin setup.")
|
||||
|
||||
/datum/event_admin_setup/warn_admin/apply_to_event(datum/round_event/event)
|
||||
return
|
||||
@@ -7,31 +7,20 @@
|
||||
weight = 15
|
||||
category = EVENT_CATEGORY_ANOMALIES
|
||||
description = "This anomaly shocks and explodes. This is the base type."
|
||||
///The admin-chosen spawn location.
|
||||
var/turf/spawn_location
|
||||
|
||||
/datum/round_event_control/anomaly/admin_setup(mob/admin)
|
||||
. = ..()
|
||||
|
||||
if(!check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
if(tgui_alert(usr, "Spawn anomaly at your current location?", "Anomaly Alert", list("Yes", "No")) == "Yes")
|
||||
spawn_location = get_turf(usr)
|
||||
admin_setup = /datum/event_admin_setup/anomaly
|
||||
|
||||
/datum/round_event/anomaly
|
||||
announce_when = 1
|
||||
var/area/impact_area
|
||||
var/datum/anomaly_placer/placer = new()
|
||||
var/obj/effect/anomaly/anomaly_path = /obj/effect/anomaly/flux
|
||||
announce_when = 1
|
||||
///The admin-chosen spawn location.
|
||||
var/turf/spawn_location
|
||||
|
||||
/datum/round_event/anomaly/setup()
|
||||
|
||||
end_when = start_when + 1 //Admin vars are cleared on end(), so we make sure the anomaly spawns before then.
|
||||
|
||||
var/datum/round_event_control/anomaly/anomaly_event = control
|
||||
if(anomaly_event.spawn_location)
|
||||
impact_area = get_area(anomaly_event.spawn_location)
|
||||
if(spawn_location)
|
||||
impact_area = get_area(spawn_location)
|
||||
else
|
||||
impact_area = placer.findValidArea()
|
||||
|
||||
@@ -41,9 +30,8 @@
|
||||
/datum/round_event/anomaly/start()
|
||||
var/turf/anomaly_turf
|
||||
|
||||
var/datum/round_event_control/anomaly/anomaly_event = control
|
||||
if(anomaly_event.spawn_location)
|
||||
anomaly_turf = anomaly_event.spawn_location
|
||||
if(spawn_location)
|
||||
anomaly_turf = spawn_location
|
||||
else
|
||||
anomaly_turf = placer.findValidTurf(impact_area)
|
||||
|
||||
@@ -53,6 +41,13 @@
|
||||
if (newAnomaly)
|
||||
announce_to_ghosts(newAnomaly)
|
||||
|
||||
/datum/round_event/anomaly/end()
|
||||
var/datum/round_event_control/anomaly/anomaly_event = control
|
||||
anomaly_event.spawn_location = null
|
||||
/datum/event_admin_setup/anomaly
|
||||
///The admin-chosen spawn location.
|
||||
var/turf/spawn_location
|
||||
|
||||
/datum/event_admin_setup/anomaly/prompt_admins()
|
||||
if(tgui_alert(usr, "Spawn anomaly at your current location?", "Anomaly Alert", list("Yes", "No")) == "Yes")
|
||||
spawn_location = get_turf(usr)
|
||||
|
||||
/datum/event_admin_setup/anomaly/apply_to_event(datum/round_event/anomaly/event)
|
||||
event.spawn_location = spawn_location
|
||||
|
||||
@@ -6,23 +6,20 @@
|
||||
description = "Vending machines will attack people until the Patient Zero is disabled."
|
||||
min_players = 15
|
||||
max_occurrences = 1
|
||||
///Var used to determine vendor subtype if used for admin setup
|
||||
var/chosen_vendor
|
||||
|
||||
/datum/round_event_control/brand_intelligence/admin_setup()
|
||||
if(!check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
if(tgui_alert(usr, "Select a specific vendor path?", "Capitalism-ho!", list("Yes", "No")) == "Yes")
|
||||
var/list/vendors = list()
|
||||
vendors += subtypesof(/obj/machinery/vending)
|
||||
chosen_vendor = tgui_input_list(usr, "Vendor type must have at least one instance on the station for this to work!","Vendor Selector", vendors)
|
||||
admin_setup = /datum/event_admin_setup/listed_options/brand_intelligence
|
||||
|
||||
/datum/round_event/brand_intelligence
|
||||
announce_when = 21
|
||||
end_when = 1000 //Ends when all vending machines are subverted anyway.
|
||||
var/list/obj/machinery/vending/vendingMachines = list()
|
||||
var/list/obj/machinery/vending/infectedMachines = list()
|
||||
var/obj/machinery/vending/originMachine
|
||||
/// Admin picked subtype for what kind of vendor goes haywire.
|
||||
var/chosen_vendor_type
|
||||
/// All vending machines valid to get infected.
|
||||
var/list/obj/machinery/vending/vending_machines = list()
|
||||
/// All vending machines that have been infected.
|
||||
var/list/obj/machinery/vending/infected_machines = list()
|
||||
/// The original machine infected. Killing it ends the event.
|
||||
var/obj/machinery/vending/origin_machine
|
||||
/// Murderous sayings from the machines.
|
||||
var/list/rampant_speeches = list(
|
||||
"Try our aggressive new marketing strategies!",
|
||||
"You should buy products to feed your lifestyle obsession!",
|
||||
@@ -33,66 +30,62 @@
|
||||
"You don't want to buy anything? Yeah, well, I didn't want to buy your mom either.",
|
||||
)
|
||||
|
||||
/datum/round_event/brand_intelligence/setup()
|
||||
//select our origin machine (which will also be the type of vending machine affected.)
|
||||
for(var/obj/machinery/vending/vendor in GLOB.machines)
|
||||
if(!is_station_level(vendor.z))
|
||||
continue
|
||||
if(!vendor.density)
|
||||
continue
|
||||
if(chosen_vendor_type && !istype(vendor, chosen_vendor_type))
|
||||
continue
|
||||
vending_machines.Add(vendor)
|
||||
if(!length(vending_machines)) //If somehow there are still no elligible vendors, give up.
|
||||
kill()
|
||||
return
|
||||
origin_machine = pick_n_take(vending_machines)
|
||||
|
||||
/datum/round_event/brand_intelligence/announce(fake)
|
||||
var/source = "unknown machine"
|
||||
if(fake)
|
||||
for(var/obj/machinery/vending/vendor in GLOB.machines)
|
||||
if(!is_station_level(vendor.z))
|
||||
continue
|
||||
vendingMachines.Add(vendor)
|
||||
var/obj/machinery/vending/chosen_vendor = pick(vendingMachines)
|
||||
source = chosen_vendor.name
|
||||
else if(originMachine)
|
||||
source = originMachine.name
|
||||
priority_announce("Rampant brand intelligence has been detected aboard [station_name()]. Please inspect any [source] brand vendors for aggressive marketing tactics, and reboot them if necessary.", "Machine Learning Alert")
|
||||
priority_announce("Rampant brand intelligence has been detected aboard [station_name()]. Please inspect any [origin_machine] brand vendors for aggressive marketing tactics, and reboot them if necessary.", "Machine Learning Alert")
|
||||
|
||||
/datum/round_event/brand_intelligence/start()
|
||||
var/datum/round_event_control/brand_intelligence/brand_event = control
|
||||
if(brand_event.chosen_vendor) //Attempt to search for vendors of the selected admin subtype
|
||||
var/chosen_vendor = brand_event.chosen_vendor
|
||||
for(var/obj/machinery/vending/vendor in GLOB.machines)
|
||||
if(!is_station_level(vendor.z) || !istype(vendor, chosen_vendor) || !vendor.density)
|
||||
continue
|
||||
vendingMachines.Add(vendor)
|
||||
brand_event.chosen_vendor = null //Event has a max_occurences of 1 but juuust in case
|
||||
if(!length(vendingMachines)) //If no vendors are in vendingMachines, setup defaults back to randomly selecting one.
|
||||
for(var/obj/machinery/vending/vendor in GLOB.machines)
|
||||
if(!is_station_level(vendor.z) || !vendor.density)
|
||||
continue
|
||||
vendingMachines.Add(vendor)
|
||||
if(!length(vendingMachines)) //If somehow there are still no elligible vendors, give up.
|
||||
kill()
|
||||
return
|
||||
originMachine = pick(vendingMachines)
|
||||
vendingMachines.Remove(originMachine)
|
||||
originMachine.shut_up = FALSE
|
||||
originMachine.shoot_inventory = TRUE
|
||||
announce_to_ghosts(originMachine)
|
||||
origin_machine.shut_up = FALSE
|
||||
origin_machine.shoot_inventory = TRUE
|
||||
announce_to_ghosts(origin_machine)
|
||||
|
||||
/datum/round_event/brand_intelligence/tick()
|
||||
if(!originMachine || QDELETED(originMachine) || originMachine.shut_up || originMachine.wires.is_all_cut()) //if the original vending machine is missing or has it's voice switch flipped
|
||||
for(var/obj/machinery/vending/saved in infectedMachines)
|
||||
if(!origin_machine || QDELETED(origin_machine) || origin_machine.shut_up || origin_machine.wires.is_all_cut()) //if the original vending machine is missing or has it's voice switch flipped
|
||||
for(var/obj/machinery/vending/saved in infected_machines)
|
||||
saved.shoot_inventory = FALSE
|
||||
if(originMachine)
|
||||
originMachine.speak("I am... vanquished. My people will remem...ber...meeee.")
|
||||
originMachine.visible_message(span_notice("[originMachine] beeps and seems lifeless."))
|
||||
if(origin_machine)
|
||||
origin_machine.speak("I am... vanquished. My people will remem...ber...meeee.")
|
||||
origin_machine.visible_message(span_notice("[origin_machine] beeps and seems lifeless."))
|
||||
kill()
|
||||
return
|
||||
list_clear_nulls(vendingMachines)
|
||||
if(!vendingMachines.len) //if every machine is infected
|
||||
for(var/obj/machinery/vending/upriser in infectedMachines)
|
||||
list_clear_nulls(vending_machines)
|
||||
if(!vending_machines.len) //if every machine is infected
|
||||
for(var/obj/machinery/vending/upriser in infected_machines)
|
||||
if(!QDELETED(upriser))
|
||||
upriser.ai_controller = new /datum/ai_controller/vending_machine(upriser)
|
||||
infectedMachines.Remove(upriser)
|
||||
infected_machines.Remove(upriser)
|
||||
kill()
|
||||
return
|
||||
if(ISMULTIPLE(activeFor, 2))
|
||||
var/obj/machinery/vending/rebel = pick(vendingMachines)
|
||||
vendingMachines.Remove(rebel)
|
||||
infectedMachines.Add(rebel)
|
||||
var/obj/machinery/vending/rebel = pick(vending_machines)
|
||||
vending_machines.Remove(rebel)
|
||||
infected_machines.Add(rebel)
|
||||
rebel.shut_up = FALSE
|
||||
rebel.shoot_inventory = TRUE
|
||||
|
||||
if(ISMULTIPLE(activeFor, 4))
|
||||
originMachine.speak(pick(rampant_speeches))
|
||||
origin_machine.speak(pick(rampant_speeches))
|
||||
|
||||
/datum/event_admin_setup/listed_options/brand_intelligence
|
||||
input_text = "Select a specific vendor path?"
|
||||
normal_run_option = "Random Vendor"
|
||||
|
||||
/datum/event_admin_setup/listed_options/brand_intelligence/get_list()
|
||||
return subtypesof(/obj/machinery/vending)
|
||||
|
||||
/datum/event_admin_setup/listed_options/brand_intelligence/apply_to_event(datum/round_event/brand_intelligence/event)
|
||||
event.chosen_vendor_type = chosen
|
||||
|
||||
@@ -6,10 +6,9 @@
|
||||
weight = 5
|
||||
category = EVENT_CATEGORY_HEALTH
|
||||
description = "A 'classic' virus will infect some members of the crew." //These are the ones with PERSONALITY
|
||||
admin_setup = /datum/event_admin_setup/disease_outbreak
|
||||
///Disease recipient candidates
|
||||
var/list/disease_candidates = list()
|
||||
///Admin selected disease, to be passed down to the round_event
|
||||
var/chosen_disease
|
||||
|
||||
/datum/round_event_control/disease_outbreak/can_spawn_event(players_amt)
|
||||
. = ..()
|
||||
@@ -19,21 +18,6 @@
|
||||
if(length(disease_candidates))
|
||||
return TRUE
|
||||
|
||||
/datum/round_event_control/disease_outbreak/admin_setup()
|
||||
if(!check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
generate_candidates()
|
||||
|
||||
if(!length(disease_candidates))
|
||||
message_admins("No disease candidates found!")
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
message_admins("[length(disease_candidates)] candidates found!")
|
||||
|
||||
if(tgui_alert(usr, "Select a specific disease?", "Sickening behavior", list("Yes", "No")) == "Yes")
|
||||
chosen_disease = tgui_input_list(usr, "Warning: Some of these are EXTREMELY dangerous.","Bacteria Hysteria", subtypesof(/datum/disease))
|
||||
|
||||
/**
|
||||
* Creates a list of people who are elligible to become disease carriers for the event
|
||||
*
|
||||
@@ -68,10 +52,6 @@
|
||||
var/datum/round_event_control/disease_outbreak/disease_event = control
|
||||
afflicted += disease_event.disease_candidates
|
||||
disease_event.disease_candidates.Cut() //Clean the list after use
|
||||
if(disease_event.chosen_disease)
|
||||
virus_type = disease_event.chosen_disease
|
||||
disease_event.chosen_disease = null
|
||||
|
||||
if(!virus_type)
|
||||
var/list/virus_candidates = list()
|
||||
|
||||
@@ -104,26 +84,7 @@
|
||||
typepath = /datum/round_event/disease_outbreak/advanced
|
||||
category = EVENT_CATEGORY_HEALTH
|
||||
description = "An 'advanced' disease will infect some members of the crew." //These are the ones that get viro lynched!
|
||||
///Admin selected custom severity rating for the event
|
||||
var/chosen_severity
|
||||
///Admin selected custom value for the maximum symptoms this virus should have
|
||||
var/chosen_max_symptoms
|
||||
|
||||
/datum/round_event_control/disease_outbreak/advanced/admin_setup()
|
||||
if(!check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
generate_candidates()
|
||||
|
||||
if(!length(disease_candidates))
|
||||
message_admins("No disease candidates found!")
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
message_admins("[length(disease_candidates)] candidates found!")
|
||||
|
||||
if(tgui_alert(usr,"Customize your virus?", "Glorified Debug Tool", list("Yes", "No")) == "Yes")
|
||||
chosen_severity = tgui_input_number(usr, "Select a custom severity for your virus!", "Plague Incorporation!", 3, 8)
|
||||
chosen_max_symptoms = tgui_input_number(usr, "How many symptoms do you want your virus to have?", "A pox upon ye!", 3, 15)
|
||||
admin_setup = /datum/event_admin_setup/disease_outbreak/advanced
|
||||
|
||||
/datum/round_event/disease_outbreak/advanced
|
||||
///Number of symptoms for our virus
|
||||
@@ -136,17 +97,11 @@
|
||||
afflicted += disease_event.disease_candidates
|
||||
disease_event.disease_candidates.Cut() //Clean the list after use
|
||||
|
||||
if(disease_event.chosen_max_symptoms)
|
||||
max_symptoms = disease_event.chosen_max_symptoms
|
||||
disease_event.chosen_max_symptoms = null
|
||||
else
|
||||
if(!max_symptoms)
|
||||
max_symptoms = 3 + max(FLOOR((world.time - control.earliest_start)/6000, 1),0) //3 symptoms at 20 minutes, plus 1 per 10 minutes.
|
||||
max_symptoms = clamp(max_symptoms, 3, 8) //Capping the virus symptoms prevents the event from becoming "smite one poor player with an -12 transmission hell virus" after a certain round length.
|
||||
|
||||
if(disease_event.chosen_severity)
|
||||
max_severity = disease_event.chosen_severity
|
||||
disease_event.chosen_severity = null
|
||||
else
|
||||
if(!max_severity)
|
||||
max_severity = 3 + max(FLOOR((world.time - control.earliest_start)/6000, 1),0) //Max severity doesn't need clamping
|
||||
|
||||
var/datum/disease/advance/advanced_disease = new /datum/disease/advance/random(max_symptoms, max_severity)
|
||||
@@ -162,3 +117,47 @@
|
||||
announce_to_ghosts(victim)
|
||||
else
|
||||
log_game("An event attempted to trigger a random advanced virus outbreak on [key_name(victim)], but failed.")
|
||||
|
||||
/datum/event_admin_setup/disease_outbreak
|
||||
///Admin selected disease, to be passed down to the round_event
|
||||
var/virus_type
|
||||
|
||||
/// Checks for candidates. Returns false if there isn't enough
|
||||
/datum/event_admin_setup/disease_outbreak/proc/candidate_check()
|
||||
var/datum/round_event_control/disease_outbreak/disease_control = event_control
|
||||
disease_control.generate_candidates() //can_spawn_event() is bypassed by admin_setup, so this makes sure that the candidates are still generated
|
||||
return length(disease_control.disease_candidates)
|
||||
|
||||
/datum/event_admin_setup/disease_outbreak/prompt_admins()
|
||||
var/candidate_count = candidate_check()
|
||||
if(!candidate_check())
|
||||
tgui_alert(usr, "There are no candidates eligible to recieve a disease!", "Error")
|
||||
return ADMIN_CANCEL_EVENT
|
||||
tgui_alert(usr, "[candidate_count] candidates found!", "Disease Outbreak")
|
||||
|
||||
if(tgui_alert(usr, "Select a specific disease?", "Sickening behavior", list("Yes", "No")) == "Yes")
|
||||
virus_type = tgui_input_list(usr, "Warning: Some of these are EXTREMELY dangerous.","Bacteria Hysteria", subtypesof(/datum/disease))
|
||||
|
||||
/datum/event_admin_setup/disease_outbreak/apply_to_event(datum/round_event/disease_outbreak/event)
|
||||
event.virus_type = virus_type
|
||||
|
||||
/datum/event_admin_setup/disease_outbreak/advanced
|
||||
///Admin selected custom severity rating for the event
|
||||
var/max_severity
|
||||
///Admin selected custom value for the maximum symptoms this virus should have
|
||||
var/max_symptoms
|
||||
|
||||
/datum/event_admin_setup/disease_outbreak/advanced/prompt_admins()
|
||||
var/candidate_count = candidate_check()
|
||||
if(!candidate_check())
|
||||
tgui_alert(usr, "There are no candidates eligible to recieve a disease!", "Error")
|
||||
return ADMIN_CANCEL_EVENT
|
||||
tgui_alert(usr, "[candidate_count] candidates found!", "Disease Outbreak")
|
||||
|
||||
if(tgui_alert(usr,"Customize your virus?", "Glorified Debug Tool", list("Yes", "No")) == "Yes")
|
||||
max_severity = tgui_input_number(usr, "Select a custom severity for your virus!", "Plague Incorporation!", 3, 8)
|
||||
max_symptoms = tgui_input_number(usr, "How many symptoms do you want your virus to have?", "A pox upon ye!", 3, 15)
|
||||
|
||||
/datum/event_admin_setup/disease_outbreak/advanced/apply_to_event(datum/round_event/disease_outbreak/advanced/event)
|
||||
event.max_severity = max_severity
|
||||
event.max_symptoms = max_symptoms
|
||||
|
||||
@@ -3,23 +3,9 @@
|
||||
typepath = /datum/round_event/falsealarm
|
||||
weight = 20
|
||||
max_occurrences = 5
|
||||
var/forced_type //Admin abuse
|
||||
category = EVENT_CATEGORY_BUREAUCRATIC
|
||||
description = "Fakes an event announcement."
|
||||
|
||||
/datum/round_event_control/falsealarm/admin_setup(mob/admin)
|
||||
if(!check_rights(R_FUN))
|
||||
return
|
||||
|
||||
var/list/possible_types = list()
|
||||
|
||||
for(var/datum/round_event_control/E in SSevents.control)
|
||||
var/datum/round_event/event = E.typepath
|
||||
if(!initial(event.fakeable))
|
||||
continue
|
||||
possible_types += E
|
||||
|
||||
forced_type = input(usr, "Select the scare.","False event") as null|anything in sort_names(possible_types)
|
||||
admin_setup = /datum/event_admin_setup/listed_options/false_alarm
|
||||
|
||||
/datum/round_event_control/falsealarm/can_spawn_event(players_amt)
|
||||
. = ..()
|
||||
@@ -34,6 +20,8 @@
|
||||
announce_when = 0
|
||||
end_when = 1
|
||||
fakeable = FALSE
|
||||
/// Admin's pick of fake event (wow! you picked blob!! you're so creative and smart!)
|
||||
var/forced_type
|
||||
|
||||
/datum/round_event/falsealarm/announce(fake)
|
||||
if(fake) //What are you doing
|
||||
@@ -42,10 +30,8 @@
|
||||
|
||||
var/events_list = gather_false_events(players_amt)
|
||||
var/datum/round_event_control/event_control
|
||||
var/datum/round_event_control/falsealarm/C = control
|
||||
if(C.forced_type)
|
||||
event_control = C.forced_type
|
||||
C.forced_type = null
|
||||
if(forced_type)
|
||||
event_control = forced_type
|
||||
else
|
||||
event_control = pick(events_list)
|
||||
if(event_control)
|
||||
@@ -66,3 +52,18 @@
|
||||
if(!initial(event.fakeable))
|
||||
continue
|
||||
. += E
|
||||
|
||||
/datum/event_admin_setup/listed_options/false_alarm
|
||||
normal_run_option = "Random Fake Event"
|
||||
|
||||
/datum/event_admin_setup/listed_options/false_alarm/get_list()
|
||||
var/list/possible_types = list()
|
||||
for(var/datum/round_event_control/event_control in SSevents.control)
|
||||
var/datum/round_event/event = event_control.typepath
|
||||
if(!initial(event.fakeable))
|
||||
continue
|
||||
possible_types += event_control
|
||||
return possible_types
|
||||
|
||||
/datum/event_admin_setup/listed_options/false_alarm/apply_to_event(datum/round_event/falsealarm/event)
|
||||
event.forced_type = chosen
|
||||
|
||||
@@ -6,10 +6,9 @@
|
||||
min_players = 40 // To avoid shafting lowpop
|
||||
category = EVENT_CATEGORY_HEALTH
|
||||
description = "A random crewmember's heart gives out."
|
||||
admin_setup = /datum/event_admin_setup/heart_attack
|
||||
///Candidates for recieving a healthy dose of heart disease
|
||||
var/list/heart_attack_candidates = list()
|
||||
///Number of candidates to be smote
|
||||
var/quantity = 1
|
||||
|
||||
/datum/round_event_control/heart_attack/can_spawn_event(players_amt)
|
||||
. = ..()
|
||||
@@ -19,17 +18,6 @@
|
||||
if(length(heart_attack_candidates))
|
||||
return TRUE
|
||||
|
||||
/datum/round_event_control/heart_attack/admin_setup()
|
||||
if(!check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
generate_candidates() //can_spawn_event() is bypassed by admin_setup, so this makes sure that the candidates are still generated
|
||||
|
||||
if(!length(heart_attack_candidates))
|
||||
message_admins("There are no candidates eligible to recieve a heart attack!")
|
||||
return ADMIN_CANCEL_EVENT
|
||||
quantity = tgui_input_number(usr, "There are [length(heart_attack_candidates)] crewmembers eligible for a heart attack. Please select how many people's days you wish to ruin.", "Shia Hato Atakku!", 1, length(heart_attack_candidates))
|
||||
|
||||
/**
|
||||
* Performs initial analysis of which living players are eligible to be selected for a heart attack.
|
||||
*
|
||||
@@ -52,19 +40,17 @@
|
||||
///A list of prime candidates for heart attacking
|
||||
var/list/victims = list()
|
||||
///Number of heart attacks to distribute
|
||||
var/attacks_left = 1
|
||||
var/quantity = 1
|
||||
|
||||
|
||||
/datum/round_event/heart_attack/start()
|
||||
var/datum/round_event_control/heart_attack/heart_attack_event = control
|
||||
var/datum/round_event_control/heart_attack/heart_control = control
|
||||
victims += heart_control.heart_attack_candidates
|
||||
heart_control.heart_attack_candidates.Cut()
|
||||
|
||||
attacks_left = heart_attack_event.quantity
|
||||
victims += heart_attack_event.heart_attack_candidates
|
||||
heart_attack_event.heart_attack_candidates.Cut()
|
||||
heart_attack_event.quantity = 1
|
||||
|
||||
while(attacks_left > 0 && length(victims))
|
||||
while(quantity > 0 && length(victims))
|
||||
if(attack_heart())
|
||||
attacks_left--
|
||||
quantity--
|
||||
|
||||
/**
|
||||
* Picks a victim from a list and attempts to give them a heart attack
|
||||
@@ -91,3 +77,19 @@
|
||||
victims -= winner
|
||||
return TRUE
|
||||
return FALSE
|
||||
|
||||
/datum/event_admin_setup/heart_attack
|
||||
///Number of candidates to be smote
|
||||
var/quantity = 1
|
||||
|
||||
/datum/event_admin_setup/heart_attack/prompt_admins()
|
||||
var/datum/round_event_control/heart_attack/heart_control = event_control
|
||||
heart_control.generate_candidates() //can_spawn_event() is bypassed by admin_setup, so this makes sure that the candidates are still generated
|
||||
|
||||
if(!length(heart_control.heart_attack_candidates))
|
||||
tgui_alert(usr, "There are no candidates eligible to recieve a heart attack!", "Error")
|
||||
return ADMIN_CANCEL_EVENT
|
||||
quantity = tgui_input_number(usr, "There are [length(heart_control.heart_attack_candidates)] crewmembers eligible for a heart attack. Please select how many people's days you wish to ruin.", "Shia Hato Atakku!", 1, length(heart_control.heart_attack_candidates))
|
||||
|
||||
/datum/event_admin_setup/heart_attack/apply_to_event(datum/round_event/heart_attack/event)
|
||||
event.quantity = quantity
|
||||
|
||||
+1
-48
@@ -1,51 +1,4 @@
|
||||
/*
|
||||
Immovable rod random event.
|
||||
The rod will spawn at some location outside the station, and travel in a straight line to the opposite side of the station
|
||||
Everything solid in the way will be ex_act()'d
|
||||
In my current plan for it, 'solid' will be defined as anything with density == 1
|
||||
|
||||
--NEOFite
|
||||
*/
|
||||
|
||||
/datum/round_event_control/immovable_rod
|
||||
name = "Immovable Rod"
|
||||
typepath = /datum/round_event/immovable_rod
|
||||
min_players = 15
|
||||
max_occurrences = 5
|
||||
var/atom/special_target
|
||||
var/force_looping = FALSE
|
||||
category = EVENT_CATEGORY_SPACE
|
||||
description = "The station passes through an immovable rod."
|
||||
|
||||
/datum/round_event_control/immovable_rod/admin_setup(mob/admin)
|
||||
if(!check_rights(R_FUN))
|
||||
return
|
||||
|
||||
var/aimed = tgui_alert(usr,"Aimed at current location?", "Sniperod", list("Yes", "No"))
|
||||
if(aimed == "Yes")
|
||||
special_target = get_turf(usr)
|
||||
var/looper = tgui_alert(usr,"Would you like this rod to force-loop across space z-levels?", "Loopy McLoopface", list("Yes", "No"))
|
||||
if(looper == "Yes")
|
||||
force_looping = TRUE
|
||||
message_admins("[key_name_admin(usr)] has aimed an immovable rod [force_looping ? "(forced looping)" : ""] at [AREACOORD(special_target)].")
|
||||
log_admin("[key_name_admin(usr)] has aimed an immovable rod [force_looping ? "(forced looping)" : ""] at [AREACOORD(special_target)].")
|
||||
|
||||
/datum/round_event/immovable_rod
|
||||
announce_when = 5
|
||||
|
||||
/datum/round_event/immovable_rod/announce(fake)
|
||||
priority_announce("What the fuck was that?!", "General Alert")
|
||||
|
||||
/datum/round_event/immovable_rod/start()
|
||||
var/datum/round_event_control/immovable_rod/our_controller = control
|
||||
var/startside = pick(GLOB.cardinals)
|
||||
var/turf/end_turf = get_edge_target_turf(get_random_station_turf(), turn(startside, 180))
|
||||
var/turf/start_turf = spaceDebrisStartLoc(startside, end_turf.z)
|
||||
var/atom/rod = new /obj/effect/immovablerod(start_turf, end_turf, our_controller.special_target, our_controller.force_looping)
|
||||
our_controller.special_target = null //Cleanup for future event rolls.
|
||||
our_controller.force_looping = FALSE
|
||||
announce_to_ghosts(rod)
|
||||
|
||||
/// "What the fuck was that?!"
|
||||
/obj/effect/immovablerod
|
||||
name = "immovable rod"
|
||||
desc = "What the fuck is that?"
|
||||
@@ -0,0 +1,47 @@
|
||||
/// Immovable rod random event.
|
||||
/// The rod will spawn at some location outside the station, and travel in a straight line to the opposite side of the station
|
||||
/datum/round_event_control/immovable_rod
|
||||
name = "Immovable Rod"
|
||||
typepath = /datum/round_event/immovable_rod
|
||||
min_players = 15
|
||||
max_occurrences = 5
|
||||
category = EVENT_CATEGORY_SPACE
|
||||
description = "The station passes through an immovable rod."
|
||||
admin_setup = /datum/event_admin_setup/immovable_rod
|
||||
|
||||
/datum/round_event/immovable_rod
|
||||
announce_when = 5
|
||||
/// Admins can pick a spot the rod will aim for.
|
||||
var/atom/special_target
|
||||
/// Admins can also force it to loop around forever, or at least until the RD gets their hands on it.
|
||||
var/force_looping = FALSE
|
||||
|
||||
/datum/round_event/immovable_rod/announce(fake)
|
||||
priority_announce("What the fuck was that?!", "General Alert")
|
||||
|
||||
/datum/round_event/immovable_rod/start()
|
||||
var/startside = pick(GLOB.cardinals)
|
||||
var/turf/end_turf = get_edge_target_turf(get_random_station_turf(), turn(startside, 180))
|
||||
var/turf/start_turf = spaceDebrisStartLoc(startside, end_turf.z)
|
||||
var/atom/rod = new /obj/effect/immovablerod(start_turf, end_turf, special_target, force_looping)
|
||||
announce_to_ghosts(rod)
|
||||
|
||||
/datum/event_admin_setup/immovable_rod
|
||||
/// Admins can pick a spot the rod will aim for.
|
||||
var/atom/special_target
|
||||
/// Admins can also force it to loop around forever, or at least until the RD gets their hands on it.
|
||||
var/force_looping = FALSE
|
||||
|
||||
/datum/event_admin_setup/immovable_rod/prompt_admins()
|
||||
var/aimed = tgui_alert(usr,"Aimed at current location?", "Sniperod", list("Yes", "No"))
|
||||
if(aimed == "Yes")
|
||||
special_target = get_turf(usr)
|
||||
var/looper = tgui_alert(usr,"Would you like this rod to force-loop across space z-levels?", "Loopy McLoopface", list("Yes", "No"))
|
||||
if(looper == "Yes")
|
||||
force_looping = TRUE
|
||||
message_admins("[key_name_admin(usr)] has aimed an immovable rod [force_looping ? "(forced looping)" : ""] at [AREACOORD(special_target)].")
|
||||
log_admin("[key_name_admin(usr)] has aimed an immovable rod [force_looping ? "(forced looping)" : ""] at [AREACOORD(special_target)].")
|
||||
|
||||
/datum/event_admin_setup/immovable_rod/apply_to_event(datum/round_event/immovable_rod/event)
|
||||
event.special_target = special_target
|
||||
event.force_looping = force_looping
|
||||
@@ -6,71 +6,36 @@
|
||||
max_occurrences = 2
|
||||
min_players = 1
|
||||
category = EVENT_CATEGORY_HEALTH
|
||||
admin_setup = /datum/event_admin_setup/mass_hallucination
|
||||
|
||||
/datum/round_event/mass_hallucination
|
||||
fakeable = FALSE
|
||||
/// For admins, what hallucination did we pick
|
||||
var/admin_forced_hallucination
|
||||
/// For admins, what arguments are we passing to said hallucination
|
||||
var/list/admin_forced_args
|
||||
|
||||
/datum/round_event_control/mass_hallucination/admin_setup(mob/admin)
|
||||
if(!check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
var/force = tgui_alert(usr, "Do you want to force a hallucination?", name, list("Yes", "No", "Cancel"))
|
||||
if(force == "Cancel")
|
||||
return ADMIN_CANCEL_EVENT
|
||||
if(force != "Yes")
|
||||
return
|
||||
|
||||
var/force_what = tgui_alert(usr, "Generic hallucination or Custom configured delusion? (Delusions are those which make people appear as other mobs)", name, list("Hallucination", "Custom Delusion", "Cancel"))
|
||||
switch(force_what)
|
||||
if("Cancel")
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
if("Hallucination")
|
||||
var/chosen = select_hallucination_type(admin, "What hallucination should be forced for [name]?", name)
|
||||
if(!chosen || !check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
admin_forced_hallucination = chosen
|
||||
|
||||
if("Custom Delusion")
|
||||
var/list/chosen_args = create_delusion(admin)
|
||||
if(!length(chosen_args) || !check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
admin_forced_hallucination = chosen_args[1]
|
||||
admin_forced_args = chosen_args.Copy(3)
|
||||
|
||||
/datum/round_event/mass_hallucination
|
||||
fakeable = FALSE
|
||||
|
||||
/datum/round_event/mass_hallucination/start()
|
||||
var/datum/round_event_control/mass_hallucination/our_controller = control
|
||||
|
||||
var/picked_hallucination = our_controller?.admin_forced_hallucination
|
||||
var/list/other_args = our_controller?.admin_forced_args
|
||||
|
||||
if(!picked_hallucination)
|
||||
if(!admin_forced_hallucination)
|
||||
var/category_to_pick_from = rand(1, 10)
|
||||
switch(category_to_pick_from)
|
||||
if(1)
|
||||
// Send the same sound to everyone
|
||||
picked_hallucination = get_random_valid_hallucination_subtype(/datum/hallucination/fake_sound/normal)
|
||||
admin_forced_hallucination = get_random_valid_hallucination_subtype(/datum/hallucination/fake_sound/normal)
|
||||
|
||||
if(2)
|
||||
// Send the same sound to everyone, but weird
|
||||
picked_hallucination = get_random_valid_hallucination_subtype(/datum/hallucination/fake_sound/weird)
|
||||
admin_forced_hallucination = get_random_valid_hallucination_subtype(/datum/hallucination/fake_sound/weird)
|
||||
|
||||
if(3)
|
||||
// Send the same message to everyone
|
||||
picked_hallucination = get_random_valid_hallucination_subtype(/datum/hallucination/station_message)
|
||||
admin_forced_hallucination = get_random_valid_hallucination_subtype(/datum/hallucination/station_message)
|
||||
|
||||
if(4)
|
||||
// Send the same delusion to everyone, but...
|
||||
picked_hallucination = get_random_valid_hallucination_subtype(/datum/hallucination/delusion/preset)
|
||||
admin_forced_hallucination = get_random_valid_hallucination_subtype(/datum/hallucination/delusion/preset)
|
||||
// The delusion will affect everyone BUT the hallucinator.
|
||||
other_args = list(
|
||||
admin_forced_args = list(
|
||||
duration = 30 SECONDS,
|
||||
skip_nearby = FALSE,
|
||||
affects_us = FALSE,
|
||||
@@ -80,9 +45,9 @@
|
||||
|
||||
if(5)
|
||||
// Send the same delusion to everyone, but...
|
||||
picked_hallucination = get_random_valid_hallucination_subtype(/datum/hallucination/delusion/preset)
|
||||
admin_forced_hallucination = get_random_valid_hallucination_subtype(/datum/hallucination/delusion/preset)
|
||||
// The delusion will affect only the hallucinator.
|
||||
other_args = list(
|
||||
admin_forced_args = list(
|
||||
duration = 45 SECONDS,
|
||||
skip_nearby = FALSE,
|
||||
affects_us = TRUE,
|
||||
@@ -103,14 +68,14 @@
|
||||
/datum/hallucination/xeno_attack,
|
||||
)
|
||||
|
||||
picked_hallucination = pick(generic_hallucinations)
|
||||
admin_forced_hallucination = pick(generic_hallucinations)
|
||||
|
||||
if(!picked_hallucination)
|
||||
CRASH("[type] couldn't find a hallucination to play. (Got: [picked_hallucination], Picked category: [category_to_pick_from])")
|
||||
if(!admin_forced_hallucination)
|
||||
CRASH("[type] couldn't find a hallucination to play. (Got: [admin_forced_hallucination], Picked category: [category_to_pick_from])")
|
||||
|
||||
var/list/hallucination_args = list(picked_hallucination, "mass hallucination")
|
||||
if(islist(other_args))
|
||||
hallucination_args += other_args
|
||||
var/list/hallucination_args = list(admin_forced_hallucination, "mass hallucination")
|
||||
if(islist(admin_forced_args))
|
||||
hallucination_args += admin_forced_args
|
||||
|
||||
// We'll only hallucinate for carbons now, even though livings can hallucinate just fine in most cases.
|
||||
for(var/mob/living/carbon/hallucinating as anything in GLOB.carbon_list)
|
||||
@@ -129,7 +94,39 @@
|
||||
// Not using the wrapper here because we already have a list / arglist
|
||||
hallucinating._cause_hallucination(hallucination_args)
|
||||
|
||||
/datum/round_event/mass_hallucination/end()
|
||||
var/datum/round_event_control/mass_hallucination/our_controller = control
|
||||
our_controller.admin_forced_hallucination = null
|
||||
our_controller.admin_forced_args = null
|
||||
/datum/event_admin_setup/mass_hallucination
|
||||
/// For admins, what hallucination did we pick
|
||||
var/admin_forced_hallucination
|
||||
/// For admins, what arguments are we passing to said hallucination
|
||||
var/list/admin_forced_args
|
||||
|
||||
/datum/event_admin_setup/mass_hallucination/prompt_admins()
|
||||
var/force = tgui_alert(usr, "Do you want to force a hallucination?", event_control.name, list("Yes", "No", "Cancel"))
|
||||
if(force == "Cancel")
|
||||
return ADMIN_CANCEL_EVENT
|
||||
if(force != "Yes")
|
||||
return
|
||||
|
||||
var/force_what = tgui_alert(usr, "Generic hallucination or Custom configured delusion? (Delusions are those which make people appear as other mobs)", event_control.name, list("Hallucination", "Custom Delusion", "Cancel"))
|
||||
switch(force_what)
|
||||
if("Cancel")
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
if("Hallucination")
|
||||
var/chosen = select_hallucination_type(usr, "What hallucination should be forced for [event_control.name]?", event_control.name)
|
||||
if(!chosen || !check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
admin_forced_hallucination = chosen
|
||||
|
||||
if("Custom Delusion")
|
||||
var/list/chosen_args = create_delusion(usr)
|
||||
if(!length(chosen_args) || !check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
admin_forced_hallucination = chosen_args[HALLUCINATION_ARG_TYPE]
|
||||
admin_forced_args = chosen_args.Copy(HALLUCINATION_ARGLIST)
|
||||
|
||||
/datum/event_admin_setup/mass_hallucination/apply_to_event(datum/round_event/mass_hallucination/event)
|
||||
event.admin_forced_hallucination = admin_forced_hallucination
|
||||
event.admin_forced_args = admin_forced_args
|
||||
|
||||
@@ -15,24 +15,7 @@
|
||||
earliest_start = 35 MINUTES
|
||||
category = EVENT_CATEGORY_SPACE
|
||||
description = "A wave of space dust continually grinds down a side of the station."
|
||||
///Where will the sandstorm be coming from -- Established in admin_setup, passed down to round_event
|
||||
var/start_side
|
||||
|
||||
/datum/round_event_control/sandstorm/admin_setup()
|
||||
if(!check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
if(tgui_alert(usr, "Choose a side to powersand?", "I hate sand.", list("Yes", "No")) == "Yes")
|
||||
var/chosen_direction = tgui_input_list(usr, "Pick one!","Rough, gets everywhere, coarse, etc.", list("Up", "Down", "Right", "Left"))
|
||||
switch(chosen_direction)
|
||||
if("Up")
|
||||
start_side = NORTH
|
||||
if("Down")
|
||||
start_side = SOUTH
|
||||
if("Right")
|
||||
start_side = EAST
|
||||
if("Left")
|
||||
start_side = WEST
|
||||
admin_setup = /datum/event_admin_setup/listed_options/sandstorm
|
||||
|
||||
/datum/round_event/sandstorm
|
||||
start_when = 60
|
||||
@@ -46,10 +29,7 @@
|
||||
end_when = rand(110, 140)
|
||||
|
||||
/datum/round_event/sandstorm/announce(fake)
|
||||
var/datum/round_event_control/sandstorm/sandstorm_event = control
|
||||
if(sandstorm_event.start_side)
|
||||
start_side = sandstorm_event.start_side
|
||||
else
|
||||
if(!start_side)
|
||||
start_side = pick(GLOB.cardinals)
|
||||
|
||||
var/start_side_text = "unknown"
|
||||
@@ -98,3 +78,21 @@
|
||||
|
||||
/datum/round_event/sandstorm_classic/tick()
|
||||
spawn_meteors(10, GLOB.meteors_dust)
|
||||
|
||||
/datum/event_admin_setup/listed_options/sandstorm
|
||||
input_text = "Choose a side to powersand?"
|
||||
normal_run_option = "Random Sandstorm Direction"
|
||||
|
||||
/datum/event_admin_setup/listed_options/sandstorm/get_list()
|
||||
return list("Up", "Down", "Right", "Left")
|
||||
|
||||
/datum/event_admin_setup/listed_options/sandstorm/apply_to_event(datum/round_event/sandstorm/event)
|
||||
switch(chosen)
|
||||
if("Up")
|
||||
event.start_side = NORTH
|
||||
if("Down")
|
||||
event.start_side = SOUTH
|
||||
if("Right")
|
||||
event.start_side = EAST
|
||||
if("Left")
|
||||
event.start_side = WEST
|
||||
|
||||
@@ -6,6 +6,7 @@
|
||||
min_players = 10
|
||||
category = EVENT_CATEGORY_JANITORIAL
|
||||
description = "The scrubbers release a tide of mostly harmless froth."
|
||||
admin_setup = /datum/event_admin_setup/listed_options/scrubber_overflow
|
||||
|
||||
/datum/round_event/scrubber_overflow
|
||||
announce_when = 1
|
||||
@@ -151,13 +152,6 @@
|
||||
/datum/round_event_control/scrubber_overflow/custom/announce_deadchat(random)
|
||||
deadchat_broadcast(" has just been[random ? " randomly" : ""] triggered!", "<b>Scrubber Overflow: [initial(custom_reagent.name)]</b>", message_type=DEADCHAT_ANNOUNCEMENT)
|
||||
|
||||
/datum/round_event_control/scrubber_overflow/custom/admin_setup(mob/admin)
|
||||
if(!check_rights(R_FUN))
|
||||
return
|
||||
custom_reagent = tgui_input_list(usr, "Choose a reagent to flood.", "Choose a reagent.", sort_list(subtypesof(/datum/reagent), /proc/cmp_typepaths_asc))
|
||||
if (isnull(custom_reagent))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
/datum/round_event/scrubber_overflow/custom
|
||||
overflow_probability = 100
|
||||
forced_reagent = /datum/reagent/consumable/ethanol/beer
|
||||
@@ -167,3 +161,12 @@
|
||||
var/datum/round_event_control/scrubber_overflow/custom/event_controller = control
|
||||
forced_reagent = event_controller.custom_reagent
|
||||
return ..()
|
||||
|
||||
/datum/event_admin_setup/listed_options/scrubber_overflow
|
||||
normal_run_option = "Random Reagent"
|
||||
|
||||
/datum/event_admin_setup/listed_options/scrubber_overflow/get_list()
|
||||
return sort_list(subtypesof(/datum/reagent), /proc/cmp_typepaths_asc)
|
||||
|
||||
/datum/event_admin_setup/listed_options/scrubber_overflow/apply_to_event(datum/round_event/scrubber_overflow/event)
|
||||
event.forced_reagent = chosen
|
||||
|
||||
@@ -5,6 +5,7 @@
|
||||
max_occurrences = 1
|
||||
category = EVENT_CATEGORY_BUREAUCRATIC
|
||||
description = "Replaces the emergency shuttle with a random one."
|
||||
admin_setup = /datum/event_admin_setup/warn_admin/shuttle_catastrophe
|
||||
|
||||
/datum/round_event_control/shuttle_catastrophe/can_spawn_event(players)
|
||||
. = ..()
|
||||
@@ -19,13 +20,6 @@
|
||||
return FALSE //don't remove all players when its already on station or going to centcom
|
||||
return TRUE
|
||||
|
||||
/datum/round_event_control/shuttle_catastrophe/admin_setup(mob/admin)
|
||||
if(EMERGENCY_AT_LEAST_DOCKED || istype(SSshuttle.emergency, /obj/docking_port/mobile/emergency/shuttle_build))
|
||||
if(tgui_alert(usr, "WARNING: This will unload the currently docked emergency shuttle, and ERASE ANYTHING within it. Proceed anyways?", "How about a REAL catastrophe?", list("Yes", "No")) == "Yes")
|
||||
message_admins("[admin.ckey] has forced a shuttle catastrophe while a shuttle was already docked.") //Just in case
|
||||
else
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
/datum/round_event/shuttle_catastrophe
|
||||
var/datum/map_template/shuttle/new_shuttle
|
||||
|
||||
@@ -63,3 +57,10 @@
|
||||
SSshuttle.existing_shuttle = SSshuttle.emergency
|
||||
SSshuttle.action_load(new_shuttle, replace = TRUE)
|
||||
log_shuttle("Shuttle Catastrophe set a new shuttle, [new_shuttle.name].")
|
||||
|
||||
/datum/event_admin_setup/warn_admin/shuttle_catastrophe
|
||||
warning_text = "This will unload the currently docked emergency shuttle, and ERASE ANYTHING within it. Proceed anyways?"
|
||||
snitch_text = "has forced a shuttle catastrophe while a shuttle was already docked."
|
||||
|
||||
/datum/event_admin_setup/warn_admin/shuttle_catastrophe/should_warn()
|
||||
return EMERGENCY_AT_LEAST_DOCKED || istype(SSshuttle.emergency, /obj/docking_port/mobile/emergency/shuttle_build)
|
||||
|
||||
@@ -1,345 +0,0 @@
|
||||
#define HIJACK_SYNDIE "syndies"
|
||||
#define RUSKY_PARTY "ruskies"
|
||||
#define SPIDER_GIFT "spiders"
|
||||
#define DEPARTMENT_RESUPPLY "resupplies"
|
||||
#define ANTIDOTE_NEEDED "disease"
|
||||
#define PIZZA_DELIVERY "pizza"
|
||||
#define ITS_HIP_TO "bees"
|
||||
#define MY_GOD_JC "bomb"
|
||||
#define PAPERS_PLEASE "paperwork"
|
||||
|
||||
/datum/round_event_control/shuttle_loan
|
||||
name = "Shuttle Loan"
|
||||
typepath = /datum/round_event/shuttle_loan
|
||||
max_occurrences = 3
|
||||
earliest_start = 7 MINUTES
|
||||
category = EVENT_CATEGORY_BUREAUCRATIC
|
||||
description = "If cargo accepts the offer, fills the shuttle with loot and/or enemies."
|
||||
///The types of loan offers that the crew can recieve.
|
||||
var/list/shuttle_loan_offers = list(
|
||||
ANTIDOTE_NEEDED,
|
||||
DEPARTMENT_RESUPPLY,
|
||||
HIJACK_SYNDIE,
|
||||
ITS_HIP_TO,
|
||||
MY_GOD_JC,
|
||||
PIZZA_DELIVERY,
|
||||
RUSKY_PARTY,
|
||||
SPIDER_GIFT,
|
||||
PAPERS_PLEASE,
|
||||
)
|
||||
///The types of loan events already run (and to be excluded if the event triggers).
|
||||
var/list/run_events = list()
|
||||
///The admin-selected loan offer ID.
|
||||
var/chosen_event
|
||||
|
||||
/datum/round_event_control/shuttle_loan/can_spawn_event(players_amt)
|
||||
. = ..()
|
||||
|
||||
for(var/datum/round_event/running_event in SSevents.running)
|
||||
if(istype(running_event, /datum/round_event/shuttle_loan)) //Make sure two of these don't happen at once.
|
||||
return FALSE
|
||||
|
||||
/datum/round_event_control/shuttle_loan/admin_setup()
|
||||
if(!check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
if(tgui_alert(usr, "Select a loan offer?", "Trade Offer:", list("Yes", "No")) == "Yes")
|
||||
chosen_event = tgui_input_list(usr, "What deal would you like to offer the crew?", "Throw them a bone.", shuttle_loan_offers)
|
||||
|
||||
for(var/datum/round_event/shuttle_loan/loan_event in SSevents.running)
|
||||
loan_event.kill() //Force out the old event for a new one to take its place
|
||||
|
||||
/datum/round_event/shuttle_loan
|
||||
announce_when = 1
|
||||
end_when = 500
|
||||
var/dispatched = FALSE
|
||||
var/dispatch_type = "none"
|
||||
var/bonus_points = 10000
|
||||
var/thanks_msg = "The cargo shuttle should return in five minutes. Have some supply points for your trouble."
|
||||
var/loan_type //for logging
|
||||
|
||||
/datum/round_event/shuttle_loan/setup()
|
||||
|
||||
for(var/datum/round_event_control/shuttle_loan/loan_event_control in SSevents.control) //We can't call control, because it hasn't been set yet
|
||||
if(loan_event_control.chosen_event) //Pass down the admin selection and clean it for future use.
|
||||
dispatch_type = loan_event_control.chosen_event
|
||||
loan_event_control.chosen_event = null
|
||||
else //Otherwise, generate and pick from the list of offerable offers.
|
||||
var/list/loan_list = list()
|
||||
loan_list += loan_event_control.shuttle_loan_offers
|
||||
var/list/run_events = loan_event_control.run_events //Ask the round_event_control which loans have already been offered
|
||||
loan_list -= run_events //Remove the already offered loans from the candidate list
|
||||
if(!length(loan_list)) //If we somehow run out of loans, they all become available again
|
||||
loan_list += loan_event_control.shuttle_loan_offers
|
||||
run_events.Cut()
|
||||
dispatch_type = pick(loan_list) //Pick a loan to offer
|
||||
loan_event_control.run_events += dispatch_type //Regardless of admin selection, we add the event being run to the run_events list
|
||||
|
||||
/datum/round_event/shuttle_loan/announce(fake)
|
||||
SSshuttle.shuttle_loan = src
|
||||
switch(dispatch_type)
|
||||
if(HIJACK_SYNDIE)
|
||||
priority_announce("Cargo: The syndicate are trying to infiltrate your station. If you let them hijack your cargo shuttle, you'll save us a headache.","CentCom Counterintelligence")
|
||||
if(RUSKY_PARTY)
|
||||
priority_announce("Cargo: A group of angry Russians want to have a party. Can you send them your cargo shuttle then make them disappear?","CentCom Russian Outreach Program")
|
||||
if(SPIDER_GIFT)
|
||||
priority_announce("Cargo: The Spider Clan has sent us a mysterious gift. Can we ship it to you to see what's inside?","CentCom Diplomatic Corps")
|
||||
if(DEPARTMENT_RESUPPLY)
|
||||
priority_announce("Cargo: Seems we've ordered doubles of our department resupply packages this month. Can we send them to you?","CentCom Supply Department")
|
||||
thanks_msg = "The cargo shuttle should return in five minutes."
|
||||
bonus_points = 0
|
||||
if(ANTIDOTE_NEEDED)
|
||||
priority_announce("Cargo: Your station has been chosen for an epidemiological research project. Send us your cargo shuttle to receive your research samples.", "CentCom Research Initiatives")
|
||||
if(PIZZA_DELIVERY)
|
||||
priority_announce("Cargo: It looks like a neighbouring station accidentally delivered their pizza to you instead.", "CentCom Spacepizza Division")
|
||||
thanks_msg = "The cargo shuttle should return in five minutes."
|
||||
bonus_points = 0
|
||||
if(ITS_HIP_TO)
|
||||
priority_announce("Cargo: One of our freighters carrying a bee shipment has been attacked by eco-terrorists. Can you clean up the mess for us?", "CentCom Janitorial Division")
|
||||
bonus_points = 20000 //Toxin bees can be unbeelievably lethal
|
||||
if(MY_GOD_JC)
|
||||
priority_announce("Cargo: We have discovered an active Syndicate bomb near our VIP shuttle's fuel lines. If you feel up to the task, we will pay you for defusing it.", "CentCom Security Division")
|
||||
thanks_msg = "Live explosive ordnance incoming via supply shuttle. Evacuating cargo bay is recommended."
|
||||
bonus_points = 45000 //If you mess up, people die and the shuttle gets turned into swiss cheese
|
||||
if(PAPERS_PLEASE)
|
||||
priority_announce("Cargo: A neighboring station needs some help handling some paperwork. Could you help process it for us?", "CentCom Paperwork Division")
|
||||
thanks_msg = "The cargo shuttle should return in five minutes. Payment will be rendered when the paperwork is processed and returned."
|
||||
bonus_points = 0 //Payout is made when the stamped papers are returned
|
||||
else
|
||||
log_game("Shuttle Loan event could not find [dispatch_type] event to offer.")
|
||||
kill()
|
||||
return
|
||||
|
||||
/datum/round_event/shuttle_loan/proc/loan_shuttle()
|
||||
priority_announce(thanks_msg, "Cargo shuttle commandeered by CentCom.")
|
||||
|
||||
dispatched = TRUE
|
||||
var/datum/bank_account/D = SSeconomy.get_dep_account(ACCOUNT_CAR)
|
||||
if(D)
|
||||
D.adjust_money(bonus_points)
|
||||
end_when = activeFor + 1
|
||||
|
||||
SSshuttle.supply.mode = SHUTTLE_CALL
|
||||
SSshuttle.supply.destination = SSshuttle.getDock("cargo_home")
|
||||
SSshuttle.supply.setTimer(3000)
|
||||
|
||||
switch(dispatch_type)
|
||||
if(HIJACK_SYNDIE)
|
||||
SSshuttle.centcom_message += "Syndicate hijack team incoming."
|
||||
loan_type = "Syndicate boarding party"
|
||||
if(RUSKY_PARTY)
|
||||
SSshuttle.centcom_message += "Partying Russians incoming."
|
||||
loan_type = "Russian party squad"
|
||||
if(SPIDER_GIFT)
|
||||
SSshuttle.centcom_message += "Spider Clan gift incoming."
|
||||
loan_type = "Shuttle full of spiders"
|
||||
if(DEPARTMENT_RESUPPLY)
|
||||
SSshuttle.centcom_message += "Department resupply incoming."
|
||||
loan_type = "Resupply packages"
|
||||
if(ANTIDOTE_NEEDED)
|
||||
SSshuttle.centcom_message += "Virus samples incoming."
|
||||
loan_type = "Virus shuttle"
|
||||
if(PIZZA_DELIVERY)
|
||||
SSshuttle.centcom_message += "Pizza delivery for [station_name()]"
|
||||
loan_type = "Pizza delivery"
|
||||
if(ITS_HIP_TO)
|
||||
SSshuttle.centcom_message += "Biohazard cleanup incoming."
|
||||
loan_type = "Shuttle full of bees"
|
||||
if(MY_GOD_JC)
|
||||
SSshuttle.centcom_message += "Live explosive ordnance incoming. Exercise extreme caution."
|
||||
loan_type = "Shuttle with a ticking bomb"
|
||||
if(PAPERS_PLEASE)
|
||||
SSshuttle.centcom_message += "Paperwork incoming."
|
||||
loan_type = "Paperwork shipment"
|
||||
|
||||
log_game("Shuttle loan event firing with type '[loan_type]'.")
|
||||
|
||||
/datum/round_event/shuttle_loan/tick()
|
||||
if(dispatched)
|
||||
if(SSshuttle.supply.mode != SHUTTLE_IDLE)
|
||||
end_when = activeFor
|
||||
else
|
||||
end_when = activeFor + 1
|
||||
|
||||
/datum/round_event/shuttle_loan/end()
|
||||
if(SSshuttle.shuttle_loan && SSshuttle.shuttle_loan.dispatched)
|
||||
//make sure the shuttle was dispatched in time
|
||||
SSshuttle.shuttle_loan = null
|
||||
|
||||
var/list/empty_shuttle_turfs = list()
|
||||
var/list/area/shuttle/shuttle_areas = SSshuttle.supply.shuttle_areas
|
||||
for(var/place in shuttle_areas)
|
||||
var/area/shuttle/shuttle_area = place
|
||||
for(var/turf/open/floor/T in shuttle_area)
|
||||
if(T.is_blocked_turf())
|
||||
continue
|
||||
empty_shuttle_turfs += T
|
||||
if(!empty_shuttle_turfs.len)
|
||||
return
|
||||
|
||||
var/list/shuttle_spawns = list()
|
||||
switch(dispatch_type)
|
||||
if(HIJACK_SYNDIE)
|
||||
var/datum/supply_pack/pack = SSshuttle.supply_packs[/datum/supply_pack/emergency/specialops]
|
||||
pack.generate(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
shuttle_spawns.Add(/mob/living/basic/syndicate/ranged/infiltrator)
|
||||
shuttle_spawns.Add(/mob/living/basic/syndicate/ranged/infiltrator)
|
||||
if(prob(75))
|
||||
shuttle_spawns.Add(/mob/living/basic/syndicate/ranged/infiltrator)
|
||||
if(prob(50))
|
||||
shuttle_spawns.Add(/mob/living/basic/syndicate/ranged/infiltrator)
|
||||
|
||||
if(RUSKY_PARTY)
|
||||
var/datum/supply_pack/pack = SSshuttle.supply_packs[/datum/supply_pack/service/party]
|
||||
pack.generate(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
shuttle_spawns.Add(/mob/living/simple_animal/hostile/russian)
|
||||
shuttle_spawns.Add(/mob/living/simple_animal/hostile/russian/ranged) //drops a mateba
|
||||
shuttle_spawns.Add(/mob/living/simple_animal/hostile/bear/russian)
|
||||
if(prob(75))
|
||||
shuttle_spawns.Add(/mob/living/simple_animal/hostile/russian)
|
||||
if(prob(50))
|
||||
shuttle_spawns.Add(/mob/living/simple_animal/hostile/bear/russian)
|
||||
|
||||
if(SPIDER_GIFT)
|
||||
var/datum/supply_pack/pack = SSshuttle.supply_packs[/datum/supply_pack/emergency/specialops]
|
||||
pack.generate(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
shuttle_spawns.Add(/mob/living/simple_animal/hostile/giant_spider)
|
||||
shuttle_spawns.Add(/mob/living/simple_animal/hostile/giant_spider)
|
||||
shuttle_spawns.Add(/mob/living/simple_animal/hostile/giant_spider/nurse)
|
||||
if(prob(50))
|
||||
shuttle_spawns.Add(/mob/living/simple_animal/hostile/giant_spider/hunter)
|
||||
|
||||
var/turf/T = pick_n_take(empty_shuttle_turfs)
|
||||
|
||||
new /obj/effect/decal/remains/human(T)
|
||||
new /obj/item/clothing/shoes/jackboots/fast(T)
|
||||
new /obj/item/clothing/mask/balaclava(T)
|
||||
|
||||
for(var/i in 1 to 5)
|
||||
T = pick_n_take(empty_shuttle_turfs)
|
||||
new /obj/structure/spider/stickyweb(T)
|
||||
|
||||
if(ANTIDOTE_NEEDED)
|
||||
var/obj/effect/mob_spawn/corpse/human/assistant/infected_assistant = pick(/obj/effect/mob_spawn/corpse/human/assistant/beesease_infection, /obj/effect/mob_spawn/corpse/human/assistant/brainrot_infection, /obj/effect/mob_spawn/corpse/human/assistant/spanishflu_infection)
|
||||
var/turf/T
|
||||
for(var/i in 1 to 10)
|
||||
if(prob(15))
|
||||
shuttle_spawns.Add(/obj/item/reagent_containers/cup/bottle)
|
||||
else if(prob(15))
|
||||
shuttle_spawns.Add(/obj/item/reagent_containers/syringe)
|
||||
else if(prob(25))
|
||||
shuttle_spawns.Add(/obj/item/shard)
|
||||
T = pick_n_take(empty_shuttle_turfs)
|
||||
new infected_assistant(T)
|
||||
shuttle_spawns.Add(/obj/structure/closet/crate)
|
||||
shuttle_spawns.Add(/obj/item/reagent_containers/cup/bottle/pierrot_throat)
|
||||
shuttle_spawns.Add(/obj/item/reagent_containers/cup/bottle/magnitis)
|
||||
|
||||
if(DEPARTMENT_RESUPPLY)
|
||||
var/list/crate_types = list(
|
||||
/datum/supply_pack/emergency/equipment,
|
||||
/datum/supply_pack/security/supplies,
|
||||
/datum/supply_pack/organic/food,
|
||||
/datum/supply_pack/emergency/weedcontrol,
|
||||
/datum/supply_pack/engineering/tools,
|
||||
/datum/supply_pack/engineering/engiequipment,
|
||||
/datum/supply_pack/science/robotics,
|
||||
/datum/supply_pack/science/plasma,
|
||||
/datum/supply_pack/medical/supplies
|
||||
)
|
||||
for(var/crate in crate_types)
|
||||
var/datum/supply_pack/pack = SSshuttle.supply_packs[crate]
|
||||
pack.generate(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
for(var/i in 1 to 5)
|
||||
var/decal = pick(/obj/effect/decal/cleanable/food/flour, /obj/effect/decal/cleanable/robot_debris, /obj/effect/decal/cleanable/oil)
|
||||
new decal(pick_n_take(empty_shuttle_turfs))
|
||||
if(PIZZA_DELIVERY)
|
||||
var/naughtypizza = list(/obj/item/pizzabox/bomb,/obj/item/pizzabox/margherita/robo) //oh look another blaklist, for pizza nonetheless!
|
||||
var/nicepizza = list(/obj/item/pizzabox/margherita, /obj/item/pizzabox/meat, /obj/item/pizzabox/vegetable, /obj/item/pizzabox/mushroom)
|
||||
for(var/i in 1 to 6)
|
||||
shuttle_spawns.Add(pick(prob(5) ? naughtypizza : nicepizza))
|
||||
if(ITS_HIP_TO)
|
||||
var/datum/supply_pack/pack = SSshuttle.supply_packs[/datum/supply_pack/organic/hydroponics/beekeeping_fullkit]
|
||||
pack.generate(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
shuttle_spawns.Add(/obj/effect/mob_spawn/corpse/human/bee_terrorist)
|
||||
shuttle_spawns.Add(/obj/effect/mob_spawn/corpse/human/cargo_tech)
|
||||
shuttle_spawns.Add(/obj/effect/mob_spawn/corpse/human/cargo_tech)
|
||||
shuttle_spawns.Add(/obj/effect/mob_spawn/corpse/human/nanotrasensoldier)
|
||||
shuttle_spawns.Add(/obj/item/gun/ballistic/automatic/pistol/no_mag)
|
||||
shuttle_spawns.Add(/obj/item/gun/ballistic/automatic/pistol/m1911/no_mag)
|
||||
shuttle_spawns.Add(/obj/item/honey_frame)
|
||||
shuttle_spawns.Add(/obj/item/honey_frame)
|
||||
shuttle_spawns.Add(/obj/item/honey_frame)
|
||||
shuttle_spawns.Add(/obj/structure/beebox/unwrenched)
|
||||
shuttle_spawns.Add(/obj/item/queen_bee/bought)
|
||||
shuttle_spawns.Add(/obj/structure/closet/crate/hydroponics)
|
||||
|
||||
for(var/i in 1 to 8)
|
||||
shuttle_spawns.Add(/mob/living/simple_animal/hostile/bee/toxin)
|
||||
|
||||
for(var/i in 1 to 5)
|
||||
var/decal = pick(/obj/effect/decal/cleanable/blood, /obj/effect/decal/cleanable/insectguts)
|
||||
new decal(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
for(var/i in 1 to 10)
|
||||
var/casing = /obj/item/ammo_casing/spent
|
||||
new casing(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
if(MY_GOD_JC)
|
||||
shuttle_spawns.Add(/obj/machinery/syndicatebomb/shuttle_loan)
|
||||
if(prob(95))
|
||||
shuttle_spawns.Add(/obj/item/paper/fluff/cargo/bomb)
|
||||
else
|
||||
shuttle_spawns.Add(/obj/item/paper/fluff/cargo/bomb/allyourbase)
|
||||
|
||||
if(PAPERS_PLEASE)
|
||||
shuttle_spawns += subtypesof(/obj/item/paperwork) - typesof(/obj/item/paperwork/photocopy) - typesof(/obj/item/paperwork/ancient)
|
||||
|
||||
var/false_positive = 0
|
||||
while(shuttle_spawns.len && empty_shuttle_turfs.len)
|
||||
var/turf/T = pick_n_take(empty_shuttle_turfs)
|
||||
if(T.contents.len && false_positive < 5)
|
||||
false_positive++
|
||||
continue
|
||||
|
||||
var/spawn_type = pick_n_take(shuttle_spawns)
|
||||
new spawn_type(T)
|
||||
|
||||
//items that appear only in shuttle loan events
|
||||
|
||||
/obj/item/storage/belt/fannypack/yellow/bee_terrorist/PopulateContents()
|
||||
new /obj/item/grenade/c4 (src)
|
||||
new /obj/item/reagent_containers/pill/cyanide(src)
|
||||
new /obj/item/grenade/chem_grenade/facid(src)
|
||||
|
||||
/obj/item/paper/fluff/bee_objectives
|
||||
name = "Objectives of a Bee Liberation Front Operative"
|
||||
default_raw_text = "<b>Objective #1</b>. Liberate all bees on the NT transport vessel 2416/B. <b>Success!</b> <br><b>Objective #2</b>. Escape alive. <b>Failed.</b>"
|
||||
|
||||
/obj/machinery/syndicatebomb/shuttle_loan/Initialize(mapload)
|
||||
. = ..()
|
||||
set_anchored(TRUE)
|
||||
timer_set = rand(480, 600) //once the supply shuttle docks (after 5 minutes travel time), players have between 3-5 minutes to defuse the bomb
|
||||
activate()
|
||||
update_appearance()
|
||||
|
||||
/obj/item/paper/fluff/cargo/bomb
|
||||
name = "hastly scribbled note"
|
||||
default_raw_text = "GOOD LUCK!"
|
||||
|
||||
/obj/item/paper/fluff/cargo/bomb/allyourbase
|
||||
default_raw_text = "Somebody set us up the bomb!"
|
||||
|
||||
#undef HIJACK_SYNDIE
|
||||
#undef RUSKY_PARTY
|
||||
#undef SPIDER_GIFT
|
||||
#undef DEPARTMENT_RESUPPLY
|
||||
#undef ANTIDOTE_NEEDED
|
||||
#undef PIZZA_DELIVERY
|
||||
#undef ITS_HIP_TO
|
||||
#undef MY_GOD_JC
|
||||
@@ -0,0 +1,213 @@
|
||||
/// One of the potential shuttle loans you might recieve.
|
||||
/datum/shuttle_loan_situation
|
||||
/// Who sent the shuttle
|
||||
var/sender = "Centcom"
|
||||
/// What they said about it.
|
||||
var/announcement_text = "Unset announcement text"
|
||||
/// What the shuttle says about it.
|
||||
var/shuttle_transit_text = "Unset transit text"
|
||||
/// Supply points earned for taking the deal.
|
||||
var/bonus_points = 10000
|
||||
/// Response for taking the deal.
|
||||
var/thanks_msg = "The cargo shuttle should return in five minutes. Have some supply points for your trouble."
|
||||
/// Small description of the loan for easier log reading.
|
||||
var/logging_desc
|
||||
|
||||
/datum/shuttle_loan_situation/New()
|
||||
. = ..()
|
||||
if(!logging_desc)
|
||||
stack_trace("No logging blurb set for [src.type]!")
|
||||
|
||||
/// Spawns paths added to `spawn_list`, and passes empty shuttle turfs so you can spawn more complicated things like dead bodies.
|
||||
/datum/shuttle_loan_situation/proc/spawn_items(list/spawn_list, list/empty_shuttle_turfs)
|
||||
SHOULD_CALL_PARENT(FALSE)
|
||||
CRASH("Unimplemented get_spawned_items() on [src.type].")
|
||||
|
||||
/datum/shuttle_loan_situation/antidote
|
||||
sender = "CentCom Research Initiatives"
|
||||
announcement_text = "Your station has been chosen for an epidemiological research project. Send us your cargo shuttle to receive your research samples."
|
||||
shuttle_transit_text = "Virus samples incoming."
|
||||
logging_desc = "Virus shuttle"
|
||||
|
||||
/datum/shuttle_loan_situation/antidote/spawn_items(list/spawn_list, list/empty_shuttle_turfs)
|
||||
var/obj/effect/mob_spawn/corpse/human/assistant/infected_assistant = pick(list(
|
||||
/obj/effect/mob_spawn/corpse/human/assistant/beesease_infection,
|
||||
/obj/effect/mob_spawn/corpse/human/assistant/brainrot_infection,
|
||||
/obj/effect/mob_spawn/corpse/human/assistant/spanishflu_infection,
|
||||
))
|
||||
for(var/i in 1 to 10)
|
||||
if(prob(15))
|
||||
spawn_list.Add(/obj/item/reagent_containers/cup/bottle)
|
||||
else if(prob(15))
|
||||
spawn_list.Add(/obj/item/reagent_containers/syringe)
|
||||
else if(prob(25))
|
||||
spawn_list.Add(/obj/item/shard)
|
||||
var/turf/assistant_turf = pick_n_take(empty_shuttle_turfs)
|
||||
new infected_assistant(assistant_turf)
|
||||
spawn_list.Add(/obj/structure/closet/crate)
|
||||
spawn_list.Add(/obj/item/reagent_containers/cup/bottle/pierrot_throat)
|
||||
spawn_list.Add(/obj/item/reagent_containers/cup/bottle/magnitis)
|
||||
|
||||
/datum/shuttle_loan_situation/department_resupply
|
||||
sender = "CentCom Supply Department"
|
||||
announcement_text = "Seems we've ordered doubles of our department resupply packages this month. Can we send them to you?"
|
||||
shuttle_transit_text = "Department resupply incoming."
|
||||
thanks_msg = "The cargo shuttle should return in five minutes."
|
||||
bonus_points = 0
|
||||
logging_desc = "Resupply packages"
|
||||
|
||||
/datum/shuttle_loan_situation/department_resupply/spawn_items(list/spawn_list, list/empty_shuttle_turfs)
|
||||
var/list/crate_types = list(
|
||||
/datum/supply_pack/emergency/equipment,
|
||||
/datum/supply_pack/security/supplies,
|
||||
/datum/supply_pack/organic/food,
|
||||
/datum/supply_pack/emergency/weedcontrol,
|
||||
/datum/supply_pack/engineering/tools,
|
||||
/datum/supply_pack/engineering/engiequipment,
|
||||
/datum/supply_pack/science/robotics,
|
||||
/datum/supply_pack/science/plasma,
|
||||
/datum/supply_pack/medical/supplies
|
||||
)
|
||||
for(var/crate in crate_types)
|
||||
var/datum/supply_pack/pack = SSshuttle.supply_packs[crate]
|
||||
pack.generate(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
for(var/i in 1 to 5)
|
||||
var/decal = pick(/obj/effect/decal/cleanable/food/flour, /obj/effect/decal/cleanable/robot_debris, /obj/effect/decal/cleanable/oil)
|
||||
new decal(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
/datum/shuttle_loan_situation/department_resupply
|
||||
sender = "CentCom Counterintelligence"
|
||||
announcement_text = "The syndicate are trying to infiltrate your station. If you let them hijack your cargo shuttle, you'll save us a headache."
|
||||
shuttle_transit_text = "Syndicate hijack team incoming."
|
||||
logging_desc = "Syndicate boarding party"
|
||||
|
||||
/datum/shuttle_loan_situation/department_resupply/spawn_items(list/spawn_list, list/empty_shuttle_turfs)
|
||||
var/datum/supply_pack/pack = SSshuttle.supply_packs[/datum/supply_pack/emergency/specialops]
|
||||
pack.generate(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
spawn_list.Add(/mob/living/basic/syndicate/ranged/infiltrator)
|
||||
spawn_list.Add(/mob/living/basic/syndicate/ranged/infiltrator)
|
||||
if(prob(75))
|
||||
spawn_list.Add(/mob/living/basic/syndicate/ranged/infiltrator)
|
||||
if(prob(50))
|
||||
spawn_list.Add(/mob/living/basic/syndicate/ranged/infiltrator)
|
||||
|
||||
/datum/shuttle_loan_situation/lots_of_bees
|
||||
sender = "CentCom Janitorial Division"
|
||||
announcement_text = "One of our freighters carrying a bee shipment has been attacked by eco-terrorists. Can you clean up the mess for us?"
|
||||
shuttle_transit_text = "Biohazard cleanup incoming."
|
||||
bonus_points = 20000 //Toxin bees can be unbeelievably lethal
|
||||
logging_desc = "Shuttle full of bees"
|
||||
|
||||
/datum/shuttle_loan_situation/lots_of_bees/spawn_items(list/spawn_list, list/empty_shuttle_turfs)
|
||||
var/datum/supply_pack/pack = SSshuttle.supply_packs[/datum/supply_pack/organic/hydroponics/beekeeping_fullkit]
|
||||
pack.generate(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
spawn_list.Add(/obj/effect/mob_spawn/corpse/human/bee_terrorist)
|
||||
spawn_list.Add(/obj/effect/mob_spawn/corpse/human/cargo_tech)
|
||||
spawn_list.Add(/obj/effect/mob_spawn/corpse/human/cargo_tech)
|
||||
spawn_list.Add(/obj/effect/mob_spawn/corpse/human/nanotrasensoldier)
|
||||
spawn_list.Add(/obj/item/gun/ballistic/automatic/pistol/no_mag)
|
||||
spawn_list.Add(/obj/item/gun/ballistic/automatic/pistol/m1911/no_mag)
|
||||
spawn_list.Add(/obj/item/honey_frame)
|
||||
spawn_list.Add(/obj/item/honey_frame)
|
||||
spawn_list.Add(/obj/item/honey_frame)
|
||||
spawn_list.Add(/obj/structure/beebox/unwrenched)
|
||||
spawn_list.Add(/obj/item/queen_bee/bought)
|
||||
spawn_list.Add(/obj/structure/closet/crate/hydroponics)
|
||||
|
||||
for(var/i in 1 to 8)
|
||||
spawn_list.Add(/mob/living/simple_animal/hostile/bee/toxin)
|
||||
|
||||
for(var/i in 1 to 5)
|
||||
var/decal = pick(/obj/effect/decal/cleanable/blood, /obj/effect/decal/cleanable/insectguts)
|
||||
new decal(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
for(var/i in 1 to 10)
|
||||
var/casing = /obj/item/ammo_casing/spent
|
||||
new casing(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
/datum/shuttle_loan_situation/jc_a_bomb
|
||||
sender = "CentCom Security Division"
|
||||
announcement_text = "We have discovered an active Syndicate bomb near our VIP shuttle's fuel lines. If you feel up to the task, we will pay you for defusing it."
|
||||
shuttle_transit_text = "Live explosive ordnance incoming. Exercise extreme caution."
|
||||
thanks_msg = "Live explosive ordnance incoming via supply shuttle. Evacuating cargo bay is recommended."
|
||||
bonus_points = 45000 //If you mess up, people die and the shuttle gets turned into swiss cheese
|
||||
logging_desc = "Shuttle with a ticking bomb"
|
||||
|
||||
/datum/shuttle_loan_situation/jc_a_bomb/spawn_items(list/spawn_list, list/empty_shuttle_turfs)
|
||||
spawn_list.Add(/obj/machinery/syndicatebomb/shuttle_loan)
|
||||
if(prob(95))
|
||||
spawn_list.Add(/obj/item/paper/fluff/cargo/bomb)
|
||||
else
|
||||
spawn_list.Add(/obj/item/paper/fluff/cargo/bomb/allyourbase)
|
||||
|
||||
/datum/shuttle_loan_situation/papers_please
|
||||
sender = "CentCom Paperwork Division"
|
||||
announcement_text = "A neighboring station needs some help handling some paperwork. Could you help process it for us?"
|
||||
shuttle_transit_text = "Paperwork incoming."
|
||||
thanks_msg = "The cargo shuttle should return in five minutes. Payment will be rendered when the paperwork is processed and returned."
|
||||
bonus_points = 0 //Payout is made when the stamped papers are returned
|
||||
logging_desc = "Paperwork shipment"
|
||||
|
||||
/datum/shuttle_loan_situation/papers_please/spawn_items(list/spawn_list, list/empty_shuttle_turfs)
|
||||
spawn_list += subtypesof(/obj/item/paperwork) - typesof(/obj/item/paperwork/photocopy) - typesof(/obj/item/paperwork/ancient)
|
||||
|
||||
/datum/shuttle_loan_situation/pizza_delivery
|
||||
sender = "CentCom Spacepizza Division"
|
||||
announcement_text = "It looks like a neighbouring station accidentally delivered their pizza to you instead."
|
||||
shuttle_transit_text = "Pizza delivery!"
|
||||
thanks_msg = "The cargo shuttle should return in five minutes."
|
||||
bonus_points = 0
|
||||
logging_desc = "Pizza delivery"
|
||||
|
||||
/datum/shuttle_loan_situation/pizza_delivery/spawn_items(list/spawn_list, list/empty_shuttle_turfs)
|
||||
var/naughtypizza = list(/obj/item/pizzabox/bomb, /obj/item/pizzabox/margherita/robo) //oh look another blacklist, for pizza nonetheless!
|
||||
var/nicepizza = list(/obj/item/pizzabox/margherita, /obj/item/pizzabox/meat, /obj/item/pizzabox/vegetable, /obj/item/pizzabox/mushroom)
|
||||
for(var/i in 1 to 6)
|
||||
spawn_list.Add(pick(prob(5) ? naughtypizza : nicepizza))
|
||||
|
||||
/datum/shuttle_loan_situation/russian_party
|
||||
sender = "CentCom Russian Outreach Program"
|
||||
announcement_text = "A group of angry Russians want to have a party. Can you send them your cargo shuttle then make them disappear?"
|
||||
shuttle_transit_text = "Partying Russians incoming."
|
||||
logging_desc = "Russian party squad"
|
||||
|
||||
/datum/shuttle_loan_situation/russian_party/spawn_items(list/spawn_list, list/empty_shuttle_turfs)
|
||||
var/datum/supply_pack/pack = SSshuttle.supply_packs[/datum/supply_pack/service/party]
|
||||
pack.generate(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
spawn_list.Add(/mob/living/simple_animal/hostile/russian)
|
||||
spawn_list.Add(/mob/living/simple_animal/hostile/russian/ranged) //drops a mateba
|
||||
spawn_list.Add(/mob/living/simple_animal/hostile/bear/russian)
|
||||
if(prob(75))
|
||||
spawn_list.Add(/mob/living/simple_animal/hostile/russian)
|
||||
if(prob(50))
|
||||
spawn_list.Add(/mob/living/simple_animal/hostile/bear/russian)
|
||||
|
||||
/datum/shuttle_loan_situation/spider_gift
|
||||
sender = "CentCom Diplomatic Corps"
|
||||
announcement_text = "The Spider Clan has sent us a mysterious gift. Can we ship it to you to see what's inside?"
|
||||
shuttle_transit_text = "Spider Clan gift incoming."
|
||||
logging_desc = "Shuttle full of spiders"
|
||||
|
||||
/datum/shuttle_loan_situation/spider_gift/spawn_items(list/spawn_list, list/empty_shuttle_turfs)
|
||||
var/datum/supply_pack/pack = SSshuttle.supply_packs[/datum/supply_pack/emergency/specialops]
|
||||
pack.generate(pick_n_take(empty_shuttle_turfs))
|
||||
|
||||
spawn_list.Add(/mob/living/simple_animal/hostile/giant_spider)
|
||||
spawn_list.Add(/mob/living/simple_animal/hostile/giant_spider)
|
||||
spawn_list.Add(/mob/living/simple_animal/hostile/giant_spider/nurse)
|
||||
if(prob(50))
|
||||
spawn_list.Add(/mob/living/simple_animal/hostile/giant_spider/hunter)
|
||||
|
||||
var/turf/victim_turf = pick_n_take(empty_shuttle_turfs)
|
||||
|
||||
new /obj/effect/decal/remains/human(victim_turf)
|
||||
new /obj/item/clothing/shoes/jackboots/fast(victim_turf)
|
||||
new /obj/item/clothing/mask/balaclava(victim_turf)
|
||||
|
||||
for(var/i in 1 to 5)
|
||||
var/turf/web_turf = pick_n_take(empty_shuttle_turfs)
|
||||
new /obj/structure/spider/stickyweb(web_turf)
|
||||
@@ -0,0 +1,106 @@
|
||||
|
||||
/datum/round_event_control/shuttle_loan
|
||||
name = "Shuttle Loan"
|
||||
typepath = /datum/round_event/shuttle_loan
|
||||
max_occurrences = 3
|
||||
earliest_start = 7 MINUTES
|
||||
category = EVENT_CATEGORY_BUREAUCRATIC
|
||||
description = "If cargo accepts the offer, fills the shuttle with loot and/or enemies."
|
||||
///The types of loan events already run (and to be excluded if the event triggers).
|
||||
admin_setup = /datum/event_admin_setup/listed_options/shuttle_loan
|
||||
var/list/run_situations = list()
|
||||
|
||||
/datum/round_event_control/shuttle_loan/can_spawn_event(players_amt)
|
||||
. = ..()
|
||||
for(var/datum/round_event/running_event in SSevents.running)
|
||||
if(istype(running_event, /datum/round_event/shuttle_loan)) //Make sure two of these don't happen at once.
|
||||
return FALSE
|
||||
|
||||
/datum/round_event/shuttle_loan
|
||||
announce_when = 1
|
||||
end_when = 500
|
||||
/// what type of shuttle loan situation the station faces.
|
||||
var/datum/shuttle_loan_situation/situation
|
||||
/// Whether the station has let Centcom commandeer the shuttle yet.
|
||||
var/dispatched = FALSE
|
||||
|
||||
/datum/round_event/shuttle_loan/setup()
|
||||
var/datum/round_event_control/shuttle_loan/loan_control = control
|
||||
//by this point if situation is admin picked, it is a type, not an instance.
|
||||
if(!situation)
|
||||
var/list/valid_situations = subtypesof(/datum/shuttle_loan_situation) - loan_control.run_situations
|
||||
if(!valid_situations.len)
|
||||
//If we somehow run out of loans (fking campbell), they all become available again
|
||||
loan_control.run_situations.Cut()
|
||||
valid_situations = subtypesof(/datum/shuttle_loan_situation)
|
||||
situation = pick(valid_situations)
|
||||
|
||||
loan_control.run_situations.Add(situation)
|
||||
situation = new situation()
|
||||
|
||||
/datum/round_event/shuttle_loan/announce(fake)
|
||||
priority_announce("Cargo: [situation.announcement_text]", situation.sender)
|
||||
SSshuttle.shuttle_loan = src
|
||||
|
||||
/datum/round_event/shuttle_loan/proc/loan_shuttle()
|
||||
priority_announce(situation.thanks_msg, "Cargo shuttle commandeered by CentCom.")
|
||||
|
||||
dispatched = TRUE
|
||||
var/datum/bank_account/dep_account = SSeconomy.get_dep_account(ACCOUNT_CAR)
|
||||
dep_account?.adjust_money(situation.bonus_points)
|
||||
end_when = activeFor + 1
|
||||
|
||||
SSshuttle.supply.mode = SHUTTLE_CALL
|
||||
SSshuttle.supply.destination = SSshuttle.getDock("cargo_home")
|
||||
SSshuttle.supply.setTimer(3000)
|
||||
SSshuttle.centcom_message += situation.shuttle_transit_text
|
||||
|
||||
log_game("Shuttle loan event firing with type '[situation.logging_desc]'.")
|
||||
|
||||
/datum/round_event/shuttle_loan/tick()
|
||||
if(dispatched)
|
||||
if(SSshuttle.supply.mode != SHUTTLE_IDLE)
|
||||
end_when = activeFor
|
||||
else
|
||||
end_when = activeFor + 1
|
||||
|
||||
/datum/round_event/shuttle_loan/end()
|
||||
if(!SSshuttle.shuttle_loan || !SSshuttle.shuttle_loan.dispatched)
|
||||
return
|
||||
//make sure the shuttle was dispatched in time
|
||||
SSshuttle.shuttle_loan = null
|
||||
|
||||
//get empty turfs
|
||||
var/list/empty_shuttle_turfs = list()
|
||||
var/list/area/shuttle/shuttle_areas = SSshuttle.supply.shuttle_areas
|
||||
for(var/area/shuttle/shuttle_area as anything in shuttle_areas)
|
||||
for(var/turf/open/floor/shuttle_turf in shuttle_area)
|
||||
if(shuttle_turf.is_blocked_turf())
|
||||
continue
|
||||
empty_shuttle_turfs += shuttle_turf
|
||||
if(!empty_shuttle_turfs.len)
|
||||
return
|
||||
|
||||
//let the situation spawn its items
|
||||
var/list/spawn_list = list()
|
||||
situation.spawn_items(spawn_list, empty_shuttle_turfs)
|
||||
|
||||
var/false_positive = 0
|
||||
while(spawn_list.len && empty_shuttle_turfs.len)
|
||||
var/turf/spawn_turf = pick_n_take(empty_shuttle_turfs)
|
||||
if(spawn_turf.contents.len && false_positive < 5)
|
||||
false_positive++
|
||||
continue
|
||||
var/spawn_type = pick_n_take(spawn_list)
|
||||
new spawn_type(spawn_turf)
|
||||
|
||||
/datum/event_admin_setup/listed_options/shuttle_loan
|
||||
input_text = "Select a loan offer?"
|
||||
|
||||
/datum/event_admin_setup/listed_options/shuttle_loan/get_list()
|
||||
var/datum/round_event_control/shuttle_loan/loan_event = event_control
|
||||
var/list/valid_situations = subtypesof(/datum/shuttle_loan_situation) - loan_event.run_situations
|
||||
return valid_situations
|
||||
|
||||
/datum/event_admin_setup/listed_options/shuttle_loan/apply_to_event(datum/round_event/shuttle_loan/event)
|
||||
event.situation = chosen
|
||||
@@ -0,0 +1,23 @@
|
||||
|
||||
/obj/item/storage/belt/fannypack/yellow/bee_terrorist/PopulateContents()
|
||||
new /obj/item/grenade/c4 (src)
|
||||
new /obj/item/reagent_containers/pill/cyanide(src)
|
||||
new /obj/item/grenade/chem_grenade/facid(src)
|
||||
|
||||
/obj/item/paper/fluff/bee_objectives
|
||||
name = "Objectives of a Bee Liberation Front Operative"
|
||||
default_raw_text = "<b>Objective #1</b>. Liberate all bees on the NT transport vessel 2416/B. <b>Success!</b> <br><b>Objective #2</b>. Escape alive. <b>Failed.</b>"
|
||||
|
||||
/obj/machinery/syndicatebomb/shuttle_loan/Initialize(mapload)
|
||||
. = ..()
|
||||
set_anchored(TRUE)
|
||||
timer_set = rand(480, 600) //once the supply shuttle docks (after 5 minutes travel time), players have between 3-5 minutes to defuse the bomb
|
||||
activate()
|
||||
update_appearance()
|
||||
|
||||
/obj/item/paper/fluff/cargo/bomb
|
||||
name = "hastly scribbled note"
|
||||
default_raw_text = "GOOD LUCK!"
|
||||
|
||||
/obj/item/paper/fluff/cargo/bomb/allyourbase
|
||||
default_raw_text = "Somebody set us up the bomb!"
|
||||
@@ -7,30 +7,17 @@
|
||||
earliest_start = 20 MINUTES
|
||||
category = EVENT_CATEGORY_SPACE
|
||||
description = "Throw a random meteor somewhere near the station."
|
||||
///The selected meteor type if chosen through admin setup.
|
||||
var/chosen_meteor
|
||||
|
||||
/datum/round_event_control/stray_meteor/admin_setup()
|
||||
if(!check_rights(R_FUN))
|
||||
return ADMIN_CANCEL_EVENT
|
||||
|
||||
if(tgui_alert(usr, "Select a meteor?", "Plasuable Deniability!", list("Yes", "No")) == "Yes")
|
||||
var/list/meteor_list = list()
|
||||
meteor_list += subtypesof(/obj/effect/meteor)
|
||||
chosen_meteor = tgui_input_list(usr, "Too lazy for buildmode?","Throw meteor", meteor_list)
|
||||
admin_setup = /datum/event_admin_setup/listed_options/stray_meteor
|
||||
|
||||
/datum/round_event/stray_meteor
|
||||
announce_when = 1
|
||||
fakeable = FALSE //Already faked by meteors that miss
|
||||
///The selected meteor type if chosen through admin setup.
|
||||
var/chosen_meteor
|
||||
|
||||
/datum/round_event/stray_meteor/start()
|
||||
var/datum/round_event_control/stray_meteor/meteor_event = control
|
||||
if(meteor_event.chosen_meteor)
|
||||
var/chosen_meteor = meteor_event.chosen_meteor
|
||||
meteor_event.chosen_meteor = null
|
||||
var/list/passed_meteor = list()
|
||||
passed_meteor[chosen_meteor] = 1
|
||||
spawn_meteor(passed_meteor)
|
||||
if(chosen_meteor)
|
||||
spawn_meteor(list(chosen_meteor = 1))
|
||||
else
|
||||
spawn_meteor(GLOB.meteors_stray)
|
||||
|
||||
@@ -39,3 +26,13 @@
|
||||
var/obj/effect/meteor/detected_meteor = pick(GLOB.meteor_list) //If we accidentally pick a meteor not spawned by the event, we're still technically not wrong
|
||||
var/sensor_name = detected_meteor.signature
|
||||
priority_announce("Our [sensor_name] sensors have detected an incoming signature approaching [GLOB.station_name]. Please brace for impact.", "Meteor Alert")
|
||||
|
||||
/datum/event_admin_setup/listed_options/stray_meteor
|
||||
input_text = "Select a meteor type?"
|
||||
normal_run_option = "Random Meteor"
|
||||
|
||||
/datum/event_admin_setup/listed_options/stray_meteor/get_list()
|
||||
return subtypesof(/obj/effect/meteor)
|
||||
|
||||
/datum/event_admin_setup/listed_options/stray_meteor/apply_to_event(datum/round_event/stray_meteor/event)
|
||||
event.chosen_meteor = chosen
|
||||
|
||||
@@ -1,3 +1,6 @@
|
||||
|
||||
#define RANDOM_DEPARTMENT "Random Department"
|
||||
|
||||
/datum/round_event_control/wizard/deprevolt //stationwide!
|
||||
name = "Departmental Uprising"
|
||||
weight = 0 //An order that requires order in a round of chaos was maybe not the best idea. Requiescat in pace departmental uprising August 2014 - March 2015 //hello motherfucker i fixed your shit in 2021
|
||||
@@ -5,25 +8,39 @@
|
||||
max_occurrences = 1
|
||||
earliest_start = 0 MINUTES
|
||||
description = "A department is turned into an independent state."
|
||||
admin_setup = /datum/event_admin_setup/department_revolt
|
||||
|
||||
///manual choice of what department to revolt for admins to pick
|
||||
/datum/round_event/wizard/deprevolt
|
||||
///which department is revolting?
|
||||
var/datum/job_department/picked_department
|
||||
///admin choice on whether to announce the department
|
||||
/// Announce the separatist nation to the round?
|
||||
var/announce = FALSE
|
||||
///admin choice on whether this nation will have objectives to attack other nations, default true for !fun!
|
||||
/// Is it going to try fighting other nations?
|
||||
var/dangerous_nation = TRUE
|
||||
|
||||
/datum/round_event_control/wizard/deprevolt/admin_setup(mob/admin)
|
||||
if(!check_rights(R_FUN))
|
||||
return
|
||||
/datum/round_event/wizard/deprevolt/start()
|
||||
// no setup needed, this proc handles empty values. God i'm good (i wrote all of this)
|
||||
create_separatist_nation(picked_department, announce, dangerous_nation)
|
||||
|
||||
var/list/options = list()
|
||||
/datum/event_admin_setup/department_revolt
|
||||
///which department is revolting?
|
||||
var/datum/job_department/picked_department
|
||||
/// Announce the separatist nation to the round?
|
||||
var/announce = FALSE
|
||||
/// Is it going to try fighting other nations?
|
||||
var/dangerous_nation = TRUE
|
||||
|
||||
/datum/event_admin_setup/department_revolt/prompt_admins()
|
||||
var/list/options = list("Random" = RANDOM_DEPARTMENT)
|
||||
var/list/pickable_departments = subtypesof(/datum/job_department)
|
||||
for(var/datum/job_department/dep as anything in pickable_departments)
|
||||
options[initial(dep.department_name)] = dep
|
||||
picked_department = options[(input(usr,"Which department should revolt? Select none for a random department.","Select a department") as null|anything in options)]
|
||||
picked_department = options[(tgui_input_list(usr,"Which department should revolt? Select none for a random department.","Select a department", options))]
|
||||
if(!picked_department)
|
||||
return //eh just random they dont care
|
||||
return ADMIN_CANCEL_EVENT
|
||||
if(picked_department == RANDOM_DEPARTMENT)
|
||||
picked_department = null
|
||||
return
|
||||
|
||||
var/announce_question = tgui_alert(usr, "Announce This New Independent State?", "Secession", list("Announce", "No Announcement"))
|
||||
if(announce_question == "Announce")
|
||||
@@ -33,6 +50,9 @@
|
||||
if(dangerous_question == "No")
|
||||
dangerous_nation = FALSE
|
||||
|
||||
/datum/round_event/wizard/deprevolt/start()
|
||||
var/datum/round_event_control/wizard/deprevolt/event_control = control
|
||||
create_separatist_nation(event_control.picked_department, event_control.announce, event_control.dangerous_nation)
|
||||
/datum/event_admin_setup/department_revolt/apply_to_event(datum/round_event/wizard/deprevolt/event)
|
||||
event.picked_department = picked_department
|
||||
event.announce = announce
|
||||
event.dangerous_nation = dangerous_nation
|
||||
|
||||
#undef RANDOM_DEPARTMENT
|
||||
|
||||
@@ -4,26 +4,23 @@
|
||||
typepath = /datum/round_event/wizard/madness
|
||||
earliest_start = 0 MINUTES
|
||||
description = "Reveals a horrifying truth to everyone, giving them a trauma."
|
||||
admin_setup = /datum/event_admin_setup/text_input/madness
|
||||
|
||||
var/forced_secret
|
||||
|
||||
/datum/round_event_control/wizard/madness/admin_setup(mob/admin)
|
||||
if(!check_rights(R_FUN))
|
||||
return
|
||||
|
||||
var/suggested = pick(strings(REDPILL_FILE, "redpill_questions"))
|
||||
|
||||
forced_secret = (input(usr, "What horrifying truth will you reveal?", "Curse of Madness", sort_list(suggested)) as text|null) || suggested
|
||||
|
||||
/datum/round_event/wizard/madness/start()
|
||||
var/datum/round_event_control/wizard/madness/C = control
|
||||
|
||||
/datum/round_event/wizard/madness
|
||||
/// the horrifying truth sent to the crew, can be picked by admins.
|
||||
var/horrifying_truth
|
||||
|
||||
if(C.forced_secret)
|
||||
horrifying_truth = C.forced_secret
|
||||
C.forced_secret = null
|
||||
else
|
||||
/datum/round_event/wizard/madness/start()
|
||||
if(!horrifying_truth)
|
||||
horrifying_truth = pick(strings(REDPILL_FILE, "redpill_questions"))
|
||||
|
||||
curse_of_madness(null, horrifying_truth)
|
||||
|
||||
/datum/event_admin_setup/text_input/madness
|
||||
input_text = "What horrifying truth will you reveal?"
|
||||
|
||||
/datum/event_admin_setup/text_input/madness/get_text_suggestion()
|
||||
return pick(strings(REDPILL_FILE, "redpill_questions"))
|
||||
|
||||
/datum/event_admin_setup/text_input/madness/apply_to_event(datum/round_event/wizard/madness/event)
|
||||
event.horrifying_truth = chosen
|
||||
|
||||
Reference in New Issue
Block a user