MIL图像库的使用——配合图像采集卡

目录

一、软硬件介绍

二、Qt中导入MIL库

三、相机的默认配置,DCF文件的使用

四、MIL和Qt之间的数据转换

4.1 MIL_INT转Int

4.2 QString转MIL中的TEXT

4.3 获取相机采集的图像

4.4 程序运行时间计时器

 4.5 存储图片到硬盘

五 连续采集图像,并在MIL自带显示器上显示

六 外部电压触发采集,方波

七、常用MIL函数

7.1 MIL_TEXT

7.2 MosGetch()

7.3 MdigHalt(MilDigitizer)

7.4 MdigGrab(MilDigitizer, MilImage)

7.5 MappAllocDefault(M_DEFAULT, &MilApplication, &MilSystem,&MilDisplay, &MilDigitizer, &MilImage);

7.6 MdigGrabContinuous(MilDigitizer, MilImage)

7.7 MappFreeDefault(MilApplication, MilSystem, MilDisplay, MilDigitizer, MilImage)

7.8 MbufClear(MilImageDisp, 0x0)

7.9 MdispSelect(MilDisplay, MilImageDisp)

7.10 MdigControl(MilDigitizer, M_GRAB_SCALE, GrabScale)

7.11 MdigInquire(MilDigitizer, M_SIZE_X,&BufSizeX)


参考链接:

梁笔记

一、软硬件介绍

Basler spL4096-140km Camera Link 相机

            

                                          Basler相机

                   

                                          图像采集卡

软件运行平台是Win7 64位电脑,Qt版本是msvc2015 64位  Debug版本。

二、Qt中导入MIL库

需要注意的是,如果你没有购买MIL库,会报错提示。

导入步骤:

将MIL库放在工程目录下,并在pro文件中写入如下代码。

#依赖freeglut库以及头文件
INCLUDEPATH += $$PWD/MIL/Include
LIBS += -L$$PWD/MIL/LIB  -lMil

使用时,在文件中添加如下代码。 

#pragma comment(lib, "mil.lib")
#include <mil.h>

三、相机的默认配置,DCF文件的使用

对相机采集卡的设置在dcf文件中,当程序在初始化各种内存时使用默认时,是按照默认dcf文件进行初始化的。

//分配默认的应用、系统
MappAllocDefault(M_DEFAULT, &MilApplication, &MilSystem, M_NULL, &MilDigitizer, &MilImage);

上面的这句代码,按照默认DCF文件来初始化了应用,系统,相机和图像BUFFER,没有初始化显示器。

注意:如果没有软件配置默认的DCF文件,就会出现即使没有开启相机依然能采到如下图像的情况。这个图像在连续采集的时候,会不断向左移动,亮度从暗到亮不断刷新。

***正确的方法是在MIL Config软件中,配置默认的DCF文件

如下面两张图所示,第一张图是MIL Config的入口(左下角第一行的蓝色字体);第二张图是配置默认的DCF文件(先用官方软件配置好需要用的DCF文件)

 

四、MIL和Qt之间的数据转换

4.1 MIL_INT转Int

MIL_INT BufSizeX=0;
MIL_INT BufSizeY=0;

//获得相机图像的宽度和高度
MdigInquire(MilDigitizer, M_SIZE_X,&BufSizeX);
MdigInquire(MilDigitizer, M_SIZE_Y,&BufSizeY);

//MIL_INT转换为Int类型,并在Qt的控件中显示
int tempintx=BufSizeX;
int tempinty=BufSizeY;
QString tempstr="图像的宽和高:";
tempstr=tempstr+QString::number(tempintx)+"   "+QString::number(tempinty);
ui->DebugText->append(tempstr);

4.2 QString转MIL中的TEXT

//保存图像
ui->DebugText->append("保存第"+QString::number(index)+"张图像");
QString savepath=ui->lineEdit->text();
savepath=savepath.append("/"+QString::number(index));
savepath=savepath.append(".tif");
const wchar_t* savepath_wchar = reinterpret_cast<const wchar_t *>(savepath.utf16());
MbufSave(savepath_wchar,MilImage);

4.3 获取相机采集的图像

//图像数据地址
void  *SrcImageDataPtr = NULL;
void  *PhysicsImagePtr = NULL;
//相机图像的属性信息
MIL_INT SrcImageDataSize=0;
MIL_INT BufSizeX=0;
MIL_INT BufSizeY=0;

