Files
Bubberstation/code/modules/tgui/status_composers.dm
The Sharkening 77616e8b0e Add Proteans to the game. (#3449)
## About The Pull Request

Adds the funny nanite blob dudes from Vigro code into the game. It's
more of a port of the idea since they're coded from the ground up. They
will be more of a utility focused species then a combat focused species.
**They are fragile.**

- Eats metal. You need metal to live and you need metal to heal. 
- Healed by materials. You feed Proteans metal to heal them.
- Difficult to kill, but extremely fragile. They are considered a
deathless species but they are stuck in their suit if they die. **You
have to order a new refactory from cargo to revive them**

**Order Refactory > Screwdriver suit > Insert refactory > Wait 5
minutes.**

- Easily dismembered. They have 30 seconds to recover their limbs and
pop them on or they will melt into nothingness. Can do a lengthy heal
which replaces missing limbs and easy to replace organs.
- Without a refactory, you will wither away.
- Without an orchastrator, you will have a lot of issues moving.
- You can lock your suit on someone. (OOC escape will work)
- You can assimilate modsuits.

- [x] OOC escape
- [x] Suit Transformation fixes
- [x] Modsuit Assimilation
- [x] Ensure organs are working
- [x] Species info and lore
- [x] Antag Proteans
- [x] Custom damage. Disable various surgeries.
- [x] Testing, polish, feedback.
- [x] Runtime and CI fixing.
- [ ] Live testing and balance.

## Why It's Good For The Game

This was the second to top vote on species people wanted to see added
and this is more custom mechanics then what is just a human reskin.

## Proof Of Testing


![NVIDIA_Overlay_bC6M2FThJP](https://github.com/user-attachments/assets/cb8c8594-f82c-408b-a9a1-e86a61bf8a0f)


![NVIDIA_Overlay_dbhHrYltOH](https://github.com/user-attachments/assets/cb643365-5512-465f-8582-337e24211b9f)

## Changelog

🆑 StrangeWeirdKitten, Majkl-J
add: New species: Proteans
/🆑

---------

Co-authored-by: Waterpig <49160555+Majkl-J@users.noreply.github.com>
Co-authored-by: Bubberbot <151680451+Bubberbot@users.noreply.github.com>
Co-authored-by: Arturlang <24881678+Arturlang@users.noreply.github.com>
Co-authored-by: aKromatopzia <94389683+aKromatopzia@users.noreply.github.com>
Co-authored-by: Jinshee <96621959+Jinshee@users.noreply.github.com>
Co-authored-by: Jinshee <manastra2536@gmail.com>
Co-authored-by: JustMeTheIInd <145101584+JustMeTheIInd@users.noreply.github.com>
Co-authored-by: nevimer <77420409+nevimer@users.noreply.github.com>
Co-authored-by: Odairu <39929315+Odairu@users.noreply.github.com>
Co-authored-by: LT3 <83487515+lessthnthree@users.noreply.github.com>
Co-authored-by: Roxy <75404941+TealSeer@users.noreply.github.com>
2025-05-13 15:05:46 -04:00

123 lines
4.8 KiB
Plaintext

/// The sane defaults for a UI such as a computer or a machine.
/proc/default_ui_state(mob/user, atom/source)
return min(
ui_status_user_is_abled(user, source),
ui_status_user_has_free_hands(user, source),
ui_status_user_is_advanced_tool_user(user),
ui_status_only_living(user),
max(
ui_status_user_is_adjacent(user, source),
ui_status_silicon_has_access(user, source),
)
)
/// Returns a UI status such that users adjacent to source will be able to interact,
/// far away users will be able to see, and anyone farther won't see anything.
/// Dead users will receive updates no matter what, though you likely want to add
/// a [`ui_status_only_living`] check for finer observer interactions.
/proc/ui_status_user_is_adjacent(mob/user, atom/source, allow_tk = TRUE, viewcheck = TRUE) // Bubber edit: Adds viewcheck
if (isliving(user))
var/mob/living/living_user = user
return living_user.shared_living_ui_distance(source, viewcheck, allow_tk = allow_tk) // Bubber edit: Adds viewcheck
else
return UI_UPDATE
/// Returns a UI status such that the dead will be able to watch, but not interact.
/proc/ui_status_only_living(mob/user, source)
if (isliving(user))
return UI_INTERACTIVE
if(isobserver(user))
// If they turn on ghost AI control, admins can always interact.
if(isAdminGhostAI(user))
return UI_INTERACTIVE
// Regular ghosts can always at least view if in range.
var/datum/client_interface/client = GET_CLIENT(user)
if(client)
var/clientviewlist = getviewsize(client.view)
if(get_dist(source, user) < max(clientviewlist[1], clientviewlist[2]))
return UI_UPDATE
return UI_CLOSE
/// Returns a UI status such that users with debilitating conditions, such as
/// being dead or not having power for silicons, will not be able to interact.
/// Being dead will disable UI, being incapacitated will continue updating it,
/// and anything else will make it interactive.
/proc/ui_status_user_is_abled(mob/user, atom/source)
return user.shared_ui_interaction(source)
/// Returns a UI status such that those without blocked hands will be able to interact,
/// but everyone else can only watch.
/proc/ui_status_user_has_free_hands(mob/user, atom/source, allowed_source)
if(allowed_source)
return HAS_TRAIT_NOT_FROM(user, TRAIT_HANDS_BLOCKED, allowed_source) ? UI_UPDATE : UI_INTERACTIVE
return HAS_TRAIT(user, TRAIT_HANDS_BLOCKED) ? UI_UPDATE : UI_INTERACTIVE
/// Returns a UI status such that advanced tool users will be able to interact,
/// but everyone else can only watch.
/proc/ui_status_user_is_advanced_tool_user(mob/user)
return ISADVANCEDTOOLUSER(user) ? UI_INTERACTIVE : UI_UPDATE
/// Returns a UI status such that silicons will be able to interact with whatever
/// they would have access to if this was a machine. For example, AIs can
/// interact if there's cameras with wireless control is enabled.
/proc/ui_status_silicon_has_access(mob/user, atom/source)
if (!issilicon(user))
return UI_CLOSE
var/mob/living/silicon/silicon_user = user
return silicon_user.get_ui_access(source)
/// Returns a UI status representing this silicon's capability to access
/// the given source. Called by `ui_status_silicon_has_access`.
/mob/living/silicon/proc/get_ui_access(atom/source)
return UI_CLOSE
/mob/living/silicon/robot/get_ui_access(atom/source)
// Robots can interact with anything they can see.
var/list/clientviewlist = getviewsize(client.view)
if(get_dist(src, source) <= min(clientviewlist[1],clientviewlist[2]))
return UI_INTERACTIVE
return UI_DISABLED // Otherwise they can keep the UI open.
/mob/living/silicon/ai/get_ui_access(atom/source)
// The AI can interact with anything it can see nearby, or with cameras while wireless control is enabled.
if(!control_disabled && can_see(source))
return UI_INTERACTIVE
return UI_CLOSE
/mob/living/silicon/pai/get_ui_access(atom/source)
// pAIs can only use themselves and the owner's radio.
if((source == src || source == radio) && !stat)
return UI_INTERACTIVE
else
return UI_CLOSE
/// Returns UI_INTERACTIVE if the user is conscious and lying down.
/// Returns UI_UPDATE otherwise.
/proc/ui_status_user_is_conscious_and_lying_down(mob/user)
if (!isliving(user))
return UI_UPDATE
var/mob/living/living_user = user
return (living_user.body_position == LYING_DOWN && living_user.stat == CONSCIOUS) \
? UI_INTERACTIVE \
: UI_UPDATE
/// Return UI_INTERACTIVE if the user is strictly adjacent to the target atom, whether they can see it or not.
/// Return UI_CLOSE otherwise.
/proc/ui_status_user_strictly_adjacent(mob/user, atom/target)
if(get_dist(target, user) > 1)
return UI_CLOSE
return UI_INTERACTIVE
/// Return UI_INTERACTIVE if the user is inside the target atom, whether they can see it or not.
/// Return UI_CLOSE otherwise.
/proc/ui_status_user_inside(mob/user, atom/target)
if(target.contains(user))
return UI_INTERACTIVE
return UI_CLOSE