C# 获取海康相机

这篇具有很好参考价值的文章主要介绍了C# 获取海康相机。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

一、简介


由于工作关系,本人最近使用到了海康的网口及USB3.0接口的工业相机。现将相关内容进行整理记录。

二、开发环境


64位VS2013 +C#
Halcon12
海康MVS3.0.0

三、项目搭建

1、添加引用

引用海康相机动态库(MvCameraControl.Net.dll)
在VS项目文件中添加添加引用,如下图

引用MVS安装目录下MVS\Development\DotNet\MvCameraControl.Net.dll这个文件。


2、创建相机类


鼠标右键单击工程项目–添加–类,选择“类”,输入类的名称,例如Hikvision,点击右下角的“添加”。
在项目中使用海康相机时,为便于程序编写,可引入如下的命名空间:
using MvCamCtrl.NET;


1.创建需要用到的全局变量
public MyCamera myCamera;//相机对象
private MyCamera.MV_CC_DEVICE_INFO_LIST deviceList;//设备列表
private MyCamera.MV_CC_DEVICE_INFO deviceInfo;//设备对象
private string seriesStr;//接收相机序列号
private MyCamera.MVCC_INTVALUE stParam;//用于接收特定的参数
//为读取、保存图像创建的数组
UInt32 m_nBufSizeForDriver = 4096 * 3000;
byte[] m_pBufForDriver = new byte[4096 * 3000];
UInt32 m_nBufSizeForSaveImage = 4096 * 3000 * 3 + 3000;
byte[] m_pBufForSaveImage = new byte[4096 * 3000 * 3 + 3000];

创建相关函数
1.创建构造函数

//在构造函数中实例化设备列表对象
public Hikvision()
 {
     deviceList = new MyCamera.MV_CC_DEVICE_INFO_LIST();
 }
2.创建改变相机IP的函数
//成功返回0失败返回-1
//调用函数时可以传入需要改变的目标IP,如过没有传入则将相机IP设置为其所连接的网卡地址+1或-1
public int changeIP(string IP = "")
{
   try
   {
         //获取相机相关信息,例如相机所连接网卡的网址
          IntPtr buffer = Marshal.UnsafeAddrOfPinnedArrayElement(deviceInfo.SpecialInfo.stGigEInfo, 0);
          MyCamera.MV_GIGE_DEVICE_INFO gigeInfo = (MyCamera.MV_GIGE_DEVICE_INFO)Marshal.PtrToStructure(buffer, typeof(MyCamera.MV_GIGE_DEVICE_INFO));
          IPAddress cameraIPAddress;
          string tempStr = "";
          if (IP.Trim().Equals("") || !(IPAddress.TryParse(IP, out cameraIPAddress)))
          {
               //当前网卡的IP地址
               UInt32 nNetIp1 = (gigeInfo.nNetExport & 0xFF000000) >> 24;
               UInt32 nNetIp2 = (gigeInfo.nNetExport & 0x00FF0000) >> 16;
               UInt32 nNetIp3 = (gigeInfo.nNetExport & 0x0000FF00) >> 8;
               UInt32 nNetIp4 = (gigeInfo.nNetExport & 0x000000FF);
               //根据网卡IP设定相机IP,如果网卡ip第四位小于252,则相机ip第四位+1,否则相机IP第四位-1
              UInt32 cameraIp1 = nNetIp1;
              UInt32 cameraIp2 = nNetIp2;
              UInt32 cameraIp3 = nNetIp3;
              UInt32 cameraIp4 = nNetIp4;
              if (nNetIp4 < 252)
              {
                    cameraIp4++;
              }
              else
              {
                     cameraIp4--;
              }
              tempStr = cameraIp1 + "." + cameraIp2 + "." + cameraIp3 + "." + cameraIp4;
          }
          else
          {
                tempStr = IP;
          }
          IPAddress.TryParse(tempStr, out cameraIPAddress);
          long cameraIP = IPAddress.NetworkToHostOrder(cameraIPAddress.Address);
          //设置相机掩码
          uint maskIp1 = (gigeInfo.nCurrentSubNetMask & 0xFF000000) >> 24;
          uint maskIp2 = (gigeInfo.nCurrentSubNetMask & 0x00FF0000) >> 16;
          uint maskIp3 = (gigeInfo.nCurrentSubNetMask & 0x0000FF00) >> 8;
          uint maskIp4 = (gigeInfo.nCurrentSubNetMask & 0x000000FF);
          IPAddress subMaskAddress;
          tempStr = maskIp1 + "." + maskIp2 + "." + maskIp3 + "." + maskIp4;
          IPAddress.TryParse(tempStr, out subMaskAddress);
          long maskIP = IPAddress.NetworkToHostOrder(subMaskAddress.Address);
          //设置网关
          uint gateIp1 = (gigeInfo.nDefultGateWay & 0xFF000000) >> 24;
          uint gateIp2 = (gigeInfo.nDefultGateWay & 0x00FF0000) >> 16;
          uint gateIp3 = (gigeInfo.nDefultGateWay & 0x0000FF00) >> 8;
          uint gateIp4 = (gigeInfo.nDefultGateWay & 0x000000FF);
          IPAddress gateAddress;
          tempStr = gateIp1 + "." + gateIp2 + "." + gateIp3 + "." + gateIp4;
          IPAddress.TryParse(tempStr, out gateAddress);
          long gateIP = IPAddress.NetworkToHostOrder(gateAddress.Address);

          int temp = myCamera.MV_GIGE_ForceIpEx_NET((UInt32)(cameraIP >> 32), (UInt32)(maskIP >> 32), (UInt32)(gateIP >> 32));//执行更改相机IP的命令
          if (temp == 0)
                //强制IP成功
                return 0;
          //强制IP失败
          return -1;
     }
     catch
     {
          return -1;
     }
 }