//定义图像格式
QImage::Format format = QImage::Format_Indexed8;
int m_iWidth=BufSizeX;
int m_iHeight=BufSizeY;
//定义QImage对象
QImage img = QImage(m_iWidth,m_iHeight,format);//后面设置为定值

//获取相机图像Buffer中的图像信息
MbufInquire(MilImage, M_HOST_ADDRESS, &SrcImageDataPtr);//数据指针
MbufInquire(MilImage,M_PHYSICAL_ADDRESS,&PhysicsImagePtr);//数据物理地址指针,仅供主线意外的

MbufInquire(MilImage, M_SIZE_BYTE, &SrcImageDataSize);//数据大小
MbufInquire(MilImage,M_SIZE_X,&BufSizeX);
MbufInquire(MilImage,M_SIZE_Y,&BufSizeY);

//将图像数据拷贝到QImage中
memcpy(img.bits(),SrcImageDataPtr,SrcImageDataSize);

4.4 程序运行时间计时器

//抓取图像数量指示
MIL_DOUBLE  Time = 0.0;//运行总时间

//重置计时器
MappTimer(M_DEFAULT, M_TIMER_RESET+M_SYNCHRONOUS, M_NULL);

//记录时间,计算帧率
MappTimer(M_DEFAULT, M_TIMER_READ + M_SYNCHRONOUS, &Time);//记录当前运行时间
double temprate=Framecount / Time;//计算每秒触发采集多少张图片
ui->lineEdit_FrameRate->setText(QString::number(temprate,10,4));//在主页面显示帧率

 4.5 存储图片到硬盘

//保存图像
//定义保存图片的路径和名称
QString savepath2="D:\\output_image";
savepath2=savepath2.append("/"+QString::number(num*10000+n*100+i));
savepath2=savepath2.append(".tif");

//将路径和名称转换为MIL的字符串类型
const wchar_t* savepath_wchar = reinterpret_cast<const wchar_t *>(savepath2.utf16());
//将MilImage[n*100+i]保存在路径下
MbufSave(savepath_wchar,MilImage[n*100+i]);
savepath2.clear();

五 连续采集图像,并在MIL自带显示器上显示

只要移植MIL库正确,只需要如下两句,即可显示实时图像

MappAllocDefault(M_DEFAULT, &MilApplication, &MilSystem, &MilDisplay,&MilDigitizer, &MilImageDisp);
MdigGrabContinuous(MilDigitizer, MilImageDisp);

六 外部电压触发采集,方波

例子:一般100KHz的方波输入,一张图像4096*1000个像素,按应该是100帧每秒

由于线扫相机,每次采集的是一行,即4096*1个像素的图像。所以100KHz即每秒采集100K行。

需要如下函数等待触发采集完成

MdigGrabWait(MilDigitizer, M_GRAB_END);//等待触发抓取完成

触发采集的图像会存储在MilImage[n*100+NbProc] 中

MdigGrab(MilDigitizer, MilImage[n*100+NbProc]);//在 第n个内存块的第NbProc个内存区域 抓取数据
//前期准备工作如下*********************************************************
//存放触发抓取图像的内存空间
MIL_ID     MilImage[200];

//每次触发抓取后调用的用户函数
MIL_INT MFTYPE GrabStart(MIL_INT, MIL_ID, void*);

//定义触发的用户数据
typedef struct
{
    MIL_INT     NbGrabStart;
} UserDataStruct;

//相机图像的属性信息
MIL_INT SrcImageDataSize;
MIL_INT BufSizeX;
MIL_INT BufSizeY;

//开始分配内存*********************************************************
//按照默认的DCF文件,初始化各类ID
MappAllocDefault(M_DEFAULT, &MilApplication, &MilSystem, M_NULL,&MilDigitizer, &MilImageDisp);

//分配抓取的图像内存
for (int n=0; n<200; n++)
    MbufAlloc2d(MilSystem,
                MdigInquire(MilDigitizer, M_SIZE_X, M_NULL),
                MdigInquire(MilDigitizer, M_SIZE_Y, M_NULL),
                8L+M_UNSIGNED,
                M_DISP+M_IMAGE+M_GRAB+M_PROC, &MilImage[n]);

