Quick answer: Set the moving Rigidbody’s Collision Detection to Continuous (vs static triggers) or Continuous Dynamic (vs moving Rigidbody triggers). Discrete misses fast movers.

A bullet flies through a damage trigger volume. Sometimes the damage applies, sometimes the bullet passes clean through with no OnTriggerEnter event. The bullet’s speed is well within game logic ranges, but the trigger is being tunneled at high frame deltas.

Why Discrete Misses Triggers

Unity’s default collision mode is Discrete. At each fixed-update tick, the physics engine checks if a Rigidbody’s collider overlaps any other collider. If the Rigidbody moved fast enough between ticks to be on one side of a trigger at tick N and the other side at tick N+1, no overlap is detected at either tick, so no OnTriggerEnter fires.

The fixed timestep defaults to 0.02 seconds (50 Hz). At 50 m/s, a body moves 1 m per tick. If a trigger’s thickness along the motion vector is less than 1 m, tunneling happens.

The Fix: Continuous Collision Detection

On the fast Rigidbody:

GetComponent<Rigidbody>().collisionDetectionMode = CollisionDetectionMode.Continuous;

Or set it in the Inspector under the Rigidbody component. The four modes:

For triggers specifically — the static trigger volume doesn’t need any setting. The flag is on the moving body.

Required Setup Quirks

CCD has caveats:

Alternate Fix: Replace Trigger with OverlapBox

For one-shot collision points (e.g., a projectile’s impact check), skip the trigger and use a swept query:

void FixedUpdate()
{
    Vector3 from = transform.position;
    Vector3 to = from + rigidbody.linearVelocity * Time.fixedDeltaTime;
    if (Physics.SphereCast(from, radius, rigidbody.linearVelocity.normalized,
        out RaycastHit hit, (to - from).magnitude, triggerMask, QueryTriggerInteraction.Collide))
    {
        OnHitTrigger(hit.collider);
    }
}

QueryTriggerInteraction.Collide tells SphereCast to include trigger colliders in its hits. This gives you the exact contact point and surface normal — better than OnTriggerEnter, which only tells you that a collider overlaps.

Increase Fixed Tick Rate

For project-wide improvement, lower the fixed timestep:

// Edit → Project Settings → Time
// Fixed Timestep: 0.01  (100 Hz, default 0.02)

Doubling the tick rate halves per-tick travel distance. Cost is double physics CPU; helpful if tunneling appears in many places.

Verifying

Add a counter for triggers entered. Launch the projectile through a thin trigger volume 100 times at varying speeds. Before the fix, miss rate scales with speed. After enabling Continuous, every pass registers an OnTriggerEnter.

“Discrete + Fast + Thin = Missed Event. Pick one to change. Continuous CD is usually the cheapest fix.”

Set Continuous per-prefab on projectiles, not project-wide — CCD cost adds up across hundreds of bodies.