3.创建相机连接函数
public int connectCamera(string id)//连接相机,返回-1为失败,0为成功
{
    this.seriesStr = id;
    string m_SerialNumber = "";//接收设备返回的序列号
    int temp;//接收命令执行结果
    myCamera = new MyCamera();
    try
    {
        temp = MyCamera.MV_CC_EnumDevices_NET(MyCamera.MV_GIGE_DEVICE | MyCamera.MV_USB_DEVICE, ref deviceList);//更新设备列表
        if (temp != 0)
        {
            //设备更新成功接收命令的返回值为0,返回值不为0则为异常
            return -1;
        }

        //强制相机IP
        for (int i = 0; i < deviceList.nDeviceNum; i++)
        {
        
        /*******该部分用于获取相机名称、序列号等,从而对指定的相机进行IP更改******/
           //更改IP的函数中也有该部分,重叠部分程序可进行相应的简化,本文暂不做处理
        
            deviceInfo = (MyCamera.MV_CC_DEVICE_INFO)Marshal.PtrToStructure(deviceList.pDeviceInfo[i], typeof(MyCamera.MV_CC_DEVICE_INFO));//获取设备信息
            IntPtr buffer = Marshal.UnsafeAddrOfPinnedArrayElement(deviceInfo.SpecialInfo.stGigEInfo, 0);
            MyCamera.MV_GIGE_DEVICE_INFO gigeInfo = (MyCamera.MV_GIGE_DEVICE_INFO)Marshal.PtrToStructure(buffer, typeof(MyCamera.MV_GIGE_DEVICE_INFO));
            
        /*****************************************************************/
        
             m_SerialNumber = gigeInfo.chUserDefinedName;
             if(deviceInfo.nTLayerType == MyCamera.MV_GIGE_DEVICE)
             {
               //判断是否为网口相机
                if (seriesStr.Equals(m_SerialNumber))
                {
                   //如果相机用户名正确则修改IP
                   temp = myCamera.MV_CC_CreateDevice_NET(ref deviceInfo);//更改IP前需要创建设备对象
                   forceIP();
                }
             }
         }
       //更改IP后需要重新刷新设备列表,否则打开相机时会报错
       temp = MyCamera.MV_CC_EnumDevices_NET(MyCamera.MV_GIGE_DEVICE | MyCamera.MV_USB_DEVICE, ref deviceList);//更新设备列表
       for (int i = 0; i < deviceList.nDeviceNum; i++)
       {
            deviceInfo = (MyCamera.MV_CC_DEVICE_INFO)Marshal.PtrToStructure(deviceList.pDeviceInfo[i], typeof(MyCamera.MV_CC_DEVICE_INFO));//获取设备
            if (deviceInfo.nTLayerType == MyCamera.MV_GIGE_DEVICE)
            {
                 IntPtr buffer = Marshal.UnsafeAddrOfPinnedArrayElement(deviceInfo.SpecialInfo.stGigEInfo, 0);
                  MyCamera.MV_GIGE_DEVICE_INFO gigeInfo = (MyCamera.MV_GIGE_DEVICE_INFO)Marshal.PtrToStructure(buffer, typeof(MyCamera.MV_GIGE_DEVICE_INFO));
                  //m_SerialNumber = gigeInfo.chSerialNumber;//获取序列号
                  m_SerialNumber = gigeInfo.chUserDefinedName;//获取用户名
           }
           else if (deviceInfo.nTLayerType == MyCamera.MV_USB_DEVICE)
           {
                  IntPtr buffer = Marshal.UnsafeAddrOfPinnedArrayElement(deviceInfo.SpecialInfo.stUsb3VInfo, 0);
                  MyCamera.MV_USB3_DEVICE_INFO usbInfo = (MyCamera.MV_USB3_DEVICE_INFO)Marshal.PtrToStructure(buffer, typeof(MyCamera.MV_USB3_DEVICE_INFO));
                  m_SerialNumber = usbInfo.chUserDefinedName;
          }
          if (seriesStr.Equals(m_SerialNumber))
          {
               temp = myCamera.MV_CC_CreateDevice_NET(ref deviceInfo);
               if (MyCamera.MV_OK != temp)
               {
                    //创建相机失败
                    return -1;
               }
               temp = myCamera.MV_CC_OpenDevice_NET();//
               if (MyCamera.MV_OK != temp)
               {
                    //打开相机失败
                    return -1;
                }
                return 0;
         }
         continue;
       }
   }
   catch
   {
        return -1;
   }
   return 0;
}
4.创建开始采集、停止采集、关闭相机函数
 public int startCamera()//相机开始采集,返回0为成功,-1为失败
 {
     int temp = myCamera.MV_CC_StartGrabbing_NET();
     if (MyCamera.MV_OK != temp)
          return -1;
     return 0;
}

