使用ffmpeg和gstreamer的Opencv RTSP流媒体
我使用的是一台ip摄像机,它有主流(分辨率为1920x1080)和子流(分辨率为720x576)。我的目标是通过使用子流来检测运动,如果运动发生,我会从主流中拍摄一个snopshot,并对该图像进行一些处理。这是我的密码使用ffmpeg和gstreamer的Opencv RTSP流媒体,opencv,ffmpeg,gstreamer,rtsp,Opencv,Ffmpeg,Gstreamer,Rtsp,我使用的是一台ip摄像机,它有主流(分辨率为1920x1080)和子流(分辨率为720x576)。我的目标是通过使用子流来检测运动,如果运动发生,我会从主流中拍摄一个snopshot,并对该图像进行一些处理。这是我的密码 VideoCapture cap; //video capture device captures the pal stream VideoCapture cap2; //video capture device captures the main str
VideoCapture cap; //video capture device captures the pal stream
VideoCapture cap2; //video capture device captures the main stream
// cap.set(CV_CAP_PROP_BUFFERSIZE,1);
// cap2.set(CV_CAP_PROP_BUFFERSIZE,1);
//cap.set(CV_CAP_GSTREAMER_QUEUE_LENGTH,1);
//cap2.set(CV_CAP_GSTREAMER_QUEUE_LENGTH,1);
cap.open("rtsp://usr:pass@x.x.x.x:554/Streaming/Channels/2?transportmode=unicast&profile=Profile_2",CAP_FFMPEG); //open substream
cap2.open("rtsp:///usr:pass@x.x.x.x:554/Streaming/Channels/1?transportmode=unicast&profile=Profile_1",CAP_FFMPEG); //open mainstream
bool frame_read = false;
int motion val;
while (true) {
frame_read = cap.read(rgb_im); //read the frame from substream
//cap2.grab();
if (!frame_read) {
break;
}
cvtColor(rgb_im, gray_im, CV_BGR2GRAY);
motion_val = detect_motion(gray_im); //find the motion value
if (motion_val > MOTION_OCCURRED) //check if motion occurs
{
cap2>>frame_big; //get one frame from the main stream
process(frame_big); //do processing
}
imshow("1", rgb_im);
if (waitKey(1) >= 0)
break;
}`
当我打开带有CAP_FFMPEG标志的流时,延迟非常低(低于1秒)。如上所示,我定期阅读子流,如果发生运动,我阅读主流。但是我从主流中读到的帧与子流不同步。很可能我抓取了在缓冲区中等待的帧。所以我错过了运动的画面,我得到了一个更老的画面。我如何处理这个问题?不知何故,我必须使缓冲区大小为1帧,但我找不到任何方法
我试过了
cap.set(CV\u cap\u PROP\u BUFFERSIZE,1)代码>但由于它需要DC1394支持,因此无法解决我的问题
其次,我在读取子流后尝试了cap2.grab()
,但它增加了延迟(使延迟大约为3秒)
第三,我尝试用cv_cap_gstreamer flagcap.open(“rtsp://usr:pass@x、 x.x.x:554/流媒体/频道/2传输模式=单播和配置文件=配置文件2”,CV\U CAP\U GSTREAMER)代码>。它解决了我的缓冲问题。换句话说,当我从子流中检测到运动时,我能够从主流中捕捉到相同的瞬间。但对于gstreamer,我有大约3秒的巨大延迟,这对于我的情况来说是不可取的。(对于gstreamer,我尝试读取多个具有不同分辨率的rtsp流,延迟保持不变)当我将gstreamer与opencv一起使用时,如何解决延迟问题?始终从两个流读取,但仅当在第一流中检测到运动时才处理第二流。顺便说一句,我认为,流在任何情况下都会不同步。谢谢你的回答。但我打开子流的原因是为了让阅读过程更快。主流的分辨率太高,不需要进行运动检测。如果我必须定期阅读主流,我只需将主流用于运动检测和处理。@DmitriSosnikReading应该很便宜,处理成本很高。