diff --git a/_maps/map_files/RandomRuins/LavaRuins/lavaland_biodome_winter.dmm b/_maps/map_files/RandomRuins/LavaRuins/lavaland_biodome_winter.dmm
index 703539c83e5..ad2e757a85a 100644
--- a/_maps/map_files/RandomRuins/LavaRuins/lavaland_biodome_winter.dmm
+++ b/_maps/map_files/RandomRuins/LavaRuins/lavaland_biodome_winter.dmm
@@ -249,7 +249,7 @@
/turf/simulated/floor/plating/asteroid/snow/atmosphere,
/area/ruin/powered/snow_biodome)
"bJ" = (
-/mob/living/simple_animal/hostile/bear/polar,
+/mob/living/basic/bear/polar,
/turf/simulated/floor/plating/asteroid/snow/atmosphere,
/area/ruin/powered/snow_biodome)
"bM" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/abandoned_engi_sat.dmm b/_maps/map_files/RandomRuins/SpaceRuins/abandoned_engi_sat.dmm
index 9bbcf9dbfdf..65c7bbbc526 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/abandoned_engi_sat.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/abandoned_engi_sat.dmm
@@ -19,7 +19,7 @@
},
/area/ruin/space/abandoned_engi_sat)
"aR" = (
-/mob/living/simple_animal/hostile/carp/megacarp,
+/mob/living/basic/carp/megacarp,
/turf/template_noop,
/area/template_noop)
"bi" = (
@@ -583,7 +583,7 @@
/turf/simulated/wall/r_wall,
/area/ruin/space/abandoned_engi_sat)
"rn" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
"rr" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/abandonedzoo.dmm b/_maps/map_files/RandomRuins/SpaceRuins/abandonedzoo.dmm
index 1f0efdcffd8..7de854b4295 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/abandonedzoo.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/abandonedzoo.dmm
@@ -572,7 +572,7 @@
/obj/machinery/light{
dir = 1
},
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/simulated/floor/plating,
/area/ruin/space/unpowered)
"bx" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/asteroid1.dmm b/_maps/map_files/RandomRuins/SpaceRuins/asteroid1.dmm
index 3017a8ec0df..44ebe37926a 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/asteroid1.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/asteroid1.dmm
@@ -1,6 +1,6 @@
//MAP CONVERTED BY dmm2tgm.py THIS HEADER COMMENT PREVENTS RECONVERSION, DO NOT REMOVE
"a" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
"b" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/asteroid2.dmm b/_maps/map_files/RandomRuins/SpaceRuins/asteroid2.dmm
index d8ad7512aba..4cd646325fa 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/asteroid2.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/asteroid2.dmm
@@ -24,7 +24,7 @@
/turf/simulated/floor/plating/asteroid/airless,
/area/ruin/space/unpowered)
"V" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/asteroid5.dmm b/_maps/map_files/RandomRuins/SpaceRuins/asteroid5.dmm
index 645b750d8d9..fa094f4eeae 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/asteroid5.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/asteroid5.dmm
@@ -23,7 +23,7 @@
/turf/simulated/mineral/random/low_chance/space,
/area/ruin/space/unpowered)
"S" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
"U" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/debris2.dmm b/_maps/map_files/RandomRuins/SpaceRuins/debris2.dmm
index d4c90eeab19..19e721a1ec9 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/debris2.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/debris2.dmm
@@ -34,7 +34,7 @@
/turf/simulated/floor/plating/burnt/airless,
/area/ruin/unpowered)
"ap" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
"ar" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/derelict3.dmm b/_maps/map_files/RandomRuins/SpaceRuins/derelict3.dmm
index 21868b544b6..779231bb73d 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/derelict3.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/derelict3.dmm
@@ -18,7 +18,7 @@
/area/ruin/space/unpowered)
"l" = (
/obj/structure/lattice,
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/space/nearstation)
"m" = (
@@ -26,11 +26,11 @@
/turf/simulated/floor/plating/airless,
/area/ruin/space/unpowered)
"n" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
"s" = (
-/mob/living/simple_animal/hostile/carp/megacarp,
+/mob/living/basic/carp/megacarp,
/turf/simulated/floor/plating/airless,
/area/ruin/space/unpowered)
"w" = (
@@ -40,7 +40,7 @@
/area/ruin/space/unpowered)
"x" = (
/obj/structure/lattice,
-/mob/living/simple_animal/hostile/carp/megacarp,
+/mob/living/basic/carp/megacarp,
/turf/template_noop,
/area/space/nearstation)
"F" = (
@@ -52,7 +52,7 @@
/turf/simulated/floor/plating/airless,
/area/ruin/space/unpowered)
"O" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/simulated/floor/plating/airless,
/area/ruin/space/unpowered)
"X" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/derelict4.dmm b/_maps/map_files/RandomRuins/SpaceRuins/derelict4.dmm
index fa30b90a81d..64975929bcf 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/derelict4.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/derelict4.dmm
@@ -220,7 +220,7 @@
/turf/simulated/floor/plating/airless,
/area/ruin/space/unpowered)
"Z" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/derelict5.dmm b/_maps/map_files/RandomRuins/SpaceRuins/derelict5.dmm
index 5bbd8d64a0c..631dfa60e31 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/derelict5.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/derelict5.dmm
@@ -180,7 +180,7 @@
/turf/simulated/floor/plasteel,
/area/ruin/space/unpowered)
"yq" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
"yY" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/meatpackers.dmm b/_maps/map_files/RandomRuins/SpaceRuins/meatpackers.dmm
index 4d8c7fc05ac..6a77239121f 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/meatpackers.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/meatpackers.dmm
@@ -8,7 +8,7 @@
/turf/template_noop,
/area/space/nearstation)
"ac" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/space/nearstation)
"ad" = (
@@ -2028,7 +2028,7 @@
/turf/template_noop,
/area/space/nearstation)
"hb" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/simulated/floor/plating/asteroid/airless,
/area/ruin/powered)
"hc" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/oldstation.dmm b/_maps/map_files/RandomRuins/SpaceRuins/oldstation.dmm
index bb2f0165da3..3a171529490 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/oldstation.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/oldstation.dmm
@@ -2016,7 +2016,7 @@
/turf/simulated/floor/plasteel/white,
/area/ruin/ancientstation/proto)
"gc" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
"gf" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/onehalf.dmm b/_maps/map_files/RandomRuins/SpaceRuins/onehalf.dmm
index 0ffd2a49d58..f81c584d0b6 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/onehalf.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/onehalf.dmm
@@ -1120,7 +1120,7 @@
/turf/template_noop,
/area/space/nearstation)
"gL" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
"jI" = (
@@ -1144,7 +1144,7 @@
/area/ruin/space/onehalf/dorms_med)
"kV" = (
/obj/item/stack/rods,
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/space/nearstation)
"xr" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/spacebar.dmm b/_maps/map_files/RandomRuins/SpaceRuins/spacebar.dmm
index 18e2eb777f5..b38055bcc17 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/spacebar.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/spacebar.dmm
@@ -513,7 +513,7 @@
/turf/simulated/floor/plasteel,
/area/ruin/space/powered/bar)
"sq" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/space/nearstation)
"st" = (
@@ -871,7 +871,7 @@
},
/area/ruin/space/powered/bar)
"PA" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
"QG" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/ussp.dmm b/_maps/map_files/RandomRuins/SpaceRuins/ussp.dmm
index d71fccb6769..23ee6264a5a 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/ussp.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/ussp.dmm
@@ -2594,7 +2594,7 @@
/turf/simulated/floor/plasteel,
/area/ruin/space/derelict/hallway/primary)
"gR" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/space/nearstation)
"gS" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/ussp_tele.dmm b/_maps/map_files/RandomRuins/SpaceRuins/ussp_tele.dmm
index 207dfe5a052..0e274dc85a9 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/ussp_tele.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/ussp_tele.dmm
@@ -72,7 +72,7 @@
/turf/template_noop,
/area/ruin/space/derelict/teleporter)
"hg" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
"ic" = (
@@ -347,7 +347,7 @@
/turf/simulated/floor/plating/airless,
/area/ruin/space/derelict/teleporter)
"HL" = (
-/mob/living/simple_animal/hostile/carp/megacarp,
+/mob/living/basic/carp/megacarp,
/obj/effect/mapping_helpers/turfs/damage,
/turf/simulated/floor/plating/airless,
/area/ruin/space/derelict/teleporter)
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/voyager.dmm b/_maps/map_files/RandomRuins/SpaceRuins/voyager.dmm
index 8f037a389f9..1ab16e942aa 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/voyager.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/voyager.dmm
@@ -32,7 +32,7 @@
/turf/template_noop,
/area/template_noop)
"R" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
"S" = (
diff --git a/_maps/map_files/RandomRuins/SpaceRuins/way_home.dmm b/_maps/map_files/RandomRuins/SpaceRuins/way_home.dmm
index 99cd51cce96..3e98d5dd5e2 100644
--- a/_maps/map_files/RandomRuins/SpaceRuins/way_home.dmm
+++ b/_maps/map_files/RandomRuins/SpaceRuins/way_home.dmm
@@ -22,7 +22,7 @@
/turf/simulated/mineral/random/high_chance/clown,
/area/ruin/space/unpowered/no_grav/way_home)
"s" = (
-/mob/living/simple_animal/hostile/carp/megacarp,
+/mob/living/basic/carp/megacarp,
/turf/template_noop,
/area/template_noop)
"z" = (
@@ -34,7 +34,7 @@
/turf/simulated/floor/plating/asteroid/airless,
/area/ruin/space/unpowered/no_grav/way_home)
"P" = (
-/mob/living/simple_animal/hostile/carp,
+/mob/living/basic/carp,
/turf/template_noop,
/area/template_noop)
"R" = (
diff --git a/_maps/map_files/stations/boxstation.dmm b/_maps/map_files/stations/boxstation.dmm
index 372a1cef8ed..9dcafa3e4f3 100644
--- a/_maps/map_files/stations/boxstation.dmm
+++ b/_maps/map_files/stations/boxstation.dmm
@@ -51533,7 +51533,7 @@
/obj/effect/turf_decal/stripes/line{
dir = 1
},
-/mob/living/simple_animal/hostile/scarybat,
+/mob/living/basic/scarybat,
/obj/machinery/atmospherics/unary/vent_pump/on{
dir = 1
},
@@ -77597,7 +77597,7 @@
req_one_access = list(33,41)
},
/obj/effect/spawner/random/maintenance,
-/mob/living/simple_animal/hostile/scarybat,
+/mob/living/basic/scarybat,
/turf/simulated/floor/plasteel{
icon_state = "vault"
},
@@ -78210,7 +78210,7 @@
/obj/structure/bed,
/obj/effect/landmark/spawner/nukedisc_respawn,
/obj/effect/mob_spawn/human/corpse/skeleton,
-/mob/living/simple_animal/hostile/scarybat,
+/mob/living/basic/scarybat,
/turf/simulated/floor/plasteel{
icon_state = "vault"
},
diff --git a/_maps/map_files/stations/cerestation.dmm b/_maps/map_files/stations/cerestation.dmm
index d1b614ddc54..02a3770e018 100644
--- a/_maps/map_files/stations/cerestation.dmm
+++ b/_maps/map_files/stations/cerestation.dmm
@@ -20881,7 +20881,7 @@
group_id = "tunnelbats";
max_per_spawner = 1;
name = "bat spawner";
- path_to_spawn = /mob/living/simple_animal/hostile/scarybat;
+ path_to_spawn = /mob/living/basic/scarybat;
total_amount = 20
},
/turf/simulated/floor/plating{
@@ -44315,7 +44315,7 @@
group_id = "tunnelbats";
max_per_spawner = 1;
name = "bat spawner";
- path_to_spawn = /mob/living/simple_animal/hostile/scarybat;
+ path_to_spawn = /mob/living/basic/scarybat;
total_amount = 20
},
/turf/simulated/floor/plating{
@@ -53319,7 +53319,7 @@
group_id = "tunnelbats";
max_per_spawner = 1;
name = "bat spawner";
- path_to_spawn = /mob/living/simple_animal/hostile/scarybat;
+ path_to_spawn = /mob/living/basic/scarybat;
total_amount = 20
},
/turf/simulated/floor/plating,
@@ -58971,7 +58971,7 @@
group_id = "tunnelbats";
max_per_spawner = 1;
name = "bat spawner";
- path_to_spawn = /mob/living/simple_animal/hostile/scarybat;
+ path_to_spawn = /mob/living/basic/scarybat;
total_amount = 20
},
/obj/machinery/atmospherics/pipe/simple/hidden/supply{
@@ -66002,7 +66002,7 @@
group_id = "tunnelbats";
max_per_spawner = 1;
name = "bat spawner";
- path_to_spawn = /mob/living/simple_animal/hostile/scarybat;
+ path_to_spawn = /mob/living/basic/scarybat;
total_amount = 20
},
/obj/machinery/light/small{
@@ -115686,7 +115686,7 @@
group_id = "tunnelbats";
max_per_spawner = 1;
name = "bat spawner";
- path_to_spawn = /mob/living/simple_animal/hostile/scarybat;
+ path_to_spawn = /mob/living/basic/scarybat;
total_amount = 20
},
/obj/machinery/atmospherics/pipe/simple/hidden/supply{
diff --git a/_maps/map_files/stations/deltastation.dmm b/_maps/map_files/stations/deltastation.dmm
index b0a681e1585..7b527e5e9e2 100644
--- a/_maps/map_files/stations/deltastation.dmm
+++ b/_maps/map_files/stations/deltastation.dmm
@@ -74902,7 +74902,7 @@
/area/station/science/genetics)
"oun" = (
/obj/machinery/light/small,
-/mob/living/simple_animal/hostile/bear{
+/mob/living/basic/bear{
dir = 1
},
/obj/effect/spawner/random/blood,
@@ -76610,7 +76610,7 @@
/turf/simulated/floor/plasteel/dark,
/area/station/aisat)
"phr" = (
-/mob/living/simple_animal/hostile/bear,
+/mob/living/basic/bear,
/obj/effect/spawner/random/blood,
/turf/simulated/floor/plasteel/dark,
/area/station/maintenance/apmaint)
@@ -78217,7 +78217,7 @@
/turf/simulated/floor/grass,
/area/station/science/lobby)
"pPJ" = (
-/mob/living/simple_animal/hostile/bear{
+/mob/living/basic/bear{
dir = 1
},
/obj/effect/spawner/random/blood,
@@ -89169,7 +89169,7 @@
/obj/machinery/light/small{
dir = 1
},
-/mob/living/simple_animal/hostile/bear,
+/mob/living/basic/bear,
/obj/effect/spawner/random/blood,
/turf/simulated/floor/plasteel/dark,
/area/station/maintenance/apmaint)
diff --git a/_maps/map_files/stations/emeraldstation.dmm b/_maps/map_files/stations/emeraldstation.dmm
index a473de7f8da..60aac20a811 100644
--- a/_maps/map_files/stations/emeraldstation.dmm
+++ b/_maps/map_files/stations/emeraldstation.dmm
@@ -42967,7 +42967,7 @@
/turf/simulated/floor/bluegrid,
/area/station/aisat/hall)
"iAo" = (
-/mob/living/simple_animal/hostile/scarybat,
+/mob/living/basic/scarybat,
/obj/structure/closet/crate{
name = "Gold Crate"
},
@@ -53620,7 +53620,7 @@
/turf/simulated/floor/plating,
/area/station/maintenance/apmaint)
"kHI" = (
-/mob/living/simple_animal/hostile/scarybat,
+/mob/living/basic/scarybat,
/obj/effect/decal/cleanable/dirt,
/turf/simulated/floor/plating,
/area/station/maintenance/aft2)
@@ -69778,7 +69778,7 @@
/turf/simulated/floor/plating,
/area/station/command/office/hos)
"nUb" = (
-/mob/living/simple_animal/hostile/scarybat,
+/mob/living/basic/scarybat,
/obj/effect/decal/cleanable/confetti,
/obj/effect/decal/cleanable/dirt,
/obj/structure/sign/poster/contraband/random/directional/west,
diff --git a/_maps/map_files/stations/submaps/cerestation.dmm b/_maps/map_files/stations/submaps/cerestation.dmm
index 8debfa11576..14bc59304d7 100644
--- a/_maps/map_files/stations/submaps/cerestation.dmm
+++ b/_maps/map_files/stations/submaps/cerestation.dmm
@@ -356,7 +356,7 @@
group_id = "tunnelbats";
max_per_spawner = 1;
name = "bat spawner";
- path_to_spawn = /mob/living/simple_animal/hostile/scarybat;
+ path_to_spawn = /mob/living/basic/scarybat;
total_amount = 20
},
/turf/simulated/floor/plating{
diff --git a/code/datums/components/basic_mob_aggro_emote.dm b/code/datums/components/basic_mob_aggro_emote.dm
new file mode 100644
index 00000000000..2a8d6f8b929
--- /dev/null
+++ b/code/datums/components/basic_mob_aggro_emote.dm
@@ -0,0 +1,57 @@
+/// A component for ai-controlled atoms which plays a sound if they switch to a living target which they can attack
+/datum/component/aggro_emote
+ /// Blackboard key in which target data is stored
+ var/target_key
+ /// If we want to limit emotes to only play at mobs
+ var/living_only
+ /// List of emotes to play
+ var/list/emote_list
+ /// Chance to play an emote
+ var/emote_chance
+ /// Chance to subtract every time we play an emote (permanently)
+ var/subtract_chance
+ /// Minimum chance to play an emote
+ var/minimum_chance
+
+/datum/component/aggro_emote/Initialize(
+ target_key = BB_BASIC_MOB_CURRENT_TARGET,
+ living_only = FALSE,
+ list/emote_list,
+ emote_chance = 30,
+ minimum_chance = 2,
+ subtract_chance = 7,
+)
+ . = ..()
+ if(!isatom(parent))
+ return COMPONENT_INCOMPATIBLE
+ var/atom/atom_parent = parent
+ if(!atom_parent.ai_controller)
+ return COMPONENT_INCOMPATIBLE
+
+ src.target_key = target_key
+ src.emote_list = emote_list
+ src.emote_chance = emote_chance
+ src.minimum_chance = minimum_chance
+ src.subtract_chance = subtract_chance
+
+/datum/component/aggro_emote/RegisterWithParent()
+ . = ..()
+ RegisterSignal(parent, COMSIG_AI_BLACKBOARD_KEY_SET(target_key), PROC_REF(on_target_changed))
+
+/datum/component/aggro_emote/UnregisterFromParent()
+ UnregisterSignal(parent, COMSIG_AI_BLACKBOARD_KEY_SET(target_key))
+ return ..()
+
+/// When we get a new target, see if we want to bark at it
+/datum/component/aggro_emote/proc/on_target_changed(atom/source)
+ SIGNAL_HANDLER
+ var/atom/new_target = source.ai_controller.blackboard[target_key]
+ if(isnull(new_target) || !prob(emote_chance))
+ return
+ if(living_only && !isliving(new_target))
+ return // If we don't want to bark at food items or chairs or windows
+ emote_chance = max(emote_chance - subtract_chance, minimum_chance)
+ var/mob/living/mob_parent = source
+ if(!istype(mob_parent))
+ return
+ mob_parent.emote("me", EMOTE_VISIBLE, "[pick(emote_list)] at [new_target].")
diff --git a/code/datums/components/spawner.dm b/code/datums/components/spawner.dm
index 1b791a95d33..a289377cf67 100644
--- a/code/datums/components/spawner.dm
+++ b/code/datums/components/spawner.dm
@@ -1,5 +1,5 @@
/datum/component/spawner
- var/mob_types = list(/mob/living/simple_animal/hostile/carp)
+ var/mob_types = list(/mob/living/basic/carp)
var/spawn_time = 300 //30 seconds default
var/list/spawned_mobs = list()
var/spawn_delay = 0
diff --git a/code/datums/spells/shapeshift.dm b/code/datums/spells/shapeshift.dm
index 3d2f38cbea9..dedd0133b69 100644
--- a/code/datums/spells/shapeshift.dm
+++ b/code/datums/spells/shapeshift.dm
@@ -98,10 +98,10 @@
action_icon_state = "vampire_bats"
gain_desc = "You have gained the ability to shapeshift into bat form. This is a weak form with no abilities, only useful for stealth."
- shapeshift_type = /mob/living/simple_animal/hostile/scarybat/adminvampire
- current_shapes = list(/mob/living/simple_animal/hostile/scarybat/adminvampire)
+ shapeshift_type = /mob/living/basic/scarybat/adminvampire
+ current_shapes = list(/mob/living/basic/scarybat/adminvampire)
current_casters = list()
- possible_shapes = list(/mob/living/simple_animal/hostile/scarybat/adminvampire)
+ possible_shapes = list(/mob/living/basic/scarybat/adminvampire)
/datum/spell/shapeshift/hellhound
name = "Lesser Hellhound Form"
diff --git a/code/datums/spells/wizard_spells.dm b/code/datums/spells/wizard_spells.dm
index 1c4bd867600..feda605ccc3 100644
--- a/code/datums/spells/wizard_spells.dm
+++ b/code/datums/spells/wizard_spells.dm
@@ -256,7 +256,7 @@
invocation = "NOUK FHUNMM SACP RISSKA"
invocation_type = "shout"
- summon_type = list(/mob/living/simple_animal/hostile/carp)
+ summon_type = list(/mob/living/basic/carp)
cast_sound = 'sound/magic/summon_karp.ogg'
aoe_range = 1
diff --git a/code/game/machinery/computer/HolodeckControl.dm b/code/game/machinery/computer/HolodeckControl.dm
index a729cc402d4..ac004eec813 100644
--- a/code/game/machinery/computer/HolodeckControl.dm
+++ b/code/game/machinery/computer/HolodeckControl.dm
@@ -93,7 +93,7 @@
derez(item)
for(var/obj/effect/decal/cleanable/blood/B in linkedholodeck)
qdel(B)
- for(var/mob/living/simple_animal/hostile/carp/holocarp/C in linkedholodeck)
+ for(var/mob/living/basic/carp/holocarp/C in linkedholodeck)
qdel(C)
holographic_items = A.copy_contents_to(linkedholodeck, platingRequired = TRUE)
@@ -104,7 +104,7 @@
spawn(30)
for(var/obj/effect/landmark/L in linkedholodeck)
if(L.name=="Holocarp Spawn")
- new /mob/living/simple_animal/hostile/carp/holocarp(L.loc)
+ new /mob/living/basic/carp/holocarp(L.loc)
/obj/machinery/computer/holodeck_control/proc/emergency_shutdown()
diff --git a/code/game/objects/effects/spawners/random/misc_spawners.dm b/code/game/objects/effects/spawners/random/misc_spawners.dm
index f02cc2d9d60..7affe2658c9 100644
--- a/code/game/objects/effects/spawners/random/misc_spawners.dm
+++ b/code/game/objects/effects/spawners/random/misc_spawners.dm
@@ -215,8 +215,8 @@
icon_state = "Carp"
spawn_loot_chance = 50
loot = list(
- /mob/living/simple_animal/hostile/carp = 4,
- /mob/living/simple_animal/hostile/carp/megacarp = 1
+ /mob/living/basic/carp = 4,
+ /mob/living/basic/carp/megacarp = 1
)
/obj/effect/spawner/random/rarely_meteor_strike
diff --git a/code/game/objects/items/dehy_carp.dm b/code/game/objects/items/dehy_carp.dm
index 8638ee8335d..5e90da5390b 100644
--- a/code/game/objects/items/dehy_carp.dm
+++ b/code/game/objects/items/dehy_carp.dm
@@ -50,7 +50,7 @@
/obj/item/toy/plushie/carpplushie/dehy_carp/proc/make_carp()
// Make space carp
- var/mob/living/simple_animal/hostile/carp/C = new /mob/living/simple_animal/hostile/carp(get_turf(src))
+ var/mob/living/basic/carp/C = new(get_turf(src))
// Make carp non-hostile to user, yes this means
C.faction |= list("syndicate", "\ref[owner]")
qdel(src)
diff --git a/code/game/objects/items/weapons/grenades/spawnergrenade.dm b/code/game/objects/items/weapons/grenades/spawnergrenade.dm
index 14973b096b2..3cfc803f28c 100644
--- a/code/game/objects/items/weapons/grenades/spawnergrenade.dm
+++ b/code/game/objects/items/weapons/grenades/spawnergrenade.dm
@@ -43,7 +43,7 @@
name = "carp delivery grenade"
desc = "This grenade contains 5 dehydrated space carp in a similar manner to dehydrated monkeys, which, upon detonation, \
will be rehydrated by a small reservoir of water contained within the grenade. These space carp will then attack anything in sight."
- spawner_type = /mob/living/simple_animal/hostile/carp
+ spawner_type = /mob/living/basic/carp
deliveryamt = 5
origin_tech = "materials=3;magnets=4;syndicate=3"
diff --git a/code/game/objects/items/weapons/legcuffs.dm b/code/game/objects/items/weapons/legcuffs.dm
index bb0f9cd93e0..aac96c88f24 100644
--- a/code/game/objects/items/weapons/legcuffs.dm
+++ b/code/game/objects/items/weapons/legcuffs.dm
@@ -123,7 +123,7 @@
H.update_inv_legcuffed()
SSblackbox.record_feedback("tally", "handcuffs", 1, type)
else
- if(istype(entered, /mob/living/simple_animal/hostile/bear))
+ if(istype(entered, /mob/living/basic/bear))
entered.apply_damage(trap_damage * 2.5, BRUTE)
else
entered.apply_damage(trap_damage * 1.75, BRUTE)
diff --git a/code/game/objects/structures/monster_spawner.dm b/code/game/objects/structures/monster_spawner.dm
index 498ebfdc9df..00d7112cd72 100644
--- a/code/game/objects/structures/monster_spawner.dm
+++ b/code/game/objects/structures/monster_spawner.dm
@@ -10,7 +10,7 @@
var/max_mobs = 5
var/spawn_time = 300 //30 seconds default
- var/mob_types = list(/mob/living/simple_animal/hostile/carp)
+ var/mob_types = list(/mob/living/basic/carp)
var/spawn_text = "emerges from"
var/faction = list("hostile")
var/spawner_type = /datum/component/spawner
diff --git a/code/game/objects/structures/nest.dm b/code/game/objects/structures/nest.dm
index a85aaf417d6..fa0759b702a 100644
--- a/code/game/objects/structures/nest.dm
+++ b/code/game/objects/structures/nest.dm
@@ -75,5 +75,5 @@
spawn_mob_options = list(/mob/living/simple_animal/hostile/asteroid/goliath/beast, /mob/living/simple_animal/hostile/asteroid/goldgrub)
/obj/structure/nest/carppuppy
- spawn_mob_options = list(/mob/living/simple_animal/hostile/carp, /mob/living/simple_animal/pet/dog/corgi/puppy/void)
+ spawn_mob_options = list(/mob/living/basic/carp, /mob/living/simple_animal/pet/dog/corgi/puppy/void)
spawn_trigger_distance = 3
diff --git a/code/modules/events/carp_migration.dm b/code/modules/events/carp_migration.dm
index d63270785c6..6ecac2de81f 100644
--- a/code/modules/events/carp_migration.dm
+++ b/code/modules/events/carp_migration.dm
@@ -3,8 +3,8 @@
endWhen = 900
var/list/spawned_mobs = list(
- /mob/living/simple_animal/hostile/carp = 95,
- /mob/living/simple_animal/hostile/carp/megacarp = 5)
+ /mob/living/basic/carp = 95,
+ /mob/living/basic/carp/megacarp = 5)
/datum/event/carp_migration/setup()
announceWhen = rand(40, 60)
diff --git a/code/modules/fish/fishtank.dm b/code/modules/fish/fishtank.dm
index 36dc425b41e..65efe5270b0 100644
--- a/code/modules/fish/fishtank.dm
+++ b/code/modules/fish/fishtank.dm
@@ -546,7 +546,7 @@
to_chat(M, "There are no fish in [src]!")
else
return ..()
- else if(istype(M, /mob/living/simple_animal/hostile/bear))
+ else if(istype(M, /mob/living/basic/bear))
if(M.a_intent == INTENT_HELP) //Bears can try to fish in open tanks on help intent
if(lid_switch) //Can't fish in a closed tank. Fishbowls are ALWAYS open.
M.visible_message("[M.name] scrapes it's claws along [src]'s lid.", "The lid is closed, so you scrape your claws against [src]'s lid.")
diff --git a/code/modules/mob/living/simple_animal/hostile/bat.dm b/code/modules/mob/living/basic/hostile/bats.dm
similarity index 55%
rename from code/modules/mob/living/simple_animal/hostile/bat.dm
rename to code/modules/mob/living/basic/hostile/bats.dm
index ce9e955292c..e2520eed6a0 100644
--- a/code/modules/mob/living/simple_animal/hostile/bat.dm
+++ b/code/modules/mob/living/basic/hostile/bats.dm
@@ -1,4 +1,4 @@
-/mob/living/simple_animal/hostile/scarybat
+/mob/living/basic/scarybat
name = "space bats"
desc = "A swarm of cute little blood sucking bats that looks pretty pissed."
icon = 'icons/mob/bats.dmi'
@@ -7,63 +7,59 @@
icon_dead = "bat_dead"
icon_gib = "bat_dead"
mob_biotypes = MOB_ORGANIC | MOB_BEAST
- speak_chance = 0
- turns_per_move = 3
butcher_results = list(/obj/item/food/meat = 1)
- response_help = "pets"
- response_disarm = "gently pushes aside"
- response_harm = "hits"
+ response_help_continuous = "pets"
+ response_help_simple = "pet"
+ response_disarm_continuous = "gently pushes aside"
+ response_disarm_simple = "gently push aside"
+ attack_verb_continuous = "bites"
+ attack_verb_simple = "bite"
speed = 4
maxHealth = 20
health = 20
mob_size = MOB_SIZE_TINY
+ melee_attack_cooldown_min = 1.5 SECONDS
+ melee_attack_cooldown_max = 2.5 SECONDS
harm_intent_damage = 8
melee_damage_lower = 10
melee_damage_upper = 10
- attacktext = "bites"
+ environment_smash = ENVIRONMENT_SMASH_STRUCTURES
attack_sound = 'sound/weapons/bite.ogg'
-
- emote_taunt = list("flutters")
- taunt_chance = 20
+ ai_controller = /datum/ai_controller/basic_controller/simple/simple_hostile_obstacles
atmos_requirements = list("min_oxy" = 0, "max_oxy" = 0, "min_tox" = 0, "max_tox" = 0, "min_co2" = 0, "max_co2" = 0, "min_n2" = 0, "max_n2" = 0)
- minbodytemp = 0
-
-// break_stuff_probability = 2
+ minimum_survivable_temperature = 0
faction = list("scarybat")
gold_core_spawnable = HOSTILE_SPAWN
initial_traits = list(TRAIT_FLYING)
-/mob/living/simple_animal/hostile/scarybat/Initialize(mapload, mob/living/L)
+/mob/living/basic/scarybat/Initialize(mapload, mob/living/L)
. = ..()
+ AddComponent(/datum/component/aggro_emote, emote_list = list("flutters"), emote_chance = 20)
if(istype(L))
faction += "\ref[L]"
-/mob/living/simple_animal/hostile/scarybat/Process_Spacemove(movement_dir = 0, continuous_move = FALSE)
- return ..() //No drifting in space for space carp! //original comments do not steal
-
-/mob/living/simple_animal/hostile/scarybat/AttackingTarget()
- . =..()
- var/mob/living/L = .
+/mob/living/basic/scarybat/melee_attack(atom/target, list/modifiers, ignore_cooldown = FALSE)
+ . = ..()
+ var/mob/living/L = target
if(istype(L))
if(prob(15))
L.Stun(2 SECONDS)
L.visible_message("\the [src] scares \the [L]!")
-//This mob is for the admin-only ancient vampire, DO NOT USE ELSEWHERE
-/mob/living/simple_animal/hostile/scarybat/adminvampire
+// This mob is for the admin-only ancient vampire, DO NOT USE ELSEWHERE
+/mob/living/basic/scarybat/adminvampire
name = "bat swarm"
desc = "A swarm of vicious, angry-looking space bats."
speed = 1
harm_intent_damage = 25
maxHealth = 300
- melee_damage_lower = 10
melee_damage_upper = 30
a_intent = INTENT_HARM
pass_flags = PASSTABLE
universal_speak = TRUE
universal_understand = TRUE
- gold_core_spawnable = NO_SPAWN //badmin only
+ gold_core_spawnable = NO_SPAWN // badmin only
diff --git a/code/modules/mob/living/simple_animal/hostile/bear.dm b/code/modules/mob/living/basic/hostile/bear.dm
similarity index 60%
rename from code/modules/mob/living/simple_animal/hostile/bear.dm
rename to code/modules/mob/living/basic/hostile/bear.dm
index 82ddad0a60f..ed8c5364365 100644
--- a/code/modules/mob/living/simple_animal/hostile/bear.dm
+++ b/code/modules/mob/living/basic/hostile/bear.dm
@@ -1,5 +1,5 @@
-//Space bears!
-/mob/living/simple_animal/hostile/bear
+// Space bears!
+/mob/living/basic/bear
name = "space bear"
desc = "You don't need to be faster than a space bear, you just need to outrun your crewmates."
icon_state = "bear"
@@ -7,53 +7,59 @@
icon_dead = "bear_dead"
icon_gib = "bear_gib"
mob_biotypes = MOB_ORGANIC | MOB_BEAST
- speak = list("RAWR!", "Rawr!", "GRR!", "Growl!")
speak_emote = list("growls", "roars")
- emote_hear = list("rawrs", "grumbles", "grawls")
- emote_see = list("stares ferociously", "stomps")
- speak_chance = 1
- turns_per_move = 5
see_in_dark = 6
butcher_results = list(/obj/item/food/monstermeat/bearmeat = 5, /obj/item/clothing/head/bearpelt = 1)
- response_help = "pets"
- response_disarm = "gently pushes aside"
- response_harm = "hits"
- stop_automated_movement_when_pulled = FALSE
+ response_help_continuous = "pets"
+ response_help_simple = "pet"
+ response_disarm_continuous = "gently pushes aside"
+ response_disarm_simple = "gently push aside"
+ attack_verb_continuous = "mauls"
+ attack_verb_simple = "maul"
+ friendly_verb_continuous = "bear hugs"
+ friendly_verb_simple = "bear hug"
+ attack_sound = 'sound/effects/bite.ogg'
maxHealth = 60
health = 60
obj_damage = 60
+ melee_attack_cooldown_min = 1.5 SECONDS
+ melee_attack_cooldown_max = 2.5 SECONDS
melee_damage_lower = 20
melee_damage_upper = 30
- attacktext = "mauls"
- friendly = "bear hugs"
+ environment_smash = ENVIRONMENT_SMASH_STRUCTURES
attack_sound = 'sound/weapons/genhit3.ogg'
+ ai_controller = /datum/ai_controller/basic_controller/simple/simple_hostile_obstacles
- //Space bears aren't affected by atmos.
+ // Space bears aren't affected by atmos.
atmos_requirements = list("min_oxy" = 0, "max_oxy" = 0, "min_tox" = 0, "max_tox" = 0, "min_co2" = 0, "max_co2" = 0, "min_n2" = 0, "max_n2" = 0)
- minbodytemp = 0
+ minimum_survivable_temperature = 0
faction = list("soviet")
gold_core_spawnable = HOSTILE_SPAWN
- footstep_type = FOOTSTEP_MOB_CLAW
+ step_type = FOOTSTEP_MOB_CLAW
-/mob/living/simple_animal/hostile/bear/Process_Spacemove(movement_dir = 0, continuous_move = FALSE)
- return TRUE //No drifting in space for space bears!
+/mob/living/basic/bear/Initialize(mapload)
+ . = ..()
+ AddComponent(/datum/component/aggro_emote, emote_list = list("roars"))
-/mob/living/simple_animal/hostile/bear/black
+/mob/living/basic/bear/Process_Spacemove(movement_dir = 0, continuous_move = FALSE)
+ return TRUE // No drifting in space for space bears!
+
+/mob/living/basic/bear/black
name = "black bear"
icon_state = "black_bear"
icon_living = "black_bear"
icon_dead = "black_bear_dead"
butcher_results = list(/obj/item/food/monstermeat/bearmeat = 5, /obj/item/clothing/head/bearpelt/black = 1)
-/mob/living/simple_animal/hostile/bear/brown
+/mob/living/basic/bear/brown
name = "brown bear"
icon_state = "brown_bear"
icon_living = "brown_bear"
icon_dead = "brown_bear_dead"
butcher_results = list(/obj/item/food/monstermeat/bearmeat = 5, /obj/item/clothing/head/bearpelt/brown = 1)
-/mob/living/simple_animal/hostile/bear/polar
+/mob/living/basic/bear/polar
name = "polar bear"
desc = "Found in the most extreme climates, its insides won't protect you from that kind of cold."
icon_state = "polar_bear"
@@ -61,16 +67,16 @@
icon_dead = "polar_bear_dead"
butcher_results = list(/obj/item/food/monstermeat/bearmeat = 5, /obj/item/clothing/head/bearpelt/polar = 1)
-//SPACE BEARS! SQUEEEEEEEE~ OW! FUCK! IT BIT MY HAND OFF!!
-/mob/living/simple_animal/hostile/bear/hudson
+// SPACE BEARS! SQUEEEEEEEE~ OW! FUCK! IT BIT MY HAND OFF!!
+/mob/living/basic/bear/hudson
name = "Hudson"
- desc = "Feared outlaw, this guy is one bad news bear." //I'm sorry...
+ desc = "Feared outlaw, this guy is one bad news bear." // I'm sorry...
icon_state = "combat_bear"
icon_living = "combat_bear"
icon_dead = "combat_bear_dead"
butcher_results = list(/obj/item/food/monstermeat/bearmeat = 5, /obj/item/clothing/head/bearpelt/brown = 1)
-/mob/living/simple_animal/hostile/bear/hudson/Initialize(mapload)
+/mob/living/basic/bear/hudson/Initialize(mapload)
. = ..()
var/unbearable_pun = pick("He's unbearably cute.", "It looks like he is a bearer of bad news.", "Sadly, he is bearly able to comprehend puns.")
desc = "That's Hudson. " + unbearable_pun // I am not sorry for this.
diff --git a/code/modules/mob/living/simple_animal/hostile/carp.dm b/code/modules/mob/living/basic/hostile/carp.dm
similarity index 64%
rename from code/modules/mob/living/simple_animal/hostile/carp.dm
rename to code/modules/mob/living/basic/hostile/carp.dm
index 83327ba9c72..1413a1824a7 100644
--- a/code/modules/mob/living/simple_animal/hostile/carp.dm
+++ b/code/modules/mob/living/basic/hostile/carp.dm
@@ -1,6 +1,6 @@
-#define REGENERATION_DELAY 60 // After taking damage, how long it takes for automatic regeneration to begin for megacarps (ty robustin!)
+#define REGENERATION_DELAY 60 // After taking damage, how long it takes for automatic regeneration to begin for megacarps
-/mob/living/simple_animal/hostile/carp
+/mob/living/basic/carp
name = "space carp"
desc = "A ferocious, fang-bearing creature that resembles a fish."
icon = 'icons/mob/carp.dmi'
@@ -9,14 +9,11 @@
icon_dead = "base_dead"
icon_gib = "carp_gib"
mob_biotypes = MOB_ORGANIC | MOB_BEAST
- speak_chance = 0
- turns_per_move = 5
butcher_results = list(/obj/item/food/carpmeat = 2)
- response_help = "pets"
- response_disarm = "gently pushes aside"
- response_harm = "hits"
- emote_taunt = list("gnashes")
- taunt_chance = 30
+ response_help_continuous = "pets"
+ response_help_simple = "pet"
+ response_disarm_continuous = "gently pushes aside"
+ response_disarm_simple = "gently push aside"
speed = 0
maxHealth = 25
health = 25
@@ -25,14 +22,19 @@
obj_damage = 50
melee_damage_lower = 15
melee_damage_upper = 15
- attacktext = "bites"
+ melee_attack_cooldown_min = 1.5 SECONDS
+ melee_attack_cooldown_max = 2.5 SECONDS
+ environment_smash = ENVIRONMENT_SMASH_STRUCTURES
+ attack_verb_continuous = "bites"
+ attack_verb_simple = "bite"
attack_sound = 'sound/weapons/bite.ogg'
speak_emote = list("gnashes")
+ ai_controller = /datum/ai_controller/basic_controller/simple/simple_hostile_obstacles
- //Space carp aren't affected by atmos.
+ // Space carp aren't affected by atmos.
atmos_requirements = list("min_oxy" = 0, "max_oxy" = 0, "min_tox" = 0, "max_tox" = 0, "min_co2" = 0, "max_co2" = 0, "min_n2" = 0, "max_n2" = 0)
- minbodytemp = 0
- maxbodytemp = 1500
+ minimum_survivable_temperature = 0
+ maximum_survivable_temperature = 1500
faction = list("carp", "mining")
pressure_resistance = 200
gold_core_spawnable = HOSTILE_SPAWN
@@ -40,8 +42,8 @@
initial_traits = list(TRAIT_FLYING, TRAIT_SHOCKIMMUNE)
- var/random_color = TRUE //if the carp uses random coloring
- var/rarechance = 1 //chance for rare color variant
+ var/random_color = TRUE // if the carp uses random coloring
+ var/rarechance = 1 // chance for rare color variant
var/static/list/carp_colors = list(\
"lightpurple" = "#c3b9f1", \
@@ -63,12 +65,13 @@
"silver" = "#fdfbf3", \
)
-/mob/living/simple_animal/hostile/carp/Initialize(mapload)
+/mob/living/basic/carp/Initialize(mapload)
. = ..()
carp_randomify(rarechance)
AddComponent(/datum/component/swarming)
+ AddComponent(/datum/component/aggro_emote, emote_list = list("gnashes"))
-/mob/living/simple_animal/hostile/carp/proc/carp_randomify(rarechance)
+/mob/living/basic/carp/proc/carp_randomify(rarechance)
if(random_color)
var/our_color
if(prob(rarechance))
@@ -79,26 +82,26 @@
add_atom_colour(carp_colors[our_color], FIXED_COLOUR_PRIORITY)
update_icon()
-/mob/living/simple_animal/hostile/carp/Process_Spacemove(movement_dir = 0, continuous_move = FALSE)
- return TRUE //No drifting in space for space carp! //original comments do not steal
+/mob/living/basic/carp/Process_Spacemove(movement_dir = 0, continuous_move = FALSE)
+ return TRUE // No drifting in space for space carp! //original comments do not steal
-/mob/living/simple_animal/hostile/carp/AttackingTarget()
+/mob/living/basic/carp/melee_attack(atom/target, list/modifiers, ignore_cooldown = FALSE)
. = ..()
if(. && ishuman(target))
var/mob/living/carbon/human/H = target
H.apply_damage(8, STAMINA)
-/mob/living/simple_animal/hostile/carp/death(gibbed)
+/mob/living/basic/carp/death(gibbed)
. = ..()
if(!random_color || gibbed)
return
update_icon()
-/mob/living/simple_animal/hostile/carp/revive()
+/mob/living/basic/carp/revive()
..()
update_icon()
-/mob/living/simple_animal/hostile/carp/update_overlays()
+/mob/living/basic/carp/update_overlays()
. = ..()
if(!random_color)
return
@@ -106,24 +109,24 @@
. += mutable_appearance(icon, "base_[stat == DEAD ? "dead_" : ""]mouth", appearance_flags = RESET_COLOR)
// We do not want mobs moving through space carp, we as such we block it if the mob is not dense
-/mob/living/simple_animal/hostile/carp/CanPass(atom/movable/mover, border_dir)
- if(isliving(mover) && !istype(mover, /mob/living/simple_animal/hostile/carp) && mover.density == TRUE && stat != DEAD)
+/mob/living/basic/carp/CanPass(atom/movable/mover, border_dir)
+ if(isliving(mover) && !istype(mover, /mob/living/basic/carp) && mover.density == TRUE && stat != DEAD)
return FALSE
return ..()
// Since it's not dense we let it always hit
-/mob/living/simple_animal/hostile/carp/projectile_hit_check(obj/item/projectile/P)
+/mob/living/basic/carp/projectile_hit_check(obj/item/projectile/P)
return stat == DEAD
-/mob/living/simple_animal/hostile/carp/holocarp
+/mob/living/basic/carp/holocarp
icon_state = "holocarp"
icon_living = "holocarp"
- maxbodytemp = INFINITY
+ maximum_survivable_temperature = INFINITY
gold_core_spawnable = NO_SPAWN
- del_on_death = TRUE
+ basic_mob_flags = DEL_ON_DEATH
random_color = FALSE
-/mob/living/simple_animal/hostile/carp/megacarp
+/mob/living/basic/carp/megacarp
icon = 'icons/mob/alienqueen.dmi'
name = "Mega Space Carp"
desc = "A ferocious, fang bearing creature that resembles a shark. This one seems especially ticked off."
@@ -146,20 +149,19 @@
contains_xeno_organ = TRUE
surgery_container = /datum/xenobiology_surgery_container/megacarp
-/mob/living/simple_animal/hostile/carp/megacarp/Initialize(mapload)
+/mob/living/basic/carp/megacarp/Initialize(mapload)
. = ..()
name = "[pick(GLOB.megacarp_first_names)] [pick(GLOB.megacarp_last_names)]"
melee_damage_lower += rand(2, 10)
melee_damage_upper += rand(10, 20)
maxHealth += rand(30, 60)
- move_to_delay = rand(3, 7)
-/mob/living/simple_animal/hostile/carp/megacarp/adjustHealth(amount, updating_health = TRUE)
+/mob/living/basic/carp/megacarp/adjustHealth(amount, updating_health = TRUE)
. = ..()
if(.)
regen_cooldown = world.time + REGENERATION_DELAY
-/mob/living/simple_animal/hostile/carp/megacarp/Life()
+/mob/living/basic/carp/megacarp/Life()
..()
if(regen_cooldown < world.time)
heal_overall_damage(4)
diff --git a/code/modules/mob/living/simple_animal/hostile/retaliate/fish.dm b/code/modules/mob/living/simple_animal/hostile/retaliate/fish.dm
index edda4355d66..af86be821c8 100644
--- a/code/modules/mob/living/simple_animal/hostile/retaliate/fish.dm
+++ b/code/modules/mob/living/simple_animal/hostile/retaliate/fish.dm
@@ -50,7 +50,7 @@
update_icons()
/mob/living/simple_animal/hostile/retaliate/carp/proc/carp_randomify(rarechance)
- // Simplified version of: /mob/living/simple_animal/hostile/carp/proc/carp_randomify(rarechance)
+ // Simplified version of: /mob/living/basic/carp/proc/carp_randomify(rarechance)
var/our_color
our_color = pick(carp_colors)
add_atom_colour(carp_colors[our_color], FIXED_COLOUR_PRIORITY)
diff --git a/code/modules/projectiles/projectile/magic_projectiles.dm b/code/modules/projectiles/projectile/magic_projectiles.dm
index ddfc2c4e417..a52638b9649 100644
--- a/code/modules/projectiles/projectile/magic_projectiles.dm
+++ b/code/modules/projectiles/projectile/magic_projectiles.dm
@@ -194,11 +194,11 @@
wabbajack(change)
GLOBAL_LIST_INIT(wabbajack_hostile_animals, list(
- "carp" = /mob/living/simple_animal/hostile/carp,
- "bear" = /mob/living/simple_animal/hostile/bear,
+ "carp" = /mob/living/basic/carp,
+ "bear" = /mob/living/basic/bear,
"mushroom" = /mob/living/simple_animal/hostile/mushroom,
"statue" = /mob/living/simple_animal/hostile/statue,
- "bat" = /mob/living/simple_animal/hostile/scarybat,
+ "bat" = /mob/living/basic/scarybat,
"goat" = /mob/living/simple_animal/hostile/retaliate/goat,
"tomato" = /mob/living/simple_animal/hostile/killertomato,
"gorilla" = /mob/living/simple_animal/hostile/gorilla,
diff --git a/code/modules/research/strange_objects.dm b/code/modules/research/strange_objects.dm
index 5b60b0b8b58..c9ebfc1b5f0 100644
--- a/code/modules/research/strange_objects.dm
+++ b/code/modules/research/strange_objects.dm
@@ -133,10 +133,10 @@
/mob/living/simple_animal/lizard,
/mob/living/simple_animal/mouse,
/mob/living/simple_animal/pet/dog/pug,
- /mob/living/simple_animal/hostile/bear/black,
- /mob/living/simple_animal/hostile/bear/brown,
+ /mob/living/basic/bear/black,
+ /mob/living/basic/bear/brown,
/mob/living/simple_animal/hostile/poison/bees,
- /mob/living/simple_animal/hostile/carp
+ /mob/living/basic/carp
)
for(var/counter in 1 to animal_spawncount)
diff --git a/code/modules/research/xenobiology/xenobiology_organs.dm b/code/modules/research/xenobiology/xenobiology_organs.dm
index 60a4963617e..4cf0fb60b31 100644
--- a/code/modules/research/xenobiology/xenobiology_organs.dm
+++ b/code/modules/research/xenobiology/xenobiology_organs.dm
@@ -1354,15 +1354,15 @@
/datum/spell/shapeshift/megacarp/New(quality)
. = ..()
if(quality == ORGAN_PRISTINE)
- shapeshift_type = /mob/living/simple_animal/hostile/carp/megacarp/xeno_organ
- current_shapes = list(/mob/living/simple_animal/hostile/carp/megacarp/xeno_organ)
+ shapeshift_type = /mob/living/basic/carp/megacarp/xeno_organ
+ current_shapes = list(/mob/living/basic/carp/megacarp/xeno_organ)
current_casters = list()
- possible_shapes = list(/mob/living/simple_animal/hostile/carp/megacarp/xeno_organ)
+ possible_shapes = list(/mob/living/basic/carp/megacarp/xeno_organ)
else
- shapeshift_type = /mob/living/simple_animal/hostile/carp/xeno_organ
- current_shapes = list(/mob/living/simple_animal/hostile/carp/xeno_organ)
+ shapeshift_type = /mob/living/basic/carp/xeno_organ
+ current_shapes = list(/mob/living/basic/carp/xeno_organ)
current_casters = list()
- possible_shapes = list(/mob/living/simple_animal/hostile/carp/xeno_organ)
+ possible_shapes = list(/mob/living/basic/carp/xeno_organ)
/datum/spell/shapeshift/megacarp/Shapeshift(mob/living/carbon/human/M)
M.visible_message("[M] screams in agony as scales and fins erupt out of [M.p_their()] flesh!",
@@ -1372,7 +1372,7 @@
return
return ..()
-/mob/living/simple_animal/hostile/carp/xeno_organ
+/mob/living/basic/carp/xeno_organ
maxHealth = 100
health = 100
gold_core_spawnable = NO_SPAWN
@@ -1380,7 +1380,7 @@
universal_understand = TRUE
pass_flags = PASSTABLE
-/mob/living/simple_animal/hostile/carp/megacarp/xeno_organ
+/mob/living/basic/carp/megacarp/xeno_organ
maxHealth = 175
health = 175
gold_core_spawnable = NO_SPAWN
diff --git a/paradise.dme b/paradise.dme
index ded31d95ddc..40c783f78bd 100644
--- a/paradise.dme
+++ b/paradise.dme
@@ -503,6 +503,7 @@
#include "code\datums\components\_component.dm"
#include "code\datums\components\ai_retaliate_advanced.dm"
#include "code\datums\components\anti_magic.dm"
+#include "code\datums\components\basic_mob_aggro_emote.dm"
#include "code\datums\components\boomerang.dm"
#include "code\datums\components\boss_music.dm"
#include "code\datums\components\caltrop.dm"
@@ -2403,6 +2404,9 @@
#include "code\modules\mob\living\stat_states.dm"
#include "code\modules\mob\living\taste.dm"
#include "code\modules\mob\living\basic\basic_mob.dm"
+#include "code\modules\mob\living\basic\hostile\bats.dm"
+#include "code\modules\mob\living\basic\hostile\bear.dm"
+#include "code\modules\mob\living\basic\hostile\carp.dm"
#include "code\modules\mob\living\basic\hostile\hellhound.dm"
#include "code\modules\mob\living\basic\hostile\hellhound_ai.dm"
#include "code\modules\mob\living\basic\hostile\skeleton_mob.dm"
@@ -2614,10 +2618,7 @@
#include "code\modules\mob\living\simple_animal\friendly\spiderbot.dm"
#include "code\modules\mob\living\simple_animal\hostile\alien_types.dm"
#include "code\modules\mob\living\simple_animal\hostile\angel_statue.dm"
-#include "code\modules\mob\living\simple_animal\hostile\bat.dm"
-#include "code\modules\mob\living\simple_animal\hostile\bear.dm"
#include "code\modules\mob\living\simple_animal\hostile\bees.dm"
-#include "code\modules\mob\living\simple_animal\hostile\carp.dm"
#include "code\modules\mob\living\simple_animal\hostile\creature.dm"
#include "code\modules\mob\living\simple_animal\hostile\deathsquid.dm"
#include "code\modules\mob\living\simple_animal\hostile\drakehound.dm"
diff --git a/tools/UpdatePaths/Scripts/29775_basic_bats_bears_carp.txt b/tools/UpdatePaths/Scripts/29775_basic_bats_bears_carp.txt
new file mode 100644
index 00000000000..c3e2b728f0e
--- /dev/null
+++ b/tools/UpdatePaths/Scripts/29775_basic_bats_bears_carp.txt
@@ -0,0 +1,3 @@
+/mob/living/simple_animal/hostile/scarybat/@SUBTYPES : /mob/living/basic/scarybat/@SUBTYPES{@OLD}
+/mob/living/simple_animal/hostile/bear/@SUBTYPES : /mob/living/basic/bear/@SUBTYPES{@OLD}
+/mob/living/simple_animal/hostile/carp/@SUBTYPES : /mob/living/basic/carp/@SUBTYPES{@OLD}