STATION TRAIT GAMEMODE: Station-Wide Background Checks (#83307)

## About The Pull Request
Adds a new station trait: Station-Wide Background Checks!

It does two things:
1. Blocks most crew-side antagonists. No traitors, changelings, spies,
heretics, etc. You won't be able to fully trust your crew though, as
Space changelings, Paradox Clones, Obsesseds and Blob Infected are
excempted crew-antags since a background check doesn't really help here.
Other antagonists still spawn: pirates, revenants, blobs, aliens,
nukies, wizards etc. Expect a LOT more of these, as Dynamic is gonna put
threat somewhere...

2. Reduces dynamics threat slightly, configurable per server, but
defaults to 15.

It is essentially the first "dynamic gamemode".

## Why It's Good For The Game

Blocking crew antagonists changes the shifts dynamic, similair to old
warops. Security can "trust" crew to not be antagonists, and instead can
focus more on petty crimes and hunting down external threats.

Due to the increased chance of external threats and reduced chance of
internal threats, the crew can focus its defenses outwards. Don't worry
about your coworker killing you (intentionally/probably), but do worry a
lot more about the pirates trying to break through your hull, or alien
nests growing in virology.

I've also reduced total threat count slightly because the idea of 90
threat being dumped into ghost spawns kinda terrifies me and I do want
people to be able to let their guard down a slight bit. It can be
reduced/disabled for servers that already tend to lower threats.

I think it's a lot of fun to change the paranoia dynamic, and a fun
deviation from a normal round of spaceman13.

## Changelog
🆑
add: Station-Wide Background Checks (station trait, rare): Disables crew
antagonists, but get a lot more non-crew antagonists
/🆑
I want to do more like these (this was just an example I threw into
discord to annoy @ Mothblocks but I realized I kinda liked), and this is
a good opportunity to gather community feedback and see how it plays!

---------

Co-authored-by: carlarctg <53100513+carlarctg@ users.noreply.github.com>
This commit is contained in:
Time-Green
2024-05-31 13:13:26 -04:00
committed by SkyratBot
co-authored by carlarctg
parent 3990805e46
commit d5b0a9de08
9 changed files with 53 additions and 6 deletions
+6
View File
@@ -38,3 +38,9 @@
#define RULESET_FORCE_ENABLED "force enabled"
/// Ruleset should not run regardless of population and threat available
#define RULESET_FORCE_DISABLED "force disabled"
// Flavor ruletypes, used by station traits
/// Rulesets selected by dynamic at default
#define RULESET_CATEGORY_DEFAULT (1 << 0)
/// Rulesets not including crew antagonists, non-witting referring to antags like obsessed which aren't really enemies of the station
#define RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS (1 << 1)
@@ -19,6 +19,8 @@ GLOBAL_VAR_INIT(dynamic_forced_threat_level, -1)
GLOBAL_LIST_EMPTY(dynamic_station_traits)
/// Rulesets which have been forcibly enabled or disabled
GLOBAL_LIST_EMPTY(dynamic_forced_rulesets)
/// Bitflags used during init by Dynamic to determine which rulesets we're allowed to use, used by station traits for gamemode-esque experiences
GLOBAL_VAR_INIT(dynamic_ruleset_categories, RULESET_CATEGORY_DEFAULT)
SUBSYSTEM_DEF(dynamic)
name = "Dynamic"
@@ -646,7 +648,6 @@ SUBSYSTEM_DEF(dynamic)
log_admin(concatenated_message)
to_chat(GLOB.admins, concatenated_message)
/// Initializes the internal ruleset variables
/datum/controller/subsystem/dynamic/proc/setup_rulesets()
midround_rules = init_rulesets(/datum/dynamic_ruleset/midround)
@@ -664,6 +665,9 @@ SUBSYSTEM_DEF(dynamic)
if (initial(ruleset_type.weight) == 0)
continue
if(!(initial(ruleset_type.ruleset_category) & GLOB.dynamic_ruleset_categories))
continue
var/ruleset = new ruleset_type
configure_ruleset(ruleset)
rulesets += ruleset
@@ -83,6 +83,8 @@
/// A list, or null, of templates that the ruleset depends on to function correctly
var/list/ruleset_lazy_templates
/// In what categories is this ruleset allowed to run? Used by station traits
var/ruleset_category = RULESET_CATEGORY_DEFAULT
/datum/dynamic_ruleset/New()
// Rulesets can be instantiated more than once, such as when an admin clicks
@@ -349,6 +349,7 @@
antag_datum = /datum/antagonist/wizard
antag_flag = ROLE_WIZARD_MIDROUND
antag_flag_override = ROLE_WIZARD
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
required_enemies = list(2,2,1,1,1,1,1,0,0,0)
required_candidates = 1
weight = 1
@@ -377,6 +378,7 @@
antag_flag = ROLE_OPERATIVE_MIDROUND
antag_flag_override = ROLE_OPERATIVE
antag_datum = /datum/antagonist/nukeop
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
enemy_roles = list(
JOB_AI,
JOB_CYBORG,
@@ -431,6 +433,7 @@
midround_ruleset_style = MIDROUND_RULESET_STYLE_HEAVY
antag_datum = /datum/antagonist/blob
antag_flag = ROLE_BLOB
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
required_enemies = list(2,2,1,1,1,1,1,0,0,0)
required_candidates = 1
minimum_round_time = 35 MINUTES
@@ -450,6 +453,7 @@
antag_datum = /datum/antagonist/blob/infection
antag_flag = ROLE_BLOB_INFECTION
antag_flag_override = ROLE_BLOB
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
protected_roles = list(
JOB_CAPTAIN,
JOB_DETECTIVE,
@@ -502,6 +506,7 @@
midround_ruleset_style = MIDROUND_RULESET_STYLE_HEAVY
antag_datum = /datum/antagonist/xeno
antag_flag = ROLE_ALIEN
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
required_enemies = list(2,2,1,1,1,1,1,0,0,0)
required_candidates = 1
minimum_round_time = 40 MINUTES
@@ -550,6 +555,7 @@
antag_datum = /datum/antagonist/nightmare
antag_flag = ROLE_NIGHTMARE
antag_flag_override = ROLE_ALIEN
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
required_enemies = list(2,2,1,1,1,1,1,0,0,0)
required_candidates = 1
weight = 3
@@ -585,7 +591,7 @@
midround_ruleset_style = MIDROUND_RULESET_STYLE_HEAVY
antag_datum = /datum/antagonist/space_dragon
antag_flag = ROLE_SPACE_DRAGON
antag_flag_override = ROLE_SPACE_DRAGON
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
required_enemies = list(2,2,1,1,1,1,1,0,0,0)
required_candidates = 1
weight = 4
@@ -625,6 +631,7 @@
midround_ruleset_style = MIDROUND_RULESET_STYLE_LIGHT
antag_datum = /datum/antagonist/abductor
antag_flag = ROLE_ABDUCTOR
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
required_enemies = list(2,2,1,1,1,1,1,0,0,0)
required_candidates = 2
required_applicants = 2
@@ -662,6 +669,7 @@
midround_ruleset_style = MIDROUND_RULESET_STYLE_HEAVY
antag_datum = /datum/antagonist/ninja
antag_flag = ROLE_NINJA
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
required_enemies = list(2,2,1,1,1,1,1,0,0,0)
required_candidates = 1
weight = 4
@@ -701,6 +709,7 @@
name = "Spiders"
midround_ruleset_style = MIDROUND_RULESET_STYLE_HEAVY
antag_flag = ROLE_SPIDER
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
required_type = /mob/dead/observer
required_enemies = list(2,2,1,1,1,1,1,0,0,0)
required_candidates = 0
@@ -718,6 +727,7 @@
/datum/dynamic_ruleset/midround/from_ghosts/revenant
name = "Revenant"
midround_ruleset_style = MIDROUND_RULESET_STYLE_LIGHT
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
antag_datum = /datum/antagonist/revenant
antag_flag = ROLE_REVENANT
required_enemies = list(2,2,1,1,1,1,1,0,0,0)
@@ -768,6 +778,7 @@
/datum/dynamic_ruleset/midround/pirates
name = "Space Pirates"
midround_ruleset_style = MIDROUND_RULESET_STYLE_LIGHT
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
antag_flag = "Space Pirates"
required_type = /mob/dead/observer
required_enemies = list(2,2,1,1,1,1,1,0,0,0)
@@ -790,6 +801,7 @@
/datum/dynamic_ruleset/midround/dangerous_pirates
name = "Dangerous Space Pirates"
midround_ruleset_style = MIDROUND_RULESET_STYLE_HEAVY
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
antag_flag = "Space Pirates"
required_type = /mob/dead/observer
required_enemies = list(2,2,1,1,1,1,1,0,0,0)
@@ -814,6 +826,7 @@
midround_ruleset_style = MIDROUND_RULESET_STYLE_LIGHT
antag_datum = /datum/antagonist/obsessed
antag_flag = ROLE_OBSESSED
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
restricted_roles = list(
JOB_AI,
JOB_CYBORG,
@@ -857,6 +870,7 @@
antag_datum = /datum/antagonist/changeling/space
antag_flag = ROLE_CHANGELING_MIDROUND
antag_flag_override = ROLE_CHANGELING
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
required_type = /mob/dead/observer
required_enemies = list(2,2,1,1,1,1,1,0,0,0)
required_candidates = 1
@@ -877,6 +891,7 @@
midround_ruleset_style = MIDROUND_RULESET_STYLE_LIGHT
antag_datum = /datum/antagonist/paradox_clone
antag_flag = ROLE_PARADOX_CLONE
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
enemy_roles = list(
JOB_CAPTAIN,
JOB_DETECTIVE,
@@ -254,6 +254,7 @@ GLOBAL_VAR_INIT(revolutionary_win, FALSE)
name = "Wizard"
antag_flag = ROLE_WIZARD
antag_datum = /datum/antagonist/wizard
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
flags = HIGH_IMPACT_RULESET
minimum_required_age = 14
restricted_roles = list(
@@ -395,6 +396,7 @@ GLOBAL_VAR_INIT(revolutionary_win, FALSE)
/datum/dynamic_ruleset/roundstart/nuclear
name = "Nuclear Emergency"
antag_flag = ROLE_OPERATIVE
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
antag_datum = /datum/antagonist/nukeop
var/datum/antagonist/antag_leader_datum = /datum/antagonist/nukeop/leader
minimum_required_age = 14
@@ -618,6 +620,7 @@ GLOBAL_VAR_INIT(revolutionary_win, FALSE)
antag_datum = /datum/antagonist/nukeop/clownop
antag_flag = ROLE_CLOWN_OPERATIVE
antag_flag_override = ROLE_OPERATIVE
ruleset_category = parent_type::ruleset_category | RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
antag_leader_datum = /datum/antagonist/nukeop/leader/clownop
requirements = list(101,101,101,101,101,101,101,101,101,101)
required_role = ROLE_CLOWN_OPERATIVE
@@ -35,6 +35,8 @@ GLOBAL_LIST_EMPTY(lobby_station_traits)
var/dynamic_threat_id
/// If ran during dynamic, do we reduce the total threat? Will be overriden by config if set
var/threat_reduction = 0
/// Which ruleset flags to allow dynamic to use. null to disregard
var/dynamic_category = null
/// Trait should not be instantiated in a round if its type matches this type
var/abstract_type = /datum/station_trait
@@ -45,6 +47,8 @@ GLOBAL_LIST_EMPTY(lobby_station_traits)
if(threat_reduction)
GLOB.dynamic_station_traits[src] = threat_reduction
if(dynamic_category)
GLOB.dynamic_ruleset_categories = dynamic_category
if(sign_up_button)
GLOB.lobby_station_traits += src
if(trait_processes)
@@ -562,3 +562,15 @@
#undef SKUB_IDFC
#undef RANDOM_SKUB
/// Crew don't ever spawn as enemies of the station. Obsesseds, blob infection, space changelings etc can still happen though
/datum/station_trait/background_checks
name = "Station-Wide Background Checks"
report_message = "We replaced the intern doing your crew's background checks with a trained screener for this shift! That said, our enemies may just find another way to infiltrate the station, so be careful."
trait_type = STATION_TRAIT_NEUTRAL
weight = 1
show_in_report = TRUE
can_revert = FALSE
dynamic_category = RULESET_CATEGORY_NO_WITTING_CREW_ANTAGONISTS
threat_reduction = 15
dynamic_threat_id = "Background Checks"
@@ -1,7 +1,6 @@
#define PARTY_COOLDOWN_LENGTH_MIN (6 MINUTES)
#define PARTY_COOLDOWN_LENGTH_MAX (12 MINUTES)
/datum/station_trait/lucky_winner
name = "Lucky winner"
trait_type = STATION_TRAIT_POSITIVE
@@ -31,6 +30,9 @@
new /obj/item/reagent_containers/cup/glass/bottle/beer(toLaunch)
new /obj/effect/pod_landingzone(T, toLaunch)
#undef PARTY_COOLDOWN_LENGTH_MIN
#undef PARTY_COOLDOWN_LENGTH_MAX
/datum/station_trait/galactic_grant
name = "Galactic grant"
trait_type = STATION_TRAIT_POSITIVE
@@ -369,6 +371,3 @@
trait_to_give = STATION_TRAIT_ASSISTANT_GIMMICKS
show_in_report = TRUE
blacklist = list(/datum/station_trait/colored_assistants)
#undef PARTY_COOLDOWN_LENGTH_MIN
#undef PARTY_COOLDOWN_LENGTH_MAX
+2
View File
@@ -162,6 +162,8 @@
"Station": {
"Radioactive Nebula": {
},
"Background Checks": {
}
}
}