Skip to content

Commit

Permalink
Vampire Rework. (ParadiseSS13#16476)
Browse files Browse the repository at this point in the history
* vampire rework

* fixes and tweaks

* cleanup + tweaks

* grug stomp

* TGUI

* TGUI rebuild

* UID fix

* debugging cooldown fix

* first review changes

* subclass refactor

* tweaks + some sprites

* blackbox logging

* tweaks + grammar

* minor UI tweaks

* ability icon sprites.

* placeholder sprite warning fix

* melee mod code comment warning

* nullification rework

* final sprites!

* fixes

* sabre review pt 1

Co-authored-by: SabreML <[email protected]>

* sabre review pt2

* sprites readd

* tgui rebuild

* removes traitor vampires

* fixes

* readds sprites

* runtime fixes

* hotfix

* more runtime fixes

* glare tweak. less confusing when the vampire is stunned.

* gargantua nerf

* minor tweaks.

* hemomancer nerfs

* bugfixes and cleanup

* I did a dumb

* couple of fixes

* confusion and shadow snare fixes

* hemomancer nerfs part 2 electric boogaloo

* TGUI rebuild

* fixes and easier events

* Umbrae tweaks

* gargantua tweak

* umbrae nerf 2 electric boogaloo. also var edit suggestion

* runtime fix

* buffs blood nutrition to be in line with its metabolic rate

* Henk stuff

Co-authored-by: Farie82 <[email protected]>

* more review changes

* final tweak

* affected request + runtime fix

* FUCK

* fat fucks

* darkness tweaks

* UMBRAE AAAAAAAAAAAAAHH

* force doors bugfix

* either git or I am drunk

* admin rejuv fix

* I CANNOT SPELL

* shitnt code

* steel review

* tgui rebuild

* mochi review

* vampire ability usage logging

Co-authored-by: SabreML <[email protected]>
Co-authored-by: Farie82 <[email protected]>
  • Loading branch information
3 people authored Nov 14, 2021
1 parent 46d3759 commit 634f9c7
Show file tree
Hide file tree
Showing 52 changed files with 1,600 additions and 819 deletions.
6 changes: 6 additions & 0 deletions code/__DEFINES/status_effects.dm
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,10 @@

#define STATUS_EFFECT_BLOODDRUNK /datum/status_effect/blooddrunk //Stun immunity and greatly reduced damage taken

#define STATUS_EFFECT_BLOOD_SWELL /datum/status_effect/bloodswell //stun resistance and halved damage for gargantua vampires

#define STATUS_EFFECT_BLOOD_RUSH /datum/status_effect/blood_rush // speed boost for gargantua vampires

/////////////
// DEBUFFS //
/////////////
Expand Down Expand Up @@ -78,6 +82,8 @@

#define STATUS_EFFECT_HIGHFIVE /datum/status_effect/high_five

#define STATUS_EFFECT_CHARGING /datum/status_effect/charging

//#define STATUS_EFFECT_SIGILMARK /datum/status_effect/sigil_mark

#define STATUS_EFFECT_CRUSHERDAMAGETRACKING /datum/status_effect/crusher_damage //tracks total kinetic crusher damage on a target
Expand Down
11 changes: 11 additions & 0 deletions code/__DEFINES/vampire.dm
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
#define SUBCLASS_HEMOMANCER /datum/vampire_subclass/hemomancer
#define SUBCLASS_GARGANTUA /datum/vampire_subclass/gargantua
#define SUBCLASS_UMBRAE /datum/vampire_subclass/umbrae
#define SUBCLASS_ANCIENT /datum/vampire_subclass/ancient

#define BLOOD_DRAIN_LIMIT 200 // the amount of blood a vampire can drain from a person.
#define FULLPOWER_DRAINED_REQUIREMENT 8 // the number of people you need to suck to become full powered.
#define FULLPOWER_BLOODTOTAL_REQUIREMENT 1000 // the amount of blood you need to suck to get full power.

#define VAMPIRE_NULLIFICATION_CAP 120 // the maximum amount a vampire can be nullified naturally.
#define VAMPIRE_COMPLETE_NULLIFICATION 100 // the point of nullification where vampires can no longer use abilities.
2 changes: 2 additions & 0 deletions code/__HELPERS/traits.dm
Original file line number Diff line number Diff line change
Expand Up @@ -179,6 +179,7 @@ Remember to update _globalvars/traits.dm if you're adding/removing/renaming trai
#define TRAIT_NODECAY "no_decay"
#define TRAIT_NOEXAMINE "no_examine"
#define TRAIT_NOPAIN "no_pain"
#define TRAIT_FORCE_DOORS "force_doors"

//***** ITEM TRAITS *****//
/// Show what machine/door wires do when held.
Expand All @@ -198,6 +199,7 @@ Remember to update _globalvars/traits.dm if you're adding/removing/renaming trai
#define CLOTHING_TRAIT "clothing"
#define CULT_TRAIT "cult"
#define INNATE_TRAIT "innate"
#define VAMPIRE_TRAIT "vampire"

// unique trait sources
#define STATUE_MUTE "statue"
Expand Down
3 changes: 2 additions & 1 deletion code/_globalvars/traits.dm
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,8 @@ GLOBAL_LIST_INIT(traits_by_type, list(
"TRAIT_NOGERMS" = TRAIT_NOGERMS,
"TRAIT_NODECAY" = TRAIT_NODECAY,
"TRAIT_NOEXAMINE" = TRAIT_NOEXAMINE,
"TRAIT_NOPAIN" = TRAIT_NOPAIN
"TRAIT_NOPAIN" = TRAIT_NOPAIN,
"TRAIT_FORCE_DOORS" = TRAIT_FORCE_DOORS,
),
/obj/item = list(
"TRAIT_SHOW_WIRE_INFO" = TRAIT_SHOW_WIRE_INFO,
Expand Down
12 changes: 10 additions & 2 deletions code/_onclick/item_attack.dm
Original file line number Diff line number Diff line change
Expand Up @@ -99,14 +99,22 @@
return

/obj/attacked_by(obj/item/I, mob/living/user)
var/damage = I.force
if(I.force)
user.visible_message("<span class='danger'>[user] has hit [src] with [I]!</span>", "<span class='danger'>You hit [src] with [I]!</span>")
take_damage(I.force, I.damtype, MELEE, 1)
if(ishuman(user))
var/mob/living/carbon/human/H = user
damage += H.physiology.melee_bonus
take_damage(damage, I.damtype, MELEE, 1)

/mob/living/attacked_by(obj/item/I, mob/living/user, def_zone)
send_item_attack_message(I, user)
if(I.force)
apply_damage(I.force, I.damtype, def_zone)
var/bonus_damage = 0
if(ishuman(user))
var/mob/living/carbon/human/H = user
bonus_damage = H.physiology.melee_bonus
apply_damage(I.force + bonus_damage, I.damtype, def_zone)
if(I.damtype == BRUTE)
if(prob(33))
I.add_mob_blood(src)
Expand Down
7 changes: 5 additions & 2 deletions code/datums/mind.dm
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,8 @@
for(var/a in antag_datums) //Makes sure all antag datums effects are applied in the new body
var/datum/antagonist/A = a
A.on_body_transfer(old_current, current)
if(vampire)
vampire.update_owner(new_character)
transfer_antag_huds(hud_to_transfer) //inherit the antag HUD
transfer_actions(new_character)
if(martial_art)
Expand Down Expand Up @@ -1544,14 +1546,15 @@

SSticker.mode.equip_syndicate(current)

/datum/mind/proc/make_Vampire()
/datum/mind/proc/make_vampire(ancient_vampire = FALSE)
if(!(src in SSticker.mode.vampires))
SSticker.mode.vampires += src
SSticker.mode.grant_vampire_powers(current)
special_role = SPECIAL_ROLE_VAMPIRE
SSticker.mode.forge_vampire_objectives(src)
SSticker.mode.greet_vampire(src)
SSticker.mode.update_vampire_icons_added(src)
if(!ancient_vampire)
SSticker.mode.forge_vampire_objectives(src)

/datum/mind/proc/make_Changeling()
if(!(src in SSticker.mode.changelings))
Expand Down
24 changes: 9 additions & 15 deletions code/datums/outfits/outfit_admin.dm
Original file line number Diff line number Diff line change
Expand Up @@ -1103,21 +1103,15 @@

if(H.mind)
if(!H.mind.vampire)
H.make_vampire()
if(H.mind.vampire)
H.mind.vampire.bloodusable = 9999
H.mind.vampire.bloodtotal = 9999
H.mind.vampire.check_vampire_upgrade(0)
H.mind.AddSpell(new /obj/effect/proc_holder/spell/targeted/shapeshift/bats)
to_chat(H, "You have gained the ability to shapeshift into bat form. This is a weak form with no abilities, only useful for stealth.")
H.mind.AddSpell(new /obj/effect/proc_holder/spell/targeted/shapeshift/hellhound)
to_chat(H, "You have gained the ability to shapeshift into lesser hellhound form. This is a combat form with different abilities, tough but not invincible. It can regenerate itself over time by resting.")
H.mind.AddSpell(new /obj/effect/proc_holder/spell/targeted/raise_vampires)
to_chat(H, "You have gained the ability to Raise Vampires. This extremely powerful AOE ability affects all humans near you. Vampires/thralls are healed. Corpses are raised as vampires. Others are stunned, then brain damaged, then killed.")
H.dna.SetSEState(GLOB.jumpblock, 1)
singlemutcheck(H, GLOB.jumpblock, MUTCHK_FORCED)
H.update_mutations()
H.gene_stability = 100
H.mind.make_vampire(TRUE)
H.mind.vampire.bloodusable = 9999
H.mind.vampire.bloodtotal = 9999
H.mind.offstation_role = TRUE
H.mind.vampire.add_subclass(SUBCLASS_ANCIENT, FALSE)
H.dna.SetSEState(GLOB.jumpblock, TRUE)
singlemutcheck(H, GLOB.jumpblock, MUTCHK_FORCED)
H.update_mutations()
H.gene_stability = 100

/datum/outfit/admin/wizard
name = "Blue Wizard"
Expand Down
54 changes: 47 additions & 7 deletions code/datums/spell.dm
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,11 @@ GLOBAL_LIST_INIT(spells, typesof(/obj/effect/proc_holder/spell))
var/special_availability_check = 0//Whether the spell needs to bypass the action button's IsAvailable()

var/sound = null //The sound the spell makes when it is cast
/// If the ability is for vampires
var/vampire_ability = FALSE
var/required_blood = 0
var/gain_desc = null
var/deduct_blood_on_cast = TRUE

/* Checks if the user can cast the spell
* @param charge_check If the proc should do the cooldown check
Expand Down Expand Up @@ -190,6 +195,8 @@ GLOBAL_LIST_INIT(spells, typesof(/obj/effect/proc_holder/spell))
charge_counter = charge_max
else
start_recharge()
if(!gain_desc)
gain_desc = "You can now use [src]."

/obj/effect/proc_holder/spell/Destroy()
QDEL_NULL(action)
Expand Down Expand Up @@ -238,6 +245,9 @@ GLOBAL_LIST_INIT(spells, typesof(/obj/effect/proc_holder/spell))
action.UpdateButtonIcon()

/obj/effect/proc_holder/spell/proc/before_cast(list/targets)
if(vampire_ability)
if(!before_cast_vampire(targets))
return
if(overlay)
for(var/atom/target in targets)
var/location
Expand Down Expand Up @@ -594,25 +604,55 @@ GLOBAL_LIST_INIT(spells, typesof(/obj/effect/proc_holder/spell))
var/mob/living/carbon/human/H = user
var/clothcheck = locate(/obj/effect/proc_holder/spell/noclothes) in user.mob_spell_list
var/clothcheck2 = user.mind && (locate(/obj/effect/proc_holder/spell/noclothes) in user.mind.spell_list)
if(clothes_req && !clothcheck && !clothcheck2) //clothes check
if(clothes_req && !clothcheck && !clothcheck2 && !vampire_ability) //clothes check
var/obj/item/clothing/robe = H.wear_suit
var/obj/item/clothing/hat = H.head
var/obj/item/clothing/shoes = H.shoes
if(!robe || !hat || !shoes)
if(show_message)
to_chat(user, "<span class='notice'>Your outfit isn't complete, you should put on your robe and wizard hat, as well as sandals.</span>")
return 0
return FALSE
if(!robe.magical || !hat.magical || !shoes.magical)
if(show_message)
to_chat(user, "<span class='notice'>Your outfit isn't magical enough, you should put on your robe and wizard hat, as well as your sandals.</span>")
return 0
return FALSE
else
if(clothes_req || human_req)
if(clothes_req || human_req || vampire_ability)
if(show_message)
to_chat(user, "<span class='notice'>This spell can only be cast by humans!</span>")
return 0
return FALSE
if(nonabstract_req && (isbrain(user) || ispAI(user)))
if(show_message)
to_chat(user, "<span class='notice'>This spell can only be cast by physical beings!</span>")
return 0
return 1
return FALSE

if(vampire_ability)

var/datum/vampire/vampire = user.mind.vampire

if(!vampire)
return FALSE

var/fullpower = vampire.get_ability(/datum/vampire_passive/full)

if(user.stat >= DEAD)
if(show_message)
to_chat(user, "<span class='warning'>Not while you're dead!</span>")
return FALSE

if(vampire.nullified >= VAMPIRE_COMPLETE_NULLIFICATION && !fullpower) // above 100 nullification vampire powers are useless
if(show_message)
to_chat(user, "<span class='warning'>Something is blocking your powers!</span>")
return FALSE
if(vampire.bloodusable < required_blood)
if(show_message)
to_chat(user, "<span class='warning'>You require at least [required_blood] units of usable blood to do that!</span>")
return FALSE
//chapel check
if(istype(get_area(user), /area/chapel) && !fullpower)
if(show_message)
to_chat(user, "<span class='warning'>Your powers are useless on this holy ground.</span>")
return FALSE

return TRUE

40 changes: 32 additions & 8 deletions code/datums/spells/ethereal_jaunt.dm
Original file line number Diff line number Diff line change
Expand Up @@ -12,16 +12,18 @@
include_user = 1
nonabstract_req = 1
centcom_cancast = 0 //Prevent people from getting to centcom

var/sound1 = 'sound/magic/ethereal_enter.ogg'
var/jaunt_duration = 50 //in deciseconds
var/jaunt_in_time = 5
var/jaunt_in_type = /obj/effect/temp_visual/wizard
var/jaunt_out_type = /obj/effect/temp_visual/wizard/out
var/jaunt_type_path = /obj/effect/dummy/spell_jaunt
var/jaunt_water_effect = TRUE

action_icon_state = "jaunt"

/obj/effect/proc_holder/spell/targeted/ethereal_jaunt/cast(list/targets, mob/user = usr) //magnets, so mostly hardcoded
playsound(get_turf(user), 'sound/magic/ethereal_enter.ogg', 50, 1, -1)
playsound(get_turf(user), sound1, 50, 1, -1)
for(var/mob/living/target in targets)
if(!target.can_safely_leave_loc()) // No more brainmobs hopping out of their brains
to_chat(target, "<span class='warning'>You are somehow too bound to your current location to abandon it.</span>")
Expand All @@ -31,25 +33,27 @@
/obj/effect/proc_holder/spell/targeted/ethereal_jaunt/proc/do_jaunt(mob/living/target)
target.notransform = 1
var/turf/mobloc = get_turf(target)
var/obj/effect/dummy/spell_jaunt/holder = new /obj/effect/dummy/spell_jaunt(mobloc)
var/obj/effect/dummy/spell_jaunt/holder = new jaunt_type_path(mobloc)
new jaunt_out_type(mobloc, target.dir)
target.ExtinguishMob()
target.forceMove(holder)
target.reset_perspective(holder)
target.notransform = 0 //mob is safely inside holder now, no need for protection.
jaunt_steam(mobloc)
if(jaunt_water_effect)
jaunt_steam(mobloc)

sleep(jaunt_duration)

if(target.loc != holder) //mob warped out of the warp
qdel(holder)
return
mobloc = get_turf(target.loc)
jaunt_steam(mobloc)
if(jaunt_water_effect)
jaunt_steam(mobloc)
target.canmove = 0
holder.reappearing = 1
playsound(get_turf(target), 'sound/magic/ethereal_exit.ogg', 50, 1, -1)
sleep(25 - jaunt_in_time)
sleep(jaunt_in_time * 4)
new jaunt_in_type(mobloc, holder.dir)
target.setDir(holder.dir)
sleep(jaunt_in_time)
Expand Down Expand Up @@ -95,14 +99,34 @@
return
var/turf/newLoc = get_step(src,direction)
setDir(direction)
if(!(newLoc.flags & NOJAUNT))
if(can_move(newLoc))
forceMove(newLoc)
else
to_chat(user, "<span class='warning'>Some strange aura is blocking the way!</span>")
to_chat(user, "<span class='warning'>Something is blocking the way!</span>")
movedelay = world.time + movespeed

/obj/effect/dummy/spell_jaunt/proc/can_move(turf/T)
if(T.flags & NOJAUNT)
return FALSE
return TRUE

/obj/effect/dummy/spell_jaunt/ex_act(blah)
return

/obj/effect/dummy/spell_jaunt/bullet_act(blah)
return

/obj/effect/dummy/spell_jaunt/blood_pool
name = "sanguine pool"
desc = "a pool of living blood."
movespeed = 1.5

/obj/effect/dummy/spell_jaunt/blood_pool/relaymove(mob/user, direction)
..()
new /obj/effect/decal/cleanable/blood(loc)


/obj/effect/dummy/spell_jaunt/blood_pool/can_move(turf/T)
if(isspaceturf(T) || T.density)
return FALSE
return TRUE
2 changes: 2 additions & 0 deletions code/datums/spells/shapeshift.dm
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,7 @@
invocation = "none"
invocation_type = "none"
action_icon_state = "vampire_bats"
gain_desc = "You have gained the ability to shapeshift into bat form. This is a weak form with no abilities, only useful for stealth."

shapeshift_type = /mob/living/simple_animal/hostile/scarybat/adminvampire
current_shapes = list(/mob/living/simple_animal/hostile/scarybat/adminvampire)
Expand All @@ -108,6 +109,7 @@
invocation_type = "none"
action_background_icon_state = "bg_demon"
action_icon_state = "glare"
gain_desc = "You have gained the ability to shapeshift into lesser hellhound form. This is a combat form with different abilities, tough but not invincible. It can regenerate itself over time by resting."

shapeshift_type = /mob/living/simple_animal/hostile/hellhound
current_shapes = list(/mob/living/simple_animal/hostile/hellhound)
Expand Down
13 changes: 11 additions & 2 deletions code/datums/spells/turf_teleport.dm
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,16 @@

var/include_space = 0 //whether it includes space tiles in possible teleport locations
var/include_dense = 0 //whether it includes dense tiles in possible teleport locations
/// Whether the spell can teleport to light locations
var/include_light_turfs = TRUE

var/sound1 = 'sound/weapons/zapbang.ogg'
var/sound2 = 'sound/weapons/zapbang.ogg'

/obj/effect/proc_holder/spell/targeted/turf_teleport/cast(list/targets,mob/living/user = usr)
playsound(get_turf(user), sound1, 50,1)
if(sound1)
playsound(get_turf(user), sound1, 50,1)

for(var/mob/living/target in targets)
var/list/turfs = new/list()
for(var/turf/T in range(target,outer_tele_radius))
Expand All @@ -22,6 +26,10 @@
if(T.density && !include_dense) continue
if(T.x>world.maxx-outer_tele_radius || T.x<outer_tele_radius) continue //putting them at the edge is dumb
if(T.y>world.maxy-outer_tele_radius || T.y<outer_tele_radius) continue
if(!include_light_turfs)
var/lightingcount = T.get_lumcount() * 10
if(lightingcount > 2)
continue
turfs += T

if(!turfs.len)
Expand All @@ -37,4 +45,5 @@
return

target.forceMove(picked)
playsound(get_turf(user), sound2, 50,1)
if(sound2)
playsound(get_turf(user), sound2, 50,1)
Loading

0 comments on commit 634f9c7

Please sign in to comment.