How to Use Matter.Query.region in Matter.js

This guide explains how to use the Matter.Query.region method in Matter.js to detect physics bodies located inside a specified bounding box. You will learn how to define an axis-aligned bounding box (AABB), query an array of bodies from your simulation, and handle the returned results. This approach is essential for implementing area-of-effect triggers, spatial selections, and viewport culling in your physics engine.


Understanding Matter.Query.region

The Matter.Query.region function performs a fast broadphase check. It tests whether the axis-aligned bounding box (AABB) of any body in a given list overlaps with a rectangular target region.

Matter.Query.region(bodies, bounds, [outside=false])

Note: Matter.Query.region checks bounding box overlap, not exact polygonal shape intersection.


Step-by-Step Implementation

1. Define the Search Bounding Box

Create a bounds object that specifies the minimum (top-left) and maximum (bottom-right) coordinates of your selection rectangle:

const selectionArea = {
    min: { x: 100, y: 100 },
    max: { x: 300, y: 300 }
};

You can also use Matter.Bounds.create to generate this object:

const vertices = [
    { x: 100, y: 100 },
    { x: 300, y: 300 }
];
const selectionArea = Matter.Bounds.create(vertices);

2. Get the Candidate Bodies

Retrieve the bodies currently in your world using Matter.Composite.allBodies:

const allBodies = Matter.Composite.allBodies(engine.world);

3. Run the Query

Pass the candidate bodies and the target region to Matter.Query.region:

const bodiesInRegion = Matter.Query.region(allBodies, selectionArea);

The returned bodiesInRegion is an array containing references to every Matter.Body whose bounding box intersects your target area.


Complete Code Example

The following example queries the world for bodies within a box, then alters the appearance of any bodies found within that area:

const { Engine, Render, Runner, Bodies, Composite, Query } = Matter;

// Create engine and world
const engine = Engine.create();
const world = engine.world;

// Add some test bodies
const boxA = Bodies.rectangle(150, 150, 40, 40);
const boxB = Bodies.rectangle(500, 500, 40, 40);
const ground = Bodies.rectangle(400, 610, 810, 60, { isStatic: true });

Composite.add(world, [boxA, boxB, ground]);

// Define the query region
const searchRegion = {
    min: { x: 100, y: 100 },
    max: { x: 250, y: 250 }
};

// Retrieve all bodies currently in the simulation
const candidateBodies = Composite.allBodies(world);

// Query for bodies intersecting the region
const foundBodies = Query.region(candidateBodies, searchRegion);

// Process the results
foundBodies.forEach(body => {
    // Highlight matched bodies
    body.render.fillStyle = '#ff0000';
});

Finding Bodies Outside a Region

To invert the query and find all bodies located outside the defined boundary, pass true as the third argument:

const bodiesOutside = Matter.Query.region(candidateBodies, searchRegion, true);

This is useful for identifying off-screen objects to remove them from memory.