//开始触发抓取设置和抓取图像*********************************************************
//定义触发事件函数
UserDataStruct UserStruct;//定义触发的 用户数据
UserStruct.NbGrabStart = 0;
//关联触发函数
MdigHookFunction(MilDigitizer, M_GRAB_START, GrabStart, (void *)(&UserStruct));
//设置抓取是同步模式
MdigControl(MilDigitizer, M_GRAB_MODE, M_ASYNCHRONOUS);

//抓取第一个图像,获取图像属性信息
MdigGrab(MilDigitizer, MilImage[0]);
//相机图像的属性信息
SrcImageDataSize=0;//图像的大小,单位像素
BufSizeX=0;//图像的宽度
BufSizeY=0;//图像的高度
//获得相机图像的宽度和高度
MdigInquire(MilDigitizer, M_SIZE_X,&BufSizeX);
MdigInquire(MilDigitizer, M_SIZE_Y,&BufSizeY);
MbufInquire(MilImage[0], M_SIZE_BYTE, &SrcImageDataSize);//数据大小

//连续抓取图像
n=0;//初始化从第0个内存块开始采集
NbProc = 0;//从内存块的第0个位置开始采集
int Framecount=0;//图像的总张数
int Framenum=1;//使用过内存块的次数
//重置计时器
MappTimer(M_DEFAULT, M_TIMER_RESET+M_SYNCHRONOUS, M_NULL);

do {
        //抓取下一个图像
        MdigGrab(MilDigitizer, MilImage[n*100+NbProc]);//在 第n个内存块的第NbProc个内存区域 抓取数据
        MdigGrabWait(MilDigitizer, M_GRAB_END);//等待触发抓取完成

        //将图像传递给显示器,这里我是在界面窗口直接显示,没有用MIL自带的显示器
        //MimArith(MilImage[n*100+NbProc], M_NULL, MilImageDisp, M_PASS);//取反M_OR

        //更新处理的图像数
        NbProc++;//下一个图像内存空间
        Framecount++;//总图像数加1

        //如果点击了关闭采集,退出循环
        if(FlagCapture==0)
        {
            break;
        }

        //每采集200张计算一下帧率
        if(Framecount%200==0)
        {
            //记录时间,计算帧率
            MappTimer(M_DEFAULT, M_TIMER_READ + M_SYNCHRONOUS, &Time);//记录当前运行时间
            double temprate=Framecount / Time;//计算每秒触发采集多少张图片
            ui->lineEdit_FrameRate->setText(QString::number(temprate,10,4));//在主页面显示帧率

            //防止页面卡死
            QCoreApplication::processEvents();
        }

        //如果抓取的图像数量达到了一个内存块的长度,换到下一个内存块。并启动线程存储当前内存块抓取的所有图像
//这一段是我自己所需的
        if(NbProc>=100)//一个内存块可以抓取100张图片
        {
            //如果抓取的图像总数量还没有达到限制数量,传递信息到存储线程中,开始存储图像
            if(Framenum<=MaxNum)
            {
                //发送信号到存储线程
                emit SendData(savepath,n,NbProc,Framenum);
            }
            NbProc=0;//重新 从第0个内存位置开始存储
            n = 1-n;//转换内存块
            Framenum++;//使用过内存块的次数加1
        }
    }
    while(!MosKbhit());

七、常用MIL函数

7.1 MIL_TEXT

MIL中的字符串,实际是Qt中的wchar_t*类型

MIL_TEXT("Matrox Capture DirectShow filter:\n")
等价于==》
QString savepath=ui->lineEdit->text();
savepath=savepath.append("/"+QString::number(index));
savepath=savepath.append(".tif");
//QString类型转换为MIL_TEXT
const wchar_t* savepath_wchar = reinterpret_cast<const wchar_t *>(savepath.utf16());

7.2 MosGetch()

获取键盘输入

7.3 MdigHalt(MilDigitizer)

暂停连续显示

7.4 MdigGrab(MilDigitizer, MilImage)

获取一张图到Millmage中

7.5 MappAllocDefault(M_DEFAULT, &MilApplication, &MilSystem,&MilDisplay, &MilDigitizer, &MilImage);

以默认模式分配所有标识内存

7.6 MdigGrabContinuous(MilDigitizer, MilImage)

连续显示图像

7.7 MappFreeDefault(MilApplication, MilSystem, MilDisplay, MilDigitizer, MilImage)

