One of the most popular tasks when dealing with AVI files is recompression. During recompression the application should read each frame and write it to a new AVI file. This AVI file typically has different compression settings which allow creating files of noticeable smaller size.
The idea is very simple. You should just do the following:
It is important to follow this order: all AVI parameters including compression should be initialized BEFORE you open writer, audio and video data should be copied AFTER opening.
This is demonstrated in the code example below. See comments in the code for more details. You can just paste this function into your code and pass source and destination AVI file name as arguments.
Public Shared Sub RecompressAvi(ByVal sourceFilename As String, _ ByVal destinationFilename As String) Dim reader As New Aurigma.GraphicsMill.Codecs.AviReader reader.Open(sourceFilename) Dim writer As New Aurigma.GraphicsMill.Codecs.AviWriter ' Copy AVI parameters which you would not like to change writer.FramesPerSecond = reader.FramesPerSecond writer.Width = reader.Width writer.Height = reader.Height writer.Quality = reader.Quality ' Specify necessary compression settings. ' In this example we use DivX5Pro compression. Note, it is not ' guarantied that an appropriate codec installed. That's why ' MsVideo1 is used as a fallback option. Dim codec As Aurigma.GraphicsMill.Codecs.AviCompressor codec = Aurigma.GraphicsMill.Codecs.AviCompressor.GetVideoCompressor( _ Aurigma.GraphicsMill.Codecs.AviCompressor.DivXPro5) If codec Is Nothing Then codec = Aurigma.GraphicsMill.Codecs.AviCompressor.GetVideoCompressor( _ Aurigma.GraphicsMill.Codecs.AviCompressor.MSVideo1) End If writer.CompressorHandler() = codec.CompressorHandler writer.BytesPerSecond = 50 writer.KeyFrameRate = 4 ' Open a destination file. Note, it should be done AFTER you ' initialized all parameters. writer.Open(destinationFilename) ' Now iterate each frame in the source file and copy them ' to the destination. Dim frame As Aurigma.GraphicsMill.Codecs.AviFrame For Each frame In reader writer.AddFrame(frame) frame.Dispose() Next ' Copy audio tracks Dim I As Integer For I = 0 To reader.AudioManager.AudioStreamCount - 1 writer.AudioManager.AddAudioStream(reader.AudioManager, I, False) Next ' Do not forget to release opened AVI files (otherwise they ' will be locked) reader.Close() writer.Close() End Sub
public static void RecompressAvi(string sourceFilename, string destinationFilename) { Aurigma.GraphicsMill.Codecs.AviReader reader = new Aurigma.GraphicsMill.Codecs.AviReader(sourceFilename); Aurigma.GraphicsMill.Codecs.AviWriter writer = new Aurigma.GraphicsMill.Codecs.AviWriter(); // Copy AVI parameters which you would not like to change writer.FramesPerSecond = reader.FramesPerSecond; writer.Width = reader.Width; writer.Height = reader.Height; writer.Quality = reader.Quality; // Specify necessary Compressor settings. // In this example we use DivX5Pro Compressor. Note, it is not // guarantied that an appropriate codec installed. That's why // MSVideo1 is used as a fallback option. Aurigma.GraphicsMill.Codecs.AviCompressor codec = Aurigma.GraphicsMill.Codecs.AviCompressor.GetVideoCompressor( Aurigma.GraphicsMill.Codecs.AviCompressor.DivXPro5); if (codec == null) { codec = Aurigma.GraphicsMill.Codecs.AviCompressor.GetVideoCompressor( Aurigma.GraphicsMill.Codecs.AviCompressor.MSVideo1); } writer.CompressorHandler = codec.CompressorHandler; writer.BytesPerSecond = 50; writer.KeyFrameRate = 4; // Open a destination file. Note, it should be done AFTER // you initialized all parameters. writer.Open(destinationFilename); // Now iterate each frame in the source file and copy them to // the destination. foreach (Aurigma.GraphicsMill.Codecs.AviFrame frame in reader) { writer.AddFrame(frame); frame.Dispose(); } // Copy audio tracks int i; for (i=0;i<reader.AudioManager.AudioStreamCount;i++) { writer.AudioManager.AddAudioStream(reader.AudioManager, i, false); } // Do not forget to release opened AVI files (otherwise they // will be locked) reader.Close(); writer.Close(); }
It is easy to modify this code so that you could resize the AVI file in addition to recompression. It allows you to optimize the code for mobile devices (which have limited screen size).
To do it, you should just set the AviWriter.Width and AviWriter.Height properties:
Public Shared Sub ResizeAvi(ByVal sourceFilename As String, _ ByVal destinationFilename As String, _ ByVal destinationWidth As Integer, _ ByVal destinationHeight As Integer) ' Create and open the reader object Dim reader As New Aurigma.GraphicsMill.Codecs.AviReader reader.Open(sourceFilename) ' Create, initialize, and open the writer object Dim writer As New Aurigma.GraphicsMill.Codecs.AviWriter writer.Width = destinationWidth writer.Height = destinationHeight ' ... All the rest code is omitted for brevity ' you can take it from the previous code snippet... End Sub
public static void ResizeAvi(string sourceFilename, string destinationFilename, int destinationWidth, int destinationHeight) { Aurigma.GraphicsMill.Codecs.AviReader reader = new Aurigma.GraphicsMill.Codecs.AviReader(sourceFilename); Aurigma.GraphicsMill.Codecs.AviWriter writer = new Aurigma.GraphicsMill.Codecs.AviWriter(); // Copy AVI parameters which you would not like to change writer.Width = destinationWidth; writer.Height = destinationHeight; // ... All the rest code is omitted for brevity // you can take it from the previous code snippet... }
Note, this code does not preserve an aspect ratio of the original video file. If you need to keep the aspect ratio, you should calculate one of the dimensions based on another. E.g. if you know a width you need to get, the height can be calculated as follows:
dest_height = source_height * (dest_width / source_width)