Camera & Input
Capture vitals in Python from a webcam, a video file, or your own frames, all returning the same VitalSigns.
The Python SDK is a full capture-capable client: it runs MediaPipe face detection and ROI extraction on-device, then sends only the cropped tensor to the server for inference. Raw video never leaves the device. You can feed that pipeline from three interchangeable sources — a webcam, a video file, or your own frames — and every one returns the same VitalSigns result.
Input sources
Pick the source that fits your environment. All three need the camera extra (pip install "circadify[camera]") for on-device MediaPipe; measure_vitals (and check_camera_access) open a camera device, while measure_from_video and measure_from_frames never do.
Open a live webcam, run the readiness gate, then capture. camera_index=0 is the default device.
from circadify import CircadifyClient
with CircadifyClient(api_key="ck_test_your_key_here") as client:
result = client.measure_vitals(camera_index=0)
print(result.heart_rate, result.confidence)pythonRead the API key from the environment — never hardcode it. Use CircadifyClient(api_key=os.environ["CIRCADIFY_API_KEY"]) with a ck_test_ (sandbox, zero quota) or ck_live_ key.
Camera permissions & availability
measure_vitals and check_camera_access open a camera device, so OS-level permissions apply to the webcam path (the macOS TCC prompt fires on the first of either call). measure_from_video and measure_from_frames never open a camera:
| Platform | What to expect |
|---|---|
| macOS | The system TCC dialog prompts for camera access on the first capture. Grant it under System Settings -> Privacy & Security -> Camera. |
| Linux | The device must exist at /dev/video0 (or another index) and be readable via v4l. Ensure your user is in the video group. |
| Windows | Camera access must be enabled under Settings -> Privacy & security -> Camera for desktop apps. |
Probe a device before a webcam scan with check_camera_access(camera_index=0), which returns a bool:
import os
from circadify import CircadifyClient
client = CircadifyClient(api_key=os.environ["CIRCADIFY_API_KEY"])
if client.check_camera_access(camera_index=0):
result = client.measure_vitals(camera_index=0)
else:
print("No usable camera — fall back to a video file or frames.")pythonmeasure_from_video and measure_from_frames need no camera permission and no camera device — the key advantage of the Python SDK. Use them for headless servers, CI, batch jobs, or any host without a webcam.
If the camera extra is missing, the capture methods raise MissingDependencyError (code MISSING_DEPENDENCY). A camera that exists but cannot be opened raises CameraError (code CAMERA_ERROR).
Frame quality
Whatever the source, the model needs enough good frames. Capture targets ~30 fps and requires MIN_CAPTURE_FRAMES=150 usable frames before it produces a result. Aim for:
- Even lighting — avoid backlight and harsh shadows on the face.
- Steady framing — keep the face centered and in shot for the whole capture.
- Face visible — no occlusions, large turns, or tilts.
- Minimal motion — hold still; motion blur drops frames.
The on_quality callback receives a QualityState with face_detected, brightness, motion, yaw_deg, pitch_deg, is_good, and reasons — a tuple drawn from no_face, face_out_of_frame, too_dark, too_bright, too_much_motion, face_turned, face_tilted. Use those reasons to coach the subject in real time:
def on_quality(q):
if not q.is_good:
print("Adjust:", ", ".join(q.reasons))
client = CircadifyClient(api_key=os.environ["CIRCADIFY_API_KEY"], on_quality=on_quality)pythonIf too few usable frames are collected (too much motion or no face detected), capture raises CaptureFailedError (code CAPTURE_FAILED, retryable). The SDK never fabricates vitals — retry with better lighting and framing, or supply more quality frames to measure_from_frames.
Next Steps
- Face-Glow Overlay — Draw the thermal glow on your frames with
render_face_glow. - Methods — Full signatures for every capture path.
- Configuration — Tune callbacks, timeouts, and capture duration.
- Error Handling — Catch
CaptureFailedError,CameraError, and more.