diff --git a/code/modules/mob/living/carbon/metroid/metroid.dm b/code/modules/mob/living/carbon/metroid/metroid.dm
deleted file mode 100644
index d62c5775d5c..00000000000
--- a/code/modules/mob/living/carbon/metroid/metroid.dm
+++ /dev/null
@@ -1,1048 +0,0 @@
-/mob/living/carbon/slime
- name = "baby slime"
- icon = 'icons/mob/slimes.dmi'
- icon_state = "grey baby slime"
- pass_flags = PASSTABLE
- ventcrawler = 2
- speak_emote = list("telepathically chirps")
-
- layer = 5
-
- maxHealth = 150
- health = 150
- gender = NEUTER
-
- update_icon = 0
- nutrition = 700
-
- see_in_dark = 8
- update_slimes = 0
-
- // canstun and canweaken don't affect slimes because they ignore stun and weakened variables
- // for the sake of cleanliness, though, here they are.
- status_flags = CANPARALYSE|CANPUSH
-
- var/cores = 1 // the number of /obj/item/slime_extract's the slime has left inside
- var/mutation_chance = 30 // Chance of mutating, should be between 25 and 35
-
- var/powerlevel = 0 // 1-10 controls how much electricity they are generating
- var/amount_grown = 0 // controls how long the slime has been overfed, if 10, grows or reproduces
-
- var/number = 0 // Used to understand when someone is talking to it
-
- var/mob/living/Victim = null // the person the slime is currently feeding on
- var/mob/living/Target = null // AI variable - tells the slime to hunt this down
- var/mob/living/Leader = null // AI variable - tells the slime to follow this person
-
- var/attacked = 0 // Determines if it's been attacked recently. Can be any number, is a cooloff-ish variable
- var/rabid = 0 // If set to 1, the slime will attack and eat anything it comes in contact with
- var/holding_still = 0 // AI variable, cooloff-ish for how long it's going to stay in one place
- var/target_patience = 0 // AI variable, cooloff-ish for how long it's going to follow its target
-
- var/list/Friends = list() // A list of friends; they are not considered targets for feeding; passed down after splitting
-
- var/list/speech_buffer = list() // Last phrase said near it and person who said it
-
- var/mood = "" // To show its face
- var/is_adult = 0
-
- var/core_removal_stage = 0 //For removing cores.
-
- ///////////TIME FOR SUBSPECIES
-
- var/colour = "grey"
- var/coretype = /obj/item/slime_extract/grey
- var/list/slime_mutation[4]
-
-/mob/living/carbon/slime/New()
- create_reagents(100)
- spawn (0)
- number = rand(1, 1000)
- name = "[colour] [is_adult ? "adult" : "baby"] slime ([number])"
- icon_state = "[colour] [is_adult ? "adult" : "baby"] slime"
- real_name = name
- slime_mutation = mutation_table(colour)
- mutation_chance = rand(25, 35)
- var/sanitizedcolour = replacetext(colour, " ", "")
- coretype = text2path("/obj/item/slime_extract/[sanitizedcolour]")
- ..()
-
-/mob/living/carbon/slime/regenerate_icons()
- icon_state = "[colour] [is_adult ? "adult" : "baby"] slime"
- overlays.len = 0
- if (mood)
- overlays += image('icons/mob/slimes.dmi', icon_state = "aslime-[mood]")
- ..()
-
-/mob/living/carbon/slime/movement_delay()
- if (bodytemperature >= 330.23) // 135 F
- return -1 // slimes become supercharged at high temperatures
-
- var/tally = 0
-
- var/health_deficiency = (100 - health)
- if(health_deficiency >= 45) tally += (health_deficiency / 25)
-
- if (bodytemperature < 183.222)
- tally += (283.222 - bodytemperature) / 10 * 1.75
-
- if(reagents)
- if(reagents.has_reagent("methamphetamine")) // Meth slows slimes down
- tally *= 2
-
- if(reagents.has_reagent("frostoil")) // Frostoil also makes them move VEEERRYYYYY slow
- tally *= 5
-
- if(health <= 0) // if damaged, the slime moves twice as slow
- tally *= 2
-
- return tally + config.slime_delay
-
-/mob/living/carbon/slime/Bump(atom/movable/AM as mob|obj, yes)
- if ((!(yes) || now_pushing))
- return
- now_pushing = 1
-
- if(isobj(AM))
- if(!client && powerlevel > 0)
- var/probab = 10
- switch(powerlevel)
- if(1 to 2) probab = 20
- if(3 to 4) probab = 30
- if(5 to 6) probab = 40
- if(7 to 8) probab = 60
- if(9) probab = 70
- if(10) probab = 95
- if(prob(probab))
- if(istype(AM, /obj/structure/window) || istype(AM, /obj/structure/grille))
- if(nutrition <= get_hunger_nutrition() && !Atkcool)
- if (is_adult || prob(5))
- AM.attack_slime(src)
- spawn()
- Atkcool = 1
- sleep(45)
- Atkcool = 0
-
- if(ismob(AM))
- var/mob/tmob = AM
-
- if(is_adult)
- if(istype(tmob, /mob/living/carbon/human))
- if(prob(90))
- now_pushing = 0
- return
- else
- if(istype(tmob, /mob/living/carbon/human))
- now_pushing = 0
- return
-
- now_pushing = 0
- ..()
- if (!istype(AM, /atom/movable))
- return
- if (!( now_pushing ))
- now_pushing = 1
- if (!( AM.anchored ))
- var/t = get_dir(src, AM)
- if (istype(AM, /obj/structure/window))
- if(AM:ini_dir == NORTHWEST || AM:ini_dir == NORTHEAST || AM:ini_dir == SOUTHWEST || AM:ini_dir == SOUTHEAST)
- for(var/obj/structure/window/win in get_step(AM,t))
- now_pushing = 0
- return
- step(AM, t)
- now_pushing = null
-
-/mob/living/carbon/slime/Process_Spacemove(var/movement_dir = 0)
- return 2
-
-/mob/living/carbon/slime/Stat()
- ..()
-
- statpanel("Status")
- if(is_adult)
- stat(null, "Health: [round((health / 200) * 100)]%")
- else
- stat(null, "Health: [round((health / 150) * 100)]%")
-
- if (client.statpanel == "Status")
- stat(null, "Nutrition: [nutrition]/[get_max_nutrition()]")
- if(amount_grown >= 10)
- if(is_adult)
- stat(null, "You can reproduce!")
- else
- stat(null, "You can evolve!")
-
- stat(null,"Power Level: [powerlevel]")
-
-/mob/living/carbon/slime/adjustFireLoss(amount)
- ..(-abs(amount)) // Heals them
- return
-
-/mob/living/carbon/slime/bullet_act(var/obj/item/projectile/Proj)
- attacked += 10
- ..(Proj)
- return 0
-
-/mob/living/carbon/slime/emp_act(severity)
- powerlevel = 0 // oh no, the power!
- ..()
-
-/mob/living/carbon/slime/ex_act(severity)
- ..()
-
- var/b_loss = null
- var/f_loss = null
- switch (severity)
- if (1.0)
- qdel(src)
- return
-
- if (2.0)
-
- b_loss += 60
- f_loss += 60
-
-
- if(3.0)
- b_loss += 30
-
- adjustBruteLoss(b_loss)
- adjustFireLoss(f_loss)
-
- updatehealth()
-
-
-/mob/living/carbon/slime/blob_act()
- show_message(" The blob attacks you!")
- adjustBruteLoss(20)
- updatehealth()
- return
-
-
-/mob/living/carbon/slime/unEquip(obj/item/W as obj)
- return
-
-/mob/living/carbon/slime/attack_ui(slot)
- return
-
-/mob/living/carbon/slime/attack_slime(mob/living/carbon/slime/M as mob)
- if (!ticker)
- M << "You cannot attack people before the game has started."
- return
-
- if (Victim) return // can't attack while eating!
-
- if (health > -100)
-
- M.do_attack_animation(src)
- visible_message(" The [M.name] has glomped [src]!", \
- " The [M.name] has glomped [src]!")
- var/damage = rand(1, 3)
- attacked += 5
-
- if(M.is_adult)
- damage = rand(1, 6)
- else
- damage = rand(1, 3)
-
- adjustBruteLoss(damage)
-
- updatehealth()
- return
-
-/mob/living/carbon/slime/attack_animal(mob/living/simple_animal/M as mob)
- if(M.melee_damage_upper == 0)
- M.custom_emote(1, "[M.friendly] [src]")
- else
- M.do_attack_animation(src)
- if(M.attack_sound)
- playsound(loc, M.attack_sound, 50, 1, 1)
- visible_message("[M] [M.attacktext] [src]!", \
- "[M] [M.attacktext] [src]!")
- M.attack_log += text("\[[time_stamp()]\] attacked [src.name] ([src.ckey])")
- src.attack_log += text("\[[time_stamp()]\] was attacked by [M.name] ([M.ckey])")
- var/damage = rand(M.melee_damage_lower, M.melee_damage_upper)
- attacked += 10
- adjustBruteLoss(damage)
- updatehealth()
-
-/mob/living/carbon/slime/attack_larva(mob/living/carbon/alien/larva/L as mob)
-
- switch(L.a_intent)
-
- if(I_HELP)
- visible_message("[L] rubs its head against [src].")
-
-
- else
- L.do_attack_animation(src)
- attacked += 10
- visible_message("[L] bites [src]!", \
- "[L] bites [src]!")
- playsound(loc, 'sound/weapons/bite.ogg', 50, 1, -1)
-
- if(stat != DEAD)
- var/damage = rand(1, 3)
- L.amount_grown = min(L.amount_grown + damage, L.max_grown)
- adjustBruteLoss(damage)
-
-/mob/living/carbon/slime/attack_hand(mob/living/carbon/human/M as mob)
- if (!ticker)
- M << "You cannot attack people before the game has started."
- return
-
- if (istype(loc, /turf) && istype(loc.loc, /area/start))
- M << "No attacking people at spawn, you jackass."
- return
-
- ..()
-
- if(Victim)
- if(Victim == M)
- if(prob(60))
- visible_message("[M] attempts to wrestle \the [name] off!")
- playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
-
- else
- visible_message(" [M] manages to wrestle \the [name] off!")
- playsound(loc, 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
-
- if(prob(90) && !client)
- Discipline++
-
- spawn()
- SStun = 1
- sleep(rand(45,60))
- if(src)
- SStun = 0
-
- Victim = null
- anchored = 0
- step_away(src,M)
-
- return
-
- else
- if(prob(30))
- visible_message("[M] attempts to wrestle \the [name] off of [Victim]!")
- playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
-
- else
- visible_message(" [M] manages to wrestle \the [name] off of [Victim]!")
- playsound(loc, 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
-
- if(prob(80) && !client)
- Discipline++
-
- if(!is_adult)
- if(Discipline == 1)
- attacked = 0
-
- spawn()
- SStun = 1
- sleep(rand(55,65))
- if(src)
- SStun = 0
-
- Victim = null
- anchored = 0
- step_away(src,M)
-
- return
-
-/*
- if(M.gloves && istype(M.gloves,/obj/item/clothing/gloves))
- var/obj/item/clothing/gloves/G = M.gloves
- if(G.cell)
- if(M.a_intent == "hurt")//Stungloves. Any contact will stun the alien.
- if(G.cell.charge >= 2500)
- G.cell.use(2500)
- visible_message("[src] has been touched with the stun gloves by [M]!")
- return
- else
- M << "\red Not enough charge! "
- return
-*/
-
- switch(M.a_intent)
-
- if (I_HELP)
- help_shake_act(M)
-
- if (I_GRAB)
- grabbedby(M)
-
- else
- M.do_attack_animation(src)
- var/damage = rand(1, 9)
-
- attacked += 10
- if (prob(90))
- if (HULK in M.mutations)
- damage += 5
- if(Victim || Target)
- Victim = null
- Target = null
- anchored = 0
- if(prob(80) && !client)
- Discipline++
- spawn(0)
-
- step_away(src,M,15)
- sleep(3)
- step_away(src,M,15)
-
-
- playsound(loc, "punch", 25, 1, -1)
- visible_message("[M] has punched [src]!", \
- "[M] has punched [src]!")
-
- adjustBruteLoss(damage)
- updatehealth()
- else
- playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
- visible_message("[M] has attempted to punch [src]!")
- return
-
-
-
-/mob/living/carbon/slime/attack_alien(mob/living/carbon/alien/humanoid/M as mob)
- if (!ticker)
- M << "You cannot attack people before the game has started."
- return
-
- if (istype(loc, /turf) && istype(loc.loc, /area/start))
- M << "No attacking people at spawn, you jackass."
- return
-
- switch(M.a_intent)
- if (I_HELP)
- visible_message("[M] caresses [src] with its scythe like arm.")
-
- if (I_HARM)
- M.do_attack_animation(src)
- if (prob(95))
- attacked += 10
- playsound(loc, 'sound/weapons/slice.ogg', 25, 1, -1)
- var/damage = rand(15, 30)
- if (damage >= 25)
- damage = rand(20, 40)
- visible_message("[M] has attacked [name]!", \
- "[M] has attacked [name]!")
- else
- visible_message("[M] has wounded [name]!", \
- ")[M] has wounded [name]!")
- adjustBruteLoss(damage)
- updatehealth()
- else
- playsound(loc, 'sound/weapons/slashmiss.ogg', 25, 1, -1)
- visible_message("[M] has attempted to lunge at [name]!", \
- "[M] has attempted to lunge at [name]!")
-
- if (I_GRAB)
- grabbedby(M)
-
- if (I_DISARM)
- M.do_attack_animation(src)
- playsound(loc, 'sound/weapons/pierce.ogg', 25, 1, -1)
- var/damage = 5
- attacked += 10
-
- if(prob(95))
- visible_message("[M] has tackled [name]!", \
- "[M] has tackled [name]!")
-
- if(Victim || Target)
- Victim = null
- Target = null
- anchored = 0
- if(prob(80) && !client)
- Discipline++
- if(!istype(src, /mob/living/carbon/slime))
- if(Discipline == 1)
- attacked = 0
-
- spawn()
- SStun = 1
- sleep(rand(5,20))
- SStun = 0
-
- spawn(0)
-
- step_away(src,M,15)
- sleep(3)
- step_away(src,M,15)
-
- else
- drop_item()
- visible_message("[M] has disarmed [name]!",
- "[M] has disarmed [name]!")
- adjustBruteLoss(damage)
- updatehealth()
- return
-
-/mob/living/carbon/slime/attackby(obj/item/W, mob/user, params)
- if(istype(W,/obj/item/stack/sheet/mineral/plasma)) //Lets you feed slimes plasma.
- if (user in Friends)
- ++Friends[user]
- else
- Friends[user] = 1
- user << "You feed the slime the plasma. It chirps happily."
- var/obj/item/stack/sheet/mineral/plasma/S = W
- S.use(1)
- return
- else if(W.force > 0)
- attacked += 10
- if(prob(25))
- user << "[W] passes right through [src]!"
- return
- if(Discipline && prob(50)) // wow, buddy, why am I getting attacked??
- Discipline = 0
- else if(W.force >= 3)
- if(is_adult)
- if(prob(5 + round(W.force/2)))
- if(Victim || Target)
- if(prob(80) && !client)
- Discipline++
-
- Victim = null
- Target = null
- anchored = 0
-
- spawn()
- SStun = 1
- sleep(rand(5,20))
- SStun = 0
-
- spawn(0)
- if(user)
- canmove = 0
- step_away(src, user)
- if(prob(25 + W.force))
- sleep(2)
- if(user)
- step_away(src, user)
- canmove = 1
-
- else
- if(prob(10 + W.force*2))
- if(Victim || Target)
- if(prob(80) && !client)
- Discipline++
- if(Discipline == 1)
- attacked = 0
- spawn()
- SStun = 1
- sleep(rand(5,20))
- SStun = 0
-
- Victim = null
- Target = null
- anchored = 0
-
- spawn(0)
- if(user)
- canmove = 0
- step_away(src, user)
- if(prob(25 + W.force*4))
- sleep(2)
- if(user)
- step_away(src, user)
- canmove = 1
- ..()
-
-/mob/living/carbon/slime/restrained()
- return 0
-
-mob/living/carbon/slime/var/temperature_resistance = T0C+75
-
-/mob/living/carbon/slime/show_inv(mob/user)
- return
-
-/mob/living/carbon/slime/toggle_throw_mode()
- return
-
-/mob/living/carbon/slime/proc/apply_water()
- adjustToxLoss(rand(15,20))
- if (!client)
- if (Target) // Like cats
- Target = null
- ++Discipline
- return
-
-/mob/living/carbon/slime/can_use_vents()
- if(Victim)
- return "You cannot ventcrawl while feeding."
- ..()
-
-/obj/item/slime_extract
- name = "slime extract"
- desc = "Goo extracted from a slime. Legends claim these to have \"magical powers\"."
- icon = 'icons/mob/slimes.dmi'
- icon_state = "grey slime extract"
- force = 1.0
- w_class = 1.0
- throwforce = 0
- throw_speed = 3
- throw_range = 6
- origin_tech = "biotech=4"
- item_color = "grey"
- var/Uses = 1 // uses before it goes inert
- var/enhanced = 0 //has it been enhanced before?
-
- attackby(obj/item/O as obj, mob/user as mob, params)
- if(istype(O, /obj/item/weapon/slimesteroid2))
- if(enhanced == 1)
- user << " This extract has already been enhanced!"
- return ..()
- if(Uses == 0)
- user << " You can't enhance a used extract!"
- return ..()
- user <<"You apply the enhancer. It now has triple the amount of uses."
- Uses = 3
- enhanced = 1
- qdel(O)
- if(istype(O,/obj/item/weapon/storage/bag))
- ..()
-
-/obj/item/slime_extract/New()
- ..()
- create_reagents(100)
-
-
-/obj/item/slime_extract/grey
- name = "grey slime extract"
- icon_state = "grey slime extract"
- item_color = "grey"
-
-/obj/item/slime_extract/gold
- name = "gold slime extract"
- icon_state = "gold slime extract"
- item_color = "gold"
-
-/obj/item/slime_extract/silver
- name = "silver slime extract"
- icon_state = "silver slime extract"
- item_color = "silver"
-
-/obj/item/slime_extract/metal
- name = "metal slime extract"
- icon_state = "metal slime extract"
- item_color = "metal"
-
-/obj/item/slime_extract/purple
- name = "purple slime extract"
- icon_state = "purple slime extract"
- item_color = "purple"
-
-/obj/item/slime_extract/darkpurple
- name = "dark purple slime extract"
- icon_state = "dark purple slime extract"
- item_color = "darkpurple"
-
-/obj/item/slime_extract/orange
- name = "orange slime extract"
- icon_state = "orange slime extract"
- item_color = "orange"
-
-/obj/item/slime_extract/yellow
- name = "yellow slime extract"
- icon_state = "yellow slime extract"
- item_color = "yellow"
-
-/obj/item/slime_extract/red
- name = "red slime extract"
- icon_state = "red slime extract"
- item_color = "red"
-
-/obj/item/slime_extract/blue
- name = "blue slime extract"
- icon_state = "blue slime extract"
- item_color = "blue"
-
-/obj/item/slime_extract/darkblue
- name = "dark blue slime extract"
- icon_state = "dark blue slime extract"
- item_color = "darkblue"
-
-/obj/item/slime_extract/pink
- name = "pink slime extract"
- icon_state = "pink slime extract"
- item_color = "pink"
-
-/obj/item/slime_extract/green
- name = "green slime extract"
- icon_state = "green slime extract"
- item_color = "green"
-
-/obj/item/slime_extract/lightpink
- name = "light pink slime extract"
- icon_state = "light pink slime extract"
- item_color = "lightpink"
-
-/obj/item/slime_extract/black
- name = "black slime extract"
- icon_state = "black slime extract"
- item_color = "black"
-
-/obj/item/slime_extract/oil
- name = "oil slime extract"
- icon_state = "oil slime extract"
- item_color = "oil"
-
-/obj/item/slime_extract/adamantine
- name = "adamantine slime extract"
- icon_state = "adamantine slime extract"
- item_color = "adamantine"
-
-/obj/item/slime_extract/bluespace
- name = "bluespace slime extract"
- icon_state = "bluespace slime extract"
-
-/obj/item/slime_extract/pyrite
- name = "pyrite slime extract"
- icon_state = "pyrite slime extract"
-
-/obj/item/slime_extract/cerulean
- name = "cerulean slime extract"
- icon_state = "cerulean slime extract"
-
-/obj/item/slime_extract/sepia
- name = "sepia slime extract"
- icon_state = "sepia slime extract"
-
-/obj/item/slime_extract/rainbow
- name = "rainbow slime extract"
- icon_state = "rainbow slime extract"
-
-////Pet Slime Creation///
-
-/obj/item/weapon/slimepotion
- name = "docility potion"
- desc = "A potent chemical mix that will nullify a slime's powers, causing it to become docile and tame."
- icon = 'icons/obj/chemical.dmi'
- icon_state = "bottle19"
- w_class = 1
- origin_tech = "biotech=4"
-
- attack(mob/living/carbon/slime/M as mob, mob/user as mob)
- if(!istype(M, /mob/living/carbon/slime))//If target is not a slime.
- user << " The potion only works on slimes!"
- return ..()
- if(M.stat)
- user << " The slime is dead!"
- return..()
- if(M.mind)
- user << " The slime resists!"
- return ..()
- if(M.is_adult)
- var/mob/living/simple_animal/adultslime/pet = new /mob/living/simple_animal/adultslime(M.loc)
- pet.icon_state = "[M.colour] adult slime"
- pet.icon_living = "[M.colour] adult slime"
- pet.icon_dead = "[M.colour] baby slime dead"
- pet.colour = "[M.colour]"
- qdel(M)
- var/newname = sanitize(copytext(input(user, "Would you like to give the slime a name?", "Name your new pet", "pet slime") as null|text,1,MAX_NAME_LEN))
-
- if (!newname)
- newname = "pet slime"
- pet.name = newname
- pet.real_name = newname
- qdel(src)
- else
- var/mob/living/simple_animal/slime/pet = new /mob/living/simple_animal/slime(M.loc)
- pet.icon_state = "[M.colour] baby slime"
- pet.icon_living = "[M.colour] baby slime"
- pet.icon_dead = "[M.colour] baby slime dead"
- pet.colour = "[M.colour]"
- qdel(M)
- var/newname = sanitize(copytext(input(user, "Would you like to give the slime a name?", "Name your new pet", "pet slime") as null|text,1,MAX_NAME_LEN))
-
- if (!newname)
- newname = "pet slime"
- pet.name = newname
- pet.real_name = newname
- qdel(src)
- user <<"You feed the slime the potion, removing it's powers and calming it."
-
-/obj/item/weapon/sentience_potion
- name = "sentience potion"
- desc = "A miraculous chemical mix that can raise the intelligence of creatures to human levels. Unlike normal slime potions, it can be absorbed by any nonsentient being."
- icon = 'icons/obj/chemical.dmi'
- icon_state = "bottle19"
- origin_tech = "biotech=5"
- var/list/not_interested = list()
- var/being_used = 0
- w_class = 1
-
-
-/obj/item/weapon/sentience_potion/afterattack(mob/living/M, mob/user)
- if(being_used || !ismob(M))
- return
- if(!isslime(M) && !isanimal(M) || M.ckey) //only works on animals that aren't player controlled
- user << "[M] is already too intelligent for this to work!"
- return ..()
- if(M.stat)
- user << "[M] is dead!"
- return..()
-
- user << "You offer the sentience potion to [M]..."
- being_used = 1
-
- var/list/candidates = get_candidates(ROLE_SENTIENT, ALIEN_AFK_BRACKET)
-
- shuffle(candidates)
-
- var/time_passed = world.time
- var/list/consenting_candidates = list()
-
- for(var/candidate in candidates)
-
- if(candidate in not_interested)
- continue
-
- spawn(0)
- switch(alert(candidate, "Would you like to play as [M.name]? Please choose quickly!","Confirmation","Yes","No"))
- if("Yes")
- if((world.time-time_passed)>=50 || !src)
- return
- consenting_candidates += candidate
- if("No")
- if(!src)
- return
- not_interested += candidate
-
- sleep(50)
-
- if(!src)
- return
-
- listclearnulls(consenting_candidates) //some candidates might have left during sleep(50)
-
- if(consenting_candidates.len)
- var/client/C = null
- C = pick(consenting_candidates)
- M.key = C.key
- M.universal_speak = 1
- M.faction |= "sentient"
- M << "All at once it makes sense: you know what you are and who you are! Self awareness is yours!"
- M << "You are grateful to be self aware and owe [user] a great debt. Serve [user], and assist them in completing their goals at any cost."
- user << "[M] accepts the potion and suddenly becomes attentive and aware. It worked!"
- if(isanimal(M))
- var/mob/living/simple_animal/S = M
- S.master_commander = user
- qdel(src)
- else
- user << "[M] looks interested for a moment, but then looks back down. Maybe you should try again later."
- being_used = 0
- ..()
-
-
-/obj/item/weapon/slimesteroid
- name = "slime steroid"
- desc = "A potent chemical mix that will cause a slime to generate more extract."
- icon = 'icons/obj/chemical.dmi'
- icon_state = "bottle16"
- w_class = 1
- origin_tech = "biotech=4"
-
-
- attack(mob/living/carbon/slime/M as mob, mob/user as mob)
- if(!istype(M, /mob/living/carbon/slime))//If target is not a slime.
- user << " The steroid only works on baby slimes!"
- return ..()
- if(M.is_adult) //Can't tame adults
- user << " Only baby slimes can use the steroid!"
- return..()
- if(M.stat)
- user << " The slime is dead!"
- return..()
- if(M.cores == 3)
- user <<" The slime already has the maximum amount of extract!"
- return..()
-
- user <<"You feed the slime the steroid. It now has triple the amount of extract."
- M.cores = 3
- qdel(src)
-
-/obj/item/weapon/slimesteroid2
- name = "extract enhancer"
- desc = "A potent chemical mix that will give a slime extract three uses."
- icon = 'icons/obj/chemical.dmi'
- icon_state = "bottle17"
- w_class = 1
- origin_tech = "biotech=4"
-
-
-/obj/item/weapon/slimespeed
- name = "slime speed potion"
- desc = "A potent chemical mix that will remove the slowdown from any item."
- icon = 'icons/obj/chemical.dmi'
- icon_state = "bottle3"
- w_class = 1
- origin_tech = "biotech=4"
-
-/obj/item/weapon/slimespeed/afterattack(obj/item/C, mob/user)
- ..()
- if(!istype(C))
- user << "The potion can only be used on items!"
- return
- if(C.slowdown <= 0)
- user << "The [C] can't be made any faster!"
- return..()
- user <<"You slather the red gunk over the [C], making it faster."
- C.color = "#FF0000"
- C.slowdown = 0
- qdel(src)
-
-/obj/item/weapon/slimefireproof
- name = "slime chill potion"
- desc = "A potent chemical mix that will fireproof any article of clothing. Has three uses."
- icon = 'icons/obj/chemical.dmi'
- icon_state = "bottle17"
- var/uses = 3
- w_class = 1
- origin_tech = "biotech=4"
-
-
-/obj/item/weapon/slimefireproof/afterattack(obj/item/clothing/C, mob/user)
- ..()
- if(!uses)
- qdel(src)
- return
- if(!istype(C))
- user << "The potion can only be used on clothing!"
- return
- if(C.max_heat_protection_temperature == FIRE_IMMUNITY_SUIT_MAX_TEMP_PROTECT)
- user << "The [C] is already fireproof!"
- return..()
- user <<"You slather the blue gunk over the [C], fireproofing it."
- C.name = "fireproofed [C.name]"
- C.color = "#000080"
- C.max_heat_protection_temperature = FIRE_IMMUNITY_SUIT_MAX_TEMP_PROTECT
- C.heat_protection = C.body_parts_covered
- uses --
- if(!uses)
- qdel(src)
-
-/obj/item/stack/tile/bluespace
- name = "bluespace floor tile"
- singular_name = "floor tile"
- desc = "Through a series of micro-teleports, these tiles let people move at incredible speeds."
- icon_state = "tile-bluespace"
- w_class = 3
- force = 6
- materials = list(MAT_METAL=500)
- throwforce = 10
- throw_speed = 3
- throw_range = 7
- flags = CONDUCT
- max_amount = 60
- turf_type = /turf/simulated/floor/bluespace
-
-
-/turf/simulated/floor/bluespace
- slowdown = -1
- icon_state = "bluespace"
- desc = "Through a series of micro-teleports, these tiles let people move at incredible speeds."
- floor_tile = /obj/item/stack/tile/bluespace
-
-
-/obj/item/stack/tile/sepia
- name = "sepia floor tile"
- singular_name = "floor tile"
- desc = "Time seems to flow very slowly around these tiles."
- icon_state = "tile-sepia"
- w_class = 3
- force = 6
- materials = list(MAT_METAL=500)
- throwforce = 10
- throw_speed = 3
- throw_range = 7
- flags = CONDUCT
- max_amount = 60
- turf_type = /turf/simulated/floor/sepia
-
-
-/turf/simulated/floor/sepia
- slowdown = 2
- icon_state = "sepia"
- desc = "Time seems to flow very slowly around these tiles."
- floor_tile = /obj/item/stack/tile/sepia
-
-/obj/effect/goleRUNe
- anchored = 1
- desc = "a strange rune used to create golems. It glows when spirits are nearby."
- name = "rune"
- icon = 'icons/obj/rune.dmi'
- icon_state = "golem"
- unacidable = 1
- layer = TURF_LAYER
- var/list/mob/dead/observer/ghosts[0]
-
- New()
- ..()
- processing_objects.Add(src)
-
- process()
- if(ghosts.len>0)
- icon_state = "golem2"
- else
- icon_state = "golem"
-
- attack_hand(mob/living/user as mob)
- var/mob/dead/observer/ghost
- for(var/mob/dead/observer/O in src.loc)
- if(!check_observer(O))
- O << "\red You are not eligible to become a golem."
- continue
- ghost = O
- break
- if(!ghost)
- user << "The rune fizzles uselessly. There is no spirit nearby."
- return
- var/mob/living/carbon/human/golem/G = new /mob/living/carbon/human/golem
- if(prob(50)) G.gender = "female"
- G.loc = src.loc
- G.key = ghost.key
- G << "You are an adamantine golem. You move slowly, but are highly resistant to heat and cold as well as blunt trauma. You are unable to wear clothes, but can still use most tools. Serve [user], and assist them in completing their goals at any cost."
- qdel(src)
-
-
- proc/announce_to_ghosts()
- for(var/mob/dead/observer/O in player_list)
- if(O.client)
- var/area/A = get_area(src)
- if(A)
- O << "\blue Golem rune created in [A.name]. (Teleport | Sign Up)"
-
- Topic(href,href_list)
- if("signup" in href_list)
- var/mob/dead/observer/O = locate(href_list["signup"])
- volunteer(O)
-
- attack_ghost(var/mob/dead/observer/O)
- if(!O) return
- volunteer(O)
-
- proc/check_observer(var/mob/dead/observer/O)
- if(!O)
- return 0
- if(!O.client)
- return 0
- if(O.mind && O.mind.current && O.mind.current.stat != DEAD)
- return 0
- if(O.has_enabled_antagHUD == 1 && config.antag_hud_restricted)
- return 0
- return 1
-
- proc/volunteer(var/mob/dead/observer/O)
- if(O in ghosts)
- ghosts.Remove(O)
- O << "\red You are no longer signed up to be a golem."
- else
- if(!check_observer(O))
- O << "\red You are not eligible to become a golem."
- return
- ghosts.Add(O)
- O << "\blue You are signed up to be a golem."
\ No newline at end of file
diff --git a/code/modules/mob/living/carbon/metroid/death.dm b/code/modules/mob/living/carbon/slime/death.dm
similarity index 93%
rename from code/modules/mob/living/carbon/metroid/death.dm
rename to code/modules/mob/living/carbon/slime/death.dm
index e7cac39a36c..6e951320bdc 100644
--- a/code/modules/mob/living/carbon/metroid/death.dm
+++ b/code/modules/mob/living/carbon/slime/death.dm
@@ -1,29 +1,29 @@
-/mob/living/carbon/slime/death(gibbed)
- if(!gibbed)
- if(is_adult)
- var/mob/living/carbon/slime/M = new /mob/living/carbon/slime(loc)
- M.colour = colour
- M.rabid = 1
- is_adult = 0
- maxHealth = 150
- revive()
- regenerate_icons()
- number = rand(1, 1000)
- name = "[colour] [is_adult ? "adult" : "baby"] slime ([number])"
- return
-
- if(stat == DEAD) return
- stat = DEAD
- icon_state = "[colour] baby slime dead"
- overlays.len = 0
- for(var/mob/O in viewers(src, null))
- O.show_message("The [name] seizes up and falls limp...", 1) //ded -- Urist
-
- update_canmove()
- if(blind)
- blind.layer = 0
-
- if(ticker && ticker.mode)
- ticker.mode.check_win()
-
+/mob/living/carbon/slime/death(gibbed)
+ if(!gibbed)
+ if(is_adult)
+ var/mob/living/carbon/slime/M = new /mob/living/carbon/slime(loc)
+ M.colour = colour
+ M.rabid = 1
+ is_adult = 0
+ maxHealth = 150
+ revive()
+ regenerate_icons()
+ number = rand(1, 1000)
+ name = "[colour] [is_adult ? "adult" : "baby"] slime ([number])"
+ return
+
+ if(stat == DEAD) return
+ stat = DEAD
+ icon_state = "[colour] baby slime dead"
+ overlays.len = 0
+ for(var/mob/O in viewers(src, null))
+ O.show_message("The [name] seizes up and falls limp...", 1) //ded -- Urist
+
+ update_canmove()
+ if(blind)
+ blind.layer = 0
+
+ if(ticker && ticker.mode)
+ ticker.mode.check_win()
+
return ..(gibbed)
\ No newline at end of file
diff --git a/code/modules/mob/living/carbon/metroid/emote.dm b/code/modules/mob/living/carbon/slime/emote.dm
similarity index 96%
rename from code/modules/mob/living/carbon/metroid/emote.dm
rename to code/modules/mob/living/carbon/slime/emote.dm
index fa7e5c07466..dcc0b066487 100644
--- a/code/modules/mob/living/carbon/metroid/emote.dm
+++ b/code/modules/mob/living/carbon/slime/emote.dm
@@ -1,74 +1,74 @@
-/mob/living/carbon/slime/emote(var/act, var/m_type=1, var/message = null)
- if (findtext(act, "-", 1, null))
- var/t1 = findtext(act, "-", 1, null)
- //param = copytext(act, t1 + 1, length(act) + 1)
- act = copytext(act, 1, t1)
-
- if(findtext(act,"s",-1) && !findtext(act,"_",-2))//Removes ending s's unless they are prefixed with a '_'
- act = copytext(act,1,length(act))
-
- switch(act) //Alphabetical please
- if ("me")
- if(silent)
- return
- if (src.client)
- if (client.prefs.muted & MUTE_IC)
- src << "\red You cannot send IC messages (muted)."
- return
- if (src.client.handle_spam_prevention(message,MUTE_IC))
- return
- if (stat)
- return
- if(!(message))
- return
- return custom_emote(m_type, message)
- if("bounce")
- message = "The [src.name] bounces in place."
- m_type = 1
-
- if ("custom")
- return custom_emote(m_type, message)
-
- if("jiggle")
- message = "The [src.name] jiggles!"
- m_type = 1
-
- if("light")
- message = "The [src.name] lights up for a bit, then stops."
- m_type = 1
-
- if("moan")
- message = "The [src.name] moans."
- m_type = 2
-
- if("shiver")
- message = "The [src.name] shivers."
- m_type = 2
-
- if("sway")
- message = "The [src.name] sways around dizzily."
- m_type = 1
-
- if("twitch")
- message = "The [src.name] twitches."
- m_type = 1
-
- if("vibrate")
- message = "The [src.name] vibrates!"
- m_type = 1
-
- if ("help") //This is an exception
- src << "Help for slime emotes. You can use these emotes with say \"*emote\":\n\nbounce, custom, jiggle, light, moan, shiver, sway, twitch, vibrate"
-
- else
- src << "\blue Unusable emote '[act]'. Say *help for a list."
- if ((message && src.stat == 0))
- if (m_type & 1)
- for(var/mob/O in viewers(src, null))
- O.show_message(message, m_type)
- //Foreach goto(703)
- else
- for(var/mob/O in hearers(src, null))
- O.show_message(message, m_type)
- //Foreach goto(746)
+/mob/living/carbon/slime/emote(var/act, var/m_type=1, var/message = null)
+ if (findtext(act, "-", 1, null))
+ var/t1 = findtext(act, "-", 1, null)
+ //param = copytext(act, t1 + 1, length(act) + 1)
+ act = copytext(act, 1, t1)
+
+ if(findtext(act,"s",-1) && !findtext(act,"_",-2))//Removes ending s's unless they are prefixed with a '_'
+ act = copytext(act,1,length(act))
+
+ switch(act) //Alphabetical please
+ if ("me")
+ if(silent)
+ return
+ if (src.client)
+ if (client.prefs.muted & MUTE_IC)
+ src << "\red You cannot send IC messages (muted)."
+ return
+ if (src.client.handle_spam_prevention(message,MUTE_IC))
+ return
+ if (stat)
+ return
+ if(!(message))
+ return
+ return custom_emote(m_type, message)
+ if("bounce")
+ message = "The [src.name] bounces in place."
+ m_type = 1
+
+ if ("custom")
+ return custom_emote(m_type, message)
+
+ if("jiggle")
+ message = "The [src.name] jiggles!"
+ m_type = 1
+
+ if("light")
+ message = "The [src.name] lights up for a bit, then stops."
+ m_type = 1
+
+ if("moan")
+ message = "The [src.name] moans."
+ m_type = 2
+
+ if("shiver")
+ message = "The [src.name] shivers."
+ m_type = 2
+
+ if("sway")
+ message = "The [src.name] sways around dizzily."
+ m_type = 1
+
+ if("twitch")
+ message = "The [src.name] twitches."
+ m_type = 1
+
+ if("vibrate")
+ message = "The [src.name] vibrates!"
+ m_type = 1
+
+ if ("help") //This is an exception
+ src << "Help for slime emotes. You can use these emotes with say \"*emote\":\n\nbounce, custom, jiggle, light, moan, shiver, sway, twitch, vibrate"
+
+ else
+ src << "\blue Unusable emote '[act]'. Say *help for a list."
+ if ((message && src.stat == 0))
+ if (m_type & 1)
+ for(var/mob/O in viewers(src, null))
+ O.show_message(message, m_type)
+ //Foreach goto(703)
+ else
+ for(var/mob/O in hearers(src, null))
+ O.show_message(message, m_type)
+ //Foreach goto(746)
return
\ No newline at end of file
diff --git a/code/modules/mob/living/carbon/metroid/examine.dm b/code/modules/mob/living/carbon/slime/examine.dm
similarity index 95%
rename from code/modules/mob/living/carbon/metroid/examine.dm
rename to code/modules/mob/living/carbon/slime/examine.dm
index 67ef5770103..826fa93c22e 100644
--- a/code/modules/mob/living/carbon/metroid/examine.dm
+++ b/code/modules/mob/living/carbon/slime/examine.dm
@@ -1,44 +1,44 @@
-/mob/living/carbon/slime/examine(mob/user)
- ..(user)
- var/msg = ""
- if (src.stat == DEAD)
- msg += "It is limp and unresponsive.\n"
- else
- if (src.getBruteLoss())
- msg += ""
- if (src.getBruteLoss() < 40)
- msg += "It has some punctures in its flesh!"
- else
- msg += "It has severe punctures and tears in its flesh!"
- msg += "\n"
-
- switch(powerlevel)
-
- if(2 to 3)
- msg += "It is flickering gently with a little electrical activity.\n"
-
- if(4 to 5)
- msg += "It is glowing gently with moderate levels of electrical activity.\n"
-
- if(6 to 9)
- msg += "It is glowing brightly with high levels of electrical activity.\n"
-
- if(10)
- msg += "It is radiating with massive levels of electrical activity!\n"
-
- msg += ""
- switch(wetlevel)
- if(1)
- msg += "It looks a bit damp.\n"
- if(2)
- msg += "It looks a little bit wet.\n"
- if(3)
- msg += "It looks wet.\n"
- if(4)
- msg += "It looks very wet.\n"
- if(5)
- msg += "It looks absolutely soaked.\n"
- msg += ""
-
- msg += "*---------*"
+/mob/living/carbon/slime/examine(mob/user)
+ ..(user)
+ var/msg = ""
+ if (src.stat == DEAD)
+ msg += "It is limp and unresponsive.\n"
+ else
+ if (src.getBruteLoss())
+ msg += ""
+ if (src.getBruteLoss() < 40)
+ msg += "It has some punctures in its flesh!"
+ else
+ msg += "It has severe punctures and tears in its flesh!"
+ msg += "\n"
+
+ switch(powerlevel)
+
+ if(2 to 3)
+ msg += "It is flickering gently with a little electrical activity.\n"
+
+ if(4 to 5)
+ msg += "It is glowing gently with moderate levels of electrical activity.\n"
+
+ if(6 to 9)
+ msg += "It is glowing brightly with high levels of electrical activity.\n"
+
+ if(10)
+ msg += "It is radiating with massive levels of electrical activity!\n"
+
+ msg += ""
+ switch(wetlevel)
+ if(1)
+ msg += "It looks a bit damp.\n"
+ if(2)
+ msg += "It looks a little bit wet.\n"
+ if(3)
+ msg += "It looks wet.\n"
+ if(4)
+ msg += "It looks very wet.\n"
+ if(5)
+ msg += "It looks absolutely soaked.\n"
+ msg += ""
+
+ msg += "*---------*"
user << msg
\ No newline at end of file
diff --git a/code/modules/mob/living/carbon/metroid/life.dm b/code/modules/mob/living/carbon/slime/life.dm
similarity index 96%
rename from code/modules/mob/living/carbon/metroid/life.dm
rename to code/modules/mob/living/carbon/slime/life.dm
index b70075a084b..1e3d901755a 100644
--- a/code/modules/mob/living/carbon/metroid/life.dm
+++ b/code/modules/mob/living/carbon/slime/life.dm
@@ -1,552 +1,552 @@
-/mob/living/carbon/slime
- var/AIproc = 0 // determines if the AI loop is activated
- var/Atkcool = 0 // attack cooldown
- var/Tempstun = 0 // temporary temperature stuns
- var/Discipline = 0 // if a slime has been hit with a freeze gun, or wrestled/attacked off a human, they become disciplined and don't attack anymore for a while
- var/SStun = 0 // stun variable
-
-/mob/living/carbon/slime/Life()
- if(..())
- handle_nutrition()
- handle_targets()
- if (!ckey)
- handle_speech_and_mood()
-
-/mob/living/carbon/slime/proc/AIprocess() // the master AI process
-
- if(AIproc || stat == DEAD || client) return
-
- var/hungry = 0
- if (nutrition < get_starve_nutrition())
- hungry = 2
- else if (nutrition < get_grow_nutrition() && prob(25) || nutrition < get_hunger_nutrition())
- hungry = 1
-
- AIproc = 1
-
- while(AIproc && stat != 2 && (attacked || hungry || rabid || Victim))
- if(Victim) // can't eat AND have this little process at the same time
- break
-
- if(!Target || client)
- break
-
- if(Target.health <= -70 || Target.stat == 2)
- Target = null
- AIproc = 0
- break
-
- if(Target)
- for(var/mob/living/carbon/slime/M in view(1,Target))
- if(M.Victim == Target)
- Target = null
- AIproc = 0
- break
- if(!AIproc)
- break
-
- if(Target in view(1,src))
- if(istype(Target, /mob/living/silicon))
- if(!Atkcool)
- Atkcool = 1
- spawn(45)
- Atkcool = 0
-
- if(Target.Adjacent(src))
- Target.attack_slime(src)
- return
- if(!Target.lying && prob(80))
-
- if(Target.client && Target.health >= 20)
- if(!Atkcool)
- Atkcool = 1
- spawn(45)
- Atkcool = 0
-
- if(Target.Adjacent(src))
- Target.attack_slime(src)
-
- else
- if(!Atkcool && Target.Adjacent(src))
- Feedon(Target)
-
- else
- if(!Atkcool && Target.Adjacent(src))
- Feedon(Target)
-
- else
- if(Target in view(7, src))
- if(!Target.Adjacent(src)) // Bug of the month candidate: slimes were attempting to move to target only if it was directly next to them, which caused them to target things, but not approach them
- step_to(src, Target)
- sleep(5)
-
- else
- Target = null
- AIproc = 0
- break
-
- var/sleeptime = movement_delay()
- if(sleeptime <= 0) sleeptime = 1
-
- sleep(sleeptime + 2) // this is about as fast as a player slime can go
-
- AIproc = 0
-
-/mob/living/carbon/slime/handle_environment(datum/gas_mixture/environment)
- if(!environment)
- adjustToxLoss(rand(10,20))
- return
-
- //var/environment_heat_capacity = environment.heat_capacity()
- var/loc_temp = T0C
- if(istype(get_turf(src), /turf/space))
- //environment_heat_capacity = loc:heat_capacity
- var/turf/heat_turf = get_turf(src)
- loc_temp = heat_turf.temperature
- else if(istype(loc, /obj/machinery/atmospherics/unary/cryo_cell))
- loc_temp = loc:air_contents.temperature
- else
- loc_temp = environment.temperature
-
- //Account for massive pressure differences
- if(bodytemperature < (T0C + 5)) // start calculating temperature damage etc
- if(bodytemperature <= (T0C - 40)) // stun temperature
- Tempstun = 1
-
- if(bodytemperature <= (T0C - 50)) // hurt temperature
- if(bodytemperature <= 50) // sqrting negative numbers is bad
- adjustToxLoss(301) //The config.health_threshold_dead is -100 by default, and slimes have 150hp (200hp for adults),
- else //so the ToxLoss needs to be 300 or above to guarrantee an instant death
- adjustToxLoss(round(sqrt(bodytemperature)) * 2)
- else
- Tempstun = 0
-
-
- /*moved after the temperature damage code so freeze beams can instantly kill slimes -Deity Link*/
- if(loc_temp < 310.15) // a cold place
- bodytemperature += adjust_body_temperature(bodytemperature, loc_temp, 1)
- else // a hot place
- bodytemperature += adjust_body_temperature(bodytemperature, loc_temp, 1)
-
- updatehealth()
-
- return //TODO: DEFERRED
-
-/mob/living/carbon/slime/proc/adjust_body_temperature(current, loc_temp, boost)
- var/temperature = current
- var/difference = abs(current-loc_temp) //get difference
- var/increments// = difference/10 //find how many increments apart they are
- if(difference > 50)
- increments = difference/5
- else
- increments = difference/10
- var/change = increments*boost // Get the amount to change by (x per increment)
- var/temp_change
- if(current < loc_temp)
- temperature = min(loc_temp, temperature+change)
- else if(current > loc_temp)
- temperature = max(loc_temp, temperature-change)
- temp_change = (temperature - current)
- return temp_change
-
-/mob/living/carbon/slime/handle_chemicals_in_body()
-
- if(reagents) reagents.metabolize(src)
- if (reagents.get_reagent_amount("plasma")>=5)
- mutation_chance = min(mutation_chance + 5,50) //Prevents mutation chance going >50%
- reagents.remove_reagent("plasma", 5)
- if (reagents.get_reagent_amount("epinephrine")>=5)
- mutation_chance = max(mutation_chance - 5,0) //Prevents muation chance going <0%
- reagents.remove_reagent("epinephrine", 5)
- src.updatehealth()
-
- return //TODO: DEFERRED
-
-/mob/living/carbon/slime/handle_regular_status_updates()
-
- if(is_adult)
- health = 200 - (getOxyLoss() + getToxLoss() + getFireLoss() + getBruteLoss() + getCloneLoss())
- else
- health = 150 - (getOxyLoss() + getToxLoss() + getFireLoss() + getBruteLoss() + getCloneLoss())
-
- if(health < config.health_threshold_dead && stat != 2)
- death()
- return
-
- else if(src.health <= config.health_threshold_crit)
-
- if(!src.reagents.has_reagent("epinephrine"))
- src.adjustOxyLoss(10)
-
- if(src.stat != DEAD)
- src.stat = UNCONSCIOUS
-
- if(prob(30)) //I think this is meant to allow slimes to starve to death
- adjustOxyLoss(-1)
- adjustToxLoss(-1)
- adjustFireLoss(-1)
- adjustCloneLoss(-1)
- adjustBruteLoss(-1)
-
- if (src.stat == DEAD)
- src.lying = 1
- src.blinded = 1
- else
- if (src.paralysis || src.stunned || src.weakened || (status_flags && FAKEDEATH)) //Stunned etc.
- if (src.stunned > 0)
- AdjustStunned(-1)
- src.stat = 0
- if (src.weakened > 0)
- AdjustWeakened(-1)
- src.lying = 0
- src.stat = 0
- if (src.paralysis > 0)
- AdjustParalysis(-1)
- src.blinded = 0
- src.lying = 0
- src.stat = 0
-
- else
- src.lying = 0
- src.stat = 0
-
- if (src.stuttering) src.stuttering = 0
-
- if (src.eye_blind)
- src.eye_blind = 0
- src.blinded = 1
-
- if (src.ear_deaf > 0) src.ear_deaf = 0
- if (src.ear_damage < 25)
- src.ear_damage = 0
-
- src.density = !( src.lying )
-
- if (src.sdisabilities & BLIND)
- src.blinded = 1
- if (src.sdisabilities & DEAF)
- src.ear_deaf = 1
-
- if (src.eye_blurry > 0)
- src.eye_blurry = 0
-
- if (src.druggy > 0)
- src.druggy = 0
-
- return 1
-
-/mob/living/carbon/slime/proc/handle_nutrition()
-
- if (prob(15))
- nutrition -= 1 + is_adult
-
- if(nutrition <= 0)
- nutrition = 0
- if(prob(75))
- adjustToxLoss(rand(0,5))
-
- else if (nutrition >= get_grow_nutrition() && amount_grown < 10)
- nutrition -= 20
- amount_grown++
-
- if(amount_grown >= 10 && !Victim && !Target && !ckey)
- if(is_adult)
- Reproduce()
- else
- Evolve()
-
-
-/mob/living/carbon/slime/proc/handle_targets()
- if(Tempstun)
- if(!Victim) // not while they're eating!
- canmove = 0
- else
- canmove = 1
-
- if(attacked > 50) attacked = 50
-
- if(attacked > 0)
- attacked--
-
- if(Discipline > 0)
-
- if(Discipline >= 5 && rabid)
- if(prob(60)) rabid = 0
-
- if(prob(10))
- Discipline--
-
- if(!client)
- if(!canmove) return
-
- if(Victim) return // if it's eating someone already, continue eating!
-
- if(Target)
- --target_patience
- if (target_patience <= 0 || SStun || Discipline || attacked) // Tired of chasing or something draws out attention
- target_patience = 0
- Target = null
-
- if(AIproc && SStun) return
-
- var/hungry = 0 // determines if the slime is hungry
-
- if (nutrition < get_starve_nutrition())
- hungry = 2
- else if (nutrition < get_grow_nutrition() && prob(25) || nutrition < get_hunger_nutrition())
- hungry = 1
-
- if(hungry == 2 && !client) // if a slime is starving, it starts losing its friends
- if(Friends.len > 0 && prob(1))
- var/mob/nofriend = pick(Friends)
- --Friends[nofriend]
-
- if(!Target)
- if(will_hunt() && hungry || attacked || rabid) // Only add to the list if we need to
- var/list/targets = list()
-
- for(var/mob/living/L in view(7,src))
-
- if(isslime(L) || L.stat == DEAD) // Ignore other slimes and dead mobs
- continue
-
- if(L in Friends) // No eating friends!
- continue
-
- if(issilicon(L) && (rabid || attacked)) // They can't eat silicons, but they can glomp them in defence
- targets += L // Possible target found!
-
- if(istype(L, /mob/living/carbon/human)) //Ignore slime(wo)men
- var/mob/living/carbon/human/H = L
- if(H.species.name == "Slime People")
- continue
-
- if(!L.canmove) // Only one slime can latch on at a time.
- var/notarget = 0
- for(var/mob/living/carbon/slime/M in view(1,L))
- if(M.Victim == L)
- notarget = 1
- if(notarget)
- continue
-
- targets += L // Possible target found!
-
- if(targets.len > 0)
- if(attacked || rabid || hungry == 2)
- Target = targets[1] // I am attacked and am fighting back or so hungry I don't even care
- else
- for(var/mob/living/carbon/C in targets)
- if(!Discipline && prob(5))
- if(ishuman(C) || isalienadult(C))
- Target = C
- break
-
- if(islarva(C) || issmall(C))
- Target = C
- break
-
- if (Target)
- target_patience = rand(5,7)
- if (is_adult)
- target_patience += 3
-
- if(!Target) // If we have no target, we are wandering or following orders
- if (Leader)
- if (holding_still)
- holding_still = max(holding_still - 1, 0)
- else if(canmove && isturf(loc))
- step_to(src, Leader)
-
- else if(hungry)
- if (holding_still)
- holding_still = max(holding_still - hungry, 0)
- else if(canmove && isturf(loc) && prob(50))
- step(src, pick(cardinal))
-
- else
- if (holding_still)
- holding_still = max(holding_still - 1, 0)
- else if(canmove && isturf(loc) && prob(33))
- step(src, pick(cardinal))
- else if(!AIproc)
- spawn()
- AIprocess()
-
-/mob/living/carbon/slime/proc/handle_speech_and_mood()
- //Mood starts here
- var/newmood = ""
- if (rabid || attacked) newmood = "angry"
- else if (Target) newmood = "mischevous"
-
- if (!newmood)
- if (Discipline && prob(25))
- newmood = "pout"
- else if (prob(1))
- newmood = pick("sad", ":3", "pout")
-
- if ((mood == "sad" || mood == ":3" || mood == "pout") && !newmood)
- if (prob(75)) newmood = mood
-
- if (newmood != mood) // This is so we don't redraw them every time
- mood = newmood
- regenerate_icons()
-
- //Speech understanding starts here
- var/to_say
- if (speech_buffer.len > 0)
- var/who = speech_buffer[1] // Who said it?
- var/phrase = speech_buffer[2] // What did they say?
- if ((findtext(phrase, num2text(number)) || findtext(phrase, "slimes"))) // Talking to us
- if (findtext(phrase, "hello") || findtext(phrase, "hi"))
- to_say = pick("Hello...", "Hi...")
- else if (findtext(phrase, "follow"))
- if (Leader)
- if (Leader == who) // Already following him
- to_say = pick("Yes...", "Lead...", "Following...")
- else if (Friends[who] > Friends[Leader]) // VIVA
- Leader = who
- to_say = "Yes... I follow [who]..."
- else
- to_say = "No... I follow [Leader]..."
- else
- if (Friends[who] > 2)
- Leader = who
- to_say = "I follow..."
- else // Not friendly enough
- to_say = pick("No...", "I won't follow...")
- else if (findtext(phrase, "stop"))
- if (Victim) // We are asked to stop feeding
- if (Friends[who] > 4)
- Victim = null
- Target = null
- if (Friends[who] < 7)
- --Friends[who]
- to_say = "Grrr..." // I'm angry but I do it
- else
- to_say = "Fine..."
- else if (Target) // We are asked to stop chasing
- if (Friends[who] > 3)
- Target = null
- if (Friends[who] < 6)
- --Friends[who]
- to_say = "Grrr..." // I'm angry but I do it
- else
- to_say = "Fine..."
- else if (Leader) // We are asked to stop following
- if (Leader == who)
- to_say = "Yes... I'll stay..."
- Leader = null
- else
- if (Friends[who] > Friends[Leader])
- Leader = null
- to_say = "Yes... I'll stop..."
- else
- to_say = "No... I'll keep following..."
- else if (findtext(phrase, "stay"))
- if (Leader)
- if (Leader == who)
- holding_still = Friends[who] * 10
- to_say = "Yes... Staying..."
- else if (Friends[who] > Friends[Leader])
- holding_still = (Friends[who] - Friends[Leader]) * 10
- to_say = "Yes... Staying..."
- else
- to_say = "No... I'll keep following..."
- else
- if (Friends[who] > 2)
- holding_still = Friends[who] * 10
- to_say = "Yes... Staying..."
- else
- to_say = "No... I won't stay..."
- speech_buffer = list()
-
- //Speech starts here
- if (to_say)
- say (to_say)
- else if(prob(1))
- emote(pick("bounce","sway","light","vibrate","jiggle"))
- else
- var/t = 10
- var/slimes_near = -1 // Don't count myself
- var/dead_slimes = 0
- var/friends_near = list()
- for (var/mob/living/carbon/M in view(7,src))
- if (isslime(M))
- ++slimes_near
- if (M.stat == DEAD)
- ++dead_slimes
- if (M in Friends)
- t += 20
- friends_near += M
- if (nutrition < get_hunger_nutrition()) t += 10
- if (nutrition < get_starve_nutrition()) t += 10
- if (prob(2) && prob(t))
- var/phrases = list()
- if (Target) phrases += "[Target]... looks tasty..."
- if (nutrition < get_starve_nutrition())
- phrases += "So... hungry..."
- phrases += "Very... hungry..."
- phrases += "Need... food..."
- phrases += "Must... eat..."
- else if (nutrition < get_hunger_nutrition())
- phrases += "Hungry..."
- phrases += "Where is the food?"
- phrases += "I want to eat..."
- phrases += "Rawr..."
- phrases += "Blop..."
- phrases += "Blorble..."
- if (rabid || attacked)
- phrases += "Hrr..."
- phrases += "Nhuu..."
- phrases += "Unn..."
- if (mood == ":3")
- phrases += "Purr..."
- if (attacked)
- phrases += "Grrr..."
- if (getToxLoss() > 30)
- phrases += "Cold..."
- if (getToxLoss() > 60)
- phrases += "So... cold..."
- phrases += "Very... cold..."
- if (getToxLoss() > 90)
- phrases += "..."
- phrases += "C... c..."
- if (Victim)
- phrases += "Nom..."
- phrases += "Tasty..."
- if (powerlevel > 3) phrases += "Bzzz..."
- if (powerlevel > 5) phrases += "Zap..."
- if (powerlevel > 8) phrases += "Zap... Bzz..."
- if (mood == "sad") phrases += "Bored..."
- if (slimes_near) phrases += "Brother..."
- if (slimes_near > 1) phrases += "Brothers..."
- if (dead_slimes) phrases += "What happened?"
- if (!slimes_near)
- phrases += "Lonely..."
- for (var/M in friends_near)
- phrases += "[M]... friend..."
- if (nutrition < get_hunger_nutrition())
- phrases += "[M]... feed me..."
- say (pick(phrases))
-
-/mob/living/carbon/slime/proc/get_max_nutrition() // Can't go above it
- if (is_adult) return 1200
- else return 1000
-
-/mob/living/carbon/slime/proc/get_grow_nutrition() // Above it we grow, below it we can eat
- if (is_adult) return 1000
- else return 800
-
-/mob/living/carbon/slime/proc/get_hunger_nutrition() // Below it we will always eat
- if (is_adult) return 600
- else return 500
-
-/mob/living/carbon/slime/proc/get_starve_nutrition() // Below it we will eat before everything else
- if (is_adult) return 300
- else return 200
-
-/mob/living/carbon/slime/proc/will_hunt(var/hunger = -1) // Check for being stopped from feeding and chasing
- if (hunger == 2 || rabid || attacked) return 1
- if (Leader) return 0
- if (holding_still) return 0
- return 1
+/mob/living/carbon/slime
+ var/AIproc = 0 // determines if the AI loop is activated
+ var/Atkcool = 0 // attack cooldown
+ var/Tempstun = 0 // temporary temperature stuns
+ var/Discipline = 0 // if a slime has been hit with a freeze gun, or wrestled/attacked off a human, they become disciplined and don't attack anymore for a while
+ var/SStun = 0 // stun variable
+
+/mob/living/carbon/slime/Life()
+ if(..())
+ handle_nutrition()
+ handle_targets()
+ if (!ckey)
+ handle_speech_and_mood()
+
+/mob/living/carbon/slime/proc/AIprocess() // the master AI process
+
+ if(AIproc || stat == DEAD || client) return
+
+ var/hungry = 0
+ if (nutrition < get_starve_nutrition())
+ hungry = 2
+ else if (nutrition < get_grow_nutrition() && prob(25) || nutrition < get_hunger_nutrition())
+ hungry = 1
+
+ AIproc = 1
+
+ while(AIproc && stat != 2 && (attacked || hungry || rabid || Victim))
+ if(Victim) // can't eat AND have this little process at the same time
+ break
+
+ if(!Target || client)
+ break
+
+ if(Target.health <= -70 || Target.stat == 2)
+ Target = null
+ AIproc = 0
+ break
+
+ if(Target)
+ for(var/mob/living/carbon/slime/M in view(1,Target))
+ if(M.Victim == Target)
+ Target = null
+ AIproc = 0
+ break
+ if(!AIproc)
+ break
+
+ if(Target in view(1,src))
+ if(istype(Target, /mob/living/silicon))
+ if(!Atkcool)
+ Atkcool = 1
+ spawn(45)
+ Atkcool = 0
+
+ if(Target.Adjacent(src))
+ Target.attack_slime(src)
+ return
+ if(!Target.lying && prob(80))
+
+ if(Target.client && Target.health >= 20)
+ if(!Atkcool)
+ Atkcool = 1
+ spawn(45)
+ Atkcool = 0
+
+ if(Target.Adjacent(src))
+ Target.attack_slime(src)
+
+ else
+ if(!Atkcool && Target.Adjacent(src))
+ Feedon(Target)
+
+ else
+ if(!Atkcool && Target.Adjacent(src))
+ Feedon(Target)
+
+ else
+ if(Target in view(7, src))
+ if(!Target.Adjacent(src)) // Bug of the month candidate: slimes were attempting to move to target only if it was directly next to them, which caused them to target things, but not approach them
+ step_to(src, Target)
+ sleep(5)
+
+ else
+ Target = null
+ AIproc = 0
+ break
+
+ var/sleeptime = movement_delay()
+ if(sleeptime <= 0) sleeptime = 1
+
+ sleep(sleeptime + 2) // this is about as fast as a player slime can go
+
+ AIproc = 0
+
+/mob/living/carbon/slime/handle_environment(datum/gas_mixture/environment)
+ if(!environment)
+ adjustToxLoss(rand(10,20))
+ return
+
+ //var/environment_heat_capacity = environment.heat_capacity()
+ var/loc_temp = T0C
+ if(istype(get_turf(src), /turf/space))
+ //environment_heat_capacity = loc:heat_capacity
+ var/turf/heat_turf = get_turf(src)
+ loc_temp = heat_turf.temperature
+ else if(istype(loc, /obj/machinery/atmospherics/unary/cryo_cell))
+ loc_temp = loc:air_contents.temperature
+ else
+ loc_temp = environment.temperature
+
+ //Account for massive pressure differences
+ if(bodytemperature < (T0C + 5)) // start calculating temperature damage etc
+ if(bodytemperature <= (T0C - 40)) // stun temperature
+ Tempstun = 1
+
+ if(bodytemperature <= (T0C - 50)) // hurt temperature
+ if(bodytemperature <= 50) // sqrting negative numbers is bad
+ adjustToxLoss(301) //The config.health_threshold_dead is -100 by default, and slimes have 150hp (200hp for adults),
+ else //so the ToxLoss needs to be 300 or above to guarrantee an instant death
+ adjustToxLoss(round(sqrt(bodytemperature)) * 2)
+ else
+ Tempstun = 0
+
+
+ /*moved after the temperature damage code so freeze beams can instantly kill slimes -Deity Link*/
+ if(loc_temp < 310.15) // a cold place
+ bodytemperature += adjust_body_temperature(bodytemperature, loc_temp, 1)
+ else // a hot place
+ bodytemperature += adjust_body_temperature(bodytemperature, loc_temp, 1)
+
+ updatehealth()
+
+ return //TODO: DEFERRED
+
+/mob/living/carbon/slime/proc/adjust_body_temperature(current, loc_temp, boost)
+ var/temperature = current
+ var/difference = abs(current-loc_temp) //get difference
+ var/increments// = difference/10 //find how many increments apart they are
+ if(difference > 50)
+ increments = difference/5
+ else
+ increments = difference/10
+ var/change = increments*boost // Get the amount to change by (x per increment)
+ var/temp_change
+ if(current < loc_temp)
+ temperature = min(loc_temp, temperature+change)
+ else if(current > loc_temp)
+ temperature = max(loc_temp, temperature-change)
+ temp_change = (temperature - current)
+ return temp_change
+
+/mob/living/carbon/slime/handle_chemicals_in_body()
+
+ if(reagents) reagents.metabolize(src)
+ if (reagents.get_reagent_amount("plasma")>=5)
+ mutation_chance = min(mutation_chance + 5,50) //Prevents mutation chance going >50%
+ reagents.remove_reagent("plasma", 5)
+ if (reagents.get_reagent_amount("epinephrine")>=5)
+ mutation_chance = max(mutation_chance - 5,0) //Prevents muation chance going <0%
+ reagents.remove_reagent("epinephrine", 5)
+ src.updatehealth()
+
+ return //TODO: DEFERRED
+
+/mob/living/carbon/slime/handle_regular_status_updates()
+
+ if(is_adult)
+ health = 200 - (getOxyLoss() + getToxLoss() + getFireLoss() + getBruteLoss() + getCloneLoss())
+ else
+ health = 150 - (getOxyLoss() + getToxLoss() + getFireLoss() + getBruteLoss() + getCloneLoss())
+
+ if(health < config.health_threshold_dead && stat != 2)
+ death()
+ return
+
+ else if(src.health <= config.health_threshold_crit)
+
+ if(!src.reagents.has_reagent("epinephrine"))
+ src.adjustOxyLoss(10)
+
+ if(src.stat != DEAD)
+ src.stat = UNCONSCIOUS
+
+ if(prob(30)) //I think this is meant to allow slimes to starve to death
+ adjustOxyLoss(-1)
+ adjustToxLoss(-1)
+ adjustFireLoss(-1)
+ adjustCloneLoss(-1)
+ adjustBruteLoss(-1)
+
+ if (src.stat == DEAD)
+ src.lying = 1
+ src.blinded = 1
+ else
+ if (src.paralysis || src.stunned || src.weakened || (status_flags && FAKEDEATH)) //Stunned etc.
+ if (src.stunned > 0)
+ AdjustStunned(-1)
+ src.stat = 0
+ if (src.weakened > 0)
+ AdjustWeakened(-1)
+ src.lying = 0
+ src.stat = 0
+ if (src.paralysis > 0)
+ AdjustParalysis(-1)
+ src.blinded = 0
+ src.lying = 0
+ src.stat = 0
+
+ else
+ src.lying = 0
+ src.stat = 0
+
+ if (src.stuttering) src.stuttering = 0
+
+ if (src.eye_blind)
+ src.eye_blind = 0
+ src.blinded = 1
+
+ if (src.ear_deaf > 0) src.ear_deaf = 0
+ if (src.ear_damage < 25)
+ src.ear_damage = 0
+
+ src.density = !( src.lying )
+
+ if (src.sdisabilities & BLIND)
+ src.blinded = 1
+ if (src.sdisabilities & DEAF)
+ src.ear_deaf = 1
+
+ if (src.eye_blurry > 0)
+ src.eye_blurry = 0
+
+ if (src.druggy > 0)
+ src.druggy = 0
+
+ return 1
+
+/mob/living/carbon/slime/proc/handle_nutrition()
+
+ if (prob(15))
+ nutrition -= 1 + is_adult
+
+ if(nutrition <= 0)
+ nutrition = 0
+ if(prob(75))
+ adjustToxLoss(rand(0,5))
+
+ else if (nutrition >= get_grow_nutrition() && amount_grown < 10)
+ nutrition -= 20
+ amount_grown++
+
+ if(amount_grown >= 10 && !Victim && !Target && !ckey)
+ if(is_adult)
+ Reproduce()
+ else
+ Evolve()
+
+
+/mob/living/carbon/slime/proc/handle_targets()
+ if(Tempstun)
+ if(!Victim) // not while they're eating!
+ canmove = 0
+ else
+ canmove = 1
+
+ if(attacked > 50) attacked = 50
+
+ if(attacked > 0)
+ attacked--
+
+ if(Discipline > 0)
+
+ if(Discipline >= 5 && rabid)
+ if(prob(60)) rabid = 0
+
+ if(prob(10))
+ Discipline--
+
+ if(!client)
+ if(!canmove) return
+
+ if(Victim) return // if it's eating someone already, continue eating!
+
+ if(Target)
+ --target_patience
+ if (target_patience <= 0 || SStun || Discipline || attacked) // Tired of chasing or something draws out attention
+ target_patience = 0
+ Target = null
+
+ if(AIproc && SStun) return
+
+ var/hungry = 0 // determines if the slime is hungry
+
+ if (nutrition < get_starve_nutrition())
+ hungry = 2
+ else if (nutrition < get_grow_nutrition() && prob(25) || nutrition < get_hunger_nutrition())
+ hungry = 1
+
+ if(hungry == 2 && !client) // if a slime is starving, it starts losing its friends
+ if(Friends.len > 0 && prob(1))
+ var/mob/nofriend = pick(Friends)
+ --Friends[nofriend]
+
+ if(!Target)
+ if(will_hunt() && hungry || attacked || rabid) // Only add to the list if we need to
+ var/list/targets = list()
+
+ for(var/mob/living/L in view(7,src))
+
+ if(isslime(L) || L.stat == DEAD) // Ignore other slimes and dead mobs
+ continue
+
+ if(L in Friends) // No eating friends!
+ continue
+
+ if(issilicon(L) && (rabid || attacked)) // They can't eat silicons, but they can glomp them in defence
+ targets += L // Possible target found!
+
+ if(istype(L, /mob/living/carbon/human)) //Ignore slime(wo)men
+ var/mob/living/carbon/human/H = L
+ if(H.species.name == "Slime People")
+ continue
+
+ if(!L.canmove) // Only one slime can latch on at a time.
+ var/notarget = 0
+ for(var/mob/living/carbon/slime/M in view(1,L))
+ if(M.Victim == L)
+ notarget = 1
+ if(notarget)
+ continue
+
+ targets += L // Possible target found!
+
+ if(targets.len > 0)
+ if(attacked || rabid || hungry == 2)
+ Target = targets[1] // I am attacked and am fighting back or so hungry I don't even care
+ else
+ for(var/mob/living/carbon/C in targets)
+ if(!Discipline && prob(5))
+ if(ishuman(C) || isalienadult(C))
+ Target = C
+ break
+
+ if(islarva(C) || issmall(C))
+ Target = C
+ break
+
+ if (Target)
+ target_patience = rand(5,7)
+ if (is_adult)
+ target_patience += 3
+
+ if(!Target) // If we have no target, we are wandering or following orders
+ if (Leader)
+ if (holding_still)
+ holding_still = max(holding_still - 1, 0)
+ else if(canmove && isturf(loc))
+ step_to(src, Leader)
+
+ else if(hungry)
+ if (holding_still)
+ holding_still = max(holding_still - hungry, 0)
+ else if(canmove && isturf(loc) && prob(50))
+ step(src, pick(cardinal))
+
+ else
+ if (holding_still)
+ holding_still = max(holding_still - 1, 0)
+ else if(canmove && isturf(loc) && prob(33))
+ step(src, pick(cardinal))
+ else if(!AIproc)
+ spawn()
+ AIprocess()
+
+/mob/living/carbon/slime/proc/handle_speech_and_mood()
+ //Mood starts here
+ var/newmood = ""
+ if (rabid || attacked) newmood = "angry"
+ else if (Target) newmood = "mischevous"
+
+ if (!newmood)
+ if (Discipline && prob(25))
+ newmood = "pout"
+ else if (prob(1))
+ newmood = pick("sad", ":3", "pout")
+
+ if ((mood == "sad" || mood == ":3" || mood == "pout") && !newmood)
+ if (prob(75)) newmood = mood
+
+ if (newmood != mood) // This is so we don't redraw them every time
+ mood = newmood
+ regenerate_icons()
+
+ //Speech understanding starts here
+ var/to_say
+ if (speech_buffer.len > 0)
+ var/who = speech_buffer[1] // Who said it?
+ var/phrase = speech_buffer[2] // What did they say?
+ if ((findtext(phrase, num2text(number)) || findtext(phrase, "slimes"))) // Talking to us
+ if (findtext(phrase, "hello") || findtext(phrase, "hi"))
+ to_say = pick("Hello...", "Hi...")
+ else if (findtext(phrase, "follow"))
+ if (Leader)
+ if (Leader == who) // Already following him
+ to_say = pick("Yes...", "Lead...", "Following...")
+ else if (Friends[who] > Friends[Leader]) // VIVA
+ Leader = who
+ to_say = "Yes... I follow [who]..."
+ else
+ to_say = "No... I follow [Leader]..."
+ else
+ if (Friends[who] > 2)
+ Leader = who
+ to_say = "I follow..."
+ else // Not friendly enough
+ to_say = pick("No...", "I won't follow...")
+ else if (findtext(phrase, "stop"))
+ if (Victim) // We are asked to stop feeding
+ if (Friends[who] > 4)
+ Victim = null
+ Target = null
+ if (Friends[who] < 7)
+ --Friends[who]
+ to_say = "Grrr..." // I'm angry but I do it
+ else
+ to_say = "Fine..."
+ else if (Target) // We are asked to stop chasing
+ if (Friends[who] > 3)
+ Target = null
+ if (Friends[who] < 6)
+ --Friends[who]
+ to_say = "Grrr..." // I'm angry but I do it
+ else
+ to_say = "Fine..."
+ else if (Leader) // We are asked to stop following
+ if (Leader == who)
+ to_say = "Yes... I'll stay..."
+ Leader = null
+ else
+ if (Friends[who] > Friends[Leader])
+ Leader = null
+ to_say = "Yes... I'll stop..."
+ else
+ to_say = "No... I'll keep following..."
+ else if (findtext(phrase, "stay"))
+ if (Leader)
+ if (Leader == who)
+ holding_still = Friends[who] * 10
+ to_say = "Yes... Staying..."
+ else if (Friends[who] > Friends[Leader])
+ holding_still = (Friends[who] - Friends[Leader]) * 10
+ to_say = "Yes... Staying..."
+ else
+ to_say = "No... I'll keep following..."
+ else
+ if (Friends[who] > 2)
+ holding_still = Friends[who] * 10
+ to_say = "Yes... Staying..."
+ else
+ to_say = "No... I won't stay..."
+ speech_buffer = list()
+
+ //Speech starts here
+ if (to_say)
+ say (to_say)
+ else if(prob(1))
+ emote(pick("bounce","sway","light","vibrate","jiggle"))
+ else
+ var/t = 10
+ var/slimes_near = -1 // Don't count myself
+ var/dead_slimes = 0
+ var/friends_near = list()
+ for (var/mob/living/carbon/M in view(7,src))
+ if (isslime(M))
+ ++slimes_near
+ if (M.stat == DEAD)
+ ++dead_slimes
+ if (M in Friends)
+ t += 20
+ friends_near += M
+ if (nutrition < get_hunger_nutrition()) t += 10
+ if (nutrition < get_starve_nutrition()) t += 10
+ if (prob(2) && prob(t))
+ var/phrases = list()
+ if (Target) phrases += "[Target]... looks tasty..."
+ if (nutrition < get_starve_nutrition())
+ phrases += "So... hungry..."
+ phrases += "Very... hungry..."
+ phrases += "Need... food..."
+ phrases += "Must... eat..."
+ else if (nutrition < get_hunger_nutrition())
+ phrases += "Hungry..."
+ phrases += "Where is the food?"
+ phrases += "I want to eat..."
+ phrases += "Rawr..."
+ phrases += "Blop..."
+ phrases += "Blorble..."
+ if (rabid || attacked)
+ phrases += "Hrr..."
+ phrases += "Nhuu..."
+ phrases += "Unn..."
+ if (mood == ":3")
+ phrases += "Purr..."
+ if (attacked)
+ phrases += "Grrr..."
+ if (getToxLoss() > 30)
+ phrases += "Cold..."
+ if (getToxLoss() > 60)
+ phrases += "So... cold..."
+ phrases += "Very... cold..."
+ if (getToxLoss() > 90)
+ phrases += "..."
+ phrases += "C... c..."
+ if (Victim)
+ phrases += "Nom..."
+ phrases += "Tasty..."
+ if (powerlevel > 3) phrases += "Bzzz..."
+ if (powerlevel > 5) phrases += "Zap..."
+ if (powerlevel > 8) phrases += "Zap... Bzz..."
+ if (mood == "sad") phrases += "Bored..."
+ if (slimes_near) phrases += "Brother..."
+ if (slimes_near > 1) phrases += "Brothers..."
+ if (dead_slimes) phrases += "What happened?"
+ if (!slimes_near)
+ phrases += "Lonely..."
+ for (var/M in friends_near)
+ phrases += "[M]... friend..."
+ if (nutrition < get_hunger_nutrition())
+ phrases += "[M]... feed me..."
+ say (pick(phrases))
+
+/mob/living/carbon/slime/proc/get_max_nutrition() // Can't go above it
+ if (is_adult) return 1200
+ else return 1000
+
+/mob/living/carbon/slime/proc/get_grow_nutrition() // Above it we grow, below it we can eat
+ if (is_adult) return 1000
+ else return 800
+
+/mob/living/carbon/slime/proc/get_hunger_nutrition() // Below it we will always eat
+ if (is_adult) return 600
+ else return 500
+
+/mob/living/carbon/slime/proc/get_starve_nutrition() // Below it we will eat before everything else
+ if (is_adult) return 300
+ else return 200
+
+/mob/living/carbon/slime/proc/will_hunt(var/hunger = -1) // Check for being stopped from feeding and chasing
+ if (hunger == 2 || rabid || attacked) return 1
+ if (Leader) return 0
+ if (holding_still) return 0
+ return 1
diff --git a/code/modules/mob/living/carbon/metroid/login.dm b/code/modules/mob/living/carbon/slime/login.dm
similarity index 93%
rename from code/modules/mob/living/carbon/metroid/login.dm
rename to code/modules/mob/living/carbon/slime/login.dm
index 8ca29bf4818..d3ac320f2f4 100644
--- a/code/modules/mob/living/carbon/metroid/login.dm
+++ b/code/modules/mob/living/carbon/slime/login.dm
@@ -1,4 +1,4 @@
-/mob/living/carbon/slime/Login()
- ..()
- update_hud()
- return
+/mob/living/carbon/slime/Login()
+ ..()
+ update_hud()
+ return
diff --git a/code/modules/mob/living/carbon/metroid/powers.dm b/code/modules/mob/living/carbon/slime/powers.dm
similarity index 95%
rename from code/modules/mob/living/carbon/metroid/powers.dm
rename to code/modules/mob/living/carbon/slime/powers.dm
index fdbe54a9220..494bb6eb6df 100644
--- a/code/modules/mob/living/carbon/metroid/powers.dm
+++ b/code/modules/mob/living/carbon/slime/powers.dm
@@ -1,228 +1,228 @@
-/mob/living/carbon/slime/verb/Feed()
- set category = "Slime"
- set desc = "This will let you feed on any valid creature in the surrounding area. This should also be used to halt the feeding process."
- if(Victim)
- Feedstop()
- return
-
- if(stat)
- src << "I must be conscious to do this..."
- return
-
- var/list/choices = list()
- for(var/mob/living/C in view(1,src))
- if(C!=src && !istype(C,/mob/living/carbon/slime) && Adjacent(C))
- choices += C
-
- var/mob/living/M = input(src,"Who do you wish to feed on?") in null|choices
- if(!M) return
- if(Adjacent(M))
-
- if(!istype(src, /mob/living/carbon/brain))
- if(!istype(M, /mob/living/carbon/slime))
- if(stat != 2)
- if(health > -70)
-
- for(var/mob/living/carbon/slime/met in view())
- if(met.Victim == M && met != src)
- src << "The [met.name] is already feeding on this subject..."
- return
- src << "\blue I have latched onto the subject and begun feeding..."
- M << "\red The [src.name] has latched onto your head!"
- Feedon(M)
-
- else
- src << "This subject does not have a strong enough life energy..."
- else
- src << "This subject does not have an edible life energy..."
- else
- src << "I must not feed on my brothers..."
- else
- src << "This subject does not have an edible life energy..."
-
-
-
-/mob/living/carbon/slime/proc/Feedon(var/mob/living/M)
- Victim = M
- src.loc = M.loc
- canmove = 0
- anchored = 1
- var/lastnut = nutrition
- var/fed_succesfully = 0
- if(is_adult)
- icon_state = "[colour] adult slime eat"
- else
- icon_state = "[colour] baby slime eat"
-
- while(Victim && M.health > -70 && M.stat != DEAD && stat != DEAD)
- canmove = 0
-
- if(Adjacent(M))
- loc = M.loc
-
- if(prob(15) && M.client && istype(M, /mob/living/carbon))
- M << "[pick("You can feel your body becoming weak!", \
- "You feel like you're about to die!", \
- "You feel every part of your body screaming in agony!", \
- "A low, rolling pain passes through your body!", \
- "Your body feels as if it's falling apart!", \
- "You feel extremely weak!", \
- "A sharp, deep pain bathes every inch of your body!")]"
-
- if(istype(M, /mob/living/carbon))
- Victim.adjustCloneLoss(rand(5,6))
- Victim.adjustToxLoss(rand(1,2))
- if(Victim.health <= 0)
- Victim.adjustToxLoss(rand(2,4))
-
- fed_succesfully = 1
-
- else if(istype(M, /mob/living/simple_animal))
- Victim.adjustBruteLoss(is_adult ? rand(7, 15) : rand(4, 12))
- fed_succesfully = 1
-
- else
- if(prob(25))
- src << "[pick("This subject is incompatable", \
- "This subject does not have a life energy", "This subject is empty", \
- "I am not satisified", "I can not feed from this subject", \
- "I do not feel nourished", "This subject is not food")]..."
-
- if(fed_succesfully)
- //I have no idea why this is not in handle_nutrition()
- nutrition += rand(15,30)
- if(nutrition >= lastnut + 50)
- if(prob(80))
- lastnut = nutrition
- powerlevel++
- if(powerlevel > 10)
- powerlevel = 10
- adjustToxLoss(-10)
-
- //Heal yourself.
- adjustOxyLoss(-10)
- adjustBruteLoss(-10)
- adjustFireLoss(-10)
- adjustCloneLoss(-10)
-
- updatehealth()
- if(Victim)
- Victim.updatehealth()
-
- sleep(rand(15,45))
-
- else
- break
-
- if(stat == 2)
- if(!is_adult)
- icon_state = "[colour] baby slime dead"
-
- else
- if(is_adult)
- icon_state = "[colour] adult slime"
- else
- icon_state = "[colour] baby slime"
-
- canmove = 1
- anchored = 0
-
- if(M)
- if(M.health <= -70)
- M.canmove = 0
- if(!client)
- if(Victim && !rabid && !attacked)
- if(Victim.LAssailant && Victim.LAssailant != Victim)
- if(prob(50))
- if(!(Victim.LAssailant in Friends))
- Friends[Victim.LAssailant] = 1
- //Friends.Add(Victim.LAssailant) // no idea why i was using the |= operator
- else
- ++Friends[Victim.LAssailant]
-
-
- if(M.client && istype(src, /mob/living/carbon/human))
- if(prob(85))
- rabid = 1 // UUUNNBGHHHH GONNA EAT JUUUUUU
-
- if(client) src << "This subject does not have a strong enough life energy anymore..."
- else
- M.canmove = 1
-
- if(client) src << "I have stopped feeding..."
- else
- if(client) src << "I have stopped feeding..."
-
- Victim = null
-
-/mob/living/carbon/slime/proc/Feedstop()
- if(Victim)
- if(Victim.client) Victim << "[src] has let go of your head!"
- Victim = null
-
-/mob/living/carbon/slime/proc/UpdateFeed(var/mob/M)
- if(Victim)
- if(Victim == M)
- loc = M.loc // simple "attach to head" effect!
-
-
-/mob/living/carbon/slime/verb/Evolve()
- set category = "Slime"
- set desc = "This will let you evolve from baby to adult slime."
-
- if(stat)
- src << "I must be conscious to do this..."
- return
- if(!is_adult)
- if(amount_grown >= 10)
- is_adult = 1
- maxHealth = 200
- amount_grown = 0
- regenerate_icons()
- name = text("[colour] [is_adult ? "adult" : "baby"] slime ([number])")
- else
- src << "I am not ready to evolve yet..."
- else
- src << "I have already evolved..."
-
-/mob/living/carbon/slime/verb/Reproduce()
- set category = "Slime"
- set desc = "This will make you split into four Slimes."
-
- if(stat)
- src << "I must be conscious to do this..."
- return
-
- if(is_adult)
- if(amount_grown >= 10)
- if(stat)
- src << "I must be conscious to do this..."
- return
-
- var/list/babies = list()
- var/new_nutrition = round(nutrition * 0.9)
- var/new_powerlevel = round(powerlevel / 4)
- for(var/i=1,i<=4,i++)
- var/mob/living/carbon/slime/M = new /mob/living/carbon/slime/(loc)
- if(prob(mutation_chance))
- M.colour = slime_mutation[rand(1,4)]
- else
- M.colour = colour
- if(ckey) M.nutrition = new_nutrition //Player slimes are more robust at spliting. Once an oversight of poor copypasta, now a feature!
- M.powerlevel = new_powerlevel
- if(i != 1) step_away(M,src)
- M.Friends = Friends.Copy()
- babies += M
- feedback_add_details("slime_babies_born","slimebirth_[replacetext(M.colour," ","_")]")
-
- var/mob/living/carbon/slime/new_slime = pick(babies)
- new_slime.universal_speak = universal_speak
- if(src.mind)
- src.mind.transfer_to(new_slime)
- else
- new_slime.key = src.key
- qdel(src)
- else
- src << "I am not ready to reproduce yet..."
- else
+/mob/living/carbon/slime/verb/Feed()
+ set category = "Slime"
+ set desc = "This will let you feed on any valid creature in the surrounding area. This should also be used to halt the feeding process."
+ if(Victim)
+ Feedstop()
+ return
+
+ if(stat)
+ src << "I must be conscious to do this..."
+ return
+
+ var/list/choices = list()
+ for(var/mob/living/C in view(1,src))
+ if(C!=src && !istype(C,/mob/living/carbon/slime) && Adjacent(C))
+ choices += C
+
+ var/mob/living/M = input(src,"Who do you wish to feed on?") in null|choices
+ if(!M) return
+ if(Adjacent(M))
+
+ if(!istype(src, /mob/living/carbon/brain))
+ if(!istype(M, /mob/living/carbon/slime))
+ if(stat != 2)
+ if(health > -70)
+
+ for(var/mob/living/carbon/slime/met in view())
+ if(met.Victim == M && met != src)
+ src << "The [met.name] is already feeding on this subject..."
+ return
+ src << "\blue I have latched onto the subject and begun feeding..."
+ M << "\red The [src.name] has latched onto your head!"
+ Feedon(M)
+
+ else
+ src << "This subject does not have a strong enough life energy..."
+ else
+ src << "This subject does not have an edible life energy..."
+ else
+ src << "I must not feed on my brothers..."
+ else
+ src << "This subject does not have an edible life energy..."
+
+
+
+/mob/living/carbon/slime/proc/Feedon(var/mob/living/M)
+ Victim = M
+ src.loc = M.loc
+ canmove = 0
+ anchored = 1
+ var/lastnut = nutrition
+ var/fed_succesfully = 0
+ if(is_adult)
+ icon_state = "[colour] adult slime eat"
+ else
+ icon_state = "[colour] baby slime eat"
+
+ while(Victim && M.health > -70 && M.stat != DEAD && stat != DEAD)
+ canmove = 0
+
+ if(Adjacent(M))
+ loc = M.loc
+
+ if(prob(15) && M.client && istype(M, /mob/living/carbon))
+ M << "[pick("You can feel your body becoming weak!", \
+ "You feel like you're about to die!", \
+ "You feel every part of your body screaming in agony!", \
+ "A low, rolling pain passes through your body!", \
+ "Your body feels as if it's falling apart!", \
+ "You feel extremely weak!", \
+ "A sharp, deep pain bathes every inch of your body!")]"
+
+ if(istype(M, /mob/living/carbon))
+ Victim.adjustCloneLoss(rand(5,6))
+ Victim.adjustToxLoss(rand(1,2))
+ if(Victim.health <= 0)
+ Victim.adjustToxLoss(rand(2,4))
+
+ fed_succesfully = 1
+
+ else if(istype(M, /mob/living/simple_animal))
+ Victim.adjustBruteLoss(is_adult ? rand(7, 15) : rand(4, 12))
+ fed_succesfully = 1
+
+ else
+ if(prob(25))
+ src << "[pick("This subject is incompatable", \
+ "This subject does not have a life energy", "This subject is empty", \
+ "I am not satisified", "I can not feed from this subject", \
+ "I do not feel nourished", "This subject is not food")]..."
+
+ if(fed_succesfully)
+ //I have no idea why this is not in handle_nutrition()
+ nutrition += rand(15,30)
+ if(nutrition >= lastnut + 50)
+ if(prob(80))
+ lastnut = nutrition
+ powerlevel++
+ if(powerlevel > 10)
+ powerlevel = 10
+ adjustToxLoss(-10)
+
+ //Heal yourself.
+ adjustOxyLoss(-10)
+ adjustBruteLoss(-10)
+ adjustFireLoss(-10)
+ adjustCloneLoss(-10)
+
+ updatehealth()
+ if(Victim)
+ Victim.updatehealth()
+
+ sleep(rand(15,45))
+
+ else
+ break
+
+ if(stat == 2)
+ if(!is_adult)
+ icon_state = "[colour] baby slime dead"
+
+ else
+ if(is_adult)
+ icon_state = "[colour] adult slime"
+ else
+ icon_state = "[colour] baby slime"
+
+ canmove = 1
+ anchored = 0
+
+ if(M)
+ if(M.health <= -70)
+ M.canmove = 0
+ if(!client)
+ if(Victim && !rabid && !attacked)
+ if(Victim.LAssailant && Victim.LAssailant != Victim)
+ if(prob(50))
+ if(!(Victim.LAssailant in Friends))
+ Friends[Victim.LAssailant] = 1
+ //Friends.Add(Victim.LAssailant) // no idea why i was using the |= operator
+ else
+ ++Friends[Victim.LAssailant]
+
+
+ if(M.client && istype(src, /mob/living/carbon/human))
+ if(prob(85))
+ rabid = 1 // UUUNNBGHHHH GONNA EAT JUUUUUU
+
+ if(client) src << "This subject does not have a strong enough life energy anymore..."
+ else
+ M.canmove = 1
+
+ if(client) src << "I have stopped feeding..."
+ else
+ if(client) src << "I have stopped feeding..."
+
+ Victim = null
+
+/mob/living/carbon/slime/proc/Feedstop()
+ if(Victim)
+ if(Victim.client) Victim << "[src] has let go of your head!"
+ Victim = null
+
+/mob/living/carbon/slime/proc/UpdateFeed(var/mob/M)
+ if(Victim)
+ if(Victim == M)
+ loc = M.loc // simple "attach to head" effect!
+
+
+/mob/living/carbon/slime/verb/Evolve()
+ set category = "Slime"
+ set desc = "This will let you evolve from baby to adult slime."
+
+ if(stat)
+ src << "I must be conscious to do this..."
+ return
+ if(!is_adult)
+ if(amount_grown >= 10)
+ is_adult = 1
+ maxHealth = 200
+ amount_grown = 0
+ regenerate_icons()
+ name = text("[colour] [is_adult ? "adult" : "baby"] slime ([number])")
+ else
+ src << "I am not ready to evolve yet..."
+ else
+ src << "I have already evolved..."
+
+/mob/living/carbon/slime/verb/Reproduce()
+ set category = "Slime"
+ set desc = "This will make you split into four Slimes."
+
+ if(stat)
+ src << "I must be conscious to do this..."
+ return
+
+ if(is_adult)
+ if(amount_grown >= 10)
+ if(stat)
+ src << "I must be conscious to do this..."
+ return
+
+ var/list/babies = list()
+ var/new_nutrition = round(nutrition * 0.9)
+ var/new_powerlevel = round(powerlevel / 4)
+ for(var/i=1,i<=4,i++)
+ var/mob/living/carbon/slime/M = new /mob/living/carbon/slime/(loc)
+ if(prob(mutation_chance))
+ M.colour = slime_mutation[rand(1,4)]
+ else
+ M.colour = colour
+ if(ckey) M.nutrition = new_nutrition //Player slimes are more robust at spliting. Once an oversight of poor copypasta, now a feature!
+ M.powerlevel = new_powerlevel
+ if(i != 1) step_away(M,src)
+ M.Friends = Friends.Copy()
+ babies += M
+ feedback_add_details("slime_babies_born","slimebirth_[replacetext(M.colour," ","_")]")
+
+ var/mob/living/carbon/slime/new_slime = pick(babies)
+ new_slime.universal_speak = universal_speak
+ if(src.mind)
+ src.mind.transfer_to(new_slime)
+ else
+ new_slime.key = src.key
+ qdel(src)
+ else
+ src << "I am not ready to reproduce yet..."
+ else
src << "I am not old enough to reproduce yet..."
\ No newline at end of file
diff --git a/code/modules/mob/living/carbon/metroid/say.dm b/code/modules/mob/living/carbon/slime/say.dm
similarity index 100%
rename from code/modules/mob/living/carbon/metroid/say.dm
rename to code/modules/mob/living/carbon/slime/say.dm
diff --git a/code/modules/mob/living/carbon/slime/slime.dm b/code/modules/mob/living/carbon/slime/slime.dm
new file mode 100644
index 00000000000..1e229b853a3
--- /dev/null
+++ b/code/modules/mob/living/carbon/slime/slime.dm
@@ -0,0 +1,576 @@
+/mob/living/carbon/slime
+ name = "baby slime"
+ icon = 'icons/mob/slimes.dmi'
+ icon_state = "grey baby slime"
+ pass_flags = PASSTABLE
+ ventcrawler = 2
+ speak_emote = list("telepathically chirps")
+
+ layer = 5
+
+ maxHealth = 150
+ health = 150
+ gender = NEUTER
+
+ update_icon = 0
+ nutrition = 700
+
+ see_in_dark = 8
+ update_slimes = 0
+
+ // canstun and canweaken don't affect slimes because they ignore stun and weakened variables
+ // for the sake of cleanliness, though, here they are.
+ status_flags = CANPARALYSE|CANPUSH
+
+ var/cores = 1 // the number of /obj/item/slime_extract's the slime has left inside
+ var/mutation_chance = 30 // Chance of mutating, should be between 25 and 35
+
+ var/powerlevel = 0 // 1-10 controls how much electricity they are generating
+ var/amount_grown = 0 // controls how long the slime has been overfed, if 10, grows or reproduces
+
+ var/number = 0 // Used to understand when someone is talking to it
+
+ var/mob/living/Victim = null // the person the slime is currently feeding on
+ var/mob/living/Target = null // AI variable - tells the slime to hunt this down
+ var/mob/living/Leader = null // AI variable - tells the slime to follow this person
+
+ var/attacked = 0 // Determines if it's been attacked recently. Can be any number, is a cooloff-ish variable
+ var/rabid = 0 // If set to 1, the slime will attack and eat anything it comes in contact with
+ var/holding_still = 0 // AI variable, cooloff-ish for how long it's going to stay in one place
+ var/target_patience = 0 // AI variable, cooloff-ish for how long it's going to follow its target
+
+ var/list/Friends = list() // A list of friends; they are not considered targets for feeding; passed down after splitting
+
+ var/list/speech_buffer = list() // Last phrase said near it and person who said it
+
+ var/mood = "" // To show its face
+ var/is_adult = 0
+
+ var/core_removal_stage = 0 //For removing cores.
+
+ ///////////TIME FOR SUBSPECIES
+
+ var/colour = "grey"
+ var/coretype = /obj/item/slime_extract/grey
+ var/list/slime_mutation[4]
+
+/mob/living/carbon/slime/New()
+ create_reagents(100)
+ spawn (0)
+ number = rand(1, 1000)
+ name = "[colour] [is_adult ? "adult" : "baby"] slime ([number])"
+ icon_state = "[colour] [is_adult ? "adult" : "baby"] slime"
+ real_name = name
+ slime_mutation = mutation_table(colour)
+ mutation_chance = rand(25, 35)
+ var/sanitizedcolour = replacetext(colour, " ", "")
+ coretype = text2path("/obj/item/slime_extract/[sanitizedcolour]")
+ ..()
+
+/mob/living/carbon/slime/regenerate_icons()
+ icon_state = "[colour] [is_adult ? "adult" : "baby"] slime"
+ overlays.len = 0
+ if (mood)
+ overlays += image('icons/mob/slimes.dmi', icon_state = "aslime-[mood]")
+ ..()
+
+/mob/living/carbon/slime/movement_delay()
+ if (bodytemperature >= 330.23) // 135 F
+ return -1 // slimes become supercharged at high temperatures
+
+ var/tally = 0
+
+ var/health_deficiency = (100 - health)
+ if(health_deficiency >= 45) tally += (health_deficiency / 25)
+
+ if (bodytemperature < 183.222)
+ tally += (283.222 - bodytemperature) / 10 * 1.75
+
+ if(reagents)
+ if(reagents.has_reagent("methamphetamine")) // Meth slows slimes down
+ tally *= 2
+
+ if(reagents.has_reagent("frostoil")) // Frostoil also makes them move VEEERRYYYYY slow
+ tally *= 5
+
+ if(health <= 0) // if damaged, the slime moves twice as slow
+ tally *= 2
+
+ return tally + config.slime_delay
+
+/mob/living/carbon/slime/Bump(atom/movable/AM as mob|obj, yes)
+ if ((!(yes) || now_pushing))
+ return
+ now_pushing = 1
+
+ if(isobj(AM))
+ if(!client && powerlevel > 0)
+ var/probab = 10
+ switch(powerlevel)
+ if(1 to 2) probab = 20
+ if(3 to 4) probab = 30
+ if(5 to 6) probab = 40
+ if(7 to 8) probab = 60
+ if(9) probab = 70
+ if(10) probab = 95
+ if(prob(probab))
+ if(istype(AM, /obj/structure/window) || istype(AM, /obj/structure/grille))
+ if(nutrition <= get_hunger_nutrition() && !Atkcool)
+ if (is_adult || prob(5))
+ AM.attack_slime(src)
+ spawn()
+ Atkcool = 1
+ sleep(45)
+ Atkcool = 0
+
+ if(ismob(AM))
+ var/mob/tmob = AM
+
+ if(is_adult)
+ if(istype(tmob, /mob/living/carbon/human))
+ if(prob(90))
+ now_pushing = 0
+ return
+ else
+ if(istype(tmob, /mob/living/carbon/human))
+ now_pushing = 0
+ return
+
+ now_pushing = 0
+ ..()
+ if (!istype(AM, /atom/movable))
+ return
+ if (!( now_pushing ))
+ now_pushing = 1
+ if (!( AM.anchored ))
+ var/t = get_dir(src, AM)
+ if (istype(AM, /obj/structure/window))
+ if(AM:ini_dir == NORTHWEST || AM:ini_dir == NORTHEAST || AM:ini_dir == SOUTHWEST || AM:ini_dir == SOUTHEAST)
+ for(var/obj/structure/window/win in get_step(AM,t))
+ now_pushing = 0
+ return
+ step(AM, t)
+ now_pushing = null
+
+/mob/living/carbon/slime/Process_Spacemove(var/movement_dir = 0)
+ return 2
+
+/mob/living/carbon/slime/Stat()
+ ..()
+
+ statpanel("Status")
+ if(is_adult)
+ stat(null, "Health: [round((health / 200) * 100)]%")
+ else
+ stat(null, "Health: [round((health / 150) * 100)]%")
+
+ if (client.statpanel == "Status")
+ stat(null, "Nutrition: [nutrition]/[get_max_nutrition()]")
+ if(amount_grown >= 10)
+ if(is_adult)
+ stat(null, "You can reproduce!")
+ else
+ stat(null, "You can evolve!")
+
+ stat(null,"Power Level: [powerlevel]")
+
+/mob/living/carbon/slime/adjustFireLoss(amount)
+ ..(-abs(amount)) // Heals them
+ return
+
+/mob/living/carbon/slime/bullet_act(var/obj/item/projectile/Proj)
+ attacked += 10
+ ..(Proj)
+ return 0
+
+/mob/living/carbon/slime/emp_act(severity)
+ powerlevel = 0 // oh no, the power!
+ ..()
+
+/mob/living/carbon/slime/ex_act(severity)
+ ..()
+
+ var/b_loss = null
+ var/f_loss = null
+ switch (severity)
+ if (1.0)
+ qdel(src)
+ return
+
+ if (2.0)
+
+ b_loss += 60
+ f_loss += 60
+
+
+ if(3.0)
+ b_loss += 30
+
+ adjustBruteLoss(b_loss)
+ adjustFireLoss(f_loss)
+
+ updatehealth()
+
+
+/mob/living/carbon/slime/blob_act()
+ show_message(" The blob attacks you!")
+ adjustBruteLoss(20)
+ updatehealth()
+ return
+
+
+/mob/living/carbon/slime/unEquip(obj/item/W as obj)
+ return
+
+/mob/living/carbon/slime/attack_ui(slot)
+ return
+
+/mob/living/carbon/slime/attack_slime(mob/living/carbon/slime/M as mob)
+ if (!ticker)
+ M << "You cannot attack people before the game has started."
+ return
+
+ if (Victim) return // can't attack while eating!
+
+ if (health > -100)
+
+ M.do_attack_animation(src)
+ visible_message(" The [M.name] has glomped [src]!", \
+ " The [M.name] has glomped [src]!")
+ var/damage = rand(1, 3)
+ attacked += 5
+
+ if(M.is_adult)
+ damage = rand(1, 6)
+ else
+ damage = rand(1, 3)
+
+ adjustBruteLoss(damage)
+
+ updatehealth()
+ return
+
+/mob/living/carbon/slime/attack_animal(mob/living/simple_animal/M as mob)
+ if(M.melee_damage_upper == 0)
+ M.custom_emote(1, "[M.friendly] [src]")
+ else
+ M.do_attack_animation(src)
+ if(M.attack_sound)
+ playsound(loc, M.attack_sound, 50, 1, 1)
+ visible_message("[M] [M.attacktext] [src]!", \
+ "[M] [M.attacktext] [src]!")
+ M.attack_log += text("\[[time_stamp()]\] attacked [src.name] ([src.ckey])")
+ src.attack_log += text("\[[time_stamp()]\] was attacked by [M.name] ([M.ckey])")
+ var/damage = rand(M.melee_damage_lower, M.melee_damage_upper)
+ attacked += 10
+ adjustBruteLoss(damage)
+ updatehealth()
+
+/mob/living/carbon/slime/attack_larva(mob/living/carbon/alien/larva/L as mob)
+
+ switch(L.a_intent)
+
+ if(I_HELP)
+ visible_message("[L] rubs its head against [src].")
+
+
+ else
+ L.do_attack_animation(src)
+ attacked += 10
+ visible_message("[L] bites [src]!", \
+ "[L] bites [src]!")
+ playsound(loc, 'sound/weapons/bite.ogg', 50, 1, -1)
+
+ if(stat != DEAD)
+ var/damage = rand(1, 3)
+ L.amount_grown = min(L.amount_grown + damage, L.max_grown)
+ adjustBruteLoss(damage)
+
+/mob/living/carbon/slime/attack_hand(mob/living/carbon/human/M as mob)
+ if (!ticker)
+ M << "You cannot attack people before the game has started."
+ return
+
+ if (istype(loc, /turf) && istype(loc.loc, /area/start))
+ M << "No attacking people at spawn, you jackass."
+ return
+
+ ..()
+
+ if(Victim)
+ if(Victim == M)
+ if(prob(60))
+ visible_message("[M] attempts to wrestle \the [name] off!")
+ playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
+
+ else
+ visible_message(" [M] manages to wrestle \the [name] off!")
+ playsound(loc, 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
+
+ if(prob(90) && !client)
+ Discipline++
+
+ spawn()
+ SStun = 1
+ sleep(rand(45,60))
+ if(src)
+ SStun = 0
+
+ Victim = null
+ anchored = 0
+ step_away(src,M)
+
+ return
+
+ else
+ if(prob(30))
+ visible_message("[M] attempts to wrestle \the [name] off of [Victim]!")
+ playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
+
+ else
+ visible_message(" [M] manages to wrestle \the [name] off of [Victim]!")
+ playsound(loc, 'sound/weapons/thudswoosh.ogg', 50, 1, -1)
+
+ if(prob(80) && !client)
+ Discipline++
+
+ if(!is_adult)
+ if(Discipline == 1)
+ attacked = 0
+
+ spawn()
+ SStun = 1
+ sleep(rand(55,65))
+ if(src)
+ SStun = 0
+
+ Victim = null
+ anchored = 0
+ step_away(src,M)
+
+ return
+
+/*
+ if(M.gloves && istype(M.gloves,/obj/item/clothing/gloves))
+ var/obj/item/clothing/gloves/G = M.gloves
+ if(G.cell)
+ if(M.a_intent == "hurt")//Stungloves. Any contact will stun the alien.
+ if(G.cell.charge >= 2500)
+ G.cell.use(2500)
+ visible_message("[src] has been touched with the stun gloves by [M]!")
+ return
+ else
+ M << "\red Not enough charge! "
+ return
+*/
+
+ switch(M.a_intent)
+
+ if (I_HELP)
+ help_shake_act(M)
+
+ if (I_GRAB)
+ grabbedby(M)
+
+ else
+ M.do_attack_animation(src)
+ var/damage = rand(1, 9)
+
+ attacked += 10
+ if (prob(90))
+ if (HULK in M.mutations)
+ damage += 5
+ if(Victim || Target)
+ Victim = null
+ Target = null
+ anchored = 0
+ if(prob(80) && !client)
+ Discipline++
+ spawn(0)
+
+ step_away(src,M,15)
+ sleep(3)
+ step_away(src,M,15)
+
+
+ playsound(loc, "punch", 25, 1, -1)
+ visible_message("[M] has punched [src]!", \
+ "[M] has punched [src]!")
+
+ adjustBruteLoss(damage)
+ updatehealth()
+ else
+ playsound(loc, 'sound/weapons/punchmiss.ogg', 25, 1, -1)
+ visible_message("[M] has attempted to punch [src]!")
+ return
+
+
+
+/mob/living/carbon/slime/attack_alien(mob/living/carbon/alien/humanoid/M as mob)
+ if (!ticker)
+ M << "You cannot attack people before the game has started."
+ return
+
+ if (istype(loc, /turf) && istype(loc.loc, /area/start))
+ M << "No attacking people at spawn, you jackass."
+ return
+
+ switch(M.a_intent)
+ if (I_HELP)
+ visible_message("[M] caresses [src] with its scythe like arm.")
+
+ if (I_HARM)
+ M.do_attack_animation(src)
+ if (prob(95))
+ attacked += 10
+ playsound(loc, 'sound/weapons/slice.ogg', 25, 1, -1)
+ var/damage = rand(15, 30)
+ if (damage >= 25)
+ damage = rand(20, 40)
+ visible_message("[M] has attacked [name]!", \
+ "[M] has attacked [name]!")
+ else
+ visible_message("[M] has wounded [name]!", \
+ ")[M] has wounded [name]!")
+ adjustBruteLoss(damage)
+ updatehealth()
+ else
+ playsound(loc, 'sound/weapons/slashmiss.ogg', 25, 1, -1)
+ visible_message("[M] has attempted to lunge at [name]!", \
+ "[M] has attempted to lunge at [name]!")
+
+ if (I_GRAB)
+ grabbedby(M)
+
+ if (I_DISARM)
+ M.do_attack_animation(src)
+ playsound(loc, 'sound/weapons/pierce.ogg', 25, 1, -1)
+ var/damage = 5
+ attacked += 10
+
+ if(prob(95))
+ visible_message("[M] has tackled [name]!", \
+ "[M] has tackled [name]!")
+
+ if(Victim || Target)
+ Victim = null
+ Target = null
+ anchored = 0
+ if(prob(80) && !client)
+ Discipline++
+ if(!istype(src, /mob/living/carbon/slime))
+ if(Discipline == 1)
+ attacked = 0
+
+ spawn()
+ SStun = 1
+ sleep(rand(5,20))
+ SStun = 0
+
+ spawn(0)
+
+ step_away(src,M,15)
+ sleep(3)
+ step_away(src,M,15)
+
+ else
+ drop_item()
+ visible_message("[M] has disarmed [name]!",
+ "[M] has disarmed [name]!")
+ adjustBruteLoss(damage)
+ updatehealth()
+ return
+
+/mob/living/carbon/slime/attackby(obj/item/W, mob/user, params)
+ if(istype(W,/obj/item/stack/sheet/mineral/plasma)) //Lets you feed slimes plasma.
+ if (user in Friends)
+ ++Friends[user]
+ else
+ Friends[user] = 1
+ user << "You feed the slime the plasma. It chirps happily."
+ var/obj/item/stack/sheet/mineral/plasma/S = W
+ S.use(1)
+ return
+ else if(W.force > 0)
+ attacked += 10
+ if(prob(25))
+ user << "[W] passes right through [src]!"
+ return
+ if(Discipline && prob(50)) // wow, buddy, why am I getting attacked??
+ Discipline = 0
+ else if(W.force >= 3)
+ if(is_adult)
+ if(prob(5 + round(W.force/2)))
+ if(Victim || Target)
+ if(prob(80) && !client)
+ Discipline++
+
+ Victim = null
+ Target = null
+ anchored = 0
+
+ spawn()
+ SStun = 1
+ sleep(rand(5,20))
+ SStun = 0
+
+ spawn(0)
+ if(user)
+ canmove = 0
+ step_away(src, user)
+ if(prob(25 + W.force))
+ sleep(2)
+ if(user)
+ step_away(src, user)
+ canmove = 1
+
+ else
+ if(prob(10 + W.force*2))
+ if(Victim || Target)
+ if(prob(80) && !client)
+ Discipline++
+ if(Discipline == 1)
+ attacked = 0
+ spawn()
+ SStun = 1
+ sleep(rand(5,20))
+ SStun = 0
+
+ Victim = null
+ Target = null
+ anchored = 0
+
+ spawn(0)
+ if(user)
+ canmove = 0
+ step_away(src, user)
+ if(prob(25 + W.force*4))
+ sleep(2)
+ if(user)
+ step_away(src, user)
+ canmove = 1
+ ..()
+
+/mob/living/carbon/slime/restrained()
+ return 0
+
+mob/living/carbon/slime/var/temperature_resistance = T0C+75
+
+/mob/living/carbon/slime/show_inv(mob/user)
+ return
+
+/mob/living/carbon/slime/toggle_throw_mode()
+ return
+
+/mob/living/carbon/slime/proc/apply_water()
+ adjustToxLoss(rand(15,20))
+ if (!client)
+ if (Target) // Like cats
+ Target = null
+ ++Discipline
+ return
+
+/mob/living/carbon/slime/can_use_vents()
+ if(Victim)
+ return "You cannot ventcrawl while feeding."
+ ..()
\ No newline at end of file
diff --git a/code/modules/mob/living/carbon/metroid/subtypes.dm b/code/modules/mob/living/carbon/slime/subtypes.dm
similarity index 95%
rename from code/modules/mob/living/carbon/metroid/subtypes.dm
rename to code/modules/mob/living/carbon/slime/subtypes.dm
index 3b7e0107abb..35d38e31a48 100644
--- a/code/modules/mob/living/carbon/metroid/subtypes.dm
+++ b/code/modules/mob/living/carbon/slime/subtypes.dm
@@ -1,79 +1,79 @@
-proc/mutation_table(var/colour)
- var/list/slime_mutation[4]
- switch(colour)
- //Tier 1
- if("grey")
- slime_mutation[1] = "orange"
- slime_mutation[2] = "metal"
- slime_mutation[3] = "blue"
- slime_mutation[4] = "purple"
- //Tier 2
- if("purple")
- slime_mutation[1] = "dark purple"
- slime_mutation[2] = "dark blue"
- slime_mutation[3] = "green"
- slime_mutation[4] = "green"
- if("metal")
- slime_mutation[1] = "silver"
- slime_mutation[2] = "yellow"
- slime_mutation[3] = "gold"
- slime_mutation[4] = "gold"
- if("orange")
- slime_mutation[1] = "dark purple"
- slime_mutation[2] = "yellow"
- slime_mutation[3] = "red"
- slime_mutation[4] = "red"
- if("blue")
- slime_mutation[1] = "dark blue"
- slime_mutation[2] = "silver"
- slime_mutation[3] = "pink"
- slime_mutation[4] = "pink"
- //Tier 3
- if("dark blue")
- slime_mutation[1] = "purple"
- slime_mutation[2] = "blue"
- slime_mutation[3] = "cerulean"
- slime_mutation[4] = "cerulean"
- if("dark purple")
- slime_mutation[1] = "purple"
- slime_mutation[2] = "orange"
- slime_mutation[3] = "sepia"
- slime_mutation[4] = "sepia"
- if("yellow")
- slime_mutation[1] = "metal"
- slime_mutation[2] = "orange"
- slime_mutation[3] = "bluespace"
- slime_mutation[4] = "bluespace"
- if("silver")
- slime_mutation[1] = "metal"
- slime_mutation[2] = "blue"
- slime_mutation[3] = "pyrite"
- slime_mutation[4] = "pyrite"
- //Tier 4
- if("pink")
- slime_mutation[1] = "pink"
- slime_mutation[2] = "pink"
- slime_mutation[3] = "light pink"
- slime_mutation[4] = "light pink"
- if("red")
- slime_mutation[1] = "red"
- slime_mutation[2] = "red"
- slime_mutation[3] = "oil"
- slime_mutation[4] = "oil"
- if("gold")
- slime_mutation[1] = "gold"
- slime_mutation[2] = "gold"
- slime_mutation[3] = "adamantine"
- slime_mutation[4] = "adamantine"
- if("green")
- slime_mutation[1] = "green"
- slime_mutation[2] = "green"
- slime_mutation[3] = "black"
- slime_mutation[4] = "black"
- // Tier 5
- else
- slime_mutation[1] = colour
- slime_mutation[2] = colour
- slime_mutation[3] = colour
- slime_mutation[4] = colour
+proc/mutation_table(var/colour)
+ var/list/slime_mutation[4]
+ switch(colour)
+ //Tier 1
+ if("grey")
+ slime_mutation[1] = "orange"
+ slime_mutation[2] = "metal"
+ slime_mutation[3] = "blue"
+ slime_mutation[4] = "purple"
+ //Tier 2
+ if("purple")
+ slime_mutation[1] = "dark purple"
+ slime_mutation[2] = "dark blue"
+ slime_mutation[3] = "green"
+ slime_mutation[4] = "green"
+ if("metal")
+ slime_mutation[1] = "silver"
+ slime_mutation[2] = "yellow"
+ slime_mutation[3] = "gold"
+ slime_mutation[4] = "gold"
+ if("orange")
+ slime_mutation[1] = "dark purple"
+ slime_mutation[2] = "yellow"
+ slime_mutation[3] = "red"
+ slime_mutation[4] = "red"
+ if("blue")
+ slime_mutation[1] = "dark blue"
+ slime_mutation[2] = "silver"
+ slime_mutation[3] = "pink"
+ slime_mutation[4] = "pink"
+ //Tier 3
+ if("dark blue")
+ slime_mutation[1] = "purple"
+ slime_mutation[2] = "blue"
+ slime_mutation[3] = "cerulean"
+ slime_mutation[4] = "cerulean"
+ if("dark purple")
+ slime_mutation[1] = "purple"
+ slime_mutation[2] = "orange"
+ slime_mutation[3] = "sepia"
+ slime_mutation[4] = "sepia"
+ if("yellow")
+ slime_mutation[1] = "metal"
+ slime_mutation[2] = "orange"
+ slime_mutation[3] = "bluespace"
+ slime_mutation[4] = "bluespace"
+ if("silver")
+ slime_mutation[1] = "metal"
+ slime_mutation[2] = "blue"
+ slime_mutation[3] = "pyrite"
+ slime_mutation[4] = "pyrite"
+ //Tier 4
+ if("pink")
+ slime_mutation[1] = "pink"
+ slime_mutation[2] = "pink"
+ slime_mutation[3] = "light pink"
+ slime_mutation[4] = "light pink"
+ if("red")
+ slime_mutation[1] = "red"
+ slime_mutation[2] = "red"
+ slime_mutation[3] = "oil"
+ slime_mutation[4] = "oil"
+ if("gold")
+ slime_mutation[1] = "gold"
+ slime_mutation[2] = "gold"
+ slime_mutation[3] = "adamantine"
+ slime_mutation[4] = "adamantine"
+ if("green")
+ slime_mutation[1] = "green"
+ slime_mutation[2] = "green"
+ slime_mutation[3] = "black"
+ slime_mutation[4] = "black"
+ // Tier 5
+ else
+ slime_mutation[1] = colour
+ slime_mutation[2] = colour
+ slime_mutation[3] = colour
+ slime_mutation[4] = colour
return(slime_mutation)
\ No newline at end of file
diff --git a/code/modules/mob/living/carbon/metroid/update_icons.dm b/code/modules/mob/living/carbon/slime/update_icons.dm
similarity index 96%
rename from code/modules/mob/living/carbon/metroid/update_icons.dm
rename to code/modules/mob/living/carbon/slime/update_icons.dm
index 8902770055d..2310f32a76e 100644
--- a/code/modules/mob/living/carbon/metroid/update_icons.dm
+++ b/code/modules/mob/living/carbon/slime/update_icons.dm
@@ -1 +1 @@
-//no special icon processing
+//no special icon processing
diff --git a/code/modules/research/xenobiology/xenobiology.dm b/code/modules/research/xenobiology/xenobiology.dm
new file mode 100644
index 00000000000..a0df8e2740a
--- /dev/null
+++ b/code/modules/research/xenobiology/xenobiology.dm
@@ -0,0 +1,474 @@
+
+/// Slime Extracts ///
+
+/obj/item/slime_extract
+ name = "slime extract"
+ desc = "Goo extracted from a slime. Legends claim these to have \"magical powers\"."
+ icon = 'icons/mob/slimes.dmi'
+ icon_state = "grey slime extract"
+ force = 1.0
+ w_class = 1.0
+ throwforce = 0
+ throw_speed = 3
+ throw_range = 6
+ origin_tech = "biotech=4"
+ item_color = "grey"
+ var/Uses = 1 // uses before it goes inert
+ var/enhanced = 0 //has it been enhanced before?
+
+ attackby(obj/item/O as obj, mob/user as mob, params)
+ if(istype(O, /obj/item/weapon/slimesteroid2))
+ if(enhanced == 1)
+ user << " This extract has already been enhanced!"
+ return ..()
+ if(Uses == 0)
+ user << " You can't enhance a used extract!"
+ return ..()
+ user <<"You apply the enhancer. It now has triple the amount of uses."
+ Uses = 3
+ enhanced = 1
+ qdel(O)
+ if(istype(O,/obj/item/weapon/storage/bag))
+ ..()
+
+/obj/item/slime_extract/New()
+ ..()
+ create_reagents(100)
+
+
+/obj/item/slime_extract/grey
+ name = "grey slime extract"
+ icon_state = "grey slime extract"
+ item_color = "grey"
+
+/obj/item/slime_extract/gold
+ name = "gold slime extract"
+ icon_state = "gold slime extract"
+ item_color = "gold"
+
+/obj/item/slime_extract/silver
+ name = "silver slime extract"
+ icon_state = "silver slime extract"
+ item_color = "silver"
+
+/obj/item/slime_extract/metal
+ name = "metal slime extract"
+ icon_state = "metal slime extract"
+ item_color = "metal"
+
+/obj/item/slime_extract/purple
+ name = "purple slime extract"
+ icon_state = "purple slime extract"
+ item_color = "purple"
+
+/obj/item/slime_extract/darkpurple
+ name = "dark purple slime extract"
+ icon_state = "dark purple slime extract"
+ item_color = "darkpurple"
+
+/obj/item/slime_extract/orange
+ name = "orange slime extract"
+ icon_state = "orange slime extract"
+ item_color = "orange"
+
+/obj/item/slime_extract/yellow
+ name = "yellow slime extract"
+ icon_state = "yellow slime extract"
+ item_color = "yellow"
+
+/obj/item/slime_extract/red
+ name = "red slime extract"
+ icon_state = "red slime extract"
+ item_color = "red"
+
+/obj/item/slime_extract/blue
+ name = "blue slime extract"
+ icon_state = "blue slime extract"
+ item_color = "blue"
+
+/obj/item/slime_extract/darkblue
+ name = "dark blue slime extract"
+ icon_state = "dark blue slime extract"
+ item_color = "darkblue"
+
+/obj/item/slime_extract/pink
+ name = "pink slime extract"
+ icon_state = "pink slime extract"
+ item_color = "pink"
+
+/obj/item/slime_extract/green
+ name = "green slime extract"
+ icon_state = "green slime extract"
+ item_color = "green"
+
+/obj/item/slime_extract/lightpink
+ name = "light pink slime extract"
+ icon_state = "light pink slime extract"
+ item_color = "lightpink"
+
+/obj/item/slime_extract/black
+ name = "black slime extract"
+ icon_state = "black slime extract"
+ item_color = "black"
+
+/obj/item/slime_extract/oil
+ name = "oil slime extract"
+ icon_state = "oil slime extract"
+ item_color = "oil"
+
+/obj/item/slime_extract/adamantine
+ name = "adamantine slime extract"
+ icon_state = "adamantine slime extract"
+ item_color = "adamantine"
+
+/obj/item/slime_extract/bluespace
+ name = "bluespace slime extract"
+ icon_state = "bluespace slime extract"
+
+/obj/item/slime_extract/pyrite
+ name = "pyrite slime extract"
+ icon_state = "pyrite slime extract"
+
+/obj/item/slime_extract/cerulean
+ name = "cerulean slime extract"
+ icon_state = "cerulean slime extract"
+
+/obj/item/slime_extract/sepia
+ name = "sepia slime extract"
+ icon_state = "sepia slime extract"
+
+/obj/item/slime_extract/rainbow
+ name = "rainbow slime extract"
+ icon_state = "rainbow slime extract"
+
+////Pet Slime Creation///
+
+/obj/item/weapon/slimepotion
+ name = "docility potion"
+ desc = "A potent chemical mix that will nullify a slime's powers, causing it to become docile and tame."
+ icon = 'icons/obj/chemical.dmi'
+ icon_state = "bottle19"
+ w_class = 1
+ origin_tech = "biotech=4"
+
+ attack(mob/living/carbon/slime/M as mob, mob/user as mob)
+ if(!istype(M, /mob/living/carbon/slime))//If target is not a slime.
+ user << " The potion only works on slimes!"
+ return ..()
+ if(M.stat)
+ user << " The slime is dead!"
+ return..()
+ if(M.mind)
+ user << " The slime resists!"
+ return ..()
+ if(M.is_adult)
+ var/mob/living/simple_animal/adultslime/pet = new /mob/living/simple_animal/adultslime(M.loc)
+ pet.icon_state = "[M.colour] adult slime"
+ pet.icon_living = "[M.colour] adult slime"
+ pet.icon_dead = "[M.colour] baby slime dead"
+ pet.colour = "[M.colour]"
+ qdel(M)
+ var/newname = sanitize(copytext(input(user, "Would you like to give the slime a name?", "Name your new pet", "pet slime") as null|text,1,MAX_NAME_LEN))
+
+ if (!newname)
+ newname = "pet slime"
+ pet.name = newname
+ pet.real_name = newname
+ qdel(src)
+ else
+ var/mob/living/simple_animal/slime/pet = new /mob/living/simple_animal/slime(M.loc)
+ pet.icon_state = "[M.colour] baby slime"
+ pet.icon_living = "[M.colour] baby slime"
+ pet.icon_dead = "[M.colour] baby slime dead"
+ pet.colour = "[M.colour]"
+ qdel(M)
+ var/newname = sanitize(copytext(input(user, "Would you like to give the slime a name?", "Name your new pet", "pet slime") as null|text,1,MAX_NAME_LEN))
+
+ if (!newname)
+ newname = "pet slime"
+ pet.name = newname
+ pet.real_name = newname
+ qdel(src)
+ user <<"You feed the slime the potion, removing it's powers and calming it."
+
+/obj/item/weapon/sentience_potion
+ name = "sentience potion"
+ desc = "A miraculous chemical mix that can raise the intelligence of creatures to human levels. Unlike normal slime potions, it can be absorbed by any nonsentient being."
+ icon = 'icons/obj/chemical.dmi'
+ icon_state = "bottle19"
+ origin_tech = "biotech=5"
+ var/list/not_interested = list()
+ var/being_used = 0
+ w_class = 1
+
+
+/obj/item/weapon/sentience_potion/afterattack(mob/living/M, mob/user)
+ if(being_used || !ismob(M))
+ return
+ if(!isslime(M) && !isanimal(M) || M.ckey) //only works on animals that aren't player controlled
+ user << "[M] is already too intelligent for this to work!"
+ return ..()
+ if(M.stat)
+ user << "[M] is dead!"
+ return..()
+
+ user << "You offer the sentience potion to [M]..."
+ being_used = 1
+
+ var/list/candidates = get_candidates(ROLE_SENTIENT, ALIEN_AFK_BRACKET)
+
+ shuffle(candidates)
+
+ var/time_passed = world.time
+ var/list/consenting_candidates = list()
+
+ for(var/candidate in candidates)
+
+ if(candidate in not_interested)
+ continue
+
+ spawn(0)
+ switch(alert(candidate, "Would you like to play as [M.name]? Please choose quickly!","Confirmation","Yes","No"))
+ if("Yes")
+ if((world.time-time_passed)>=50 || !src)
+ return
+ consenting_candidates += candidate
+ if("No")
+ if(!src)
+ return
+ not_interested += candidate
+
+ sleep(50)
+
+ if(!src)
+ return
+
+ listclearnulls(consenting_candidates) //some candidates might have left during sleep(50)
+
+ if(consenting_candidates.len)
+ var/client/C = null
+ C = pick(consenting_candidates)
+ M.key = C.key
+ M.universal_speak = 1
+ M.faction |= "sentient"
+ M << "All at once it makes sense: you know what you are and who you are! Self awareness is yours!"
+ M << "You are grateful to be self aware and owe [user] a great debt. Serve [user], and assist them in completing their goals at any cost."
+ user << "[M] accepts the potion and suddenly becomes attentive and aware. It worked!"
+ if(isanimal(M))
+ var/mob/living/simple_animal/S = M
+ S.master_commander = user
+ qdel(src)
+ else
+ user << "[M] looks interested for a moment, but then looks back down. Maybe you should try again later."
+ being_used = 0
+ ..()
+
+
+/obj/item/weapon/slimesteroid
+ name = "slime steroid"
+ desc = "A potent chemical mix that will cause a slime to generate more extract."
+ icon = 'icons/obj/chemical.dmi'
+ icon_state = "bottle16"
+ w_class = 1
+ origin_tech = "biotech=4"
+
+
+ attack(mob/living/carbon/slime/M as mob, mob/user as mob)
+ if(!istype(M, /mob/living/carbon/slime))//If target is not a slime.
+ user << " The steroid only works on baby slimes!"
+ return ..()
+ if(M.is_adult) //Can't tame adults
+ user << " Only baby slimes can use the steroid!"
+ return..()
+ if(M.stat)
+ user << " The slime is dead!"
+ return..()
+ if(M.cores == 3)
+ user <<" The slime already has the maximum amount of extract!"
+ return..()
+
+ user <<"You feed the slime the steroid. It now has triple the amount of extract."
+ M.cores = 3
+ qdel(src)
+
+/obj/item/weapon/slimesteroid2
+ name = "extract enhancer"
+ desc = "A potent chemical mix that will give a slime extract three uses."
+ icon = 'icons/obj/chemical.dmi'
+ icon_state = "bottle17"
+ w_class = 1
+ origin_tech = "biotech=4"
+
+
+/obj/item/weapon/slimespeed
+ name = "slime speed potion"
+ desc = "A potent chemical mix that will remove the slowdown from any item."
+ icon = 'icons/obj/chemical.dmi'
+ icon_state = "bottle3"
+ w_class = 1
+ origin_tech = "biotech=4"
+
+/obj/item/weapon/slimespeed/afterattack(obj/item/C, mob/user)
+ ..()
+ if(!istype(C))
+ user << "The potion can only be used on items!"
+ return
+ if(C.slowdown <= 0)
+ user << "The [C] can't be made any faster!"
+ return..()
+ user <<"You slather the red gunk over the [C], making it faster."
+ C.color = "#FF0000"
+ C.slowdown = 0
+ qdel(src)
+
+/obj/item/weapon/slimefireproof
+ name = "slime chill potion"
+ desc = "A potent chemical mix that will fireproof any article of clothing. Has three uses."
+ icon = 'icons/obj/chemical.dmi'
+ icon_state = "bottle17"
+ var/uses = 3
+ w_class = 1
+ origin_tech = "biotech=4"
+
+
+/obj/item/weapon/slimefireproof/afterattack(obj/item/clothing/C, mob/user)
+ ..()
+ if(!uses)
+ qdel(src)
+ return
+ if(!istype(C))
+ user << "The potion can only be used on clothing!"
+ return
+ if(C.max_heat_protection_temperature == FIRE_IMMUNITY_SUIT_MAX_TEMP_PROTECT)
+ user << "The [C] is already fireproof!"
+ return..()
+ user <<"You slather the blue gunk over the [C], fireproofing it."
+ C.name = "fireproofed [C.name]"
+ C.color = "#000080"
+ C.max_heat_protection_temperature = FIRE_IMMUNITY_SUIT_MAX_TEMP_PROTECT
+ C.heat_protection = C.body_parts_covered
+ uses --
+ if(!uses)
+ qdel(src)
+
+/obj/item/stack/tile/bluespace
+ name = "bluespace floor tile"
+ singular_name = "floor tile"
+ desc = "Through a series of micro-teleports, these tiles let people move at incredible speeds."
+ icon_state = "tile-bluespace"
+ w_class = 3
+ force = 6
+ materials = list(MAT_METAL=500)
+ throwforce = 10
+ throw_speed = 3
+ throw_range = 7
+ flags = CONDUCT
+ max_amount = 60
+ turf_type = /turf/simulated/floor/bluespace
+
+
+/turf/simulated/floor/bluespace
+ slowdown = -1
+ icon_state = "bluespace"
+ desc = "Through a series of micro-teleports, these tiles let people move at incredible speeds."
+ floor_tile = /obj/item/stack/tile/bluespace
+
+
+/obj/item/stack/tile/sepia
+ name = "sepia floor tile"
+ singular_name = "floor tile"
+ desc = "Time seems to flow very slowly around these tiles."
+ icon_state = "tile-sepia"
+ w_class = 3
+ force = 6
+ materials = list(MAT_METAL=500)
+ throwforce = 10
+ throw_speed = 3
+ throw_range = 7
+ flags = CONDUCT
+ max_amount = 60
+ turf_type = /turf/simulated/floor/sepia
+
+
+/turf/simulated/floor/sepia
+ slowdown = 2
+ icon_state = "sepia"
+ desc = "Time seems to flow very slowly around these tiles."
+ floor_tile = /obj/item/stack/tile/sepia
+
+/obj/effect/goleRUNe
+ anchored = 1
+ desc = "a strange rune used to create golems. It glows when spirits are nearby."
+ name = "rune"
+ icon = 'icons/obj/rune.dmi'
+ icon_state = "golem"
+ unacidable = 1
+ layer = TURF_LAYER
+ var/list/mob/dead/observer/ghosts[0]
+
+ New()
+ ..()
+ processing_objects.Add(src)
+
+ process()
+ if(ghosts.len>0)
+ icon_state = "golem2"
+ else
+ icon_state = "golem"
+
+ attack_hand(mob/living/user as mob)
+ var/mob/dead/observer/ghost
+ for(var/mob/dead/observer/O in src.loc)
+ if(!check_observer(O))
+ O << "\red You are not eligible to become a golem."
+ continue
+ ghost = O
+ break
+ if(!ghost)
+ user << "The rune fizzles uselessly. There is no spirit nearby."
+ return
+ var/mob/living/carbon/human/golem/G = new /mob/living/carbon/human/golem
+ if(prob(50)) G.gender = "female"
+ G.loc = src.loc
+ G.key = ghost.key
+ G << "You are an adamantine golem. You move slowly, but are highly resistant to heat and cold as well as blunt trauma. You are unable to wear clothes, but can still use most tools. Serve [user], and assist them in completing their goals at any cost."
+ qdel(src)
+
+
+ proc/announce_to_ghosts()
+ for(var/mob/dead/observer/O in player_list)
+ if(O.client)
+ var/area/A = get_area(src)
+ if(A)
+ O << "\blue Golem rune created in [A.name]. (Teleport | Sign Up)"
+
+ Topic(href,href_list)
+ if("signup" in href_list)
+ var/mob/dead/observer/O = locate(href_list["signup"])
+ volunteer(O)
+
+ attack_ghost(var/mob/dead/observer/O)
+ if(!O) return
+ volunteer(O)
+
+ proc/check_observer(var/mob/dead/observer/O)
+ if(!O)
+ return 0
+ if(!O.client)
+ return 0
+ if(O.mind && O.mind.current && O.mind.current.stat != DEAD)
+ return 0
+ if(O.has_enabled_antagHUD == 1 && config.antag_hud_restricted)
+ return 0
+ return 1
+
+ proc/volunteer(var/mob/dead/observer/O)
+ if(O in ghosts)
+ ghosts.Remove(O)
+ O << "\red You are no longer signed up to be a golem."
+ else
+ if(!check_observer(O))
+ O << "\red You are not eligible to become a golem."
+ return
+ ghosts.Add(O)
+ O << "\blue You are signed up to be a golem."
\ No newline at end of file
diff --git a/paradise.dme b/paradise.dme
index ddc9a9720dd..a5325a0933e 100644
--- a/paradise.dme
+++ b/paradise.dme
@@ -1380,16 +1380,16 @@
#include "code\modules\mob\living\carbon\human\species\shadow.dm"
#include "code\modules\mob\living\carbon\human\species\species.dm"
#include "code\modules\mob\living\carbon\human\species\station.dm"
-#include "code\modules\mob\living\carbon\metroid\death.dm"
-#include "code\modules\mob\living\carbon\metroid\emote.dm"
-#include "code\modules\mob\living\carbon\metroid\examine.dm"
-#include "code\modules\mob\living\carbon\metroid\life.dm"
-#include "code\modules\mob\living\carbon\metroid\login.dm"
-#include "code\modules\mob\living\carbon\metroid\metroid.dm"
-#include "code\modules\mob\living\carbon\metroid\powers.dm"
-#include "code\modules\mob\living\carbon\metroid\say.dm"
-#include "code\modules\mob\living\carbon\metroid\subtypes.dm"
-#include "code\modules\mob\living\carbon\metroid\update_icons.dm"
+#include "code\modules\mob\living\carbon\slime\death.dm"
+#include "code\modules\mob\living\carbon\slime\emote.dm"
+#include "code\modules\mob\living\carbon\slime\examine.dm"
+#include "code\modules\mob\living\carbon\slime\life.dm"
+#include "code\modules\mob\living\carbon\slime\login.dm"
+#include "code\modules\mob\living\carbon\slime\powers.dm"
+#include "code\modules\mob\living\carbon\slime\say.dm"
+#include "code\modules\mob\living\carbon\slime\slime.dm"
+#include "code\modules\mob\living\carbon\slime\subtypes.dm"
+#include "code\modules\mob\living\carbon\slime\update_icons.dm"
#include "code\modules\mob\living\silicon\death.dm"
#include "code\modules\mob\living\silicon\emote.dm"
#include "code\modules\mob\living\silicon\laws.dm"
@@ -1818,6 +1818,7 @@
#include "code\modules\research\xenoarchaeology\tools\tools_depthscanner.dm"
#include "code\modules\research\xenoarchaeology\tools\tools_locater.dm"
#include "code\modules\research\xenoarchaeology\tools\tools_pickaxe.dm"
+#include "code\modules\research\xenobiology\xenobiology.dm"
#include "code\modules\scripting\Errors.dm"
#include "code\modules\scripting\Options.dm"
#include "code\modules\scripting\AST\AST Nodes.dm"