{"id":2956,"date":"2017-07-17T00:00:48","date_gmt":"2017-07-17T07:00:48","guid":{"rendered":"http:\/\/192.168.3.4\/?p=2956"},"modified":"2018-01-09T06:51:50","modified_gmt":"2018-01-09T14:51:50","slug":"ffmpeg-video-processing","status":"publish","type":"post","link":"https:\/\/www.cloudacm.com\/?p=2956","title":{"rendered":"FFMpeg Night Enhancement Processing"},"content":{"rendered":"<p>In this post I&#8217;ll be covering how to process footage that was shot at night. By default, it is difficult to see what was captured with the camera. I do know the length of the video as well as other aspects of it. The clip I&#8217;ll be using is 5 minutes long and has a resolution of 1280&#215;720 at 30fps using the H.264 \/ AVC codec. The audio is a single channel (mono) 16-bit PCM at 32000Hz. I like that the audio is a lossless raw format, this will be useful for later posts when doing audio signal processing.<\/p>\n<p>Before I start to apply filters, I&#8217;ll want to select a portion of the footage to use as a filter test.\u00a0 I&#8217;ll be selecting a 5 second portion of the video and splitting it out to another file.\u00a0 I&#8217;ll test my filters on that new file instead of wasting time processing all of video.\u00a0 To split the video, I&#8217;ll choose a point when I want to start my split and set it for a duration of 5 seconds.\u00a0 Here is the command I&#8217;ll use.<\/p>\n<pre>ffmpeg -i MINI0492.MOV -ss 00:03:10 -t 00:00:05 -acodec copy -vcodec copy -async 1 -y MINI0492_Split1.MOV<\/pre>\n<p>Now I have a nice short clip that has most of the visual attributes I can test filters with.\u00a0 Also, the command retained the format of the source video, so I shouldn&#8217;t see any artifacts created by FFMpeg.<\/p>\n<p>The first filter I would like to use is one that will brighten the video.\u00a0 I&#8217;ll use the hue filter to do this.\u00a0 Here is the command I&#8217;ll use to test the filter hue=b=x, x being a range from -10 to 10.<\/p>\n<pre>ffmpeg -i MINI0492_Split1.MOV -vf hue=b=2.11 MINI0492_Brightness.MOV<\/pre>\n<p>This command increases the output video brightness by a factor of 21.1 percent.\u00a0 Based on the range, we have a lot of variance.\u00a0 There is one problem with the results, the dark areas lack depth.\u00a0 I&#8217;m going to use the &#8220;eq&#8221; filter with my 5 second clip to correct the gamma levels, here is the command.<\/p>\n<pre>ffmpeg -i MINI0492_Split1.MOV -vf \"eq=gamma=1.8\" MINI0492_Gamma.MOV<\/pre>\n<p>The results of this were better than the brightness filter.\u00a0 The clip has better dynamic range.\u00a0 Now I can see how shaky the video is.\u00a0 This next filter will stabilize the video with 2 commands.\u00a0 The first command creates what I call a motion profile.\u00a0 The second command applies the motion profile against the source video to create a stabilized clip.\u00a0 Here are the commands.<\/p>\n<pre>ffmpeg -i MINI0492_Gamma.MOV -vf vidstabdetect=shakiness=10:accuracy=15 -f null -\r\nffmpeg -i MINI0492_Gamma.MOV -vf vidstabtransform=smoothing=40:input=\"transforms.trf\" MINI0492_Stable.MOV<\/pre>\n<p>The profiling filter are already set to their highest setting, shakiness=10 and accuracy=15.\u00a0 The second stabilization filter has a smoothing range of 0 to 1000.\u00a0 The higher you go, the more smooth, but you sacrifice FOV (field of view).\u00a0 I found 50 good enough.\u00a0 Now I want to sharpen the video, since much of it appears to be out of focus.\u00a0 Here is a command I ran to enhance the edges of the clip.<\/p>\n<pre>ffmpeg -i MINI0492_Stable.MOV -vf unsharp=luma_msize_x=9:luma_msize_y=9:luma_amount=3 MINI0492_Sharp.MOV<\/pre>\n<p>This gave me good results after changing values for the following filter ranges.<\/p>\n<p>luma_msize_x range 3 to 23<br \/>\nluma_msize_y range 3 to 23<br \/>\nluma_amount range -2 to 5<\/p>\n<p>Next I&#8217;ll create a side by side composite of both the source and final processed clip.\u00a0 Here is the command to do that.<\/p>\n<pre>ffmpeg -i MINI0492_Split1.MOV -i MINI0492_Sharp.MOV -filter_complex \"[0:v]setpts=PTS-STARTPTS, pad=iw*2:ih[bg]; [1:v]setpts=PTS-STARTPTS[fg]; [bg][fg]overlay=w\" MINI0492_SideBySide.MOV<\/pre>\n<p>The results are impressive, I find that I&#8217;m referencing the clearer clip on the right to see what isn&#8217;t visible on the left.\u00a0 With the commands tested and validated with my clip, I&#8217;m ready to apply these commands to the entire video.<\/p>\n<p>This will be a time consuming process, that&#8217;s alright.\u00a0 I&#8217;m going to script it and go to sleep.\u00a0 When I wake, the final processed video will be ready.\u00a0 Here is the script I&#8217;ll be using.<\/p>\n<p>[bash]#!\/bin\/bash<br \/>\n# this runs while everyone else sleeps<br \/>\n# use the command &quot;sh ProcessVideos.sh&quot; to run manually from command line<\/p>\n<p>#########################################################<br \/>\n# #<br \/>\n# Night Time Video #<br \/>\n# Enhance and stabilize processing #<br \/>\n# #<br \/>\n#########################################################<\/p>\n<p># Change to the working directory<br \/>\ncd \/home\/local\/Desktop\/Clip<\/p>\n<p># Correct the gamma levels so video is brighter and depth remains<br \/>\n# The commented command will brighten only<br \/>\n# ffmpeg -i MINI0492.MOV -vf hue=b=2.11 MINI0492_Brightness1.MOV<br \/>\nffmpeg -i MINI0492.MOV -vf &quot;eq=gamma=1.8&quot; MINI0492_Gamma.MOV<\/p>\n<p># Create a stablization profile and apply it<br \/>\nffmpeg -i MINI0492_Gamma.MOV -vf vidstabdetect=shakiness=10:accuracy=15 -f null &#8211;<br \/>\nffmpeg -i MINI0492_Gamma.MOV -vf vidstabtransform=smoothing=50:input=&quot;transforms.trf&quot; MINI0492_Stable.MOV<\/p>\n<p># Sharpen the video<br \/>\nffmpeg -i MINI0492_Stable.MOV -vf unsharp=luma_msize_x=9:luma_msize_y=9:luma_amount=3 MINI0492_Sharp.MOV<\/p>\n<p># Create a side by side video of the original on the left and processed on the right<br \/>\nffmpeg -i MINI0492.MOV -i MINI0492_Sharp.MOV -filter_complex &quot;[0:v]setpts=PTS-STARTPTS, pad=iw*2:ih[bg]; [1:v]setpts=PTS-STARTPTS[fg]; [bg][fg]overlay=w&quot; MINI0492_SideBySide.MOV[\/bash]<\/p>\n<p>Here are the results.\u00a0 The noise from the camera&#8217;s processor shows some noise.\u00a0 I&#8217;m guessing it&#8217;s the write burst to the SD media on the camera.\u00a0 Daylight video doesn&#8217;t reveal that artifact, but night time processed video does.\u00a0 It messes with the stablization, so I would dial the level of stabiliztion down a bit to reduce that.<\/p>\n<p><iframe loading=\"lazy\" title=\"MINI0492 SideBySide\" width=\"640\" height=\"360\" src=\"https:\/\/www.youtube.com\/embed\/rITGd6qETWs?feature=oembed\" frameborder=\"0\" allow=\"accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share\" referrerpolicy=\"strict-origin-when-cross-origin\" allowfullscreen><\/iframe><\/p>\n<p>Still, it&#8217;s nice to be able to take a bunch of night time video and process it in bulk.\u00a0 The platform doing the work could be a Raspberry Pi.\u00a0 All you really need is time, space, and support for FFMpeg and the filter libraries.\u00a0 I&#8217;m going to cover more things FFMpeg can do in later posts.\u00a0 Simple enhancements to day time video as well as some audio visual stuff will be covered.\u00a0 I hope you enjoyed.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>In this post I&#8217;ll be covering how to process footage that was shot at night. By default, it is difficult to see what was captured with the camera. I do know the length of the video as well as other aspects of it. The clip I&#8217;ll be using is 5 minutes long and has a resolution of 1280&#215;720 at 30fps using the H.264 \/ AVC codec. The audio is a single channel (mono) 16-bit PCM at 32000Hz. I like that&#8230;<\/p>\n<p class=\"read-more\"><a class=\"btn btn-default\" href=\"https:\/\/www.cloudacm.com\/?p=2956\"> Read More<span class=\"screen-reader-text\">  Read More<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[9],"tags":[],"class_list":["post-2956","post","type-post","status-publish","format-standard","hentry","category-computer-vision"],"_links":{"self":[{"href":"https:\/\/www.cloudacm.com\/index.php?rest_route=\/wp\/v2\/posts\/2956","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.cloudacm.com\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.cloudacm.com\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.cloudacm.com\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.cloudacm.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=2956"}],"version-history":[{"count":36,"href":"https:\/\/www.cloudacm.com\/index.php?rest_route=\/wp\/v2\/posts\/2956\/revisions"}],"predecessor-version":[{"id":2987,"href":"https:\/\/www.cloudacm.com\/index.php?rest_route=\/wp\/v2\/posts\/2956\/revisions\/2987"}],"wp:attachment":[{"href":"https:\/\/www.cloudacm.com\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=2956"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.cloudacm.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=2956"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.cloudacm.com\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=2956"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}