earwax.mapping.box module

Provides box-related classes, functions, and exceptions.

class earwax.mapping.box.Box(game: Game, start: earwax.point.Point, end: earwax.point.Point, name: Optional[str] = None, surface_sound: Optional[pathlib.Path] = None, wall_sound: Optional[pathlib.Path] = None, type: earwax.mapping.box.BoxTypes = NOTHING, data: Optional[T] = None, stationary: bool = NOTHING, reverb: Optional[object] = NOTHING, box_level: Optional[BoxLevel] = None)

Bases: typing.Generic, earwax.mixins.RegisterEventMixin

A box on a map.

You can create instances of this class either singly, or by using the earwax.Box.create_row() method.

If you already have a list of boxes, you can fit them all onto one map with the earwax.Box.create_fitted() method.

Boxes can be assigned arbitrary user data:

b: Box[Enemy] = Box(start, end, data=Enemy())
b.data.do_something()

In addition to the coordinates supplied to this class’s constructor, a earwax.BoxBounds instance is created as earwax.Box.bounds.

This class uses the pyglet.event framework, so you can register and dispatch events in the same way you would with pyglet.window.Window, or any other EventDispatcher subclass.

Variables:
  • game – The game that this box will work with.
  • start – The coordinates at the bottom rear left corner of this box.
  • end – The coordinates at the top front right corner of this box.
  • name – An optional name for this box.
  • surface_sound – The sound that should be heard when walking in this box.
  • wall_sound – The sound that should be heard when colliding with walls in this box.
  • type – The type of this box.
  • data – Arbitrary data for this box.
  • bounds – The bounds of this box.
  • centre – The point that lies at the centre of this box.
  • reverb – The reverb that is assigned to this box.
close() → None

Close the attached door.

If this box is a door, set the open attribute of its data to False, and play the appropriate sound. Otherwise, raise earwax.NotADoor.

Parameters:door – The door to close.
contains_point(coordinates: earwax.point.Point) → bool

Return whether or not this box contains the given point.

Returns True if this box spans the given coordinates, False otherwise.

Parameters:coordinates – The coordinates to check.
could_fit(box: earwax.mapping.box.Box) → bool

Return whether or not the given box could be contained by this one.

Returns True if the given box could be contained by this box, False otherwise.

This method behaves like the contains_point() method, except that it works with Box instances, rather than Point instances.

This method simply checks that the start and end points would fit inside this box.

Parameters:box – The box whose bounds will be checked.
classmethod create_fitted(game: Game, children: List[Box], pad_start: Optional[earwax.point.Point] = None, pad_end: Optional[earwax.point.Point] = None, **kwargs) → BoxType

Return a box that fits all of children inside itself.

Pass a list of Box instances, and you’ll get a box with its start, and end attributes set to match the outer bounds of the provided children.

You can use pad_start, and pad_end to add or subtract from the calculated start and end coordinates.

Parameters:
  • children – The list of Box instances to encapsulate.
  • pad_start – A point to add to the calculated start coordinates.
  • pad_end – A point to add to the calculated end coordinates.
  • kwargs – The extra keyword arguments to pass to Box.__init__.
classmethod create_row(game: Game, start: earwax.point.Point, size: earwax.point.Point, count: int, offset: earwax.point.Point, get_name: Optional[Callable[[int], str]] = None, on_create: Optional[Callable[[Box], None]] = None, **kwargs) → List[BoxType]

Generate a list of boxes.

This method is useful for creating rows of buildings, or rooms on a corridor to name a couple of examples.

It can be used like so:

offices = Box.create_row(
    game,  # Every Box instance needs a game.
    Point(0, 0),  # The bottom_left corner of the first box.
    Point(3, 2, 0),  # The size of each box.
    3,  # The number of boxes to build.
    # The next argument is how far to move from the top right
    # corner of each created box:
    Point(1, 0, 0),
    # We want to name each room. For that, there is a function!
    get_name=lambda i: f'Room {i + 1}',
    # Let's make them all rooms.
    type=RoomTypes.room
)

This will result in a list containing 3 rooms:

  • The first from (0, 0, 0) to (2, 1, 0)
  • The second from (3, 0, 0) to (5, 1, 0)
  • And the third from (6, 0, 0) to (8, 1, 0)