释放所有内存

7.8 MbufClear(MilImageDisp, 0x0)

清空某个标识的内存

7.9 MdispSelect(MilDisplay, MilImageDisp)

在MIL自带显示屏上显示图像

7.10 MdigControl(MilDigitizer, M_GRAB_SCALE, GrabScale)

控制显示器的属性

格式如下:

void MdigControl(DigId, ControlType, Value)

MIL_ID DigId;Digitizer 标识符
long ControlType;控制类型
double ControlValue;控制值

控制类型如下: 

控制类型描述
M_GRAB_SCALE

控制使用MdigGrab or MdigGrabContinuous函数抓取数据时的水平和竖直缩放因子

典型值:0.25, 0.5, and 1.0。间隔取值方式缩放

M_GRAB_SCALE_X控制使用MdigGrab or MdigGrabContinuous函数抓取数据时的水平缩放因子
M_GRAB_SCALE_Y控制使用MdigGrab or MdigGrabContinuous函数抓取数据时的水平和竖直缩放因子
M_GRAB_MODE控制抓取图像时的同步性 MdigGrab .
M_GRAB_FIELD_NUM控制抓取图像时的区域数量 MdigGrab.
M_GRAB_FRAME_NUM控制抓取图像时的帧数量 MdigGrab.
M_GRAB_START_MODE设置开始抓取图像模式为奇、偶或其他: M_FIELD_START_ODD, M_FIELD_START_EVEN (M_DEFAULT), or M_FIELD_START.
M_GRAB_HALT_ON_NEXT_FIELD无论最后一帧是否有效,停止抓取 M_ENABLE, M_DISABLE or M_DEFAULT (same as M_DISABLE).
M_GRAB_TRIGGER_SOURCE设置抓取触发源
M_GRAB_TRIGGER_MODE设置硬件触发使能模式
M_GRAB_TRIGGER设置触发抓取的检测状态 M_DEFAULT, M_ENABLE, M_DISABLE, or M_ACTIVATE.
M_SOURCE_SIZE_X设置输入信号抓取窗的宽度
M_SOURCE_SIZE_Y设置输入信号抓取窗的高度
M_SOURCE_OFFSET_X设置输入信号抓取窗的X方向偏移
M_SOURCE_OFFSET_Y设置输入信号抓取窗的Y方向偏移

7.11 MdigInquire(MilDigitizer, M_SIZE_X,&BufSizeX)

获取显示器的属性

格式

long MdigInquire(DigId, ParamToInquire, UserVarPtr)

