🐥
sora-cpp-sdk-samplesでカメラの代わりにpipe経由でビデオデータを入力してWebRTCで送信してみた
前回の続き。
ビデオの入力をカメラからではなく、別のプロセスで生成したI420形式のビデオデータをpipe経由で取り込んでWebRTCで送信するようにしてみました。
PipeVideoCaptureのclassはsora-cpp-sdkのV4L2VideoCaptureの構造を参考にしました。特にスレッドを使うところはそっくり真似ています。
ポイントはI420のビデオデータをlibwebrtcに渡す部分です。
void PipeVideoCapturer::OnCaptured(uint8_t* data) {
auto w = _width;
auto h = _height;
auto i420_buffer = webrtc::I420Buffer::Copy(w, h,
data, w,
data + (w * h), w/2,
data + (w * h) + (w/2 * h/2), w/2);
webrtc::VideoFrame video_frame = webrtc::VideoFrame::Builder()
.set_video_frame_buffer(i420_buffer)
.set_timestamp_rtp(0)
.set_timestamp_ms(rtc::TimeMillis())
.set_timestamp_us(rtc::TimeMicros())
.set_rotation(webrtc::kVideoRotation_0)
.build();
OnCapturedFrame(video_frame);
}
自分で描画した映像を送信するときの参考になると思います。
I420のデータはかなりサイズが大きいので、解像度フレームレートを高くする場合にはプロセス間でのデータの受け渡し方法に工夫が必要だと思います。例えば、共有メモリ上に数フレーム分をリングバッファとして持つとか。
使い方
--video-fifo
オプションで入力するfifo(名前付きパイプ)を指定します。-
を指定すると標準入力になります。そのパイプに別のプロセスからI420のビデオデータを流し込みます。
ffmpegでテストパターンを作ってそれを送信する方法。
#!/bin/sh -eux
SIGNALING_URL=wss://207-148-110-182.canary.sora.sora-labo.shiguredo.app/signaling
CHANNEL_ID=tetsu-koba@sora-devtools
SIGNALING_KEY=xxxyyy
WIDTH=1280
HEIGHT=720
FRAMERATE=10
AUDIO_OPT='--no-audio-device'
ffmpeg -re -f lavfi -i testsrc=s=${WIDTH}x${HEIGHT}:r=$FRAMERATE -pix_fmt yuv420p -f rawvideo pipe: | \
./pipe_video_src --log-level 1 $AUDIO_OPT --video-fifo - --resolution ${WIDTH}x${HEIGHT} --framerate $FRAMERATE \
--signaling-url $SIGNALING_URL --channel-id $CHANNEL_ID \
--multistream true --video-codec-type H264 \
--metadata "{\"signaling_key\": \"$SIGNALING_KEY\"}" > log 2>&1
Discussion