# Why Do Long Videos Show Sparse Frame Coverage in Claude Video: Causes and Fixes

> Fix sparse frame coverage in Claude Video for long videos. Learn why it happens and discover solutions like using token-burner, increasing max-frames, or zooming to specific ranges.

- Repository: [bradautomates/claude-video](https://github.com/bradautomates/claude-video)
- Tags: deep-dive
- Published: 2026-08-01

---

**Long videos show sparse frame coverage because the tool budgets a fixed number of frames across the entire duration, forcing the auto-fps logic to drop to the minimum `2.0` fps floor.** Fix this by using `--detail token-burner` to remove the cap, increasing `--max-frames`, or zooming into a sub-range with `--start` and `--end`.

In the `bradautomates/claude-video` repository, the video processing pipeline automatically throttles frame extraction to manage API costs and token usage. This causes **sparse frame coverage** where lengthy content is represented by widely spaced screenshots. Understanding the `auto_fps()` logic in [`skills/watch/scripts/frames.py`](https://github.com/bradautomates/claude-video/blob/main/skills/watch/scripts/frames.py) reveals exactly why this happens and how to override it.

## How the Frame Budget Creates Sparse Coverage

### The Fixed Frame Cap (max_frames)

The extraction logic budgets a fixed number of frames based on the selected detail level. In "balanced" mode, `max_frames` defaults to 100. The system calculates the target frame count using the formula found at lines 22-38 in [`skills/watch/scripts/frames.py`](https://github.com/bradautomates/claude-video/blob/main/skills/watch/scripts/frames.py):

```

target = min(max_frames, round(fps * duration))

```

This equation ensures the total extracted frames never exceeds the budget, regardless of video length.

### Auto-FPS Floor Limitations

The `auto_fps()` function divides the `max_frames` budget by the video duration to determine sampling density. For videos exceeding roughly 50 seconds, this calculation drops below the `MAX_FPS = 2.0` constant defined in [`frames.py`](https://github.com/bradautomates/claude-video/blob/main/frames.py). When this occurs, the system forces extraction at 2 frames per second, creating large gaps between captured moments in long videos.

### Scene Detection Fallbacks

When scene detection yields fewer than `SCENE_MIN_FRAMES = 8` cuts, the logic falls back to uniform sampling (lines 49-57 in [`frames.py`](https://github.com/bradautomates/claude-video/blob/main/frames.py)). If the frame budget is already exhausted due to length, this fallback results in even sparser coverage as the system distributes the remaining frames across the full duration.

### Warning Triggers

For videos longer than 10 minutes processed with default caps, [`watch.py`](https://github.com/bradautomates/claude-video/blob/main/watch.py) generates explicit warnings (lines 26-34) indicating that frame coverage may be insufficient for accurate analysis.

## Six Methods to Fix Sparse Frame Coverage

### 1. Use Uncapped Token-Burner Mode

**`--detail token-burner`** disables the `max_frames` budget entirely. This mode extracts every detected scene change without the 100-frame constraint, providing complete visual coverage regardless of video length.

### 2. Increase the Frame Cap

Raise **`--max-frames N`** to provide more samples across the same duration. Increasing from the default 100 to 300 triples your frame density, though API costs scale accordingly.

### 3. Zoom Into Specific Ranges

Use **`--start`** and **`--end`** timestamps to reduce effective duration. This concentrates the fixed budget on a shorter span, effectively increasing local fps without raising the global cap.

### 4. Override Auto-FPS

Force a specific extraction rate with **`--fps N`**. Note that this remains constrained by the `MAX_FPS = 2.0` ceiling in the source code unless you manually edit that constant in [`frames.py`](https://github.com/bradautomates/claude-video/blob/main/frames.py).

### 5. Select Alternative Detail Levels

- **`--detail efficient`**: Uses keyframes only, often resulting in fewer frames than "balanced" mode.
- **`--detail balanced`**: Default scene-detection mode with the 100-frame cap and warnings for long videos.
- **`--detail token-burner`**: Uncapped scene-detection mode with no `max_frames` restriction.

### 6. Configure Global Defaults

Set `WATCH_DETAIL=token-burner` in `~/.config/watch/.env` to permanently disable caps. The [`config.py`](https://github.com/bradautomates/claude-video/blob/main/config.py) module reads this environment variable during initialization, applying your preference to all future invocations.

## Practical Code Examples

```bash

# Extract every scene-change frame without budget limits

watch https://example.com/long-video.mp4 --detail token-burner

# Triple the frame budget for denser coverage

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

# Focus the budget on a specific 2-minute segment

watch https://example.com/long-video.mp4 --start 00:10:00 --end 00:12:00

# Force maximum allowed fps extraction

watch https://example.com/long-video.mp4 --fps 2.0

```

## Implementation Details in the Source Code

The sparse coverage behavior stems from three critical components in the `claude-video` codebase:

**[`skills/watch/scripts/frames.py`](https://github.com/bradautomates/claude-video/blob/main/skills/watch/scripts/frames.py)** contains the core `auto_fps()` logic (lines 22-38) that implements the budget calculation. It also defines `SCENE_MIN_FRAMES = 8` (lines 21-30) as the threshold for falling back to uniform sampling when scene detection is insufficient.

**[`skills/watch/scripts/watch.py`](https://github.com/bradautomates/claude-video/blob/main/skills/watch/scripts/watch.py)** (lines 26-34) implements the warning system for videos exceeding 10 minutes and coordinates the frame budget allocation between detail modes.

**[`skills/watch/scripts/config.py`](https://github.com/bradautomates/claude-video/blob/main/skills/watch/scripts/config.py)** defines the default `max_frames` values for each detail level and reads the `WATCH_DETAIL` environment variable to determine processing behavior without command-line flags.

## Summary

- **Sparse coverage** occurs when `auto_fps()` hits the `MAX_FPS = 2.0` floor due to the fixed `max_frames` budget spread over long durations.
- **`--detail token-burner`** removes the frame cap entirely, extracting every scene change detected by the algorithm.
- **`--max-frames N`** increases the budget linearly, directly improving frame density for the full video.
- **Time ranges** (`--start`/`--end`) concentrate the fixed budget on relevant segments, increasing local sampling rates.
- The warning for videos >10 minutes originates in [`watch.py`](https://github.com/bradautomates/claude-video/blob/main/watch.py) lines 26-34 to alert users before processing resource-intensive content.

## Frequently Asked Questions

### What is the default frame cap for balanced detail mode?

The "balanced" detail mode defaults to **100 frames** (`max_frames=100`). This value is defined in [`config.py`](https://github.com/bradautomates/claude-video/blob/main/config.py) and represents a compromise between visual coverage and API token consumption for typical video analysis tasks.

### Why is my video limited to 2 fps extraction?

The codebase enforces a `MAX_FPS = 2.0` constant in [`frames.py`](https://github.com/bradautomates/claude-video/blob/main/frames.py) as a hard ceiling to prevent excessive frame generation. The `auto_fps()` function calculates the theoretical optimal fps by dividing the `max_frames` budget by duration, but floors the result at 2.0 fps for long videos to stay within budget constraints.

### Does token-burner mode have any limits?

**`--detail token-burner`** removes the `max_frames` restriction entirely, but still respects scene detection boundaries. It extracts every frame where scene-change criteria exceed the `SCENE_MIN_FRAMES` threshold, potentially generating hundreds of frames for long videos with frequent cuts.

### Can I permanently change the default detail level?

Yes. Create or edit `~/.config/watch/.env` and add `WATCH_DETAIL=token-burner` to default all `watch` invocations to uncapped mode. The [`config.py`](https://github.com/bradautomates/claude-video/blob/main/config.py) module reads this file during initialization, applying your configuration without requiring command-line flags.