A robust, high-performance Rust tool for extracting unique frames from video sequences using Mean Squared Error (MSE) analysis with comprehensive error handling and parallel processing.
Screenshotter processes sequential PNG frames extracted from video files and identifies visually distinct images by computing pixel-level differences between consecutive frames. The tool employs configurable parallel processing with robust error handling to efficiently and reliably handle large frame sequences.
The core algorithm implements Mean Squared Error calculation between consecutive frames:
- Frame Processing: Loads PNG images from input directory in lexicographical order
- MSE Computation: For each pixel (i,j), calculates:
MSE = Σ[(R₂-R₁)² + (G₂-G₁)² + (B₂-B₁)²] / (3 × width × height) - Threshold Evaluation: Frames exceeding the MSE threshold are copied to output directory
- Parallel Execution: Uses thread pool sized to available CPU cores for concurrent processing
Initial Frame Handling: The first frame is compared against a white baseline image, assuming typical video sequences begin with dark frames.
- Complexity: O(n×w×h) where n=frames, w=width, h=height
- Threading: Work-stealing queue with configurable worker threads
- Memory Usage: Processes frame pairs on-demand, minimal memory footprint
- I/O Pattern: Sequential read with selective write based on threshold
- Scalability: Automatic CPU core detection with manual override
- Error Recovery: Individual frame failures don't halt processing
git clone <repository-url>
cd screenshotter
cargo build --releasescreenshotter --input <frame_directory> --output <output_directory> [--threshold <value>]--input, -i: Source directory containing sequential PNG frames--output, -o: Destination directory for unique frames--threshold, -t: MSE threshold value (default: 499.0)--workers, -w: Number of worker threads (default: CPU cores)--progress, -p: Show progress information during processing
Extract frames using FFmpeg with consistent naming:
ffmpeg -i video.mp4 -vf "fps=1" frames/frame_%04d.png# With custom worker count and progress reporting
screenshotter -i frames -o unique_frames -t 600 -w 8 -p
# High sensitivity processing
screenshotter -i frames -o unique_frames -t 200 -pMSE values correlate with visual change magnitude:
- 100-300: High sensitivity, captures subtle lighting changes
- 400-600: Balanced sensitivity for general content
- 700+: Low sensitivity, major scene transitions only
- Robust Error Handling: Comprehensive error recovery and meaningful error messages
- Progress Reporting: Real-time progress feedback during processing
- Configurable Threading: Adjustable worker thread count for optimal performance
- Input Validation: Automatic validation of image dimensions and file integrity
- Resource Management: Efficient memory usage and file handling
- Graceful degradation: Processing continues even if individual frames fail
- Detailed error reporting: Specific error messages for troubleshooting
- Input validation: Early detection of common issues before processing
- Progress tracking: Resume capability through progress reporting
Scanning Phase
Scanning for PNG files in 'frames'...
Found 1500 PNG files
Processing Phase
Processing with 8 worker threads
Using MSE threshold: 499
Processed 150/1499 pairs (10.0%)
Processed 300/1499 pairs (20.0%)
Completion Summary
Processing complete! Copied 87 unique frames to 'unique_frames'
With Progress Flag (-p)
Copied: frame_0045.png (MSE: 623.45)
Copied: frame_0089.png (MSE: 892.12)
- Perceptual Accuracy: MSE may not correlate with human visual perception
- Transition Artifacts: Gradual effects (fades, dissolves) can produce false positives
- Format Constraints: PNG input only, no format conversion
- Temporal Assumptions: Requires chronologically ordered input files
Fernando Meyer fm@pobox.com
0.1.0