ExCollision.World
(ExCollision v1.1.0)
View Source
Collision world: static and dynamic bodies (AABB).
Supports collision checks and simulation (step with collision resolution).
Implements Enumerable over bodies.
Summary
Functions
Add body and return {world, body_id}
Add object (dynamic body) to world. Returns {world, id}.
Add static AABB (e.g. from tiles or objectgroup)
Check if two bodies intersect (e.g. bullet and player)
List of body ids intersecting the given AABB (e.g. where a bullet would move). exclude_body_id — body to ignore (the bullet itself). Useful for bullet collision: where it would move — who it hit.
Number of bodies
List of all object (body) ids in world
Check if AABB collides with world (static or body)
Get body by id
Interpolated body center (for sprite rendering by center).
Same as get_interpolated_center/4 with clamp: true.
Interpolated body position for smooth rendering. alpha in [0, 1]: 0 = previous frame, 1 = current (e.g.: time_since_step / step_interval). Returns {:ok, {x, y}} — top-left corner, or {:error, :not_found}.
Same as get_interpolated_position/4 with clamp: true.
Get object (body) by id
Check if body/object with given id exists in world
Try to move body by (dx, dy); on collision the body does not move.
If body has on_collision set, it is called with (world, body_id, [collided body ids], hit_static);
callback returns updated world (e.g. remove bullet, apply damage).
Returns {:ok, world, body} | {:collision, world, body} | {:error, :not_found}.
Update body in world
Update object (body) in world by its id
Рейкастинг: возвращает ближайшее попадание луча from → to или :miss.
Рейкастинг: возвращает все попадания вдоль луча from → to, отсортированные от ближайшего к дальнему.
Remove body by id
Remove object (body) from world by id. Returns updated world.
Remove static AABB by index (0 = first added). Returns {:ok, world} or {:error, :out_of_range}.
Set body velocity (vx, vy) in pixels/sec
Number of static AABBs in the world
World simulation step: for each dynamic body with velocity applies movement, stores previous_aabb for interpolation, resolves collisions (on collision movement is reverted). Returns updated world.
Types
@type t() :: %ExCollision.World{ bodies: %{required(term()) => ExCollision.World.Body.t()}, next_id: non_neg_integer(), static_bodies: [ExCollision.Geometry.AABB.t()] }
Functions
Add body and return {world, body_id}
Add object (dynamic body) to world. Returns {world, id}.
Add static AABB (e.g. from tiles or objectgroup)
Check if two bodies intersect (e.g. bullet and player)
List of body ids intersecting the given AABB (e.g. where a bullet would move). exclude_body_id — body to ignore (the bullet itself). Useful for bullet collision: where it would move — who it hit.
Number of bodies
List of all object (body) ids in world
Check if AABB collides with world (static or body)
Get body by id
Interpolated body center (for sprite rendering by center).
Options:
:clamp— iftrue, clampsalphato[0, 1]before interpolating (defaultfalse).
Same as get_interpolated_center/4 with clamp: true.
Interpolated body position for smooth rendering. alpha in [0, 1]: 0 = previous frame, 1 = current (e.g.: time_since_step / step_interval). Returns {:ok, {x, y}} — top-left corner, or {:error, :not_found}.
Options:
:clamp— iftrue, clampsalphato[0, 1]before interpolating (defaultfalse).
Same as get_interpolated_position/4 with clamp: true.
Get object (body) by id
Check if body/object with given id exists in world
Try to move body by (dx, dy); on collision the body does not move.
If body has on_collision set, it is called with (world, body_id, [collided body ids], hit_static);
callback returns updated world (e.g. remove bullet, apply damage).
Returns {:ok, world, body} | {:collision, world, body} | {:error, :not_found}.
Update body in world
Update object (body) in world by its id
@spec raycast(t(), {number(), number()}, {number(), number()}, keyword()) :: {:hit, float(), {float(), float()}, {:static, ExCollision.Geometry.AABB.t()} | {:body, term()}} | :miss
Рейкастинг: возвращает ближайшее попадание луча from → to или :miss.
from/to—{x, y}начало и конец луча; задают направление и максимальную длину.t ∈ [0, 1]— параметр вдоль луча:0=from,1=to.- Опции:
:check_static(defaulttrue) — проверять статические AABB:check_dynamic(defaulttrue) — проверять динамические тела:exclude_body_id— пропустить тело с этим id (например, стрелок)
Возвращает:
{:hit, t, {x, y}, tag}гдеtag={:static, aabb}|{:body, body_id}:miss
@spec raycast_all(t(), {number(), number()}, {number(), number()}, keyword()) :: [ {float(), {float(), float()}, {:static, ExCollision.Geometry.AABB.t()} | {:body, term()}} ]
Рейкастинг: возвращает все попадания вдоль луча from → to, отсортированные от ближайшего к дальнему.
Каждый элемент: {t, {x, y}, tag}. Опции: те же, что у raycast/4.
Remove body by id
Remove object (body) from world by id. Returns updated world.
Remove static AABB by index (0 = first added). Returns {:ok, world} or {:error, :out_of_range}.
Set body velocity (vx, vy) in pixels/sec
Number of static AABBs in the world
World simulation step: for each dynamic body with velocity applies movement, stores previous_aabb for interpolation, resolves collisions (on collision movement is reverted). Returns updated world.
Call every server tick (e.g. in GenServer or game loop):
world = World.step(world, dt).
- dt — step time in seconds. For fixed 60 ticks/sec use
1/60. - For deterministic simulation use fixed dt; for real-time use actual interval between ticks.