mirror of
https://github.com/CHOMPStation2/CHOMPStation2.git
synced 2026-08-27 23:29:10 +01:00
[MIRROR] Makes the Voodoo doll scrungle people, various recycler fixes. (#11087)
Co-authored-by: eghughguhhhhhh <Hawoogabooga@gmail.com>
This commit is contained in:
co-authored by
eghughguhhhhhh
parent
d1e9a9fbf0
commit
c5988b41fc
@@ -4,7 +4,7 @@
|
||||
|
||||
|
||||
/obj/machinery/maint_recycler //fresh outta 2288 baby
|
||||
name = "Decrepit Machine"
|
||||
name = "\improper Decrepit Machine"
|
||||
|
||||
//icon etc are self contained because it's dumb that they not to begin with.
|
||||
//it's not a MODULE if everything required for it to work is thrown everywhere. grr.
|
||||
@@ -196,7 +196,7 @@
|
||||
if(!door_open)
|
||||
if(O.has_tool_quality(TOOL_CROWBAR))
|
||||
if(stat & (BROKEN|NOPOWER))
|
||||
to_chat(user, span_warning("you lever \The [src]'s door open!"))
|
||||
to_chat(user, span_warning("you lever \the [src]'s door open!"))
|
||||
open_door(user)
|
||||
eject_item(user) //also kick out the item they're looking for
|
||||
playsound(src,"sound/machines/door/airlock_creaking.ogg",4,FALSE)
|
||||
@@ -204,11 +204,11 @@
|
||||
else
|
||||
to_chat(user, span_warning("\The [src]'s door won't budge!"))
|
||||
else
|
||||
to_chat(user, span_warning("\The [src] doesn't have it's door open!"))
|
||||
to_chat(user, span_warning("\The [src] doesn't have its door open!"))
|
||||
return
|
||||
|
||||
if(inserted_item)
|
||||
to_chat(user, span_warning("\The [src] already has [inserted_item] in it's recycling compartment!"))
|
||||
to_chat(user, span_warning("\The [src] already has [inserted_item] in its recycling compartment!"))
|
||||
return
|
||||
|
||||
switch(get_item_whitelist(O))
|
||||
@@ -220,7 +220,7 @@
|
||||
evil_act(O,user)
|
||||
return
|
||||
|
||||
to_chat(user, span_notice("you put \The [O] into \The [src]'s processing compartment!"))
|
||||
to_chat(user, span_notice("You put \the [O] into \the [src]'s processing compartment!"))
|
||||
if(istype(O,/obj/item/holder))
|
||||
var/obj/item/holder/h = O
|
||||
var/mob/m = h.held_mob
|
||||
@@ -250,7 +250,7 @@
|
||||
if(prob(75))
|
||||
if(get_item_whitelist(AM) == RECYCLER_ALLOWED)
|
||||
if(inserted_item == null)
|
||||
visible_message("\The [AM] lands in \the [src].")
|
||||
visible_message("\The [AM] lands in \the [src].",runemessage = "swish")
|
||||
AM.forceMove(src)
|
||||
inserted_item = AM
|
||||
update_icon()
|
||||
@@ -264,7 +264,7 @@
|
||||
|
||||
/obj/machinery/maint_recycler/proc/deny_act(var/obj/item/O,var/mob/user)
|
||||
set_screen_state("screen_deny",10)
|
||||
to_chat(user, span_warning("\The [src] rejects \The [O]!"))
|
||||
to_chat(user, span_warning("\The [src] rejects \the [O]!"))
|
||||
if(prob(99))
|
||||
playsound(src, 'code/modules/maint_recycler/sfx/generaldeny.ogg', 75, 1)
|
||||
return
|
||||
@@ -282,7 +282,7 @@
|
||||
if(!isRepeat) GLOB.global_announcer.autosay("HARM ALERT: Crewmember [user] recorded displaying murderous tendencies towards innocent creatures in [get_area(src)]. Please schedule psych evaluation and ensure the wellbeing of recorded victim: [h.held_mob]", "[src]", "Security")
|
||||
audible_message("[src] states, \"AMORAL INTENT DETECTED.\" ", "\The [src]'s screen briefly flashes to an angry red graphic!" , runemessage = ">:(")
|
||||
else
|
||||
if(!isRepeat) GLOB.global_announcer.autosay("PROPERTY DESTRUCTION ALERT: Crewmember [user] has been recorded attempting to destroy high priority station equipment in [get_area(src)]. Please ensure the integrity of \The [O].", "[src]", "Security")
|
||||
if(!isRepeat) GLOB.global_announcer.autosay("PROPERTY DESTRUCTION ALERT: Crewmember [user] has been recorded attempting to destroy high priority station equipment in [get_area(src)]. Please ensure the integrity of \the [O].", "[src]", "Security")
|
||||
audible_message("[src] states, \"CRIMINAL INTENT DETECTED.\" ", "\The [src]'s screen briefly flashes to an angry red graphic!" , runemessage = ">:(")
|
||||
|
||||
playsound(src,pick(angry_sounds),80)
|
||||
@@ -344,7 +344,7 @@
|
||||
|
||||
/obj/machinery/maint_recycler/proc/eject_item_act(var/mob/user)
|
||||
inserted_item.forceMove(get_turf(src))
|
||||
visible_message(span_warning("[src] ejects \The [inserted_item] from it's recycling chamber!"))
|
||||
visible_message(span_warning("[src] ejects \the [inserted_item] from its recycling chamber!"))
|
||||
inserted_item.throw_at(get_step(src,SOUTH),5,1,src)
|
||||
inserted_item = null;
|
||||
update_icon()
|
||||
@@ -389,7 +389,7 @@
|
||||
//todo, assoc list for icon states from type
|
||||
if(istype(inserted_item,/mob/living/simple_mob/animal/passive/mouse))
|
||||
item_overlay.icon = src.icon
|
||||
item_overlay.icon_state = "hepme" //the creature deserves it's horrible end
|
||||
item_overlay.icon_state = "hepme" //the creature deserves its horrible end
|
||||
|
||||
item_overlay.vis_flags = VIS_INHERIT_ID //gotta reapply
|
||||
item_overlay.appearance_flags = KEEP_TOGETHER | LONG_GLIDE | PASS_MOUSE
|
||||
@@ -474,6 +474,7 @@ TGUI PROCS
|
||||
|
||||
/obj/machinery/maint_recycler/tgui_close(mob/user)
|
||||
. = ..()
|
||||
if(LAZYLEN(open_tguis) > 0) return
|
||||
set_on_state(FALSE)
|
||||
|
||||
|
||||
@@ -484,7 +485,7 @@ UTILITY PROCS
|
||||
/obj/machinery/maint_recycler/proc/credit_user(var/mob/user, var/amount)
|
||||
if(!user || !user.client || !user.client.prefs) return
|
||||
var/currentValue = user.client?.prefs?.read_preference(/datum/preference/numeric/recycler_points)
|
||||
user.client?.prefs?.write_preference_by_type(/datum/preference/numeric/recycler_points, currentValue + amount)
|
||||
user.client?.prefs?.write_preference_by_type(/datum/preference/numeric/recycler_points, min(currentValue + amount,999))
|
||||
if(granted_points[user.key])
|
||||
granted_points[user.key] += amount
|
||||
else
|
||||
@@ -496,13 +497,13 @@ UTILITY PROCS
|
||||
|
||||
/obj/machinery/maint_recycler/proc/canRecycle(var/mob/user, var/potentialValue)
|
||||
if(!user.key) return FALSE
|
||||
if(granted_points[user.key]+potentialValue > point_cap) return FALSE
|
||||
if(granted_points[user.key]+potentialValue > point_cap) return FALSE
|
||||
return TRUE
|
||||
|
||||
/obj/machinery/maint_recycler/proc/mob_consent_check(var/mob/probable_victim)
|
||||
if(probable_victim.key)
|
||||
if(probable_victim.client) //sanity check to make sure they are alright with getting squished to death
|
||||
return (tgui_alert(usr,"Do you want to be put in \The [src]? Industrial machinery is pretty damn deadly, you'll probably die. to death. A fine paste.", "Welcome to the Hydralulic Press Prompt", list("OSHA is for chumps", "what the fuck? get me outta here!")) == "OSHA is for chumps")
|
||||
return (tgui_alert(probable_victim,"Do you want to be put in \The [src]? Industrial machinery is pretty damn deadly, you'll probably die. to death. A fine paste.", "Welcome to the Hydralulic Press Prompt", list("OSHA is for chumps", "what the fuck? get me outta here!")) == "OSHA is for chumps")
|
||||
else return FALSE //no logged out users
|
||||
else return TRUE //mindless mobs that've never felt the gentle touch of a client are fine
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/obj/machinery/maint_vendor
|
||||
name = "Large Decrepit Machine"
|
||||
name = "\improper Large Decrepit Machine"
|
||||
desc = "A long since abandoned \"trash 4 cash\" rewards kiosk. Now featuring a state of the art, monochrome holographic tube display!"
|
||||
icon = 'code/modules/maint_recycler/icons/maint_vendor.dmi'
|
||||
icon_state = "default"
|
||||
@@ -117,7 +117,7 @@
|
||||
|
||||
playsound(src, 'code/modules/maint_recycler/sfx/ejectgoodies.ogg', 75, 1)
|
||||
used_entry.spawn_with_delay(src);
|
||||
audible_message("[src] states, \"[used_entry.tagline]\" ", "\The [src]'s screen briefly flashes an $!" , runemessage = "$$$")
|
||||
audible_message("[src] states, \"[used_entry.tagline]\" ", "\The [src]'s screen briefly flashes a $!" , runemessage = "$$$")
|
||||
if(prob(95))
|
||||
set_screen_state("screen_cashout",10)
|
||||
else
|
||||
@@ -187,6 +187,7 @@
|
||||
|
||||
/obj/machinery/maint_vendor/tgui_close(mob/user)
|
||||
. = ..()
|
||||
if(LAZYLEN(open_tguis) > 0) return
|
||||
set_on_state(FALSE)
|
||||
|
||||
/obj/machinery/maint_vendor/tgui_data(mob/user)
|
||||
@@ -202,7 +203,7 @@
|
||||
"desc" = entry.desc,
|
||||
"ad" = entry.ad_message,
|
||||
"icon" = entry.icon_state,
|
||||
"index" = i //TODO
|
||||
"index" = i
|
||||
))
|
||||
data["items"] = items
|
||||
data["userBalance"] = user_balance(user)
|
||||
|
||||
@@ -21,6 +21,16 @@
|
||||
object_type_to_spawn = /obj/item/stack/material/wood/hard{amount = 20}
|
||||
|
||||
|
||||
/datum/maint_recycler_vendor_entry/cardboard
|
||||
vendor_category = MAINTVENDOR_CONSTRUCTION
|
||||
name = "C.A.R.D.B.O.A.R.D"
|
||||
ad_message = "5 sheets!"
|
||||
desc = "Not an acronym (maybe?), we just asked the person in charge of designating stationbounds to make this listing, we have no idea what it means!"
|
||||
object_type_to_spawn = /obj/item/stack/material/cardboard{amount = 5}
|
||||
item_cost = 10 //not too pricy
|
||||
per_person_cap = 1
|
||||
per_round_cap = 3 //limited supply!
|
||||
|
||||
/datum/maint_recycler_vendor_entry/DIY_Steel
|
||||
vendor_category = MAINTVENDOR_CONSTRUCTION
|
||||
name = "steel!"
|
||||
|
||||
@@ -21,6 +21,7 @@
|
||||
tagline = "I HAVE 8.2 PETABYTES OF MECHHAMMER MODELS!"
|
||||
item_cost = 50 //even discount bin warhammer's comically expensive
|
||||
object_type_to_spawn = /obj/random/fromList/mecha_toys
|
||||
icon_state = "copyright"
|
||||
|
||||
/datum/maint_recycler_vendor_entry/burger //packaged 40 years ago. you should regret this.
|
||||
name = "TRASH 4 BURGER REDEMPTION"
|
||||
|
||||
@@ -104,7 +104,7 @@
|
||||
/datum/maint_recycler_vendor_entry/NIF_laws
|
||||
name = "COMM4ND UR N1F!"
|
||||
ad_message = "KNEEL!"
|
||||
icon_state = "law"
|
||||
icon_state = "laws"
|
||||
desc = "Unlocks the TRUE potential of your NIF! You set laws, you follow laws! Simple as! (we are not liable for usage on other parties)"
|
||||
object_type_to_spawn = /obj/item/disk/nifsoft/compliance
|
||||
tagline = "You didn't get it from us!"
|
||||
@@ -113,7 +113,7 @@
|
||||
/datum/maint_recycler_vendor_entry/NIFlet_laws
|
||||
name = "Implnt law?"
|
||||
ad_message = "Niflets seething!"
|
||||
icon_state = "law"
|
||||
icon_state = "laws"
|
||||
desc = "Underlings not listening to you? Someone forgetting to do whta you tell them to? No more! this implant WILL make people bend to your will! KNEEL!"
|
||||
object_type_to_spawn = /obj/item/implanter/compliance
|
||||
item_cost = 25
|
||||
|
||||
@@ -10,18 +10,6 @@
|
||||
required_access = list(access_security)
|
||||
vendor_category = MAINTVENDOR_WEAPONS
|
||||
|
||||
/datum/maint_recycler_vendor_entry/foamforce_ammo //fun!
|
||||
name = "MUNITIONS FOR GUN"
|
||||
ad_message = "FOAM FLINGING PAIN!"
|
||||
desc = "BIG BOX? BIG AMMO. THAT'S RIGHT. WE'LL BIG YOUR AMMO. FOAM DARTS, FOR FOAM DART GUNS - LIMITED EDITION FRAG MONTAGE BUY NOW"
|
||||
object_type_to_spawn = /obj/item/toy/russian_revolver/trick_revolver
|
||||
item_cost = 15 //cheap!
|
||||
tagline = "to war!"
|
||||
per_person_cap = 1
|
||||
per_round_cap = 3 //limited supply!
|
||||
required_access = list(access_security)
|
||||
vendor_category = MAINTVENDOR_WEAPONS
|
||||
|
||||
/datum/maint_recycler_vendor_entry/foamforce_ammo //fun!
|
||||
name = "MUNITIONS FOR GUN"
|
||||
ad_message = "FOAM FLINGING PAIN!"
|
||||
|
||||
+19
@@ -0,0 +1,19 @@
|
||||
//todo, figure out a better place for this
|
||||
/proc/get_humanoid_displacement_map_image(var/mob/living/carbon/human/target,var/list/discarded_layer_indicies, var/icon/displacement_map, var/outlineWidth = 0, var/render_target = null)
|
||||
|
||||
var/list/to_overlays = target.overlays_standing.Copy()
|
||||
|
||||
for(var/layer_to_kill in discarded_layer_indicies)
|
||||
to_overlays[layer_to_kill] = null
|
||||
|
||||
var/image/displacement_render_image = image(icon = null, icon_state = "empty", dir = SOUTH)
|
||||
displacement_render_image.appearance_flags = KEEP_TOGETHER
|
||||
displacement_render_image.overlays = to_overlays
|
||||
|
||||
displacement_render_image.filters += filter(type = "displace", size = 128, icon=displacement_map) //size is 128 because that's the god given standard. if you're doing something unhinged enough to need a bigger or smaller size, by all means.
|
||||
if(outlineWidth)
|
||||
displacement_render_image.filters += filter(type="outline", size = outlineWidth)
|
||||
if(render_target)
|
||||
displacement_render_image.render_target = render_target
|
||||
|
||||
return displacement_render_image
|
||||
+72
-76
@@ -1,6 +1,13 @@
|
||||
//remote stuff! like uhhhh
|
||||
// the funny stickers
|
||||
// the funny voodoo doll
|
||||
/*
|
||||
Remote scene tools! These, in effects, serve 2 purposes:
|
||||
|
||||
* Forward emotes from wearer of one to wearer of its partner
|
||||
* Provide simple feedback - is your partner dead, SSD, did they log out? - some are more explicit.
|
||||
|
||||
why aren't these accessories?
|
||||
They easily could be! I'm just lazy and don't wanna forward the "see emote" from wearables to all the accessories
|
||||
|
||||
*/
|
||||
|
||||
|
||||
/obj/item/remote_scene_tool
|
||||
@@ -12,11 +19,15 @@
|
||||
icon_state = "sticker_inactive"
|
||||
name = "Bluespace Sticker"
|
||||
desc = "A stretchable, flexible sticker that induces a quasi-stable 4th dimensional bluespace buzzword rift, enabling moderate levels of touch between the two."
|
||||
description_info = "These stickers act as remote scene tools - any sort of emotes or subtles that the wearer does will go DIRECTLY to the other sticker! It's vauge, so use it how you want in RP! Just remember bystander consent!"
|
||||
description_info = "These stickers act as remote scene tools - any sort of emotes or subtles that the wearer does will go DIRECTLY to the other sticker! It's vague, so use it how you want in RP! Just remember bystander consent!"
|
||||
slot_flags = (SLOT_OCLOTHING | SLOT_ICLOTHING | SLOT_GLOVES | SLOT_MASK | SLOT_HEAD | SLOT_FEET | SLOT_ID | SLOT_BELT | SLOT_BACK | SLOT_POCKET)
|
||||
|
||||
w_class = ITEMSIZE_SMALL
|
||||
var/mob/worn_mob = null
|
||||
var/last_loc
|
||||
var/can_summon = TRUE
|
||||
var/can_replace = TRUE
|
||||
|
||||
var/replacementType = /obj/item/remote_scene_tool
|
||||
|
||||
/obj/item/remote_scene_tool/proc/link_to(var/obj/item/remote_scene_tool/to_link)
|
||||
//link to a remote scene tool
|
||||
@@ -37,43 +48,43 @@
|
||||
|
||||
RegisterSignal(mob, COMSIG_MOB_LOGIN, PROC_REF(worn_mob_logged_in))
|
||||
RegisterSignal(mob, COMSIG_MOB_LOGOUT, PROC_REF(worn_mob_logged_out))
|
||||
transmit_emote(src, span_notice("The [src]\'s has been put on by [mob]!"))
|
||||
|
||||
|
||||
transmit_emote(src, span_notice("\The [src] has been put on by [mob]!"))
|
||||
|
||||
/obj/item/remote_scene_tool/proc/unregister_from_mob(var/mob)
|
||||
if(worn_mob == null) return
|
||||
UnregisterSignal(worn_mob, COMSIG_MOB_LOGIN)
|
||||
UnregisterSignal(worn_mob, COMSIG_MOB_LOGOUT)
|
||||
worn_mob = null
|
||||
transmit_emote(src, span_warning("The [src]\'s wearer has removed it!"))
|
||||
transmit_emote(src, span_warning("\The [src]'s wearer has removed it!"))
|
||||
|
||||
|
||||
//called when the mob wearing this item logs out
|
||||
/obj/item/remote_scene_tool/proc/worn_mob_logged_out()
|
||||
SIGNAL_HANDLER
|
||||
if(!linked)
|
||||
return
|
||||
transmit_emote(src, span_warning("The [src]\'s wearer has gone SSD!"))
|
||||
transmit_emote(src, span_warning("\The [src]'s wearer has gone SSD!"))
|
||||
linked?.linked_updated()
|
||||
|
||||
//called when the mob wearing this item logs out
|
||||
|
||||
/obj/item/remote_scene_tool/proc/worn_mob_logged_in()
|
||||
SIGNAL_HANDLER
|
||||
//called when the mob wearing this item logs in
|
||||
if(!linked)
|
||||
return
|
||||
transmit_emote(src, "The [src]\'s wearer has returned from SSD!")
|
||||
transmit_emote(src, "\The [src]'s wearer has returned from SSD!")
|
||||
linked?.linked_updated()
|
||||
|
||||
/obj/item/remote_scene_tool/see_emote(var/mob/M as mob, var/text, var/emote_type)
|
||||
//to_world_log("emote: [text] from [M] to [linked]")
|
||||
if(M == loc)
|
||||
if(M == getWearer())
|
||||
//we're the one doing the emote
|
||||
transmit_emote(src, text,emote_type)
|
||||
|
||||
/obj/item/remote_scene_tool/proc/transmit_emote(var/mob/M as mob, var/text, var/emote_type)
|
||||
if(ismob(linked.loc))
|
||||
var/mob/m = linked.loc
|
||||
if(linked == null) return
|
||||
if(ismob(linked.getWearer()))
|
||||
var/mob/m = linked.getWearer()
|
||||
if(!m.client) return;
|
||||
to_chat(linked.loc, icon2html(src,m.client) + text)
|
||||
|
||||
@@ -87,9 +98,10 @@
|
||||
return FALSE
|
||||
if(linked.linked != src)
|
||||
return FALSE
|
||||
if(!ismob(linked.loc))
|
||||
|
||||
var/mob/m = linked.getWearer()
|
||||
if(!ismob(m))
|
||||
return FALSE
|
||||
var/mob/m = linked.loc
|
||||
if(!m.client) //no scene partner? whoopsie!
|
||||
return FALSE
|
||||
|
||||
@@ -104,18 +116,21 @@
|
||||
/obj/item/remote_scene_tool/proc/delayed_loc_check()
|
||||
//why is this delayed? because when moving stuff between slots, it considers it in a different spot, and calls the commsig multiple times - so the end
|
||||
//user just gets the shit spammed out of them
|
||||
|
||||
if(last_loc == loc)
|
||||
return
|
||||
last_loc = loc
|
||||
linked?.linked_updated()
|
||||
linked_updated()
|
||||
|
||||
if(ismob(loc))
|
||||
register_to_mob(loc) //handles any caching
|
||||
var/mob/m = getWearer()
|
||||
|
||||
|
||||
if(ismob(m))
|
||||
register_to_mob(m) //handles any caching
|
||||
else
|
||||
if(worn_mob)
|
||||
unregister_from_mob(worn_mob) //unregister from the mob if we aren't on it anymore
|
||||
|
||||
/obj/item/remote_scene_tool/proc/linked_updated()
|
||||
update_icon()
|
||||
|
||||
@@ -136,13 +151,18 @@
|
||||
|
||||
/obj/item/remote_scene_tool/examine(mob/user)
|
||||
. = ..()
|
||||
if(linked && ismob(linked.loc))
|
||||
. += span_notice("This is linked to [linked.loc]\'s [linked.name].")
|
||||
var/mob/m = linked.loc
|
||||
if(!m.client)
|
||||
. += span_warning("The wearer of \The [src]'s counterpart doesn't appear to be all there!")
|
||||
var/mob/living/carbon/human/lw = linked?.getWearer()
|
||||
|
||||
if(lw)
|
||||
. += span_notice("This is linked to [lw]'s [linked.name].")
|
||||
if(!lw.client || lw.stat == UNCONSCIOUS || lw.stat == DEAD)
|
||||
. += span_warning("The wearer of \the [src]'s counterpart doesn't appear to be conscious!")
|
||||
else
|
||||
. += span_notice("Its counterpart seems to be in \the [get_area(linked).name]")
|
||||
|
||||
if(!linked)
|
||||
. += span_warning("This is not linked to anything!")
|
||||
|
||||
if(!ismob(linked.loc))
|
||||
. += span_warning("\The [src]'s counterpart isn't being worn or carried by anyone!")
|
||||
|
||||
@@ -168,56 +188,32 @@
|
||||
contents += RST2
|
||||
calibrate_size()
|
||||
|
||||
/obj/item/remote_scene_tool/voodoo_doll
|
||||
name = "voodoo doll"
|
||||
desc = "A dubiously-cursed-esq Voodoo doll that mimics whoever is wearing it's matching necklace via built in hardlight projection."
|
||||
icon = 'code/modules/maint_recycler/icons/goodies/remote_scene_tools.dmi'
|
||||
icon_state = "voodoo_doll_inactive"
|
||||
icon_root = "voodoo_doll"
|
||||
description_info = "The Doll acts as a remote scene tool - any sort of emotes or subtles that the wearer does will go DIRECTLY to the necklace! It's vauge, so use it how you want in RP! Just remember bystander consent!"
|
||||
//this is just a copy of the remote scene tool, but with a different icon
|
||||
//and a different name
|
||||
/obj/item/remote_scene_tool/proc/getWearer()
|
||||
if(ismob(loc))
|
||||
return loc
|
||||
if(istype(loc,/obj/item/clothing))
|
||||
if(ismob(loc.loc))
|
||||
return loc.loc
|
||||
return null
|
||||
|
||||
var/last_loc_update = null
|
||||
/obj/item/remote_scene_tool/verb/summon_counterpart()
|
||||
set name = "Summon Counterpart"
|
||||
set desc = "Forcibly moves the linked object over to you - or, if it doesn't exist, spawn a new one."
|
||||
if(can_summon || (linked == null && can_replace))
|
||||
if(linked == null)
|
||||
create_counterpart()
|
||||
to_chat(usr,span_notice("\The [src] forms a new [linked]!"))
|
||||
else
|
||||
var/mob/counterpart = linked.getWearer()
|
||||
if(counterpart)
|
||||
counterpart.remove_from_mob(linked,get_turf(src))
|
||||
else
|
||||
linked.forceMove(get_turf(src))
|
||||
to_chat(usr,span_notice("\The [linked] materializes in front of you!"))
|
||||
else
|
||||
to_chat(usr,span_notice("Nothing seems to happen!"))
|
||||
|
||||
/obj/item/remote_scene_tool/voodoo_doll/update_icon()
|
||||
. = ..()
|
||||
|
||||
last_loc_update = linked.loc
|
||||
|
||||
overlays.Cut()
|
||||
|
||||
dir = SOUTH
|
||||
src.alpha = 255
|
||||
|
||||
name = initial(name)
|
||||
desc = initial(desc)
|
||||
|
||||
if(!linked)
|
||||
return
|
||||
if(!ismob(linked.loc))
|
||||
return
|
||||
if(!ismob(loc)) //only show the person's icon if we're holding it. makes "found in the hall" interactions less weird
|
||||
return
|
||||
|
||||
var/mob/M = linked.loc
|
||||
if(ismob(M))
|
||||
src.alpha = 190 //make it a bit transparent so it doesn't look like a mob holder.
|
||||
name = "Voodoo doll of " + M.name
|
||||
desc = "A small, marketable doll that looks suspiciously like [M]... "
|
||||
overlays |= M.overlays
|
||||
|
||||
/obj/item/remote_scene_tool/voodoo_necklace
|
||||
name = "Gem-Encruseted Necklace"
|
||||
desc = "A bitingly cold metal necklace with a swirling gem in the center. haters will say it's not magical"
|
||||
icon_state = "necklace_inactive"
|
||||
icon_root = "necklace"
|
||||
slot_flags = SLOT_MASK
|
||||
description_info = "The necklace and the associated doll act as remote scene tools - any sort of emotes or subtles that the wearer does will go DIRECTLY to the other! It's vauge, so use it how you want in RP! Just remember bystander consent!"
|
||||
|
||||
/obj/item/storage/box/remote_scene_tools/voodoo
|
||||
icon_state = "voodoobox"
|
||||
name = "Voodoo Supplies Box"
|
||||
desc = "a horribly dusty box from 'magici-corp' with a ludicrously corny image of a voodoo doll on the front. marketed as part of a DIY magician routine, they stopped making them after someone broke their nose when the doll was dropped."
|
||||
primary = /obj/item/remote_scene_tool/voodoo_doll
|
||||
secondary = /obj/item/remote_scene_tool/voodoo_necklace
|
||||
/obj/item/remote_scene_tool/proc/create_counterpart()
|
||||
var/obj/item/remote_scene_tool/newrst = new replacementType(get_turf(src))
|
||||
link_to(newrst)
|
||||
newrst.link_to(src)
|
||||
@@ -0,0 +1,183 @@
|
||||
#define DATA_SCALE "scale"
|
||||
#define DATA_X_OFFSET "x"
|
||||
#define DATA_Y_OFFSET "y"
|
||||
#define DATA_ROTATION "rotation"
|
||||
|
||||
/obj/item/remote_scene_tool/voodoo_doll
|
||||
name = "voodoo doll"
|
||||
desc = "A dubiously cursed-esq Voodoo doll that mimics whoever is wearing its matching necklace via built in hardlight projection."
|
||||
icon = 'code/modules/maint_recycler/icons/goodies/remote_scene_tools.dmi'
|
||||
icon_state = "voodoo_doll_inactive"
|
||||
icon_root = "voodoo_doll"
|
||||
description_info = "The Doll acts as a remote scene tool - any sort of emotes or subtles that the wearer does will go DIRECTLY to the necklace! It's vague, so use it how you want in RP! Just remember bystander consent!"
|
||||
|
||||
replacementType = /obj/item/remote_scene_tool/voodoo_necklace
|
||||
|
||||
//this is just a copy of the remote scene tool, but with a different icon
|
||||
//and a different name
|
||||
|
||||
var/underlayRotation = 45
|
||||
//TODO: make this generic so it's easier for other stuff to use. ideally there's a magical thing that just has all the various greebles set up so u can pick and choose which ones are rendered traditionally
|
||||
var/list/tail_data = list( DATA_X_OFFSET = 2, DATA_Y_OFFSET = -2,DATA_SCALE = 1.6, DATA_ROTATION = 45)
|
||||
var/list/taur_data = list( DATA_X_OFFSET = 2, DATA_Y_OFFSET = 2, DATA_SCALE = 1.1, DATA_ROTATION = 45)
|
||||
var/list/wing_data = list( DATA_X_OFFSET = 2, DATA_Y_OFFSET = -2,DATA_SCALE = 1, DATA_ROTATION = 45)
|
||||
var/list/ear_data = list( DATA_X_OFFSET = 0, DATA_Y_OFFSET = 1, DATA_SCALE = 1.5, DATA_ROTATION = 45)
|
||||
var/list/hat_data = list( DATA_X_OFFSET = 0, DATA_Y_OFFSET = 3, DATA_SCALE = 1, DATA_ROTATION = 45)
|
||||
var/outline_size = 1
|
||||
|
||||
var/list/discarded_layer_indicies = list(
|
||||
VORE_BELLY_LAYER, //not even gonna try with this lmfao
|
||||
TAIL_LOWER_LAYER,
|
||||
TAIL_UPPER_LAYER,
|
||||
TAIL_UPPER_LAYER_LOW,
|
||||
TAIL_UPPER_LAYER_HIGH, //drawn manually
|
||||
FIRE_LAYER, //not relevant
|
||||
TARGETED_LAYER, //not relevant
|
||||
MOB_WATER_LAYER, //not relevant
|
||||
L_HAND_LAYER, //not drawn, looks like ass
|
||||
R_HAND_LAYER,
|
||||
EARS_LAYER, //drawn manually
|
||||
WING_LAYER,
|
||||
WING_LOWER_LAYER, //drawn manually
|
||||
HEAD_LAYER, //drawn manually
|
||||
)
|
||||
appearance_flags = KEEP_TOGETHER
|
||||
var/no_fun_mode = FALSE //if true, we just draw the mob as an overlay
|
||||
|
||||
/obj/item/remote_scene_tool/voodoo_necklace
|
||||
name = "Gem-Encrusted Necklace"
|
||||
desc = "A bitingly cold metal necklace with a swirling gem in the center. Haters will say it's not magical"
|
||||
icon_state = "necklace_inactive"
|
||||
icon_root = "necklace"
|
||||
slot_flags = SLOT_MASK
|
||||
description_info = "The necklace and the associated doll act as remote scene tools - any sort of emotes or subtles that the wearer does will go DIRECTLY to the other! It's vague, so use it how you want in RP! Just remember bystander consent!"
|
||||
replacementType = /obj/item/remote_scene_tool/voodoo_doll
|
||||
|
||||
/obj/item/storage/box/remote_scene_tools/voodoo
|
||||
icon_state = "voodoobox"
|
||||
name = "Voodoo Supplies Box"
|
||||
desc = "a horribly dusty box from 'magici-corp' with a ludicrously corny image of a voodoo doll on the front."
|
||||
description_fluff = "originally marketed as part of a DIY magician routine, the company making them went under due to countless lawsuits from people who broke their nose upon the doll being dropped, and tesh filing descrimination suits. they haven't been made in well over a decade."
|
||||
primary =/obj/item/remote_scene_tool/voodoo_doll
|
||||
secondary =/obj/item/remote_scene_tool/voodoo_necklace
|
||||
|
||||
/obj/item/remote_scene_tool/voodoo_doll/verb/toggle_fun_mode()
|
||||
set name = "Disable Special Rendering"
|
||||
set desc = "Disables the displacement-based rendering on the doll, leaving it as just a doll at all times."
|
||||
no_fun_mode = !no_fun_mode
|
||||
to_chat(usr,span_notice("you turn the dial on the back of \the [src], and turn the advanced projection matrix [no_fun_mode ? "off" : "on"]"))
|
||||
update_icon() //force a refresh
|
||||
|
||||
|
||||
/obj/item/remote_scene_tool/voodoo_doll/Move(atom/newloc, direct, movetime)
|
||||
. = ..()
|
||||
dir = SOUTH //we need to do this
|
||||
|
||||
/obj/item/remote_scene_tool/voodoo_doll/proc/get_outline_color(var/r,var/g,var/b,var/a, var/offset = 30)
|
||||
var/new_rgba = rgb(r-offset,g-offset,b-offset,a)
|
||||
return new_rgba
|
||||
|
||||
/obj/item/remote_scene_tool/voodoo_doll/proc/generate_layer_matrix(var/list/data)
|
||||
var/matrix/output = matrix()
|
||||
output.Translate(data[DATA_X_OFFSET], data[DATA_Y_OFFSET])
|
||||
output.Turn(data[DATA_ROTATION])
|
||||
output.Scale(data[DATA_SCALE], data[DATA_SCALE])
|
||||
return output
|
||||
|
||||
/obj/item/remote_scene_tool/voodoo_doll/proc/generate_layer_image(var/image/input, var/matrix/newtransform, var/outline_width = 0, var/outline_color = rgb(50,50,50))
|
||||
if(input == null)
|
||||
return null
|
||||
|
||||
input.dir = SOUTH
|
||||
input.transform = newtransform
|
||||
input.layer = FLOAT_LAYER
|
||||
if(outline_width > 0)
|
||||
input.filters += filter(type="outline", size = outline_width, color = outline_color)
|
||||
|
||||
return input
|
||||
|
||||
/obj/item/remote_scene_tool/voodoo_doll/update_icon()
|
||||
. = ..()
|
||||
//reset
|
||||
overlays?.Cut()
|
||||
underlays?.Cut()
|
||||
filters = null
|
||||
dir = SOUTH
|
||||
name = initial(name)
|
||||
desc = initial(desc)
|
||||
var/matrix/rotateMatrix = matrix()
|
||||
transform = rotateMatrix
|
||||
|
||||
if(!linked)
|
||||
return
|
||||
|
||||
var/mob/owner = linked.getWearer()
|
||||
if(!owner) return;
|
||||
|
||||
name = "Voodoo doll of " + owner.name
|
||||
desc = "A small, marketable doll that looks suspiciously like [owner]... "
|
||||
|
||||
|
||||
if(istype(owner,/mob/living/carbon/human/teshari)) return //no flesh horror, sorry
|
||||
|
||||
if(!ismob(loc) && !ismob(loc.loc)) return //only render the funny when we're on a humie
|
||||
|
||||
if(no_fun_mode) return //no fun allowed
|
||||
|
||||
if(ishuman(owner)) //TODO, refactor the fuck out of this once I port the tgui filter manager stuff over.
|
||||
var/mob/living/carbon/human/buddy = owner
|
||||
var/is_tail_taur = istaurtail(buddy.tail_style)
|
||||
var/icon/displacement_map = icon(src.icon,is_tail_taur ? "taurdisplacement" : "displacement",SOUTH)
|
||||
var/image/displacement_rendered = get_humanoid_displacement_map_image(buddy,discarded_layer_indicies,displacement_map,2,null)
|
||||
|
||||
//tails need special attention because taurs
|
||||
var/tailoutlinecolor = rgb(50,50,50) //default to a grey, otherwise we use a darker version of one of the tail colors
|
||||
if(buddy.tail_style?.do_colouration)
|
||||
tailoutlinecolor = get_outline_color(buddy.r_tail,buddy.g_tail,buddy.b_tail,buddy.a_tail)
|
||||
|
||||
var/image/tail_image = buddy.get_tail_image()
|
||||
if(is_tail_taur)
|
||||
tail_image = generate_layer_image(buddy.get_tail_image(),generate_layer_matrix(taur_data),outline_size,tailoutlinecolor)
|
||||
tail_image.filters += filter(type="alpha", flags = MASK_INVERSE)
|
||||
else
|
||||
tail_image = generate_layer_image(buddy.get_tail_image(),generate_layer_matrix(tail_data),outline_size,tailoutlinecolor)
|
||||
|
||||
//same kind of scenario for wings
|
||||
var/wingoutlinecolor = rgb(50,50,50)
|
||||
if(buddy.wing_style?.do_colouration)
|
||||
wingoutlinecolor = get_outline_color(buddy.r_wing,buddy.g_wing,buddy.b_wing,buddy.a_wing)
|
||||
var/image/wing_image = generate_layer_image(buddy.get_wing_image(FALSE),generate_layer_matrix(wing_data),outline_size,wingoutlinecolor)
|
||||
var/image/under_wing_image = generate_layer_image(buddy.get_wing_image(TRUE),generate_layer_matrix(wing_data),outline_size,wingoutlinecolor)
|
||||
|
||||
//the rest are pretty simple
|
||||
var/ear_icon = buddy.get_ears_overlay()
|
||||
var/image/ear_image = generate_layer_image(image(icon = ear_icon),generate_layer_matrix(ear_data))
|
||||
|
||||
//hat
|
||||
var/hat_icon = buddy.head?.make_worn_icon(body_type = buddy.species.get_bodytype(src), slot_name = slot_head_str, default_icon = INV_HEAD_DEF_ICON, default_layer = HEAD_LAYER)
|
||||
var/image/hat_image = generate_layer_image(image(icon = hat_icon),generate_layer_matrix(hat_data))
|
||||
|
||||
|
||||
|
||||
//add them all
|
||||
overlays |= displacement_rendered
|
||||
overlays += ear_image
|
||||
overlays += hat_image
|
||||
|
||||
if(!is_tail_taur)
|
||||
underlays += tail_image
|
||||
else
|
||||
overlays += tail_image
|
||||
|
||||
underlays |= wing_image
|
||||
underlays |= under_wing_image
|
||||
|
||||
//filtering time
|
||||
|
||||
rotateMatrix.Turn(2) //very slight blur. this is unironically the best way to do it, any of the blur filters are just way too strong at a minimum value.
|
||||
transform = rotateMatrix
|
||||
|
||||
#undef DATA_X_OFFSET
|
||||
#undef DATA_Y_OFFSET
|
||||
#undef DATA_SCALE
|
||||
#undef DATA_ROTATION
|
||||
Binary file not shown.
|
Before Width: | Height: | Size: 4.2 KiB After Width: | Height: | Size: 4.9 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 235 B |
+3
-1
@@ -3057,8 +3057,10 @@
|
||||
#include "code\modules\maint_recycler\code\vendor_datums\entries\misc_entries.dm"
|
||||
#include "code\modules\maint_recycler\code\vendor_datums\entries\scene_tools.dm"
|
||||
#include "code\modules\maint_recycler\code\vendor_datums\entries\weapons_and_arms.dm"
|
||||
#include "code\modules\maint_recycler\code\vendor_goodies\remote_scene_tools.dm"
|
||||
#include "code\modules\maint_recycler\code\vendor_goodies\vendor_goodies.dm"
|
||||
#include "code\modules\maint_recycler\code\vendor_goodies\remote_scene_tools\displacement_map_generation.dm"
|
||||
#include "code\modules\maint_recycler\code\vendor_goodies\remote_scene_tools\remote_scene_tools.dm"
|
||||
#include "code\modules\maint_recycler\code\vendor_goodies\remote_scene_tools\voodoo.dm"
|
||||
#include "code\modules\makeup\nailpolish.dm"
|
||||
#include "code\modules\maps\merge_conflicts.dm"
|
||||
#include "code\modules\maps\bapi-dmm\bapi_bindings.dm"
|
||||
|
||||
Reference in New Issue
Block a user