Files
Bubberstation/code/datums/ai/generic/find_and_set.dm
SkyratBot 7ee524f748 [MIRROR] Basic Mob Carp Part VIII: Basic Mob Carp [MDB IGNORE] (#18344)
* Basic Mob Carp Part VIII: Basic Mob Carp

* maps

* missed killing main carp file

* shorki and ocean biomes

* shorki 2: pet-a-boogaloo

Co-authored-by: Jacquerel <hnevard@gmail.com>
Co-authored-by: tastyfish <crazychris32@gmail.com>
2023-01-09 05:48:50 -05:00

135 lines
4.7 KiB
Plaintext

/**find and set
* Finds an item near themselves, sets a blackboard key as it. Very useful for ais that need to use machines or something.
* if you want to do something more complicated than find a single atom, change the search_tactic() proc
* cool tip: search_tactic() can set lists
*/
/datum/ai_behavior/find_and_set
action_cooldown = 2 SECONDS
/datum/ai_behavior/find_and_set/perform(delta_time, datum/ai_controller/controller, set_key, locate_path, search_range)
. = ..()
var/find_this_thing = search_tactic(controller, locate_path, search_range)
if(find_this_thing)
controller.blackboard[set_key] = WEAKREF(find_this_thing)
finish_action(controller, TRUE)
else
finish_action(controller, FALSE)
/datum/ai_behavior/find_and_set/proc/search_tactic(datum/ai_controller/controller, locate_path, search_range)
return locate(locate_path) in oview(search_range, controller.pawn)
/**
* Variant of find and set that fails if the living pawn doesn't hold something
*/
/datum/ai_behavior/find_and_set/pawn_must_hold_item
/datum/ai_behavior/find_and_set/pawn_must_hold_item/search_tactic(datum/ai_controller/controller)
var/mob/living/living_pawn = controller.pawn
if(!living_pawn.get_num_held_items())
return //we want to fail the search if we don't have something held
return ..()
/**
* Variant of find and set that also requires the item to be edible. checks hands too
*/
/datum/ai_behavior/find_and_set/edible
/datum/ai_behavior/find_and_set/edible/search_tactic(datum/ai_controller/controller, locate_path, search_range)
var/mob/living/living_pawn = controller.pawn
var/list/food_candidates = list()
for(var/held_candidate as anything in living_pawn.held_items)
if(!held_candidate || !IsEdible(held_candidate))
continue
food_candidates += held_candidate
var/list/local_results = locate(locate_path) in oview(search_range, controller.pawn)
for(var/local_candidate in local_results)
if(!IsEdible(local_candidate))
continue
food_candidates += local_candidate
if(food_candidates.len)
return pick(food_candidates)
/**
* Variant of find and set that only checks in hands, search range should be excluded for this
*/
/datum/ai_behavior/find_and_set/in_hands
/datum/ai_behavior/find_and_set/in_hands/search_tactic(datum/ai_controller/controller, locate_path)
var/mob/living/living_pawn = controller.pawn
return locate(locate_path) in living_pawn.held_items
/**
* Variant of find and set that takes a list of things to find.
*/
/datum/ai_behavior/find_and_set/in_list
/datum/ai_behavior/find_and_set/in_list/search_tactic(datum/ai_controller/controller, locate_paths, search_range)
var/list/found = list()
for(var/locate_path in locate_paths)
var/single_locate = ..(controller, locate_path, search_range)
if(single_locate)
found += single_locate
if(found.len)
return pick(found)
/**
* Variant of find and set which returns an object which can be animated with a staff of change
*/
/datum/ai_behavior/find_and_set/animatable
/datum/ai_behavior/find_and_set/animatable/search_tactic(datum/ai_controller/controller, locate_path, search_range)
var/mob/living/living_pawn = controller.pawn
var/list/nearby_items = list()
for (var/obj/new_friend as anything in oview(search_range, controller.pawn))
if (!isitem(new_friend) && !isstructure(new_friend))
continue
if (is_type_in_list(new_friend, GLOB.animatable_blacklist))
continue
if (living_pawn.see_invisible < new_friend.invisibility)
continue
nearby_items += new_friend
if(nearby_items.len)
return pick(nearby_items)
/**
* Variant of find and set which returns the nearest wall which isn't invulnerable
*/
/datum/ai_behavior/find_and_set/nearest_wall
/datum/ai_behavior/find_and_set/nearest_wall/search_tactic(datum/ai_controller/controller, locate_path, search_range)
var/mob/living/living_pawn = controller.pawn
var/list/nearby_walls = list()
for (var/turf/closed/new_wall in oview(search_range, controller.pawn))
if (isindestructiblewall(new_wall))
continue
nearby_walls += new_wall
if(nearby_walls.len)
return get_closest_atom(/turf/closed/, nearby_walls, living_pawn)
/**
* Variant of find and set which returns corpses who share your faction
*/
/datum/ai_behavior/find_and_set/friendly_corpses
/datum/ai_behavior/find_and_set/friendly_corpses/search_tactic(datum/ai_controller/controller, locate_path, search_range)
var/mob/living/living_pawn = controller.pawn
var/list/nearby_bodies = list()
for (var/mob/living/dead_pal in oview(search_range, controller.pawn))
if (!isturf(dead_pal.loc))
continue
if (!dead_pal.stat || dead_pal.health > 0)
continue
if (living_pawn.see_invisible < dead_pal.invisibility)
continue
if (!living_pawn.faction_check_mob(dead_pal))
continue
nearby_bodies += dead_pal
if (nearby_bodies.len)
return pick(nearby_bodies)