Prevent OutOfMemoryException With AForge and Graphics.FromImage.DrawImage

不打扰是莪最后的温柔 提交于 2019-12-11 03:43:16

问题


I have written a code to allow the user to start and stop a feed from their webcam. I have used AForge.NET's NewFrameEventArgs to update a PictureBox with the new frame each time it changes. Everything works perfectly however whenever I start the feed, the RAM usage on my computer slowly goes up until an OutOfMemoryException occurs.

Please could you help me find out how to clear or flush this somehow. When I get the exception, it occurs at the bottom of the code in ScaleImage:

System.Drawing.Graphics.FromImage(newScaledImage).DrawImage(image, 0, 0, newWidth, newHeight);

My code so far:

using System;
using System.Windows.Forms;
using System.Drawing;
using System.Drawing.Imaging;
using AForge.Video;
using AForge.Video.DirectShow;

namespace WebCameraCapture
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private VideoCaptureDevice FinalFrame;
        System.Drawing.Bitmap fullResClone;

        void FinalFrame_NewFrame(object sender, NewFrameEventArgs eventArgs)
        {
            pictureBox1.Image = ScaleImage((Bitmap)eventArgs.Frame.Clone(), 640, 480);
        }

        private void btn_startCapture_Click(object sender, EventArgs e)
        {
            FinalFrame = new VideoCaptureDevice(CaptureDevice[comboBox1.SelectedIndex].MonikerString);//Specified web cam and its filter moniker string.
            FinalFrame.NewFrame += new NewFrameEventHandler(FinalFrame_NewFrame);
            FinalFrame.Start();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            CaptureDevice = new FilterInfoCollection(FilterCategory.VideoInputDevice);
            foreach (FilterInfo Device in CaptureDevice) { comboBox1.Items.Add(Device.Name); }

            comboBox1.SelectedIndex = 0; //Default index.
            FinalFrame = new VideoCaptureDevice();
        }

        //This ScaleImage is where the OutOfMemoryException occurs.
        public static System.Drawing.Image ScaleImage(System.Drawing.Image image, int maxWidth, int maxHeight) //Changes the height and width of the image to make sure it fits the PictureBox.
        {
            var ratioX = (double)maxWidth / image.Width;
            var ratioY = (double)maxHeight / image.Height;
            var ratio = Math.Min(ratioX, ratioY);

            var newWidth = (int)(image.Width * ratio);
            var newHeight = (int)(image.Height * ratio);

            var newScaledImage = new Bitmap(newWidth, newHeight);
            System.Drawing.Graphics.FromImage(newScaledImage).DrawImage(image, 0, 0, newWidth, newHeight); // <<<< RIGHT HERE
            return newScaledImage;
        }
    }
}

回答1:


You need to dispose the previous image (as long as it is not null) before you add the new scaled image.

void FinalFrame_NewFrame(object sender, NewFrameEventArgs eventArgs)
{
    if (pictureBox1.Image != null) { pictureBox1.Image.Dispose(); }

    Bitmap tempBitmap = (Bitmap)eventArgs.Frame.Clone();
    pictureBox1.Image = ScaleImage(tempBitmap, 640, 480);
    tempBitmap.Dispose();
}

Question: Is it really necessary to create a clone of the input image? What exactly does eventArgs.Frame reference? (I don't have AForge.)



来源:https://stackoverflow.com/questions/27758731/prevent-outofmemoryexception-with-aforge-and-graphics-fromimage-drawimage

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!