private IntPtr CreateCompressedStream(IntPtr stream) { Avi.AVICOMPRESSOPTIONS_CLASS options = new Avi.AVICOMPRESSOPTIONS_CLASS(); options.fccType = (uint)Avi.StreamtypeVIDEO; options.lpParms = IntPtr.Zero; options.lpFormat = IntPtr.Zero; //display the compression options dialog Avi.AVISaveOptions( IntPtr.Zero, Avi.ICMF_CHOOSE_KEYFRAME | Avi.ICMF_CHOOSE_DATARATE, 1, ref aviStream, ref options); options.dwQuality = 10000; //Avi.AVISaveOptionsFree(1, ref options); //get a compressed stream IntPtr compressedStream = IntPtr.Zero; Avi.AVICOMPRESSOPTIONS structOptions = options.ToStruct(); int result = Avi.AVIMakeCompressedStream( out compressedStream, stream, ref structOptions, 0); return(compressedStream); }
/// <summary>Adds a new frame to the AVI stream</summary> /// <param name="bmp">The image to add</param> public void AddFrame(Bitmap bmp) { bmp.RotateFlip(RotateFlipType.RotateNoneFlipY); BitmapData bmpDat = bmp.LockBits( new Rectangle(0, 0, bmp.Width, bmp.Height), ImageLockMode.ReadOnly, bmp.PixelFormat); if (countFrames == 0) { //this is the first frame - get size and create a new stream this.stride = (UInt32)bmpDat.Stride; this.width = bmp.Width; this.height = bmp.Height; CreateStream(); } int result = Avi.AVIStreamWrite(aviStream, countFrames, 1, bmpDat.Scan0, //pointer to the beginning of the image data (Int32)(stride * height), 0, 0, 0); if (result != 0) { throw new Exception("Error in AVIStreamWrite: " + result.ToString()); } bmp.UnlockBits(bmpDat); bmp.Dispose(); countFrames++; }
/// <summary>Opens an AVI file and creates a GetFrame object</summary> /// <param name="fileName">Name of the AVI file</param> public void Open(string fileName) { //Intitialize AVI library Avi.AVIFileInit(); //Open the file int result = Avi.AVIFileOpen( ref aviFile, fileName, Avi.OF_SHARE_DENY_WRITE, 0); if (result != 0) { throw new Exception("Exception in AVIFileOpen: " + result.ToString()); } //Get the video stream result = Avi.AVIFileGetStream( aviFile, out aviStream, Avi.StreamtypeVIDEO, 0); if (result != 0) { throw new Exception("Exception in AVIFileGetStream: " + result.ToString()); } firstFrame = Avi.AVIStreamStart(aviStream.ToInt32()); countFrames = Avi.AVIStreamLength(aviStream.ToInt32()); streamInfo = new Avi.AVISTREAMINFO(); result = Avi.AVIStreamInfo(aviStream.ToInt32(), ref streamInfo, Marshal.SizeOf(streamInfo)); if (result != 0) { throw new Exception("Exception in AVIStreamInfo: " + result.ToString()); } //Open frames Avi.BITMAPINFOHEADER bih = new Avi.BITMAPINFOHEADER(); bih.biBitCount = 24; bih.biClrImportant = 0; bih.biClrUsed = 0; bih.biCompression = 0; //BI_RGB; bih.biHeight = (Int32)streamInfo.rcFrame.bottom; bih.biWidth = (Int32)streamInfo.rcFrame.right; bih.biPlanes = 1; bih.biSize = (UInt32)Marshal.SizeOf(bih); bih.biXPelsPerMeter = 0; bih.biYPelsPerMeter = 0; getFrameObject = Avi.AVIStreamGetFrameOpen(aviStream, ref bih); //force function to return 24bit DIBS //getFrameObject = Avi.AVIStreamGetFrameOpen(aviStream, 0); //return any bitmaps if (getFrameObject == 0) { throw new Exception("Exception in AVIStreamGetFrameOpen!"); } }
/// <summary>Closes stream, file and AVI library</summary> public void Close() { if (aviStream != IntPtr.Zero) { Avi.AVIStreamRelease(aviStream); aviStream = IntPtr.Zero; } if (aviFile != 0) { Avi.AVIFileRelease(aviFile); aviFile = 0; } Avi.AVIFileExit(); }
private UInt32 fccHandler = 1668707181; //"Microsoft Video 1" - Use CVID for default codec: (UInt32)Avi.mmioStringToFOURCC("CVID", 0); /// <summary>Creates a new AVI file</summary> /// <param name="fileName">Name of the new AVI file</param> /// <param name="frameRate">Frames per second</param> /// <param name="width">Width</param><param name="height">Height</param> public void Open(string fileName, UInt32 frameRate) { this.frameRate = frameRate; Avi.AVIFileInit(); int hr = Avi.AVIFileOpen( ref aviFile, fileName, 4097 /* OF_WRITE | OF_CREATE (winbase.h) */, 0); if (hr != 0) { throw new Exception("Error in AVIFileOpen: " + hr.ToString()); } }
/// <summary>Closes all streams, files and libraries</summary> public void Close() { if (getFrameObject != 0) { Avi.AVIStreamGetFrameClose(getFrameObject); getFrameObject = 0; } if (aviStream != IntPtr.Zero) { Avi.AVIStreamRelease(aviStream); aviStream = IntPtr.Zero; } if (aviFile != 0) { Avi.AVIFileRelease(aviFile); aviFile = 0; } Avi.AVIFileExit(); }
/// <summary>Creates a new video stream in the AVI file</summary> private void CreateStream() { Avi.AVISTREAMINFO strhdr = new Avi.AVISTREAMINFO(); strhdr.fccType = fccType; strhdr.fccHandler = fccHandler; strhdr.dwScale = 1; strhdr.dwRate = frameRate; strhdr.dwSuggestedBufferSize = (UInt32)(height * stride); strhdr.dwQuality = 10000; //highest quality! Compression destroys the hidden message strhdr.rcFrame.bottom = (UInt32)height; strhdr.rcFrame.right = (UInt32)width; strhdr.szName = new UInt16[64]; int result = Avi.AVIFileCreateStream(aviFile, out aviStream, ref strhdr); if (result != 0) { throw new Exception("Error in AVIFileCreateStream: " + result.ToString()); } //define the image format Avi.BITMAPINFOHEADER bi = new Avi.BITMAPINFOHEADER(); bi.biSize = (UInt32)Marshal.SizeOf(bi); bi.biWidth = (Int32)width; bi.biHeight = (Int32)height; bi.biPlanes = 1; bi.biBitCount = 32; bi.biSizeImage = (UInt32)(stride * height); oldStream = aviStream; aviStream = CreateCompressedStream(aviStream); result = Avi.AVIStreamSetFormat(aviStream, 0, ref bi, Marshal.SizeOf(bi)); if (result != 0) { throw new Exception("Error in AVIStreamSetFormat: " + result.ToString()); } }
/// <summary>Exports a frame into a bitmap file</summary> /// <param name="position">Position of the frame</param> /// <param name="dstFileName">Name ofthe file to store the bitmap</param> public void ExportBitmap(int position, String dstFileName) { if (position > countFrames) { throw new Exception("Invalid frame position"); } //Decompress the frame and return a pointer to the DIB int pDib = Avi.AVIStreamGetFrame(getFrameObject, firstFrame + position); //Copy the bitmap header into a managed struct Avi.BITMAPINFOHEADER bih = new Avi.BITMAPINFOHEADER(); bih = (Avi.BITMAPINFOHEADER)Marshal.PtrToStructure(new IntPtr(pDib), bih.GetType()); /*if(bih.biBitCount < 24){ * throw new Exception("Not enough colors! DIB color depth is less than 24 bit."); * }else */ if (bih.biSizeImage < 1) { throw new Exception("Exception in AVIStreamGetFrame: Not bitmap decompressed."); } //Copy the image byte[] bitmapData = new byte[bih.biSizeImage]; int address = pDib + Marshal.SizeOf(bih); for (int offset = 0; offset < bitmapData.Length; offset++) { bitmapData[offset] = Marshal.ReadByte(new IntPtr(address)); address++; } //Copy bitmap info byte[] bitmapInfo = new byte[Marshal.SizeOf(bih)]; IntPtr ptr; ptr = Marshal.AllocHGlobal(bitmapInfo.Length); Marshal.StructureToPtr(bih, ptr, false); address = ptr.ToInt32(); for (int offset = 0; offset < bitmapInfo.Length; offset++) { bitmapInfo[offset] = Marshal.ReadByte(new IntPtr(address)); address++; } //Create file header Avi.BITMAPFILEHEADER bfh = new Avi.BITMAPFILEHEADER(); bfh.bfType = Avi.BMP_MAGIC_COOKIE; bfh.bfSize = (Int32)(55 + bih.biSizeImage); //size of file as written to disk bfh.bfReserved1 = 0; bfh.bfReserved2 = 0; bfh.bfOffBits = Marshal.SizeOf(bih) + Marshal.SizeOf(bfh); //Create or overwrite the destination file FileStream fs = new FileStream(dstFileName, System.IO.FileMode.Create); BinaryWriter bw = new BinaryWriter(fs); //Write header bw.Write(bfh.bfType); bw.Write(bfh.bfSize); bw.Write(bfh.bfReserved1); bw.Write(bfh.bfReserved2); bw.Write(bfh.bfOffBits); //Write bitmap info bw.Write(bitmapInfo); //Write bitmap data bw.Write(bitmapData); bw.Close(); fs.Close(); }