# Pause Off-Screen Videos

**MUST** · **ID:** `performance-video-autoplay-performance` · **Category:** performance
**Source:** [Rauno](https://interfaces.rauno.me/)
**Interactive version:** https://ui-guides-agent-rules.netlify.app/principles/performance-video-autoplay-performance

> MUST: Do not autoplay every video at once — observe visibility with `IntersectionObserver` and pause (or unmount) off-screen videos; iOS chokes otherwise.

Auto-playing too many videos chokes the device — pause or unmount off-screen videos

Each playing video consumes CPU and GPU resources. On mobile devices especially, having multiple videos playing simultaneously can cause the device to lag, overheat, and drain battery. Use IntersectionObserver to only play videos visible in the viewport.

## Bad — do not do this

`performance-video-autoplay-performance-bad`

```tsx
export function VideoAutoplayPerformanceBad() {
  return (
    <div className="w-full max-w-sm space-y-4">
      <div className="bg-card border border-border rounded-lg p-4 space-y-3">
        {[1, 2, 3, 4].map(i => (
          <div key={i} className="bg-muted rounded aspect-video flex items-center justify-center relative">
            <span className="text-xs text-muted-foreground">Video {i}</span>
            <span className="absolute top-1 right-1 text-[10px] bg-destructive text-white px-1 rounded">▶ Playing</span>
          </div>
        ))}
      </div>
      <p className="text-xs text-error">All 4 videos autoplay simultaneously — chokes iOS devices</p>
    </div>
  );
}
```

## Good — do this

`performance-video-autoplay-performance-good`

```tsx
export function VideoAutoplayPerformanceGood() {
  return (
    <div className="w-full max-w-sm space-y-4">
      <div className="bg-card border border-border rounded-lg p-4 space-y-3">
        {[1, 2, 3, 4].map(i => (
          <div key={i} className="bg-muted rounded aspect-video flex items-center justify-center relative">
            <span className="text-xs text-muted-foreground">Video {i}</span>
            {i === 1 ? (
              <span className="absolute top-1 right-1 text-[10px] bg-primary text-primary-foreground px-1 rounded">▶ Visible</span>
            ) : (
              <span className="absolute top-1 right-1 text-[10px] bg-muted-foreground/50 text-background px-1 rounded">⏸ Paused</span>
            )}
          </div>
        ))}
        <code className="text-xs bg-muted px-2 py-1 rounded text-foreground block">IntersectionObserver → pause off-screen</code>
      </div>
      <p className="text-xs text-success">Only visible video plays — off-screen videos paused/unmounted</p>
    </div>
  );
}
```

## References

- [interfaces.rauno.me](https://interfaces.rauno.me/)
