Merge branch 'master' into kk-charpod

This commit is contained in:
Killian
2024-12-04 09:25:02 +00:00
committed by GitHub
382 changed files with 4527 additions and 3682 deletions
+6 -6
View File
@@ -43,7 +43,7 @@
/datum/ColorMate/tgui_state(mob/user)
return GLOB.tgui_conscious_state
/datum/ColorMate/tgui_data()
/datum/ColorMate/tgui_data(mob/user)
. = list()
.["activemode"] = active_mode
.["matrixcolors"] = list(
@@ -69,7 +69,7 @@
.["item"] = list()
.["item"]["name"] = inserted.name
.["item"]["sprite"] = icon2base64(get_flat_icon(inserted,dir=SOUTH,no_anim=TRUE))
.["item"]["preview"] = icon2base64(build_preview())
.["item"]["preview"] = icon2base64(build_preview(user))
else
.["item"] = null
@@ -159,7 +159,7 @@
return TRUE
/// Produces the preview image of the item, used in the UI, the way the color is not stacking is a sin.
/datum/ColorMate/proc/build_preview()
/datum/ColorMate/proc/build_preview(mob/user)
if(inserted) //sanity
var/list/cm
switch(active_mode)
@@ -178,17 +178,17 @@
text2num(color_matrix_last[11]),
text2num(color_matrix_last[12]),
)
if(!check_valid_color(cm, usr))
if(!check_valid_color(cm, user))
return get_flat_icon(inserted, dir=SOUTH, no_anim=TRUE)
if(COLORMATE_TINT)
if(!check_valid_color(activecolor, usr))
if(!check_valid_color(activecolor, user))
return get_flat_icon(inserted, dir=SOUTH, no_anim=TRUE)
if(COLORMATE_HSV)
cm = color_matrix_hsv(build_hue, build_sat, build_val)
color_matrix_last = cm
if(!check_valid_color(cm, usr))
if(!check_valid_color(cm, user))
return get_flat_icon(inserted, dir=SOUTH, no_anim=TRUE)
var/cur_color = inserted.color
+9 -10
View File
@@ -452,26 +452,25 @@
data["crafting_recipes"] = crafting_recipes
return data
/datum/component/personal_crafting/tgui_act(action, params)
/datum/component/personal_crafting/tgui_act(action, params, datum/tgui/ui)
. = ..()
if(.)
return
switch(action)
if("make")
var/mob/user = usr
var/datum/crafting_recipe/TR = locate(params["recipe"]) in GLOB.crafting_recipes
busy = TRUE
tgui_interact(user)
var/atom/movable/result = construct_item(user, TR)
tgui_interact(ui.user)
var/atom/movable/result = construct_item(ui.user, TR)
if(!istext(result)) //We made an item and didn't get a fail message
if(ismob(user) && isitem(result)) //In case the user is actually possessing a non mob like a machine
user.put_in_hands(result)
if(ismob(ui.user) && isitem(result)) //In case the user is actually possessing a non mob like a machine
ui.user.put_in_hands(result)
else
result.forceMove(user.drop_location())
to_chat(user, span_notice("[TR.name] constructed."))
TR.on_craft_completion(user, result)
result.forceMove(ui.user.drop_location())
to_chat(ui.user, span_notice("[TR.name] constructed."))
TR.on_craft_completion(ui.user, result)
else
to_chat(user, span_warning("Construction failed[result]"))
to_chat(ui.user, span_warning("Construction failed[result]"))
busy = FALSE
if("toggle_recipes")
display_craftable_only = !display_craftable_only
+101
View File
@@ -0,0 +1,101 @@
/datum/component/gargoyle
var/energy = 100
var/transformed = FALSE
var/paused = FALSE
var/paused_loc
var/cooldown
var/mob/living/carbon/human/gargoyle //easy reference
var/obj/structure/gargoyle/statue //another easy ref
//Adjustable mod
var/identifier = "statue"
var/adjective = "hardens"
var/material = "stone"
var/tint = "#FFFFFF"
/datum/component/gargoyle/Initialize()
if (!ishuman(parent))
return COMPONENT_INCOMPATIBLE
gargoyle = parent
add_verb(gargoyle,/mob/living/carbon/human/proc/gargoyle_transformation)
add_verb(gargoyle,/mob/living/carbon/human/proc/gargoyle_pause)
add_verb(gargoyle,/mob/living/carbon/human/proc/gargoyle_checkenergy)
START_PROCESSING(SSprocessing, src)
/datum/component/gargoyle/process()
if (QDELETED(gargoyle))
return
if (paused && gargoyle.loc != paused_loc)
unpause()
if (energy > 0)
if (!transformed && !paused)
energy = max(0,energy-0.05)
else if (!transformed && isturf(gargoyle.loc))
gargoyle.gargoyle_transformation()
if (transformed)
if (!statue)
transformed = FALSE
statue.damage(-0.5)
energy = min(energy+0.3, 100)
/datum/component/gargoyle/proc/unpause()
if (!paused || transformed)
paused = FALSE
paused_loc = null
UnregisterSignal(gargoyle, COMSIG_ATOM_ENTERING)
return
if (gargoyle?.loc != paused_loc)
paused = FALSE
paused_loc = null
energy = max(energy - 5, 0)
if (energy == 0)
gargoyle.gargoyle_transformation()
UnregisterSignal(gargoyle, COMSIG_ATOM_ENTERING)
//verbs or action buttons...?
/mob/living/carbon/human/proc/gargoyle_transformation()
set name = "Gargoyle - Petrification"
set category = "Abilities.Gargoyle"
set desc = "Turn yourself into (or back from) being a gargoyle."
if (stat == DEAD)
return
var/datum/component/gargoyle/comp = GetComponent(/datum/component/gargoyle)
if (comp)
if (comp.energy <= 0 && isturf(loc))
to_chat(src, span_danger("You suddenly turn into a [comp.identifier] as you run out of energy!"))
else if (comp.cooldown > world.time)
var/time_to_wait = (comp.cooldown - world.time) / (1 SECONDS)
to_chat(src, span_warning("You can't transform just yet again! Wait for another [round(time_to_wait,0.1)] seconds!"))
return
if (istype(loc, /obj/structure/gargoyle))
qdel(loc)
else if (isturf(loc))
new /obj/structure/gargoyle(loc, src)
/mob/living/carbon/human/proc/gargoyle_pause()
set name = "Gargoyle - Pause"
set category = "Abilities.Gargoyle"
set desc = "Pause your energy while standing still, so you don't use up any more, though you will lose a small amount upon moving again."
if (stat)
return
var/datum/component/gargoyle/comp = GetComponent(/datum/component/gargoyle)
if (comp && !comp.transformed && !comp.paused)
comp.paused = TRUE
comp.paused_loc = loc
comp.RegisterSignal(src, COMSIG_ATOM_ENTERING, /datum/component/gargoyle/proc/unpause)
to_chat(src, span_notice("You start conserving your energy."))
/mob/living/carbon/human/proc/gargoyle_checkenergy()
set name = "Gargoyle - Check Energy"
set category = "Abilities.Gargoyle"
set desc = "Check how much energy you have remaining as a gargoyle."
var/datum/component/gargoyle/comp = GetComponent(/datum/component/gargoyle)
if (comp)
to_chat(src, span_notice("You have [round(comp.energy,0.01)] energy remaining. It is currently [comp.paused ? "stable" : (comp.transformed ? "increasing" : "decreasing")]."))
@@ -0,0 +1,32 @@
/**
Stack End Detector.
Can detect if a given code stack has exited, used by the mc for stack overflow detection.
**/
/datum/stack_end_detector
var/datum/weakref/_WF
var/datum/stack_canary/_canary
/datum/stack_end_detector/New()
_canary = new()
_WF = WEAKREF(_canary)
/** Prime the stack overflow detector.
Store the return value of this proc call in a proc level var.
Can only be called once.
**/
/datum/stack_end_detector/proc/prime_canary()
if (!_canary)
CRASH("Prime_canary called twice")
. = _canary
_canary = null
/// Returns true if the stack is still going. Calling before the canary has been primed also returns true
/datum/stack_end_detector/proc/check()
return !!_WF.resolve()
/// Stack canary. Will go away if the stack it was primed by is ended by byond for return or stack overflow reasons.
/datum/stack_canary
/// empty proc to avoid warnings about unused variables. Call this proc on your canary in the stack it's watching.
/datum/stack_canary/proc/use_variable()
+27
View File
@@ -0,0 +1,27 @@
///like normal callbacks but they also record their creation time for measurement purposes
///they also require the same usr/user that made the callback to both still exist and to still have a client in order to execute
/datum/callback/verb_callback
///the tick this callback datum was created in. used for testing latency
var/creation_time = 0
/datum/callback/verb_callback/New(thingtocall, proctocall, ...)
creation_time = DS2TICKS(world.time)
. = ..()
#ifndef UNIT_TEST
/datum/callback/verb_callback/Invoke(...)
var/mob/our_user = user?.resolve()
if(QDELETED(our_user) || isnull(our_user.client))
return
var/mob/temp = usr
. = ..()
usr = temp
/datum/callback/verb_callback/InvokeAsync(...)
var/mob/our_user = user?.resolve()
if(QDELETED(our_user) || isnull(our_user.client))
return
var/mob/temp = usr
. = ..()
usr = temp
#endif
+11 -12
View File
@@ -153,24 +153,23 @@
data["status"] = status
return data
/datum/wires/tgui_act(action, list/params)
/datum/wires/tgui_act(action, list/params, datum/tgui/ui)
if(..())
return TRUE
var/mob/user = usr
if(!interactable(user))
if(!interactable(ui.user))
return
var/obj/item/I = user.get_active_hand()
var/obj/item/I = ui.user.get_active_hand()
var/color = lowertext(params["wire"])
holder.add_hiddenprint(user)
holder.add_hiddenprint(ui.user)
switch(action)
// Toggles the cut/mend status.
if("cut")
// if(!I.has_tool_quality(TOOL_WIRECUTTER) && !user.can_admin_interact())
if(!istype(I) || !I.has_tool_quality(TOOL_WIRECUTTER))
to_chat(user, span_warning("You need wirecutters!"))
to_chat(ui.user, span_warning("You need wirecutters!"))
return
playsound(holder, I.usesound, 20, 1)
@@ -181,7 +180,7 @@
if("pulse")
// if(!I.has_tool_quality(TOOL_MULTITOOL) && !user.can_admin_interact())
if(!istype(I) || !I.has_tool_quality(TOOL_MULTITOOL))
to_chat(user, span_warning("You need a multitool!"))
to_chat(ui.user, span_warning("You need a multitool!"))
return
playsound(holder, 'sound/weapons/empty.ogg', 20, 1)
@@ -189,7 +188,7 @@
// If they pulse the electrify wire, call interactable() and try to shock them.
if(get_wire(color) == WIRE_ELECTRIFY)
interactable(user)
interactable(ui.user)
return TRUE
@@ -198,18 +197,18 @@
if(is_attached(color))
var/obj/item/O = detach_assembly(color)
if(O)
user.put_in_hands(O)
ui.user.put_in_hands(O)
return TRUE
if(!istype(I, /obj/item/assembly/signaler))
to_chat(user, span_warning("You need a remote signaller!"))
to_chat(ui.user, span_warning("You need a remote signaller!"))
return
if(user.unEquip(I))
if(ui.user.unEquip(I))
attach_assembly(color, I)
return TRUE
else
to_chat(user, span_warning("[I] is stuck to your hand!"))
to_chat(ui.user, span_warning("[I] is stuck to your hand!"))
/**
* Proc called to determine if the user can see wire define information, such as "Contraband", "Door Bolts", etc.