Replaces Mice w/ Rats (#6625)

This commit is contained in:
ParadoxSpace
2019-07-06 00:03:35 +02:00
committed by Werner
parent 4e88af8be2
commit 6916089d4e
72 changed files with 556 additions and 508 deletions
+13 -13
View File
@@ -448,15 +448,15 @@ This is the proc mobs get to turn into a ghost. Forked from ghostize due to comp
to_chat(src, "<span class='notice'>Heat Capacity: [round(environment.heat_capacity(),0.1)]</span>")
/mob/abstract/observer/verb/become_mouse()
set name = "Become mouse"
set name = "Become Rat"
set category = "Ghost"
if(config.disable_player_mice)
to_chat(src, "<span class='warning'>Spawning as a mouse is currently disabled.</span>")
if(config.disable_player_rats)
to_chat(src, "<span class='warning'>Spawning as a rat is currently disabled.</span>")
return
if(!ROUND_IS_STARTED)
to_chat(src, "<span class='warning'>You can not spawn as a mouse before round start!</span>")
to_chat(src, "<span class='warning'>You can not spawn as a rat before round start!</span>")
return
if(!MayRespawn(1, ANIMAL))
@@ -464,31 +464,31 @@ This is the proc mobs get to turn into a ghost. Forked from ghostize due to comp
var/turf/T = get_turf(src)
if(!T || (T.z in current_map.admin_levels))
to_chat(src, "<span class='warning'>You may not spawn as a mouse on this Z-level.</span>")
to_chat(src, "<span class='warning'>You may not spawn as a rat on this Z-level.</span>")
return
var/response = alert(src, "Are you -sure- you want to become a mouse?","Are you sure you want to squeek?","Squeek!","Nope!")
var/response = alert(src, "Are you -sure- you want to become a rat?","Are you sure you want to squeek?","Squeek!","Nope!")
if(response != "Squeek!") return //Hit the wrong key...again.
//find a viable mouse candidate
var/mob/living/simple_animal/mouse/host
var/mob/living/simple_animal/rat/host
var/obj/machinery/atmospherics/unary/vent_pump/spawnpoint = find_mouse_spawnpoint(T.z)
if (spawnpoint)
host = new /mob/living/simple_animal/mouse(spawnpoint.loc)
host = new /mob/living/simple_animal/rat(spawnpoint.loc)
else
to_chat(src, "<span class='warning'>Unable to find any safe, unwelded vents to spawn mice at. The station must be quite a mess! Trying again might work, if you think there's still a safe place. </span>")
to_chat(src, "<span class='warning'>Unable to find any safe, unwelded vents to spawn rats at. The station must be quite a mess! Trying again might work, if you think there's still a safe place. </span>")
if(host)
if(config.uneducated_mice)
if(config.uneducated_rats)
host.universal_understand = 0
announce_ghost_joinleave(src, 0, "They are now a mouse.")
announce_ghost_joinleave(src, 0, "They are now a rat.")
host.ckey = src.ckey
to_chat(host, "<span class='info'>You are now a mouse. Try to avoid interaction with players, and do not give hints away that you are more than a simple rodent.</span>")
to_chat(host, "<span class='info'>You are now a rat. Though you may interact with players, do not give any hints away that you are more than a simple rodent. Find food, avoid cats, and try to survive!</span>")
/proc/find_mouse_spawnpoint(var/ZLevel)
//This function will attempt to find a good spawnpoint for mice, and prevent them from spawning in closed vent systems with no escape
//This function will attempt to find a good spawnpoint for rats, and prevent them from spawning in closed vent systems with no escape
//It does this by bruteforce: Picks a random vent, tests if it has enough connections, if not, repeat
//Continues either until a valid one is found (in which case we return it), or until we hit a limit on attempts..
//If we hit the limit without finding a valid one, then the best one we found is selected
+29 -20
View File
@@ -63,7 +63,7 @@ var/list/holder_mob_icon_cache = list()
/obj/item/weapon/holder/drone
origin_tech = list(TECH_MAGNET = 3, TECH_ENGINEERING = 5)
/obj/item/weapon/holder/mouse
/obj/item/weapon/holder/rat
w_class = 1
/obj/item/weapon/holder/borer
@@ -468,35 +468,44 @@ var/list/holder_mob_icon_cache = list()
slot_flags = SLOT_HEAD
w_class = 3
//Holders for mice
/obj/item/weapon/holder/mouse
name = "mouse"
//Holders for rats
/obj/item/weapon/holder/rat
name = "rat"
desc = "It's a fuzzy little critter."
desc_dead = "It's filthy vermin, throw it in the trash."
icon = 'icons/mob/npc/mouse.dmi'
icon_state = "mouse_brown_sleep"
item_state = "mouse_brown"
icon_state_dead = "mouse_brown_dead"
icon = 'icons/mob/npc/rat.dmi'
icon_state = "rat_brown_sleep"
item_state = "rat_brown"
icon_state_dead = "rat_brown_dead"
slot_flags = SLOT_EARS
contained_sprite = 1
origin_tech = list(TECH_BIO = 2)
w_class = 1
/obj/item/weapon/holder/mouse/white
icon_state = "mouse_white_sleep"
item_state = "mouse_white"
icon_state_dead = "mouse_white_dead"
/obj/item/weapon/holder/rat/white
icon_state = "rat_white_sleep"
item_state = "rat_white"
icon_state_dead = "rat_white_dead"
/obj/item/weapon/holder/mouse/gray
icon_state = "mouse_gray_sleep"
item_state = "mouse_gray"
icon_state_dead = "mouse_gray_dead"
/obj/item/weapon/holder/rat/gray
icon_state = "rat_gray_sleep"
item_state = "rat_gray"
icon_state_dead = "rat_gray_dead"
/obj/item/weapon/holder/mouse/brown
icon_state = "mouse_brown_sleep"
item_state = "mouse_brown"
icon_state_dead = "mouse_brown_dead"
/obj/item/weapon/holder/rat/brown
icon_state = "rat_brown_sleep"
item_state = "rat_brown"
icon_state_dead = "rat_brown_dead"
/obj/item/weapon/holder/rat/hooded
icon_state = "rat_hooded_sleep"
item_state = "rat_hooded"
icon_state_dead = "rat_hooded_dead"
/obj/item/weapon/holder/rat/irish
icon_state = "rat_irish_sleep"
item_state = "rat_irish"
icon_state_dead = "rat_irish_dead"
//Lizards
@@ -394,7 +394,7 @@ emp_act
if(assailant)
src.attack_log += text("\[[time_stamp()]\] <font color='orange'>Has been hit with a [O], thrown by [M.name] ([assailant.ckey])</font>")
M.attack_log += text("\[[time_stamp()]\] <font color='red'>Hit [src.name] ([src.ckey]) with a thrown [O]</font>")
if(!istype(src,/mob/living/simple_animal/mouse))
if(!istype(src,/mob/living/simple_animal/rat))
msg_admin_attack("[src.name] ([src.ckey]) was hit by a [O], thrown by [M.name] ([assailant.ckey]) (<A HREF='?_src_=holder;adminplayerobservecoodjump=1;X=[src.x];Y=[src.y];Z=[src.z]'>JMP</a>)",ckey=key_name(M),ckey_target=key_name(src))
//thrown weapon embedded object code.
+1 -1
View File
@@ -40,7 +40,7 @@
/mob/living/carbon/human/say_understands(var/mob/other,var/datum/language/speaking = null)
if(has_brain_worms()) //Brain worms translate everything. Even mice and alien speak.
if(has_brain_worms()) //Brain worms translate everything. Even rat and alien speak.
return 1
if(species.can_understand(other))
+1 -1
View File
@@ -189,7 +189,7 @@
if(assailant)
src.attack_log += text("\[[time_stamp()]\] <font color='orange'>Has been hit with a [O], thrown by [M.name] ([assailant.ckey])</font>")
M.attack_log += text("\[[time_stamp()]\] <font color='red'>Hit [src.name] ([src.ckey]) with a thrown [O]</font>")
if(!istype(src,/mob/living/simple_animal/mouse))
if(!istype(src,/mob/living/simple_animal/rat))
msg_admin_attack("[src.name] ([src.ckey]) was hit by a [O], thrown by [M.name] ([assailant.ckey]) (<A HREF='?_src_=holder;adminplayerobservecoodjump=1;X=[src.x];Y=[src.y];Z=[src.z]'>JMP</a>)",ckey=key_name(M),ckey_target=key_name(src))
// Begin BS12 momentum-transfer code.
@@ -58,7 +58,7 @@
plastic.add_charge(1000)
else if(istype(M,/mob/living/simple_animal/lizard) || (istype(M,/mob/living/simple_animal/mouse) && M.mob_size <= 2))
else if(istype(M,/mob/living/simple_animal/lizard) || (istype(M,/mob/living/simple_animal/rat) && M.mob_size <= 2))
src.loc.visible_message("<span class='danger'>[src.loc] sucks [M] into its decompiler. There's a horrible crunching noise.</span>","<span class='danger'>It's a bit of a struggle, but you manage to suck [M] into your decompiler. It makes a series of visceral crunching noises.</span>")
new/obj/effect/decal/cleanable/blood/splatter(get_turf(src))
qdel(M)
@@ -181,8 +181,8 @@
butchering_products = list(/obj/item/stack/material/animalhide/cat = 2)
/mob/living/simple_animal/mouse/familiar
name = "ancient mouse"
/mob/living/simple_animal/rat/familiar
name = "ancient rat"
desc = "A small rodent. It looks very old."
body_color = "gray"
@@ -205,7 +205,7 @@
supernatural = 1
/mob/living/simple_animal/mouse/familiar/Initialize()
/mob/living/simple_animal/rat/familiar/Initialize()
. = ..()
add_spell(new /spell/targeted/heal_target, "const_spell_ready")
add_spell(new /spell/targeted/heal_target/area, "const_spell_ready")
@@ -19,7 +19,6 @@
response_help = "pets"
response_disarm = "gently pushes aside"
response_harm = "kicks"
//var/mob/living/simple_animal/mouse/movement_target
var/mob/flee_target
min_oxy = 16 //Require atleast 16kPA oxygen
minbodytemp = 223 //Below -50 Degrees Celcius
@@ -30,21 +29,20 @@
metabolic_factor = 0.75
max_nutrition = 60
density = 0
var/mob/living/simple_animal/mouse/mousetarget = null
var/mob/living/simple_animal/rat/mousetarget = null
seek_speed = 5
pass_flags = PASSTABLE
possession_candidate = 1
butchering_products = list(/obj/item/stack/material/animalhide/cat = 2)
/mob/living/simple_animal/cat/think()
//MICE!
..()
if (!stat)
for(var/mob/living/simple_animal/mouse/snack in oview(src,7))
for(var/mob/living/simple_animal/rat/snack in oview(src,7))
if(snack.stat != DEAD && prob(65))//The probability allows her to not get stuck target the first mouse, reducing exploits
mousetarget = snack
movement_target = snack
foodtarget = 0 //chasing mice takes precedence over eating food
foodtarget = 0 //chasing rats takes precedence over eating food
if(prob(15))
audible_emote(pick("hisses and spits!","mrowls fiercely!","eyes [snack] hungrily."))
@@ -94,7 +92,7 @@
/mob/living/simple_animal/cat/proc/attack_mice()
if((src.loc) && isturf(src.loc))
if(!stat && !resting && !buckled)
for(var/mob/living/simple_animal/mouse/M in oview(src,1))
for(var/mob/living/simple_animal/rat/M in oview(src,1))
if(M.stat != DEAD)
M.splat()
visible_emote(pick("bites \the [M]!","toys with \the [M].","chomps on \the [M]!"),0)
@@ -107,7 +105,7 @@
visible_emote("licks [get_pronoun(POSESSIVE_ADJECTIVE)] lips and hungrily glares at [holder]'s [thing.name]",0)
/mob/living/simple_animal/cat/Released()
//A thrown cat will immediately attack mice near where it lands
//A thrown cat will immediately attack rats near where it lands
handle_movement_target()
addtimer(CALLBACK(src, .proc/attack_mice), 3)
..()
@@ -175,7 +173,7 @@
var/current_dist = get_dist(src, friend)
if (movement_target != friend)
if (current_dist > follow_dist && !istype(movement_target, /mob/living/simple_animal/mouse) && (friend in oview(src)))
if (current_dist > follow_dist && !istype(movement_target, /mob/living/simple_animal/rat) && (friend in oview(src)))
//stop existing movement
walk_to(src,0)
turns_since_scan = 0
@@ -1,311 +1,323 @@
/mob/living/simple_animal/mouse
name = "mouse"
real_name = "mouse"
desc = "It's a small, disgusting rodent, often found being annoying, and aiding in the spread of disease."
icon = 'icons/mob/npc/mouse.dmi'
icon_state = "mouse_gray"
item_state = "mouse_gray"
icon_living = "mouse_gray"
icon_dead = "mouse_gray_dead"
icon_rest = "mouse_gray_sleep"
can_nap = 1
speak = list("Squeek!","SQUEEK!","Squeek?")
speak_emote = list("squeeks","squeeks","squiks")
emote_hear = list("squeeks","squeaks","squiks")
emote_see = list("runs in a circle", "shakes", "scritches at something")
var/soft_squeaks = list('sound/effects/creatures/mouse_squeaks_1.ogg',
'sound/effects/creatures/mouse_squeaks_2.ogg',
'sound/effects/creatures/mouse_squeaks_3.ogg',
'sound/effects/creatures/mouse_squeaks_4.ogg')
var/last_softsqueak = null//Used to prevent the same soft squeak twice in a row
var/squeals = 5//Spam control.
var/maxSqueals = 2//SPAM PROTECTION
var/last_squealgain = 0// #TODO-FUTURE: Remove from life() once something else is created
var/squeakcooldown = 0
pass_flags = PASSTABLE
speak_chance = 5
turns_per_move = 5
see_in_dark = 6
maxHealth = 5
health = 5
meat_type = /obj/item/weapon/reagent_containers/food/snacks/meat/mice
response_help = "pets"
response_disarm = "gently pushes aside"
response_harm = "stomps on"
density = 0
meat_amount = 1 // Mice are small so you will get less meat
var/body_color //brown, gray and white, leave blank for random
layer = MOB_LAYER
mob_size = MOB_MINISCULE
min_oxy = 16 //Require atleast 16kPA oxygen
minbodytemp = 223 //Below -50 Degrees Celcius
maxbodytemp = 323 //Above 50 Degrees Celcius
universal_speak = 0
universal_understand = 1
holder_type = /obj/item/weapon/holder/mouse
digest_factor = 0.05
min_scan_interval = 2
max_scan_interval = 20
seek_speed = 1
max_nutrition = 17
can_pull_size = 1
can_pull_mobs = MOB_PULL_NONE
var/decompose_time = 18000
kitchen_tag = "rodent"
/mob/living/simple_animal/mouse/Life()
if(..())
if(client)
walk_to(src,0)
//Player-animals don't do random speech normally, so this is here
//Player-controlled mice will still squeak, but less often than NPC mice
if (stat == CONSCIOUS && prob(speak_chance*0.05))
squeak_soft(0)
if(is_ventcrawling == 0)
sight = initial(sight) // Returns mouse sight to normal when they leave a vent
if (squeals < maxSqueals)
var/diff = world.time - last_squealgain
if (diff > 600)
squeals++
last_squealgain = world.time
else
if ((world.time - timeofdeath) > decompose_time)
dust()
/mob/living/simple_animal/mouse/Destroy()
SSmob.all_mice -= src
return ..()
//Pixel offsetting as they scamper around
/mob/living/simple_animal/mouse/Move()
if(..())
if (prob(50))
var/new_pixelx = pixel_x
new_pixelx += rand(-2,2)
new_pixelx = Clamp(new_pixelx, -10, 10)
animate(src, pixel_x = new_pixelx, time = 0.5)
else
var/new_pixely = pixel_y
new_pixely += rand(-2,2)
new_pixely = Clamp(new_pixely, -4, 14)
animate(src, pixel_y = new_pixely, time = 0.5)
/mob/living/simple_animal/mouse/Initialize()
. = ..()
nutrition = rand(max_nutrition*0.25, max_nutrition*0.75)
verbs += /mob/living/proc/ventcrawl
verbs += /mob/living/proc/hide
if(name == initial(name))
name = "[name] ([rand(1, 1000)])"
real_name = name
if(!body_color)
body_color = pick( list("brown","gray","white") )
icon_state = "mouse_[body_color]"
item_state = "mouse_[body_color]"
icon_living = "mouse_[body_color]"
icon_rest = "mouse_[body_color]_sleep"
icon_dead = "mouse_[body_color]_dead"
if (body_color == "brown")
holder_type = /obj/item/weapon/holder/mouse/brown
if (body_color == "gray")
holder_type = /obj/item/weapon/holder/mouse/gray
if (body_color == "white")
holder_type = /obj/item/weapon/holder/mouse/white
//verbs += /mob/living/simple_animal/mouse/proc/squeak
//verbs += /mob/living/simple_animal/mouse/proc/squeak_soft
//verbs += /mob/living/simple_animal/mouse/proc/squeak_loud(1)
SSmob.all_mice += src
/mob/living/simple_animal/mouse/speak_audio()
squeak_soft(0)
/mob/living/simple_animal/mouse/beg(var/atom/thing, var/atom/holder)
squeak_soft(0)
visible_emote("squeaks timidly, sniffs the air and gazes longingly up at \the [thing.name].",0)
/mob/living/simple_animal/mouse/attack_hand(mob/living/carbon/human/M as mob)
if (src.stat == DEAD)//If the mouse is dead, we don't pet it, we just pickup the corpse on click
get_scooped(M, usr)
return
else
..()
/mob/living/simple_animal/mouse/proc/splat()
src.health = 0
src.death()
src.icon_dead = "mouse_[body_color]_splat"
src.icon_state = "mouse_[body_color]_splat"
if(client)
client.time_died_as_mouse = world.time
//Plays a sound.
//This is triggered when a mob steps on an NPC mouse, or manually by a playermouse
/mob/living/simple_animal/mouse/proc/squeak(var/manual = 1)
if (stat == CONSCIOUS)
if (squeakcooldown > world.time)
return
squeakcooldown = world.time + 2 SECONDS
playsound(src, 'sound/effects/mousesqueek.ogg', 70, 1)
if (manual)
log_say("[key_name(src)] squeaks! ",ckey=key_name(src))
//Plays a random selection of four sounds, at a low volume
//This is triggered randomly periodically by any mouse, or manually
/mob/living/simple_animal/mouse/proc/squeak_soft(var/manual = 1)
if (stat != DEAD) //Soft squeaks are allowed while sleeping
var/list/new_squeaks = last_softsqueak ? soft_squeaks - last_softsqueak : soft_squeaks
var/sound = pick(new_squeaks)
last_softsqueak = sound
if (squeakcooldown > world.time)
return
squeakcooldown = world.time + 2 SECONDS
playsound(src, sound, 5, 1, -4.6)
if (manual)
log_say("[key_name(src)] squeaks softly! ",ckey=key_name(src))
//Plays a loud sound
//Triggered manually, when a mouse dies, or rarely when its stepped on
/mob/living/simple_animal/mouse/proc/squeak_loud(var/manual = 0)
if (stat == CONSCIOUS)
if (squeakcooldown > world.time)
return
squeakcooldown = world.time + 4 SECONDS
if (squeals > 0 || !manual)
playsound(src, 'sound/effects/creatures/mouse_squeak_loud.ogg', 50, 1)
squeals --
log_say("[key_name(src)] squeals! ",ckey=key_name(src))
else
to_chat(src, "<span class='warning'>Your hoarse mousey throat can't squeal just now, stop and take a breath!</span>")
//Wrapper verbs for the squeak functions
/mob/living/simple_animal/mouse/verb/squeak_loud_verb()
set name = "Squeal!"
set category = "Abilities"
if (usr.client.prefs.muted & MUTE_IC)
to_chat(usr, "<span class='danger'>You are muted from IC emotes.</span>")
return
squeak_loud(1)
/mob/living/simple_animal/mouse/verb/squeak_soft_verb()
set name = "Soft Squeaking"
set category = "Abilities"
if (usr.client.prefs.muted & MUTE_IC)
to_chat(usr, "<span class='danger'>You are muted from IC emotes.</span>")
return
squeak_soft(1)
/mob/living/simple_animal/mouse/verb/squeak_verb()
set name = "Squeak"
set category = "Abilities"
if (usr.client.prefs.muted & MUTE_IC)
to_chat(usr, "<span class='danger'>You are muted from IC emotes.</span>")
return
squeak(1)
/mob/living/simple_animal/mouse/Crossed(AM as mob|obj)
if( ishuman(AM) )
if(!stat)
var/mob/M = AM
to_chat(M, "<span class='notice'>\icon[src] Squeek!</span>")
poke(1) //Wake up if stepped on
if (prob(95))
squeak(0)
else
squeak_loud(0)//You trod on its tail
if(!health)
return
if(istype(AM,/mob/living/simple_animal/mouse/king))
var/mob/living/simple_animal/mouse/king/K = AM
if(!K.health)
return
src.visible_message("<span class='warning'>[src] joins the [K.swarm_name] of \the [K]</span>", \
"<span class='notice'>We join our brethren in \the [K.swarm_name]. Long live \the [K].</span>")
K.absorb(src)
..()
/mob/living/simple_animal/mouse/death()
layer = MOB_LAYER
if (stat != DEAD && (ckey || prob(50)))
squeak_loud(0)//deathgasp
if(client)
client.time_died_as_mouse = world.time
SSmob.all_mice -= src
..()
/mob/living/simple_animal/mouse/dust()
..(anim = "dust_[body_color]", remains = /obj/effect/decal/remains/mouse, iconfile = 'icons/mob/npc/mouse.dmi')
/*
* Mouse types
*/
/mob/living/simple_animal/mouse/white
body_color = "white"
icon_state = "mouse_white"
icon_rest = "mouse_white_sleep"
holder_type = /obj/item/weapon/holder/mouse/white
/mob/living/simple_animal/mouse/gray
body_color = "gray"
icon_state = "mouse_gray"
icon_rest = "mouse_gray_sleep"
holder_type = /obj/item/weapon/holder/mouse/gray
/mob/living/simple_animal/mouse/brown
body_color = "brown"
icon_state = "mouse_brown"
icon_rest = "mouse_brown_sleep"
holder_type = /obj/item/weapon/holder/mouse/brown
/mob/living/simple_animal/mouse/brown/Tom
name = "Tom"
real_name = "Tom"
desc = "Jerry the cat is not amused."
/mob/living/simple_animal/mouse/brown/Tom/Initialize()
. = ..()
// Change my name back, don't want to be named Tom (666)
name = initial(name)
real_name = name
/mob/living/simple_animal/mouse/cannot_use_vents()
return
/mob/living/simple_animal/rat
name = "rat"
real_name = "rat"
desc = "It's a rather large, long-tailed rodent, often found rooting through tunnels, and aiding in the destruction of the culinary arts."
icon = 'icons/mob/npc/rat.dmi'
icon_state = "rat_gray"
item_state = "rat_gray"
icon_living = "rat_gray"
icon_dead = "rat_gray_dead"
icon_rest = "rat_gray_sleep"
can_nap = 1
speak = list("Squeek!","SQUEEK!","Squeek?")
speak_emote = list("squeeks","squeeks","squiks")
emote_hear = list("squeeks","squeaks","squiks")
emote_see = list("runs in a circle", "shakes", "scritches at something")
var/soft_squeaks = list('sound/effects/creatures/rat_squeaks_1.ogg',
'sound/effects/creatures/rat_squeaks_2.ogg',
'sound/effects/creatures/rat_squeaks_3.ogg',
'sound/effects/creatures/rat_squeaks_4.ogg')
var/last_softsqueak = null//Used to prevent the same soft squeak twice in a row
var/squeals = 5//Spam control.
var/maxSqueals = 2//SPAM PROTECTION
var/last_squealgain = 0// #TODO-FUTURE: Remove from life() once something else is created
var/squeakcooldown = 0
pass_flags = PASSTABLE
speak_chance = 3
turns_per_move = 5
see_in_dark = 6
maxHealth = 10
health = 10
meat_type = /obj/item/weapon/reagent_containers/food/snacks/meat/rat
response_help = "pets"
response_disarm = "gently pushes aside"
response_harm = "stomps on"
density = 0
meat_amount = 2 // Rats are a bit bigger, so a bit more meat for dreg-feeding.
var/body_color //brown, gray, white, american irish, hooded leave blank for random
layer = MOB_LAYER
mob_size = MOB_MINISCULE
min_oxy = 16 //Require atleast 16kPA oxygen
minbodytemp = 223 //Below -50 Degrees Celcius
maxbodytemp = 323 //Above 50 Degrees Celcius
universal_speak = 0
universal_understand = 1
holder_type = /obj/item/weapon/holder/rat
digest_factor = 0.05
min_scan_interval = 2
max_scan_interval = 20
seek_speed = 1
max_nutrition = 17
can_pull_size = 1
can_pull_mobs = MOB_PULL_NONE
var/decompose_time = 18000
kitchen_tag = "rodent"
/mob/living/simple_animal/rat/Life()
if(..())
if(client)
walk_to(src,0)
//Player-animals don't do random speech normally, so this is here
//Player-controlled rats will still squeak, but less often than NPC rats
if (stat == CONSCIOUS && prob(speak_chance*0.05))
squeak_soft(0)
if(is_ventcrawling == 0)
sight = initial(sight) // Returns mouse sight to normal when they leave a vent
if (squeals < maxSqueals)
var/diff = world.time - last_squealgain
if (diff > 600)
squeals++
last_squealgain = world.time
else
if ((world.time - timeofdeath) > decompose_time)
dust()
/mob/living/simple_animal/rat/Destroy()
SSmob.all_rats -= src
return ..()
//Pixel offsetting as they scamper around
/mob/living/simple_animal/rat/Move()
if(..())
if (prob(50))
var/new_pixelx = pixel_x
new_pixelx += rand(-2,2)
new_pixelx = Clamp(new_pixelx, -10, 10)
animate(src, pixel_x = new_pixelx, time = 0.5)
else
var/new_pixely = pixel_y
new_pixely += rand(-2,2)
new_pixely = Clamp(new_pixely, -4, 14)
animate(src, pixel_y = new_pixely, time = 0.5)
/mob/living/simple_animal/rat/Initialize()
. = ..()
nutrition = rand(max_nutrition*0.25, max_nutrition*0.75)
verbs += /mob/living/proc/ventcrawl
verbs += /mob/living/proc/hide
if(name == initial(name))
name = "[name] ([rand(1, 1000)])"
real_name = name
if(!body_color)
body_color = pick( list("brown","gray","white","hooded","irish") )
icon_state = "rat_[body_color]"
item_state = "rat_[body_color]"
icon_living = "rat_[body_color]"
icon_rest = "rat_[body_color]_sleep"
icon_dead = "rat_[body_color]_dead"
if (body_color == "brown")
holder_type = /obj/item/weapon/holder/rat/brown
if (body_color == "gray")
holder_type = /obj/item/weapon/holder/rat/gray
if (body_color == "white")
holder_type = /obj/item/weapon/holder/rat/white
if (body_color == "hooded")
holder_type = /obj/item/weapon/holder/rat/hooded
if (body_color == "irish")
holder_type = /obj/item/weapon/holder/rat/irish
SSmob.all_rats += src
/mob/living/simple_animal/rat/speak_audio()
squeak_soft(0)
/mob/living/simple_animal/rat/beg(var/atom/thing, var/atom/holder)
squeak_soft(0)
visible_emote("squeaks timidly, sniffs the air and gazes longingly up at \the [thing.name].",0)
/mob/living/simple_animal/rat/attack_hand(mob/living/carbon/human/M as mob)
if (src.stat == DEAD)//If the mouse is dead, we don't pet it, we just pickup the corpse on click
get_scooped(M, usr)
return
else
..()
/mob/living/simple_animal/rat/proc/splat()
src.health = 0
src.death()
src.icon_dead = "mouse_[body_color]_splat"
src.icon_state = "mouse_[body_color]_splat"
if(client)
client.time_died_as_rat = world.time
//Plays a sound.
//This is triggered when a mob steps on an NPC mouse, or manually by a playermouse
/mob/living/simple_animal/rat/proc/squeak(var/manual = 1)
if (stat == CONSCIOUS)
if (squeakcooldown > world.time)
return
squeakcooldown = world.time + 2 SECONDS
playsound(src, 'sound/effects/ratsqueek.ogg', 70, 1)
if (manual)
log_say("[key_name(src)] squeaks! ",ckey=key_name(src))
//Plays a random selection of four sounds, at a low volume
//This is triggered randomly periodically by any mouse, or manually
/mob/living/simple_animal/rat/proc/squeak_soft(var/manual = 1)
if (stat != DEAD) //Soft squeaks are allowed while sleeping
var/list/new_squeaks = last_softsqueak ? soft_squeaks - last_softsqueak : soft_squeaks
var/sound = pick(new_squeaks)
last_softsqueak = sound
if (squeakcooldown > world.time)
return
squeakcooldown = world.time + 2 SECONDS
playsound(src, sound, 5, 1, -4.6)
if (manual)
log_say("[key_name(src)] squeaks softly! ",ckey=key_name(src))
//Plays a loud sound
//Triggered manually, when a mouse dies, or rarely when its stepped on
/mob/living/simple_animal/rat/proc/squeak_loud(var/manual = 0)
if (stat == CONSCIOUS)
if (squeakcooldown > world.time)
return
squeakcooldown = world.time + 4 SECONDS
if (squeals > 0 || !manual)
playsound(src, 'sound/effects/creatures/rat_squeak_loud.ogg', 50, 1)
squeals --
log_say("[key_name(src)] squeals! ",ckey=key_name(src))
else
to_chat(src, "<span class='warning'>Your hoarse rattish throat can't squeal just now, stop and take a breath!</span>")
//Wrapper verbs for the squeak functions
/mob/living/simple_animal/rat/verb/squeak_loud_verb()
set name = "Squeal!"
set category = "Abilities"
if (usr.client.prefs.muted & MUTE_IC)
to_chat(usr, "<span class='danger'>You are muted from IC emotes.</span>")
return
squeak_loud(1)
/mob/living/simple_animal/rat/verb/squeak_soft_verb()
set name = "Soft Squeaking"
set category = "Abilities"
if (usr.client.prefs.muted & MUTE_IC)
to_chat(usr, "<span class='danger'>You are muted from IC emotes.</span>")
return
squeak_soft(1)
/mob/living/simple_animal/rat/verb/squeak_verb()
set name = "Squeak"
set category = "Abilities"
if (usr.client.prefs.muted & MUTE_IC)
to_chat(usr, "<span class='danger'>You are muted from IC emotes.</span>")
return
squeak(1)
/mob/living/simple_animal/rat/Crossed(AM as mob|obj)
if( ishuman(AM) )
if(!stat)
var/mob/M = AM
to_chat(M, "<span class='notice'>\icon[src] Squeek!</span>")
poke(1) //Wake up if stepped on
if (prob(95))
squeak(0)
else
squeak_loud(0)//You trod on its tail
if(!health)
return
if(istype(AM,/mob/living/simple_animal/rat/king))
var/mob/living/simple_animal/rat/king/K = AM
if(!K.health)
return
src.visible_message("<span class='warning'>[src] joins the [K.swarm_name] of \the [K]</span>", \
"<span class='notice'>We join our brethren in \the [K.swarm_name]. Long live \the [K].</span>")
K.absorb(src)
..()
/mob/living/simple_animal/rat/death()
layer = MOB_LAYER
if (stat != DEAD && (ckey || prob(50)))
squeak_loud(0)//deathgasp
if(client)
client.time_died_as_rat = world.time
SSmob.all_rats -= src
..()
/mob/living/simple_animal/rat/dust()
..(anim = "dust_[body_color]", remains = /obj/effect/decal/remains/rat, iconfile = 'icons/mob/npc/rat.dmi')
/*
* Mouse types
*/
/mob/living/simple_animal/rat/white
body_color = "white"
icon_state = "rat_white"
icon_rest = "rat_white_sleep"
holder_type = /obj/item/weapon/holder/rat/white
/mob/living/simple_animal/rat/gray
body_color = "gray"
icon_state = "rat_gray"
icon_rest = "rat_gray_sleep"
holder_type = /obj/item/weapon/holder/rat/gray
/mob/living/simple_animal/rat/brown
body_color = "brown"
icon_state = "rat_brown"
icon_rest = "rat_brown_sleep"
holder_type = /obj/item/weapon/holder/rat/brown
/mob/living/simple_animal/rat/hooded
body_color = "hooded"
icon_state = "rat_hooded"
icon_rest = "rat_brown_sleep"
holder_type = /obj/item/weapon/holder/rat/hooded
/mob/living/simple_animal/rat/irish
body_color = "irish"
icon_state = "rat_irish"
icon_rest = "rat_irish_sleep"
holder_type = /obj/item/weapon/holder/rat/irish
/mob/living/simple_animal/rat/brown/Tom
name = "Tom"
real_name = "Tom"
desc = "Jerry the cat is not amused."
/mob/living/simple_animal/rat/brown/Tom/Initialize()
. = ..()
// Change my name back, don't want to be named Tom (666)
name = initial(name)
real_name = name
/mob/living/simple_animal/rat/cannot_use_vents()
return
@@ -8,18 +8,18 @@
/proc/announceToRodents(var/message)
for(var/R in SSmob.all_mice)
for(var/R in SSmob.all_rats)
to_chat(R, message)
/mob/living/simple_animal/mouse/king
/mob/living/simple_animal/rat/king
attacktext = "bitten"
a_intent = "harm"
icon_state = "mouse_gray"
item_state = "mouse_gray"
icon_living = "mouse_gray"
icon_dead = "mouse_gray_dead"
icon_rest = "mouse_gray_sleep"
icon_state = "rat_gray"
item_state = "rat_gray"
icon_living = "rat_gray"
icon_dead = "rat_gray_dead"
icon_rest = "rat_gray_sleep"
see_in_dark = 8
see_invisible = SEE_INVISIBLE_NOLIGHTING
@@ -28,7 +28,7 @@
var/announce_name = "Request"
var/list/rats = list()
/mob/living/simple_animal/mouse/king/Initialize()
/mob/living/simple_animal/rat/king/Initialize()
. = ..()
update()
@@ -41,24 +41,24 @@
say_dead_direct("An heir to the rat throne has risen, all rejoice and celebrate.")
announceToRodents("<span class='notice'>The rat king has risen! Go at once and join his kingdom, long live the king!</span>")
/mob/living/simple_animal/mouse/king/death()
/mob/living/simple_animal/rat/king/death()
while(rats.len)
eject(rats[1], 1)
..()
/mob/living/simple_animal/mouse/king/Move()
/mob/living/simple_animal/rat/king/Move()
..()
for(var/image/I in overlays)
I.dir = src.dir
/mob/living/simple_animal/mouse/king/update_icon()
/mob/living/simple_animal/rat/king/update_icon()
..()
cut_overlays()
for(var/mob/living/simple_animal/mouse/R in rats)
for(var/mob/living/simple_animal/rat/R in rats)
var/image/rat_overlay = image('icons/mob/npc/animal.dmi', "[R.icon_state]")
rat_overlay.dir = src.dir
var/matrix/M = matrix()
@@ -66,7 +66,7 @@
rat_overlay.transform = M
add_overlay(rat_overlay)
/mob/living/simple_animal/mouse/king/proc/update()
/mob/living/simple_animal/rat/king/proc/update()
if( rats.len >= RAT_GOD_LEVEL)
name = "rat god"
swarm_name = "creation"
@@ -155,10 +155,10 @@
update_icon()
update_nutrition_stats()
/mob/living/simple_animal/mouse/king/splat()
/mob/living/simple_animal/rat/king/splat()
src.apply_damage(5, BRUTE)
/mob/living/simple_animal/mouse/king/verb/kingDecree()
/mob/living/simple_animal/rat/king/verb/kingDecree()
set category = "Abilities"
set name = "Decree"
@@ -176,7 +176,7 @@
announceToRodents( "[full_message]" )
/mob/living/simple_animal/mouse/king/verb/roar()
/mob/living/simple_animal/rat/king/verb/roar()
set category = "Abilities"
set name = "Mighty Roar"
@@ -200,7 +200,7 @@
L.flicker()
last_special = world.time + 30
/mob/living/simple_animal/mouse/king/verb/devourdead(mob/target as mob in oview())
/mob/living/simple_animal/rat/king/verb/devourdead(mob/target as mob in oview())
set category = "Abilities"
set name = "Devour Body"
@@ -236,7 +236,7 @@
last_special = world.time + 100
return
/mob/living/simple_animal/mouse/king/proc/absorb(var/mob/living/simple_animal/mouse/R, var/update = 1)
/mob/living/simple_animal/rat/king/proc/absorb(var/mob/living/simple_animal/rat/R, var/update = 1)
if(!(R in rats))
R.forceMove(src)
rats += R
@@ -244,7 +244,7 @@
if( update )
update()
/mob/living/simple_animal/mouse/king/proc/eject(var/mob/living/simple_animal/mouse/R, var/update = 1)
/mob/living/simple_animal/rat/king/proc/eject(var/mob/living/simple_animal/rat/R, var/update = 1)
if(R in rats)
R.forceMove(get_turf(src))
rats -= R
@@ -252,7 +252,7 @@
if(update)
update()
/mob/living/simple_animal/mouse/king/proc/kingdomMessage(var/message, var/king_message)
/mob/living/simple_animal/rat/king/proc/kingdomMessage(var/message, var/king_message)
for(var/R in rats)
to_chat(R, message)
@@ -261,22 +261,22 @@
else
to_chat(src, message)
/mob/living/simple_animal/mouse/king/proc/canNibbleWire()
/mob/living/simple_animal/rat/king/proc/canNibbleWire()
if(rats.len >= RAT_MAYOR_LEVEL)
return 1
return 0
/mob/living/simple_animal/mouse/king/proc/canRoar()
/mob/living/simple_animal/rat/king/proc/canRoar()
if(rats.len >= RAT_BARON_LEVEL)
return 1
return 0
/mob/living/simple_animal/mouse/king/proc/canRoarBreakLights()
/mob/living/simple_animal/rat/king/proc/canRoarBreakLights()
if(rats.len >= RAT_EMPEROR_LEVEL)
return 1
return 0
/mob/living/simple_animal/mouse/king/proc/canEatCorpse()
/mob/living/simple_animal/rat/king/proc/canEatCorpse()
if(rats.len >= RAT_KING_LEVEL)
return 1
return 0
+2 -2
View File
@@ -368,8 +368,8 @@
return 1
if(ispath(MP, /mob/living/simple_animal/tomato))
return 1
if(ispath(MP, /mob/living/simple_animal/mouse))
return 1 //It is impossible to pull up the player panel for mice (Fixed! - Nodrak)
if(ispath(MP, /mob/living/simple_animal/rat))
return 1 //It is impossible to pull up the player panel for rats (Fixed! - Nodrak)
if(ispath(MP, /mob/living/simple_animal/hostile/bear))
return 1 //Bears will auto-attack mobs, even if they're player controlled (Fixed! - Nodrak)
if(ispath(MP, /mob/living/simple_animal/parrot))