I have an IP security camera ( which able to broadcast rtsp content over network.

I'm able to save that (RAW) content without changes using next ffmpeg command from my computer:

ffmpeg -i "rtsp://" -acodec copy -vcodec copy test-raw.mp4

I'm also able to resize it on the fly:

ffmpeg -i "rtsp://" -vf  "scale=640:-1" test640.mp4

But how to save only that video which contains motion detection parts only?

I tried to get it solved using ffmpeg's scene change filters, but no luck.

My goal - to have common video monitoring solution, which detects when someone is moving near the camera and save it into the video file. I understand that it might be not possible to do it on the fly from stream, so it is OK for me to save big file firstly, then process it with another ffmpeg command and generate new video file which contains only motion detected parts. If you can give me advice what exactly should I research more, I will be really thankful.

My camera stream is transmitted without sound. So, I can generate set of images from original video, then pick proper images and then save new video from images.

  • Do you want to implement this system or find a ready to use product?
    – Woeitg
    Nov 30 '15 at 10:54
  • 1
    @WOEITG I just need any free working solution for Ubuntu 15.04+
    – rfedorov
    Dec 2 '15 at 16:46
  • For Windows, there's a piece of software called ispy, which you can set to record on motion detection. Since you're requesting a Linux solution, zoneminder.com should be a similar product. Unfortunately I don't have a direct answer to your question, but +1 because I'd like an answer too Jan 4 '16 at 14:15
  • @MyNameWouldGoHere Does zoneminder run on OS X? I found some messages from a few years back which mentioned it working on OS X Server, but the actual product page seems to suggest only Linux (but maybe if manually compiled from sourcE???)
    – Michael
    Mar 14 '20 at 23:42
  • Also see here: stackoverflow.com/questions/29881070/… Sep 22 '20 at 1:14

What I'd do, is do exactly like you said, and save a big file of the stream, then use the select FFMPEG filter with the scene expression, that compares the similarity of consecutive frames: select=gt(scene\,0.003) for instance. The higher the number, the more change between frames is ignored, in quick testing you might need to go as low as 0.00001-0.00005 depending on the kind of footage you're dealing with.

Combine that with the setpts filter, that modifies the "start time" of video frames, and you'd end up with something like (for a 25fps video):

ffmpeg -i input.mp4 -vf "select=gt(scene\,0.003),setpts=N/(25*TB)" output.mp4

Mind you, you won't be able to use -vcodec copy when you use video filters.

  • 2
    how can you blur the filter so it doesn't start detecting motion where there is none due to noise when light conditions deteriorate?
    – Michael
    Mar 25 '20 at 4:15
  • @Michael Maybe it's possible to blur a bit (to denoise), then find edges (to get rid of the changes caused by e.g. flickering light), then select the frames and somehow store their original time. Then this could be processed with some event stream (e.g. using ReactJS) to get more continuous parts, and then feed it to FFMpeg to cut those parts. Sep 22 '20 at 1:13

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.