MIL_ID DigId;Digitizer 标识符
long InquireType;获取的属性类型
void *UserVarPtr;获取属性值的存储位置
属性类型描述
M_OWNER_SYSTEM获取MIL的标识符名称 (MdigAlloc).
M_NATIVE_IDThe native identifier of the digitizer (if any).
M_NUMBER获取显示器在系统中的排名 (MdigAlloc).
M_FORMAT获取显示器数据格式 (MdigAlloc).
M_FORMAT_SIZE获取显示器数据格式字符串的字符长度
M_INIT_FLAG获取显示器初始化标志值 (MdigAlloc).
M_CHANNELCurrent channel of the digitizer (MdigChannel).
M_CHANNEL+M_SYNCCurrent synchronization channel of the digitizer (MdigChannel).
M_CHANNEL+M_SIGNALCurrent signal channel of the digitizer (MdigChannel).
M_CHANNEL_NUMNumber of available channels of the device (MdigChannel).
M_LUT_IDMIL identifier (MIL_ID) of the LUT associated with the digitizer (MdigLut).
M_BLACK_REF显示器的黑色参考值 (MdigReference).
M_WHITE_REF显示器的白色参考值 (MdigReference).
M_HUE_REF显示器的色彩参考值 (MdigReference).
M_SATURATION_REF显示器的饱和度值 (MdigReference).
M_BRIGHTNESS_REF显示器的明度值 (MdigReference).
M_CONTRAST_REF显示器的对比度值 (MdigReference).
M_GRAB_SCALE_X显示器的水平缩放因子值 (MdigControl).
M_GRAB_SCALE_Y显示器的竖直缩放因子值 (MdigControl).
M_GRAB_MODE抓取同步 (M_SYNCHRONOUS or M_ASYNCHRONOUS) (MdigControl).
M_GRAB_FRAME_NUM抓取帧的数量when MdigGrab is called (MdigControl).
M_GRAB_FIELD_NUM抓取域的数量when MdigGrab is called (MdigControl).
M_GRAB_START_MODE开始抓取模式Type of field on which to grab.
M_GRAB_HALT_ON_NEXT_FIELDWhether to stop grabbing as soon as possible, whether the last frame is valid or not. (MdigControl).
M_GRAB_TRIGGER_SOURCEGrab trigger source (MdigControl).
M_GRAB_TRIGGER_MODEHardware trigger activation mode (MdigControl).
M_GRAB_TRIGGERGrab trigger state (M_ENABLE, M_DISABLE, M_START_GRAB or M_DEFAULT (same as .dcf, if any, or M_DISABLE) (MdigControl).
M_GRAB_START_HANDLER_PTRThe pointer of the grab hook to start of grab.
M_GRAB_START_HANDLER_USER_PTRThe user pointer of the grab hook to start of grab.
M_GRAB_END_HANDLER_PTRThe pointer of the grab hook to end of grab.
M_GRAB_END_HANDLER_USER_PTRThe user pointer of the grab hook to end of grab.
M_GRAB_FRAME_START_HANDLER_PTRThe pointer of the grab hook to start of frame grab.
M_GRAB_FRAME_START_HANDLER_USER_PTRThe user pointer of the grab hook to start of frame grab.
M_GRAB_FRAME_END_HANDLER_PTRThe pointer of the grab hook to end of frame grab.
M_GRAB_FRAME_END_HANDLER_USER_PTRThe user pointer of the grab hook to end of frame grab.
M_FIELD_START_HANDLER_PTRThe pointer of the grab hook to start of field.
M_FIELD_START_HANDLER_USER_PTRThe user pointer of the grab hook to start of field.
M_FIELD_START_ODD_HANDLER_PTRThe pointer of the grab hook to start of odd field.
M_FIELD_START_ODD_HANDLER_USER_PTRThe user pointer of the grab hook to start of odd field.
M_FIELD_START_EVEN_HANDLER_PTRThe pointer of the grab hook to start of even field.
M_FIELD_START_EVEN_HANDLER_USER_PTRThe user pointer of the grab hook to start of even field.
M_GRAB_FIELD_END_HANDLER_PTRThe pointer of the grab hook to end of field grab.
M_GRAB_FIELD_END_HANDLER_USER_PTRThe user pointer of the grab hook to end of field grab.
M_GRAB_FIELD_END_ODD_HANDLER_PTRThe pointer of the grab hook to end of odd field grab.
M_GRAB_FIELD_END_ODD_HANDLER_USER_PTRThe user pointer of the grab hook to end of odd field grab.
M_GRAB_FIELD_END_EVEN_HANDLER_PTRThe pointer of the grab hook to end of even field grab.
M_GRAB_FIELD_END_EVEN_HANDLER_USER_PTRThe user pointer of the grab hook to end of even field grab.
M_FRAME_START_HANDLER_PTRThe pointer of the grab hook to start of frame.
M_FRAME_START_HANDLER_USER_PTRThe user pointer of the grab hook to start of frame.
M_SIZE_X显示器输入宽度Digitizer input width.
M_SIZE_Y显示器输入高度Digitizer input height.
M_SIZE_BANDNumber of input color bands of the digitizer.
M_SIZE_BAND_LUTNumber of input color bands of the input LUT (if any) associated with the digitizer.
M_SIZE_BIT显示器的位数
M_SIGN显示器的数据范围 (M_SIGNED or M_UNSIGNED).
M_TYPE显示器的数据类型 (number of bits + M_SIGNED or M_UNSIGNED).
M_SOURCE_SIZE_X输入信号抓取窗口的宽度
M_SOURCE_SIZE_Y输入信号抓取窗口的高度
M_SOURCE_OFFSET_X输入信号抓取窗口的X偏移
M_SOURCE_OFFSET_Y输入信号抓取窗口的Y偏移
M_COLOR_MODEMonochrome or color input.
M_SCAN_MODEScan mode (M_INTERLACE, M_PROGRESSIVE, or M_LINESCAN).
M_INPUT_MODE模拟或者数字输入

 

  • 5
    点赞
  • 28
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

kissgoodbye2012

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值