领胜LDS 键盘AOI检测项目
src/Bro.Common.Device/DeviceBase/CameraBase.cs
@@ -71,7 +71,7 @@
        #endregion
        #region 图片相关
        public event Action<CameraBase, Bitmap, string> OnImageUpdated;
        public Action<CameraBase, Bitmap, string> OnImageUpdated;
        public Action<CameraBase, HObject, string> OnHImageOutput { get; set; }
        public event Action OnCameraOpModeChanged;
@@ -141,22 +141,21 @@
        /// </summary>
        /// <returns></returns>
        public abstract void Snapshot();
        public abstract IImageSet Snapshot(IOperationConfig config);
        public virtual ImageSet Snapshot(IOperationConfig config)
        public virtual void InitialImageSet(IImageSet set, ImageSaveOption saveOption)
        {
            OpMode = CameraOpMode.SingleSnapShot;
            ImageSet set = new ImageSet();
            CameraOprerationConfigBase opConfig = config as CameraOprerationConfigBase;
            set.ImageSaveOption.DataFrom(opConfig.ImageSaveOption);
            //CameraOprerationConfigBase opConfig = config as CameraOprerationConfigBase;
            set.ImageSaveOption.DataFrom(saveOption);
            set.IsOriginSaved = !set.ImageSaveOption.IsSaveOriginImage;
            set.IsFitSaved = !set.ImageSaveOption.IsSaveFitImage;
            set.IsAddtionalSaved = !string.IsNullOrWhiteSpace(set.ImageSaveOption.AddtionalSaveType);
            set.IsAddtionalSaved = string.IsNullOrWhiteSpace(set.ImageSaveOption.AddtionalSaveType);
            set.OnImageSetTimeout += ImageSet_OnImageSetTimeout;
            _imageSetList.Add(set);
            return set;
            _imageSetList.Add(set);
        }
        /// <summary>
@@ -172,17 +171,17 @@
        #endregion
        #region 基元处理
        public event Action<CameraBase, List<IShapeElement>, string> OnElementsUpdated;
        public Action<CameraBase, List<IShapeElement>, string> OnElementsUpdated;
        #endregion
        #region 图片缓存/保存
        readonly ConcurrentBag<ImageSet> _imageSetList = new ConcurrentBag<ImageSet>();
        public readonly ConcurrentBag<IImageSet> _imageSetList = new ConcurrentBag<IImageSet>();
        public void NewImageSet(ImageSet set)
        public void NewImageSet(IImageSet set)
        {
            set.IsOriginSaved = !set.ImageSaveOption.IsSaveOriginImage;
            set.IsFitSaved = !set.ImageSaveOption.IsSaveFitImage;
            set.IsAddtionalSaved = !string.IsNullOrWhiteSpace(set.ImageSaveOption.AddtionalSaveType);
            set.IsAddtionalSaved = string.IsNullOrWhiteSpace(set.ImageSaveOption.AddtionalSaveType);
            set.OnImageSetTimeout += ImageSet_OnImageSetTimeout;
            _imageSetList.Add(set);
        }
