From e8a6cfb6722c00ed2ccb989777891b84482ba31f Mon Sep 17 00:00:00 2001 From: "Valeriano A.R" Date: Mon, 5 Nov 2018 00:13:45 +0100 Subject: [PATCH] Webcam: Buffer some frames to avoid garbage accumulation. --- VAR.Toolbox/Code/DirectShow/ISampleGrabber.cs | 2 +- .../Code/DirectShow/ISampleGrabberCB.cs | 2 +- VAR.Toolbox/Code/Webcam.cs | 27 +++++++++++++------ 3 files changed, 21 insertions(+), 10 deletions(-) diff --git a/VAR.Toolbox/Code/DirectShow/ISampleGrabber.cs b/VAR.Toolbox/Code/DirectShow/ISampleGrabber.cs index e60bb0a..2069d68 100644 --- a/VAR.Toolbox/Code/DirectShow/ISampleGrabber.cs +++ b/VAR.Toolbox/Code/DirectShow/ISampleGrabber.cs @@ -8,7 +8,7 @@ namespace VAR.Toolbox.Code.DirectShow /// individual media samples as they move through the filter graph. /// /// - [ComImport, + [ComImport, Guid("6B652FFF-11FE-4FCE-92AD-0266B5D7C78F"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown)] internal interface ISampleGrabber diff --git a/VAR.Toolbox/Code/DirectShow/ISampleGrabberCB.cs b/VAR.Toolbox/Code/DirectShow/ISampleGrabberCB.cs index f1ffa65..536faab 100644 --- a/VAR.Toolbox/Code/DirectShow/ISampleGrabberCB.cs +++ b/VAR.Toolbox/Code/DirectShow/ISampleGrabberCB.cs @@ -7,7 +7,7 @@ namespace VAR.Toolbox.Code.DirectShow /// The interface provides callback methods for the method. /// /// - [ComImport, + [ComImport, Guid("0579154A-2B53-4994-B0D0-E773148EFF85"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown)] internal interface ISampleGrabberCB diff --git a/VAR.Toolbox/Code/Webcam.cs b/VAR.Toolbox/Code/Webcam.cs index 6268b51..c8bb66f 100644 --- a/VAR.Toolbox/Code/Webcam.cs +++ b/VAR.Toolbox/Code/Webcam.cs @@ -252,12 +252,6 @@ namespace VAR.Toolbox.Code public event NewFrameEventHandler NewFrame; - private void OnNewFrame(Bitmap frame) - { - if (NewFrame != null) - NewFrame(this, frame); - } - #endregion NewFrameEvent #region Grabber @@ -266,9 +260,26 @@ namespace VAR.Toolbox.Code { private Webcam _parent; + private Bitmap[] _frames = null; + private int _numFrames = 10; + private int _currentFrameIndex = -1; + public Grabber(Webcam parent) { _parent = parent; + _frames = new Bitmap[_numFrames]; + } + + private Bitmap GetNextFrame() + { + _currentFrameIndex = (_currentFrameIndex + 1) % _numFrames; + Bitmap currentBitmap = _frames[_currentFrameIndex]; + if (currentBitmap == null || currentBitmap?.Width != _parent.width || currentBitmap?.Height != _parent.height) + { + currentBitmap = new Bitmap(_parent.width, _parent.height, PixelFormat.Format24bppRgb); + _frames[_currentFrameIndex] = currentBitmap; + } + return currentBitmap; } public int SampleCB(double sampleTime, IntPtr sample) @@ -281,7 +292,7 @@ namespace VAR.Toolbox.Code if (_parent.NewFrame != null) { // create new image - Bitmap _image = new Bitmap(_parent.width, _parent.height, PixelFormat.Format24bppRgb); + Bitmap _image = GetNextFrame(); Rectangle _imageRect = new Rectangle(0, 0, _parent.width, _parent.height); // lock bitmap data @@ -311,7 +322,7 @@ namespace VAR.Toolbox.Code _image.UnlockBits(imageData); // notify parent - _parent.OnNewFrame(_image); + _parent.NewFrame?.Invoke(this, _image); } return 0;