[MIRROR] Mobs will not path into dangerous turfs. [MDB IGNORE] (#24739)

* Mobs will not path into dangerous turfs. (#79428)

## About The Pull Request

Fixes #79255
Fixes #79272
Fixes #79313
Fixes #79328

As it turns out, "basic avoidance" and "dumb" AI pathfinding were both
broken with regards to dangerous turfs, as was "random walk" idle
behavior. Now, these three things will properly avoid turfs that could
kill the mob.

The global typecache of dangerous turfs has been removed, in favor of a
turf-level proc, `can_cross_safely`, which returns TRUE or FALSE based
on whether a movable atom can cross the turf without being harmed. This
obviously defaults to TRUE, and is overridden for the four dangerous
turf types:
- **Space** can be safely crossed only with TRAIT_SPACEWALK. While space
does not directly cause harm, being sent drifting away is not desirable
behavior.
- **Chasms** and **open space** can be safely crossed with
TRAIT_MOVE_FLYING.
- **Lava** can be safely crossed with TRAIT_MOVE_FLYING or
TRAIT_LAVA_IMMUNE.

If an AI's pathfinding would take it through a dangerous turf, or if it
tries to randomly step onto one, the movement will be cancelled.
## Why It's Good For The Game

Basic mobs have all been ignoring dangerous terrain this whole time.
This means that mobs on Lavaland could walk right into chasms, mobs on
multi-Z stations could be tricked into falling into pits, and so on. In
the case of idle movement, no checks were happening whatsoever, causing
similar problems without players ever being involved.

Notably, skeleton mobs on certain away missions were randomly wandering
into lava, causing one of our many random CI failures of the last week.
They won't do that anymore.

All told, this should make AI behavior a little more believable, by
giving basic mobs literally any sense whatsoever of self-preservation.
## Changelog
🆑
fix: Basic mobs will no longer randomly walk into terrain that harms or
kills them.
/🆑

---------

Co-authored-by: Jacquerel <hnevard@ gmail.com>

* Mobs will not path into dangerous turfs.

---------

Co-authored-by: lizardqueenlexi <105025397+lizardqueenlexi@users.noreply.github.com>
Co-authored-by: Jacquerel <hnevard@ gmail.com>
This commit is contained in:
SkyratBot
2023-11-02 16:36:44 -04:00
committed by GitHub
co-authored by Jacquerel lizardqueenlexi
parent 678648c584
commit fdfaf83b22
9 changed files with 26 additions and 13 deletions
-6
View File
@@ -6,12 +6,6 @@ GLOBAL_LIST_EMPTY(deadmins) //all ckeys who have used the de-admin verb.
GLOBAL_LIST_EMPTY(directory) //all ckeys with associated client
GLOBAL_LIST_EMPTY(stealthminID) //reference list with IDs that store ckeys, for stealthmins
GLOBAL_LIST_INIT(dangerous_turfs, typecacheof(list(
/turf/open/lava,
/turf/open/chasm,
/turf/open/space,
/turf/open/openspace)))
/// List of types of abstract mob which shouldn't usually exist in the world on its own if we're spawning random mobs
GLOBAL_LIST_INIT(abstract_mob_types, list(
/mob/living/basic/blob_minion,
@@ -10,7 +10,10 @@
if(SPT_PROB(walk_chance, seconds_per_tick) && (living_pawn.mobility_flags & MOBILITY_MOVE) && isturf(living_pawn.loc) && !living_pawn.pulledby)
var/move_dir = pick(GLOB.alldirs)
living_pawn.Move(get_step(living_pawn, move_dir), move_dir)
var/turf/destination_turf = get_step(living_pawn, move_dir)
if(!destination_turf?.can_cross_safely(living_pawn))
return
living_pawn.Move(destination_turf, move_dir)
/datum/idle_behavior/idle_random_walk/less_walking
walk_chance = 10
@@ -69,7 +72,7 @@
var/turf/possible_step = get_step(living_pawn, direction)
if(get_dist(possible_step, target) > minimum_distance)
continue
if(possible_step.is_blocked_turf())
if(possible_step.is_blocked_turf() || !possible_step.can_cross_safely(living_pawn))
continue
possible_turfs += possible_step
@@ -17,8 +17,8 @@
. = ..()
var/turf/target_turf = get_step_towards(source.moving, source.target)
if(is_type_in_typecache(target_turf, GLOB.dangerous_turfs))
. = FALSE
if(!target_turf?.can_cross_safely(source.moving))
. = MOVELOOP_SKIP_STEP
return .
/// Move immediately and don't update our facing
+2 -2
View File
@@ -15,6 +15,6 @@
. = ..()
var/turf/target_turf = get_step_towards(source.moving, source.target)
if(is_type_in_typecache(target_turf, GLOB.dangerous_turfs))
. = FALSE
if(!target_turf?.can_cross_safely(source.moving))
. = MOVELOOP_SKIP_STEP
return .
+3
View File
@@ -76,6 +76,9 @@
/turf/open/chasm/proc/apply_components(mapload)
AddComponent(/datum/component/chasm, GET_TURF_BELOW(src), mapload)
/turf/open/chasm/can_cross_safely(atom/movable/crossing)
return HAS_TRAIT(src, TRAIT_CHASM_STOPPED) || HAS_TRAIT(crossing, TRAIT_MOVE_FLYING)
// Chasms for Lavaland, with planetary atmos and lava glow
/turf/open/chasm/lavaland
initial_gas_mix = LAVALAND_DEFAULT_ATMOS
+3
View File
@@ -315,6 +315,9 @@
burn_living.adjust_fire_stacks(lava_firestacks * seconds_per_tick)
burn_living.ignite_mob()
/turf/open/lava/can_cross_safely(atom/movable/crossing)
return HAS_TRAIT(src, TRAIT_LAVA_STOPPED) || HAS_TRAIT(crossing, immunity_trait ) || HAS_TRAIT(crossing, TRAIT_MOVE_FLYING)
/turf/open/lava/smooth
name = "lava"
baseturfs = /turf/open/lava/smooth
+3
View File
@@ -166,6 +166,9 @@
PlaceOnTop(/turf/open/floor/plating, flags = flags)
PlaceOnTop(new_floor_path, flags = flags)
/turf/open/openspace/can_cross_safely(atom/movable/crossing)
return HAS_TRAIT(crossing, TRAIT_MOVE_FLYING)
/turf/open/openspace/icemoon
name = "ice chasm"
baseturfs = /turf/open/openspace/icemoon
+3
View File
@@ -254,6 +254,9 @@ GLOBAL_LIST_EMPTY(starlight)
destination_y = dest_y
destination_z = dest_z
/turf/open/space/can_cross_safely(atom/movable/crossing)
return HAS_TRAIT(crossing, TRAIT_SPACEWALK)
/turf/open/space/openspace
icon = 'icons/turf/floors.dmi'
icon_state = MAP_SWITCH("pure_white", "invisible")
+5 -1
View File
@@ -6,7 +6,7 @@ GLOBAL_LIST_EMPTY(station_turfs)
vis_flags = VIS_INHERIT_ID // Important for interaction with and visualization of openspace.
luminosity = 1
light_height = LIGHTING_HEIGHT_FLOOR
///what /mob/oranges_ear instance is already assigned to us as there should only ever be one.
///used for guaranteeing there is only one oranges_ear per turf when assigned, speeds up view() iteration
var/mob/oranges_ear/assigned_oranges_ear
@@ -756,3 +756,7 @@ GLOBAL_LIST_EMPTY(station_turfs)
explosive_resistance -= get_explosive_block()
inherent_explosive_resistance = explosion_block
explosive_resistance += get_explosive_block()
/// Returns whether it is safe for an atom to move across this turf
/turf/proc/can_cross_safely(atom/movable/crossing)
return TRUE