Skip to content

Zones and Influences

Alexander Parent edited this page Jul 31, 2026 · 1 revision

Zones and Influences

Influences are immutable and scoped to one request. They add cost, express a preference with a negative delta, or forbid a node outright.

controller.moveTo(target, List.of(
        new EntityFearInfluence(threats, 8, 2, 20),
        new BlockAvoidanceInfluence(Set.of(Block.CACTUS), 1, true, 0),
        new ReturnRadiusInfluence(home, start, 32)),
        NavigationModifiers.NONE);

Blocks are named with Minestom's Block constants and compared by identity, so block state is ignored and a modded block never collides with a vanilla one of the same short name.

Shapes

Minestom's own Area covers spheres, lines, cuboids and single cells:

// A radial danger zone. A box cannot express this.
new AreaInfluence(Area.sphere(new BlockVec(0, 64, 0), 12), true, 0, "breath");

// A costly lane rather than a closed one.
AreaInfluence.costing(Area.line(from, to), 6, "patrol-lane");

Areas are values, so two influences describing the same region compare equal and the mobs carrying them can still share a computed route.

Axis-aligned zones

NavigationZoneInfluence.blocks(
        new Vec(4, 64, 4), new Vec(6, 66, 6), true, 0, "closed-road");

Use the block factories. Zones are bounded in continuous coordinates, because a zone may be thinner than a block. Cell n occupies [n, n + 1), so bounds built from raw block coordinates silently cover one fewer cell per axis and leave it walkable. The canonical constructors are for genuinely sub-block bounds.

Roads and rooms

Restrict a request to a union of named areas. The whole bounding box must fit:

AllowedNavigationAreas roads = AllowedNavigationAreas.of(
        NavigationArea.blocks(roadFirst, roadLast, "market-road"),
        NavigationArea.blocks(turnFirst, turnLast, "market-turn"));

controller.moveTo(target, List.of(roads), NavigationModifiers.NONE);

Overlapping areas form roads, rooms, turns and junctions.

Temporary behaviour

NavigationModifiers change the profile for one request, snapshotted so an async search can never mutate another entity's:

controller.moveTo(owner.getPosition(), NavigationModifiers.builder()
        .terrainCost(TerrainType.WATER, 0)      // follow the owner into water
        .build());

They also toggle door passing and opening, floating, fence traversal and sunlight avoidance.

Clone this wiki locally