## About The Pull Request
I've seen a few cases in the past where LateInitialize is done cause of
the init return value being set to do so for no real reason, I thought I
should try to avoid that by ensuring LateInitialize isn't ever called
without overriding.
This fixes a ton of machine's LateInitialize not calling parent
(mechpad, door buttons, message monitor, a lot of tram machines,
abductor console, holodeck computer & disposal bin), avoiding having to
set itself up to be connected to power. If they were intended to not
connect to power, they should be using ``NO_POWER_USE`` instead.
Also removes a ton of returns to LateInit when it's already getting it
from parent regardless (many cases of that in machine code).
## Why It's Good For The Game
I think this is better for coding standard reasons as well as just
making sure we're not calling this proc on things that does absolutely
nothing with them. A machine not using power can be seen evidently not
using power with ``NO_POWER_USE``, not so much if it's LateInitialize
not calling parent.
## Changelog
🆑
fix: Mech pads, door buttons, message monitors, tram machines, abductor
consoles & holodeck computers now use power.
/🆑
## About The Pull Request
We currently have 2 types of xenos in the codebase, simple animal and
carbon.
I'd like to unite them both under basic, and I thought I should go for
simple animal first since it's more of a conversion than a remake.
This helps set a base for a future basic-only xeno, which would require
the following:
- Basic mobs (or just anything than Carbon) to have Organs, which we can
then use for things like referring to their plasma sac for egg-laying,
etc.
- All xeno types having a basic mob variant, preferably with an AI so
they would work without a player.
- Something be done about larva, either we'd split basic xenos into
"larva" and "adult" (like carbon) or have it be a separate path that can
also have organs so they can still have hivemind.
Everything else seems to have been done overtime as simple animals have
been converted to basic (HUDs and holding things now seem possible,
etc.)
Even if this doesn't work out, at least this cuts off a good chunk of
the remaining simple animals to convert to basic.
Sprites used (for mapping helpers):
Fire medkit
Toxin medkit
Oingo Boingo punch face (i tried to shrink it down)
## Why It's Good For The Game
This helps advance us move away from simple animals, and helps move
carbon xenos to basic mob later too if that's what we want to go for.
## Changelog
🆑
refactor: Xenomorphs (Lavaland & Oldstation ones) are now basic mobs.
/🆑
## About The Pull Request
adds a new gateway map, the Nanotrasen Museum it is filled with
""""Mannequins"""" and Common Core lore
im not putting the preview here because you really should explore it
yourself but if youre that curious i think the Checks tab in mapdiffbot
would have it
this gateway map contains no combat unless you count falling into chasms
because you did not carry a light
or going into the boarded room with no loot or any incentive with
obvious signs that there is the sole enemy on the map in there
the loot is the lore ok thanks
also makes mines detonate if theyre detonated by a non-mob im pretty
sure this couldnt have been intentional
trams stop chasms
and also the relevant items
<details>
<summary>on second thought if you want spoilers check this</summary>

</details>
## Why It's Good For The Game
more gateway maps = good
## Changelog
🆑
add: nanotrasen museum gateway map
/🆑
---------
Co-authored-by: MrMelbert <51863163+MrMelbert@users.noreply.github.com>
Co-authored-by: Ghom <42542238+Ghommie@users.noreply.github.com>
## About The Pull Request
Situation: areas have a list of all turfs in their area.
Problem: `/area/space` is an area and has a 6 to 7 digit count of turfs
that has to be traversed for every turf we need to remove from it. This
can take multiple byond ticks just to preform this action for a single
space rune
Solution: split the list by zlevel, and only search the right zlevel
list when removing turfs from areas.
replaces `area.get_contained_turfs()` with a few new procs:
* `get_highest_zlevel()` - returns the highest zlevel the area contains
turfs in. useful for use with `get_turfs_by_zlevel`
* `get_turfs_by_zlevel(zlevel)` - returns a list of turfs in the area in
a given zlevel. Useful for code that only cares about a specific zlevel
or changes behavior based on zlevel like lighting init.
* `get_turfs_from_all_zlevels()` - the replacement for
`get_contained_turfs()`, renamed as such so anybody copying/cargo
culting code gets a hint that a zlevel specific version might exist.
Still used in for loops that type checked so byond would do that all at
once
* `get_zlevel_turf_lists()` - returns the area's zlevel lists of lists
but only for non-empty zlevels. very useful for for loops.
The area contents unit test has been rewritten to ensure any improper
data triggers failures or runtimes by not having it use the helpers
above (some of which ensure a list is always returned) and access the
lists directly.
## About The Pull Request
Goes through and changes some `in area` / `in a` loops to use
`get_contained_turfs` to cut down on `in_world` loops. Saves some free
lag.
## Changelog
🆑 Melbert
fix: Some things which affect everything in an area are less laggy, the
"all lights are broken" station trait especially
/🆑
## About The Pull Request
I find the proc hard to read honestly. There's no reason we can't split
this into two functions - the secondary functionality is used only once,
in reader.dmm.
## Why It's Good For The Game
Code improvement
Glorious snake case
## Changelog
N/A nothing player facing
---------
Co-authored-by: san7890 <34697715+san7890@users.noreply.github.com>
## About The Pull Request
Fixes#76349
I didn't know that people needed to add any new traits to a global list
so they can be easily read in View Variables, and was pretty shocked to
find out many other people didn't know it was a thing. Let's make it a
thing by testing it using a new CI Python Linter to check this. But oh
no-

