Raspberry PiとGStreamerを使ってWebカメラ映像を配信する方法

markdown-img-paste-2021090623242667.webp
目次

はじめに

今回は、Raspberry pi上でWEBカメラの映像を取得して、Windows PCに配信するシステムを構築する方法について説明します。このシステムは、ベビーモニターやペットの監視など、さまざまな用途に活用できます。GStreamerを使って、コマンドラインから簡単に操作できるので、手軽に始められます。

Gstreamerについて

GStreamerは、オープンソースのマルチメディアフレームワークです。ビデオ編集、ストリーミング、メディアプレーヤーなど、さまざまなマルチメディアアプリケーションのベースとなる機能を提供しています。GStreamerは、LinuxやUnixなどのオペレーティングシステムで使用されており、Python、C、C++などのプログラミング言語で書かれています。

プラグインベースのアーキテクチャを採用しており、多くのプラグインが利用可能です。これらのプラグインは、GStreamerのフレームワーク内で処理を行うモジュールであり、ビデオのキャプチャ、エンコード、デコード、オーディオの再生などの機能を提供します。また、GStreamerは、パイプラインと呼ばれるコンポーネントを使って、各種処理を連結できます。パイプラインは、複数のプラグインを組み合わせて、マルチメディア処理を行う方法を提供しています。

多くのプロジェクトで使用されており、多数のアプリケーションが開発されています。例えば、GNOMEデスクトップ環境、Firefoxブラウザ、Skype、VLCメディアプレーヤーなどが挙げられます。

マルチメディアの処理を簡単かつ効率的に行うことができるため、様々なプラットフォームで使用されています。GStreamerを利用することで、高度なマルチメディアアプリケーションの開発が可能になります。

配信側(raspberry pi)の準備

初期設定

Raspberry piで、WEBカメラを接続して使えるようにします。 まずは、raspi-configを立ち上げます。

sudo raspi-config

3.Interface Optionsを開いて、P1 CameraそしてEnableにします。

変更したらRaspberry piを再起動します。

sudo reboot

gstreamerのインストール

続いて今回の要である、gstreamerをインストールしていきます。 コマンドラインからポチポチやってインストールできるので特に問題ないはずです。

アップデート前に、インストールパッケージの更新を行います。

sudo apt-get update
sudo apt-get upgrade

apt-getでgstreamer関連ツール群をインストールします。

sudo apt-get install gstreamer1.0-tools gstreamer1.0-plugins-good gstreamer1.0-plugins-bad gstreamer1.0-plugins-ugly

成功するとこんな感じに表示されるはずです。

Reading package lists... Done
Building dependency tree
Reading state information... Done
gstreamer1.0-plugins-bad is already the newest version (1.14.4-1+rvt+deb10u2).
gstreamer1.0-plugins-good is already the newest version (1.14.4-1+rpt1+deb10u1).
The following NEW packages will be installed:
  gstreamer1.0-tools
0 upgraded, 1 newly installed, 0 to remove and 97 not upgraded.
Need to get 1,109 kB of archives.
After this operation, 1,196 kB of additional disk space will be used.
Do you want to continue? [Y/n] y
Get:1 http://ftp.jaist.ac.jp/pub/Linux/raspbian-archive/raspbian buster/main armhf gstreamer1.0-tools armhf 1.14.4-1 [1,109 kB]
Fetched 1,109 kB in 1s (921 kB/s)
Selecting previously unselected package gstreamer1.0-tools.
(Reading database ... 98616 files and directories currently installed.)
Preparing to unpack .../gstreamer1.0-tools_1.14.4-1_armhf.deb ...
Unpacking gstreamer1.0-tools (1.14.4-1) ...
Setting up gstreamer1.0-tools (1.14.4-1) ...
Processing triggers for man-db (2.8.5-2) ...

準備はこれでOKです。

WEBカメラの接続確認

続いて、WEBカメラをRaspberry piのUSBポートに繋いで、以下のコマンドを実行します。 繋がっているデバイスを確認でき、WEBCAMERAっぽいデバイスがあることを確認します。

v4l2-ctl --list-devices
bcm2835-codec-decode (platform:bcm2835-codec):
        /dev/video10
        /dev/video11
        /dev/video12

bcm2835-isp (platform:bcm2835-isp):
        /dev/video13
        /dev/video14
        /dev/video15
        /dev/video16

GENERAL WEBCAM: GENERAL WEBCAM (usb-3f980000.usb-1.5):
        /dev/video0
        /dev/video1

この状態では、gstreamerから上手く認識しないことがあるので、 usermodを使って、セカンダリグループにvideoを作ってそこに$USERを追加します。

sudo usermod -a -G video $USER

有効になっているカメラデバイスを確認します。 arecordはAudioデバイスの録音とかに使うものらしいです。 デバイス確認以外でそういや使ったこと無いな…

arecord -l
**** List of CAPTURE Hardware Devices ****
card 1: WEBCAM [GENERAL WEBCAM], device 0: USB Audio [USB Audio]
  Subdevices: 1/1
  Subdevice #0: subdevice #0

上手く動いていそうですね。

Gstreamerの動作確認(ERROR対応)

gstreamerの起動はこのように行います。

gst-launch-1.0 v4l2src ! videoconvert ! ximagesink
Setting pipeline to PAUSED ...
ERROR: Pipeline doesn't want to pause.
ERROR: from element /GstPipeline:pipeline0/GstXImageSink:ximagesink0: Could not initialise X output
Additional debug info:
ximagesink.c(860): gst_x_image_sink_xcontext_get (): /GstPipeline:pipeline0/GstXImageSink:ximagesink0:
Could not open display
Setting pipeline to NULL ...
Freeing pipeline ...

