diff --git a/code/game/gamemodes/shadowling/shadowling.dm b/code/game/gamemodes/shadowling/shadowling.dm
index acb36b6e0be..6409717d278 100644
--- a/code/game/gamemodes/shadowling/shadowling.dm
+++ b/code/game/gamemodes/shadowling/shadowling.dm
@@ -1,6 +1,7 @@
#define LIGHT_DAM_THRESHOLD 4
#define LIGHT_HEAL_THRESHOLD 2
#define LIGHT_DAMAGE_TAKEN 7
+
/*
SHADOWLING: A gamemode based on previously-run events
@@ -14,7 +15,7 @@ The game will end under two conditions:
Shadowling strengths:
- The dark
- - Hard vacuum (They are not affected by it)
+ - Hard vacuum (They are not affected by it, but are affected by starlight!)
- Their thralls who are not harmed by the light
- Stealth
@@ -22,8 +23,7 @@ Shadowling weaknesses:
- The light
- Fire
- Enemy numbers
- - Lasers (Lasers are concentrated light and do more damage)
- - Flashbangs (High stun and high burn damage; if the light stuns humans, you bet your ass it'll hurt the shadowling very much!)
+ - Burn-based weapons and items (flashbangs, lasers, etc.)
Shadowlings start off disguised as normal crew members, and they only have two abilities: Hatch and Enthrall.
They can still enthrall and perhaps complete their objectives in this form.
@@ -76,7 +76,7 @@ Made by Xhuis
/datum/game_mode/shadowling/announce()
world << "The current game mode is - Shadowling!"
- world << "There are alien shadowlings on the station. Crew: Kill the shadowlings before they can eat or enthrall the crew. Shadowlings: Enthrall the crew while remaining in hiding."
+ world << "There are alien shadowlings on the station. Crew: Kill the shadowlings before they can enthrall the crew. Shadowlings: Enthrall the crew while remaining in hiding."
/datum/game_mode/shadowling/pre_setup()
if(config.protect_roles_from_antagonist)
@@ -104,7 +104,7 @@ Made by Xhuis
log_game("[shadow.key] (ckey) has been selected as a Shadowling.")
sleep(10)
shadow.current << "
"
- shadow.current << "You are a shadowling!"
+ shadow.current << "You are a shadowling!"
greet_shadow(shadow)
finalize_shadowling(shadow)
process_shadow_objectives(shadow)
@@ -113,7 +113,7 @@ Made by Xhuis
return
/datum/game_mode/proc/greet_shadow(datum/mind/shadow)
- shadow.current << "Currently, you are disguised as an employee aboard [world.name]."
+ shadow.current << "Currently, you are disguised as an employee aboard [station_name()]]."
shadow.current << "In your limited state, you have three abilities: Enthrall, Hatch, and Hivemind Commune."
shadow.current << "Any other shadowlings are you allies. You must assist them as they shall assist you."
shadow.current << "If you are new to shadowling, or want to read about abilities, check the wiki page at https://tgstation13.org/wiki/Shadowling
"
@@ -232,7 +232,7 @@ Made by Xhuis
id = "shadowling"
say_mod = "chitters"
specflags = list(NOBREATH,NOBLOOD,RADIMMUNE,NOGUNS) //Can't use guns due to muzzle flash
- burnmod = 1.5 //1.5x burn damage, 2x is excessive
+ burnmod = 1.5 //1.5x burn damage, 2x is excessive
heatmod = 1.5
/datum/species/shadow/ling/spec_life(mob/living/carbon/human/H)
@@ -254,6 +254,29 @@ Made by Xhuis
H.SetWeakened(0)
H.SetStunned(0)
+/datum/species/shadow/ling/lesser //Empowered thralls. Obvious, but powerful
+ name = "Lesser Shadowling"
+ id = "l_shadowling"
+ say_mod = "chitters"
+ specflags = list(NOBREATH,NOBLOOD,RADIMMUNE)
+ burnmod = 1.1
+ heatmod = 1.1
+
+/datum/species/shadow/ling/lesser/spec_life(mob/living/carbon/human/H)
+ if(!H.weakeyes) H.weakeyes = 1
+ var/light_amount = 0
+ H.nutrition = NUTRITION_LEVEL_WELL_FED //i aint never get hongry
+ if(isturf(H.loc))
+ var/turf/T = H.loc
+ light_amount = T.get_lumcount()
+ if(light_amount > LIGHT_DAM_THRESHOLD && !H.incorporeal_move)
+ H.take_overall_damage(0, LIGHT_DAMAGE_TAKEN/2)
+ else if (light_amount < LIGHT_HEAL_THRESHOLD)
+ H.heal_overall_damage(2,2)
+ H.adjustToxLoss(-5)
+ H.adjustBrainLoss(-25)
+ H.adjustCloneLoss(-1)
+
/datum/game_mode/proc/update_shadow_icons_added(datum/mind/shadow_mind)
var/datum/atom_hud/antag/shadow_hud = huds[ANTAG_HUD_SHADOW]
shadow_hud.join_hud(shadow_mind.current)
diff --git a/code/game/gamemodes/shadowling/shadowling_abilities.dm b/code/game/gamemodes/shadowling/shadowling_abilities.dm
index 9a8b8ab9482..eb0a55a9ee9 100644
--- a/code/game/gamemodes/shadowling/shadowling_abilities.dm
+++ b/code/game/gamemodes/shadowling/shadowling_abilities.dm
@@ -1,6 +1,9 @@
+#define EMPOWERED_THRALL_LIMIT 5
+
/obj/effect/proc_holder/spell/proc/shadowling_check(var/mob/living/carbon/human/H)
if(!H || !istype(H)) return
if(H.dna.species.id == "shadowling" && is_shadow(H)) return 1
+ if(H.dna.species.id == "l_shadowling" && is_thrall(H)) return 1
if(!is_shadow_or_thrall(usr)) usr << "You can't wrap your head around how to do this."
else if(is_thrall(usr)) usr << "You aren't powerful enough to do this."
else if(is_shadow(usr)) usr << "Your telepathic ability is suppressed. Hatch or regenerate first."
@@ -171,7 +174,7 @@
/obj/effect/proc_holder/spell/targeted/enthrall/cast(list/targets)
var/mob/living/carbon/human/user = usr
listclearnulls(ticker.mode.thralls)
- if(!shadowling_check(usr)) return
+ if(!(usr.mind in ticker.mode.shadows)) return
if(user.dna.species.id != "shadowling")
if(ticker.mode.thralls.len >= 5)
user << "With your telepathic abilities suppressed, your human form will not allow you to enthrall any others. Hatch first."
@@ -229,7 +232,7 @@
for(var/obj/item/weapon/implant/loyalty/L in target)
if(L && L.implanted)
qdel(L)
- target << "Your unwavering loyalty to Nanotrasen unexpectedly falters, dims, dies. You feel a sense of liberation which is quickly stifled by terror."
+ target << "Your unwavering loyalty to Nanotrasen unexpectedly falters, dims, dies."
if(3)
usr << "You begin rearranging [target]'s memories."
usr.visible_message("[usr]'s eyes flare brightly.")
@@ -511,46 +514,96 @@ datum/reagent/shadowling_blindness_smoke //Reagent used for above spell
/obj/effect/proc_holder/spell/targeted/revive_thrall //Completely revives a dead thrall
name = "Black Recuperation"
- desc = "Brings a dead thrall back to life."
+ desc = "Revives or empowers a thrall."
panel = "Shadowling Abilities"
range = 1
- charge_max = 3000
+ charge_max = 600
clothes_req = 0
include_user = 0
action_icon_state = "revive_thrall"
- var/list/thralls_in_world = list()
/obj/effect/proc_holder/spell/targeted/revive_thrall/cast(list/targets)
if(!shadowling_check(usr))
charge_counter = charge_max
return
for(var/mob/living/carbon/human/thrallToRevive in targets)
- if(!is_thrall(thrallToRevive))
- usr << "[thrallToRevive] is not a thrall."
- charge_counter = charge_max
- return
- if(thrallToRevive.stat != DEAD)
- usr << "[thrallToRevive] is not dead."
- charge_counter = charge_max
- return
- usr.visible_message("[usr] kneels over [thrallToRevive], placing their hands on \his chest.", \
- "You crouch over the body of your thrall and begin gathering energy...")
- thrallToRevive.notify_ghost_cloning("Your masters are resuscitating you! Re-enter your corpse if you wish to be brought to life.")
- if(!do_mob(usr, thrallToRevive, 30))
- usr << "Your concentration snaps. The flow of energy ebbs."
- charge_counter= charge_max
- return
- usr << "You release a massive surge of power into [thrallToRevive]!"
- usr.visible_message("Red lightning surges from [usr]'s hands into [thrallToRevive]'s chest!")
- playsound(thrallToRevive, 'sound/weapons/Egloves.ogg', 50, 1)
- playsound(thrallToRevive, 'sound/machines/defib_zap.ogg', 50, 1)
- sleep(10)
- thrallToRevive.revive()
- thrallToRevive.visible_message("[thrallToRevive] draws in a huge breath, blinding violet light shining from their eyes.", \
- "You have returned. One of your masters has brought you from the darkness beyond.")
- thrallToRevive.Weaken(4)
- thrallToRevive.emote("gasp")
- playsound(thrallToRevive, "bodyfall", 50, 1)
+ var/choice = alert(usr,"Empower a living thrall or revive a dead one?",,"Empower","Revive","Cancel")
+ switch(choice)
+ if("Empower")
+ if(!is_thrall(thrallToRevive))
+ usr << "[thrallToRevive] is not a thrall."
+ charge_counter = charge_max
+ return
+ if(thrallToRevive.stat != CONSCIOUS)
+ usr << "[thrallToRevive] must be conscious to become empowered."
+ charge_counter = charge_max
+ return
+ var/empowered_thralls = 0
+ for(var/datum/mind/M in ticker.mode.thralls)
+ if(!ishuman(M.current))
+ return
+ var/mob/living/carbon/human/H = M.current
+ if(H.dna.species.id == "l_shadowling")
+ empowered_thralls++
+ if(empowered_thralls >= EMPOWERED_THRALL_LIMIT)
+ usr << "You cannot spare this much energy. There are too many empowered thralls."
+ charge_counter = charge_max
+ return
+ usr.visible_message("[usr] places their hands over [thrallToRevive]'s face, red light shining from beneath.", \
+ "You place your hands on [thrallToRevive]'s face and begin gathering energy...")
+ thrallToRevive << "[usr] places their hands over your face. You feel energy gathering. Stand still..."
+ if(!do_mob(usr, thrallToRevive, 80))
+ usr << "Your concentration snaps. The flow of energy ebbs."
+ charge_counter = charge_max
+ return
+ usr << "You release a massive surge of power into [thrallToRevive]!"
+ usr.visible_message("Red lightning surges into [thrallToRevive]'s face!")
+ playsound(thrallToRevive, 'sound/weapons/Egloves.ogg', 50, 1)
+ playsound(thrallToRevive, 'sound/machines/defib_zap.ogg', 50, 1)
+ usr.Beam(thrallToRevive,icon_state="red_lightning",icon='icons/effects/effects.dmi',time=1)
+ thrallToRevive.Weaken(5)
+ thrallToRevive.visible_message("[thrallToRevive] collapses, their skin and face distorting!", \
+ "AAAAAAAAAAAAAAAAAAAGH-")
+ sleep(20)
+ thrallToRevive.visible_message("[thrallToRevive] slowly rises, no longer recognizable as human.", \
+ "You feel new power flow into you. You have been gifted by your masters. You now closely resemble them. You are empowered in \
+ darkness but wither slowly in light. In addition, Lesser Glare and Guise have been upgraded into their true forms.")
+ hardset_dna(thrallToRevive, null, null, null, null, /datum/species/shadow/ling/lesser)
+ thrallToRevive.mind.remove_spell(/obj/effect/proc_holder/spell/targeted/lesser_glare)
+ thrallToRevive.mind.remove_spell(/obj/effect/proc_holder/spell/targeted/lesser_shadow_walk)
+ thrallToRevive.mind.AddSpell(new /obj/effect/proc_holder/spell/targeted/glare(null))
+ thrallToRevive.mind.AddSpell(new /obj/effect/proc_holder/spell/targeted/shadow_walk(null))
+ if("Revive")
+ if(!is_thrall(thrallToRevive))
+ usr << "[thrallToRevive] is not a thrall."
+ charge_counter = charge_max
+ return
+ if(thrallToRevive.stat != DEAD)
+ usr << "[thrallToRevive] is not dead."
+ charge_counter = charge_max
+ return
+ usr.visible_message("[usr] kneels over [thrallToRevive], placing their hands on \his chest.", \
+ "You crouch over the body of your thrall and begin gathering energy...")
+ thrallToRevive.notify_ghost_cloning("Your masters are resuscitating you! Re-enter your corpse if you wish to be brought to life.")
+ if(!do_mob(usr, thrallToRevive, 30))
+ usr << "Your concentration snaps. The flow of energy ebbs."
+ charge_counter = charge_max
+ return
+ usr << "You release a massive surge of power into [thrallToRevive]!"
+ usr.visible_message("Red lightning surges from [usr]'s hands into [thrallToRevive]'s chest!")
+ playsound(thrallToRevive, 'sound/weapons/Egloves.ogg', 50, 1)
+ playsound(thrallToRevive, 'sound/machines/defib_zap.ogg', 50, 1)
+ usr.Beam(thrallToRevive,icon_state="red_lightning",icon='icons/effects/effects.dmi',time=1)
+ sleep(10)
+ thrallToRevive.revive()
+ thrallToRevive.visible_message("[thrallToRevive] heaves in breath, dim red light shining in their eyes.", \
+ "You have returned. One of your masters has brought you from the darkness beyond.")
+ thrallToRevive.Weaken(4)
+ thrallToRevive.emote("gasp")
+ playsound(thrallToRevive, "bodyfall", 50, 1)
+ else
+ charge_counter = charge_max
+ return
// THRALL ABILITIES BEYOND THIS POINT //
@@ -599,15 +652,8 @@ datum/reagent/shadowling_blindness_smoke //Reagent used for above spell
/obj/effect/proc_holder/spell/targeted/lesser_shadow_walk/cast(list/targets)
for(var/mob/living/user in targets)
- var/lumcount = 0
- var/turf/T = user.loc
- lumcount = T.get_lumcount()
- if(lumcount > LIGHT_DAM_THRESHOLD)
- user << "It's too bright to do that!"
- charge_counter = charge_max
- return
user.visible_message("[user] suddenly fades away!", "You veil yourself in darkness, making you harder to see.")
- user.alpha = 20
+ user.alpha = 10
sleep(40)
user.visible_message("[user] appears from nowhere!", "Your shadowy guise slips away.")
user.alpha = initial(user.alpha)
@@ -621,7 +667,7 @@ datum/reagent/shadowling_blindness_smoke //Reagent used for above spell
range = -1
include_user = 1
clothes_req = 0
- action_icon_state = "collective_mind"
+ action_icon_state = "darksight"
var/active = 0
/obj/effect/proc_holder/spell/targeted/thrall_vision/cast(list/targets)
@@ -831,7 +877,7 @@ datum/reagent/shadowling_blindness_smoke //Reagent used for above spell
/obj/effect/proc_holder/spell/targeted/ascendant_transmit/cast(list/targets)
for(var/mob/living/user in targets)
- var/text = stripped_input(user, "What do you want to say to everything on and near [world.name]?.", "Transmit to World", "")
+ var/text = stripped_input(user, "What do you want to say to everything on and near [station_name()]?.", "Transmit to World", "")
if(!text)
return
world << "\"[text]\""
diff --git a/code/game/gamemodes/shadowling/shadowling_items.dm b/code/game/gamemodes/shadowling/shadowling_items.dm
index 1f81126f29b..b90e78b4bdf 100644
--- a/code/game/gamemodes/shadowling/shadowling_items.dm
+++ b/code/game/gamemodes/shadowling/shadowling_items.dm
@@ -77,11 +77,33 @@
item_state = null
origin_tech = null
vision_flags = SEE_MOBS
- darkness_view = 3
+ darkness_view = 1
invis_view = 2
flash_protect = -1
unacidable = 1
flags = ABSTRACT | NODROP
+ action_button_name = "Shift Nerves"
+ action_button_is_hands_free = 1
+ var/max_darkness_view = 8
+ var/min_darkness_view = 0
+
+/obj/item/clothing/glasses/night/shadowling/attack_self(mob/user)
+ if(!ishuman(user))
+ return
+ var/mob/living/carbon/human/H = user
+ if(H.dna.species.id != "shadowling")
+ user << "You aren't sure how to do this..."
+ return
+ var/new_dark_view
+ new_dark_view = (input(user, "Enter the radius of tiles to see with night vision.", "Night Vision", "[new_dark_view]") as num)
+ new_dark_view = Clamp(new_dark_view,min_darkness_view,max_darkness_view)
+ switch(new_dark_view)
+ if(0)
+ user << "Your night vision capabilities fade away for the time being."
+ else
+ user << "You shift your night vision capabilities to see [new_dark_view] tiles away."
+ darkness_view = new_dark_view
+ return
/obj/structure/shadow_vortex
diff --git a/code/game/objects/items/devices/flashlight.dm b/code/game/objects/items/devices/flashlight.dm
index b929937aa8b..b7e662fe401 100644
--- a/code/game/objects/items/devices/flashlight.dm
+++ b/code/game/objects/items/devices/flashlight.dm
@@ -253,10 +253,11 @@ obj/item/device/flashlight/lamp/bananalamp
name = "torch"
desc = "A torch fashioned from some leaves and a log."
w_class = 4
- brightness_on = 7
+ brightness_on = 4
icon_state = "torch"
item_state = "torch"
on_damage = 10
+ slot_flags = null
/obj/item/device/flashlight/lantern
name = "lantern"
diff --git a/code/modules/surgery/dethrall.dm b/code/modules/surgery/dethrall.dm
index c421e8ece6e..5a028336e9a 100644
--- a/code/modules/surgery/dethrall.dm
+++ b/code/modules/surgery/dethrall.dm
@@ -23,6 +23,7 @@
user << "You are unable to locate anything on [target]'s brain."
return 1
sleep(30)
+
user.visible_message("[user] begins removing something from [target]'s head.", \
"You begin carefully extracting the tumor...")
if(!do_mob(user, target, 50))
@@ -34,6 +35,21 @@
else
user.visible_message("[user] screws up!")
return 0
+ if(target.dna.species.id == "l_shadowling")
+ target << "NOT LIKE THIS!"
+ user.visible_message("[target] suddenly slams upward and knocks down [user]!", \
+ "[target] suddenly bolts up and slams you with tremendous force!")
+ if(iscarbon(user))
+ var/mob/living/carbon/C = user
+ C.Weaken(6)
+ C.apply_damage(20, "brute", "chest")
+ else if(issilicon(user))
+ var/mob/living/silicon/S = user
+ S.Weaken(8)
+ S.apply_damage(20, "brute")
+ playsound(S, 'sound/effects/bang.ogg', 50, 1)
+ return
+
user.visible_message("[user] carefully extracts the tumor from [target]'s brain!", \
"You extract the black tumor from [target]'s head. It quickly shrivels and burns away.")
ticker.mode.remove_thrall(target.mind,0)
diff --git a/html/changelogs/Xhuis-SU4.yml b/html/changelogs/Xhuis-SU4.yml
new file mode 100644
index 00000000000..c45a1d02253
--- /dev/null
+++ b/html/changelogs/Xhuis-SU4.yml
@@ -0,0 +1,11 @@
+author: Xhuis
+delete-after: True
+
+changes:
+ - rscadd: "Darksight now has its own icon."
+ - rscadd: "Empowered thralls have been added. While obvious, they are more powerful and can resist dethralling while conscious. Only 5 can exist at one time."
+ - rscadd: "Shadowlings can now change their night vision radius by using the action button their eyes (glasses) now provide."
+ - tweak: "Torches are dimmer, being as bright as flashlights, and no longer fit on belts."
+ - tweak: "Black Recuperation now has a 1 minute cooldown, down from 5. It can also be used to empower living thralls."
+ - tweak: "Guise can now be used outside of darkness and makes the user more invisible than before."
+ - bugfix: "Enthrall now functions properly when a shadowling is not hatched, allowing them to enthrall up to 5 people before hatching."
\ No newline at end of file
diff --git a/icons/mob/actions.dmi b/icons/mob/actions.dmi
index 7419670c30b..485d89155bc 100644
Binary files a/icons/mob/actions.dmi and b/icons/mob/actions.dmi differ
diff --git a/icons/mob/human.dmi b/icons/mob/human.dmi
index cb72485b1bc..dd7fdde2c7b 100644
Binary files a/icons/mob/human.dmi and b/icons/mob/human.dmi differ