# `QuakeServer.World`
[🔗](https://github.com/jaman/quake_server/blob/v0.1.0/lib/quake_server/world.ex#L1)

Where a level's entities are, and what moving boxes run into, as FTE's `world.c` has it.

Linking an entity records its box (`absmin`..`absmax`) and the map leaves it touches
(`leaves`, kept after unlinking; `QuakeServer.Visibility`), and files it in the grid
of `QuakeServer.World.Area` (`near/2` reads it back); traces test the world model and
then the entities filed where the move passes, in the order they were filed. Triggers
are touched when an entity is linked with `touch?` true.

    {server, trace} = QuakeServer.World.trace(server, start, mins, maxs, stop, 0, mover)
    QuakeServer.World.move(server, start, mins, maxs, stop, :normal, mover)

A trace's `type` is FTE's `MOVE_` bits: 1 no monsters (only brush models block), 2
missile (monsters are hit as 30-unit boxes), 3 the world alone, 4 against studio models'
hitboxes, 16 triggers marked findable, 32 every entity marked findable whether linked
or not, 128 a chain of the entities hit through their `chain` field, 256 the entity in
the program's `other` alone, and `0x80000000` the mover's `hull` field left out. What
stops the move is the mover's `hitcontentsmaski` (or `dphitcontentsmask`), otherwise
the contents its solid kind and flags give.

# `type`

```elixir
@type type() :: :normal | :nomonsters | :missile | non_neg_integer()
```

# `bounds`

```elixir
@spec bounds(QuakeServer.Server.t(), non_neg_integer()) ::
  {Cauldron3D.Vec.t(), Cauldron3D.Vec.t()}
```

The box (`absmin`, `absmax`) linking `entity` would give it now, from its origin, size,
`solid` and angles; an entity that changed these without being linked again still holds
its old box.

# `box_contents`

```elixir
@spec box_contents(
  QuakeServer.Server.t(),
  Cauldron3D.Vec.t(),
  Cauldron3D.Vec.t(),
  Cauldron3D.Vec.t(),
  non_neg_integer()
) :: non_neg_integer()
```

The contents bits of everything a box of `mins`..`maxs` at `origin` is inside: the
world at `origin`, and every brush entity it overlaps, other than `entity`, by the
contents its negative `skin` forces or as solid.

# `choose_hull`

```elixir
@spec choose_hull([Cauldron3D.Hull.t()], Cauldron3D.Vec.t()) :: Cauldron3D.Hull.t()
```

The hull of `hulls` a box of `size` moves through, as FTE chooses it with no hull
forced (`Q1BSP_ChooseHull`): under 3 wide the point hull, up to 32.1 wide hull 3 (Half-
Life's crouching hull) when under 54.1 high or else hull 1, wider hull 2, each falling
back to a smaller hull the list has.

# `contents_all`

```elixir
@spec contents_all(QuakeServer.Server.t(), Cauldron3D.Vec.t()) :: non_neg_integer()
```

The contents bits at `point` of the world and of every `SOLID_BSP` entity whose box
holds it, a brush entity with a negative `skin` giving the contents that skin forces
wherever it has any (`World_PointContentsAllBSPs`).

# `contents_world`

```elixir
@spec contents_world(QuakeServer.Server.t(), Cauldron3D.Vec.t()) :: non_neg_integer()
```

The contents bits (`QuakeServer.Contents`) of the world model at `point` (`World_PointContentsWorldOnly`).

# `link`

```elixir
@spec link(QuakeServer.Server.t(), non_neg_integer(), boolean()) ::
  QuakeServer.Server.t()
```

Record `entity`'s box, and touch the triggers it is in when `touch?`.

# `move`

```elixir
@spec move(
  QuakeServer.Server.t(),
  Cauldron3D.Vec.t(),
  Cauldron3D.Vec.t(),
  Cauldron3D.Vec.t(),
  Cauldron3D.Vec.t(),
  type(),
  non_neg_integer()
) :: Cauldron3D.Hull.Trace.t()
```

A box of `mins`..`maxs` moved from `start` to `stop` for `mover`, as `trace/7` with
`type` `:normal` (0), `:nomonsters` (1), `:missile` (2) or `MOVE_` bits without the
entity chain; the result as a `Cauldron3D.Hull.Trace`.

# `near`

```elixir
@spec near(QuakeServer.Server.t(), {Cauldron3D.Vec.t(), Cauldron3D.Vec.t()}) ::
  MapSet.t(non_neg_integer())
```

The linked entities filed where the box `{mins, maxs}` lies.

# `point_contents`

```elixir
@spec point_contents(QuakeServer.Server.t(), Cauldron3D.Vec.t()) :: integer()
```

What `point` is in: a contents value, liquids by kind.

# `stuck?`

```elixir
@spec stuck?(QuakeServer.Server.t(), non_neg_integer()) :: boolean()
```

Whether `entity`'s box, where it stands, is inside something solid; brush models only
for a non-solid or trigger entity (`World_TestEntityPosition`).

# `touch_triggers`

```elixir
@spec touch_triggers(QuakeServer.Server.t(), non_neg_integer()) ::
  QuakeServer.Server.t()
```

Run the touch of every trigger whose box `entity`'s box overlaps, last filed first,
stopping once `entity` is freed (`World_TouchAllLinks`).

# `trace`

```elixir
@spec trace(
  QuakeServer.Server.t(),
  Cauldron3D.Vec.t(),
  Cauldron3D.Vec.t(),
  Cauldron3D.Vec.t(),
  Cauldron3D.Vec.t(),
  type(),
  non_neg_integer()
) :: {QuakeServer.Server.t(), QuakeServer.World.Trace.t()}
```

A box of `mins`..`maxs` moved from `start` to `stop` for `mover`, stopped by the first
thing in the way (`World_Move`). `type` is `MOVE_` bits (see the module doc). Starting
inside something marks the trace `start_solid` without stopping it there: whatever
the box meets later still stops it. The server comes back with the `chain` fields an
entity-chain trace writes.

# `trace_world`

```elixir
@spec trace_world(QuakeServer.Server.t(), Cauldron3D.Vec.t(), Cauldron3D.Vec.t()) ::
  Cauldron3D.Hull.Trace.t()
```

A line from `start` to `stop` through the world model alone, no entities.

# `unlink`

```elixir
@spec unlink(QuakeServer.Server.t(), non_neg_integer()) :: QuakeServer.Server.t()
```

Forget `entity`'s box.

---

*Consult [api-reference.md](api-reference.md) for complete listing*