@@ -197,12 +196,12 @@
        public virtual async void SaveOriginImage(Bitmap map, Bitmap showImage, string imgSetId)
        {
            Task.Run(() =>
            await Task.Run(() =>
            {
                OnImageUpdated?.Invoke(this, showImage, imgSetId);
            });
            ImageSet set = _imageSetList.FirstOrDefault(u => u.Id == imgSetId);
            IImageSet set = _imageSetList.FirstOrDefault(u => u.Id == imgSetId);
            if (set == null)
                return;
@@ -225,10 +224,6 @@
                        {
                            LogAsync(DateTime.Now, $"{set.Id}原图保存失败", ex.GetExceptionMessage());
                        }
                        //finally
                        //{
                        //    set.IsOriginSaved = true;
                        //}
                    }
                    set.IsOriginSaved = true;
                    ClearImageSet(set);
@@ -241,7 +236,7 @@
            if (eleList.Count > 0)
                OnElementsUpdated?.BeginInvoke(this, eleList, imgSetId, null, null);
            ImageSet set = _imageSetList.FirstOrDefault(u => u.Id == imgSetId);
            IImageSet set = _imageSetList.FirstOrDefault(u => u.Id == imgSetId);
            if (set == null)
                return;
@@ -305,7 +300,7 @@
        {
            await Task.Run(() =>
            {
                ImageSet set = _imageSetList.FirstOrDefault(u => u.Id == imgSetId);
                IImageSet set = _imageSetList.FirstOrDefault(u => u.Id == imgSetId);
                if (set == null)
                    return;
@@ -341,7 +336,7 @@
            });
        }
        private string CheckImageDirectory(string subDir, string prefix)
        protected string CheckImageDirectory(string subDir, string prefix)
        {
            if (string.IsNullOrWhiteSpace(subDir))
            {
@@ -363,7 +358,7 @@
            return imgDir;
        }
        private void SaveImageByNameAndType(Bitmap map, string imageName, ImageFormat imgFormat, string imageDir)
        protected void SaveImageByNameAndType(Bitmap map, string imageName, ImageFormat imgFormat, string imageDir)
        {
            string filePath = Path.Combine(imageDir, $"{imageName}.{imgFormat.ToString().ToLower()}");
            map.Save(filePath, imgFormat);
@@ -371,7 +366,7 @@
        //private Timer clearImageSetTimer = null;
        public void ClearImageSet(ImageSet set)
        public void ClearImageSet(IImageSet set)
        {
            try
            {
@@ -402,7 +397,7 @@
        public void ClearImageSet(string imgSetId)
        {
            ImageSet set = _imageSetList.First(u => u.Id == imgSetId);
            IImageSet set = _imageSetList.First(u => u.Id == imgSetId);
            if (set != null)
                ClearImageSet(set);
        }
@@ -544,10 +539,11 @@
            });
        }
        protected async void Generate16GrayImageByPointer(int width, int height, IntPtr dataPtr, string imgSetId)
        protected async Task Generate16GrayImageByPointer(int width, int height, IntPtr dataPtr, string imgSetId)
        {
            await Task.Run(() =>
            {
                Thread.Sleep(1000);
                int widthIn4 = (int)Math.Ceiling(width / 4.0) * 4;
                Bitmap bmp = new Bitmap(widthIn4, height, PixelFormat.Format48bppRgb);
@@ -575,15 +571,14 @@
                      {
                          int index = (i + 1) % width + widthIn4 * ((i + 1) / width) - 1;
                          showBitmapBuffer[index * 6] = data[i * 2];
                          showBitmapBuffer[index * 6 + 1] = data[i * 2 + 1];
                          showBitmapBuffer[index * 6] = bitmapBuffer[index * 6] = data[i * 2];
                          showBitmapBuffer[index * 6 + 1] = bitmapBuffer[index * 6 + 1] = data[i * 2 + 1];
                      });
                }
                bmp.UnlockBits(bitmapData);
                showImage.UnlockBits(showImageData);
                //showImage.Save(@"D:\1.bmp", ImageFormat.Bmp);
                SaveOriginImage(bmp, showImage, imgSetId);
            });
        }
@@ -838,7 +833,29 @@
        }
    }
    public class ImageSet : IDisposable
    public interface IImageSet : IDisposable
    {
        DateTime InitialTime { get; set; }
        string Id { get; }
        HImage HImage { get; set; }
        Bitmap Image { get; set; }
        object SaveLock { get; set; }
        ImageSaveOption ImageSaveOption { get; set; }
        bool IsOriginSaved { get; set; }
        bool IsFitSaved { get; set; }
        bool IsAddtionalSaved { get; set; }
        event Action<ImageSet> OnImageSetTimeout;
        /// <summary>
        /// 序列化操作的图像信息
        /// </summary>
        string ImageData { get; set; }
    }
    public class ImageSet : IImageSet
    {
        public DateTime InitialTime { get; set; } = DateTime.Now;
@@ -873,7 +890,9 @@
        //public bool IsInvokeSaveNG { get; set; } = false;
        public bool IsAddtionalSaved { get; set; } = false;
        public object SaveLock = new object();
        public object SaveLock { get; set; } = new object();
        public virtual string ImageData { get; set; }
        public event Action<ImageSet> OnImageSetTimeout;
        private Timer autoDisposeTimer = null;
@@ -885,19 +904,19 @@
        public ImageSet()
        {
            autoDisposeTimer = new Timer(OnAutoDispose, null, -1, 10 * 1000);
            autoDisposeTimer = new Timer(OnAutoDispose, null, 10 * 1000, -1);
        }
        public void Dispose()
        public virtual void Dispose()
        {
            autoDisposeTimer.Change(-1, -1);
            autoDisposeTimer.Dispose();
            Image?.Dispose();
            Image = null;
            //Image?.Dispose();
            //Image = null;
            HImage?.Dispose();
            HImage = null;
            //HImage?.Dispose();
            //HImage = null;
        }
        #endregion
    }