There were about 200+ missing traits. Alright, so let's do the
following:
* Move trait defines to their own dedicated folder in the `_DEFINES`
folder.
* Split up the traits mega-file into different files, for better
organization. One for the macros, one for the sources, and a few for the
"trait declarations"
* Run the linter a load of times and add everything to the globalvars
file, removing anything that's no longer used and figuring out where the
best categorization of it is. also minor code improvements. also rename
all of the ones that look weird. also fix list indentations
* Also alphabetize the lists because it's easy
* Move everything to a new `traits_by_type` list, while keeping the
admin one the way it is for the time being while we figure out a better
way to show that list to admins.
* Profit
## Why It's Good For The Game
Mapping trait injectors will now work for any type of trait. You
shouldn't add any trait via this injector though, but you're no longer
limited to coders remembering to add it to that critical list you
needed.
Lays the framework for a better view variables experience. This work is
too lengthy to presently do, but hopefully we can get this done sooner
rather than later. we will need a code-accessible way to view these
traits for such a framework to be implemented, so let's just do that.
Future steps are to break down the mega-declarations file into a folder
full of separate files by typepath, but that requires a lot of auditing.
Does need to happen one day though, there's a lot of mob traits mingled
with datum traits and auuugh we gotta do this later this PR is already
massive.
there's probably ways to game this but this catches _my_ mistakes so
good luck to everyone else (it should work for 99% of everyone)
## Changelog
Nothing applicable to players. However, to mappers, the mapping trait
injector should always be able to add any kind of trait (which is rather
good for the times when you need it).
## About The Pull Request
- Reworks transformation sting.
- Transformation sting is now temporary, lasting 8 minutes (number not
final) in humans.
- If used on a monkey, it lasts forever instead.
- While the target mob is dead or in stasis, the duration will not
progress, making it functionally infinite until revived and taken off
stasis, where it will resume its timer where it left off.
- Chemical cost reduced to 33
- DNA cost reduced to 2
- Removes TRAIT_NO_TRANSFORMATION_STING, instead just checks for
TRAIT_NO_DNA_COPY
- These were essentially the same traits, so I just combined the two
- Organizes some trait lists alphabetically
- Adds TRAIT_STASIS, to allow for reacting to mobs entering and exiting
stasis via COMSIGS
- Everything that checks IS_IN_STASIS now checks HAS_TRAIT TRAIT_STASIS,
which is probably more performant, so that's a bonus.
## Why It's Good For The Game
A lot of people don't like the current iteration of Transformation
Sting, me included
Right now it's only use is for a meme - you make the entire station into
felinids until you get lynched, and that's it.
It's not really a healthy ability for ling's current kit, so this pr
attempts to soft rework it to make it a bit more in line with how ling
should be acting - turning it into a source of short term confusion
between people, or using it on a body to cover your tracks.
This accomplish it two fold - One, it is now cheap enough to use twice
in rapid succession, allowing for quick on-the-spot "BE CONFUSED"
situations while you abscond. Two, as mentioned in the last paragraph,
you can poke a body of someone you murder to obfuscate the crime scene
and maybe help out in taking over someone's identity.
## Changelog
🆑 Melbert
balance: Transformation sting now lasts 8 minutes, down from permanent.
However, the effect is paused for dead and stasis mobs, making it
permanent SO LONG AS they stay dead or in stasis. The effect is also
permanent if used on a monkey.
balance: Transformation sting now costs 33 chemicals, down from 50.
balance: Transformation sting now costs 2 dna points, down from 3.
fix: Transformation sting works on monkeys again.
refactor: Refactored a bit of human randomization.
/🆑
## About The Pull Request
#78239 is a fun mapping add but engineered in a way that
1. Creates a real eyesore of a typepath
2. Would further proliferate a hundred subtypes if it became commonly
used
Instead of using subtypes for this I put the behaviour in a component
and made a mapping helper to apply the component.
Now you can just put the mapping helper on top of any turf you want to
make into a zelda bomb wall and it will be so, rather than having to
make different subtypes for walls with different icons.
## Why It's Good For The Game
Cleaner, more maintainable.
## Changelog
not player facing
---------
Co-authored-by: san7890 <the@san7890.com>
## About The Pull Request
- Morgue guarantees 1 human body to dissect even if
`morgue_cadaver_disable_nonhumans` config flag is set.
- All maps bar birdboat will now spawn with one additional morgue
cadaver.
- Did some minor code cleanup around the dead body placer, removes an
`in world` loop, etc.
## Why It's Good For The Game
- Morgue guarantees 1 human body to dissect even if
`morgue_cadaver_disable_nonhumans` config flag is set.
- This is mostly a downstream server issue but if your server enables
this config and has additional species enabled, the odds of you getting
a human to dissect tends to be very low.
- Why is this a problem? Well, a human is necessary to dissect to get
medical's tech.
- Why not get genetics to get you a hu-monkey? This is an option, but if
A. there's no geneticists or B. they are refusing to cooperate then you
tend to be SOL unless you want to wait for a greytide to come in after
drinking themselves to death. Given we have a role now dedicated to
performing dissections, having no job to do for the first twenty or so
minutes due to a lack of a human body is kind of sad.
- If this is an intended facet, I will revert this change and leave it
to the code improvements / bodycount uptick.
- All maps bar birdboat will now spawn with one additional morgue
cadaver.
- This was actually intended on some maps but has been stealthily
removed in some cases? Icebox and Delta used to have two dead body
spawners to place 4 cadavers. So I decided to bring this back.
- For the most part, this just gives higher population maps more bodies
to mess around with. Higher pop means more people means more people need
bodies, either for antagging, cooking, body replacements, or coron-ing.
- Also like, sometimes messing around with dead bodies are fun, and it's
nice to not have to worry that you're running out of them for actual
medical use.
- I can also make this scale on roundstart pop if we really care. But
that seems overkill. Especially as these maps had their body counts
higher for a while and were fine.
## Changelog
🆑 Melbert
balance: If your server has non-human morgue cadavers enabled, you will
be guaranteed one human cadaver no matter what.
balance: All maps (with the exception of Birdboat) now have an
additional morgue cadaver roundstart.
/🆑
## About The Pull Request
This adds a new emergency shuttle called the **Hall of Fame**.