PLEASE NOTE: If none of the size coordinates are >= 1, the top right coordinate will be less than the bottom left, so get_containing_box() won’t ever find it.

Parameters:
  • start – The start coordinate of the first box.
  • size – The size of each box.
  • count – The number of boxes to build.
  • offset

    The distance between the boxes.

    If no coordinate of the given value is >= 1, overlaps will occur.

  • get_name

    A function which should return an appropriate name.

    This function will be called with the current position in the loop.

    0 for the first room, 1 for the second, and so on.

  • on_create

    A function which will be called after each box is created.

    The only provided argument will be the box that was just created.

  • kwargs – Extra keyword arguments to be passed to Box.__init__.
get_nearest_point(point: earwax.point.Point) → earwax.point.Point

Return the point on this box nearest to the provided point.

Parameters:point – The point to start from.
handle_door() → None

Open or close the door attached to this box.

handle_portal() → None

Activate a portal attached to this box.

is_door

Return True if this box is a door.

is_portal

Return True if this box is a portal.

is_wall(p: earwax.point.Point) → bool

Return True if the provided point is inside a wall.

Parameters:p – The point to interrogate.
classmethod maze(game: Game, grid: ndarray, box_height: int = 3) → Generator[Box, None, None]

Return a generator containing a list of boxes.

This constructor supports mazes generated by mazelib for example.

on_activate() → None

Handle the enter key.

This event is dispatched when the player presses the enter key.

It is guaranteed that the instance this event is dispatched on is the one the player is stood on.

on_close() → None

Handle this box being closed.

on_collide(coordinates: earwax.point.Point) → None

Play an appropriate wall sound.

This function will be called by the Pyglet event framework, and should be called when a player collides with this box.

on_footstep(bearing: float, coordinates: earwax.point.Point) → None

Play an appropriate surface sound.

This function will be called by the Pyglet event framework, and should be called when a player is walking on this box.

This event is dispatched by earwax.BoxLevel.move upon a successful move.

Parameters:coordinates – The coordinates the player has just moved to.
on_open() → None

Handle this box being opened.

open() → None

Open the attached door.

If this box is a door, set the open attribute of its data to True, and play the appropriate sound. Otherwise, raise earwax.NotADoor.

Parameters:box – The box to open.
scheduled_close(dt: float) → None

Call close().

This method will be called by pyglet.clock.schedule_once.

Parameters:dt – The dt parameter expected by Pyglet’s schedule functions.
sound_manager

Return a suitable sound manager.

class earwax.mapping.box.BoxBounds(bottom_back_left: earwax.point.Point, top_front_right: earwax.point.Point)

Bases: object

Bounds for a earwax.Box instance.

Variables:
  • bottom_back_left – The bottom back left point.
  • top_front_right – The top front right point.
  • bottom_front_left – The bottom front left point.
  • bottom_front_right – The bottom front right point.
  • bottom_back_right – The bottom back right point.
  • top_back_left – The top back left point.
  • top_front_left – The top front left point.
  • top_back_right – The top back right point.
area

Return the area of the box.

depth

Get the depth of this box (front to back).

height

Return the height of this box.

is_edge(p: earwax.point.Point) → bool

Return True if p represents an edge.

Parameters:p – The point to interrogate.
volume

Return the volume of this box.

width

Return the width of this box.

exception earwax.mapping.box.BoxError

Bases: Exception

General box level error.

class earwax.mapping.box.BoxTypes

Bases: enum.Enum

The type of a box.

Variables:
  • empty

    Empty space.

    Boxes of this type can be traversed wit no barriers.

  • room

    An open room with walls around the edge.

    Boxes of this type can be entered by means of a door. The programmer must provide some means of exit.

  • solid

    Signifies a solid, impassible barrier.

    Boxes of this type cannot be traversed.

empty = 0
room = 1
solid = 2
exception earwax.mapping.box.NotADoor

Bases: earwax.mapping.box.BoxError

The current box is not a door.

exception earwax.mapping.box.NotAPortal

Bases: earwax.mapping.box.BoxError

The current box is not a portal.