diff --git a/code/__DEFINES/layers.dm b/code/__DEFINES/layers.dm index 8680212a0ba..d68948ce0bd 100644 --- a/code/__DEFINES/layers.dm +++ b/code/__DEFINES/layers.dm @@ -236,3 +236,21 @@ ///Plane master controller keys #define PLANE_MASTERS_GAME "plane_masters_game" #define PLANE_MASTERS_COLORBLIND "plane_masters_colorblind" + +//Plane master critical flags +//Describes how different plane masters behave when they are being culled for performance reasons +/// This plane master will not go away if its layer is culled. useful for preserving effects +#define PLANE_CRITICAL_DISPLAY (1<<0) +/// This plane master will temporarially remove relays to non critical planes if it's layer is culled (and it's critical) +/// This is VERY hacky, but needed to ensure that some instances of BLEND_MULITPLY work as expected (fuck you god damn parallax) +/// It also implies that the critical plane has a *'d render target, making it mask itself +#define PLANE_CRITICAL_NO_EMPTY_RELAY (1<<1) + +#define PLANE_CRITICAL_FUCKO_PARALLAX (PLANE_CRITICAL_DISPLAY|PLANE_CRITICAL_NO_EMPTY_RELAY) + +/// A value of /datum/preference/numeric/multiz_performance that disables the option +#define MULTIZ_PERFORMANCE_DISABLE -1 +/// We expect at most 3 layers of multiz +/// Increment this define if you make a huge map. We unit test for it too just to make it easy for you +/// If you modify this, you'll need to modify the tsx file too +#define MAX_EXPECTED_Z_DEPTH 2 diff --git a/code/__HELPERS/_planes.dm b/code/__HELPERS/_planes.dm index 1af0b636514..d8306c356d4 100644 --- a/code/__HELPERS/_planes.dm +++ b/code/__HELPERS/_planes.dm @@ -63,6 +63,8 @@ #define PLANE_TO_TRUE(plane) ((SSmapping.plane_offset_to_true) ? SSmapping.plane_offset_to_true["[plane]"] : plane) /// Takes a plane, returns the offset it uses #define PLANE_TO_OFFSET(plane) ((SSmapping.plane_to_offset) ? SSmapping.plane_to_offset["[plane]"] : plane) +/// Takes a plane, returns TRUE if it is of critical priority, FALSE otherwise +#define PLANE_IS_CRITICAL(plane) ((SSmapping.plane_to_offset) ? !!SSmapping.critical_planes["[plane]"] : FALSE) /// Takes a true plane, returns the offset planes that would canonically represent it #define TRUE_PLANE_TO_OFFSETS(plane) ((SSmapping.true_to_offset_planes) ? SSmapping.true_to_offset_planes["[plane]"] : list(plane)) /// Takes a render target and an offset, returns a canonical render target string for it diff --git a/code/_onclick/hud/parallax.dm b/code/_onclick/hud/parallax.dm index 05f3f6e48cc..a4b20d521fe 100755 --- a/code/_onclick/hud/parallax.dm +++ b/code/_onclick/hud/parallax.dm @@ -2,9 +2,15 @@ /datum/hud/proc/create_parallax(mob/viewmob) var/mob/screenmob = viewmob || mymob var/client/C = screenmob.client + if (!apply_parallax_pref(viewmob)) //don't want shit computers to crash when specing someone with insane parallax, so use the viewer's pref + for(var/atom/movable/screen/plane_master/parallax as anything in get_true_plane_masters(PLANE_SPACE_PARALLAX)) + parallax.hide_plane(screenmob) return + for(var/atom/movable/screen/plane_master/parallax as anything in get_true_plane_masters(PLANE_SPACE_PARALLAX)) + parallax.unhide_plane(screenmob) + if(!length(C.parallax_layers_cached)) C.parallax_layers_cached = list() C.parallax_layers_cached += new /atom/movable/screen/parallax_layer/layer_1(null, screenmob) @@ -23,7 +29,7 @@ // We could do not do parallax for anything except the main plane group // This could be changed, but it would require refactoring this whole thing // And adding non client particular hooks for all the inputs, and I do not have the time I'm sorry :( - for(var/atom/movable/screen/plane_master/plane_master in screenmob.hud_used.get_true_plane_masters(PLANE_SPACE)) + for(var/atom/movable/screen/plane_master/plane_master as anything in screenmob.hud_used.get_true_plane_masters(PLANE_SPACE)) if(screenmob != mymob) C.screen -= locate(/atom/movable/screen/plane_master/parallax_white) in C.screen C.screen += plane_master @@ -39,7 +45,7 @@ var/mob/screenmob = viewmob || mymob var/client/C = screenmob.client C.screen -= (C.parallax_layers_cached) - for(var/atom/movable/screen/plane_master/plane_master in screenmob.hud_used.get_true_plane_masters(PLANE_SPACE)) + for(var/atom/movable/screen/plane_master/plane_master as anything in screenmob.hud_used.get_true_plane_masters(PLANE_SPACE)) if(screenmob != mymob) C.screen -= locate(/atom/movable/screen/plane_master/parallax_white) in C.screen C.screen += plane_master @@ -50,7 +56,13 @@ var/mob/screenmob = viewmob || mymob if(SSmapping.level_trait(screenmob.z, ZTRAIT_NOPARALLAX)) + for(var/atom/movable/screen/plane_master/white_space as anything in get_true_plane_masters(PLANE_SPACE)) + white_space.hide_plane(screenmob) return FALSE + + for(var/atom/movable/screen/plane_master/white_space as anything in get_true_plane_masters(PLANE_SPACE)) + white_space.unhide_plane(screenmob) + if (SSlag_switch.measures[DISABLE_PARALLAX] && !HAS_TRAIT(viewmob, TRAIT_BYPASS_MEASURES)) return FALSE diff --git a/code/_onclick/hud/rendering/plane_master.dm b/code/_onclick/hud/rendering/plane_master.dm index 048b7185a42..9a37ee05a49 100644 --- a/code/_onclick/hud/rendering/plane_master.dm +++ b/code/_onclick/hud/rendering/plane_master.dm @@ -1,5 +1,6 @@ // I hate this place INITIALIZE_IMMEDIATE(/atom/movable/screen/plane_master) + /atom/movable/screen/plane_master screen_loc = "CENTER" icon_state = "blank" @@ -51,6 +52,18 @@ INITIALIZE_IMMEDIATE(/atom/movable/screen/plane_master) /// Planes with this set should NEVER be relay'd into each other, as that will cause visual fuck var/multiz_scaled = TRUE + /// Bitfield that describes how this plane master will render if its z layer is being "optimized" + /// If a plane master is NOT critical, it will be completely dropped if we start to render outside a client's multiz boundary prefs + /// Of note: most of the time we will relay renders to non critical planes in this stage. so the plane master will end up drawing roughly "in order" with its friends + /// This is NOT done for parallax and other problem children, because the rules of BLEND_MULTIPLY appear to not behave as expected :( + /// This will also just make debugging harder, because we do fragile things in order to ensure things operate as epected. I'm sorry + /// Compile time + /// See [code\__DEFINES\layers.dm] for our bitflags + var/critical = NONE + + /// If this plane master is outside of our visual bounds right now + var/is_outside_bounds = FALSE + /atom/movable/screen/plane_master/Initialize(mapload, datum/plane_master_group/home, offset = 0) . = ..() src.offset = offset @@ -116,7 +129,7 @@ INITIALIZE_IMMEDIATE(/atom/movable/screen/plane_master) /// Returns TRUE if the call is allowed, FALSE otherwise /atom/movable/screen/plane_master/proc/show_to(mob/mymob) SHOULD_CALL_PARENT(TRUE) - if(force_hidden) + if(force_hidden || is_outside_bounds) return FALSE var/client/our_client = mymob?.client @@ -166,6 +179,45 @@ INITIALIZE_IMMEDIATE(/atom/movable/screen/plane_master) else unhide_plane(our_mob) +/atom/movable/screen/plane_master/proc/outside_bounds(mob/relevant) + if(force_hidden || is_outside_bounds) + return + is_outside_bounds = TRUE + // If we're of critical importance, AND we're below the rendering layer + if(critical & PLANE_CRITICAL_DISPLAY) + if(!(critical & PLANE_CRITICAL_NO_EMPTY_RELAY)) + return + var/client/our_client = relevant.client + if(!our_client) + return + for(var/atom/movable/render_plane_relay/relay as anything in relays) + if(!relay.critical_target) + our_client.screen -= relay + + // We here assume that your render target starts with * + if(render_target) + render_target = copytext_char(render_target, 2) + return + hide_from(relevant) + +/atom/movable/screen/plane_master/proc/inside_bounds(mob/relevant) + is_outside_bounds = FALSE + if(critical & PLANE_CRITICAL_DISPLAY) + if(!(critical & PLANE_CRITICAL_NO_EMPTY_RELAY)) + return + var/client/our_client = relevant.client + if(!our_client) + return + for(var/atom/movable/render_plane_relay/relay as anything in relays) + if(!relay.critical_target) + our_client.screen += relay + + // We here assume that your render target starts with * + if(render_target) + render_target = "*[render_target]" + return + show_to(relevant) + /atom/movable/screen/plane_master/clickcatcher name = "Click Catcher" documentation = "Contains the screen object we use as a backdrop to catch clicks on portions of the screen that would otherwise contain nothing else. \ @@ -173,6 +225,7 @@ INITIALIZE_IMMEDIATE(/atom/movable/screen/plane_master) plane = CLICKCATCHER_PLANE appearance_flags = PLANE_MASTER|NO_CLIENT_COLOR multiz_scaled = FALSE + critical = PLANE_CRITICAL_DISPLAY /atom/movable/screen/plane_master/clickcatcher/Initialize(mapload, datum/plane_master_group/home, offset) . = ..() @@ -192,6 +245,7 @@ INITIALIZE_IMMEDIATE(/atom/movable/screen/plane_master)
If you want something to look as if it has parallax on it, draw it to this plane." plane = PLANE_SPACE appearance_flags = PLANE_MASTER|NO_CLIENT_COLOR + critical = PLANE_CRITICAL_FUCKO_PARALLAX // goes funny when touched. no idea why I don't trust byond ///Contains space parallax /atom/movable/screen/plane_master/parallax @@ -205,6 +259,7 @@ INITIALIZE_IMMEDIATE(/atom/movable/screen/plane_master) blend_mode = BLEND_MULTIPLY mouse_opacity = MOUSE_OPACITY_TRANSPARENT multiz_scaled = FALSE + critical = PLANE_CRITICAL_FUCKO_PARALLAX /atom/movable/screen/plane_master/parallax/Initialize(mapload, datum/plane_master_group/home, offset) . = ..() @@ -225,6 +280,21 @@ INITIALIZE_IMMEDIATE(/atom/movable/screen/plane_master) // Overlay so we don't multiply twice, and thus fuck up our rendering add_relay_to(GET_NEW_PLANE(plane, offset), BLEND_OVERLAY) +// Hacky shit to ensure parallax works in perf mode +/atom/movable/screen/plane_master/parallax/outside_bounds(mob/relevant) + if(offset == 0) + remove_relay_from(GET_NEW_PLANE(RENDER_PLANE_GAME, 0)) + is_outside_bounds = TRUE // I'm sorry :( + return + return ..() + +/atom/movable/screen/plane_master/parallax/inside_bounds(mob/relevant) + if(offset == 0) + add_relay_to(GET_NEW_PLANE(RENDER_PLANE_GAME, 0)) + is_outside_bounds = FALSE + return + return ..() + /atom/movable/screen/plane_master/gravpulse name = "Gravpulse" documentation = "Ok so this one's fun. Basically, we want to be able to distort the game plane when a grav annom is around.\ @@ -407,6 +477,7 @@ INITIALIZE_IMMEDIATE(/atom/movable/screen/plane_master) render_relay_planes = list(RENDER_PLANE_LIGHTING) blend_mode_override = BLEND_ADD mouse_opacity = MOUSE_OPACITY_TRANSPARENT + critical = PLANE_CRITICAL_DISPLAY /// This will not work through multiz, because of a byond bug with BLEND_MULTIPLY /// Bug report is up, waiting on a fix @@ -420,6 +491,7 @@ INITIALIZE_IMMEDIATE(/atom/movable/screen/plane_master) render_target = O_LIGHTING_VISUAL_RENDER_TARGET mouse_opacity = MOUSE_OPACITY_TRANSPARENT blend_mode = BLEND_MULTIPLY + critical = PLANE_CRITICAL_DISPLAY /atom/movable/screen/plane_master/above_lighting name = "Above lighting" @@ -444,6 +516,7 @@ INITIALIZE_IMMEDIATE(/atom/movable/screen/plane_master) mouse_opacity = MOUSE_OPACITY_TRANSPARENT render_target = EMISSIVE_RENDER_TARGET render_relay_planes = list() + critical = PLANE_CRITICAL_DISPLAY /atom/movable/screen/plane_master/emissive/Initialize(mapload) . = ..() diff --git a/code/_onclick/hud/rendering/plane_master_group.dm b/code/_onclick/hud/rendering/plane_master_group.dm index 48c3ed00388..d3b9902171d 100644 --- a/code/_onclick/hud/rendering/plane_master_group.dm +++ b/code/_onclick/hud/rendering/plane_master_group.dm @@ -11,7 +11,6 @@ var/list/atom/movable/screen/plane_master/plane_masters = list() /// The visual offset we are currently using var/active_offset = 0 - /// What, if any, submap we render onto var/map = "" @@ -94,7 +93,8 @@ // It's hard, and potentially expensive. be careful /datum/plane_master_group/proc/transform_lower_turfs(datum/hud/source, new_offset, use_scale = TRUE) // Check if this feature is disabled for the client, in which case don't use scale. - if(!our_hud?.mymob?.client?.prefs?.read_preference(/datum/preference/toggle/multiz_parallax)) + var/mob/our_mob = our_hud?.mymob + if(!our_mob?.client?.prefs?.read_preference(/datum/preference/toggle/multiz_parallax)) use_scale = FALSE // No offset? piss off @@ -115,8 +115,15 @@ scale_by = 1 var/list/offsets = list() + var/multiz_boundary = our_mob?.client?.prefs?.read_preference(/datum/preference/numeric/multiz_performance) + // We accept negatives so going down "zooms" away the drop above as it goes for(var/offset in -SSmapping.max_plane_offset to SSmapping.max_plane_offset) + // Multiz boundaries disable transforms + if(multiz_boundary != MULTIZ_PERFORMANCE_DISABLE && (multiz_boundary < abs(offset))) + offsets += null + continue + // No transformations if we're landing ON you if(offset == 0) offsets += null @@ -132,11 +139,23 @@ for(var/plane_key in plane_masters) var/atom/movable/screen/plane_master/plane = plane_masters[plane_key] - if(!plane.multiz_scaled || !plane.allows_offsetting) + if(!plane.allows_offsetting) continue var/visual_offset = plane.offset - new_offset - if(plane.force_hidden || visual_offset < 0) + // we get like 47 -> 42 from just no AO/displace on lower levels. 39 with no FOV blocking + // 31 with only barebones lower planes + + // Basically uh, if we're showing something down X amount of levels, or up any amount of levels + if(multiz_boundary != MULTIZ_PERFORMANCE_DISABLE && (visual_offset > multiz_boundary || visual_offset < 0)) + plane.outside_bounds(our_mob) + else if(plane.is_outside_bounds) + plane.inside_bounds(our_mob) + + if(!plane.multiz_scaled) + continue + + if(plane.force_hidden || plane.is_outside_bounds || visual_offset < 0) // We don't animate here because it should be invisble, but we do mark because it'll look nice plane.transform = offsets[visual_offset + offset_offset] continue diff --git a/code/_onclick/hud/rendering/render_plate.dm b/code/_onclick/hud/rendering/render_plate.dm index 5c0bc5b985f..47c1c495382 100644 --- a/code/_onclick/hud/rendering/render_plate.dm +++ b/code/_onclick/hud/rendering/render_plate.dm @@ -13,6 +13,8 @@ layer = -1 plane = 0 appearance_flags = PASS_MOUSE | NO_CLIENT_COLOR | KEEP_TOGETHER + /// If we render into a critical plane master, or not + var/critical_target = FALSE /** * ## Rendering plate @@ -119,6 +121,7 @@ plane = RENDER_PLANE_LIGHTING blend_mode_override = BLEND_MULTIPLY mouse_opacity = MOUSE_OPACITY_TRANSPARENT + critical = PLANE_CRITICAL_DISPLAY /atom/movable/screen/plane_master/rendering_plate/lighting/show_to(mob/mymob) . = ..() @@ -251,6 +254,7 @@ relay.blend_mode = blend_to_use relay.mouse_opacity = mouse_opacity relay.name = render_target + relay.critical_target = PLANE_IS_CRITICAL(target_plane) relays += relay // Relays are sometimes generated early, before huds have a mob to display stuff to // That's what this is for diff --git a/code/controllers/subsystem/mapping.dm b/code/controllers/subsystem/mapping.dm index a0f5096226e..0ae858b3fc6 100644 --- a/code/controllers/subsystem/mapping.dm +++ b/code/controllers/subsystem/mapping.dm @@ -47,6 +47,8 @@ SUBSYSTEM_DEF(mapping) var/list/plane_offset_blacklist /// List of render targets that do not allow for offsetting var/list/render_offset_blacklist + /// List of plane masters that are of critical priority + var/list/critical_planes /// The largest plane offset we've generated so far var/max_plane_offset = 0 @@ -111,6 +113,7 @@ SUBSYSTEM_DEF(mapping) plane_to_offset["[FLOAT_PLANE]"] = 0 plane_offset_blacklist = list() render_offset_blacklist = list() + critical_planes = list() create_plane_offsets(0, 0) initialize_biomes() loadWorld() @@ -802,6 +805,9 @@ GLOBAL_LIST_EMPTY(the_station_areas) generate_offset_lists(old_max + 1, max_plane_offset) SEND_SIGNAL(src, COMSIG_PLANE_OFFSET_INCREASE, old_max, max_plane_offset) + // Sanity check + if(max_plane_offset > MAX_EXPECTED_Z_DEPTH) + stack_trace("We've loaded a map deeper then the max expected z depth. Preferences won't cover visually disabling all of it!") /// Takes an offset to generate misc lists to, and a base to start from /// Use this to react globally to maintain parity with plane offsets @@ -833,6 +839,9 @@ GLOBAL_LIST_EMPTY(the_station_areas) if(plane_offset != 0) continue + if(initial(master_type.critical) & PLANE_CRITICAL_DISPLAY) + critical_planes[string_plane] = TRUE + plane_offset_to_true[string_plane] = plane_to_use plane_to_offset[string_plane] = plane_offset diff --git a/code/datums/components/fov_handler.dm b/code/datums/components/fov_handler.dm index 1316f7ff7e0..10f58186991 100644 --- a/code/datums/components/fov_handler.dm +++ b/code/datums/components/fov_handler.dm @@ -22,7 +22,7 @@ qdel(src) //no QDEL hint for components, and we dont want this to print a warning regarding bad component application return - for(var/atom/movable/screen/plane_master/plane_master in mob_parent.hud_used.get_true_plane_masters(FIELD_OF_VISION_BLOCKER_PLANE)) + for(var/atom/movable/screen/plane_master/plane_master as anything in mob_parent.hud_used.get_true_plane_masters(FIELD_OF_VISION_BLOCKER_PLANE)) plane_master.unhide_plane(mob_parent) blocker_mask = new @@ -36,7 +36,7 @@ /datum/component/fov_handler/Destroy() var/mob/living/mob_parent = parent - for(var/atom/movable/screen/plane_master/plane_master in mob_parent.hud_used.get_true_plane_masters(FIELD_OF_VISION_BLOCKER_PLANE)) + for(var/atom/movable/screen/plane_master/plane_master as anything in mob_parent.hud_used.get_true_plane_masters(FIELD_OF_VISION_BLOCKER_PLANE)) plane_master.hide_plane(mob_parent) if(applied_mask) diff --git a/code/modules/cargo/centcom_podlauncher.dm b/code/modules/cargo/centcom_podlauncher.dm index 0f185c0effc..baec0b57829 100644 --- a/code/modules/cargo/centcom_podlauncher.dm +++ b/code/modules/cargo/centcom_podlauncher.dm @@ -105,7 +105,7 @@ var/datum/plane_master_group/planes = cam_screen.display_to(holder.mob) if(!renderLighting) - for(var/atom/movable/screen/plane_master/instance in holder.mob.hud_used.get_true_plane_masters(LIGHTING_PLANE, planes.key)) + for(var/atom/movable/screen/plane_master/instance as anything in holder.mob.hud_used.get_true_plane_masters(LIGHTING_PLANE, planes.key)) instance.set_alpha(100) cam_background = new diff --git a/code/modules/client/preferences/ambient_occlusion.dm b/code/modules/client/preferences/ambient_occlusion.dm index 1a58b065968..cf8bf28c1e5 100644 --- a/code/modules/client/preferences/ambient_occlusion.dm +++ b/code/modules/client/preferences/ambient_occlusion.dm @@ -6,5 +6,5 @@ /datum/preference/toggle/ambient_occlusion/apply_to_client(client/client, value) /// Backdrop for the game world plane. - for(var/atom/movable/screen/plane_master/rendering_plate/game_world/plane_master in client.mob?.hud_used?.get_true_plane_masters(GAME_PLANE)) + for(var/atom/movable/screen/plane_master/plane_master as anything in client.mob?.hud_used?.get_true_plane_masters(GAME_PLANE)) plane_master.show_to(client.mob) diff --git a/code/modules/client/preferences/multiz_performance.dm b/code/modules/client/preferences/multiz_performance.dm new file mode 100644 index 00000000000..7591401f2d8 --- /dev/null +++ b/code/modules/client/preferences/multiz_performance.dm @@ -0,0 +1,21 @@ +/// Boundary for how many z levels down to render properly before we start going cheapo mode +/datum/preference/numeric/multiz_performance + category = PREFERENCE_CATEGORY_GAME_PREFERENCES + savefile_key = "multiz_performance" + savefile_identifier = PREFERENCE_PLAYER + + minimum = MULTIZ_PERFORMANCE_DISABLE + maximum = MAX_EXPECTED_Z_DEPTH - 1 + +/datum/preference/numeric/multiz_performance/create_default_value() + return -1 + +/datum/preference/numeric/multiz_performance/apply_to_client(client/client, value) + // Update the plane master group's layering + var/datum/hud/my_hud = client.mob?.hud_used + if(!my_hud) + return + + for(var/group_key as anything in my_hud.master_groups) + var/datum/plane_master_group/group = my_hud.master_groups[group_key] + group.transform_lower_turfs(my_hud, my_hud.current_plane_offset) diff --git a/code/modules/mob/living/ventcrawling.dm b/code/modules/mob/living/ventcrawling.dm index fc139e00762..646659a6255 100644 --- a/code/modules/mob/living/ventcrawling.dm +++ b/code/modules/mob/living/ventcrawling.dm @@ -110,18 +110,18 @@ client.images -= current_image pipes_shown.len = 0 pipetracker = null - for(var/atom/movable/screen/plane_master/lighting in hud_used.get_true_plane_masters(LIGHTING_PLANE)) + for(var/atom/movable/screen/plane_master/lighting as anything in hud_used.get_true_plane_masters(LIGHTING_PLANE)) lighting.remove_atom_colour(TEMPORARY_COLOUR_PRIORITY, "#4d4d4d") - for(var/atom/movable/screen/plane_master/pipecrawl in hud_used.get_true_plane_masters(PIPECRAWL_IMAGES_PLANE)) + for(var/atom/movable/screen/plane_master/pipecrawl as anything in hud_used.get_true_plane_masters(PIPECRAWL_IMAGES_PLANE)) pipecrawl.hide_plane(src) return // We're gonna color the lighting plane to make it darker while ventcrawling, so things look nicer // This is a bit hacky but it makes the background darker, which has a nice effect - for(var/atom/movable/screen/plane_master/lighting in hud_used.get_true_plane_masters(LIGHTING_PLANE)) + for(var/atom/movable/screen/plane_master/lighting as anything in hud_used.get_true_plane_masters(LIGHTING_PLANE)) lighting.add_atom_colour("#4d4d4d", TEMPORARY_COLOUR_PRIORITY) - for(var/atom/movable/screen/plane_master/pipecrawl in hud_used.get_true_plane_masters(PIPECRAWL_IMAGES_PLANE)) + for(var/atom/movable/screen/plane_master/pipecrawl as anything in hud_used.get_true_plane_masters(PIPECRAWL_IMAGES_PLANE)) pipecrawl.unhide_plane(src) var/obj/machinery/atmospherics/current_location = loc diff --git a/code/modules/mob/mob.dm b/code/modules/mob/mob.dm index 6b0d03fdf87..5ef7d4d5da4 100644 --- a/code/modules/mob/mob.dm +++ b/code/modules/mob/mob.dm @@ -1142,7 +1142,7 @@ /mob/proc/sync_lighting_plane_alpha() if(!hud_used) return - for(var/atom/movable/screen/plane_master/rendering_plate/lighting/light_plane in hud_used.get_true_plane_masters(RENDER_PLANE_LIGHTING)) + for(var/atom/movable/screen/plane_master/light_plane as anything in hud_used.get_true_plane_masters(RENDER_PLANE_LIGHTING)) light_plane.set_alpha(lighting_alpha) ///Update the mouse pointer of the attached client in this mob diff --git a/code/modules/paperwork/paperbin.dm b/code/modules/paperwork/paperbin.dm index 8a1665014f7..032e24b12a6 100644 --- a/code/modules/paperwork/paperbin.dm +++ b/code/modules/paperwork/paperbin.dm @@ -152,7 +152,7 @@ /obj/item/paper_bin/update_overlays() . = ..() - var/static/reference_paper + var/static/obj/item/paper/reference_paper if (isnull(reference_paper)) reference_paper = new /obj/item/paper @@ -163,6 +163,9 @@ bin_overlay = mutable_appearance(icon, bin_overlay_string) if(total_paper > 0) + if(total_paper > length(paper_stack)) + SET_PLANE_EXPLICIT(reference_paper, initial(reference_paper.plane), src) + reference_paper.update_appearance() // Ensures all our overlays are on the right plane for(var/paper_number in 1 to total_paper) if(paper_number != total_paper && paper_number % PAPERS_PER_OVERLAY != 0) //only top paper and every nth paper get overlays continue diff --git a/tgstation.dme b/tgstation.dme index 2ebc8f0228c..74564061078 100644 --- a/tgstation.dme +++ b/tgstation.dme @@ -2830,6 +2830,7 @@ #include "code\modules\client\preferences\jobless_role.dm" #include "code\modules\client\preferences\mod_select.dm" #include "code\modules\client\preferences\multiz_parallax.dm" +#include "code\modules\client\preferences\multiz_performance.dm" #include "code\modules\client\preferences\names.dm" #include "code\modules\client\preferences\ooc.dm" #include "code\modules\client\preferences\parallax.dm" diff --git a/tgui/packages/tgui/interfaces/PreferencesMenu/preferences/features/game_preferences/multiz_performance.tsx b/tgui/packages/tgui/interfaces/PreferencesMenu/preferences/features/game_preferences/multiz_performance.tsx new file mode 100644 index 00000000000..1d3a70f144c --- /dev/null +++ b/tgui/packages/tgui/interfaces/PreferencesMenu/preferences/features/game_preferences/multiz_performance.tsx @@ -0,0 +1,12 @@ +import { createDropdownInput, Feature } from '../base'; + +export const multiz_performance: Feature = { + name: 'Multi-Z Detail', + category: 'GAMEPLAY', + description: 'How detailed multi-z is. Lower this to improve performance', + component: createDropdownInput({ + [-1]: 'Standard', + 1: 'Medium', + 0: 'Low', + }), +};