// TODO: make a class that only resolves the sizing once, also use in InsertImages
        public void AddImages(IEnumerable <Bitmap> bmp, bool opacify, bool transparent, bool smooth, SizingCallback resolve)
        {
            EnsureUndisposed();
            int i = frames.Count;

            foreach (Bitmap b in bmp)
            {
                frames.AddRange(CreateFrames(b, opacify, transparent, smooth, resolve));
            }
            for (; i < frames.Count; i++)
            {
                ComputeBoundingBox(i);
            }
        }
        // TODO: (above)
        public void InsertImages(IEnumerable <Bitmap> bmp, int pos, bool opacify, bool transparent, bool smooth, SizingCallback resolve)
        {
            EnsureUndisposed();
            int count = frames.Count;
            int i     = pos;

            foreach (Bitmap b in bmp)
            {
                frames.InsertRange(pos, CreateFrames(b, opacify, transparent, smooth, resolve));
                pos  += frames.Count - count;
                count = frames.Count;
            }
            for (; i < pos; i++)
            {
                ComputeBoundingBox(i);
            }
        }
        IEnumerable <Bitmap> CreateFrames(Bitmap original, bool opacify, bool transparent, bool smooth, SizingCallback resolve)
        {
            EnsureUndisposed();
            FramePlacement placement = FramePlacement.TopLeft;
            FrameSizing    sizing    = FrameSizing.OriginalSize;

            if (frames.Count == 0)
            {
                sizing = FrameSizing.NewSize;
            }
            else if (original.Width != width || original.Height != height)
            {
                if (resolve != null)
                {
                    resolve(out placement, out sizing);
                }
            }
            bool newsize = false;

            if (sizing == FrameSizing.NewSize)
            {
                width   = original.Width;
                height  = original.Height;
                newsize = true;
            }
            else if (sizing == FrameSizing.MaximumSize)
            {
                if (original.Width * original.Height > width * height)
                {
                    width   = original.Width;
                    height  = original.Height;
                    newsize = true;
                }
            }
            if (newsize)
            {
                for (int i = 0; i < frames.Count; i++)
                {
                    Bitmap b = frames[i];
                    frames[i] = Resize(b, width, height, placement);
                    b.Dispose();
                }
            }
            FrameDimension fd = new FrameDimension(original.FrameDimensionsList[0]);
            int            c  = original.GetFrameCount(fd);

            for (int f = 0; f < c; f++)
            {
                original.SelectActiveFrame(fd, f);
                Bitmap     temp = Resize(original, original.Width, original.Height, FramePlacement.TopLeft); // Don't modify the bitmap, just make a new one from the frame with format32bppargb;
                BitmapData bd   = temp.LockBits(new Rectangle(0, 0, temp.Width, temp.Height), ImageLockMode.ReadWrite, PixelFormat.Format32bppArgb);
                if (opacify)
                {
                    for (int i = 0; i < bd.Height; i++)
                    {
                        for (int j = 0; j < bd.Width; j++)
                        {
                            int ofs = bd.Stride * i + j * 4;
                            System.Runtime.InteropServices.Marshal.WriteInt32(bd.Scan0, ofs, unchecked (System.Runtime.InteropServices.Marshal.ReadInt32(bd.Scan0, ofs) & (int)0xFF000000));
                        }
                    }
                }
                if (transparent)
                {
                    int col = System.Runtime.InteropServices.Marshal.ReadInt32(bd.Scan0, bd.Stride * (bd.Height - 1)) & 0xFFFFFF;
                    for (int i = 0; i < bd.Height; i++)
                    {
                        for (int j = 0; j < bd.Width; j++)
                        {
                            int ofs = bd.Stride * i + j * 4;
                            if ((System.Runtime.InteropServices.Marshal.ReadInt32(bd.Scan0, ofs) & 0xFFFFFF) == col)
                            {
                                System.Runtime.InteropServices.Marshal.WriteInt32(bd.Scan0, ofs, col);
                            }
                        }
                    }
                }
                temp.UnlockBits(bd);
                Bitmap bmp = temp;
                if (original.Width != width || original.Height != height)
                {
                    bmp = Resize(temp, width, height, placement);
                    temp.Dispose();
                }
                if (smooth)
                {
                    temp = bmp;
                    bmp  = SmoothEdges(temp);
                    temp.Dispose();
                }
                yield return(bmp); // me likes ;D
            }
        }
        public void InsertImage(Bitmap bmp, int pos, bool opacify, bool transparent, bool smooth, SizingCallback resolve)
        {
            EnsureUndisposed();
            int i = frames.Count;

            frames.InsertRange(pos, CreateFrames(bmp, opacify, transparent, smooth, resolve));
            for (; i < frames.Count; i++)
            {
                ComputeBoundingBox(i);
            }
        }
 IEnumerable<Bitmap> CreateFrames(Bitmap original, bool opacify, bool transparent, bool smooth, SizingCallback resolve)
 {
     EnsureUndisposed();
     FramePlacement placement = FramePlacement.TopLeft;
     FrameSizing sizing = FrameSizing.OriginalSize;
     if (frames.Count == 0)
         sizing = FrameSizing.NewSize;
     else if (original.Width != width || original.Height != height)
         if (resolve != null) resolve(out placement, out sizing);
     bool newsize = false;
     if (sizing == FrameSizing.NewSize)
     {
         width = original.Width;
         height = original.Height;
         newsize = true;
     }
     else if (sizing == FrameSizing.MaximumSize)
     {
         if (original.Width*original.Height > width*height)
         {
             width = original.Width;
             height = original.Height;
             newsize = true;
         }
     }
     if (newsize)
     {
         for (int i = 0; i < frames.Count; i++)
         {
             Bitmap b = frames[i];
             frames[i] = Resize(b, width, height, placement);
             b.Dispose();
         }
     }
     FrameDimension fd = new FrameDimension(original.FrameDimensionsList[0]);
     int c = original.GetFrameCount(fd);
     for (int f = 0; f < c; f++)
     {
         original.SelectActiveFrame(fd, f);
         Bitmap temp = Resize(original, original.Width, original.Height, FramePlacement.TopLeft); // Don't modify the bitmap, just make a new one from the frame with format32bppargb;
         BitmapData bd = temp.LockBits(new Rectangle(0, 0, temp.Width, temp.Height), ImageLockMode.ReadWrite, PixelFormat.Format32bppArgb);
         if (opacify)
         {
             for (int i = 0; i < bd.Height; i++)
                 for (int j = 0; j < bd.Width; j++)
                 {
                     int ofs = bd.Stride * i + j * 4;
                     System.Runtime.InteropServices.Marshal.WriteInt32(bd.Scan0, ofs, unchecked(System.Runtime.InteropServices.Marshal.ReadInt32(bd.Scan0, ofs) & (int)0xFF000000));
                 }
         }
         if (transparent)
         {
             int col = System.Runtime.InteropServices.Marshal.ReadInt32(bd.Scan0, bd.Stride * (bd.Height - 1)) & 0xFFFFFF;
             for (int i = 0; i < bd.Height; i++)
                 for (int j = 0; j < bd.Width; j++)
                 {
                     int ofs = bd.Stride * i + j * 4;
                     if ((System.Runtime.InteropServices.Marshal.ReadInt32(bd.Scan0, ofs) & 0xFFFFFF) == col)
                         System.Runtime.InteropServices.Marshal.WriteInt32(bd.Scan0, ofs, col);
                 }
         }
         temp.UnlockBits(bd);
         Bitmap bmp = temp;
         if (original.Width != width || original.Height != height)
         {
             bmp = Resize(temp, width, height, placement);
             temp.Dispose();
         }
         if (smooth)
         {
             temp = bmp;
             bmp = SmoothEdges(temp);
             temp.Dispose();
         }
         yield return bmp; // me likes ;D
     }
 }
 // TODO: (above)
 public void InsertImages(IEnumerable<Bitmap> bmp, int pos, bool opacify, bool transparent, bool smooth, SizingCallback resolve)
 {
     EnsureUndisposed();
     int count = frames.Count;
     int i = pos;
     foreach (Bitmap b in bmp)
     {
         frames.InsertRange(pos, CreateFrames(b, opacify, transparent, smooth, resolve));
         pos += frames.Count - count;
         count = frames.Count;
     }
     for (; i < pos; i++)
         ComputeBoundingBox(i);
 }
 public void InsertImage(Bitmap bmp, int pos, bool opacify, bool transparent, bool smooth, SizingCallback resolve)
 {
     EnsureUndisposed();
     int i = frames.Count;
     frames.InsertRange(pos, CreateFrames(bmp, opacify, transparent, smooth, resolve));
     for (; i < frames.Count; i++)
         ComputeBoundingBox(i);
 }
 // TODO: make a class that only resolves the sizing once, also use in InsertImages
 public void AddImages(IEnumerable<Bitmap> bmp, bool opacify, bool transparent, bool smooth, SizingCallback resolve)
 {
     EnsureUndisposed();
     int i = frames.Count;
     foreach (Bitmap b in bmp)
         frames.AddRange(CreateFrames(b, opacify, transparent, smooth, resolve));
     for (; i < frames.Count; i++)
         ComputeBoundingBox(i);
 }