예제 #1
0
        public static void CreateAnimatedGif(List <string> gifFiles, int delay, string outputFile)
        {
            BinaryWriter writer = new BinaryWriter(new FileStream(outputFile, FileMode.Create, FileAccess.ReadWrite));

            byte[] gif_Signature = new byte[] { (byte)'G', (byte)'I', (byte)'F', (byte)'8', (byte)'9', (byte)'a' };
            writer.Write(gif_Signature);
            for (int i = 0; i < gifFiles.Count; i++)
            {
                GifClass gif = new GifClass();
                gif.LoadGifPicture(gifFiles[i]);
                if (i == 0)
                {
                    writer.Write(gif.m_ScreenDescriptor.ToArray());
                }
                writer.Write(GifCreator.CreateGraphicControlExtensionBlock(delay));
                writer.Write(gif.m_ImageDescriptor.ToArray());
                writer.Write(gif.m_ColorTable.ToArray());
                writer.Write(gif.m_ImageData.ToArray());
            }
            writer.Write(GifCreator.CreateLoopBlock());
            writer.Write((byte)0x3B); //End file
            writer.Close();
        }
예제 #2
0
        private void WriteAnimatedGif(Bitmap src, Stream output, IEncoder ios, ResizeSettings queryString)
        {
            //http://www.fileformat.info/format/gif/egff.htm
            //http://www.fileformat.info/format/gif/spec/44ed77668592476fb7a682c714a68bac/view.htm

            //Heavily modified and patched from comments on http://bloggingabout.net/blogs/rick/archive/2005/05/10/3830.aspx
            MemoryStream memoryStream = null;
            BinaryWriter writer       = null;

            //Variable declaration
            try
            {
                writer       = new BinaryWriter(output);
                memoryStream = new MemoryStream(4096);
                //Write the GIF 89a sig
                writer.Write(new byte[] { (byte)'G', (byte)'I', (byte)'F', (byte)'8', (byte)'9', (byte)'a' });

                //We parse this from the source image
                int   loops  = GetLoops(src.PropertyItems);
                int[] delays = GetDelays(src.PropertyItems);//20736 (delays) 20737 (loop);

                int frames = src.GetFrameCount(FrameDimension.Time);
                for (int frame = 0; frame < frames; frame++)
                {
                    //Select the frame
                    src.SelectActiveFrame(FrameDimension.Time, frame);


                    // http://radio.weblogs.com/0122832/2005/10/20.html
                    //src.MakeTransparent(); This call makes some GIFs replicate the first image on all frames.. i.e. SelectActiveFrame doesn't work.

                    bool transparent = ios.SupportsTransparency;

                    using (Bitmap b = c.CurrentImageBuilder.Build(src, queryString, false)){
                        //Useful to check if animation is occurring - sometimes the problem isn't the output file, but the input frames are
                        //all the same.
                        //for (var i = 0; i < b.Height; i++) b.SetPixel(frame * 10, i, Color.Green);
                        // b.Save(memoryStream, ImageFormat.Gif);
                        if (ios is DefaultEncoder)
                        {
                            //For both WIC Builder and DefaultBuilder
                            //We assume no transparency
                            transparent = false;
                        }
                        ios.Write(b, memoryStream); //Allows quantization and dithering
                    }

                    GifClass gif = new GifClass();
                    gif.LoadGifPicture(memoryStream);
                    if (frame == 0)
                    {
                        //Only one screen descriptor per file. Steal from the first image
                        writer.Write(gif.m_ScreenDescriptor.ToArray());
                        //How many times to loop the image (unless it is 1) IE and FF3 loop endlessly if loop=1
                        if (loops != 1)
                        {
                            writer.Write(GifCreator.CreateLoopBlock(loops));
                        }
                    }
                    //Restore frame delay
                    int delay = 0;
                    if (delays != null && delays.Length > frame)
                    {
                        delay = delays[frame];
                    }
                    writer.Write(GifCreator.CreateGraphicControlExtensionBlock(delay, 0, transparent)); //The delay/transparent color block
                    writer.Write(gif.m_ImageDescriptor.ToArray());                                      //The image desc
                    writer.Write(gif.m_ColorTable.ToArray());                                           //The palette
                    writer.Write(gif.m_ImageData.ToArray());                                            //Image data

                    memoryStream.SetLength(0);                                                          //Clear the mem stream, but leave it allocated for now
                    memoryStream.Seek(0, SeekOrigin.Begin);                                             //Reset memory buffer
                }

                writer.Write((byte)0x3B); //End file
            }
            finally
            {
                if (memoryStream != null)
                {
                    memoryStream.Dispose();
                }
                //if (writer != null) writer.Close
            }
        }