Metadata-Version: 2.4
Name: triggercam
Version: 0.2.0
Summary: Thread-safe webcam capture with on-demand start/stop recording, built on OpenCV
Author: tuo170
License-Expression: MIT
Project-URL: Homepage, https://github.com/tuo170/triggercam
Project-URL: Issues, https://github.com/tuo170/triggercam/issues
Keywords: opencv,webcam,camera,recording,threading
Classifier: Programming Language :: Python :: 3
Classifier: Operating System :: OS Independent
Classifier: Topic :: Multimedia :: Video :: Capture
Classifier: Intended Audience :: Developers
Requires-Python: >=3.9
Description-Content-Type: text/markdown
License-File: LICENSE
Requires-Dist: opencv-python>=4.5
Provides-Extra: dev
Requires-Dist: pytest>=7; extra == "dev"
Dynamic: license-file

# triggercam

[![Tests](https://github.com/tuo170/triggercam/actions/workflows/test.yml/badge.svg)](https://github.com/tuo170/triggercam/actions/workflows/test.yml)

> Thread-safe webcam capture for Python with on-demand start/stop recording, built on OpenCV.

OpenCVベースの、スレッドセーフなWebカメラキャプチャライブラリです。プレビューを表示し続けたまま、録画の開始・停止を好きなタイミングでトリガーできます。

```python
import time
from triggercam import Camera

with Camera() as cam:
    time.sleep(10)
    cam.start_recording("clip")   # clip.mp4 に書き込み開始
    time.sleep(10)
    cam.stop_recording()          # clip_20260101-120000.mp4 にリネーム
```

## なぜtriggercamなのか

よくある録画系のサンプルは「プログラム起動と同時に録画開始、`q`キーで終了」という一発勝負の構成がほとんどです。

カメラのプレビューは動かし続けたまま、録画のON/OFFだけを自分のコードから好きなタイミング（センサーのトリガー、スケジュール、ボタン操作、検知イベントなど）で切り替えたい、というケース向けの例はあまり見かけませんでした。

triggercam（本プログラム）では、それができます。

現状、単純な録画ON/OFFのみの機能となっています。
複数カメラ対応・動体検知・NVR的なUIが欲しい場合は、他の本格的なアプリケーションについても検討してください。

## インストール

```bash
pip install triggercam
```

[PyPI](https://pypi.org/project/triggercam/)で公開しています。

## API

- `Camera(index=0, width=1280, height=720, fps=30, show_preview=True, capture_fourcc="MJPG", output_fourcc="mp4v")` — カメラを開き、即座にバックグラウンドのキャプチャスレッドを開始します。`capture_fourcc`はカメラから読み込む際のフォーマット、`output_fourcc`は録画ファイルを書き出す際のコーデックです（どちらも4文字で指定、例: `capture_fourcc="YUYV"`, `output_fourcc="H264"`）。
- `cam.start_recording(filename)` — `<filename>.mp4`への書き込みを開始します。Writerが開けなかった場合（非対応コーデックなど）は`RuntimeError`を送出します。すでに録画中の場合は何もしません。
- `cam.stop_recording()` — 録画を停止し、ファイル名を`<filename>_<タイムスタンプ>.mp4`にリネームします。最終的なパスを返します（録画していなかった場合は`None`）。
- `cam.running` — キャプチャスレッドが停止すると`False`になります（カメラが切断された場合、プレビューウィンドウで`q`が押された場合など）。
- `cam.close()` — スレッドを停止し、カメラ・Writerのリソースを解放します。プログラムが中断されても録画ファイルが壊れた状態で残らないよう、必ず呼び出してください（`with Camera() as cam:`を使えば自動的に呼ばれます）。
- `triggercam.presets` — 特定機種向けの設定をまとめたモジュール。現状`LOGITECH_C270`(動作検証済みの機種)のみですが、他機種を使う場合は同じ形の`dict`を自分で定義して`Camera(**your_preset)`のように渡せます。`Camera`自体は特定機種を一切知りません。

```python
from triggercam import Camera
from triggercam.presets import LOGITECH_C270

with Camera(**LOGITECH_C270) as cam:
    ...
```

一通りの流れと、Ctrl+Cでの安全な終了方法は[`examples/basic_recording.py`](examples/basic_recording.py)を参照してください。

## 動作検証

### 検証環境（2026-08-21）

| 項目 | 内容 |
|---|---|
| OS | Windows 11 Pro |
| Python | 3.10.6（プロジェクト専用のvenv） |
| インストール方法 | `pip install -e .` |
| 依存パッケージ | opencv-python 5.0.0.93 |
| カメラ | Logi C270 HD WebCam（USB UVCカメラ） |

### 確認できたこと

- カメラが正しく認識され、プレビューウィンドウに実際の映像が表示されることを確認（起動してからプレビューウィンドウが表示されるまで少し時間がかかる）。
- `start_recording()` → `stop_recording()` の一連の流れが正常に動作し、`clip.mp4` が `clip_<タイムスタンプ>.mp4` に正しくリネームされることを確認。
- 録画サイクル（10秒待機→録画→待機→停止）が問題なく動作することを確認。
- 録画中に`Ctrl+C`で強制中断した際、そのファイルが正しく`stop_recording()`まで処理された状態で残ることを確認（未リネームの壊れたファイルが残らない）。
- 生成された動画ファイルはメディアプレイヤーで正常に再生可能なことを確認。

### 未検証

- Linux / macOSでの動作（カメラインデックスでのキャプチャのため動作するはずだが、実機未確認）

## ライセンス

MIT — [LICENSE](LICENSE)を参照してください。

## 背景

このライブラリは、[Qiitaに投稿した元のプログラム](https://qiita.com/tuo170/items/ca1933a88f3255792214)
（ https://qiita.com/tuo170/items/ca1933a88f3255792214 ）
を土台に、バグ修正・API設計・パッケージ化を行って作られています。

実装のコーディングやレビュー、設計の壁打ち相手としてClaude Codeを使用しました。
