mirror of
https://github.com/Citadel-Station-13/Citadel-Station-13-RP.git
synced 2026-08-21 00:26:37 +01:00
180 lines
4.2 KiB
Plaintext
180 lines
4.2 KiB
Plaintext
//* This file is explicitly licensed under the MIT license. *//
|
|
//* Copyright (c) 2024 Citadel Station Developers *//
|
|
|
|
// * Mapping Functions * //
|
|
|
|
/// These are not super optimized, but work fine enough; using them outside of SDQL is allowed,
|
|
/// These are usually typechecked, and will silently remove invalid inputs. Keep that in mind.
|
|
|
|
//* Deduping *//
|
|
|
|
/proc/sdql_list_dedupe(list/L)
|
|
. = list()
|
|
for(var/thing in L)
|
|
. |= thing
|
|
|
|
//* Type filtering *//
|
|
|
|
/**
|
|
* datums only
|
|
*/
|
|
/proc/sdql_typecache_filter(list/datum/things, list/typecache)
|
|
. = list()
|
|
for(var/datum/thing as anything in things)
|
|
if(!isdatum(thing) || !typecache[thing.type])
|
|
continue
|
|
. += thing
|
|
|
|
/**
|
|
* datums only
|
|
*/
|
|
/proc/sdql_typecache_filter_exclude(list/datum/things, list/typecache)
|
|
. = list()
|
|
for(var/datum/thing as anything in things)
|
|
if(!isdatum(thing) || typecache[thing.type])
|
|
continue
|
|
. += thing
|
|
|
|
/**
|
|
* datums only
|
|
*/
|
|
/proc/sdql_type_filter(list/datum/things, type)
|
|
. = list()
|
|
for(var/datum/thing as anything in things)
|
|
if(!istype(thing, type))
|
|
continue
|
|
. += thing
|
|
|
|
/**
|
|
* datums only
|
|
*/
|
|
/proc/sdql_type_filter_exclude(list/datum/things, type)
|
|
. = list()
|
|
for(var/datum/thing as anything in things)
|
|
if(!isdatum(thing) || istype(thing, type))
|
|
continue
|
|
. += thing
|
|
|
|
//* Turfs to contents *//
|
|
|
|
/**
|
|
* this will **not** dupe filter
|
|
*/
|
|
/proc/sdql_turfs_to_contents(list/turf/turfs, forbid_atom_flags, any_atom_flags, all_atom_flags)
|
|
. = list()
|
|
// i wish byond would compiler optimize this
|
|
// but silicons, for once, will not write a hand-optimized 500 line monstrosity
|
|
for(var/turf/T in turfs)
|
|
for(var/atom/movable/AM as anything in T.contents)
|
|
if(forbid_atom_flags && (AM.atom_flags & forbid_atom_flags))
|
|
continue
|
|
if(any_atom_flags && !(AM.atom_flags & any_atom_flags))
|
|
continue
|
|
if(all_atom_flags && ((AM.atom_flags & all_atom_flags) != all_atom_flags))
|
|
continue
|
|
. += AM
|
|
|
|
/**
|
|
* ignores NONWORLD and ABSTRACT mobs
|
|
*/
|
|
/proc/sdql_turfs_to_game_mobs(list/turf/turfs)
|
|
. = list()
|
|
for(var/turf/T in turfs)
|
|
for(var/mob/M in T)
|
|
if(M.atom_flags & (ATOM_NONWORLD | ATOM_ABSTRACT))
|
|
continue
|
|
. += M
|
|
|
|
/**
|
|
* ignores NONWORLD and ABSTRACT objs
|
|
*
|
|
* * warning: /atom/movables may or may not be objs. blame byond.
|
|
*/
|
|
/proc/sdql_turfs_to_game_objs(list/turf/turfs)
|
|
. = list()
|
|
for(var/turf/T in turfs)
|
|
for(var/obj/O in T)
|
|
if(O.atom_flags & (ATOM_NONWORLD | ATOM_ABSTRACT))
|
|
continue
|
|
. += O
|
|
|
|
//* Movables to loc *//
|
|
|
|
/proc/sdql_movable_to_loc(list/atom/movable/movables, allow_dupe = FALSE, allow_null = FALSE)
|
|
. = list()
|
|
if(allow_dupe)
|
|
if(allow_null)
|
|
for(var/atom/movable/AM in movables)
|
|
. += AM.loc
|
|
else
|
|
for(var/atom/movable/AM in movables)
|
|
if(!AM.loc)
|
|
continue
|
|
. += AM.loc
|
|
else
|
|
if(allow_null)
|
|
for(var/atom/movable/AM in movables)
|
|
. |= AM.loc
|
|
else
|
|
for(var/atom/movable/AM in movables)
|
|
if(!AM.loc)
|
|
continue
|
|
. |= AM.loc
|
|
|
|
/proc/sdql_movable_to_on_turf(list/atom/movable/movables, allow_dupe = FALSE)
|
|
. = list()
|
|
if(allow_dupe)
|
|
for(var/atom/movable/AM in movables)
|
|
if(!isturf(AM.loc))
|
|
continue
|
|
. += AM.loc
|
|
else
|
|
for(var/atom/movable/AM in movables)
|
|
if(!isturf(AM.loc))
|
|
continue
|
|
. |= AM.loc
|
|
|
|
/proc/sdql_movable_to_get_turf(list/atom/movable/movables, allow_dupe = FALSE, allow_null = FALSE)
|
|
. = list()
|
|
for(var/atom/movable/AM in movables)
|
|
var/turf/location = get_turf(AM)
|
|
if(!allow_null && !location)
|
|
continue
|
|
if(allow_dupe)
|
|
. += location
|
|
else
|
|
. |= location
|
|
|
|
//* spatial query / ranging *//
|
|
|
|
/proc/sdql_atoms_to_turfs_in_range(list/atom/movables, radius = 0, allow_dupe = FALSE)
|
|
. = list()
|
|
var/safety = 100000 // a bit more than 1MB
|
|
var/list/results
|
|
if(allow_dupe)
|
|
for(var/atom/A in movables)
|
|
results = range(radius, A)
|
|
if(!length(results))
|
|
continue
|
|
. += results
|
|
if(length(.) > safety)
|
|
stack_trace("hit safety limit")
|
|
break
|
|
else
|
|
var/list/hashed = list()
|
|
for(var/atom/A in movables)
|
|
results = range(radius, A)
|
|
if(!length(results))
|
|
continue
|
|
for(var/turf/T as anything in results)
|
|
hashed[T] = TRUE
|
|
if(length(hashed) > safety) // a bit more than 3MB due to assoclist...
|
|
stack_trace("hit safety limit")
|
|
break
|
|
// we want a flat list
|
|
for(var/key in hashed)
|
|
. += key
|
|
|
|
// todo: in view
|
|
// todo: in dview
|