# How Claude Video Frame Cap Logic Works and When Warnings Trigger

> Understand Claude Video frame cap logic and warning triggers. Learn about detail-level caps and max frames override. Get insights for efficient video processing.

- Repository: [bradautomates/claude-video](https://github.com/bradautomates/claude-video)
- Tags: internals
- Published: 2026-08-02

---

**Claude Video uses a detail-level-based frame cap system (efficient=50, balanced=100, token-burner/transcript=unlimited) with an optional `--max-frames` override, and triggers warnings only when local files have unrecognized video extensions.**

The frame cap logic in **bradautomates/claude-video** governs how many frames the tool extracts from videos before sending them to Claude. This mechanism balances token cost against visual fidelity, implementing a tiered cap system in [`config.py`](https://github.com/bradautomates/claude-video/blob/main/config.py) that the main [`watch.py`](https://github.com/bradautomates/claude-video/blob/main/watch.py) script consumes during processing.

## Frame Cap Levels and Configuration

The `frame_cap` function in [`skills/watch/scripts/config.py`](https://github.com/bradautomates/claude-video/blob/main/skills/watch/scripts/config.py) maps user-selected detail levels to numeric limits. This function is the single source of truth for extraction budgets.

| Detail level | Frame cap | Behavior |
|-------------|-----------|----------|
| `efficient` | **50** | Minimal token usage for cost-sensitive workflows |
| `balanced` | **100** | Default reasonable budget for most use cases |
| `token-burner` | **None** | Uncapped—engine may emit every frame |
| `transcript` | **None** | Uncapped—intended for transcript-only cues |
| Any other value | **100** | Falls back to `balanced` default |

Source: [`config.py`](https://github.com/bradautomates/claude-video/blob/main/config.py) lines 65-74

The `balanced` level serves as the implicit default when no detail level is specified, ensuring predictable behavior across different invocation patterns.

## How the Frame Cap Is Applied

The [`watch.py`](https://github.com/bradautomates/claude-video/blob/main/watch.py) entry point implements a three-step resolution for determining the effective frame limit:

1. **Explicit override**: If `--max-frames` is provided on the command line, that value takes precedence unconditionally
2. **Detail lookup**: Otherwise, `frame_cap(detail)` is called to retrieve the cap for the current detail level
3. **Pipeline injection**: The resulting `max_frames` value is passed to extraction pipelines (keyframe, scene-change, uniform sampling, etc.)

Source: [`watch.py`](https://github.com/bradautomates/claude-video/blob/main/watch.py) lines 73-78

This design allows users to either respect the curated presets or bypass them entirely for specific requirements.

### Example: Explicit Frame Override

```bash

# Use balanced default (100 frames)

watch https://example.com/video.mp4

# Override to extract only 30 frames regardless of detail level

watch https://example.com/video.mp4 --max-frames 30

```

### Example: Uncapped Extraction

```bash

# Set detail environment variable to disable frame limiting

export WATCH_DETAIL=token-burner
watch https://example.com/video.mp4

```

## When Warnings Are Triggered

The codebase contains **one** frame-related warning path. Unlike the silent capping mechanism, this warning explicitly alerts users to potential issues with local file handling.

In [`skills/watch/scripts/download.py`](https://github.com/bradautomates/claude-video/blob/main/skills/watch/scripts/download.py), the `resolve_local` helper validates file extensions against the `VIDEO_EXTS` set. Unrecognized extensions trigger a warning to stderr while permitting continuation:

```python
if p.suffix.lower() not in VIDEO_EXTS:
    print(
        f"[watch] warning: {p.suffix} is not a known video extension, proceeding anyway",
        file=sys.stderr,
    )

```

Source: [`download.py`](https://github.com/bradautomates/claude-video/blob/main/download.py) lines 31-36

### Warning Trigger Example

```bash
watch /path/to/video.xyz

```

Output:

```

[watch] warning: .xyz is not a known video extension, proceeding anyway

```

No warnings exist for frame-cap violations. The cap operates silently—extraction functions (`extract_keyframes`, `extract_scene_or_uniform`, etc.) simply stop producing frames once the limit is reached.

## Key Files in the Frame Cap System

| File | Purpose | Critical Lines |
|------|---------|--------------|
| [`skills/watch/scripts/config.py`](https://github.com/bradautomates/claude-video/blob/main/skills/watch/scripts/config.py) | Maps detail strings to numeric caps | 65-74 (`frame_cap` function) |
| [`skills/watch/scripts/watch.py`](https://github.com/bradautomates/claude-video/blob/main/skills/watch/scripts/watch.py) | Resolves effective `max_frames` and drives extraction | 73-78 (cap consumption logic) |
| [`skills/watch/scripts/download.py`](https://github.com/bradautomates/claude-video/blob/main/skills/watch/scripts/download.py) | Emits extension warnings for local files | 31-36 (warning condition) |

## Summary

- **Frame caps are detail-driven**: `efficient` (50), `balanced` (100), `token-burner`/`transcript` (unlimited)
- **`--max-frames` always wins**: Explicit user values override all preset logic
- **Capping is silent**: No warnings when limits are reached—extraction simply stops
- **Only one warning exists**: Unrecognized video extensions in [`download.py`](https://github.com/bradautomates/claude-video/blob/main/download.py) trigger stderr output but don't halt processing
- **Three files implement the system**: [`config.py`](https://github.com/bradautomates/claude-video/blob/main/config.py) (definitions), [`watch.py`](https://github.com/bradautomates/claude-video/blob/main/watch.py) (application), [`download.py`](https://github.com/bradautomates/claude-video/blob/main/download.py) (extension validation)

## Frequently Asked Questions

### How do I disable the frame cap entirely in Claude Video?

Set the `WATCH_DETAIL` environment variable to `token-burner` or `transcript`. Both detail levels return `None` from `frame_cap()`, signaling extraction pipelines to process without limits. Alternatively, pass a very high `--max-frames` value to override any preset.

### Why don't I see a warning when my video hits the frame cap?

The frame cap mechanism is intentionally silent. According to the source code in [`watch.py`](https://github.com/bradautomates/claude-video/blob/main/watch.py), the cap value flows directly into extraction functions that simply stop emitting frames once exhausted. No telemetry or logging indicates when truncation occurs—this design choice prioritizes clean output over operational transparency.

### What video extensions does Claude Video recognize without warning?

The `VIDEO_EXTS` set in [`download.py`](https://github.com/bradautomates/claude-video/blob/main/download.py) defines recognized extensions. While the exact set isn't enumerated in the analyzed lines, common containers like `.mp4`, `.mov`, `.avi`, `.mkv`, and `.webm` are standard. Any extension not in this set triggers the `[watch] warning` message but processing continues.

### Can I use different frame caps for different extraction methods?

Not through built-in configuration. The `max_frames` value resolved in [`watch.py`](https://github.com/bradautomates/claude-video/blob/main/watch.py) lines 73-78 is passed uniformly to all extraction pipelines. Per-method caps would require modifying the extraction functions themselves or implementing custom preprocessing logic outside the main codebase.