From 312760bb011412cd71f69a82879a9cf995192077 Mon Sep 17 00:00:00 2001 From: harryob Date: Thu, 22 Jun 2023 07:33:32 +0100 Subject: [PATCH 01/25] browser assets to be served via the cdn (#3683) more stuff offloaded from byond's slowness the better thank you mso https://github.com/tgstation/tgstation/pull/52681 :cl: server: server's can now support using a cdn for web assets /:cl: --- code/__HELPERS/files.dm | 5 -- code/controllers/subsystem/assets.dm | 14 +++ code/modules/admin/admin_verbs.dm | 1 + code/modules/admin/tabs/round_tab.dm | 31 +++++++ code/modules/asset_cache/asset_cache_item.dm | 6 ++ .../transports/webroot_transport.dm | 87 +++++++++++++++++++ colonialmarines.dme | 1 + config/example/resources.txt | 40 +++++++++ tools/localhost-asset-webroot-server.py | 15 ++++ 9 files changed, 195 insertions(+), 5 deletions(-) create mode 100644 code/modules/asset_cache/transports/webroot_transport.dm create mode 100644 config/example/resources.txt create mode 100644 tools/localhost-asset-webroot-server.py diff --git a/code/__HELPERS/files.dm b/code/__HELPERS/files.dm index 717a2ed5347b..f88fe7168f8d 100644 --- a/code/__HELPERS/files.dm +++ b/code/__HELPERS/files.dm @@ -12,11 +12,6 @@ return text -//Sends resource files to client cache -/client/proc/getFiles() - for(var/file in args) - src << browse_rsc(file) - /client/proc/browse_files(root="data/logs/", max_iterations=10, list/valid_extensions=list(".txt",".log",".htm")) var/path = root diff --git a/code/controllers/subsystem/assets.dm b/code/controllers/subsystem/assets.dm index 283fe79cfead..38e57df93cef 100644 --- a/code/controllers/subsystem/assets.dm +++ b/code/controllers/subsystem/assets.dm @@ -7,6 +7,20 @@ SUBSYSTEM_DEF(assets) var/list/preload = list() var/datum/asset_transport/transport = new() +/datum/controller/subsystem/assets/OnConfigLoad() + var/newtransporttype = /datum/asset_transport + switch (CONFIG_GET(string/asset_transport)) + if ("webroot") + newtransporttype = /datum/asset_transport/webroot + + if (newtransporttype == transport.type) + return + + var/datum/asset_transport/newtransport = new newtransporttype () + if (newtransport.validate_config()) + transport = newtransport + transport.Load() + /datum/controller/subsystem/assets/Initialize() for(var/type in typesof(/datum/asset)) var/datum/asset/A = type diff --git a/code/modules/admin/admin_verbs.dm b/code/modules/admin/admin_verbs.dm index d21188615785..debffa9b25b0 100644 --- a/code/modules/admin/admin_verbs.dm +++ b/code/modules/admin/admin_verbs.dm @@ -176,6 +176,7 @@ var/list/admin_verbs_server = list( /client/proc/cmd_admin_delete, /*delete an instance/object/mob/etc*/ /client/proc/cmd_debug_del_all, /datum/admins/proc/togglejoin, + /client/proc/toggle_cdn, ) var/list/admin_verbs_debug = list( diff --git a/code/modules/admin/tabs/round_tab.dm b/code/modules/admin/tabs/round_tab.dm index 980de9eed855..deb27e73f7dc 100644 --- a/code/modules/admin/tabs/round_tab.dm +++ b/code/modules/admin/tabs/round_tab.dm @@ -181,3 +181,34 @@ else to_chat(usr, "Error: Start Now: Game has already started.") return FALSE + +/client/proc/toggle_cdn() + set name = "Toggle CDN" + set category = "Server" + var/static/admin_disabled_cdn_transport = null + if(alert(usr, "Are you sure you want to toggle CDN asset transport?", "Confirm", "Yes", "No") != "Yes") + return + + var/current_transport = CONFIG_GET(string/asset_transport) + if(!current_transport || current_transport == "simple") + if(admin_disabled_cdn_transport) + CONFIG_SET(string/asset_transport, admin_disabled_cdn_transport) + admin_disabled_cdn_transport = null + SSassets.OnConfigLoad() + message_admins("[key_name_admin(usr)] re-enabled the CDN asset transport") + log_admin("[key_name(usr)] re-enabled the CDN asset transport") + return + + to_chat(usr, SPAN_ADMINNOTICE("The CDN is not enabled!")) + if(alert(usr, "CDN asset transport is not enabled! If you're having issues with assets, you can also try disabling filename mutations.", "CDN asset transport is not enabled!", "Try disabling filename mutations", "Nevermind") == "Try disabling filename mutations") + SSassets.transport.dont_mutate_filenames = !SSassets.transport.dont_mutate_filenames + message_admins("[key_name_admin(usr)] [(SSassets.transport.dont_mutate_filenames ? "disabled" : "re-enabled")] asset filename transforms.") + log_admin("[key_name(usr)] [(SSassets.transport.dont_mutate_filenames ? "disabled" : "re-enabled")] asset filename transforms.") + return + + admin_disabled_cdn_transport = current_transport + CONFIG_SET(string/asset_transport, "simple") + SSassets.OnConfigLoad() + SSassets.transport.dont_mutate_filenames = TRUE + message_admins("[key_name_admin(usr)] disabled CDN asset transport") + log_admin("[key_name(usr)] disabled CDN asset transport") diff --git a/code/modules/asset_cache/asset_cache_item.dm b/code/modules/asset_cache/asset_cache_item.dm index 52ebc7190372..72d976bf11f1 100644 --- a/code/modules/asset_cache/asset_cache_item.dm +++ b/code/modules/asset_cache/asset_cache_item.dm @@ -33,3 +33,9 @@ if (extstart) ext = ".[copytext(name, extstart+1)]" resource = file + +/datum/asset_cache_item/vv_edit_var(var_name, var_value) + return FALSE + +/datum/asset_cache_item/CanProcCall(procname) + return FALSE diff --git a/code/modules/asset_cache/transports/webroot_transport.dm b/code/modules/asset_cache/transports/webroot_transport.dm new file mode 100644 index 000000000000..e3cb33b8fabf --- /dev/null +++ b/code/modules/asset_cache/transports/webroot_transport.dm @@ -0,0 +1,87 @@ +/// CDN Webroot asset transport. +/datum/asset_transport/webroot + name = "CDN Webroot asset transport" + +/datum/asset_transport/webroot/Load() + if (validate_config(log = FALSE)) + load_existing_assets() + +/// Processes thru any assets that were registered before we were loaded as a transport. +/datum/asset_transport/webroot/proc/load_existing_assets() + for (var/asset_name in SSassets.cache) + var/datum/asset_cache_item/ACI = SSassets.cache[asset_name] + save_asset_to_webroot(ACI) + +/// Register a browser asset with the asset cache system +/// We also save it to the CDN webroot at this step instead of waiting for send_assets() +/// asset_name - the identifier of the asset +/// asset - the actual asset file or an asset_cache_item datum. +/datum/asset_transport/webroot/register_asset(asset_name, asset) + . = ..() + var/datum/asset_cache_item/ACI = . + + if (istype(ACI) && ACI.hash) + save_asset_to_webroot(ACI) + +/// Saves the asset to the webroot taking into account namespaces and hashes. +/datum/asset_transport/webroot/proc/save_asset_to_webroot(datum/asset_cache_item/ACI) + var/webroot = CONFIG_GET(string/asset_cdn_webroot) + var/newpath = "[webroot][get_asset_suffex(ACI)]" + if (fexists(newpath)) + return + if (fexists("[newpath].gz")) //its a common pattern in webhosting to save gzip'ed versions of text files and let the webserver serve them up as gzip compressed normal files, sometimes without keeping the original version. + return + return fcopy(ACI.resource, newpath) + +/// Returns a url for a given asset. +/// asset_name - Name of the asset. +/// asset_cache_item - asset cache item datum for the asset, optional, overrides asset_name +/datum/asset_transport/webroot/get_asset_url(asset_name, datum/asset_cache_item/asset_cache_item) + if (!istype(asset_cache_item)) + asset_cache_item = SSassets.cache[asset_name] + var/url = CONFIG_GET(string/asset_cdn_url) //config loading will handle making sure this ends in a / + return "[url][get_asset_suffex(asset_cache_item)]" + +/datum/asset_transport/webroot/proc/get_asset_suffex(datum/asset_cache_item/asset_cache_item) + var/base = "[copytext(asset_cache_item.hash, 1, 3)]/" + var/filename = "asset.[asset_cache_item.hash][asset_cache_item.ext]" + if (length(asset_cache_item.namespace)) + base = "namespaces/[copytext(asset_cache_item.namespace, 1, 3)]/[asset_cache_item.namespace]/" + if (!asset_cache_item.namespace_parent) + filename = "[asset_cache_item.name]" + return base + filename + + +/// webroot asset sending - does nothing unless passed legacy assets +/datum/asset_transport/webroot/send_assets(client/client, list/asset_list) + . = FALSE + var/list/legacy_assets = list() + if (!islist(asset_list)) + asset_list = list(asset_list) + for (var/asset_name in asset_list) + var/datum/asset_cache_item/ACI = asset_list[asset_name] + if (!istype(ACI)) + ACI = SSassets.cache[asset_name] + if (!ACI) + legacy_assets += asset_name //pass it on to base send_assets so it can output an error + continue + if (ACI.legacy) + legacy_assets[asset_name] = ACI + if (length(legacy_assets)) + . = ..(client, legacy_assets) + + +/// webroot slow asset sending - does nothing. +/datum/asset_transport/webroot/send_assets_slow(client/client, list/files, filerate) + return FALSE + +/datum/asset_transport/webroot/validate_config(log = TRUE) + if (!CONFIG_GET(string/asset_cdn_url)) + if (log) + log_asset("ERROR: [type]: Invalid Config: ASSET_CDN_URL") + return FALSE + if (!CONFIG_GET(string/asset_cdn_webroot)) + if (log) + log_asset("ERROR: [type]: Invalid Config: ASSET_CDN_WEBROOT") + return FALSE + return TRUE diff --git a/colonialmarines.dme b/colonialmarines.dme index 6e5bda16e73d..991c23d53bbe 100644 --- a/colonialmarines.dme +++ b/colonialmarines.dme @@ -1382,6 +1382,7 @@ #include "code\modules\asset_cache\assets\tgui.dm" #include "code\modules\asset_cache\assets\vending.dm" #include "code\modules\asset_cache\transports\asset_transport.dm" +#include "code\modules\asset_cache\transports\webroot_transport.dm" #include "code\modules\buildmode\bm-mode.dm" #include "code\modules\buildmode\buildmode.dm" #include "code\modules\buildmode\buttons.dm" diff --git a/config/example/resources.txt b/config/example/resources.txt new file mode 100644 index 000000000000..0f9aaf021aa5 --- /dev/null +++ b/config/example/resources.txt @@ -0,0 +1,40 @@ +# External resources +# Set this to the location of a .zip with the server's .rsc inside of it. +# If you set this mutiple times, the server will rotate between the links. +# To use this, the compile option PRELOAD_RSC must be set to 0 to keep byond from preloading resources +# Resource urls can not be encrypted (https://), as they are downloaded by byond, not IE, and byond can't into encryption + +EXTERNAL_RSC_URLS http://rsc.cm-ss13.com/ + + +######################## +# Browser Asset Config # +######################## +# Browser assets are any file included in interfaces. css, images, javascript, etc. +# This handles configuring how we get these to the player so interfaces can access them. + +# Asset Transport +# The normal way of getting assets to clients is to use the internal byond system. This can be slow and delay the opening of interface windows. It also doesn't allow the internal IE windows byond uses to cache anything. +# You can instead have the server save them to a website via a folder within the game server that the web server can read. This could be a simple webserver or something backed by a CDN. +# Valid values: simple, webroot. Simple is the default. +#ASSET_TRANSPORT webroot + + +# Simple asset transport configurable values. + +# Uncomment this to have the server passively send all browser assets to each client in the background. (instead of waiting for them to be needed) +# This should be uncommented in production and commented in development +#ASSET_SIMPLE_PRELOAD + + +# Webroot asset transport configurable values. + +# Local folder to save assets to. +# Assets will be saved in the format of asset.MD5HASH.EXT or in namespaces/hash/ as ASSET_FILE_NAME or asset.MD5HASH.EXT +#ASSET_CDN_WEBROOT data/asset-store/ + +# URL the folder from above can be accessed from. +# for best results the webserver powering this should return a long cache validity time, as all assets sent via this transport use hash based urls +# Encryption (https) is supported here, but linux clients will have issues if you require higher then tls 1.0. Windows clients down to windows 7 can handle tls 1.2 no issue. +# if you want to test this locally, you simpily run the `localhost-asset-webroot-server.py` python3 script to host assets stored in `data/asset-store/` via http://localhost:58715/ +#ASSET_CDN_URL http://localhost:58715/ diff --git a/tools/localhost-asset-webroot-server.py b/tools/localhost-asset-webroot-server.py new file mode 100644 index 000000000000..31a85a4eb4b5 --- /dev/null +++ b/tools/localhost-asset-webroot-server.py @@ -0,0 +1,15 @@ +#!/usr/bin/env python3 +from http.server import HTTPServer, SimpleHTTPRequestHandler +import os + +class CORSRequestHandler(SimpleHTTPRequestHandler): + def end_headers(self): + self.send_header('Access-Control-Allow-Origin', '*') + self.send_header('Access-Control-Allow-Methods', 'GET') + self.send_header('Cache-Control', 'no-store, no-cache, must-revalidate') + return super(CORSRequestHandler, self).end_headers() + +os.makedirs('../data/asset-store/', exist_ok=True) +os.chdir('../data/asset-store/') +httpd = HTTPServer(('localhost', 58715), CORSRequestHandler) +httpd.serve_forever() From 80ed7b1db0978216080e70fada15926de206448d Mon Sep 17 00:00:00 2001 From: cm13-github <128137806+cm13-github@users.noreply.github.com> Date: Thu, 22 Jun 2023 07:46:25 +0100 Subject: [PATCH 02/25] Automatic changelog for PR #3683 [ci skip] --- html/changelogs/AutoChangeLog-pr-3683.yml | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 html/changelogs/AutoChangeLog-pr-3683.yml diff --git a/html/changelogs/AutoChangeLog-pr-3683.yml b/html/changelogs/AutoChangeLog-pr-3683.yml new file mode 100644 index 000000000000..74f16d9344af --- /dev/null +++ b/html/changelogs/AutoChangeLog-pr-3683.yml @@ -0,0 +1,4 @@ +author: "harryob" +delete-after: True +changes: + - server: "server's can now support using a cdn for web assets" \ No newline at end of file From 95a20695458623bfe9d21a839ba97801315a6627 Mon Sep 17 00:00:00 2001 From: Changelogs Date: Fri, 23 Jun 2023 01:45:52 +0000 Subject: [PATCH 03/25] Automatic changelog compile [ci skip] --- html/changelogs/AutoChangeLog-pr-3683.yml | 4 ---- html/changelogs/archive/2023-06.yml | 3 +++ 2 files changed, 3 insertions(+), 4 deletions(-) delete mode 100644 html/changelogs/AutoChangeLog-pr-3683.yml diff --git a/html/changelogs/AutoChangeLog-pr-3683.yml b/html/changelogs/AutoChangeLog-pr-3683.yml deleted file mode 100644 index 74f16d9344af..000000000000 --- a/html/changelogs/AutoChangeLog-pr-3683.yml +++ /dev/null @@ -1,4 +0,0 @@ -author: "harryob" -delete-after: True -changes: - - server: "server's can now support using a cdn for web assets" \ No newline at end of file diff --git a/html/changelogs/archive/2023-06.yml b/html/changelogs/archive/2023-06.yml index 53b779e0fab1..9e9081238a2a 100644 --- a/html/changelogs/archive/2023-06.yml +++ b/html/changelogs/archive/2023-06.yml @@ -315,3 +315,6 @@ - bugfix: Flashlight gun attachments turn off when they should sg2002: - bugfix: XM88 now correctly notifies the user on the hit streak end. +2023-06-23: + harryob: + - server: server's can now support using a cdn for web assets From 907f2352f8377b12e27610c2f20be64186021e77 Mon Sep 17 00:00:00 2001 From: Drathek <76988376+Drulikar@users.noreply.github.com> Date: Thu, 22 Jun 2023 19:10:23 -0700 Subject: [PATCH 04/25] Xeno Candidate Queue (#3636) # About the pull request This PR changes it so get_alien_candidates is normally a sorted list based generally on timeofdeath in ascending order and larva spawns now pull candidates out of that list in order. That means that an observer that has yet to play, or was the first to die, and still meets all other criteria to become a larva (not AFK, has preferences set to become larva, has been dead long enough, etc.) will be chosen before others. Playing as a facehugger (dying or hugging successfully) or dying in an admin z-levels (such as thunderdome) also do not affect the value used for how you are sorted in the queue. So you should be able to freely play in either of those situations without losing your relative spot in the queue. Of course its not going to nab you out of whatever mob you are playing, but when you are a ghost again the same values will be used to sort you in the queue. Since people may enter and leave the queue each time the queue is checked, your place in the queue may go up or down. It is just a snapshot of that moment where you are. If you missed your queue message, or haven't gotten one yet, the join xeno action will now display the last message for you. # Explain why it's good for the game Picking candidates randomly is okay, but it would be more fair to give privilege to those that have been waiting longer - especially those who have yet to play. # Testing Photographs and Procedure
Screenshots & Videos Example of queen death code (since that was the most altered): ![larva](https://github.com/cmss13-devs/cmss13/assets/76988376/48211b1e-7556-4a41-879f-1dfbfabe8704)
# Changelog :cl: Drathek add: The selection to become a xeno larva is now based on timeofdeath rather than random and also sends a message to all candidates when the queue moves. Playing as a facehugger or on admin z-levels (thunderdome) will not affect your relative place in queue. The join xeno action will also display the last queue message for you when you allow xeno candidacy. fix: Fixed gibbed humans not properly setting their timeofdeath when on an admin z-level. fix: Fixed a bad del on shuttle doors when a shuttle deletes (such as intoTheSunset). /:cl: --------- Co-authored-by: harryob --- code/__DEFINES/mobs.dm | 2 - code/__DEFINES/xeno.dm | 16 +++++ code/__HELPERS/_time.dm | 4 -- code/__HELPERS/cmp.dm | 9 +++ code/__HELPERS/game.dm | 61 +++++++++++++++---- code/_onclick/observer.dm | 4 +- code/game/gamemodes/cm_initialize.dm | 36 ++++++++--- code/modules/client/client_defines.dm | 2 + .../structures/special/pylon_core.dm | 15 ++++- code/modules/mob/dead/observer/observer.dm | 19 ++++-- .../mob/living/carbon/xenomorph/Embryo.dm | 3 +- .../carbon/xenomorph/castes/Facehugger.dm | 1 + .../mob/living/carbon/xenomorph/death.dm | 18 +++--- code/modules/shuttle/helpers.dm | 3 +- code/modules/shuttle/shuttle.dm | 16 ++--- 15 files changed, 155 insertions(+), 54 deletions(-) diff --git a/code/__DEFINES/mobs.dm b/code/__DEFINES/mobs.dm index 495b5fb472c5..ba928e202cf0 100644 --- a/code/__DEFINES/mobs.dm +++ b/code/__DEFINES/mobs.dm @@ -11,8 +11,6 @@ #define OVEREAT_TIME 200 //================================================= -#define ALIEN_SELECT_AFK_BUFFER 1 // How many minutes that a person can be AFK before not being allowed to be an alien. - #define HEAT_DAMAGE_LEVEL_1 2 //Amount of damage applied when your body temperature just passes the 360.15k safety point #define HEAT_DAMAGE_LEVEL_2 4 //Amount of damage applied when your body temperature passes the 400K point #define HEAT_DAMAGE_LEVEL_3 8 //Amount of damage applied when your body temperature passes the 1000K point diff --git a/code/__DEFINES/xeno.dm b/code/__DEFINES/xeno.dm index 6d6bd64ea918..7741beecedef 100644 --- a/code/__DEFINES/xeno.dm +++ b/code/__DEFINES/xeno.dm @@ -154,6 +154,22 @@ #define WEED_BASE_GROW_SPEED (5 SECONDS) #define WEED_BASE_DECAY_SPEED (10 SECONDS) +/// The time you must be dead to join as a xeno larva +#define XENO_JOIN_DEAD_LARVA_TIME (2.5 MINUTES) +/// The time you must be dead to join as xeno (not larva) +#define XENO_JOIN_DEAD_TIME (5 MINUTES) +/// The time of inactivity you cannot exceed to join as a xeno +#define XENO_JOIN_AFK_TIME_LIMIT (5 MINUTES) +/// The amount of time after round start before buried larva spawns are disallowed +#define XENO_BURIED_LARVA_TIME_LIMIT (30 MINUTES) + +/// The time against away_timer when an AFK xeno larva can be replaced +#define XENO_LEAVE_TIMER_LARVA 80 //80 seconds +/// The time against away_timer when an AFK xeno (not larva) can be replaced +#define XENO_LEAVE_TIMER 300 //300 seconds +/// The time against away_timer when an AFK xeno gets listed in the available list so ghosts can get ready +#define XENO_AVAILABLE_TIMER 60 //60 seconds + /// Between 2% to 10% of explosion severity #define WEED_EXPLOSION_DAMAGEMULT rand(2, 10)*0.01 diff --git a/code/__HELPERS/_time.dm b/code/__HELPERS/_time.dm index 85acafa0e2f6..b929ae8636b3 100644 --- a/code/__HELPERS/_time.dm +++ b/code/__HELPERS/_time.dm @@ -15,10 +15,6 @@ #define DECISECONDS_TO_HOURS /36000 -#define XENO_LEAVE_TIMER_LARVA 80 //80 seconds -#define XENO_LEAVE_TIMER 300 //300 seconds -#define XENO_AVAILABLE_TIMER 60 //60 seconds, when to add a xeno to the avaliable list so ghosts can get ready - var/midnight_rollovers = 0 var/rollovercheck_last_timeofday = 0 diff --git a/code/__HELPERS/cmp.dm b/code/__HELPERS/cmp.dm index 4ca0edcf43d0..888e3c2ce657 100644 --- a/code/__HELPERS/cmp.dm +++ b/code/__HELPERS/cmp.dm @@ -57,3 +57,12 @@ var/atom/cmp_dist_origin=null /proc/cmp_typepaths_asc(A, B) return sorttext("[B]","[A]") + +/// Compares mobs based on their timeofdeath value in ascending order +/proc/cmp_mob_deathtime_asc(mob/A, mob/B) + return A.timeofdeath - B.timeofdeath + +/// Compares observers based on their larva_queue_time value in ascending order +/// Assumes the client on the observer is not null +/proc/cmp_obs_larvaqueuetime_asc(mob/dead/observer/A, mob/dead/observer/B) + return A.client.larva_queue_time - B.client.larva_queue_time diff --git a/code/__HELPERS/game.dm b/code/__HELPERS/game.dm index a0bb9dd98423..61976f4dc903 100644 --- a/code/__HELPERS/game.dm +++ b/code/__HELPERS/game.dm @@ -241,35 +241,70 @@ else return get_step(start, EAST) -// Same as above but for alien candidates. -/proc/get_alien_candidates() +/// Get a list of observers that can be alien candidates, optionally sorted by larva_queue_time +/proc/get_alien_candidates(sorted = TRUE) var/list/candidates = list() - for(var/i in GLOB.observer_list) - var/mob/dead/observer/O = i + for(var/mob/dead/observer/cur_obs as anything in GLOB.observer_list) + // Preference check + if(!cur_obs.client || !cur_obs.client.prefs || !(cur_obs.client.prefs.be_special & BE_ALIEN_AFTER_DEATH)) + continue + // Jobban check - if(!O.client || !O.client.prefs || !(O.client.prefs.be_special & BE_ALIEN_AFTER_DEATH) || jobban_isbanned(O, JOB_XENOMORPH)) + if(jobban_isbanned(cur_obs, JOB_XENOMORPH)) continue //players that can still be revived are skipped - if(O.mind && O.mind.original && ishuman(O.mind.original)) - var/mob/living/carbon/human/H = O.mind.original - if (H.check_tod() && H.is_revivable()) + if(cur_obs.mind && cur_obs.mind.original && ishuman(cur_obs.mind.original)) + var/mob/living/carbon/human/cur_human = cur_obs.mind.original + if(cur_human.check_tod() && cur_human.is_revivable()) continue // copied from join as xeno - var/deathtime = world.time - O.timeofdeath - if(deathtime < 3000 && ( !O.client.admin_holder || !(O.client.admin_holder.rights & R_ADMIN)) ) + var/deathtime = world.time - cur_obs.timeofdeath + if(deathtime < XENO_JOIN_DEAD_TIME && ( !cur_obs.client.admin_holder || !(cur_obs.client.admin_holder.rights & R_ADMIN)) ) continue - // Admins and AFK players cannot be drafted - if(O.client.inactivity / 600 > ALIEN_SELECT_AFK_BUFFER + 5 || (O.client.admin_holder && (O.client.admin_holder.rights & R_MOD)) && O.adminlarva == 0) + // AFK players cannot be drafted + if(cur_obs.client.inactivity > XENO_JOIN_AFK_TIME_LIMIT) continue - candidates += O + // Mods with larva protection cannot be drafted + if((cur_obs.client.admin_holder && (cur_obs.client.admin_holder.rights & R_MOD)) && !cur_obs.adminlarva) + continue + + candidates += cur_obs + + // Optionally sort by larva_queue_time + if(sorted && length(candidates)) + candidates = sort_list(candidates, GLOBAL_PROC_REF(cmp_obs_larvaqueuetime_asc)) return candidates +/** + * Messages observers that are currently candidates an update on the queue. + * + * Arguments: + * * candidates - The list of observers from get_alien_candidates() + * * dequeued - How many candidates to skip messaging because they were dequeued + * * cache_only - Whether to not actually send a to_chat message and instead only update larva_queue_cached_message + */ +/proc/message_alien_candidates(list/candidates, dequeued, cache_only = FALSE) + var/new_players = 0 + for(var/i in (1 + dequeued) to candidates.len) + var/mob/dead/observer/cur_obs = candidates[i] + + // Generate the messages + var/cached_message = SPAN_XENONOTICE("You are currently [i-dequeued]\th in the larva queue. There are [new_players] ahead of you that have yet to play this round.") + cur_obs.larva_queue_cached_message = cached_message + if(!cache_only) + var/chat_message = dequeued ? replacetext(cached_message, "currently", "now") : cached_message + to_chat(candidates[i], chat_message) + + // Count how many are prioritized + if(cur_obs.client.larva_queue_time < 2) // 0 and 1 because facehuggers/t-domers are slightly deprioritized + new_players++ + /proc/convert_k2c(temp) return ((temp - T0C)) diff --git a/code/_onclick/observer.dm b/code/_onclick/observer.dm index 21ac66e5f222..5acfe74f2965 100644 --- a/code/_onclick/observer.dm +++ b/code/_onclick/observer.dm @@ -45,11 +45,11 @@ return FALSE var/deathtime = world.time - timeofdeath - if(deathtime < 2.5 MINUTES) + if(deathtime < XENO_JOIN_DEAD_LARVA_TIME) var/message = "You have been dead for [DisplayTimeText(deathtime)]." message = SPAN_WARNING("[message]") to_chat(src, message) - to_chat(src, SPAN_WARNING("You must wait 2.5 minutes before rejoining the game!")) + to_chat(src, SPAN_WARNING("You must wait atleast 2.5 minutes before rejoining the game!")) ManualFollow(target) return FALSE diff --git a/code/game/gamemodes/cm_initialize.dm b/code/game/gamemodes/cm_initialize.dm index 8237fc63b7e2..2f6dc6e38118 100644 --- a/code/game/gamemodes/cm_initialize.dm +++ b/code/game/gamemodes/cm_initialize.dm @@ -354,7 +354,7 @@ Additional game mode variables. var/datum/hive_status/hive for(var/hivenumber in GLOB.hive_datum) hive = GLOB.hive_datum[hivenumber] - if(!hive.hardcore && hive.stored_larva && (hive.hive_location || (world.time < 30 MINUTES + SSticker.round_start_time))) + if(!hive.hardcore && hive.stored_larva && (hive.hive_location || (world.time < XENO_BURIED_LARVA_TIME_LIMIT + SSticker.round_start_time))) if(SSticker.mode && (SSticker.mode.flags_round_type & MODE_RANDOM_HIVE)) available_xenos |= "any buried larva" LAZYADD(available_xenos["any buried larva"], hive) @@ -364,7 +364,27 @@ Additional game mode variables. available_xenos[larva_option] = list(hive) if(!available_xenos.len || (instant_join && !available_xenos_non_ssd.len)) - to_chat(xeno_candidate, SPAN_WARNING("There aren't any available xenomorphs or burrowed larvae. You can try getting spawned as a chestburster larva by toggling your Xenomorph candidacy in Preferences -> Toggle SpecialRole Candidacy.")) + if(!xeno_candidate.client || !xeno_candidate.client.prefs || !(xeno_candidate.client.prefs.be_special & BE_ALIEN_AFTER_DEATH)) + to_chat(xeno_candidate, SPAN_WARNING("There aren't any available xenomorphs or burrowed larvae. You can try getting spawned as a chestburster larva by toggling your Xenomorph candidacy in Preferences -> Toggle SpecialRole Candidacy.")) + return FALSE + to_chat(xeno_candidate, SPAN_WARNING("There aren't any available xenomorphs or burrowed larvae.")) + + // Give the player a cached message of their queue status if they are an observer + var/mob/dead/observer/candidate_observer = xeno_candidate + if(istype(candidate_observer)) + if(candidate_observer.larva_queue_cached_message) + to_chat(xeno_candidate, candidate_observer.larva_queue_cached_message) + return FALSE + + // No cache, lets check now then + message_alien_candidates(get_alien_candidates(), dequeued = 0, cache_only = TRUE) + if(candidate_observer.larva_queue_cached_message) + to_chat(xeno_candidate, candidate_observer.larva_queue_cached_message) + return FALSE + + // We aren't in queue yet, lets teach them about the queue then + candidate_observer.larva_queue_cached_message = SPAN_XENONOTICE("You are currently still awaiting assignment in the larva queue. Priority is given to players who have yet to play in the round, but otherwise the ordering is based on your time of death. When you have been dead long enough and are not inactive, you will periodically receive messages where you are in the queue relative to other currently valid xeno candidates. Note: Playing as a facehugger or in the thunderdome will not alter your time of death. This means you won't lose your relative place in queue if you step away, disconnect, play as a facehugger, or play in the thunderdome.") + to_chat(xeno_candidate, candidate_observer.larva_queue_cached_message) return FALSE var/mob/living/carbon/xenomorph/new_xeno @@ -377,11 +397,11 @@ Additional game mode variables. if(!xeno_bypass_timer) var/deathtime = world.time - xeno_candidate.timeofdeath if(isnewplayer(xeno_candidate)) - deathtime = 2.5 MINUTES //so new players don't have to wait to latejoin as xeno in the round's first 5 mins. - if(deathtime < 2.5 MINUTES && !check_client_rights(xeno_candidate.client, R_ADMIN, FALSE)) + deathtime = XENO_JOIN_DEAD_LARVA_TIME //so new players don't have to wait to latejoin as xeno in the round's first 5 mins. + if(deathtime < XENO_JOIN_DEAD_LARVA_TIME && !check_client_rights(xeno_candidate.client, R_ADMIN, FALSE)) var/message = SPAN_WARNING("You have been dead for [DisplayTimeText(deathtime)].") to_chat(xeno_candidate, message) - to_chat(xeno_candidate, SPAN_WARNING("You must wait 2.5 minutes before rejoining the game as a buried larva!")) + to_chat(xeno_candidate, SPAN_WARNING("You must wait 2 minutes and 30 seconds before rejoining the game as a buried larva!")) return FALSE for(var/mob_name in picked_hive.banished_ckeys) @@ -393,7 +413,7 @@ Additional game mode variables. noob.close_spawn_windows() if(picked_hive.hive_location) picked_hive.hive_location.spawn_burrowed_larva(xeno_candidate) - else if((world.time < 30 MINUTES + SSticker.round_start_time)) + else if((world.time < XENO_BURIED_LARVA_TIME_LIMIT + SSticker.round_start_time)) picked_hive.do_buried_larva_spawn(xeno_candidate) else to_chat(xeno_candidate, SPAN_WARNING("Seems like something went wrong. Try again?")) @@ -417,8 +437,8 @@ Additional game mode variables. if(!xeno_bypass_timer) var/deathtime = world.time - xeno_candidate.timeofdeath if(istype(xeno_candidate, /mob/new_player)) - deathtime = 5 MINUTES //so new players don't have to wait to latejoin as xeno in the round's first 5 mins. - if(deathtime < 5 MINUTES && !check_client_rights(xeno_candidate.client, R_ADMIN, FALSE)) + deathtime = XENO_JOIN_DEAD_TIME //so new players don't have to wait to latejoin as xeno in the round's first 5 mins. + if(deathtime < XENO_JOIN_DEAD_TIME && !check_client_rights(xeno_candidate.client, R_ADMIN, FALSE)) var/message = "You have been dead for [DisplayTimeText(deathtime)]." message = SPAN_WARNING("[message]") to_chat(xeno_candidate, message) diff --git a/code/modules/client/client_defines.dm b/code/modules/client/client_defines.dm index 8f0939474427..fbec4aa13f36 100644 --- a/code/modules/client/client_defines.dm +++ b/code/modules/client/client_defines.dm @@ -26,6 +26,8 @@ var/adminobs = null var/area = null var/time_died_as_mouse = null //when the client last died as a mouse + /// The descriminator for larva queue ordering: Generally set to timeofdeath except for facehuggers/admin z-level play + var/larva_queue_time var/donator = 0 var/adminhelped = 0 diff --git a/code/modules/cm_aliens/structures/special/pylon_core.dm b/code/modules/cm_aliens/structures/special/pylon_core.dm index 9376e2b6e914..08aa2f86c1bc 100644 --- a/code/modules/cm_aliens/structures/special/pylon_core.dm +++ b/code/modules/cm_aliens/structures/special/pylon_core.dm @@ -108,6 +108,7 @@ var/last_healed = 0 var/last_attempt = 0 // logs time of last attempt to prevent spam. if you want to destroy it, you must commit. var/last_larva_time = 0 + var/last_larva_queue_time = 0 var/last_surge_time = 0 var/spawn_cooldown = 30 SECONDS var/surge_cooldown = 90 SECONDS @@ -142,11 +143,19 @@ linked_hive.hive_ui.update_burrowed_larva() qdel(L) - if((last_larva_time + spawn_cooldown) < world.time && can_spawn_larva()) // every minute + var/spawning_larva = can_spawn_larva() && (last_larva_time + spawn_cooldown) < world.time + if(spawning_larva) last_larva_time = world.time + if(spawning_larva || (last_larva_queue_time + spawn_cooldown * 4) < world.time) + last_larva_queue_time = world.time var/list/players_with_xeno_pref = get_alien_candidates() - if(players_with_xeno_pref && players_with_xeno_pref.len && can_spawn_larva()) - spawn_burrowed_larva(pick(players_with_xeno_pref)) + if(players_with_xeno_pref && players_with_xeno_pref.len) + if(spawning_larva && spawn_burrowed_larva(players_with_xeno_pref[1])) + // We were in spawning_larva mode and successfully spawned someone + message_alien_candidates(players_with_xeno_pref, dequeued = 1) + else + // Just time to update everyone their queue status (or the spawn failed) + message_alien_candidates(players_with_xeno_pref, dequeued = 0) if(linked_hive.hijack_burrowed_surge && (last_surge_time + surge_cooldown) < world.time) last_surge_time = world.time diff --git a/code/modules/mob/dead/observer/observer.dm b/code/modules/mob/dead/observer/observer.dm index 47e747d4cd5c..fcb95a6fd783 100644 --- a/code/modules/mob/dead/observer/observer.dm +++ b/code/modules/mob/dead/observer/observer.dm @@ -33,8 +33,8 @@ plane = GHOST_PLANE layer = ABOVE_FLY_LAYER stat = DEAD - var/adminlarva = 0 - var/ghostvision = 1 + var/adminlarva = FALSE + var/ghostvision = TRUE var/can_reenter_corpse var/started_as_observer //This variable is set to 1 when you enter the game as an observer. //If you died in the game and are a ghost - this will remain as null. @@ -45,7 +45,7 @@ "Squad HUD" = FALSE, "Xeno Status HUD" = FALSE ) - universal_speak = 1 + universal_speak = TRUE var/updatedir = TRUE //Do we have to update our dir as the ghost moves around? var/atom/movable/following = null var/datum/orbit_menu/orbit_menu @@ -55,6 +55,8 @@ var/own_orbit_size = 0 var/observer_actions = list(/datum/action/observer_action/join_xeno) var/datum/action/minimap/observer/minimap + var/larva_queue_cached_message + alpha = 127 /mob/dead/observer/verb/toggle_ghostsee() @@ -327,8 +329,8 @@ Works together with spawning an observer, noted above. ghost.langchat_make_image() SStgui.on_transfer(src, ghost) - if(is_admin_level(z)) - ghost.timeofdeath = 0 // Bypass respawn limit if you die on the admin zlevel + if(is_admin_level((get_turf(src))?.z)) // Gibbed humans ghostize the brain in their head which itself is z 0 + ghost.timeofdeath = 1 // Bypass respawn limit if you die on the admin zlevel ghost.key = key ghost.mind = mind @@ -363,6 +365,12 @@ Works together with spawning an observer, noted above. if(ghost.client.player_data) ghost.client.player_data.load_timestat_data() + // Larva queue: We use the larger of their existing queue time or the new timeofdeath except for facehuggers + // We don't change facehugger timeofdeath because they are still on cooldown if they died as a hugger + // Facehuggers are atleast 1 because they did get some action compared to those at 0 timeofdeath + var/new_tod = isfacehugger(src) ? 1 : ghost.timeofdeath + ghost.client.larva_queue_time = max(ghost.client.larva_queue_time, new_tod) + ghost.set_huds_from_prefs() return ghost @@ -405,6 +413,7 @@ This is the proc mobs get to turn into a ghost. Forked from ghostize due to comp var/mob/dead/observer/ghost = ghostize((is_nested && nest && !QDELETED(nest))) //FALSE parameter is so we can never re-enter our body, "Charlie, you can never come baaaack~" :3 if(ghost && !is_admin_level(z)) ghost.timeofdeath = world.time + ghost.client?.larva_queue_time = world.time if(is_nested && nest && !QDELETED(nest)) ghost.can_reenter_corpse = FALSE nest.ghost_of_buckled_mob = ghost diff --git a/code/modules/mob/living/carbon/xenomorph/Embryo.dm b/code/modules/mob/living/carbon/xenomorph/Embryo.dm index e03f225ccade..a74c82026dbe 100644 --- a/code/modules/mob/living/carbon/xenomorph/Embryo.dm +++ b/code/modules/mob/living/carbon/xenomorph/Embryo.dm @@ -157,7 +157,8 @@ var/list/candidates = get_alien_candidates() if(candidates && candidates.len) - picked = pick(candidates) + picked = candidates[1] + message_alien_candidates(candidates, dequeued = 1) // Spawn the larva var/mob/living/carbon/xenomorph/larva/new_xeno diff --git a/code/modules/mob/living/carbon/xenomorph/castes/Facehugger.dm b/code/modules/mob/living/carbon/xenomorph/castes/Facehugger.dm index d9ab8a1e849d..c0b57af9d3db 100644 --- a/code/modules/mob/living/carbon/xenomorph/castes/Facehugger.dm +++ b/code/modules/mob/living/carbon/xenomorph/castes/Facehugger.dm @@ -155,6 +155,7 @@ for(var/mob/dead/observer/observer as anything in GLOB.observer_list) to_chat(observer, SPAN_DEADSAY("[human] has been facehugged by [src]" + " [OBSERVER_JMP(observer, human)]")) to_chat(src, SPAN_DEADSAY("[human] has been facehugged by [src]")) + timeofdeath = 1 // Ever so slightly deprioritized for larva queue qdel(src) if(hug_area) xeno_message(SPAN_XENOMINORWARNING("You sense that [src] has facehugged a host at \the [hug_area]!"), 1, src.hivenumber) diff --git a/code/modules/mob/living/carbon/xenomorph/death.dm b/code/modules/mob/living/carbon/xenomorph/death.dm index ce3f55700753..f3534318f673 100644 --- a/code/modules/mob/living/carbon/xenomorph/death.dm +++ b/code/modules/mob/living/carbon/xenomorph/death.dm @@ -37,12 +37,13 @@ if(GLOB.hive_datum[hivenumber].stored_larva) GLOB.hive_datum[hivenumber].stored_larva = round(GLOB.hive_datum[hivenumber].stored_larva * 0.5) //Lose half on dead queen - var/turf/larva_spawn + var/list/players_with_xeno_pref = get_alien_candidates() - while(GLOB.hive_datum[hivenumber].stored_larva > 0 && istype(GLOB.hive_datum[hivenumber].hive_location, /obj/effect/alien/resin/special/pylon/core)) // stil some left - larva_spawn = get_turf(GLOB.hive_datum[hivenumber].hive_location) - if(players_with_xeno_pref && players_with_xeno_pref.len) - var/mob/xeno_candidate = pick(players_with_xeno_pref) + if(players_with_xeno_pref && istype(GLOB.hive_datum[hivenumber].hive_location, /obj/effect/alien/resin/special/pylon/core)) + var/turf/larva_spawn = get_turf(GLOB.hive_datum[hivenumber].hive_location) + var/count = 0 + while(GLOB.hive_datum[hivenumber].stored_larva > 0 && count < length(players_with_xeno_pref)) // still some left + var/mob/xeno_candidate = players_with_xeno_pref[++count] var/mob/living/carbon/xenomorph/larva/new_xeno = new /mob/living/carbon/xenomorph/larva(larva_spawn) new_xeno.set_hive_and_update(hivenumber) @@ -50,11 +51,14 @@ if(!SSticker.mode.transfer_xeno(xeno_candidate, new_xeno)) qdel(new_xeno) return + new_xeno.visible_message(SPAN_XENODANGER("A larva suddenly burrows out of the ground!"), SPAN_XENODANGER("You burrow out of the ground after feeling an immense tremor through the hive, which quickly fades into complete silence...")) - GLOB.hive_datum[hivenumber].stored_larva-- - GLOB.hive_datum[hivenumber].hive_ui.update_burrowed_larva() + GLOB.hive_datum[hivenumber].stored_larva-- + GLOB.hive_datum[hivenumber].hive_ui.update_burrowed_larva() + if(count) + message_alien_candidates(players_with_xeno_pref, dequeued = count) if(hive && hive.living_xeno_queen == src) xeno_message(SPAN_XENOANNOUNCE("A sudden tremor ripples through the hive... the Queen has been slain! Vengeance!"),3, hivenumber) diff --git a/code/modules/shuttle/helpers.dm b/code/modules/shuttle/helpers.dm index 14cfcc3cd691..1d841581faa0 100644 --- a/code/modules/shuttle/helpers.dm +++ b/code/modules/shuttle/helpers.dm @@ -8,7 +8,8 @@ /datum/door_controller/aggregate/Destroy(force, ...) . = ..() - QDEL_NULL_LIST(door_controllers) + QDEL_LIST_ASSOC_VAL(door_controllers) + door_controllers = null /datum/door_controller/aggregate/proc/set_label(label) for(var/datum/door_controller/single/cont in door_controllers) diff --git a/code/modules/shuttle/shuttle.dm b/code/modules/shuttle/shuttle.dm index 77ba9681ebb6..7e181ed470cb 100644 --- a/code/modules/shuttle/shuttle.dm +++ b/code/modules/shuttle/shuttle.dm @@ -628,15 +628,15 @@ /obj/docking_port/mobile/proc/intoTheSunset() // Loop over mobs - for(var/t in return_turfs()) - var/turf/T = t - for(var/mob/living/L in T.GetAllContents()) + for(var/turf/turf as anything in return_turfs()) + for(var/mob/living/mob in turf.GetAllContents()) // Ghostize them and put them in nullspace stasis (for stat & possession checks) - //L.notransform = TRUE - var/mob/dead/observer/O = L.ghostize(FALSE) - if(O) - O.timeofdeath = world.time - L.moveToNullspace() + //mob.notransform = TRUE + var/mob/dead/observer/obs = mob.ghostize(FALSE) + if(obs) + obs.timeofdeath = world.time + obs.client?.larva_queue_time = world.time + mob.moveToNullspace() // Now that mobs are stowed, delete the shuttle jumpToNullSpace() From 2d9c4526bf4ffe45c5d8ad72493c83b0a2d18371 Mon Sep 17 00:00:00 2001 From: cm13-github <128137806+cm13-github@users.noreply.github.com> Date: Fri, 23 Jun 2023 03:19:01 +0100 Subject: [PATCH 05/25] Automatic changelog for PR #3636 [ci skip] --- html/changelogs/AutoChangeLog-pr-3636.yml | 6 ++++++ 1 file changed, 6 insertions(+) create mode 100644 html/changelogs/AutoChangeLog-pr-3636.yml diff --git a/html/changelogs/AutoChangeLog-pr-3636.yml b/html/changelogs/AutoChangeLog-pr-3636.yml new file mode 100644 index 000000000000..a1dcf5fbeb71 --- /dev/null +++ b/html/changelogs/AutoChangeLog-pr-3636.yml @@ -0,0 +1,6 @@ +author: "Drathek" +delete-after: True +changes: + - rscadd: "The selection to become a xeno larva is now based on timeofdeath rather than random and also sends a message to all candidates when the queue moves. Playing as a facehugger or on admin z-levels (thunderdome) will not affect your relative place in queue. The join xeno action will also display the last queue message for you when you allow xeno candidacy." + - bugfix: "Fixed gibbed humans not properly setting their timeofdeath when on an admin z-level." + - bugfix: "Fixed a bad del on shuttle doors when a shuttle deletes (such as intoTheSunset)." \ No newline at end of file From 84252782a8eb1e45987d81945b67bfd7dad1f2bd Mon Sep 17 00:00:00 2001 From: Cursor <102828457+theselfish@users.noreply.github.com> Date: Fri, 23 Jun 2023 07:59:10 +0100 Subject: [PATCH 06/25] Adds the Corpsman Helmet to Req (#3692) # About the pull request Wanna know what the rarest marine helmet is? Basic grunt, squad level I mean. The Medic helmet. Can't get it from Req, or nothing. And most folks dump them anyway because they wanna drop their flags. # Explain why it's good for the game If you want to replace it, it's near impossible. If you wanna deploy as a FOB Surgeon you have to stick with a grunt helmet. This makes that better. It, as before has the exact same stats and usage as a regular helmet. If we can give tech helmets to everyone (don't get me started) then we should be able to give red crosses to everyone. # Testing Photographs and Procedure
Screenshots & Videos Put screenshots and videos here with an empty line between the screenshots and the `
` tags.
# Changelog :cl: qol: Added the Corpsman Helmet to Req's surplus vendor. /:cl: --- code/game/machinery/vending/vendor_types/requisitions.dm | 1 + 1 file changed, 1 insertion(+) diff --git a/code/game/machinery/vending/vendor_types/requisitions.dm b/code/game/machinery/vending/vendor_types/requisitions.dm index 250a998f38bf..838b21a00e6f 100644 --- a/code/game/machinery/vending/vendor_types/requisitions.dm +++ b/code/game/machinery/vending/vendor_types/requisitions.dm @@ -426,6 +426,7 @@ list("ARMOR", -1, null, null), list("M10 Pattern Marine Helmet", 20, /obj/item/clothing/head/helmet/marine, VENDOR_ITEM_REGULAR), list("M10 Pattern Technician Helmet", 20, /obj/item/clothing/head/helmet/marine/tech, VENDOR_ITEM_REGULAR), + list("M10 Pattern Corpman Helmet", 20, /obj/item/clothing/head/helmet/marine/medic, VENDOR_ITEM_REGULAR), list("M3 Pattern Carrier Marine Armor", 20, /obj/item/clothing/suit/storage/marine/carrier, VENDOR_ITEM_REGULAR), list("M3 Pattern Padded Marine Armor", 20, /obj/item/clothing/suit/storage/marine/padded, VENDOR_ITEM_REGULAR), list("M3 Pattern Padless Marine Armor", 20, /obj/item/clothing/suit/storage/marine/padless, VENDOR_ITEM_REGULAR), From e4b50ad01bccbad4dd6f1bba31af53807c2b64f4 Mon Sep 17 00:00:00 2001 From: cm13-github <128137806+cm13-github@users.noreply.github.com> Date: Fri, 23 Jun 2023 08:12:27 +0100 Subject: [PATCH 07/25] Automatic changelog for PR #3692 [ci skip] --- html/changelogs/AutoChangeLog-pr-3692.yml | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 html/changelogs/AutoChangeLog-pr-3692.yml diff --git a/html/changelogs/AutoChangeLog-pr-3692.yml b/html/changelogs/AutoChangeLog-pr-3692.yml new file mode 100644 index 000000000000..cf20a4947af4 --- /dev/null +++ b/html/changelogs/AutoChangeLog-pr-3692.yml @@ -0,0 +1,4 @@ +author: "theselfish" +delete-after: True +changes: + - qol: "Added the Corpsman Helmet to Req's surplus vendor." \ No newline at end of file From 89baad17a584cdfadac861abba63a21443b0fc11 Mon Sep 17 00:00:00 2001 From: forest2001 <41653574+realforest2001@users.noreply.github.com> Date: Fri, 23 Jun 2023 08:03:04 +0100 Subject: [PATCH 08/25] Logging Improvements (#3652) # About the pull request Makes admin deadchat logs clearer # Explain why it's good for the game Logs being confusing isn't good # Testing Photographs and Procedure
Screenshots & Videos Put screenshots and videos here with an empty line between the screenshots and the `
` tags.
# Changelog :cl: admin: Improves logging for admin deadchat. admin: Adds logging for xeno evolution. /:cl: --- code/modules/admin/verbs/deadsay.dm | 2 +- code/modules/mob/living/carbon/xenomorph/Evolution.dm | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/code/modules/admin/verbs/deadsay.dm b/code/modules/admin/verbs/deadsay.dm index be8a5693df6e..700d42808a07 100644 --- a/code/modules/admin/verbs/deadsay.dm +++ b/code/modules/admin/verbs/deadsay.dm @@ -23,7 +23,7 @@ stafftype = "[admin_holder.rank]" msg = strip_html(msg) - log_admin("[key_name(src)] : [msg]") + log_admin("DEAD: [key_name(src)] : [msg]") if (!msg) return diff --git a/code/modules/mob/living/carbon/xenomorph/Evolution.dm b/code/modules/mob/living/carbon/xenomorph/Evolution.dm index 1f88643db764..4806f7528582 100644 --- a/code/modules/mob/living/carbon/xenomorph/Evolution.dm +++ b/code/modules/mob/living/carbon/xenomorph/Evolution.dm @@ -140,6 +140,7 @@ if(3) hive.tier_3_xenos |= new_xeno + log_game("EVOLVE: [key_name(src)] evolved into [new_xeno].") if(mind) mind.transfer_to(new_xeno) else @@ -327,6 +328,7 @@ qdel(new_xeno) return + log_game("EVOLVE: [key_name(src)] de-evolved into [new_xeno].") if(mind) mind.transfer_to(new_xeno) else From cc7a9099bc2dbe6c1807080d66c9fdb4d28d7cbc Mon Sep 17 00:00:00 2001 From: cm13-github <128137806+cm13-github@users.noreply.github.com> Date: Fri, 23 Jun 2023 08:26:49 +0100 Subject: [PATCH 09/25] Automatic changelog for PR #3652 [ci skip] --- html/changelogs/AutoChangeLog-pr-3652.yml | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 html/changelogs/AutoChangeLog-pr-3652.yml diff --git a/html/changelogs/AutoChangeLog-pr-3652.yml b/html/changelogs/AutoChangeLog-pr-3652.yml new file mode 100644 index 000000000000..d95df39d8567 --- /dev/null +++ b/html/changelogs/AutoChangeLog-pr-3652.yml @@ -0,0 +1,5 @@ +author: "realforest2001" +delete-after: True +changes: + - admin: "Improves logging for admin deadchat." + - admin: "Adds logging for xeno evolution." \ No newline at end of file From f994b37c622bd40bab67fb44128fda4c89efbb48 Mon Sep 17 00:00:00 2001 From: morrowwolf Date: Fri, 23 Jun 2023 13:01:56 -0400 Subject: [PATCH 10/25] Fixes gun light attachment issues (#3696) # About the pull request Remember, when you move an object around you drop it. Fun. This PR should fix two things: Lights not being disconnected from a mob and back to the gun when dropping a gun with a light. Light attachments turning off when moving a weapon around. Uuuuh my bad. Somehow missed this in testing. # Explain why it's good for the game Bugs bad. # Testing Photographs and Procedure
Screenshots & Videos Put screenshots and videos here with an empty line between the screenshots and the `
` tags.
# Changelog :cl: Morrow fix: Fixed two gun light attachment issues /:cl: --- code/modules/projectiles/gun_helpers.dm | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) diff --git a/code/modules/projectiles/gun_helpers.dm b/code/modules/projectiles/gun_helpers.dm index 2cfd827b1fc2..d8ea29cd92f8 100644 --- a/code/modules/projectiles/gun_helpers.dm +++ b/code/modules/projectiles/gun_helpers.dm @@ -143,7 +143,7 @@ As sniper rifles have both and weapon mods can change them as well. ..() deals w /obj/item/weapon/gun/dropped(mob/user) . = ..() - turn_off_light(user) + disconnect_light_from_mob(user) var/delay_left = (last_fired + fire_delay + additional_fire_group_delay) - world.time if(fire_delay_group && delay_left > 0) @@ -160,16 +160,28 @@ As sniper rifles have both and weapon mods can change them as well. ..() deals w for(var/group in fire_delay_group) LAZYSET(user.fire_delay_next_fire, group, world.time + delay_left) -/obj/item/weapon/gun/proc/turn_off_light(mob/bearer) +/// This function disconnects the luminosity from the mob and back to the gun +/obj/item/weapon/gun/proc/disconnect_light_from_mob(mob/bearer) if (!(flags_gun_features & GUN_FLASHLIGHT_ON)) return FALSE for (var/slot in attachments) var/obj/item/attachable/attachment = attachments[slot] if (!attachment || !attachment.light_mod) continue + bearer.SetLuminosity(0, FALSE, src) + SetLuminosity(attachment.light_mod) + return TRUE + return FALSE +/// This function actually turns the lights on the gun off +/obj/item/weapon/gun/proc/turn_off_light(mob/bearer) + if (!(flags_gun_features & GUN_FLASHLIGHT_ON)) + return FALSE + for (var/slot in attachments) + var/obj/item/attachable/attachment = attachments[slot] + if (!attachment || !attachment.light_mod) + continue attachment.activate_attachment(src, bearer) - return TRUE return FALSE From 902e7cd1e9bde157c6cc84580fe7fb099dc22b86 Mon Sep 17 00:00:00 2001 From: cm13-github <128137806+cm13-github@users.noreply.github.com> Date: Fri, 23 Jun 2023 18:10:45 +0100 Subject: [PATCH 11/25] Automatic changelog for PR #3696 [ci skip] --- html/changelogs/AutoChangeLog-pr-3696.yml | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 html/changelogs/AutoChangeLog-pr-3696.yml diff --git a/html/changelogs/AutoChangeLog-pr-3696.yml b/html/changelogs/AutoChangeLog-pr-3696.yml new file mode 100644 index 000000000000..dabfba255741 --- /dev/null +++ b/html/changelogs/AutoChangeLog-pr-3696.yml @@ -0,0 +1,4 @@ +author: "Morrow" +delete-after: True +changes: + - bugfix: "Fixed two gun light attachment issues" \ No newline at end of file From 3aa4f199eca4870c681b66406726cc78bff0b983 Mon Sep 17 00:00:00 2001 From: Drathek <76988376+Drulikar@users.noreply.github.com> Date: Fri, 23 Jun 2023 10:07:04 -0700 Subject: [PATCH 12/25] Fix erronous flamer_tank is empty messages and add sfx to empty canister verb (#3623) # About the pull request This PR is a followup to #3357 to fix an incorrect message discovered when reviewing that PR as well as to make the existing empty_reagents verb behave the same as the empty_reagents verb added in that PR. # Explain why it's good for the game The messages sent to the user should be accurate, and verbs should have consistent behavior. # Testing Photographs and Procedure
Screenshots & Videos [Refill](https://github.com/cmss13-devs/cmss13/assets/76988376/50b1cbca-ac0f-4856-9e27-8d1004c722f0)
# Changelog :cl: Drathek fix: Fixed erroneous is empty messages when inserting tanks into a flamer pack. soundadd: Added the refill sfx when using the empty canister verb on flamer tanks. /:cl: --------- Co-authored-by: harryob --- code/modules/projectiles/magazines/flamer.dm | 19 ++++++++++--------- 1 file changed, 10 insertions(+), 9 deletions(-) diff --git a/code/modules/projectiles/magazines/flamer.dm b/code/modules/projectiles/magazines/flamer.dm index 782b6bfe8910..787a0585640a 100644 --- a/code/modules/projectiles/magazines/flamer.dm +++ b/code/modules/projectiles/magazines/flamer.dm @@ -58,6 +58,7 @@ reagents.clear_reagents() + playsound(loc, 'sound/effects/refill.ogg', 25, 1, 3) to_chat(usr, SPAN_NOTICE("You empty out [src]")) update_icon() @@ -71,22 +72,21 @@ G.update_icon() /obj/item/ammo_magazine/flamer_tank/afterattack(obj/target, mob/user , flag) //refuel at fueltanks when we run out of ammo. - if(!istype(target, /obj/structure/reagent_dispensers/fueltank) && !istype(target, /obj/item/tool/weldpack) && !istype(target, /obj/item/storage/backpack/marine/engineerpack)) - return ..() if(get_dist(user,target) > 1) return ..() + if(!istype(target, /obj/structure/reagent_dispensers/fueltank) && !istype(target, /obj/item/tool/weldpack) && !istype(target, /obj/item/storage/backpack/marine/engineerpack)) + return ..() - var/obj/O = target - if(!O.reagents || O.reagents.reagent_list.len < 1) - to_chat(user, SPAN_WARNING("[O] is empty!")) + if(!target.reagents || target.reagents.reagent_list.len < 1) + to_chat(user, SPAN_WARNING("[target] is empty!")) return if(!reagents) create_reagents(max_rounds) - var/datum/reagent/to_add = O.reagents.reagent_list[1] + var/datum/reagent/to_add = target.reagents.reagent_list[1] - if(!istype(to_add) || (length(reagents.reagent_list) && flamer_chem != to_add.id) || length(O.reagents.reagent_list) > 1) + if(!istype(to_add) || (length(reagents.reagent_list) && flamer_chem != to_add.id) || length(target.reagents.reagent_list) > 1) to_chat(user, SPAN_WARNING("You can't mix fuel mixtures!")) return @@ -96,10 +96,11 @@ var/fuel_amt_to_remove = Clamp(to_add.volume, 0, max_rounds - reagents.get_reagent_amount(to_add.id)) if(!fuel_amt_to_remove) - to_chat(user, SPAN_WARNING("[O] is empty!")) + if(!max_rounds) + to_chat(user, SPAN_WARNING("[target] is empty!")) return - O.reagents.remove_reagent(to_add.id, fuel_amt_to_remove) + target.reagents.remove_reagent(to_add.id, fuel_amt_to_remove) reagents.add_reagent(to_add.id, fuel_amt_to_remove) playsound(loc, 'sound/effects/refill.ogg', 25, 1, 3) caliber = to_add.name From 39d2f9888b3142ca3cbf48c969816abf90d25091 Mon Sep 17 00:00:00 2001 From: harryob Date: Fri, 23 Jun 2023 18:27:37 +0100 Subject: [PATCH 13/25] sanitizes some more player input (#3702) closes #3698 --- code/modules/cm_marines/marines_consoles.dm | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/code/modules/cm_marines/marines_consoles.dm b/code/modules/cm_marines/marines_consoles.dm index 21f8a461a016..3539a43e6c15 100644 --- a/code/modules/cm_marines/marines_consoles.dm +++ b/code/modules/cm_marines/marines_consoles.dm @@ -177,7 +177,7 @@ if(!authenticated || !target_id_card) return - var/new_name = params["name"] // reject_bad_name() can be added here + var/new_name = strip_html(params["name"]) if(!new_name) visible_message(SPAN_NOTICE("[src] buzzes rudely.")) return @@ -191,7 +191,7 @@ return if(target == "Custom") - var/custom_name = params["custom_name"] + var/custom_name = strip_html(params["custom_name"]) if(custom_name) target_id_card.assignment = custom_name else From ab775c7ea8024c2c19a31964fed262da38417801 Mon Sep 17 00:00:00 2001 From: cm13-github <128137806+cm13-github@users.noreply.github.com> Date: Fri, 23 Jun 2023 18:29:05 +0100 Subject: [PATCH 14/25] Automatic changelog for PR #3623 [ci skip] --- html/changelogs/AutoChangeLog-pr-3623.yml | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 html/changelogs/AutoChangeLog-pr-3623.yml diff --git a/html/changelogs/AutoChangeLog-pr-3623.yml b/html/changelogs/AutoChangeLog-pr-3623.yml new file mode 100644 index 000000000000..d0909a0051e9 --- /dev/null +++ b/html/changelogs/AutoChangeLog-pr-3623.yml @@ -0,0 +1,5 @@ +author: "Drathek" +delete-after: True +changes: + - bugfix: "Fixed erroneous is empty messages when inserting tanks into a flamer pack." + - soundadd: "Added the refill sfx when using the empty canister verb on flamer tanks." \ No newline at end of file From 9a51e5d4e5db16715e1172415bc8a998bd0fa2df Mon Sep 17 00:00:00 2001 From: morrowwolf Date: Fri, 23 Jun 2023 15:54:45 -0400 Subject: [PATCH 15/25] Devour now turns off lights (#3668) # About the pull request This PR makes it so devour turns off lights. # Explain why it's good for the game This should stop some of the pesky bugs that have been cropping up around lights and devour/regurg. # Testing Photographs and Procedure
Screenshots & Videos Put screenshots and videos here with an empty line between the screenshots and the `
` tags.
# Changelog :cl: Morrow fix: Prevented some light bugs with devouring marines /:cl: --------- Co-authored-by: Zonespace <41448081+Zonespace27@users.noreply.github.com> --- code/modules/mob/mob_grab.dm | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/code/modules/mob/mob_grab.dm b/code/modules/mob/mob_grab.dm index 81296f346d50..39cc5b25e519 100644 --- a/code/modules/mob/mob_grab.dm +++ b/code/modules/mob/mob_grab.dm @@ -141,10 +141,9 @@ X.visible_message(SPAN_WARNING("[X] devours [pulled]!"), \ SPAN_WARNING("You devour [pulled]!"), null, 5) - //IMPORTANT CODER NOTE: Due to us using the old lighting engine, we need to hacky hack hard to get this working properly - //So we're just going to get the lights out of here by forceMoving them to a far-away place - //They will be recovered when regurgitating, since this also calls forceMove - pulled.moveToNullspace() + if(ishuman(pulled)) + var/mob/living/carbon/human/pulled_human = pulled + pulled_human.disable_lights() //Then, we place the mob where it ought to be X.stomach_contents.Add(pulled) From 13be6b625511eee688f0812e98e1cdafb296e801 Mon Sep 17 00:00:00 2001 From: cm13-github <128137806+cm13-github@users.noreply.github.com> Date: Fri, 23 Jun 2023 21:03:24 +0100 Subject: [PATCH 16/25] Automatic changelog for PR #3668 [ci skip] --- html/changelogs/AutoChangeLog-pr-3668.yml | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 html/changelogs/AutoChangeLog-pr-3668.yml diff --git a/html/changelogs/AutoChangeLog-pr-3668.yml b/html/changelogs/AutoChangeLog-pr-3668.yml new file mode 100644 index 000000000000..9d94c2c6f3d0 --- /dev/null +++ b/html/changelogs/AutoChangeLog-pr-3668.yml @@ -0,0 +1,4 @@ +author: "Morrow" +delete-after: True +changes: + - bugfix: "Prevented some light bugs with devouring marines" \ No newline at end of file From 39d6b77ce81ad790d3bd196d967202dfd29449f2 Mon Sep 17 00:00:00 2001 From: Steelpoint <6595389+Steelpoint@users.noreply.github.com> Date: Sat, 24 Jun 2023 06:04:31 +0800 Subject: [PATCH 17/25] Adds USCM Poncho To Synth Vendor (#3687) # About the pull request Adds the USCM Poncho as a purchase option to the Synthetic snowflake vendor. # Explain why it's good for the game More ability to customize your shipboard Synthetic is a good thing I believe. # Testing Photographs and Procedure
Screenshots & Videos ![Screenshot 2023-06-21 19 18 53](https://github.com/cmss13-devs/cmss13/assets/6595389/1f07a8b0-197d-43e3-9603-9f3dcd052170)
# Changelog :cl: add: Synthetics may now vend Ponchos. /:cl: Co-authored-by: Steelpoint --- code/game/machinery/vending/vendor_types/crew/synthetic.dm | 1 + 1 file changed, 1 insertion(+) diff --git a/code/game/machinery/vending/vendor_types/crew/synthetic.dm b/code/game/machinery/vending/vendor_types/crew/synthetic.dm index bd403c65c31b..1d8e5e289066 100644 --- a/code/game/machinery/vending/vendor_types/crew/synthetic.dm +++ b/code/game/machinery/vending/vendor_types/crew/synthetic.dm @@ -244,6 +244,7 @@ GLOBAL_LIST_INIT(cm_vending_clothing_synth_snowflake, list( list("Labcoat", 12, /obj/item/clothing/suit/storage/labcoat, null, VENDOR_ITEM_REGULAR), list("Labcoat, Researcher", 12, /obj/item/clothing/suit/storage/labcoat/researcher, null, VENDOR_ITEM_REGULAR), list("RO Jacket", 12, /obj/item/clothing/suit/storage/RO, null, VENDOR_ITEM_REGULAR), + list("USCM Poncho", 12, /obj/item/clothing/accessory/poncho, null, VENDOR_ITEM_REGULAR), list("BACKPACK", 0, null, null, null), list("Backpack, Industrial", 12, /obj/item/storage/backpack/industrial, null, VENDOR_ITEM_REGULAR), From 316057c45b7fa870c997044a3bd58a03f0cc68ed Mon Sep 17 00:00:00 2001 From: cm13-github <128137806+cm13-github@users.noreply.github.com> Date: Fri, 23 Jun 2023 23:13:25 +0100 Subject: [PATCH 18/25] Automatic changelog for PR #3687 [ci skip] --- html/changelogs/AutoChangeLog-pr-3687.yml | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 html/changelogs/AutoChangeLog-pr-3687.yml diff --git a/html/changelogs/AutoChangeLog-pr-3687.yml b/html/changelogs/AutoChangeLog-pr-3687.yml new file mode 100644 index 000000000000..f2a9cc2507d3 --- /dev/null +++ b/html/changelogs/AutoChangeLog-pr-3687.yml @@ -0,0 +1,4 @@ +author: "Steelpoint" +delete-after: True +changes: + - rscadd: "Synthetics may now vend Ponchos." \ No newline at end of file From 76533dec9795b7641cd1681eed91d1c477533d36 Mon Sep 17 00:00:00 2001 From: Changelogs Date: Sat, 24 Jun 2023 01:44:35 +0000 Subject: [PATCH 19/25] Automatic changelog compile [ci skip] --- html/changelogs/AutoChangeLog-pr-3623.yml | 5 ----- html/changelogs/AutoChangeLog-pr-3636.yml | 6 ------ html/changelogs/AutoChangeLog-pr-3652.yml | 5 ----- html/changelogs/AutoChangeLog-pr-3668.yml | 4 ---- html/changelogs/AutoChangeLog-pr-3687.yml | 4 ---- html/changelogs/AutoChangeLog-pr-3692.yml | 4 ---- html/changelogs/AutoChangeLog-pr-3696.yml | 4 ---- html/changelogs/archive/2023-06.yml | 22 ++++++++++++++++++++++ 8 files changed, 22 insertions(+), 32 deletions(-) delete mode 100644 html/changelogs/AutoChangeLog-pr-3623.yml delete mode 100644 html/changelogs/AutoChangeLog-pr-3636.yml delete mode 100644 html/changelogs/AutoChangeLog-pr-3652.yml delete mode 100644 html/changelogs/AutoChangeLog-pr-3668.yml delete mode 100644 html/changelogs/AutoChangeLog-pr-3687.yml delete mode 100644 html/changelogs/AutoChangeLog-pr-3692.yml delete mode 100644 html/changelogs/AutoChangeLog-pr-3696.yml diff --git a/html/changelogs/AutoChangeLog-pr-3623.yml b/html/changelogs/AutoChangeLog-pr-3623.yml deleted file mode 100644 index d0909a0051e9..000000000000 --- a/html/changelogs/AutoChangeLog-pr-3623.yml +++ /dev/null @@ -1,5 +0,0 @@ -author: "Drathek" -delete-after: True -changes: - - bugfix: "Fixed erroneous is empty messages when inserting tanks into a flamer pack." - - soundadd: "Added the refill sfx when using the empty canister verb on flamer tanks." \ No newline at end of file diff --git a/html/changelogs/AutoChangeLog-pr-3636.yml b/html/changelogs/AutoChangeLog-pr-3636.yml deleted file mode 100644 index a1dcf5fbeb71..000000000000 --- a/html/changelogs/AutoChangeLog-pr-3636.yml +++ /dev/null @@ -1,6 +0,0 @@ -author: "Drathek" -delete-after: True -changes: - - rscadd: "The selection to become a xeno larva is now based on timeofdeath rather than random and also sends a message to all candidates when the queue moves. Playing as a facehugger or on admin z-levels (thunderdome) will not affect your relative place in queue. The join xeno action will also display the last queue message for you when you allow xeno candidacy." - - bugfix: "Fixed gibbed humans not properly setting their timeofdeath when on an admin z-level." - - bugfix: "Fixed a bad del on shuttle doors when a shuttle deletes (such as intoTheSunset)." \ No newline at end of file diff --git a/html/changelogs/AutoChangeLog-pr-3652.yml b/html/changelogs/AutoChangeLog-pr-3652.yml deleted file mode 100644 index d95df39d8567..000000000000 --- a/html/changelogs/AutoChangeLog-pr-3652.yml +++ /dev/null @@ -1,5 +0,0 @@ -author: "realforest2001" -delete-after: True -changes: - - admin: "Improves logging for admin deadchat." - - admin: "Adds logging for xeno evolution." \ No newline at end of file diff --git a/html/changelogs/AutoChangeLog-pr-3668.yml b/html/changelogs/AutoChangeLog-pr-3668.yml deleted file mode 100644 index 9d94c2c6f3d0..000000000000 --- a/html/changelogs/AutoChangeLog-pr-3668.yml +++ /dev/null @@ -1,4 +0,0 @@ -author: "Morrow" -delete-after: True -changes: - - bugfix: "Prevented some light bugs with devouring marines" \ No newline at end of file diff --git a/html/changelogs/AutoChangeLog-pr-3687.yml b/html/changelogs/AutoChangeLog-pr-3687.yml deleted file mode 100644 index f2a9cc2507d3..000000000000 --- a/html/changelogs/AutoChangeLog-pr-3687.yml +++ /dev/null @@ -1,4 +0,0 @@ -author: "Steelpoint" -delete-after: True -changes: - - rscadd: "Synthetics may now vend Ponchos." \ No newline at end of file diff --git a/html/changelogs/AutoChangeLog-pr-3692.yml b/html/changelogs/AutoChangeLog-pr-3692.yml deleted file mode 100644 index cf20a4947af4..000000000000 --- a/html/changelogs/AutoChangeLog-pr-3692.yml +++ /dev/null @@ -1,4 +0,0 @@ -author: "theselfish" -delete-after: True -changes: - - qol: "Added the Corpsman Helmet to Req's surplus vendor." \ No newline at end of file diff --git a/html/changelogs/AutoChangeLog-pr-3696.yml b/html/changelogs/AutoChangeLog-pr-3696.yml deleted file mode 100644 index dabfba255741..000000000000 --- a/html/changelogs/AutoChangeLog-pr-3696.yml +++ /dev/null @@ -1,4 +0,0 @@ -author: "Morrow" -delete-after: True -changes: - - bugfix: "Fixed two gun light attachment issues" \ No newline at end of file diff --git a/html/changelogs/archive/2023-06.yml b/html/changelogs/archive/2023-06.yml index 9e9081238a2a..f1ae2b2dd14e 100644 --- a/html/changelogs/archive/2023-06.yml +++ b/html/changelogs/archive/2023-06.yml @@ -318,3 +318,25 @@ 2023-06-23: harryob: - server: server's can now support using a cdn for web assets +2023-06-24: + Drathek: + - rscadd: The selection to become a xeno larva is now based on timeofdeath rather + than random and also sends a message to all candidates when the queue moves. + Playing as a facehugger or on admin z-levels (thunderdome) will not affect your + relative place in queue. The join xeno action will also display the last queue + message for you when you allow xeno candidacy. + - bugfix: Fixed gibbed humans not properly setting their timeofdeath when on an + admin z-level. + - bugfix: Fixed a bad del on shuttle doors when a shuttle deletes (such as intoTheSunset). + - bugfix: Fixed erroneous is empty messages when inserting tanks into a flamer pack. + - soundadd: Added the refill sfx when using the empty canister verb on flamer tanks. + Morrow: + - bugfix: Prevented some light bugs with devouring marines + - bugfix: Fixed two gun light attachment issues + Steelpoint: + - rscadd: Synthetics may now vend Ponchos. + realforest2001: + - admin: Improves logging for admin deadchat. + - admin: Adds logging for xeno evolution. + theselfish: + - qol: Added the Corpsman Helmet to Req's surplus vendor. From 71455d4fd8947610a25d47729429a35ed8a2a1c2 Mon Sep 17 00:00:00 2001 From: Segrain Date: Sat, 24 Jun 2023 11:33:43 +0400 Subject: [PATCH 20/25] Fix for dummy rotation in character setup. (#3699) # About the pull request Followup to #3516. That PR changed the general click behaviour from `if (click(A, mods) | A.clicked(src, mods, location, params))` to use `||` instead. And in Byond, that means quick resolution: if left side is true, then right side is not evaluated - thus not executed - at all. ~~I am not sure what exactly was that meant to address (or whether it was intentional at all, for that matter),~~ but as it happens, `/mob/new_player/click()` is set to always simply return true while all the code for those arrows is in their `clicked()`. Solution is obvious then. P.S. On second thought, reading the PR does explain the PR. But quick resolution is not exactly intuitive, and even though it is probably highly unlikely to ever change, there is probably no need to rely on it so implicitly. While I have the file open anyway, might as well make returning after the left half alone explicit. # Explain why it's good for the game Is fix. # Changelog :cl: fix: Preview dummy in character setup once again can be rotated. /:cl: --- code/_onclick/click.dm | 4 +++- code/_onclick/other_mobs.dm | 2 +- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/code/_onclick/click.dm b/code/_onclick/click.dm index ad2f305790d2..affbc28cdd45 100644 --- a/code/_onclick/click.dm +++ b/code/_onclick/click.dm @@ -71,7 +71,9 @@ return // Click handled elsewhere. (These clicks are not affected by the next_move cooldown) - if (click(A, mods) || A.clicked(src, mods, location, params)) + if(click(A, mods)) + return + if(A.clicked(src, mods, location, params)) return // Default click functions from here on. diff --git a/code/_onclick/other_mobs.dm b/code/_onclick/other_mobs.dm index a8ed20f5c4b3..9c9784286d09 100644 --- a/code/_onclick/other_mobs.dm +++ b/code/_onclick/other_mobs.dm @@ -34,4 +34,4 @@ Have no reason to click on anything at all. */ /mob/new_player/click() - return 1 + return From 04b47c92e7827614f76debf6485bc679c8379d2a Mon Sep 17 00:00:00 2001 From: cm13-github <128137806+cm13-github@users.noreply.github.com> Date: Sat, 24 Jun 2023 08:42:04 +0100 Subject: [PATCH 21/25] Automatic changelog for PR #3699 [ci skip] --- html/changelogs/AutoChangeLog-pr-3699.yml | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 html/changelogs/AutoChangeLog-pr-3699.yml diff --git a/html/changelogs/AutoChangeLog-pr-3699.yml b/html/changelogs/AutoChangeLog-pr-3699.yml new file mode 100644 index 000000000000..5cac5307b4c6 --- /dev/null +++ b/html/changelogs/AutoChangeLog-pr-3699.yml @@ -0,0 +1,4 @@ +author: "Segrain" +delete-after: True +changes: + - bugfix: "Preview dummy in character setup once again can be rotated." \ No newline at end of file From 610c8b3099f479c9948ff7e9df2151c2370c1f2f Mon Sep 17 00:00:00 2001 From: Segrain Date: Sat, 24 Jun 2023 11:33:54 +0400 Subject: [PATCH 22/25] Hive core and dead larvas. (#3700) # About the pull request Hive core, by design, absorbs AFK larvas to let somebody else actually play instead. And as long as it has been a thing, the definition of "AFK" was actually "without a client", so a dead larva that ghosted was absorbed all the same and replaced with a new alive larva - while dead larvas that did not ghost were seen as being actively played and left alone. Frankly, if a larva dies without the core and entire hive being destroyed, it was most likely running out somewhere whither it has no business going. We refund these anyway. Might as well formally declare it an intended mechanic that dead larvas can be recycled at core. Also, funny as it might be, it should only work on the hive's _own_ larvas. # Explain why it's good for the game Closes #3667. # Changelog :cl: fix: Hive core now always correctly absorbs hive's dead larvas. /:cl: --- code/modules/cm_aliens/structures/special/pylon_core.dm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/code/modules/cm_aliens/structures/special/pylon_core.dm b/code/modules/cm_aliens/structures/special/pylon_core.dm index 08aa2f86c1bc..40b4ad8e1718 100644 --- a/code/modules/cm_aliens/structures/special/pylon_core.dm +++ b/code/modules/cm_aliens/structures/special/pylon_core.dm @@ -137,7 +137,7 @@ // Handle spawning larva if core is connected to a hive if(linked_hive) for(var/mob/living/carbon/xenomorph/larva/L in range(2, src)) - if(!L.ckey && L.burrowable && !QDELETED(L)) + if((!L.ckey || L.stat == DEAD) && L.burrowable && (L.hivenumber == linked_hive.hivenumber) && !QDELETED(L)) visible_message(SPAN_XENODANGER("[L] quickly burrows into \the [src].")) linked_hive.stored_larva++ linked_hive.hive_ui.update_burrowed_larva() From 036b4cd019ebec1bf3d41513620e5bd105b37353 Mon Sep 17 00:00:00 2001 From: cm13-github <128137806+cm13-github@users.noreply.github.com> Date: Sat, 24 Jun 2023 08:56:37 +0100 Subject: [PATCH 23/25] Automatic changelog for PR #3700 [ci skip] --- html/changelogs/AutoChangeLog-pr-3700.yml | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 html/changelogs/AutoChangeLog-pr-3700.yml diff --git a/html/changelogs/AutoChangeLog-pr-3700.yml b/html/changelogs/AutoChangeLog-pr-3700.yml new file mode 100644 index 000000000000..5aa90e4d8ece --- /dev/null +++ b/html/changelogs/AutoChangeLog-pr-3700.yml @@ -0,0 +1,4 @@ +author: "Segrain" +delete-after: True +changes: + - bugfix: "Hive core now always correctly absorbs hive's dead larvas." \ No newline at end of file From db5a3892631223bb7fcab81146356b049edce082 Mon Sep 17 00:00:00 2001 From: Sargeantmuffinman <104228030+Sargeantmuffinman@users.noreply.github.com> Date: Sat, 24 Jun 2023 08:34:11 +0100 Subject: [PATCH 24/25] Email rewrites (#3701) # About the pull request Rewrites and or updates some of the emails I created while adding two new ones. These are simple text changes. # Explain why it's good for the game More consistent writing and lore is great for the game. # Testing Photographs and Procedure
Screenshots & Videos ![image](https://github.com/cmss13-devs/cmss13/assets/104228030/8264a067-b147-4093-abde-7fa08b68100c) ![image](https://github.com/cmss13-devs/cmss13/assets/104228030/efd81d99-2d73-4bc9-a1c9-28ca945c6823) ![image](https://github.com/cmss13-devs/cmss13/assets/104228030/88155524-7fea-4809-b036-b52fc56a0eb9) ![image](https://github.com/cmss13-devs/cmss13/assets/104228030/9db716d6-7734-440a-9237-56e8879c2e01) ![image](https://github.com/cmss13-devs/cmss13/assets/104228030/fca43d28-71a9-4a8c-919b-610561a32892)
# Changelog :cl: add: Added two new emails to the Almayer's personal computers and rewrote 3 other emails. /:cl: --- code/datums/fluff_emails.dm | 128 ++++++++++++++++++------------------ 1 file changed, 64 insertions(+), 64 deletions(-) diff --git a/code/datums/fluff_emails.dm b/code/datums/fluff_emails.dm index 6dd8cd590860..f7083541dd5a 100644 --- a/code/datums/fluff_emails.dm +++ b/code/datums/fluff_emails.dm @@ -93,9 +93,9 @@ /datum/fluff_email/almayer/themajor title = "The Major?" entry_text = {" - I keep forgetting what the new Major's name is. I got quizzed by one of the jackass staff officers last week about the captain's name, - and I absolutely spilled my marbles. PCF Mable was watching too, and she probably thinks I've got rocks in my head. I know it's been weeks - since the new captain took over, but for some reason the name keeps escaping me when it matters. Either the cryo-sleepers are juicing my + I keep forgetting what the new Major's name is. I got quizzed by one of the jackass staff officers last week about the Major's name, + and I absolutely spilled my marbles. PFC Mable was watching too, and she probably thinks I've got rocks in my head. I know it's been weeks + since the new Major took over, but for some reason the name keeps escaping me when it matters. Either the cryo-sleepers are juicing my memory capacity or the CO keeps changing their name and not telling anybody. Maybe next jump I'll scrawl it on a sticky note and plaster it to the inside of my sleeper pod. I can't be the only one having this problem. @@ -105,7 +105,8 @@ /datum/fluff_email/almayer/tunes title = "RE: Tunes" entry_text = {" - Cryosleep is killing me, man. Inside and outside. I mean really, they expect us to sit in that tube for god only knows how long, and when we wake up? It's all 'grab a crappy protein bar and grab your gear, you're going to war, Marine!' Bullshit. + Cryosleep is killing me, man. Inside and outside. I mean really, they expect us to sit in that tube for god only knows how long, and when we wake up? + It's all 'grab a crappy protein bar and grab your gear, you're going to war, Marine!' Bullshit.

Anywho, I've been thinking how to make the whole thing more bearable. Tried to take a plush from the bunks with me inside. That dickwad MP took it away from me though, said it was against Operating Procedure. Like I care. Can't do anything fun around here, right? @@ -113,82 +114,81 @@ I don't usually use these things, and frankly that vendor near Medbay has waaay too many cassettes to choose from. Not that I know most songs on them anywho.

- I saw you with a Walkman from time to time, so... any chances you could recommend a tape to me? Or two, I'm not gonna be picky. Just anything to start out with, I just want some nice sounds. Please, I'm gonna go mad if I don't do something about my cryophobia or whatever. This might just help with that. + I saw you with a Walkman from time to time, so... any chances you could recommend a tape to me? Or two, I'm not gonna be picky. + Just anything to start out with, I just want some nice sounds. Please, I'm gonna go mad if I don't do something about my cryophobia or whatever. + This might just help with that. "} -/datum/fluff_email/almayer/lasergun - title = "RE: Lasergun" +/datum/fluff_email/almayer/lasergun1 + title = "Prototype Weapon" entry_text = {" - Hey REDACTED. Thanks for letting me test out the laser gun. That thing is a factual blast to use. It literally set the targets down range on fire! Those cooling coils work wonders. Used it a good few times and the barrel didn't explode! + This thing is an absolute blast to use. + It disintegrated some of the targets down range but you're going to need to work on those cooling coils. + I used it a few times and I'm seeing the front barrel glow red.

- Hell, it's even pretty accurate too. I know there's like, a couple of prototypes issued to some USCM detachments but we got to have this shit in production one day. It's just good. Now, I don't think it's gonna replace the old Mark two's but it would be a nice addition for some of our grunts that prefer the high tech approach. You know the ones, all nerdy and gadget loving geeks in the corps. Hell I can already hear them glossing over this thing in their sleep. + Surprisingly accurate too despite being a prototype. + I know there's like, a couple of prototypes issued to some USCM detachments, but we got to have this shit in production one day.

- Anyway, I've already attached the weapon report you wanted on this thing back to the email. Hopefully you guys in R&D will get some useful info out of it. + Even as a prototype, it's leagues better than some of the junk we're issued. + Now, I don't think it's going to replace the old Mark Twos, but it would be a nice addition for some of our grunts that prefer the high-tech approach.
- Alright see you when I see you - REDACTED
-
- RE:RE: The Plasma Gun (It's called the XM99 Phased Plasma Pulse Rifle) - Hey REDACTED, REDACTED here. Thanks for the report but I'm going to need you to send the Phased Plasma Pulse Rifle back to me. Apparently we're not allowed to ship them out for testing... I guess I must've missed that memo. The memo came three days after I shipped it out to you. Sorry for the inconvenience. You know where to send it back to and how to. I did tell you how right? There was a small pamphlet in the casing if you forgot. -
-
- Don't think this is going to be issued en masse for a while, it's still going under trials and when I got the weapon report you sent me, they sent in a new updated design for the gun which invalidated most of the things in the report, shame. Looks more promising than the last one though. -
-
- Okay, I'll hopefully be seeing the XM99 Phased Plasma Pulse Rifle in the lab soon. -
-
- REDACTED RE:RE:RE: The Plasma Gun (It's called the XM99 Phased Plasma Pulse Rifle) -
- Holy shit, what the fuck did you do to the damned thing? When I opened the case, I could see fractures and scratches everywhere! Did you give this to the entire platoon to try out? And from the data I'm reading, you fired over 178 shots with this. I only gave you two batteries for the thing. -
-
- How the hell did you recharge it?! The prototype can't take any other forms of power other than those two batteries. And even then, you can't recharge those specially made batteries either without the equipment back in the lab here. And the inside of the barrel is all messed up man. The cooling coils expired and there're bits of the barrel loose inside of it. How the hell did you not notice bits of the inside of the barrel spewing out from the muzzle man?! -
-
- Right. They've threatened to drop me from the project if something like this happens again. In the rare case that I send another prototype out, it had better come back in one piece. And I mean in pristine condition, you got that? -
-
Regards, -
REDACTED + You know the ones, all nerdy and gadget loving geeks in the corps. Hell, I can already hear them glossing over this thing in their sleep. + My report has been sent back to you and I'm really excited to see how this turns out. + + "} + + +/datum/fluff_email/almayer/lasergun2 + title = "New Prototype Design" + entry_text = {" + Thanks for sending the report in, we've been mulling over the data you sent over. + We've updated the design for the prototype which solves most of the problems everyone has encountered. + This one looks more promising than the last one. + And as much as everyone wants this done and shippped, I don't think this is going to be issued en masse for a good while. "} /datum/fluff_email/almayer/beatup - title = "RE: Beat Up" + title = "Beat Up" entry_text = {" - Yo. -
-
- Man, last mission was an absolute shit show. The USS Heyst got their shit kicked in with a missile and we got our cargo hold set on fire by that damn suicide craft. They even blew up most of our good ammo too! Now we're left with the soft point backup munitions. Shit, most of 1st platoon is pretty much out of action. Lotta folks are in sickbay and the rest of us are heading off to cryosleep, well what's left of us. -
-
- When the comms got cut and we were cut off from command; Squad Foxtrot was immediately ambushed on the logistics route to get supplies in and out of the combat zone. I suspect they were taping into your comms to find the literal perfect moment to fuck with our logistics. Thankfully those trucks of ours had their engines tricked out by the techies back on LV-176 in the civilian garage. Those guys hosted rally races around their colony and Sergeant DATA EXPUNGED won a few races for us. Instead of taking their trophy, he pulled a few favors to get our trucks pimped out with better engines. We owe our lives to Sarge for winning one for the corps. -
-
- Hell, at least we're all going back to Chinook Station to get resupplied. Hopefully the wounded wake up to the docs on station rather than our poor and cramped excuse for a medical bay. The number of times the medbay has been packed with wounded where even the damn front lobby had bodies lining up on the sides of the walls waiting for treatment; it still amazes. Worse still was the stench from all the blood and guts, it made it hell for the maint. techs to clean up afterwards. -
- I'm still surprised those doctors we had on hand took care of most of them so quickly, even if most of them are still injured heading to the fridge. -
-
- I read the After-Action Report which the Heyst's XO did, and they're leaving out a few details. When it came to that city, they left out how we had to DATA EXPUNGED. The entire building collapsed with them in it too. Damn shame we couldn't save them. -
-
- The only damn silver lining i see in this shit is that the AI is going to cycle cryo again and we ain't waking to deal with whatever bullshit is happening next time. 2nd Platoon is dealing with that, cause 1st platoon is undermanned as is with our casualties. I heard they have a few screws loose, not that ours are entirely in either! But I don't care, it's their problem now y'know? -
-
- Worst case scenario, we don't wake up at all. -
- Right, see you back on station friend. -
-
- Regards, -
- REDACTED + Man last mission was an absolute shit show. +
+ The USS Heyst got their shit kicked in with a missile and we got our cargo hold set on fire. And most of our good ammo is gone too! + Now we're left with the FMJs and the older AP munitions. What's worse is that most of 1st platoon is pretty much out of action. + Lotta folks are in the sickbay and the rest of us are heading off to cryosleep, well what's left of us. There's not many of the old guard left I'm afraid. + Until we get reinforced with more bodies, command has given the go ahead to merge 2nd platoon into 1st for the time being. + + "} + + +/datum/fluff_email/almayer/rallyrace + title = "Rally Racing" + entry_text = {" + Hey, remember last shore leave on LV-179? Man, that was one crazy night. The folks at the colony had setup a rally race with their tractors all stripped of non-essentials. + LCPL Millard got pretty friendly with the locals and got himself into the competition. + We all put in a little wager to see if he'd even get close to first place or even survive to the finish line. + Now most of the boys bet a fair amount against him since he was pretty new to our outfit, yet I've been out on detail with the guy. +
+
+ Millard grew up on one of those shake and bake colonies and used to drive the big daisies around. + He knew the ins and outs of what made them tick. The few of us who had faith in him reaped everyone else's + paycheck for the week with Millard finishing first place by a near country mile. "} + +/datum/fluff_email/almayer/missing + title = "Missing Personnel" + entry_text = {" + Has anyone seen Mendoza around? He owes me half of his paycheck from last month's poker game. + Everyone's payday was a week ago and we're all set to head back to Chinook station. + Could have sworn I saw him near the cargo elevator yesterday. + I'll catch him back at base once we've docked because I need that money to pay off my tab at the bar. + + "} + From 807387b2930f74c389bef793bd44b3a77c53c710 Mon Sep 17 00:00:00 2001 From: cm13-github <128137806+cm13-github@users.noreply.github.com> Date: Sat, 24 Jun 2023 09:11:38 +0100 Subject: [PATCH 25/25] Automatic changelog for PR #3701 [ci skip] --- html/changelogs/AutoChangeLog-pr-3701.yml | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 html/changelogs/AutoChangeLog-pr-3701.yml diff --git a/html/changelogs/AutoChangeLog-pr-3701.yml b/html/changelogs/AutoChangeLog-pr-3701.yml new file mode 100644 index 000000000000..41559592d55d --- /dev/null +++ b/html/changelogs/AutoChangeLog-pr-3701.yml @@ -0,0 +1,4 @@ +author: "Sargeantmuffinman" +delete-after: True +changes: + - rscadd: "Added two new emails to the Almayer's personal computers and rewrote 3 other emails." \ No newline at end of file