It's designed around persistence. The goal is to have the shuttle store
memories, photos, and trophies for the crew to see!
## Why It's Good For The Game
Cool way for the crew to store and share memories.
## Changelog
🆑
add: Add a new 'Hall of Fame' emergency shuttle. It even comes with it's
own nifty photo album.
/🆑
## About The Pull Request
Hello friends, I've been on a bit of a lighting kick recently, and I
decided I clearly do not have enough things to work on as it is.
This pr adds angle support to static lights, and a concepting/debug tool
for playing with lights on a map.
Let's start from first principles yeah?
### Why Angled Lights?
Mappers, since they can't actually see a light's effect in editor, tend
to go off gut.
That gut is based more off what "makes sense" then how things actually
work
This means they'll overplace light sources, and also they tend to treat
lights, particularly light "bars" (the bigger ones) as directional.
So you'll have two lights on either sides of a pillar, lights inside a
room with lights outside pointing out, etc.

This has annoying side effects. A lot of our map is overlit, to the
point that knocking out a light does.... pretty much nothing.
I find this sad, and would like to work to prevent it. I think dark and
dim, while it does not suit the normal game, is amazing for vibes, and I
want it to be easier to see that.
Angled lights bring how lights work more in line with how mappers expect
lights work, and avoids bleedover into rooms that shouldn't be bled
into, working towards that goal of mine.
### How Angled Lights?
This is more complex then you'd first think so we'll go step by step

Oh before we start, some catchup from the last time I touched lighting
code.
Instead of doing a lighting falloff calculation for each lighting corner
(a block that represents the resolution of our lights) in view we
instead generate cached lightsheets. These precalculate and store all
possible falloffs for x and y distances from a source.
This is very useful for angle work, since it makes it almost totally
free.
Atoms get 2 new values. light_angle and light_dir
Light angle is the angle the light uses, and light_dir is a cardinal
direction it displays in
We take these values, and inside sheetbuilding do some optional angle
work. getting the center angle, the angle of a pair of coords, and then
the delta between them.
This is then multiplied against the standard falloff formula, and job
done.
We do need some extra fenangling to make this all work nicely tho.
We currently use a pixel turf var stored on the light source to do
distance calculations.
This is the turf we pretend the light source is on for visuals, most
often used to make wall lights work nice.
The trouble is it's not very granular, and doesn't always have the
effect you might want.
So, instead of generating and storing a pixel turf to do our distance
calculations against, we store x and y offset variables.
We use them to expand our working range and sheet size to ensure things
visually make sense, and then offset any positions by them.
I've added a way for sources to have opinions on their offsets too, and
am using them for wall lights.
This ensures the angle calculations don't make the wall behind a light
fulldark, which would be silly.
### Debug Tool?
In the interest of helping with that core problem, lights being complex
to display, I've added a prototyping tool to the game.
It's locked behind mapping verbs, and works about like this.
Once the verb is activated, it iterates over all the sources in the
world (except turfs because those are kinda silly), outlining and
"freezing" them, preventing any future changes.
Then, it adds 3 buttons to the owners of a light source.

The first button toggles the light on and off, as desired.
The third allows you to move the source around, with a little targeting
icon replacing your mouse
The second tho, that's more interesting.
The second button opens a debug menu for that light

There's a lot here, let's go through it.
Bit on the left is a list of templates, which allow you to sample
existing light types (No I have no idea why the background is fullwhite,
need to work on that pre merge)
You can choose one by clicking it, and hitting the upload button.
This replaces your existing lighting values with the template's,
alongside replacing its icon and icon state so it looks right.
There are three types as of now, mostly for categorization. Bar, which
are the larger typically stronger lights, Bulb, which are well, bulbs,
and Misc which could be expanded, but currently just contains floor
lights.
Alongside that you can manually edit the power, range, color and angle
of the focused light.
I also have support for changing the direction of the light source,
since anything that uses directional lighting would also tie light dir
to it.
This isn't *always* done tho, so I should maybe find a way to edit light
dir too.
My hope is this tool will allow for better concepting of a room's
lights, and easier changing of individual object's light values to suit
the right visuals.
### Lemon No Why What
Ok so I applied angle lights to bars and bulbs, which means I am
changing the lighting of pretty much every map in the codebase.
I'm gonna uh, go check my work.
Alongside this I intend to give lighting some depth. So if there's room
to make a space warmer, or highlight light colors from other sources, I
will do that.
(Images as examples)

I also want to work on that other goal of mine, making breaking lights
matter. So I'll be doing what I can to ensure you only need to break one
light to make a meaningful change in the scene.
This is semi complicated by one light source not ever actually reaching
fullbright on its own, but we do what we must because we can.

I'm as I hope you know biased towards darker spaces, I think contrast
has vibes.
In particular I do not think strong lights really suit maintenance.
Most of what is used there are bulbs, so I'm planning on replacing most
uses with low power bulbs, to keep light impacts to rooms, alongside
reducing the amount of lights placed in the main tunnels