このERRORは、コマンドラインからSSH接続なのでGUIが無いことで怒られているようです。

Raspberry piにGUIで接続できるようにする。

WEBカメラが接続されてGstreamerの動作確認を行うために手順を続けます。 WEBカメラ映像配信にはGUIが不必要なので省略してもらっても良いです。

xrdpをインストールします。 インストールしたらサービスを再起動して動かします。

sudo apt-get install xrdp
sudo service xrdp restart
raspi-config

VNCを有効にします。

Windowsからの接続

標準では言っている、リモートデスクトップアプリからつなげることができます。 コンピュータ名のところにRaspberry piのIPアドレスを入力しましょう。

接続したらRaspberry piのユーザ名とPASSを求められるので入力すると、デスクトップ画面に繋がります。

Raspberry piのTerminalを立ち上げて先程動かせなかったコマンドを実行しましょう。

gst-launch-1.0 v4l2src ! videoconvert ! ximagesink

WEBカメラの映像が移りましたね。良いですね。

使用中のカメラの性能を確認する

さて自分が繋いでいるカメラの解像度がどこまで対応してるのか確認します。 配信に使えるサイズを超えてないことが条件です。

v4l2-ctl --list-formats-ext --device=/dev/video0

出力結果はこんな感じになります。 画像は、1920x1080動画は、640x480と読み取れます。1000円カメラなのでこんなものかという感じです。

ioctl: VIDIOC_ENUM_FMT
    Type: Video Capture

    [0]: 'MJPG' (Motion-JPEG, compressed)
        Size: Discrete 1920x1080
            Interval: Discrete 0.033s (30.000 fps)
            Interval: Discrete 0.033s (30.000 fps)
        Size: Discrete 1280x720
            Interval: Discrete 0.033s (30.000 fps)
        Size: Discrete 800x480
            Interval: Discrete 0.033s (30.000 fps)
        Size: Discrete 640x480
            Interval: Discrete 0.033s (30.000 fps)
        Size: Discrete 640x360
            Interval: Discrete 0.033s (30.000 fps)
        Size: Discrete 320x240
            Interval: Discrete 0.033s (30.000 fps)
        Size: Discrete 176x144
            Interval: Discrete 0.033s (30.000 fps)
        Size: Discrete 800x600
            Interval: Discrete 0.033s (30.000 fps)
        Size: Discrete 1920x1080
            Interval: Discrete 0.033s (30.000 fps)
            Interval: Discrete 0.033s (30.000 fps)
    [1]: 'YUYV' (YUYV 4:2:2)
        Size: Discrete 640x480
            Interval: Discrete 0.033s (30.000 fps)
            Interval: Discrete 0.033s (30.000 fps)
        Size: Discrete 640x360
            Interval: Discrete 0.033s (30.000 fps)
        Size: Discrete 320x240
            Interval: Discrete 0.033s (30.000 fps)
        Size: Discrete 176x144
            Interval: Discrete 0.033s (30.000 fps)
        Size: Discrete 640x480
            Interval: Discrete 0.033s (30.000 fps)
            Interval: Discrete 0.033s (30.000 fps)

Raspberry piのWeb Cameraから配信を行う

Raspberry pi側

Raspberry piにSSHで接続して、以下のコマンドを実行します。 tcpserversinkを使ってTCP/IPで動画データを配信しています。

gst-launch-1.0 -v v4l2src ! video/x-raw,width=320,height=240,framerate=30/1 ! gdppay ! tcpserversink host=192.168.0.32

待受状態になっているかを確認するときはこのように打てばよいです。 画像はGUIでTerminal2つ立ち上げて確認シテますが、SSHで繋ぐ場合は2つのTerminalで繋ぐか、コマンドに&でもつけて裏で動かせば良いんじゃないかと思います。

netstat -an |grep 4953

これで準備は完了です。

Windows側

PowerShellから実行しました。 Gstreamerは、Windows向けにもインストーラが配布されているのでインストールしておいてください。 インストール後はBinフォルダを環境変数のPATHに追加しておきます。

gst-launch-1.0 -v tcpclientsrc host=192.168.0.32 ! gdpdepay ! videoconvert ! autovideosink

接続確認

WEBカメラの映像をつなげることが出来ました。

こんな感じです。動作イメージをつかみやすいようにYoutubeにあげておきました。

同じネットワークに繋いでいますが遅延が結構あります。 体感で20秒ぐらいの遅延があるためリアルタイム監視とかそういった用途で使うのは厳しそうです。 もしかすると、配信するサーバをRaspberry piの最新にするとか、デスクトップPCにするなどの工夫が必要かもしれないです。 あとは、配信する映像のサイズを小さくするとか、動画ではなく画像を配信するとか何か別の工夫が必要だと思います。

まとめ

今回は、GStreamerを使って、Raspberry pi上のWEBカメラから映像を取得し、Windows PCに配信する方法を紹介しました。GStreamerの簡単なコマンドで、手軽に配信システムを構築できます。ただし、同じネットワーク内でも遅延があるため、リアルタイム監視などには向いていません。配信する映像のサイズを小さくするなどの工夫が必要です。GStreamerの他の機能も活用して、さまざまなマルチメディアアプリケーションの開発に挑戦してみてはいかがでしょうか。

Related Post

> Raspberry PiとGStreamerを使ってWebカメラ映像を配信する方法
Raspberry Piのセットアップ記録と使い方のまとめ

おすすめの商品

>