mirror of
https://github.com/ParadiseSS13/Paradise.git
synced 2026-07-18 18:44:48 +01:00
Merge pull request #6446 from Kyep/terrorspiders-PR3
Terror Spiders 3 - Awaymission & AI
This commit is contained in:
@@ -0,0 +1,256 @@
|
||||
/area/awaymission/UO71
|
||||
name = "UO71"
|
||||
icon_state = "away"
|
||||
report_alerts = 0
|
||||
tele_proof = 1
|
||||
|
||||
|
||||
/area/awaymission/UO71/plaza
|
||||
name = "UO71 Plaza"
|
||||
icon_state = "awaycontent1"
|
||||
fire = 1
|
||||
|
||||
/area/awaymission/UO71/centralhall
|
||||
name = "UO71 Central"
|
||||
icon_state = "awaycontent2"
|
||||
fire = 1
|
||||
|
||||
/area/awaymission/UO71/eng
|
||||
name = "UO71 Engineering"
|
||||
icon_state = "awaycontent3"
|
||||
fire = 1
|
||||
|
||||
/area/awaymission/UO71/mining
|
||||
name = "UO71 Mining"
|
||||
icon_state = "awaycontent4"
|
||||
fire = 1
|
||||
|
||||
/area/awaymission/UO71/science
|
||||
name = "UO71 Science"
|
||||
icon_state = "awaycontent5"
|
||||
fire = 1
|
||||
|
||||
/area/awaymission/UO71/medical
|
||||
name = "UO71 Medical"
|
||||
icon_state = "awaycontent6"
|
||||
fire = 1
|
||||
|
||||
/area/awaymission/UO71/gateway
|
||||
name = "UO71 Gateway"
|
||||
icon_state = "awaycontent7"
|
||||
fire = 1
|
||||
|
||||
/area/awaymission/UO71/outside
|
||||
name = "UO71 Outside"
|
||||
icon_state = "awaycontent8"
|
||||
|
||||
/area/awaymission/UO71/bridge
|
||||
name = "UO71 Bridge"
|
||||
icon_state = "awaycontent21"
|
||||
fire = 1
|
||||
requires_power = 0
|
||||
tele_proof = 1
|
||||
|
||||
/area/awaymission/UO71/queen
|
||||
name = "UO71 Queen Lair"
|
||||
icon_state = "awaycontent9"
|
||||
fire = 1
|
||||
requires_power = 0
|
||||
tele_proof = 1
|
||||
|
||||
/area/awaymission/UO71/prince
|
||||
name = "UO71 Prince Containment"
|
||||
icon_state = "awaycontent10"
|
||||
fire = 1
|
||||
requires_power = 0
|
||||
tele_proof = 1
|
||||
|
||||
/area/awaymission/UO71/mother
|
||||
name = "UO71 Mother Containment"
|
||||
icon_state = "awaycontent10"
|
||||
fire = 1
|
||||
requires_power = 0
|
||||
tele_proof = 1
|
||||
|
||||
/area/awaymission/UO71/loot
|
||||
name = "UO71 Loot Vault"
|
||||
icon_state = "awaycontent11"
|
||||
requires_power = 0
|
||||
tele_proof = 1
|
||||
|
||||
/obj/item/weapon/paper/terrorspiders1
|
||||
name = "paper - 'Sealed Facility'"
|
||||
info = {"<b>SEALED FACILITY</b><br>
|
||||
<br>
|
||||
This facility is sealed shut by order of Commander Marquez. Do not enter.<br>
|
||||
Terror spiders live here. We believe they are a weapon developed by the syndicate.<br>
|
||||
Any surviving personnel are to evacuate immediately via the gateway.<br>
|
||||
"}
|
||||
|
||||
/obj/item/weapon/paper/terrorspiders2
|
||||
name = "paper - 'The Trio of Terror'"
|
||||
info = {"<b>Status Report on the 'Terrors'</b><br>
|
||||
<br>
|
||||
All the spiders are deadly. We know this much already. Within an hour of their appearance, they have killed several staff.<br>
|
||||
Three, however, bear particular mention, as they appear to be leading the spider hivemind.<br>
|
||||
<br>
|
||||
The Mother is held in containment 1. Advise leaving her alone.<br>
|
||||
It is likely that the hundreds of tiny spiders swarming over her back would come to her defense if she was threatened.<br>
|
||||
<br>
|
||||
The Prince is held in containment 2. He appears very aggressive, incredibly fast, strong, and durable. Extreme force and agility would be required to neutralize him.<br>
|
||||
It is likely the appearance of the prince was related to our initial aggression against the Queen. These things can THINK.<br>
|
||||
<br>
|
||||
The Queen cannot be contained. She lives in the old bar, south of mining. She continues to breed dangerous spiders at an alarming rate.<br>
|
||||
Many of her offspring are already roaming the compound, traveling through the vents. Contact with the team sent to subdue her has been lost.<br>
|
||||
<br>
|
||||
<br>
|
||||
Based on the situation, Commander, I advise immediate evacuation through the gateway.<br>
|
||||
-Research Director Simons<br>
|
||||
"}
|
||||
|
||||
|
||||
/obj/item/weapon/paper/terrorspiders3
|
||||
name = "paper - 'Final Report'"
|
||||
info = {"FROM: Field Agent 0738<br>
|
||||
TO: Syndicate #873589<br>
|
||||
SUBJECT: Mission Success<br>
|
||||
<br>
|
||||
I have seeded the Terror Queen egg in a dingy looking bar that bored engineers constructed near the mining tunnels.<br>
|
||||
No doubt she will grow soon.<br>
|
||||
<br>
|
||||
I have also placed the Mother and Prince eggs nearby, injected with sedative. Hopefully the dimwitted NT scientists bring them back for study.<br>
|
||||
With any luck, the Queen will sense them telepathically, think NT is holding her children hostage, and attack.<br>
|
||||
<br>
|
||||
I am going to extract out of the gateway before this all goes down.<br>
|
||||
I don't imagine the staff have very long to live once the Queen declares war on this place.<br>
|
||||
"}
|
||||
|
||||
/obj/item/weapon/paper/terrorspiders4
|
||||
name = "paper - 'Prescription for Jones, David'"
|
||||
info = {"PRESCRIPTION FOR: David Jones<br>
|
||||
RANK: Miner<br>
|
||||
FOR: Haloperidol<br>
|
||||
REASON FOR TREATMENT: Hallucinations, Paranoia<br>
|
||||
CAUSE: Hallucinations caused by encounter with toxic spit of spider in the caves. Paranoia caused by disappearing staff and suspicions of syndicate infiltration.<br>
|
||||
TREATMENT PLAN: Take as needed. See Dr. Phloxi in one week if symptoms persist. <br>
|
||||
"}
|
||||
|
||||
/obj/item/weapon/paper/terrorspiders5
|
||||
name = "paper - 'A Study in Terror'"
|
||||
info = {"<b>Findings Overview</b><br>
|
||||
<br>
|
||||
<p>Gray Spiders<br>Stealthy predators that ambush prey from vents. Otherwise weak.</p>
|
||||
<p>Red Spiders<br>Can kill anyone in melee, but slow.</p>
|
||||
<p>Green<br>Will lay eggs on dead bodies, breeding more spiders.</p>
|
||||
<p>Black<br>Even a single bite is enough to kill a humanoid, given time.</p>
|
||||
<p>White<br>Injects a parasitic agent. Deemed to pose too great an infection risk to study.</p>
|
||||
<p>Purple<br>Only seen guarding the nest of the Queen to the south. Appear to be territorial, and very dangerous.</p>
|
||||
<p>Prince<br>Held in containment 2. Appears to be a sort of super-warrior. Fast, strong, and thickly armored.</p>
|
||||
<p>Mother<br>Carries hordes of spiderlings on its back. Held in containment 1. </p>
|
||||
<p>Queen<br>Unable to contain. Present south of Cargo before contact was lost. Presumed ruler of the local hive.</p>
|
||||
"}
|
||||
|
||||
/obj/item/weapon/paper/terrorspiders6
|
||||
name = "paper - 'A Study in Venom'"
|
||||
info = {"<b>Initial Report - Black Widow Venom</b><br>
|
||||
<br>
|
||||
Even a single bite kills within a few minutes. Immediate charcoal is necessary for the victim to survive.<br>
|
||||
The fascinating thing is that multiple bites actually cause rapid symptom onset. The victim quickly loses the ability to walk.<br>
|
||||
One test monkey went from perfect health to death in under 60 seconds - from 3 bites.<br>
|
||||
I am so very glad I'm not responsible for keeping these things contained."}
|
||||
|
||||
/obj/item/weapon/paper/terrorspiders7
|
||||
name = "paper - 'Security Orders'"
|
||||
info = {"<b>Directives for Officer James</b><br>
|
||||
<br>
|
||||
1. Find a way to lift the bridge lockdown.<br>
|
||||
2. Kill any spiders you encounter.<br>
|
||||
3. Once on the bridge, open a path to the Queen in the south, and find a way to kill her, ending the infestation. <br>
|
||||
Good luck, Officer.<br>
|
||||
"}
|
||||
|
||||
/obj/item/weapon/paper/terrorspiders8
|
||||
name = "paper - 'Last Words'"
|
||||
info = {"<b>The Last Words of Nurse Barnes</b><br>
|
||||
<br>
|
||||
It is too much. First Phil, then those damn spiders bite Mary too. Heaven help us. <br>
|
||||
I'll be evacuating as soon as I've grabbed my supplies. I had to pay for those myself. Stupid budget cuts. <br>
|
||||
The new world they've found for us isn't that hospitable, but at least there are no deadly spid---<br>
|
||||
(the writing trails off, as if the writer was interrupted)<br>
|
||||
"}
|
||||
|
||||
|
||||
/obj/item/weapon/gun/energy/laser/awaymission_aeg
|
||||
name = "Wireless Energy Gun"
|
||||
desc = "An energy gun that recharges wirelessly during away missions. Does not work on the main station."
|
||||
force = 10
|
||||
origin_tech = null
|
||||
selfcharge = 1
|
||||
var/inawaymission = 1
|
||||
|
||||
/obj/item/weapon/gun/energy/laser/awaymission_aeg/process()
|
||||
var/turf/my_loc = get_turf(src)
|
||||
if(is_away_level(my_loc.z))
|
||||
if(inawaymission)
|
||||
return ..()
|
||||
if(ismob(loc))
|
||||
to_chat(loc, "<span class='notice'>Your [src] activates, starting to draw power from a nearby wireless power source.</span>")
|
||||
inawaymission = 1
|
||||
else
|
||||
if(inawaymission)
|
||||
if(ismob(loc))
|
||||
to_chat(loc, "<span class='danger'>Your [src] deactivates, as it is out of range from its power source.</span>")
|
||||
power_supply.charge = 0
|
||||
inawaymission = 0
|
||||
update_icon()
|
||||
|
||||
|
||||
|
||||
/obj/item/weapon/reagent_containers/glass/beaker/terror_black_toxin
|
||||
name = "beaker 'Black Terror Venom'"
|
||||
|
||||
/obj/item/weapon/reagent_containers/glass/beaker/terror_black_toxin/New()
|
||||
..()
|
||||
reagents.add_reagent("terror_black_toxin", 50)
|
||||
update_icon()
|
||||
|
||||
|
||||
/obj/machinery/computer/id_upgrader
|
||||
name = "ID Upgrade Machine"
|
||||
icon_state = "guest"
|
||||
icon_screen = "pass"
|
||||
var/list/access_to_give = list(access_away01)
|
||||
var/beenused = 0
|
||||
var/door_to_open = "UO71_Start"
|
||||
|
||||
/obj/machinery/computer/id_upgrader/attackby(obj/item/I, mob/user, params)
|
||||
if(istype(I, /obj/item/weapon/card/id))
|
||||
var/obj/item/weapon/card/id/D = I
|
||||
if(!access_to_give.len)
|
||||
to_chat(user, "<span class='notice'>This machine appears to be configured incorrectly.</span>")
|
||||
return
|
||||
var/did_upgrade = 0
|
||||
var/list/id_access = D.GetAccess()
|
||||
for(var/this_access in access_to_give)
|
||||
if(!(this_access in id_access))
|
||||
// don't have it - add it
|
||||
D.access |= this_access
|
||||
did_upgrade = 1
|
||||
if(did_upgrade)
|
||||
to_chat(user, "<span class='notice'>An access type was added to your ID card.</span>")
|
||||
if(beenused)
|
||||
return
|
||||
spawn(1)
|
||||
beenused = 1
|
||||
var/unlocked_something = 0
|
||||
for(var/obj/machinery/door/poddoor/P in airlocks)
|
||||
if(P.density && P.id_tag == door_to_open && P.z == z)
|
||||
P.open()
|
||||
unlocked_something = 1
|
||||
if(unlocked_something)
|
||||
to_chat(user, "<span class='danger'>Activating the machine has unlocked a way forward!</span>")
|
||||
else
|
||||
to_chat(user, "<span class='notice'>Your ID card already has all the access this machine can give.</span>")
|
||||
. = 1
|
||||
|
||||
|
||||
@@ -191,7 +191,7 @@ var/list/event_last_fired = list()
|
||||
new /datum/event_meta(EVENT_LEVEL_MAJOR, "Abductor Visit", /datum/event/abductor, 80, is_one_shot = 1),
|
||||
new /datum/event_meta/alien(EVENT_LEVEL_MAJOR, "Alien Infestation", /datum/event/alien_infestation, 0, list(ASSIGNMENT_SECURITY = 30), 1),
|
||||
new /datum/event_meta(EVENT_LEVEL_MAJOR, "Traders", /datum/event/traders, 0, is_one_shot = 1),
|
||||
new /datum/event_meta(EVENT_LEVEL_MAJOR, "Terror Spiders", /datum/event/spider_terror, 0, is_one_shot = 1),
|
||||
new /datum/event_meta(EVENT_LEVEL_MAJOR, "Terror Spiders", /datum/event/spider_terror, 0, list(ASSIGNMENT_SECURITY = 20), is_one_shot = 1),
|
||||
new /datum/event_meta(EVENT_LEVEL_MAJOR, "Slaughter Demon", /datum/event/spawn_slaughter, 15, is_one_shot = 1)
|
||||
)
|
||||
|
||||
|
||||
@@ -1,14 +1,14 @@
|
||||
|
||||
/datum/event/spider_terror
|
||||
announceWhen = 400
|
||||
announceWhen = 120
|
||||
var/spawncount = 1
|
||||
|
||||
/datum/event/spider_terror/setup()
|
||||
announceWhen = rand(announceWhen, announceWhen + 50)
|
||||
announceWhen = rand(announceWhen, announceWhen + 30)
|
||||
spawncount = 1
|
||||
|
||||
/datum/event/spider_infestation/announce()
|
||||
command_announcement.Announce("Confirmed outbreak of level 3 biohazard aboard [station_name()]. All personnel must contain the outbreak.", "Biohazard Alert", 'sound/effects/siren.ogg')
|
||||
/datum/event/spider_terror/announce()
|
||||
command_announcement.Announce("Confirmed outbreak of level 3 biohazard aboard [station_name()]. All personnel must contain the outbreak.", "Biohazard Alert", 'sound/effects/siren-spooky.ogg')
|
||||
|
||||
/datum/event/spider_terror/start()
|
||||
|
||||
@@ -17,23 +17,24 @@
|
||||
if(is_station_level(temp_vent.loc.z) && !temp_vent.welded)
|
||||
if(temp_vent.parent.other_atmosmch.len > 50)
|
||||
vents += temp_vent
|
||||
|
||||
var/spider_type
|
||||
var/infestation_type = pick(1, 2, 3, 4)
|
||||
var/infestation_type = pick(1, 2, 3, 4, 5)
|
||||
switch(infestation_type)
|
||||
if(1)
|
||||
spider_type = /mob/living/simple_animal/hostile/poison/terror_spider/green
|
||||
spawncount = pick(2,3)
|
||||
spawncount = 3
|
||||
if(2)
|
||||
spider_type = /mob/living/simple_animal/hostile/poison/terror_spider/white
|
||||
spawncount = 1
|
||||
spawncount = 2
|
||||
if(3)
|
||||
spider_type = /mob/living/simple_animal/hostile/poison/terror_spider/prince
|
||||
spawncount = 1
|
||||
if(4)
|
||||
spider_type = /mob/living/simple_animal/hostile/poison/terror_spider/queen
|
||||
spawncount = 1
|
||||
|
||||
if(5)
|
||||
spider_type = /mob/living/simple_animal/hostile/poison/terror_spider/mother
|
||||
spawncount = 1
|
||||
while(spawncount >= 1 && vents.len)
|
||||
var/obj/vent = pick(vents)
|
||||
var/obj/effect/spider/spiderling/terror_spiderling/S = new(vent.loc)
|
||||
|
||||
@@ -4,6 +4,13 @@
|
||||
#define MOVING_TO_TARGET 3
|
||||
#define SPINNING_COCOON 4
|
||||
|
||||
#define TS_AI_AGGRESSIVE 0
|
||||
#define TS_AI_DEFENSIVE 1
|
||||
|
||||
#define TS_DAMAGE_SIMPLE 0
|
||||
#define TS_DAMAGE_POISON 1
|
||||
#define TS_DAMAGE_BRUTE 2
|
||||
|
||||
#define TS_DESC_RED "Red - Assault"
|
||||
#define TS_DESC_GRAY "Gray - Ambush"
|
||||
#define TS_DESC_GREEN "Green - Nurse"
|
||||
|
||||
@@ -84,7 +84,7 @@
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/Web()
|
||||
var/turf/mylocation = loc
|
||||
visible_message("<span class='notice'>[src] begins to secrete a sticky substance.</span>")
|
||||
if(do_after(src, 40, target = loc))
|
||||
if(do_after(src, delay_web, target = loc))
|
||||
if(loc != mylocation)
|
||||
return
|
||||
else if(istype(loc, /turf/space))
|
||||
@@ -112,20 +112,30 @@
|
||||
if(prob(50))
|
||||
icon_state = "stickyweb2"
|
||||
|
||||
/obj/effect/spider/terrorweb/proc/DeCloakNearby()
|
||||
for(var/mob/living/simple_animal/hostile/poison/terror_spider/gray/G in view(6,src))
|
||||
if(!G.ckey && G.stat != DEAD)
|
||||
G.GrayDeCloak()
|
||||
G.Aggro()
|
||||
|
||||
/obj/effect/spider/terrorweb/CanPass(atom/movable/mover, turf/target)
|
||||
if(istype(mover, /mob/living/simple_animal/hostile/poison/terror_spider))
|
||||
return 1
|
||||
if(istype(mover, /obj/item/projectile/terrorqueenspit))
|
||||
return 1
|
||||
if(isliving(mover))
|
||||
var/mob/living/M = mover
|
||||
if(M.lying)
|
||||
return 1
|
||||
if(prob(80))
|
||||
to_chat(mover, "<span class='danger'>You get stuck in [src] for a moment.</span>")
|
||||
var/mob/living/M = mover
|
||||
M.Stun(4) // 8 seconds.
|
||||
M.Weaken(4) // 8 seconds.
|
||||
DeCloakNearby()
|
||||
if(iscarbon(mover))
|
||||
spawn(70)
|
||||
qdel(src)
|
||||
if(mover.loc == loc)
|
||||
qdel(src)
|
||||
return 1
|
||||
else
|
||||
return 0
|
||||
@@ -188,12 +198,15 @@
|
||||
if(iscarbon(L))
|
||||
regen_points += regen_points_per_kill
|
||||
fed++
|
||||
visible_message("<span class='danger'>[src] sticks a proboscis into [L] and sucks a viscous substance out.</span>")
|
||||
to_chat(src, "<span class='notice'>You feel invigorated!</span>")
|
||||
else
|
||||
visible_message("<span class='danger'>[src] wraps [L] in a web.</span>")
|
||||
large_cocoon = 1
|
||||
last_cocoon_object = 0
|
||||
L.loc = C
|
||||
C.pixel_x = L.pixel_x
|
||||
C.pixel_y = L.pixel_y
|
||||
visible_message("<span class='danger'>[src] sticks a proboscis into [L] and sucks a viscous substance out.</span>")
|
||||
break
|
||||
if(large_cocoon)
|
||||
C.icon_state = pick("cocoon_large1","cocoon_large2","cocoon_large3")
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
name = "Black Terror spider"
|
||||
desc = "An ominous-looking spider, black as the darkest night. It has merciless eyes, and a blood-red hourglass pattern on its back."
|
||||
spider_role_summary = "Hit-and-run attacker with extremely venomous bite."
|
||||
ai_target_method = TS_DAMAGE_POISON
|
||||
|
||||
icon_state = "terror_widow"
|
||||
icon_living = "terror_widow"
|
||||
@@ -37,3 +38,10 @@
|
||||
else
|
||||
visible_message("<span class='danger'>[src] bites [target], but cannot inject venom into their [inject_target]!</span>")
|
||||
L.attack_animal(src)
|
||||
if(!ckey && (!(target in enemies) || L.reagents.has_reagent("terror_black_toxin", 60)))
|
||||
step_away(src,L)
|
||||
step_away(src,L)
|
||||
LoseTarget()
|
||||
for(var/i in 0 to 3)
|
||||
step_away(src, L)
|
||||
visible_message("<span class='notice'>[src] warily eyes [L] from a distance.</span>")
|
||||
@@ -0,0 +1,92 @@
|
||||
// --------------------------------------------------------------------------------
|
||||
// ----------------- TERROR SPIDERS: T5 EMPRESS OF TERROR -------------------------
|
||||
// --------------------------------------------------------------------------------
|
||||
// -------------: ROLE: ruling over planets of uncountable spiders, like Xenomorph Empresses.
|
||||
// -------------: AI: none - this is strictly adminspawn-only and intended for RP events, coder testing, and teaching people 'how to queen'
|
||||
// -------------: SPECIAL: Lay Eggs ability that allows laying queen-level eggs.
|
||||
// -------------: TO FIGHT IT: run away screaming?
|
||||
// -------------: SPRITES FROM: FoS, http://nanotrasen.se/phpBB3/memberlist.php?mode=viewprofile&u=386
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/queen/empress
|
||||
name = "Empress of Terror"
|
||||
desc = "The unholy offspring of spiders, nightmares, and lovecraft fiction."
|
||||
spider_role_summary = "Adminbus spider"
|
||||
ai_target_method = TS_DAMAGE_SIMPLE
|
||||
maxHealth = 1000
|
||||
health = 1000
|
||||
melee_damage_lower = 30
|
||||
melee_damage_upper = 60
|
||||
move_to_delay = 5
|
||||
ventcrawler = 1
|
||||
idle_ventcrawl_chance = 0
|
||||
ai_playercontrol_allowtype = 0
|
||||
ai_type = TS_AI_AGGRESSIVE
|
||||
rapid = 1
|
||||
canlay = 1000
|
||||
spider_tier = TS_TIER_5
|
||||
var/datum/action/innate/terrorspider/queen/empress/empresslings/empresslings_action
|
||||
atmos_requirements = list("min_oxy" = 0, "max_oxy" = 0, "min_tox" = 0, "max_tox" = 0, "min_co2" = 0, "max_co2" = 0, "min_n2" = 0, "max_n2" = 0)
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/queen/empress/handle_automated_action()
|
||||
return
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/queen/empress/NestMode()
|
||||
..()
|
||||
queeneggs_action.button.name = "Empress Eggs"
|
||||
queenfakelings_action.button.name = "Empress Lings"
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/queen/empress/LayQueenEggs()
|
||||
var/eggtype = input("What kind of eggs?") as null|anything in list(TS_DESC_QUEEN, TS_DESC_MOTHER, TS_DESC_PRINCE, TS_DESC_RED, TS_DESC_GRAY, TS_DESC_GREEN, TS_DESC_BLACK, TS_DESC_PURPLE, TS_DESC_WHITE)
|
||||
var/numlings = input("How many in the batch?") as null|anything in list(1, 2, 3, 4, 5, 10, 15, 20, 30, 40, 50)
|
||||
if(eggtype == null || numlings == null)
|
||||
to_chat(src, "<span class='danger'>Cancelled.</span>")
|
||||
return
|
||||
switch(eggtype)
|
||||
if(TS_DESC_RED)
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/red,numlings,1)
|
||||
if(TS_DESC_GRAY)
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/gray,numlings,1)
|
||||
if(TS_DESC_GREEN)
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/green,numlings,1)
|
||||
if(TS_DESC_BLACK)
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/black,numlings,1)
|
||||
if(TS_DESC_PURPLE)
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/purple,numlings,0)
|
||||
if(TS_DESC_WHITE)
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/white,numlings,0)
|
||||
if(TS_DESC_PRINCE)
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/prince,numlings,1)
|
||||
if(TS_DESC_MOTHER)
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/mother,numlings,1)
|
||||
if(TS_DESC_QUEEN)
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/queen,numlings,1)
|
||||
else
|
||||
to_chat(src, "<span class='danger'>Unrecognized egg type.</span>")
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/queen/empress/QueenFakeLings()
|
||||
var/numlings = input("How many?") as null|anything in list(10, 20, 30, 40, 50)
|
||||
var/sbpc = input("%chance to be stillborn?") as null|anything in list(0, 25, 50, 75, 100)
|
||||
for(var/i=0, i<numlings, i++)
|
||||
var/obj/effect/spider/spiderling/terror_spiderling/S = new /obj/effect/spider/spiderling/terror_spiderling(get_turf(src))
|
||||
S.grow_as = pick(/mob/living/simple_animal/hostile/poison/terror_spider/red, \
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/gray, \
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/green, \
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/white, \
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/black)
|
||||
S.spider_myqueen = spider_myqueen
|
||||
if(prob(sbpc))
|
||||
S.stillborn = 1
|
||||
if(spider_growinstantly)
|
||||
S.amount_grown = 250
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/queen/empress/proc/EraseBrood()
|
||||
for(var/mob/living/simple_animal/hostile/poison/terror_spider/T in ts_spiderlist)
|
||||
if(T.spider_tier < spider_tier)
|
||||
T.degenerate = 1
|
||||
to_chat(T, "<span class='userdanger'>Through the hivemind, the raw power of [src] floods into your body, burning it from the inside out!</span>")
|
||||
for(var/obj/effect/spider/eggcluster/terror_eggcluster/T in ts_egg_list)
|
||||
qdel(T)
|
||||
for(var/obj/effect/spider/spiderling/terror_spiderling/T in ts_spiderling_list)
|
||||
T.stillborn = 1
|
||||
to_chat(src, "<span class='userdanger'>Brood will die off shortly.</span>")
|
||||
|
||||
@@ -2,24 +2,30 @@
|
||||
// --------------------------------------------------------------------------------
|
||||
// ----------------- TERROR SPIDERS: T1 GRAY TERROR -------------------------------
|
||||
// --------------------------------------------------------------------------------
|
||||
// -------------: ROLE: fast, weak terror spider
|
||||
// -------------: SPECIAL: silences targets
|
||||
// -------------: TO FIGHT IT: shoot it!
|
||||
// -------------: ROLE: ambusher
|
||||
// -------------: AI: hides in vents, emerges when prey is near to kill it, then hides again. Intended to scare normal crew.
|
||||
// -------------: SPECIAL: invisible when on top of a vent, emerges when prey approaches or gets trapped in webs. Bite silences targets.
|
||||
// -------------: TO FIGHT IT: shoot it through a window, or make it regret ambushing you
|
||||
// -------------: SPRITES FROM: FoS, http://nanotrasen.se/phpBB3/memberlist.php?mode=viewprofile&u=386
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/gray
|
||||
name = "Gray Terror spider"
|
||||
desc = "An ominous-looking gray spider, it seems jittery."
|
||||
spider_role_summary = "Fast-moving but weak spider."
|
||||
desc = "An ominous-looking gray spider. It twitches occasionally, always seeming ready to pounce."
|
||||
spider_role_summary = "Stealth spider that ambushes weak humans from vents."
|
||||
ai_target_method = TS_DAMAGE_BRUTE
|
||||
icon_state = "terror_gray"
|
||||
icon_living = "terror_gray"
|
||||
icon_dead = "terror_gray_dead"
|
||||
maxHealth = 120 // same health as hunter spider, aka, pretty weak.. but silences its targets
|
||||
maxHealth = 120 // same health as hunter spider, aka, pretty weak.. but its almost invisible.
|
||||
health = 120
|
||||
melee_damage_lower = 10
|
||||
melee_damage_upper = 20
|
||||
move_to_delay = 5 // normal speed
|
||||
regen_points_per_hp = 2 // 50% higher regen speed
|
||||
move_to_delay = 5 // slightly faster than normal
|
||||
stat_attack = 1 // ensures they will target people in crit, too!
|
||||
wander = 0 // wandering defeats the purpose of stealth
|
||||
idle_vision_range = 3 // very low idle vision range
|
||||
delay_web = 20 // double speed
|
||||
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/gray/spider_specialattack(mob/living/carbon/human/L, poisonable)
|
||||
@@ -35,4 +41,102 @@
|
||||
visible_message("<span class='danger'>[src] buries grey fangs deep into the [inject_target] of [target]!</span>")
|
||||
else
|
||||
visible_message("<span class='danger'>[src] bites [target], but cannot inject venom into their [inject_target]!</span>")
|
||||
L.attack_animal(src)
|
||||
L.attack_animal(src)
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/gray/adjustBruteLoss(damage)
|
||||
..(damage)
|
||||
if(invisibility > 0)
|
||||
GrayDeCloak()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/gray/adjustFireLoss(damage)
|
||||
..(damage)
|
||||
if(invisibility > 0)
|
||||
GrayDeCloak()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/gray/Aggro()
|
||||
GrayDeCloak()
|
||||
..()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/gray/AttackingTarget()
|
||||
if(invisibility > 0)
|
||||
GrayDeCloak()
|
||||
else
|
||||
..()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/GrayCloak()
|
||||
visible_message("<span class='notice'>[src] hides in the vent.</span>")
|
||||
invisibility = SEE_INVISIBLE_LEVEL_ONE
|
||||
icon_state = "terror_gray_cloaked"
|
||||
icon_living = "terror_gray_cloaked"
|
||||
if(!ckey)
|
||||
vision_range = 3
|
||||
idle_vision_range = 3
|
||||
// Bugged, does not work yet. Also spams webs. Also doesn't look great. But... planned.
|
||||
move_to_delay = 15 // while invisible, slow.
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/GrayDeCloak()
|
||||
invisibility = 0
|
||||
icon_state = "terror_gray"
|
||||
icon_living = "terror_gray"
|
||||
vision_range = 9
|
||||
idle_vision_range = 9
|
||||
move_to_delay = 5
|
||||
prob_ai_hides_in_vents = 10
|
||||
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/gray/spider_special_action()
|
||||
if(prob(prob_ai_hides_in_vents))
|
||||
var/obj/machinery/atmospherics/unary/vent_pump/e = locate() in get_turf(src)
|
||||
if(e)
|
||||
if(!e.welded || spider_awaymission)
|
||||
if(invisibility != SEE_INVISIBLE_LEVEL_ONE) // aka: 35. ghosts have 15 with no darkness, 60 with darkness. Weird...
|
||||
var/list/g_turfs_webbed = ListWebbedTurfs()
|
||||
var/webcount = g_turfs_webbed.len
|
||||
if(webcount >= 4)
|
||||
// if there are already at least 4 webs around us, then we have a good web setup already. Cloak.
|
||||
GrayCloak()
|
||||
// I wonder if we should settle down here forever?
|
||||
var/foundqueen = 0
|
||||
for(var/mob/living/H in view(src, 10))
|
||||
if(istype(H, /mob/living/simple_animal/hostile/poison/terror_spider/queen))
|
||||
foundqueen = 1
|
||||
break
|
||||
if(!foundqueen)
|
||||
var/list/g_turfs_visible = ListVisibleTurfs()
|
||||
if(g_turfs_visible.len >= 12)
|
||||
// So long as the room isn't tiny, and it has no queen in it, sure, settle there
|
||||
// since we are settled now, disable most AI behaviors so we don't waste CPU.
|
||||
ai_ventcrawls = 0
|
||||
ai_spins_webs = 0
|
||||
ai_break_lights = 0
|
||||
prob_ai_hides_in_vents = 3
|
||||
visible_message("<span class='notice'>[src] finishes setting up its trap in [get_area(src)].</span>")
|
||||
else
|
||||
var/list/g_turfs_valid = ListValidTurfs()
|
||||
var/turfcount = g_turfs_valid.len
|
||||
if(turfcount == 0)
|
||||
// if there is literally nowhere else we could put a web, cloak.
|
||||
GrayCloak()
|
||||
else
|
||||
// otherwise, pick one of the valid turfs with no web to create a web there.
|
||||
new /obj/effect/spider/terrorweb(pick(g_turfs_valid))
|
||||
visible_message("<span class='notice'>[src] spins a web.</span>")
|
||||
else
|
||||
if(invisibility == SEE_INVISIBLE_LEVEL_ONE)
|
||||
// if our vent is welded, decloak
|
||||
GrayDeCloak()
|
||||
else
|
||||
if(invisibility == SEE_INVISIBLE_LEVEL_ONE)
|
||||
// if there is no vent under us, and we are cloaked, decloak
|
||||
GrayDeCloak()
|
||||
var/vdistance = 99
|
||||
var/temp_vent = null
|
||||
for(var/obj/machinery/atmospherics/unary/vent_pump/v in view(7,src))
|
||||
if(!v.welded)
|
||||
if(get_dist(src,v) < vdistance)
|
||||
temp_vent = v
|
||||
vdistance = get_dist(src,v)
|
||||
if(temp_vent)
|
||||
if(get_dist(src,temp_vent) > 0 && get_dist(src,temp_vent) < 5)
|
||||
step_to(src,temp_vent)
|
||||
// if you're bumped off your vent, try to get back to it
|
||||
@@ -3,6 +3,7 @@
|
||||
// ----------------- TERROR SPIDERS: T1 GREEN TERROR ------------------------------
|
||||
// --------------------------------------------------------------------------------
|
||||
// -------------: ROLE: reproduction
|
||||
// -------------: AI: after it kills you, it webs you and lays new terror eggs on your body
|
||||
// -------------: SPECIAL: can also create webs, web normal objects, etc
|
||||
// -------------: TO FIGHT IT: kill it however you like - just don't die to it!
|
||||
// -------------: SPRITES FROM: FoS, http://nanotrasen.se/phpBB3/memberlist.php?mode=viewprofile&u=386
|
||||
@@ -11,7 +12,7 @@
|
||||
name = "Green Terror spider"
|
||||
desc = "An ominous-looking green spider. It has a small egg-sac attached to it, and dried blood stains on its carapace."
|
||||
spider_role_summary = "Average melee spider that webs its victims and lays more spider eggs"
|
||||
|
||||
ai_target_method = TS_DAMAGE_BRUTE
|
||||
icon_state = "terror_green"
|
||||
icon_living = "terror_green"
|
||||
icon_dead = "terror_green_dead"
|
||||
@@ -20,7 +21,6 @@
|
||||
melee_damage_lower = 10
|
||||
melee_damage_upper = 20
|
||||
var/feedings_to_lay = 2
|
||||
|
||||
var/datum/action/innate/terrorspider/greeneggs/greeneggs_action
|
||||
|
||||
|
||||
@@ -34,7 +34,7 @@
|
||||
if(E)
|
||||
to_chat(src, "<span class='notice'>There is already a cluster of eggs here!</span>")
|
||||
else if(fed < feedings_to_lay)
|
||||
to_chat(src, "<span class='warning'>You must wrap more prey before you can do this!</span>")
|
||||
to_chat(src, "<span class='warning'>You must wrap more humanoid prey before you can do this!</span>")
|
||||
else
|
||||
visible_message("<span class='notice'>[src] begins to lay a cluster of eggs.</span>")
|
||||
if(prob(33))
|
||||
@@ -45,6 +45,43 @@
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/green, 1, 1)
|
||||
fed -= feedings_to_lay
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/green/spider_special_action()
|
||||
if(cocoon_target)
|
||||
if(get_dist(src, cocoon_target) <= 1)
|
||||
spider_steps_taken = 0
|
||||
DoWrap()
|
||||
else
|
||||
if(spider_steps_taken > spider_max_steps)
|
||||
spider_steps_taken = 0
|
||||
cocoon_target = null
|
||||
busy = 0
|
||||
stop_automated_movement = 0
|
||||
else
|
||||
spider_steps_taken++
|
||||
CreatePath(cocoon_target)
|
||||
step_to(src,cocoon_target)
|
||||
if(spider_debug)
|
||||
visible_message("<span class='notice'>[src] moves towards [cocoon_target] to cocoon it.</span>")
|
||||
else if(fed >= feedings_to_lay)
|
||||
DoLayGreenEggs()
|
||||
else if(world.time > (last_cocoon_object + freq_cocoon_object))
|
||||
last_cocoon_object = world.time
|
||||
var/list/can_see = view(src, 10)
|
||||
for(var/mob/living/C in can_see)
|
||||
if(C.stat == DEAD && !isterrorspider(C) && !C.anchored)
|
||||
spider_steps_taken = 0
|
||||
cocoon_target = C
|
||||
return
|
||||
for(var/obj/O in can_see)
|
||||
if(O.anchored)
|
||||
continue
|
||||
if(istype(O, /obj/item) || istype(O, /obj/structure) || istype(O, /obj/machinery))
|
||||
if(!istype(O, /obj/item/weapon/paper))
|
||||
cocoon_target = O
|
||||
stop_automated_movement = 1
|
||||
spider_steps_taken = 0
|
||||
return
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/green/spider_specialattack(mob/living/carbon/human/L, poisonable)
|
||||
if(!poisonable)
|
||||
..()
|
||||
|
||||
@@ -18,6 +18,21 @@
|
||||
hsline += " AI "
|
||||
to_chat(src,hsline)
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/SetHiveCommand(set_ai, set_ventcrawl)
|
||||
var/numspiders = 0
|
||||
for(var/mob/living/simple_animal/hostile/poison/terror_spider/T in ts_spiderlist)
|
||||
if(spider_awaymission && !T.spider_awaymission)
|
||||
continue
|
||||
else if(!spider_awaymission && T.spider_awaymission)
|
||||
continue
|
||||
numspiders += 1
|
||||
if(spider_tier >= T.spider_tier)
|
||||
if(T.ai_type != set_ai)
|
||||
T.ai_type = set_ai
|
||||
if(T.idle_ventcrawl_chance != set_ventcrawl)
|
||||
T.idle_ventcrawl_chance = set_ventcrawl
|
||||
return numspiders
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/CountSpiders()
|
||||
var/numspiders = 0
|
||||
for(var/mob/living/simple_animal/hostile/poison/terror_spider/T in ts_spiderlist)
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
// ----------------- TERROR SPIDERS: T3 MOTHER OF TERROR --------------------------
|
||||
// --------------------------------------------------------------------------------
|
||||
// -------------: ROLE: living schmuck bait
|
||||
// -------------: AI: no special ai
|
||||
// -------------: SPECIAL: spawns an ungodly number of spiderlings when killed
|
||||
// -------------: TO FIGHT IT: don't! Just leave it alone! It is harmless by itself... but god help you if you aggro it.
|
||||
// -------------: SPRITES FROM: FoS, http://nanotrasen.se/phpBB3/memberlist.php?mode=viewprofile&u=386
|
||||
@@ -11,7 +12,7 @@
|
||||
name = "Mother of Terror spider"
|
||||
desc = "An enormous spider. Hundreds of tiny spiderlings are crawling all over it. Their beady little eyes all stare at you. The horror!"
|
||||
spider_role_summary = "Schmuck bait. Extremely weak in combat, but spawns many spiderlings when it dies."
|
||||
|
||||
ai_target_method = TS_DAMAGE_SIMPLE
|
||||
icon_state = "terror_gray2"
|
||||
icon_living = "terror_gray2"
|
||||
icon_dead = "terror_gray2_dead"
|
||||
@@ -20,10 +21,9 @@
|
||||
melee_damage_lower = 10
|
||||
melee_damage_upper = 20
|
||||
move_to_delay = 5
|
||||
|
||||
idle_ventcrawl_chance = 5
|
||||
spider_tier = TS_TIER_3
|
||||
spider_opens_doors = 2
|
||||
|
||||
var/canspawn = 1
|
||||
|
||||
|
||||
@@ -37,6 +37,7 @@
|
||||
S.stillborn = 1
|
||||
else if(prob(10))
|
||||
S.grow_as = pick(/mob/living/simple_animal/hostile/poison/terror_spider/black, /mob/living/simple_animal/hostile/poison/terror_spider/green)
|
||||
S.amount_grown = 50 // double speed growth
|
||||
visible_message("<span class='userdanger'>[src] breaks apart, the many spiders on its back scurrying everywhere!</span>")
|
||||
degenerate = 1
|
||||
..()
|
||||
|
||||
@@ -12,26 +12,23 @@
|
||||
name = "Prince of Terror spider"
|
||||
desc = "An enormous, terrifying spider. It looks like it is judging everything it sees. Its hide seems armored, and it bears the scars of many battles."
|
||||
spider_role_summary = "Miniboss terror spider. Lightning bruiser."
|
||||
|
||||
ai_target_method = TS_DAMAGE_BRUTE
|
||||
icon_state = "terror_allblack"
|
||||
icon_living = "terror_allblack"
|
||||
icon_dead = "terror_allblack_dead"
|
||||
|
||||
maxHealth = 600 // 30 laser shots
|
||||
health = 600
|
||||
regen_points_per_hp = 6 // double the normal - IE halved regen speed
|
||||
|
||||
melee_damage_lower = 20
|
||||
melee_damage_upper = 30
|
||||
move_to_delay = 4 // faster than normal
|
||||
|
||||
ventcrawler = 0
|
||||
ai_ventcrawls = 0
|
||||
environment_smash = 3
|
||||
|
||||
loot = list(/obj/item/clothing/accessory/medal)
|
||||
idle_ventcrawl_chance = 0
|
||||
spider_tier = TS_TIER_3
|
||||
spider_opens_doors = 2
|
||||
|
||||
var/datum/action/innate/terrorspider/princesmash/princesmash_action
|
||||
|
||||
|
||||
@@ -40,6 +37,12 @@
|
||||
princesmash_action = new()
|
||||
princesmash_action.Grant(src)
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/prince/death(gibbed)
|
||||
if(!hasdied)
|
||||
if(spider_uo71)
|
||||
UnlockBlastDoors("UO71_SciStorage")
|
||||
..()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/prince/spider_specialattack(mob/living/carbon/human/L)
|
||||
if(prob(15))
|
||||
visible_message("<span class='danger'>[src] rams into [L], knocking them to the floor!</span>")
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
// ----------------- TERROR SPIDERS: T2 PURPLE TERROR -----------------------------
|
||||
// --------------------------------------------------------------------------------
|
||||
// -------------: ROLE: guarding queen nests
|
||||
// -------------: AI: dies if too far from queen
|
||||
// -------------: SPECIAL: chance to stun on hit
|
||||
// -------------: TO FIGHT IT: shoot it from range, bring friends!
|
||||
// -------------: SPRITES FROM: FoS, http://nanotrasen.se/phpBB3/memberlist.php?mode=viewprofile&u=386
|
||||
@@ -11,7 +12,7 @@
|
||||
name = "Purple Terror spider"
|
||||
desc = "An ominous-looking purple spider. It looks about warily, as if waiting for something."
|
||||
spider_role_summary = "Guards the nest of the Queen of Terror."
|
||||
|
||||
ai_target_method = TS_DAMAGE_BRUTE
|
||||
icon_state = "terror_purple"
|
||||
icon_living = "terror_purple"
|
||||
icon_dead = "terror_purple_dead"
|
||||
@@ -20,17 +21,28 @@
|
||||
melee_damage_lower = 15
|
||||
melee_damage_upper = 25
|
||||
move_to_delay = 6
|
||||
|
||||
spider_tier = TS_TIER_2
|
||||
spider_opens_doors = 2
|
||||
|
||||
ventcrawler = 0
|
||||
ai_ventcrawls = 0
|
||||
environment_smash = 3
|
||||
|
||||
idle_ventcrawl_chance = 0 // stick to the queen!
|
||||
var/dcheck_counter = 0
|
||||
var/queen_visible = 1
|
||||
var/cycles_noqueen = 0
|
||||
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/purple/death(gibbed)
|
||||
if(spider_myqueen)
|
||||
var/mob/living/simple_animal/hostile/poison/terror_spider/queen/Q = spider_myqueen
|
||||
if(Q.stat != DEAD && !Q.ckey)
|
||||
if(get_dist(src,Q) > 20)
|
||||
if(!degenerate && !Q.degenerate)
|
||||
degenerate = 1
|
||||
Q.DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/purple,1,0)
|
||||
visible_message("<span class='notice'>[src] chitters in the direction of [Q]!</span>")
|
||||
. = ..()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/purple/spider_specialattack(mob/living/carbon/human/L, poisonable)
|
||||
if(cycles_noqueen < 6 && prob(10))
|
||||
visible_message("<span class='danger'>[src] rams into [L], knocking them to the floor!</span>")
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
// ----------------- TERROR SPIDERS: T4 QUEEN OF TERROR ---------------------------
|
||||
// --------------------------------------------------------------------------------
|
||||
// -------------: ROLE: gamma-level threat to the whole station, like a blob
|
||||
// -------------: AI: builds a nest, lays many eggs, attempts to take over the station
|
||||
// -------------: SPECIAL: spins webs, breaks lights, breaks cameras, webs objects, lays eggs, commands other spiders...
|
||||
// -------------: TO FIGHT IT: bring an army, and take no prisoners. Mechs and/or decloner guns are a very good idea.
|
||||
// -------------: SPRITES FROM: FoS, http://nanotrasen.se/phpBB3/memberlist.php?mode=viewprofile&u=386
|
||||
@@ -11,7 +12,7 @@
|
||||
name = "Queen of Terror spider"
|
||||
desc = "An enormous, terrifying spider. Its egg sac is almost as big as its body, and teeming with spider eggs!"
|
||||
spider_role_summary = "Commander of the spider forces. Lays eggs, directs the brood."
|
||||
|
||||
ai_target_method = TS_DAMAGE_SIMPLE
|
||||
icon_state = "terror_queen"
|
||||
icon_living = "terror_queen"
|
||||
icon_dead = "terror_queen_dead"
|
||||
@@ -29,22 +30,19 @@
|
||||
var/neststep = 0
|
||||
var/hasnested = 0
|
||||
var/spider_max_per_nest = 20 // above this, queen stops spawning more, and declares war.
|
||||
|
||||
var/canlay = 0 // main counter for egg-laying ability! # = num uses, incremented at intervals
|
||||
var/eggslaid = 0
|
||||
var/spider_can_fakelings = 3 // spawns defective spiderlings that don't grow up, used to freak out crew, atmosphere
|
||||
|
||||
idle_ventcrawl_chance = 0
|
||||
force_threshold = 18 // outright immune to anything of force under 18, this means welders can't hurt it, only guns can
|
||||
|
||||
ranged = 1
|
||||
retreat_distance = 5
|
||||
minimum_distance = 5
|
||||
projectilesound = 'sound/weapons/pierce.ogg'
|
||||
projectiletype = /obj/item/projectile/terrorqueenspit
|
||||
|
||||
spider_tier = TS_TIER_4
|
||||
spider_opens_doors = 2
|
||||
loot = list(/obj/item/clothing/accessory/medal)
|
||||
|
||||
var/datum/action/innate/terrorspider/queen/queennest/queennest_action
|
||||
var/datum/action/innate/terrorspider/queen/queensense/queensense_action
|
||||
var/datum/action/innate/terrorspider/queen/queeneggs/queeneggs_action
|
||||
@@ -65,10 +63,15 @@
|
||||
if(.) // if mob is NOT dead
|
||||
if(ckey && canlay < 12 && hasnested) // max 12 eggs worth stored at any one time, realistically that's tons.
|
||||
if(world.time > (spider_lastspawn + spider_spawnfrequency))
|
||||
canlay++
|
||||
if(eggslaid >= 20)
|
||||
canlay += 3
|
||||
else if(eggslaid >= 10)
|
||||
canlay += 2
|
||||
else
|
||||
canlay++
|
||||
spider_lastspawn = world.time
|
||||
if(canlay == 1)
|
||||
to_chat(src, "<span class='notice'>You are able to lay eggs again.</span>")
|
||||
to_chat(src, "<span class='notice'>You have an egg available to lay.</span>")
|
||||
else if(canlay == 12)
|
||||
to_chat(src, "<span class='notice'>You have [canlay] eggs available to lay. You won't grow any more eggs until you lay some of your existing ones.</span>")
|
||||
else
|
||||
@@ -76,6 +79,9 @@
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/queen/death(gibbed)
|
||||
if(!hasdied)
|
||||
SetHiveCommand(0, 15) // Hive becomes very aggressive.
|
||||
if(spider_uo71)
|
||||
UnlockBlastDoors("UO71_Caves")
|
||||
// When a queen dies, so do her player-controlled purple-type guardians. Intended as a motivator for purples to ensure they guard her.
|
||||
for(var/mob/living/simple_animal/hostile/poison/terror_spider/purple/P in ts_spiderlist)
|
||||
if(ckey)
|
||||
@@ -84,6 +90,131 @@
|
||||
P.degenerate = 1
|
||||
..()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/queen/Retaliate()
|
||||
..()
|
||||
for(var/mob/living/simple_animal/hostile/poison/terror_spider/T in ts_spiderlist)
|
||||
T.enemies |= enemies
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/queen/handle_automated_action()
|
||||
..()
|
||||
if(!stat && !ckey && AIStatus != AI_OFF && !target && !path_to_vent)
|
||||
switch(neststep)
|
||||
if(0)
|
||||
// we have no nest :(
|
||||
var/ok_to_nest = 1
|
||||
var/area/new_area = get_area(loc)
|
||||
if(new_area)
|
||||
if(findtext(new_area.name, "hall"))
|
||||
ok_to_nest = 0
|
||||
// nesting in a hallway would be very stupid - crew would find and kill you almost instantly
|
||||
var/numhostiles = 0
|
||||
for(var/mob/living/H in oview(10, src))
|
||||
if(!istype(H, /mob/living/simple_animal/hostile/poison/terror_spider))
|
||||
if(H.stat != DEAD)
|
||||
numhostiles += 1
|
||||
// nesting RIGHT NEXT TO SOMEONE is even worse
|
||||
if(numhostiles > 0)
|
||||
ok_to_nest = 0
|
||||
var/vdistance = 99
|
||||
for(var/obj/machinery/atmospherics/unary/vent_pump/v in view(10, src))
|
||||
if(!v.welded)
|
||||
if(get_dist(src, v) < vdistance)
|
||||
entry_vent = v
|
||||
vdistance = get_dist(src, v)
|
||||
if(!entry_vent)
|
||||
ok_to_nest = 0
|
||||
// don't nest somewhere with no vent - your brood won't be able to get out!
|
||||
if(ok_to_nest && entry_vent)
|
||||
nest_vent = entry_vent
|
||||
neststep = 1
|
||||
visible_message("<span class='danger'>\The [src] settles down, starting to build a nest.</span>")
|
||||
else if(entry_vent)
|
||||
if(!path_to_vent)
|
||||
visible_message("<span class='danger'>\The [src] looks around warily - then seeks a better nesting ground.</span>")
|
||||
path_to_vent = 1
|
||||
else
|
||||
visible_message("<span class='danger'>\The [src] looks around, searching for the vent that should be there, but isn't. A bluespace portal forms on her, and she is gone.</span>")
|
||||
qdel(src)
|
||||
new /obj/effect/portal(get_turf(loc))
|
||||
if(1)
|
||||
if(world.time > (lastnestsetup + nestfrequency))
|
||||
lastnestsetup = world.time
|
||||
neststep = 2
|
||||
NestMode()
|
||||
if(2)
|
||||
if(world.time > (lastnestsetup + nestfrequency))
|
||||
lastnestsetup = world.time
|
||||
spider_lastspawn = world.time
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/purple, 2, 0)
|
||||
neststep = 3
|
||||
if(3)
|
||||
if(world.time > (spider_lastspawn + spider_spawnfrequency))
|
||||
if(prob(20))
|
||||
var/obj/effect/spider/eggcluster/terror_eggcluster/N = locate() in get_turf(src)
|
||||
if(!N)
|
||||
spider_lastspawn = world.time
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/green, 2, 0)
|
||||
neststep = 4
|
||||
if(4)
|
||||
if(world.time > (spider_lastspawn + spider_spawnfrequency))
|
||||
if(prob(20))
|
||||
var/obj/effect/spider/eggcluster/terror_eggcluster/N = locate() in get_turf(src)
|
||||
if(!N)
|
||||
if(!spider_awaymission)
|
||||
QueenFakeLings()
|
||||
spider_lastspawn = world.time
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/red, 2, 1)
|
||||
neststep = 5
|
||||
if(5)
|
||||
if(world.time > (spider_lastspawn + spider_spawnfrequency))
|
||||
if(prob(20))
|
||||
var/obj/effect/spider/eggcluster/terror_eggcluster/N = locate() in get_turf(src)
|
||||
if(!N)
|
||||
if(!spider_awaymission)
|
||||
QueenFakeLings()
|
||||
spider_lastspawn = world.time
|
||||
if(prob(33))
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/gray, 2, 1)
|
||||
else if(prob(50))
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/red, 2, 1)
|
||||
else
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/green, 2, 1)
|
||||
var/spidercount = CountSpiders()
|
||||
if(spidercount >= spider_max_per_nest) // station overwhelmed!
|
||||
neststep = 6
|
||||
if(6)
|
||||
if(world.time > (spider_lastspawn + spider_spawnfrequency))
|
||||
spider_lastspawn = world.time
|
||||
// go hostile, EXTERMINATE MODE.
|
||||
SetHiveCommand(0, 15) // AI=0 (attack everyone), ventcrawl=15%/tick
|
||||
var/numspiders = CountSpiders()
|
||||
if(numspiders < spider_max_per_nest)
|
||||
if(prob(33))
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/black, 2, 1)
|
||||
else if(prob(50))
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/red, 2, 0)
|
||||
else
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/green, 2, 1)
|
||||
else if(spider_awaymission)
|
||||
neststep = 7
|
||||
spider_spawnfrequency = spider_spawnfrequency_stable
|
||||
// if we're an away mission queen... don't keep spawning spiders at high rates. Away team should have a chance.
|
||||
if(7)
|
||||
if(world.time > (spider_lastspawn + spider_spawnfrequency))
|
||||
spider_lastspawn = world.time
|
||||
var/numspiders = CountSpiders()
|
||||
if(numspiders < spider_max_per_nest)
|
||||
// someone is killing my children...
|
||||
if(prob(25))
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/black, 2, 1)
|
||||
else if(prob(33))
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/red, 2, 0)
|
||||
else if(prob(50))
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/green, 2, 1)
|
||||
else
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/purple, 2, 0)
|
||||
neststep = 6
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/queen/proc/NestMode()
|
||||
queeneggs_action = new()
|
||||
queeneggs_action.Grant(src)
|
||||
@@ -94,6 +225,7 @@
|
||||
queennest_action.Remove(src)
|
||||
hasnested = 1
|
||||
ventcrawler = 0
|
||||
ai_ventcrawls = 0
|
||||
environment_smash = 3
|
||||
DoQueenScreech(8, 100, 8, 100)
|
||||
MassFlicker()
|
||||
@@ -159,8 +291,8 @@
|
||||
if(eggtype == null || numlings == null)
|
||||
to_chat(src, "<span class='danger'>Cancelled.</span>")
|
||||
return
|
||||
//spider_lastspawn = world.time // don't think we actually need this, if queen is laying manually canlay controls her rate.
|
||||
canlay -= numlings
|
||||
eggslaid += numlings
|
||||
if(eggtype == TS_DESC_RED)
|
||||
DoLayTerrorEggs(/mob/living/simple_animal/hostile/poison/terror_spider/red, numlings, 1)
|
||||
else if(eggtype == TS_DESC_GRAY)
|
||||
@@ -210,5 +342,5 @@
|
||||
if(L.reagents)
|
||||
if(L.can_inject(null, 0, "chest", 0))
|
||||
L.reagents.add_reagent("terror_queen_toxin", 15)
|
||||
if(!istype(L, /mob/living/simple_animal/hostile/poison/terror_spider))
|
||||
if(!isterrorspider(L))
|
||||
L.adjustToxLoss(30)
|
||||
@@ -12,9 +12,8 @@
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/red
|
||||
name = "Red Terror spider"
|
||||
desc = "An ominous-looking red spider, it has eight beady red eyes, and nasty, big, pointy fangs! It looks like it has a vicious streak a mile wide."
|
||||
|
||||
spider_role_summary = "High health, high damage, very slow, melee juggernaut"
|
||||
|
||||
ai_target_method = TS_DAMAGE_BRUTE
|
||||
icon_state = "terror_red"
|
||||
icon_living = "terror_red"
|
||||
icon_dead = "terror_red_dead"
|
||||
|
||||
@@ -14,6 +14,7 @@
|
||||
faction = list("terrorspiders")
|
||||
var/spider_myqueen = null
|
||||
var/use_vents = 1
|
||||
var/list/enemies = list()
|
||||
|
||||
/obj/effect/spider/spiderling/terror_spiderling/New()
|
||||
..()
|
||||
@@ -91,6 +92,7 @@
|
||||
S.faction = faction
|
||||
S.spider_myqueen = spider_myqueen
|
||||
S.master_commander = master_commander
|
||||
S.enemies = enemies
|
||||
qdel(src)
|
||||
|
||||
// --------------------------------------------------------------------------------
|
||||
@@ -106,6 +108,7 @@
|
||||
C.faction = faction
|
||||
C.spider_myqueen = spider_myqueen
|
||||
C.master_commander = master_commander
|
||||
C.enemies = enemies
|
||||
if(spider_growinstantly)
|
||||
C.amount_grown = 250
|
||||
C.spider_growinstantly = 1
|
||||
@@ -122,6 +125,7 @@
|
||||
var/spiderling_type = null
|
||||
var/spiderling_number = 1
|
||||
var/spiderling_ventcrawl = 1
|
||||
var/list/enemies = list()
|
||||
|
||||
/obj/effect/spider/eggcluster/terror_eggcluster/New()
|
||||
..()
|
||||
@@ -162,6 +166,7 @@
|
||||
S.faction = faction
|
||||
S.spider_myqueen = spider_myqueen
|
||||
S.master_commander = master_commander
|
||||
S.enemies = enemies
|
||||
if(spider_growinstantly)
|
||||
S.amount_grown = 250
|
||||
var/rnum = 5 - spiderling_number
|
||||
|
||||
@@ -0,0 +1,310 @@
|
||||
// --------------------------------------------------------------------------------
|
||||
// --------------------- TERROR SPIDERS: TARGETING CODE -----------------------
|
||||
// --------------------------------------------------------------------------------
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/ListTargets()
|
||||
var/list/targets1 = list()
|
||||
var/list/targets2 = list()
|
||||
var/list/targets3 = list()
|
||||
for(var/mob/living/H in view(src, vision_range))
|
||||
if(H.stat == DEAD)
|
||||
continue
|
||||
if(H.flags & GODMODE)
|
||||
continue
|
||||
if(H.stat == UNCONSCIOUS && !stat_attack)
|
||||
continue
|
||||
if(ai_type == TS_AI_DEFENSIVE && !(H in enemies))
|
||||
continue
|
||||
if(isterrorspider(H))
|
||||
if(H in enemies)
|
||||
targets3 += H
|
||||
continue
|
||||
if(iscarbon(H))
|
||||
var/mob/living/carbon/C = H
|
||||
if(IsInfected(C)) // only target the infected if they're attacking us. Even then, lowest priority.
|
||||
if(C in enemies)
|
||||
targets3 += C
|
||||
continue
|
||||
else if(C.reagents.has_reagent("terror_black_toxin",60))
|
||||
// only target those dying of black spider venom if they are close, or our enemy
|
||||
if(get_dist(src,C) <= 2 || (C in enemies))
|
||||
targets2 += C
|
||||
else
|
||||
// Target prioritization by spider type. BRUTE spiders prioritize lower armor values, POISON spiders prioritize poisonable targets
|
||||
if(ai_target_method == TS_DAMAGE_BRUTE)
|
||||
var/theirarmor = C.getarmor(type = "melee")
|
||||
// Example values: Civilian: 2, Engineer w/ Hardsuit: 10, Sec Officer with armor: 19, HoS: 48, Deathsquad: 80
|
||||
if(theirarmor < 10)
|
||||
targets1 += C
|
||||
else if(C in enemies)
|
||||
if(theirarmor < 30)
|
||||
targets2 += C
|
||||
else
|
||||
targets3 += C
|
||||
else
|
||||
targets3 += C
|
||||
else if(ai_target_method == TS_DAMAGE_POISON)
|
||||
if(C.can_inject(null,0,"chest",0))
|
||||
targets1 += C
|
||||
else if(C in enemies)
|
||||
targets2 += C
|
||||
else
|
||||
targets3 += C
|
||||
else
|
||||
// TS_DAMAGE_SIMPLE
|
||||
if(C in enemies)
|
||||
targets2 += C
|
||||
else
|
||||
targets3 += C
|
||||
else
|
||||
if(istype(H,/mob/living/simple_animal))
|
||||
var/mob/living/simple_animal/S = H
|
||||
if(S.force_threshold > melee_damage_upper)
|
||||
continue
|
||||
if(H in enemies)
|
||||
targets2 += H
|
||||
else
|
||||
targets3 += H
|
||||
if(health < maxHealth)
|
||||
// if we're hurt, and ONLY if we're hurt, do the additional check for mechs/space pods. Save processing time.
|
||||
for(var/obj/mecha/M in view(src, vision_range))
|
||||
if(get_dist(M, src) <= 2)
|
||||
targets2 += M
|
||||
else
|
||||
targets3 += M
|
||||
for(var/obj/spacepod/S in view(src, vision_range))
|
||||
targets3 += S
|
||||
if(targets1.len)
|
||||
return targets1
|
||||
if(targets2.len)
|
||||
return targets2
|
||||
return targets3
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/LoseTarget()
|
||||
if(target && isliving(target))
|
||||
var/mob/living/T = target
|
||||
if(T.stat > 0)
|
||||
killcount++
|
||||
regen_points += regen_points_per_kill
|
||||
attackstep = 0
|
||||
attackcycles = 0
|
||||
..()
|
||||
|
||||
// --------------------------------------------------------------------------------
|
||||
// --------------------- TERROR SPIDERS: AI BEHAVIOR CODE -------------------------
|
||||
// --------------------------------------------------------------------------------
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/handle_automated_action()
|
||||
if (stat || ckey)
|
||||
return ..()
|
||||
if(AIStatus != AI_OFF && !target)
|
||||
var/my_ventcrawl_freq = freq_ventcrawl_idle
|
||||
if(ts_count_dead > 0)
|
||||
if(world.time < (ts_death_last + ts_death_window))
|
||||
my_ventcrawl_freq = freq_ventcrawl_combat
|
||||
// First, check for general actions that any spider could take.
|
||||
if(path_to_vent)
|
||||
if(entry_vent)
|
||||
if(spider_steps_taken > spider_max_steps)
|
||||
path_to_vent = 0
|
||||
stop_automated_movement = 0
|
||||
spider_steps_taken = 0
|
||||
path_to_vent = 0
|
||||
entry_vent = null
|
||||
else if(get_dist(src, entry_vent) <= 1)
|
||||
path_to_vent = 0
|
||||
stop_automated_movement = 1
|
||||
spider_steps_taken = 0
|
||||
spawn(50)
|
||||
stop_automated_movement = 0
|
||||
TSVentCrawlRandom(entry_vent)
|
||||
else
|
||||
spider_steps_taken++
|
||||
CreatePath(entry_vent)
|
||||
step_to(src,entry_vent)
|
||||
if(spider_debug > 0)
|
||||
visible_message("<span class='notice'>[src] moves towards the vent [entry_vent].</span>")
|
||||
else
|
||||
path_to_vent = 0
|
||||
else if(ai_break_lights && world.time > (last_break_light + freq_break_light))
|
||||
last_break_light = world.time
|
||||
for(var/obj/machinery/light/L in range(1, src))
|
||||
if(!L.status)
|
||||
step_to(src,L)
|
||||
L.on = 1
|
||||
L.broken()
|
||||
L.do_attack_animation(src)
|
||||
visible_message("<span class='danger'>[src] smashes the [L.name].</span>")
|
||||
break
|
||||
else if(ai_spins_webs && world.time > (last_spins_webs + freq_spins_webs))
|
||||
last_spins_webs = world.time
|
||||
var/obj/effect/spider/terrorweb/T = locate() in get_turf(src)
|
||||
if(!T)
|
||||
new /obj/effect/spider/terrorweb(get_turf(src))
|
||||
visible_message("<span class='notice'>[src] puts up some spider webs.</span>")
|
||||
else if(ai_ventcrawls && world.time > (last_ventcrawl_time + my_ventcrawl_freq))
|
||||
if(prob(idle_ventcrawl_chance))
|
||||
last_ventcrawl_time = world.time
|
||||
var/vdistance = 99
|
||||
for(var/obj/machinery/atmospherics/unary/vent_pump/v in view(10, src))
|
||||
if(!v.welded)
|
||||
if(get_dist(src,v) < vdistance)
|
||||
entry_vent = v
|
||||
vdistance = get_dist(src,v)
|
||||
if(entry_vent)
|
||||
path_to_vent = 1
|
||||
else
|
||||
// If none of the general actions apply, check for class-specific actions.
|
||||
spider_special_action()
|
||||
else if(AIStatus != AI_OFF && target)
|
||||
CreatePath(target)
|
||||
..()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/adjustBruteLoss(damage)
|
||||
..(damage)
|
||||
Retaliate()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/adjustFireLoss(damage)
|
||||
..(damage)
|
||||
Retaliate()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/Retaliate()
|
||||
var/list/around = oview(src, 7)
|
||||
var/list/ts_nearby = list()
|
||||
for(var/atom/movable/A in around)
|
||||
if(A in enemies)
|
||||
continue
|
||||
if(isterrorspider(A))
|
||||
ts_nearby += A
|
||||
continue
|
||||
if(isliving(A))
|
||||
var/mob/living/M = A
|
||||
if(!("terrorspiders" in M.faction))
|
||||
enemies |= M
|
||||
visible_message("<span class='danger'>[src] glares at [M]!</span>")
|
||||
else if(istype(A, /obj/mecha))
|
||||
var/obj/mecha/M = A
|
||||
if(M.occupant)
|
||||
enemies |= M
|
||||
enemies |= M.occupant
|
||||
else if(istype(A, /obj/spacepod))
|
||||
var/obj/spacepod/M = A
|
||||
if(M.pilot)
|
||||
enemies |= M
|
||||
enemies |= M.pilot
|
||||
for(var/mob/living/simple_animal/hostile/poison/terror_spider/H in ts_nearby)
|
||||
var/retaliate_faction_check = 0
|
||||
for(var/F in faction)
|
||||
if(F in H.faction)
|
||||
retaliate_faction_check = 1
|
||||
break
|
||||
if(retaliate_faction_check && !attack_same && !H.attack_same)
|
||||
H.enemies |= enemies
|
||||
return 0
|
||||
|
||||
// --------------------------------------------------------------------------------
|
||||
// --------------------- TERROR SPIDERS: PATHING CODE -----------------------------
|
||||
// --------------------------------------------------------------------------------
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/CreatePath(mygoal)
|
||||
var/m2 = get_turf(src)
|
||||
if(m2 == mylocation)
|
||||
chasecycles++
|
||||
ClearObstacle(get_turf(mygoal))
|
||||
if(chasecycles >= 2)
|
||||
chasecycles = 0
|
||||
if(spider_opens_doors)
|
||||
var/tgt_dir = get_dir(src,mygoal)
|
||||
for(var/obj/machinery/door/airlock/A in view(1, src))
|
||||
if(A.density)
|
||||
try_open_airlock(A)
|
||||
for(var/obj/machinery/door/firedoor/F in view(1, src))
|
||||
if(tgt_dir == get_dir(src,F) && F.density && !F.welded)
|
||||
visible_message("<span class='danger'>[src] pries open the firedoor!</span>")
|
||||
F.open()
|
||||
|
||||
else
|
||||
mylocation = m2
|
||||
chasecycles = 0
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/ClearObstacle(turf/target_turf)
|
||||
var/list/valid_obstacles = list(/obj/structure/window, /obj/structure/closet, /obj/structure/table, /obj/structure/grille, /obj/structure/rack, /obj/machinery/door/window)
|
||||
for(var/dir in cardinal) // North, South, East, West
|
||||
var/obj/structure/obstacle = locate(/obj/structure, get_step(src, dir))
|
||||
if(is_type_in_list(obstacle, valid_obstacles))
|
||||
obstacle.attack_animal(src)
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/TSVentCrawlRandom(/var/entry_vent)
|
||||
if(entry_vent)
|
||||
if(get_dist(src, entry_vent) <= 2)
|
||||
var/list/vents = list()
|
||||
for(var/obj/machinery/atmospherics/unary/vent_pump/temp_vent in entry_vent.parent.other_atmosmch)
|
||||
vents.Add(temp_vent)
|
||||
if(!vents.len)
|
||||
entry_vent = null
|
||||
return
|
||||
var/obj/machinery/atmospherics/unary/vent_pump/exit_vent = pick(vents)
|
||||
visible_message("<B>[src] scrambles into the ventillation ducts!</B>", "<span class='notice'>You hear something squeezing through the ventilation ducts.</span>")
|
||||
spawn(rand(20,60))
|
||||
var/original_location = loc
|
||||
forceMove(exit_vent)
|
||||
var/travel_time = round(get_dist(loc, exit_vent.loc) / 2)
|
||||
spawn(travel_time)
|
||||
if(!exit_vent || exit_vent.welded)
|
||||
forceMove(original_location)
|
||||
entry_vent = null
|
||||
return
|
||||
if(prob(50))
|
||||
audible_message("<span class='notice'>You hear something squeezing through the ventilation ducts.</span>")
|
||||
spawn(travel_time)
|
||||
if(!exit_vent || exit_vent.welded)
|
||||
forceMove(original_location)
|
||||
entry_vent = null
|
||||
return
|
||||
forceMove(exit_vent.loc)
|
||||
entry_vent = null
|
||||
var/area/new_area = get_area(loc)
|
||||
if(new_area)
|
||||
new_area.Entered(src)
|
||||
|
||||
// --------------------------------------------------------------------------------
|
||||
// --------------------- TERROR SPIDERS: ENVIRONMENT CODE -------------------------
|
||||
// --------------------------------------------------------------------------------
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/ListValidTurfs()
|
||||
var/list/potentials = list()
|
||||
for(var/turf/simulated/T in oview(3,get_turf(src)))
|
||||
if(T.density == 0 && get_dist(get_turf(src),T) == 3)
|
||||
var/obj/effect/spider/terrorweb/W = locate() in T
|
||||
if(!W)
|
||||
var/obj/structure/grille/G = locate() in T
|
||||
if(!G)
|
||||
var/obj/structure/window/O = locate() in T
|
||||
if(!O)
|
||||
potentials += T
|
||||
return potentials
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/ListWebbedTurfs()
|
||||
var/list/webbed = list()
|
||||
for(var/turf/simulated/T in oview(3,get_turf(src)))
|
||||
if(T.density == 0 && get_dist(get_turf(src),T) == 3)
|
||||
var/obj/effect/spider/terrorweb/W = locate() in T
|
||||
if(W)
|
||||
webbed += T
|
||||
return webbed
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/ListVisibleTurfs()
|
||||
var/list/vturfs = list()
|
||||
for(var/turf/simulated/T in oview(7,get_turf(src)))
|
||||
if(T.density == 0)
|
||||
vturfs += T
|
||||
return vturfs
|
||||
|
||||
// --------------------------------------------------------------------------------
|
||||
// --------------------- TERROR SPIDERS: MISC AI CODE -----------------------------
|
||||
// --------------------------------------------------------------------------------
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/UnlockBlastDoors(target_id_tag)
|
||||
for(var/obj/machinery/door/poddoor/P in airlocks)
|
||||
if(P.density && P.id_tag == target_id_tag && P.z == z && !P.operating)
|
||||
P.open()
|
||||
@@ -1,4 +1,3 @@
|
||||
|
||||
var/global/list/ts_ckey_blacklist = list()
|
||||
var/global/ts_count_dead = 0
|
||||
var/global/ts_count_alive_awaymission = 0
|
||||
@@ -43,6 +42,15 @@ var/global/list/ts_spiderling_list = list()
|
||||
|
||||
// Ventcrawling
|
||||
ventcrawler = 1 // allows player ventcrawling
|
||||
var/ai_ventcrawls = 1
|
||||
var/idle_ventcrawl_chance = 3 // default 3% chance to ventcrawl when not in combat to a random exit vent
|
||||
var/freq_ventcrawl_combat = 1800 // 3 minutes
|
||||
var/freq_ventcrawl_idle = 9000 // 15 minutes
|
||||
var/last_ventcrawl_time = -9000 // Last time the spider crawled. Used to prevent excessive crawling. Setting to freq*-1 ensures they can crawl once on spawn.
|
||||
|
||||
// AI movement tracking
|
||||
var/spider_steps_taken = 0 // leave at 0, its a counter for ai steps taken.
|
||||
var/spider_max_steps = 15 // after we take X turns trying to do something, give up!
|
||||
|
||||
// Speech
|
||||
speak_chance = 0 // quiet but deadly
|
||||
@@ -71,15 +79,35 @@ var/global/list/ts_spiderling_list = list()
|
||||
aggro_vision_range = 10
|
||||
see_in_dark = 10
|
||||
nightvision = 1
|
||||
vision_type = new /datum/vision_override/nightvision/thermals/ling_augmented_eyesight
|
||||
see_invisible = 5
|
||||
sight = SEE_MOBS
|
||||
|
||||
// AI aggression settings
|
||||
var/ai_type = TS_AI_AGGRESSIVE // 0 = aggressive to everyone, 1 = defends self only
|
||||
var/ai_target_method = TS_DAMAGE_SIMPLE
|
||||
|
||||
// AI player control by ghosts
|
||||
var/ai_playercontrol_allowtype = 1 // if 0, this specific class of spider is not player-controllable. Default set in code for each class, cannot be changed.
|
||||
|
||||
var/ai_break_lights = 1 // AI lightbreaking behavior
|
||||
var/freq_break_light = 600
|
||||
var/last_break_light = 0 // leave this, changed by procs.
|
||||
|
||||
var/ai_spins_webs = 1 // AI web-spinning behavior
|
||||
var/freq_spins_webs = 600
|
||||
var/last_spins_webs = 0 // leave this, changed by procs.
|
||||
var/delay_web = 40 // delay between starting to spin web, and finishing
|
||||
|
||||
var/freq_cocoon_object = 1200 // two minutes between each attempt
|
||||
var/last_cocoon_object = 0 // leave this, changed by procs.
|
||||
|
||||
var/prob_ai_hides_in_vents = 15 // probabily of a gray spider hiding in a vent
|
||||
|
||||
var/spider_opens_doors = 1 // all spiders can open firedoors (they have no security). 1 = can open depowered doors. 2 = can open powered doors
|
||||
faction = list("terrorspiders")
|
||||
var/spider_awaymission = 0 // if 1, limits certain behavior in away missions
|
||||
var/spider_uo71 = 0 // if 1, spider is in the UO71 away mission
|
||||
var/spider_unlock_id_tag = "" // if defined, unlock awaymission blast doors with this tag on death
|
||||
var/spider_role_summary = "UNDEFINED"
|
||||
var/spider_placed = 0
|
||||
|
||||
@@ -90,16 +118,18 @@ var/global/list/ts_spiderling_list = list()
|
||||
var/obj/machinery/atmospherics/unary/vent_pump/nest_vent // home vent, usually used by queens
|
||||
var/fed = 0
|
||||
var/travelling_in_vent = 0
|
||||
var/list/enemies = list()
|
||||
var/path_to_vent = 0
|
||||
var/killcount = 0
|
||||
var/busy = 0 // leave this alone!
|
||||
var/spider_tier = TS_TIER_1 // 1 for red,gray,green. 2 for purple,black,white, 3 for prince, mother. 4 for queen
|
||||
var/hasdied = 0
|
||||
var/list/spider_special_drops = list()
|
||||
var/attackstep = 0
|
||||
var/attackcycles = 0
|
||||
var/spider_myqueen = null
|
||||
var/mylocation = null
|
||||
var/chasecycles = 0
|
||||
var/last_cocoon_object = 0 // leave this, changed by procs.
|
||||
|
||||
var/datum/action/innate/terrorspider/web/web_action
|
||||
var/datum/action/innate/terrorspider/wrap/wrap_action
|
||||
@@ -124,13 +154,15 @@ var/global/list/ts_spiderling_list = list()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/AttackingTarget()
|
||||
if(isterrorspider(target))
|
||||
if(target in enemies)
|
||||
enemies -= target
|
||||
var/mob/living/simple_animal/hostile/poison/terror_spider/T = target
|
||||
if(T.spider_tier > spider_tier)
|
||||
visible_message("<span class='notice'>[src] bows in respect for the terrifying presence of [target].</span>")
|
||||
visible_message("<span class='notice'>[src] cowers before [target].</span>")
|
||||
else if(T.spider_tier == spider_tier)
|
||||
visible_message("<span class='notice'>[src] nuzzles [target].</span>")
|
||||
else if(T.spider_tier < spider_tier && spider_tier >= 4)
|
||||
visible_message("<span class='notice'>[src] gives [target] a stern look.</span>")
|
||||
target.attack_animal(src)
|
||||
else
|
||||
visible_message("<span class='notice'>[src] harmlessly nuzzles [target].</span>")
|
||||
T.CheckFaction()
|
||||
@@ -223,6 +255,15 @@ var/global/list/ts_spiderling_list = list()
|
||||
if(is_away_level(z))
|
||||
spider_awaymission = 1
|
||||
ts_count_alive_awaymission++
|
||||
if(spider_tier >= 3)
|
||||
ai_ventcrawls = 0 // means that pre-spawned bosses on away maps won't ventcrawl. Necessary to keep prince/mother in one place.
|
||||
if(istype(get_area(src), /area/awaymission/UO71)) // if we are playing the away mission with our special spiders...
|
||||
spider_uo71 = 1
|
||||
if(world.time < 600)
|
||||
// these are static spiders, specifically for the UO71 away mission, make them stay in place
|
||||
ai_ventcrawls = 0
|
||||
spider_placed = 1
|
||||
wander = 0
|
||||
else
|
||||
ts_count_alive_station++
|
||||
// after 30 seconds, assuming nobody took control of it yet, offer it to ghosts.
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
|
||||
// --------------------------------------------------------------------------------
|
||||
// ----------------- TERROR SPIDERS: T2 WHITE TERROR ------------------------------
|
||||
// --------------------------------------------------------------------------------
|
||||
@@ -12,12 +11,12 @@
|
||||
name = "White Terror spider"
|
||||
desc = "An ominous-looking white spider, its ghostly eyes and vicious-looking fangs are the stuff of nightmares."
|
||||
spider_role_summary = "Rare, bite-and-run spider that infects hosts with spiderlings"
|
||||
|
||||
ai_target_method = TS_DAMAGE_POISON
|
||||
icon_state = "terror_white"
|
||||
icon_living = "terror_white"
|
||||
icon_dead = "terror_white_dead"
|
||||
maxHealth = 100
|
||||
health = 100
|
||||
maxHealth = 200
|
||||
health = 200
|
||||
melee_damage_lower = 5
|
||||
melee_damage_upper = 15
|
||||
move_to_delay = 4
|
||||
@@ -25,6 +24,18 @@
|
||||
loot = list(/obj/item/clothing/accessory/medal)
|
||||
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/white/LoseTarget()
|
||||
stop_automated_movement = 0
|
||||
attackstep = 0
|
||||
attackcycles = 0
|
||||
..()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/white/death(gibbed)
|
||||
if(!hasdied)
|
||||
if(spider_uo71)
|
||||
UnlockBlastDoors("UO71_Bridge")
|
||||
..()
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/white/spider_specialattack(mob/living/carbon/human/L, poisonable)
|
||||
if(!poisonable)
|
||||
..()
|
||||
@@ -35,6 +46,13 @@
|
||||
if(!IsInfected(L))
|
||||
visible_message("<span class='danger'>[src] buries its long fangs deep into the [inject_target] of [L]!</span>")
|
||||
new /obj/item/organ/internal/body_egg/terror_eggs(L)
|
||||
if(!ckey)
|
||||
LoseTarget()
|
||||
walk_away(src,L,2,1)
|
||||
else if(prob(25))
|
||||
visible_message("<span class='danger'>[src] pounces on [L]!</span>")
|
||||
L.Weaken(5)
|
||||
L.Stun(5)
|
||||
|
||||
/mob/living/simple_animal/hostile/poison/terror_spider/proc/IsInfected(mob/living/carbon/C) // Terror AI requires this
|
||||
if(C.get_int_organ(/obj/item/organ/internal/body_egg))
|
||||
|
||||
@@ -63,19 +63,19 @@
|
||||
to_chat(owner,"<span class='danger'>Your spider bite wound hurts horribly! </span>")
|
||||
if(istype(get_area(owner), /area/awaycontent) || istype(get_area(owner), /area/awaymission))
|
||||
awaymission_infection = 1
|
||||
if(15) // 30 seconds... enough time for the nerve agent to kick in, the pain to be blocked, and healing to begin
|
||||
if(15) // 30s... enough time for the nerve agent to kick in, the pain to be blocked, and healing to begin
|
||||
to_chat(owner,"<span class='notice'>The pain has faded, and stopped bleeding, though the skin around it has turned black.</span>")
|
||||
owner.adjustBruteLoss(-10)
|
||||
if(60) // 2 minutes... the point where the venom uses and accellerates the healing process, to feed the eggs
|
||||
if(30) // 1m... the point where the venom uses and accellerates the healing process, to feed the eggs
|
||||
to_chat(owner,"<span class='notice'>Your bite wound has completely sealed up, though the skin is still black. You feel significantly better.</span>")
|
||||
owner.adjustBruteLoss(-20)
|
||||
if(120) // 4 minutes... where the eggs are developing, and the wound is turning into a hatching site, but invisibly
|
||||
if(90) // 3m... where the eggs are developing, and the wound is turning into a hatching site, but invisibly
|
||||
to_chat(owner,"<span class='notice'>The black flesh around your old spider bite wound has started to peel off.</span>")
|
||||
if(150) // 5 minutes... where the victim realizes something is wrong - this is not a normal wound
|
||||
if(100) // 3m20s... where the victim realizes something is wrong - this is not a normal wound
|
||||
to_chat(owner,"<span class='danger'>The black flesh around your spider bite wound has cracked, and started to split open!</span>")
|
||||
if(165) // 5m 30s
|
||||
if(110) // 3m40s...
|
||||
to_chat(owner,"<span class='danger'>The black flesh splits open completely, revealing a cluster of small black oval shapes inside you, shapes that seem to be moving!</span>")
|
||||
if(180) // 6m
|
||||
if(120) // 4m...
|
||||
if(awaymission_infection && is_away_level(owner.z))
|
||||
// we started in the awaymission, we ended on the station.
|
||||
// To prevent someone bringing an infection back, we're going to trigger an alternate, equally-bad result here.
|
||||
|
||||
Reference in New Issue
Block a user