**If you take issue with this methodology please do so NOW**, I don't
want to have to do another pass over things.
Oh also I'm saving station maps for last since ruins are less likely to
get touched in mapping march and all.
### Misc + Finishing Thoughts
Light templates support mirroring vars off typepaths using a subtype,
which means all the templates added here do not require updating if the
source type changes somehow. I'd like to expand the template list at
some point, perhaps in future.
I've opened this as a draft to make my intentions to make my changes to
lights known, and to serve as motivation for all the map changes I need
to do.
### Farish Future
I'm unhappy with how we currently configure lights. I would like a
system that more directly matches the idea of drawing falloff curves,
along with allowing for different falloffs for different colors,
alongside extending the idea to angle falloff.
This would make out of engine lighting easier, allow for nicer looking
lights (red to pink, blue to purple, etc), and improve accessibility by
artists.
This is slightly far off, because I have other obligations and it's
kinda complicated, but I'd like to mention it cause it's one of my many
pipedreams.
## Changelog
🆑
add: Added angle lighting, applies it to most wall lights!
add: Adds a lighting prototyping tool, mappers go try it out (it's
locked behind the mapping verb)
/🆑
---------
Co-authored-by: MMMiracles <lolaccount1@hotmail.com>
## About The Pull Request
Some things, like door control buttons, set locked directly instead of
calling lock() or unlock(). This fixes that, which should make sound
effects play. Also annotates some code where we *don't* want that to
happen with an explanation of why we just set locked directly.
## Why It's Good For The Game
Fixes Skyrat-SS13/Skyrat-tg/issues/21510, which also applies to
upstream.
## About The Pull Request
There were some attempts to get an area of an object that is confirmed
to be null in the condition, which resulted in runtimes when the helper
couldn't find an object.
Also ensures that the window spawner places window before the helper
tries to find it.
And updates damaged window integrity roll thresholds to guarantee
cracks.
## Why It's Good For The Game
No runtimes
## Changelog
🆑
fix: fixed possible issues with apc, airalarm and damaged
machinery/windows helpers
/🆑
## About The Pull Request
To control vents and scrubbers in ordinance, burn and engine chambers,
mappers extend the area outside of the walls towards a tile where they
place the air alarm.
With this PR, they can now assign `chamber_id` to an air alarm and
connect to the chamber with an air sensor. There is a new map helper for
this.
Also, this connection can be done manually. You need to click on a
sensor with a multi-tool, then unlock certain air alarm, and click with
a multi-tool on it. This action will link sensor to an air alarm,
reporting gas mixture from the sensor tile and giving control over the
vents and scrubbers of the sensor's area.
### TLDR
Before:
<img width="718" alt="ordnance_before"
src="https://user-images.githubusercontent.com/3625094/236577769-5d79871f-2dce-43be-a20a-e6669bfbc1c6.PNG">
After:
<img width="638" alt="ordnance_after"
src="https://user-images.githubusercontent.com/3625094/236577786-3c7e9c9f-1501-4747-bbe1-292fc4947b0d.PNG">
This is how the area is setup on meta station right now vs if it was
setup with a link

This is also true for the supermatter chamber - you can make the air
alarm display the gas mix in the actual chamber and avoid using mapping
area hack there too.
<img width="954" alt="supermatter_after"
src="https://user-images.githubusercontent.com/3625094/236578528-4650b426-6bf0-4634-a5b0-cad7a50d5b01.PNG">
## Why It's Good For The Game
The area hack is no longer needed and you can place air alarm to control
certain remote area wherever you want when you design a map. Even 3 air
alarms next to each other controlling 3 different burn chambers.
The air alarm will also report the gas mix on the actual tile of a
sensor, instead of the gas mix before the air alarm, which is usually a
normal habitable environment.
Also, now you can build such chambers manually because there are no
precise area editing tools available in-game to repeat the area hack.
## Changelog
🆑
add: Air alarms can be connected to an area remotely via air sensor with
multi-tool and corresponding access
qol: Mapping: Added air alarm helper to link air alarm with certain
chamber_id on map load
/🆑
## About The Pull Request
This PR adds mapping helpers for requests consoles. Two of them set up
if the console can receive ore updates, and if it can make
announcements, flipping their relevant variables to TRUE. The other
three adds the consoles to their relevant department console lists
during late initialize. This allowed me to remove three variables
directly from the consoles themselves.

