| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163 |
- using System;
- using System.Runtime.InteropServices;
- using System.Text;
- namespace AutoFocusTool.Camera
- {
- /// <summary>
- /// Microview MVC2000 相机封装。精简自原工程 aivfo_ccd\Util\Camera.cs +
- /// ivf_tl_CameraHelper\Camera.cs,只保留自动对焦测试程序需要的能力:
- /// 连接 / 采集模式 / 抓单帧 / 调曝光增益 / 取像素 / 转 WPF 位图 / 序列号。
- ///
- /// 重要:所有原生调用用同一把锁串行化(SDK 非线程安全)。
- /// 多舱室共用同一 SDK,跨相机操作也走这把全局锁。
- /// </summary>
- public class Camera : IDisposable
- {
- private static readonly object Locker = new object();
- private readonly int _width;
- private readonly int _height;
- private int _index;
- private int _exposure;
- private CapInfoStruct _capInfo;
- private IntPtr _hImager; // MV_Usb2Init 返回的设备句柄
- private IntPtr _pDest; // RGB 输出缓冲(width*height*3)
- public int Index => _index;
- public int Width => _width;
- public int Height => _height;
- public int Exposure => _exposure;
- public string SerialNumber { get; private set; } = "";
- public bool IsInit { get; private set; }
- public bool IsStart { get; private set; }
- /// <param name="index">相机枚举索引 0..9(MV_Usb2Init 用)</param>
- /// <param name="width">分辨率宽,默认 1600</param>
- /// <param name="height">分辨率高,默认 1200</param>
- /// <param name="exposure">曝光时间,单位 100us</param>
- public Camera(int index, int width = 1600, int height = 1200, int exposure = 400)
- {
- _index = index;
- _width = width;
- _height = height;
- _exposure = exposure;
- _pDest = Marshal.AllocCoTaskMem(_width * _height * 3);
- }
- /// <summary>初始化相机。执行后需立即 SetOpMode 才能抓图。返回 0 成功。</summary>
- public int Init(byte redGain = 25, byte greenGain = 14, byte blueGain = 25)
- {
- _capInfo.Buffer = Marshal.AllocCoTaskMem(_width * _height * 3);
- _capInfo.Width = _width;
- _capInfo.Height = _height;
- _capInfo.HorizontalOffset = 0;
- _capInfo.VerticalOffset = 0;
- _capInfo.Exposure = _exposure;
- _capInfo.Gain = new byte[] { redGain, greenGain, blueGain };
- _capInfo.Control = 0x04;
- _capInfo.Reserved = new byte[8];
- int result;
- lock (Locker)
- {
- result = MVCAPI.MV_Usb2Init("MVC2000", out _index, ref _capInfo, out _hImager);
- }
- IsInit = result == 0;
- return result;
- }
- /// <summary>设置采集模式:0=拍照(单帧,对焦用),1=实时图像。返回 0 成功。</summary>
- public int SetOpMode(byte mode = 0, bool strobe = false)
- {
- if (!IsInit) return -1;
- int result;
- lock (Locker)
- {
- result = MVCAPI.MV_Usb2SetOpMode(_hImager, mode, strobe);
- }
- IsStart = result == 0;
- return result;
- }
- /// <summary>读相机序列号到 SerialNumber。返回 0 成功。</summary>
- public int ReadSerial()
- {
- try
- {
- lock (Locker)
- {
- var sb = new StringBuilder(125);
- int r = MVCAPI.MV_Usb2GetSerial(_hImager, sb);
- SerialNumber = sb.ToString();
- return r;
- }
- }
- catch { return -2; }
- }
- /// <summary>抓取一帧 RGB 到内部缓冲。返回 0 成功,之后用 GetSourceBuffer / GetBitmapSource 取。</summary>
- public int GrabRgb()
- {
- if (!IsStart) return -1;
- lock (Locker)
- {
- return MVCAPI.MV_Usb2GetRgbData(_hImager, ref _capInfo, _pDest);
- }
- }
- /// <summary>设置曝光时间(单位 100us)。返回 0 成功。</summary>
- public int SetExposure(int exposure100us)
- {
- _exposure = exposure100us;
- _capInfo.Exposure = exposure100us;
- lock (Locker)
- {
- return MVCAPI.MV_Usb2SetPartOfCapInfo(_hImager, ref _capInfo);
- }
- }
- /// <summary>设置 RGB 三通道增益(0-255)。返回 0 成功。</summary>
- public int SetGain(byte red, byte green, byte blue)
- {
- if (_capInfo.Gain == null) _capInfo.Gain = new byte[3];
- _capInfo.Gain[0] = red;
- _capInfo.Gain[1] = green;
- _capInfo.Gain[2] = blue;
- lock (Locker)
- {
- return MVCAPI.MV_Usb2SetPartOfCapInfo(_hImager, ref _capInfo);
- }
- }
- /// <summary>取当前帧像素(24bpp BGR,width*height*3 字节,未翻转)。</summary>
- public byte[] GetSourceBuffer()
- {
- byte[] buf = new byte[_width * _height * 3];
- Marshal.Copy(_pDest, buf, 0, buf.Length);
- return buf;
- }
- /// <summary>卸载相机。</summary>
- public int UnInit()
- {
- int result = 0;
- lock (Locker)
- {
- if (_hImager != IntPtr.Zero)
- result = MVCAPI.MV_Usb2Uninit(ref _hImager);
- }
- IsInit = false;
- IsStart = false;
- return result;
- }
- public void Dispose()
- {
- try { UnInit(); } catch { }
- if (_pDest != IntPtr.Zero) { Marshal.FreeCoTaskMem(_pDest); _pDest = IntPtr.Zero; }
- if (_capInfo.Buffer != IntPtr.Zero) { Marshal.FreeCoTaskMem(_capInfo.Buffer); _capInfo.Buffer = IntPtr.Zero; }
- }
- }
- }
|