public int stopCamera()//停止相机采集,返回0为成功,-1为失败
{
     int temp = myCamera.MV_CC_StopGrabbing_NET();
     if (MyCamera.MV_OK != temp )
           return -1;
     return 0;
}

 public int closeCamera()//关闭相机,返回0为成功,-1为失败
 {
      int temp = stopCamera();//停止相机采集
       if (MyCamera.MV_OK != temp )
           return -1;
      temp = myCamera.MV_CC_CloseDevice_NET();
       if (MyCamera.MV_OK != temp )
           return -1;
      temp = myCamera.MV_CC_DestroyDevice_NET();
       if (MyCamera.MV_OK != temp )
           return -1;
       return 0;
 }
5.创建发送软触发函数
//发送成功返回0,失败返回-1
public int softTrigger()
{
     int temp = myCamera.MV_CC_SetCommandValue_NET("TriggerSoftware");
     if (MyCamera.MV_OK != temp )
           return -1;
      return 0;
 }
6.创建读取图像函数
函数返回Halcon图像库可以处理的Himage格式。
如何添加halcon图像库请自行百度,网上教程非常多
//读取成功返回Himage图像,失败返回NULL
public HImage readImage()
{
    UInt32 nPayloadSize = 0;
    int temp = myCamera.MV_CC_GetIntValue_NET("PayloadSize", ref stParam);
    if (MyCamera.MV_OK != temp)
    {
        return null;
    }
    nPayloadSize = stParam.nCurValue;
    if (nPayloadSize > m_nBufSizeForDriver)
    {
        m_nBufSizeForDriver = nPayloadSize;
        m_pBufForDriver = new byte[m_nBufSizeForDriver];
        m_nBufSizeForSaveImage = m_nBufSizeForDriver * 3 + 2048;
        m_pBufForSaveImage = new byte[m_nBufSizeForSaveImage];
     }
     IntPtr pData = Marshal.UnsafeAddrOfPinnedArrayElement(m_pBufForDriver, 0);
     MyCamera.MV_FRAME_OUT_INFO_EX stFrameInfo = new MyCamera.MV_FRAME_OUT_INFO_EX();
     temp = myCamera.MV_CC_GetOneFrameTimeout_NET(pData, m_nBufSizeForDriver, ref stFrameInfo, 1000);//获取一帧图像,超时时间设置为1000
     if (MyCamera.MV_OK != temp)
     {
         return null;
     }
     HImage image = new HImage();
     if (IsMonoData(stFrameInfo.enPixelType))//判断是否为黑白图像
     {
          //如果是黑白图像,则利用Halcon图像库中的GenImage1算子来构建图像
          image .GenImage1("byte", (int)stFrameInfo.nWidth, (int)stFrameInfo.nHeight, pData);
     }
     else
     {
          if (stFrameInfo.enPixelType == MyCamera.MvGvspPixelType.PixelType_Gvsp_RGB8_Packed)
          {
              //如果彩色图像是RGB8格式,则可以直接利用GenImageInterleaved算子来构建图像
              image .GenImageInterleaved(pData, "rgb", (int)stFrameInfo.nWidth, (int)stFrameInfo.nHeight, 0, "byte", (int)stFrameInfo.nWidth, (int)stFrameInfo.nHeight, 0, 0, -1, 0);
          }
          else
          {
               //如果彩色图像不是RGB8格式,则需要将图像格式转换为RGB8。
               IntPtr pBufForSaveImage = IntPtr.Zero;
               if (pBufForSaveImage == IntPtr.Zero)
               {
                   pBufForSaveImage = Marshal.AllocHGlobal((int)(stFrameInfo.nWidth * stFrameInfo.nHeight * 3 + 2048));
               }
               MyCamera.MV_PIXEL_CONVERT_PARAM stConverPixelParam = new MyCamera.MV_PIXEL_CONVERT_PARAM();
               stConverPixelParam.nWidth = stFrameInfo.nWidth;
               stConverPixelParam.nHeight = stFrameInfo.nHeight;
               stConverPixelParam.pSrcData = pData;
               stConverPixelParam.nSrcDataLen = stFrameInfo.nFrameLen;
               stConverPixelParam.enSrcPixelType = stFrameInfo.enPixelType;
               stConverPixelParam.enDstPixelType = MyCamera.MvGvspPixelType.PixelType_Gvsp_RGB8_Packed;//在此处选择需要转换的目标类型
               stConverPixelParam.pDstBuffer = pBufForSaveImage;
               stConverPixelParam.nDstBufferSize = (uint)(stFrameInfo.nWidth * stFrameInfo.nHeight * 3 + 2048);
               myCamera.MV_CC_ConvertPixelType_NET(ref stConverPixelParam);
               image .GenImageInterleaved(pBufForSaveImage, "rgb", (int)stFrameInfo.nWidth, (int)stFrameInfo.nHeight, 0, "byte", (int)stFrameInfo.nWidth, (int)stFrameInfo.nHeight, 0, 0, -1, 0);
               //释放指针
               Marshal.FreeHGlobal(pBufForSaveImage);
             }
        }
        return image ;
}
7.在海康MVS安装目录下MVS\Development\Documentations\MvCameraNode.xlsx是一个关于参数设置的文档,可以参考MVS并结合该文档进行相应参数的设置,非常方便。