New sprites by CoiledLamb!
~~This PR also anchors mapping helpers, to prevent effects like the
roundstart crate initialization from moving them.~~ This was fixed by a
different PR.
## Why It's Good For The Game
Less var edits, easier to see a console's type at a glance.
## Changelog
🆑 Profakos, sprites by CoiledLamb
qol: Most request console varedits have been moved to mapping helpers.
/🆑
## About The Pull Request
Persistent Birdshot CI failure was caused by broken floor helper sharing
a tile with a random loot spawner, which would sometimes spawn a
maintenance crate which deletes itself, but only after the crate eats
the mapping helper. This causes the mapping helper to delete before it
has initialised.
There's no reason for a mapper to assume this would cause a problem so
the fix isn't to edit the map, instead I just anchored all mapping
helpers so that closets won't try to contain them.
## Why It's Good For The Game
I'm really tired of birdshot failing CI
This probably fixes some other really niche bug nobody has noticed
## Changelog
Not player facing
## About The Pull Request
I asked someone in discord if it was worth it, they said it was, from
what i remember at least.
## Why It's Good For The Game
More comfort with apc's for mappers.
---------
Co-authored-by: san7890 <the@san7890.com>
## About The Pull Request
What it says on the tin. Warning: copy-pasted mapper sprites.
## Why It's Good For The Game
Fewer varedits, better maintainability, more obvious in the map editor
what's been applied to a given airlock.
## Changelog
No player facing changes.
Internal_organs now also contains external organs, so the naming was
incorrect
Requested by @tralezab in #72734
Also removed some now incorrect 'as anythings' that assumed everything
in the internal_organs list was an internal_organ (which is a lie since
I put extorgans in there which means runtimes and unintentionakl
behaviour
🆑
fix: fixes deadly harvesting just taking harmless extorgans
code: renames internal_organs to organs now that it can also contain
external_organs
/🆑
## About The Pull Request
Fixes#71504#70237 attempted to remove this and did in some cases, however the case
where the abandoned airlock is able to find an adjacent wall turf to
copy the type of still fails to delete the airlock.
This fixes that.
Also in my testing, the times where it _failed_ to find a nearby wall
turf to copy and spawned a default wall would leave the mapping helper
visible in the round. Oops!
## Why It's Good For The Game
Mapping helpers should always delete themselves when finished.
The airlocks with walls under them are funny once and annoying the rest
of the time. As of that older PR, this continuing to happen is regarded
as a bug.
Also apparently it might be required anyway for Wallening.
## Changelog
🆑
fix: Maintenance tunnels should no longer sometimes contain airlocks
with walls underneath them.
/🆑
New regression in init times. Closes
https://github.com/tgstation/dev-cycles-initiative/issues/32. CC @Fikou
- Instead of creating a human and icon for *every* cardboard cutout when
initialized, only creates the one we're actually using. When you're
about to use a crayon, creates all of them.
- Instead of using getFlatIcon, uses appearances directly.
## About The Pull Request
Reinforced plating mapping helpers worked for only a feew specific
use-case which ended up being the only usecases I tested, I've modified
the code so it should work as expected in all usecases. In short this
fixes reinforced plating appearing in places where there is not actually
plating for it to replace, and stacking multiple layers of plating where
there should not be multiple layers.
## Why It's Good For The Game
Fixes a bug I introduced myself.
## Changelog
🆑
fix: Reinforced Plating baseturf helpers work and should now be bug free
enough to be used in maps.
/🆑
## About The Pull Request
revive of #68760
this time a proc, not an element
this time supports cardboard cutouts
this time supports mob corpses

## Why It's Good For The Game
prevents these icons ever being outdated, they'll always look what they
are supposed to, saves spriting work
## Changelog
🆑 Fikou, a hood by Viro
refactor: humanoid mobs and cardboard cutouts automatically generate
their sprites, they no longer will be outdated
/🆑
Co-authored-by: Time-Green <timkoster1@hotmail.com>
Adds some new procs relating to baseturfs that replaces some code that
reads and sets them directly. Moves them to their own file. **To
reviewers: Any proc in baseturfs.dm that is snake_case is mine, anything
else is just moved**.
Adds tests for the existing procs of baseturfs.
I'm going to be doing some optimizations to baseturfs that change the
actual representation of baseturfs, and so I'm prepping these to be
implementation agnostic.
Co-authored-by: LemonInTheDark <58055496+LemonInTheDark@users.noreply.github.com>
## About The Pull Request
[Saves 0.2 seconds of init time. 50% of emissive
blockers](8318b648f6)
Emissive blockers are a decent expense during init, even these, which
are the ones that update outside of initialize.
I've inlined them, removed some redundant vars and checks, reduced the
arg count, and shifted some things around. This ends up saving 200ms, or
50% of its total cost.
I also shifted mutable_appearance about a bit. it's not a massive
saving, but it is technically faster
[Prevents a few redundant appearance_updates, saves 0.8 seconds of
init](5475cd778b)
Prequisit info: update_appearance is decently expensive
It's good then to only do it if we have a reason to, right?
Me and moth were shooting the shit about just general init time, and we
came up with the idea of tracking which update_appearances actually
"worked" and which didn't.
That bit comes later, let's enjoy the fruits of that work first
First, holograms were calling update_appearance on process, for almost
no reason.
I patched the one event they don't already "react" to, and then locked
it behind a change decection if.
good for live, doesn't impact init.
Next, decals. If you add a decal to something before it inits, it'll
react to the after successful init signal.
The trouble is the same atom could have its appearance updated from this
MORE then once, since decals can be stacked on tiles, and signal
unregisters don't work once the signal is sent.
So we add a flag to track if we've had this happen to us or not, so it
only happens once.
saves 80 ms
Power! lots of things call power_change on init, often more then once.
We'll update appearance for each of those calls, even if only one is an
actual change.
That's silly, better to track what sort of power we're using for our
appearance and go off that changing
This was taking about 300ms. Really stupid
Icon smoothing. After emissive blockers were added, any change to
something's icon smoothing would lead to an update_appearance call.
Nasty shit, specially cause of walls, which don't even use emissive
blockers.
Ok then, so we'll always update appearance for movables, and will allow
turfs that are interested to hook it manually.
Not many of those anyhow
This is slightly a dev ux thing, but it saves 600ms so I think it's
worth it. Rare case anyway
Telecomms:
telecomm machines were updating appearance on process. This is to cover
for them turning on/off on process.
Better then to just check if on actually changed.
This cost adds up midgame, doesn't impact init tho
Materials:
There's this update_appearance call in material on_apply. it doesn't do
anything.
The logs will lie to you and say it does, but it's just like reapplying
emissives. It doesn't need to exist
Saves like 50ms
Canisters:
Live thing, lots of time wasted updating appearance for no reason, lets
see if we change anything first yes?
[Uses defines to wrap update_appearance for
tracking](4fa82e1c9d)
[Undoes _update_appearance changes, instead reccomends 2 regexes to
use](a8c8fec57a)
I need file and line number for my tracking, so I need to override
update_appearance calls, and also preferably not require every override
of update_appearance to handle dummy file + line args.
So instead, I created a wrapper proc that checks to see if appearanaces
match (they're unique remember, the two of the same visual appearance
will be equivalent)
The trouble is I can't intercept JUST proc calls, or JUST function
definitions with defines. it needs to be both.
So I renamed the /update_appearance proc to /_update_appearance
this way I can capture old uses, and don't need to worry about merge/dev
brain skew
~~It does mean that all update_appearance proc definitions now look
weird tho.
My profiling is leaking into dev ux. I wish I had better templating.~~
**The above is no longer being pr'd**, it's instead just recommended via
a few regexes adjacent to the define.
Smelled wrong anyhow
[Adds a setter for panel_open, so I can update_appearance on
it](cf1df8a69f)
## Why It's Good For The Game
Speed
## About The Pull Request
This PR adds reinforced plating and a corresponding baseturf_helper,
plating that cannot be deconstructed with the RCD and requires a few
steps to degrade to regular plating.
The plating is designed to serve the same purpose as R-Walls but for
verticality. It shares its heat resistance with reinforced floor and
hull, and in texting it can endure a single C4 blast but not X4 assuming
the floor placed on it is already removed.
It is currently is unused on the existing maps due to it being poor
practice to place secure locations that would justify reinforced floors
on the lower Z levels, however I have spoken to people working on maps
actively at the moment and they have express interest in being able to
use these floors.
The plating can be constructed by using 2 sheets of plasteel on standard
plating and is disassembled using wrench > welding tool > crowbar. The
first stage of deconstruction causes the bolts holding the
reinforcements in place to fall to the Z level below playing a sound and
leaving a cleanable decal, adding a audio-visual alert that someone is
about to come through your ceiling.
UPDATE: I've added a ceiling variant of the baseturf editor, this can be
placed on a lower Z level where it will modify the baseturfs of the Z
level above within the original area. This will make it significantly
easier to ensure that you only cover tiles you want reinforced when
protecting lower Z levels.
If anyone has any recommendations for sounds please tell me and I might
swap them out but I think the two I've chosen work well. Additionally if
anyone is able to make a better sprite for the screws or plates then
that'd be a great help but I think the current ones work well enough.
## Why It's Good For The Game
Currently Multi-Z maps have a very tight restriction on where secure
areas can be put, only allowing for them to be placed on the top Z
level, under more secure Z levels or in exterior satellites and coated
with hulls. This is due to standard plating and/or reinforced floors are
very easy to get through without warning if you bring the right tools.
This PR effectively adds R-Walls but for floors allowing mappers to
properly protect lower Z levels from vertical infiltration methods. This
also adds a visual and audible indictor to the deconstruction of
reinforced floor tiles to bring them more in line with the visuals of
deconstructing a wall.
## Changelog
🆑
add: You can now reinforce plating to protect your department from the
troublemakers upstairs. Station builders might find these useful to put
the stations most secure locations on the lower floors.
imageadd: added sprites for reinforced plating
code: RCD proofing has been variablized and can now be applied to any
floor type instead of just reinforced floors.
/🆑
Makes the code compatible with 515.1594+
Few simple changes and one very painful one.
Let's start with the easy:
* puts call behind `LIBCALL` define, so call_ext is properly used in 515
* Adds `NAMEOF_STATIC(_,X)` macro for nameof in static definitions since
src is now invalid there.
* Fixes tgui and devserver. From 515 onward the tmp3333{procid} cache
directory is not appened to base path in browser controls so we don't
check for it in base js and put the dev server dummy window file in
actual directory not the byond root.
* Renames the few things that had /final/ in typepath to ultimate since
final is a new keyword
And the very painful change:
`.proc/whatever` format is no longer valid, so we're replacing it with
new nameof() function. All this wrapped in three new macros.
`PROC_REF(X)`,`TYPE_PROC_REF(TYPE,X)`,`GLOBAL_PROC_REF(X)`. Global is
not actually necessary but if we get nameof that does not allow globals
it would be nice validation.
This is pretty unwieldy but there's no real alternative.
If you notice anything weird in the commits let me know because majority
was done with regex replace.
@tgstation/commit-access Since the .proc/stuff is pretty big change.
Co-authored-by: san7890 <the@san7890.com>
Co-authored-by: Mothblocks <35135081+Mothblocks@users.noreply.github.com>
* Fixes halloween races.
- Fixes a race condition involve checking for holidays befores SSevents is instantiated. Now, holiday checking is done through a helper, which will ensure the holidays list is created and filled before checked.
Splits head dmi into separate files for both mob and obj icons. Kept similar to suit split categorization + some more. New files include beanie, bio, chaplain, costume, cowboy, default, hats(softcaps, fedoras, head caps, generic hats), helmet(helmets and other armored headgear/hoods), spacehelm, utility(hardhats, mostly work related hats), wizard.
Moves animal/pet head sitting icons to 1 folder, pets_head.dmi
Renames PAI head sitting icon file to pai_head.dmi
fix: Fixed a runtime preventing nonhuman cadavers from spawning properly.
config: Cadaver spawners will no longer yell at you when morgue_cadaver_other_species_probability is blank.
config: morgue_cadaver_disable_nonhumans will now properly disable nonhuman races! (It was reversed, woops.)
* Optimizes away /obj/Initialize
We were spending like 0.15 seconds just checking for blueprints, obj
flags and network ids
All these things can just be applied where they're wanted, saves time
Oh and I replaced object flags with an emag injector. I'll give it a
sprite and name later I promise
* Requires a GenerateTag() call to set DF_USE_TAG, rather then doing a check in atom New
This is technically harder to use, but I don't really want people using
tags, and it saves 0.15 seconds
* Moves generatetag to /datum
* I am dumb
* Saves 0.5 seconds, makes init emissive blockers actually work
Ok so background. If an overlay is added with add_overlay, and not
"managed" somehow, it will effectively never be removed, because
nothing's tracking it.
Update_overlays uses the managed_overlays list/var (one of those) to do
this.
I'm gonna piggyback off this to make emissive overlays actually like,
respect overlay updates.
Oh and uh, I've saved maybe 0.5 seconds by caching the new emissive, and
not using add_overlay. There's a chance this will lead to overlay
corruption, but since we never readd the flattened, I think we'll be
safe
* Fixes plane not being set right, changes color logic too, since alpha will override past color sets
* Makes it actually work. also makes rand posters update appearance to clear away the overlay, since it shows on right click and looks bad
* Fixes blockers showing as emissives. It turns out alpha sets override the color list we use. Not sure why we pretend to support them
* Makes the injector support traits, adds an amazing sprite
Makes trapdoors player-craftable.
Player-crafted trapdoors have a tiny outline as well as being visible on examine. (Mapped in trapdoors have conspicuous = FALSE by default)
Trapdoors can be made by using a trapdoor kit (crafted via player crafting menu) on openspace.
Trapdoor electronics / assembly can be made via autolathe or engineering lathe.
A preloaded trapdoor remote (optional) can be made by crafting the electronics with a compact remote (from science lathe / circuit lab) and some cable coil.
Also allows unlinking trapdoors via a multitool, decreased trapdoor link range, and made some changes to trapdoor code.
Added change: Trapdoors now don't break with just a crowbar
Why It's Good For The Game
Trapdoors currently can only be added in by mappers and this would allow for a lot of interesting contraptions, while having player-crafted trapdoors be detectable provides some counterplay
Picture
trapdoorlookdemo
Changelog
cl
add: You can now make trapdoors. Craft a trapdoor kit and use it on an openspace tile to make one, then link and activate it with some trapdoor electronics (printable at an autolathe or the engineering lathe) and optionally a trapdoor remote (crafted in personal crafting menu).
qol: You can now unlink trapdoors by using a multitool on them.
balance: Trapdoors now won't break if you just crowbar them. You need to block them from closing, such as with a lattice, cover it up with a wall, or fully destroy the floor tile its on to get rid of them.
/cl
* Makes condiments their own subtype, fixes geese, prepares for merging
* Fixes geese checking drink type instead of edible foodtype to eat gross food.
* Renames foodtype var on drinks to drink_types to prevent above from happening again because it KEEPS HAPPENING. DRINKS AREN'T FOOD!
* Makes Condiments their own subtype of reagent_containers because they don't make any use of being a subtype of food, at all.
* Starts moving things from food to /food/drink subtype in preparation for merging /food/drink with /drink
* fully removes Food subtype
* /reagent_containers/drinks are now /reagent_containers/cup - This is so it's no longer confused with eachother.
* /food/drinks is now /reagent_containers/cup/drinks, so we can keep their special abilities.
* Fixes a LOT of errors with food, which are STILL checking the reagent_containers, despite ACTUAL food being refactored away from it a long time ago.
This doesn't compile yet, but I do want to make sure my progress is well tracked.
* remove copypaste code, changes soda cans
* Removes most copy paste code between the two drinks, moving most stuff to parent whenever needed.
* Made soda cans their own subtype since they didn't share anything with glass bottles anyways.
* Fixes more problems with food/drinks, especially with geese. Geese really were just broken this whole time and no one said a word...
* Removes a snowflake signal, now that both drink types share a common one.
* Adds everything to the .dme
Currently my goal is to get this all compiling, then remove isGlass var by making glass be all glass ones only.
* Moves all icons into a single drinks dmi
I'm not that great at icon stuff, hopefully I didn't forget/break anything.
* Turns juices into their own subtype
This allows us to let them check for type in molotov, to both get rid of a use of isGlass, and so non-glass non-cartons don't show up as 'carton'.
* fixes compile issues, adds updatepaths
* a better updatepaths
* updates the damn maps now
* properly names the updatepath
* how did that get there
* i suck at handling merge conflicts
* how am i this bad
* code improvement and soda fix
* more fixes
* Don't be a timer
Ports from old food bottles to trans the reagents, rather than add a timer to.
* Merge conflicts and fixes bottle smashing
* Bottle smashing is now consistently functional regardless of how much liquid they have in them, when before it would spill first, then smash on the second hit.
* runs updatepaths again
* Abusing Generosity - Unrestricted Airlock Access Flip
Hey there,
We now have a lot of unrestricted access helpers on airlocks, which are neato. However, while spitballing ideas in regards to this a few months ago, someone suggested to make it such that you can use the airlock wires to "flip" the directional way. I decided to sit down and code it in today.
The high details are this: You can only do it if the airlock has a directional Request-to-Exit sensor (which is just a thing I made up, you can't get this in-game outside of mapping it in via a directional helper). You can tell if a door has it the same way you can tell if any door is a directional door, or you can simply just check to see if the Unrestricted Access Display is "on" in any capcity (the airlock will not have the sensor if the display is off).
It's effectively a dud without the "sensor". However, if it does have it, you can either pulse it (to switch the direction by 180 degrees) or cut the wire (to disable the direction entirely). When you mend the wire though, it'll activate to a random direction (could even be inside a wall). You can keep cutting and mending until you get what you want, though. If it gets stuck in a wall though... shouldn't have cut it.
While in the area, I alphabetized a bunch of lists, added a new color of airlock wire, and probably some other stuff.
* Adds this behavior to building new airlocks
I also renamed it to "sensor" so it's a bit clearer across all the potential contexts.
It does seem to handle setting multiple directions on creating a new mapload, cutting/pulsing will condense the nice multi-directional stuff into one direction (i am okay with this).
Co-authored-by: spookydonut <github@spooksoftware.com>
Co-authored-by: John Willard <53777086+JohnFulpWillard@users.noreply.github.com>
* Merge Conflict Markers - The Explicit Pathing
Hey there,
This PR corrects an issue I've been having with mapmerge2 these last few months. Basically, what it does is create a base `/obj` that is given the name `---Merge Conflict Marker---`. This is fine and all, but the problem is that the base `/obj` is set to a certain plane. This does mean that sometimes, this VERY IMPORTANT marker is covered up by rocks or other objects. So, this seeks to get rid of that potential flaw, as well as do some other things.
Sometimes, when objects are rendered via GAGS or other code-means, they tend to have the same default Purple/White Sprite that any object without a valid icon_state has. This has caused me some confusion, so I have decided to create a new icon for conflict markers. This icon was designed to be as ugly as possible, while creating as much contrast as possible with the background by incorporating several colors into its design. I hope you find merge conflicts as unpleasant as I do.
I also updated mapmerge2 to have it so you can set the specified path of the object, as well as a small comment on the warnings if you do not heed it. I'm keeping the fact that mapmerge2 adds a name to the object just in case someone else really needs that. I also updated the linters to check for this path as well (even though the name and description should suffice for linting), and it should all be gravy from here.
* Adds further contrast to the DMI.
* Splits the merge conflict marker into a generic /obj
I also added a thing where if it didn't get caught by linters and it showed up on Initalize, it would error to mapping logs, spit out an error in world, and do all sorts of stuff to remind you.
* python new line
* forgot to add a tab
Hey there,
Access helper layers are great and all, but they tended to have this sort of effect on maps where since they were on the same layer as all of the other mapping helpers for doors, they would just tend to cover up the smaller sprites the others used, like this:
So, this just switches up the layers a bit by having a new layer called `DOOR_ACCESS_HELPER_LAYER` (that is still above `OPEN_DOOR_LAYER`) just for Access Helpers, while every other airlock helper takes the `DOOR_HELPER_LAYER` (like before), which has been increased by 0.01 more funny number.
Ok?
Small QoL thing for mappers. Mapping Helpers automatically go on the highest plane possible, POINT_LAYER. This would result in broken/burnt flooring having the following appearance in map editors:
This is just weird clutter that doesn't particularly look good. So, I just switched both of those subtypes to the same layer that we use for cleanable decal effects, just for nice visual clarify. Here's what that looks like:
About The Pull Request
Hello once more! As we near summer, I continued to reminisce on several PRs done throughout last year! One of them was the controversial, but rather positive Tilening V1, as done by me and Twaticus a while back (#58932), and felt I could've done a better job with how it was presented.
And thus, thanks to @Fikou encouraging me with a very interesting find of a previous tile resprite attempt, I've successfully done it!
Ladies and Gentlemen, I present to you all, Tilening Version Two!
image
Now this isn't your run of the mill tile resprite. While I did improve the appearance of several tiles I haven't touched last time (including the showroom/freezer tiles now), I decided to do something special that most mappers shall appreciate!
Don't you hate it when of all damaged states, there's only ones for grey tiles when we have white, black, terracotta and a bunch of other materials? Don't you wish they were overlays instead?
Well golly gee do I have good news for you!
image
image
After painstakingly spending at least several hours trying to learn enough code to pull it off, I have successfully made it so most tiles display transparent versions of damage overlays over them! This means mappers can express their creativity that much better! And thanks to how the code is written, its super easy to snowflake certain tile types to make them use unique damaged states (looking at you wooden tiles), so fret not in that aspect.
Credits to:
@WJohn For actually making those damaged overlays! Wouldn't've done the PR if it wasn't for you.
@dragomagol, @RigglePrime and @LemonInTheDark for helping me out in a VC at 10 PM to 12 AM troubleshooting the code to make this improvement work!
Why It's Good For The Game
The shading is done better as compared to last time, making them feel more cubical and less like a pancake when seen from above! This PR also makes it so that we never ever have to touch damaged tiles ever again potentially, saving up some RSC regarding icons.
However, due to how damaged tiles are currently mapped in, rather than overlayed as I envision in the future, it'll require a PR by San to be merged later that should make it safe to remove these icons.
Changelog
cl PositiveEntropy, WJohnston, Dragomagol, LemonInTheDark, Riggle
imageadd: Resprites most variety of tiles into a better shaded version!
code: Damaged floors are now damaged overlays, meaning that most tiles should properly display a damaged state!
/cl