Skip to content

add ci2-video-file / i.e. MP4 backend - #31

Open
Mharrap wants to merge 2 commits into
strawlab:mainfrom
Mharrap:main
Open

add ci2-video-file / i.e. MP4 backend#31
Mharrap wants to merge 2 commits into
strawlab:mainfrom
Mharrap:main

Conversation

@Mharrap

@Mharrap Mharrap commented Jul 29, 2026

Copy link
Copy Markdown

Add MP4 backend, this backend allows one to play a prerecorded MP4 (although it should be able to do other formats I have not tested) as a camera backend. It works best if this is MP4 recroded by strand camera itself. The video can loop or hold the first frame, until it receives a command, it then uses an enviromental variable to indicate it has stopped. Frame rate can also be controlled.

Mharrap and others added 2 commits July 29, 2026 13:53
Adds a new, purely additive ci2 camera backend (camera/ci2-video-file,
--camera-backend video-file) that decodes a video file (MP4, FMF, MKV, ...)
directly via the existing media-utils/frame-source crate and plays it back
at its own native frame rate, looping by default. This lets strand-cam's
live acquisition/processing pipeline run against pre-recorded footage with
no camera hardware, v4l2loopback, or nokhwa involved at all.

Modeled on ci2-sim's shape: a new CameraBackend::VideoFile enum variant and
dispatch arm in strand-cam/src/cli_app.rs, one new workspace member/path
dependency, and a strand-cam/Cargo.toml dependency line. No existing backend
(ci2-pylon, ci2-vimba, ci2-webcam, ci2-sim) is touched.

Also adds a new CamArg::ExecuteCommand(String) variant (strand-cam-remote-control)
and its dispatcher in cam_arg_task.rs, letting the BUI trigger a named,
backend-defined command via ci2::Camera::command_execute -- used by
ci2-video-file's "StartPlayback" command to end a hold on the first frame
(STRAND_CAM_VIDEO_FILE_AUTOSTART=false), and by STRAND_CAM_VIDEO_FILE_LOOP/
STRAND_CAM_VIDEO_FILE_DONE_MARKER/STRAND_CAM_VIDEO_FILE_LIMIT_FRAMERATE for
play-once, end-of-playback signaling, and pacing overrides respectively --
all documented in ci2-video-file/src/lib.rs's own module docs.

Two real bugs were found and fixed while developing this, not just on a
happy path:
- frame_source::FrameDataSource::average_framerate() only reports a value
  for video carrying strand-cam's own SEI timing metadata, so it's None for
  an ordinary MP4 -- a naive 30fps fallback would silently play such a file
  at the wrong speed. Fixed with a priority order: prefer average_framerate()
  when present, else estimate fps from two consecutive frames' own
  presentation timestamps, else a fixed default.
- The Instant-based "absolute schedule" pacer (the same idiom ci2-sim uses)
  blasts through a backlog instead of resyncing if the caller is ever
  delayed by a downstream stall. Fixed with a resync guard: when the pacer
  falls more than one frame period behind, it resyncs its schedule origin to
  "now" instead of dumping the whole backlog at once.

Verified: cargo build/clippy/fmt clean; cargo build --release -p strand-cam
--no-default-features --features flydra_feat_detect,serve_files succeeds;
--list-cameras correctly enumerates a video-file camera (name derived from
the file's stem).

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Strengthens the existing module-level doc comments rather than adding a
separate README (ci2-pylon, the default backend, has neither a README nor
much inline prose, so a README here would be out of parity with it):

- New "Starting and stopping playback" section naming all three controls
  that govern when frames move (acquisition_start/acquisition_stop,
  VIDEO_FILE_AUTOSTART_ENV, VIDEO_FILE_LOOP_ENV) with cross-references to
  their existing detailed sections.
- The "Pacing" section now explicitly names the GenICam accessor methods
  (acquisition_frame_rate_enable/set_acquisition_frame_rate_enable,
  acquisition_frame_rate/set_acquisition_frame_rate) and includes the
  real-camera-hardware-buffer reasoning for the resync guard, previously
  only in an inline code comment near next_frame.
- acquisition_start/acquisition_stop themselves gain doc comments (they had
  none at all before), since these are the actual generic start/stop API a
  dev would reach for first.

No behavior change. Verified: cargo fmt/clippy -D warnings/license-check
clean, cargo doc shows no new warnings (still only the 3 pre-existing
private-intra-doc-link ones, unrelated to this change).

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant