8

I have approximately 3000 short video clips, each about 3 seconds in duration. I need to rotate each of them 90 degrees. What is the best way to do this? I have Adobe Creative Cloud subscription, as well as access to both Windows and Mac machines. Looking for the easiest solution to automate/batch process the rotation of so many videos.

If you were wondering - the videos are part of an e-learning course on lumber. The learner views each randomly selected video, which is just a short clip of a piece of lumber rotating. The videos were shot so that the lumber (2x4s, etc.) were horizontal. But now the client wants the lumber to be vertical in the clips.

  • Only rotation? From e.g. 1280x720 to 720x1280 right? – p2or Apr 22 '15 at 12:11
  • Just rotation 90 degrees clockwise (or counter cw - doesn't matter for this project). – user172586 Apr 22 '15 at 15:49
  • Does the container of your video files includes an 'orientation' metadata ? – audionuma Apr 23 '15 at 8:41
8

Use ffmpeg and the "transpose" filter as "poor" suggested. For example, if your files are mp4 and are in the current directory:

mkdir -p rotated
for f in *.mp4; do ffmpeg -i "$f" -vf transpose=2 -c:a copy -metadata:s:v rotate="" rotated/"$f"; done
  • The transpose value can be "1" or "clock" for clockwise rotation, "2" or "cclock" for counter-clockwise rotation. There are other values which will also apply a flip.

  • The audio will be stream copied to avoid unnecessary re-encoding.

  • The video stream rotation metadata is cleared in this example. Otherwise ffmpeg will copy it from the input to the output resulting in an incorrect rotation for players that pay attention to this metadata (some do, and some don't).

Another example, more verbose and flexible, and which keeps the rotated file in the same directory with a new name:

ext=mp4
for f in /some/dir/*.$ext; do
    new=${f/%.$ext/-rotated.$ext};
    ffmpeg -i "$f" -vf transpose=2 -c:a copy -metadata:s:v rotate="" "$new"
done
  • Yes! I should learn more about bash scripting :) – p2or Apr 24 '15 at 18:57
1

You have specified that you are interested in working on a huge number of videos, if you have a multicore machine and you will use a normal for loop provided by your shell, you will have one of your cores running hot, while others are doing absolutely nothing. This is not ideal.

What you should be doing for such a job is using parallel, a tool that allows you to start several jobs at once, and it can do everything that a for-loop can, but better.

I will not write about all the features of this tool, but will concentrate on your specific task.

One way to start all these jobs would be:

parallel avconv -i "{}" -vf transpose=2 "{.}[rotated].mp4" ::: *.mp4

In here {} replaces each filename, and {.} replaces filename without an extension.

I will suggest that you will start as many jobs as you have cores, take away one. The reason for that is so your operating system will still remain useable, and also this will save you in case if you are using harddisk encryption (which will be using processing power to read/write data). To do this simply add --jobs -1 to your command line, and you will limit the number of jobs.

parallel --jobs -1 avconv -i "{}" -vf transpose=2 "{.}[rotated].mp4" ::: *.mp4

Please keep in mind that no output will be given until each encoding completes. So you will not see just how much of each of your video is done.

0

Based on this answer you can use ffmpeg with following commands to rotate a video:

ffmpeg -i input -vf transpose=2 output

To Batch process a folder of movies you can use a programming language of your choice and iterate through the files. I've used linux with python 2.7+ here. You only have to edit folder_movies path, path_to_ffmpeg and set your movie extension:

import os # import os module
import subprocess # import subprocess module

# set the path to your video folder
folder_movies = '/home/user/Desktop/test/'

# set ffmpeg path
path_to_ffmpeg = "/opt/ffmpeg/ffmpeg"

# set file extension
ext = ".mp4"

# collect all videos in folder_movies
movie_files = [f for f in os.listdir(folder_movies) if f.endswith(ext)] 

# iterate through the files
for i in movie_files:

    # setup correct filepath for mov's
    file_path = os.path.join(folder_movies,i)

    # generate new file path
    new_path = os.path.splitext(file_path)[0] + '_rotated_90' + ext

    # call ffmpeg with the correct arguments
    # command: ffmpeg -i input -vf transpose=2 output
    subprocess.call([path_to_ffmpeg, "-i",  file_path, "-vf", "transpose=2", "-c:a", "copy", new_path])

Afterwards your movie folder should looks like:

enter image description here

The advantage of using python is that the code runs cross platform. The only thing you need to consider are the paths to the directory and the ffmpeg executable. In order to run this on a windows machine you only have to replace the paths to something like:

# folder_movies = '/home/user/Desktop/test/' # linux or osx
folder_movies = r'c:\some\directory\test'    # windows, the r is important
folder_movies = 'c:/some/directory\test'     # windows (alternative)

# path_to_ffmpeg = '/opt/ffmpeg/ffmpeg'            # linux or osx
path_to_ffmpeg = r'c:\Program Files\ffmpeg\ffmpeg' # windows, the r is important
path_to_ffmpeg = 'c:/Program Files/ffmpeg\ffmpeg'  # windows (alternative)

Note: I'm not a ffmpeg expert, maybe there is a way to batch process with it directly.

  • 1
    You don't really need a whole script for this. It can be done directly on the Mac or Linux command-line with something like : mkdir -p rotated; for f in *.mp4; do ffmpeg -i "$f" -vf transpose=2 rotated/"$f"; done (assuming your video files are .mp4 in this example). – mivk Apr 23 '15 at 17:48
  • @mivk nice, why not converting this to an answer? – p2or Apr 24 '15 at 7:17
  • @mivk Since you are using a for loop it's nearly the same. For those who don't use linux or osx, it makes sense to use python or another scripting language. – p2or Jun 5 '15 at 11:54
  • @poor : well, for those users who are neither on linux nor on mac, the translation into PowerShell is "left as an exercise for the reader"... :-) – mivk Jun 5 '15 at 16:51
  • @mivk hehe, yeah, but no one wants to use it ;) – p2or Jun 5 '15 at 16:53

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.