v1.0.0 — released 2.1KB gzip 0 dependencies TypeScript-first MIT license

collide.js

IntersectionObserver for any two elements. Proximity, collision, and time-to-collision — with real metrics.

Drag the balls. Lines connect pairs within 140px. Shapes flash when they collide.
A
B
C
D
E
0 collisions · 0 near
2.1
KB gzipped
0
Runtime deps
1 RAF
Shared loop
0
Ticks observed
Five observer primitives

Everything. Colliding. In one line.

DOM-first by default, shape-agnostic underneath. Batched RAF reads, rich metrics, TypeScript-strict.

Pair observer

Watch two elements. Fires near, collide, separate with distance + overlap.

const p = Collide.watch(a, b);
p.on('collide', (m) => ...);

One-to-many

Watch a source element against many targets — drag-to-drop zones, closest-match, etc.

const g = Collide.group(drag, zones);
g.on('near', (t, m) => ...);

All-pairs

N×N observer over a set. Every pairwise collision as it happens — avoidance, layout packing, boids.

const a = Collide.all(nodes);
a.on('collide', (a,b,m)=>...);

Velocity + TTC

Auto-tracks relative velocity and estimates time-to-collision in seconds.

m.velocity   // {x,y} px/s
m.ttc        // seconds
m.closingSpeed

Shapes

AABB by default. Opt into circles for organic UI. Cross-shape (AABB↔circle) handled.

Collide.watch(a, b, {
  shape: 'circle'
});

One shared RAF

All observers share one loop. Reads batched, zero layout thrash. Stops when idle.

Collide.check(a, b); // instant
Collide.shapes(sA, sB); // raw

Drag & drop with proximity

Drop zones glow orange when the card is near (≤ 80px), turn green on collision. No polling — one RAF read per frame, regardless of zone count.

Drag me
Zone 1
Zone 2
Zone 3

Magnetic snap

Drag the purple node. As it gets within 120px, collide.js feeds the direction vector into a simple easing loop that pulls it toward the target. Release inside the target to lock in.

Target
Drag

Time-to-collision

The green ball drifts. Drag the pink ring anywhere. TTC is computed from the relative velocity and reported before the collision happens.

distance:
closing: px/s
TTC:

Crowd avoidance

An N×N observer pushes every node away from every other when they get within 20px. Classic separation steering, driven entirely by collide.js metrics.

Event console

Every near, collide, and separate from every observer on this page streams here.

0 events

Install

2.1KB gzipped. Zero runtime dependencies. Ships ESM, UMD, and TypeScript declarations.

npm install @techzunction/collide.js
import Collide from '@techzunction/collide.js';

// Watch two elements — fires near, collide, separate
const pair = Collide.watch(cardA, cardB, { near: 80 });
pair.on('collide', (m) => console.log(m.overlap, m.ttc));
pair.on('near',    (m) => console.log(m.distance));

// Drag-to-drop zones — one source vs many targets
const g = Collide.group(drag, zones, { near: 60 });
g.on('near',    (zone, m) => zone.classList.add('near'));
g.on('collide', (zone, m) => commitDrop(zone));

// Many-to-many — crowd avoidance, packing
const all = Collide.all(nodes);
all.on('collide', (a, b, m) => separate(a, b, m.direction));

// One-shot — no observer, no RAF
const hit = Collide.check(bullet, target).colliding;