8.实例化相机对象,并通过软触发采集图像
 Hikvision camera = new Hikvision();//创建相机对象并实例化
 camera.connectCamera("123456");//连接相机,传入相机序列号123456
 camera.startCamera();//开启相机采集
 camera.setExposureTime(10000);//设置曝光时间为10ms
 camera.softTrigger();//发送软触发采集图像
 Himage image=camera.readImage();//获取采集到且转换后的图像
 camera.stopCamera();//停止相机采集
 camera.closeCamera();//关闭相机


————————————————
版权声明:本文为CSDN博主「大_樱_桃」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/biggestcherry/article/details/87011094文章来源地址https://www.toymoban.com/news/detail-738960.html

到了这里,关于C# 获取海康相机的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • C# 获取海康相机

    一、简介 由于工作关系,本人最近使用到了海康的网口及USB3.0接口的工业相机。现将相关内容进行整理记录。 二、开发环境 64位VS2013 +C# Halcon12 海康MVS3.0.0 三、项目搭建 1、添加引用 引用海康相机动态库(MvCameraControl.Net.dll) 在VS项目文件中添加添加引用,如下图 引用MVS安装

    2024年02月06日
    浏览(34)
  • C# 开源SDK 工业相机库 调用海康相机 大恒相机

    c# 相机库,含海康、大恒品牌2D相机的常用功能。 底层采用回调+信号量模式封装 ,最大程度减小线程资源,提高采图效率。 开源地址 :https://gitee.com/laomaogu/mgcamctrl 现只兼容了大恒和海康,都是常用的 其他相机,看我老板啥时候换品牌吧,或者换老板? 当然如果小伙伴感兴

    2024年04月26日
    浏览(49)
  • C# 上位机之海康相机开发(SDK)

    发现工作中好多计算机视觉上位机项目都用海康相机,为了能够更好的学习和工作,我自己依据同事的源码和网上的一些总结编写本博客。通过本次学习,让我明白一点,无论学习什么技术都要学会自己看技术文档,而不是第一时间上网找源码。以工业相机SDK使用说明.chm为例

    2024年02月03日
    浏览(52)
  • 机器视觉海康工业相机SDK参数设置获取

    视觉人机器视觉培训-缺陷检测项目-食品行业草鸡蛋外观检测 相机参数类型可分为六类,除 command 参数外,每一类都有其对应的设置与获取函数接口。 表 1 参数类型及对应函数接口介绍 *详细函数接口可参考 SDK 手册: ​C:Program Files (x86)MVSDevelopmentDocumentations 相机参数类型

    2024年02月07日
    浏览(89)
  • 海康工业相机SDK基于C#关于IO输入输出的控制

    海康工业相机功能模块sdk提供了很多相机的接口,本文主要介绍下相机的io相关的控制。例如在通过io输入触发相机拍照。通过io输出传递拍照成功,或者存图成功的信号等。 IO输入的主要作用就是,相机通过IO管脚,收到1个IO信号,来触发相机拍照; 触发模式:TriggerMode设置

    2024年02月03日
    浏览(218)
  • Baumer工业相机堡盟工业相机如何通过BGAPI SDK获取相机当前实时帧率(C#)

    ​ Baumer工业相机堡盟相机是一种高性能、高质量的工业相机,可用于各种应用场景,如物体检测、计数和识别、运动分析和图像处理。 Baumer的万兆网相机拥有出色的图像处理性能,可以实时传输高分辨率图像。此外,该相机还具有快速数据传输、低功耗、易于集成以及高度

    2024年02月15日
    浏览(43)
  • Baumer工业相机堡盟工业相机如何通过NEOAPI SDK获取相机当前实时帧率(C#)

    ​ Baumer工业相机堡盟相机是一种高性能、高质量的工业相机,可用于各种应用场景,如物体检测、计数和识别、运动分析和图像处理。 Baumer的万兆网相机拥有出色的图像处理性能,可以实时传输高分辨率图像。此外,该相机还具有快速数据传输、低功耗、易于集成以及高度

    2024年02月04日
    浏览(48)
  • Baumer工业相机堡盟工业相机如何通过BGAPI SDK获取相机当前数据吞吐量(C#)

    ​ Baumer工业相机堡盟相机是一种高性能、高质量的工业相机,可用于各种应用场景,如物体检测、计数和识别、运动分析和图像处理。 Baumer的万兆网相机拥有出色的图像处理性能,可以实时传输高分辨率图像。此外,该相机还具有快速数据传输、低功耗、易于集成以及高度

    2024年02月14日
    浏览(58)
  • Baumer工业相机堡盟工业相机如何通过NEOAPI SDK获取相机当前数据吞吐量(C#)

    ​ Baumer工业相机堡盟相机是一种高性能、高质量的工业相机,可用于各种应用场景,如物体检测、计数和识别、运动分析和图像处理。 Baumer的万兆网相机拥有出色的图像处理性能,可以实时传输高分辨率图像。此外,该相机还具有快速数据传输、低功耗、易于集成以及高度

    2024年02月03日
    浏览(48)
  • Baumer工业相机堡盟工业相机如何通过BGAPI SDK获取每张图像的微秒时间和FrameID(C#)

    BGAPI SDK获取图像微秒级时间和FrameID Baumer工业相机 Baumer工业相机FrameID技术背景 一、FrameID是什么? 二、使用BGAPI SDK获取图像微秒时间和FrameID步骤 1.获取SDK图像微秒级时间 2.获取SDK图像FrameID Baumer工业相机使用微秒级时间和FrameID保存的用处 Baumer工业相机使用微秒级时间和Fra

    2024年02月01日
    浏览(37)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包