Cauldron3D.Bsp (Cauldron3D v0.2.2)

Copy Markdown View Source

A world cut into convex leaves by a binary space partition, with its faces, textures, lightmaps, what each leaf can see, and its brush models.

A loader fills the struct from its own file format; the engine draws it (Cauldron3D.Bsp.Draw), lights its faces (Cauldron3D.Bsp.Surfaces) and moves things through it (Cauldron3D.Hull).

  • planes — a tuple of {normal, distance}; a point p is in front when Vec.dot(p, normal) - distance >= 0
  • nodes — a tuple of %{plane: index, front: child, back: child, mins: Vec, maxs: Vec}; a child at or above zero is a node, below zero the leaf -child - 1
  • leaves — a tuple of %{contents: integer, faces: [face index], mins: Vec, maxs: Vec}
  • faces — a tuple of Cauldron3D.Bsp.Face
  • textures — a tuple of %{name: String.t(), kind: kind, mips: [Texture.t()]}, the mips halving in size, kind one of :solid, :masked (solid but see-through where it is colour 255), :sky, :liquid or :hidden
  • lightmaps — the lightmap bytes faces point into
  • light_channels — bytes per lightmap sample: 1 for a grey level, 3 for red, green and blue
  • world_leaves — how many leaves after leaf 0 belong to the world itself (model 0); the leaves after them belong to the brush models. nil when every leaf is the world's
  • game — the game the map was made for, :quake or :half_life
  • visibility — a tuple holding for each leaf a bitset of the leaves it can see (bit i of byte div(i, 8), least significant first), or nil where it can see every world leaf; nil for a world that keeps none. A brush model's leaves are never among those seen
  • models — a tuple of %{mins:, maxs:, origin:, heads: [node per hull], first_face:, face_count:}; model 0 is the world itself
  • hulls — the collision hulls, as Cauldron3D.Hulls with the head of model 0

Contents follow one convention: -1 empty, -2 solid, -3 water, -4 slime, -5 lava, -6 sky.

Summary

Functions

What point is inside: the contents of its leaf.

The contents value for open space.

The leaf point is in, walking from model model's first node (default the world).

The leaves whose boxes overlap the box mins..maxs.

The plane of index: {normal, distance}.

Whether leaf to is among those leaf from can see.

The contents value for solid.

The leaves leaf can see, itself included, in ascending order.

Types

kind()

@type kind() :: :solid | :masked | :sky | :liquid | :hidden

t()

@type t() :: %Cauldron3D.Bsp{
  faces: tuple(),
  game: :quake | :half_life,
  hulls: [Cauldron3D.Hull.t()],
  leaves: tuple(),
  light_channels: 1 | 3,
  lightmaps: binary(),
  models: tuple(),
  nodes: tuple(),
  planes: tuple(),
  textures: tuple(),
  visibility: tuple() | nil,
  world_leaves: non_neg_integer() | nil
}

Functions

contents(bsp, point)

@spec contents(t(), Cauldron3D.Vec.t()) :: integer()

What point is inside: the contents of its leaf.

empty()

@spec empty() :: integer()

The contents value for open space.

leaf_at(bsp, point, model \\ 0)

@spec leaf_at(t(), Cauldron3D.Vec.t(), non_neg_integer()) :: non_neg_integer()

The leaf point is in, walking from model model's first node (default the world).

leaves_touching(bsp, mins, maxs)

@spec leaves_touching(t(), Cauldron3D.Vec.t(), Cauldron3D.Vec.t()) :: [
  non_neg_integer()
]

The leaves whose boxes overlap the box mins..maxs.

plane(bsp, index)

@spec plane(t(), non_neg_integer()) :: {Cauldron3D.Vec.t(), float()}

The plane of index: {normal, distance}.

sees?(bsp, from, to)

@spec sees?(t(), non_neg_integer(), non_neg_integer()) :: boolean()

Whether leaf to is among those leaf from can see.

solid()

@spec solid() :: integer()

The contents value for solid.

visible_leaves(bsp, leaf)

@spec visible_leaves(t(), non_neg_integer()) :: [non_neg_integer()]

The leaves leaf can see, itself included, in ascending order.