多线程halcon调用实现

1、应用背景

在实际应用中,程序往往需要既能完成图像的连续抓取显示(监视功能),又需要能实现单帧抓取做图像处理。

实际上连续抓取在实现上就是循环单次抓取,只是需要单独开辟线程来实现。


2、实时刷图线程

1)开启线程:

HANDLE hThreadControl = ::CreateThread(NULL, 0, ThreadControl, (LPVOID)this, 0, 0);

2)线程实现:

while(1)

{

m_Camera.SingleGrab();

set_part(m_hHalconWnd, 0 0, 480-1, 640-1);

disp_obj(m_ImageThreadBuf, m_hHalconWnd);

}

3)变量说明:

m_Camera相机对象,用于封装SingleGrab()单帧抓取函数,后面有描述;

m_hHalconWnd窗口句柄,类型Htuple;

m_ImageThreadBuf图像数据,类型Hobject;


3、单帧抓取原理

1)抓包图像处理回调函数

int WINAPI CCameraDlg::ImageProcess(void *pWebCamera)

{

CCameraDlg* pThis = (CCameraDlg*)pVoid; //回调函数属于静态函数,采用全局变量的方式获取对象指针

gen_image1(&(pThis->m_ImageThread), "byte", 640, 480, 

(long)((WebCamera *)pWebCamera)->pFrame->DataBuffer);//获取一幅图片

EnterCriticalSection(&(pThis->m_Camera.m_cCriticalSection));//关键代码段保护

//如果需要单帧抓取,则拷贝一份图片出来

if(TRUE == pThis->m_Camera.m_bIsSingleGrabRequire)

{

pThis->m_Camera.m_bIsSingleGrabRequire = FALSE;

copy_image(pThis->m_ImageThread, &(pThis->m_ImageThreadBuf));

SetEvent(pThis->m_Camera.m_hEvernt); //事件通知拷贝完成

}

LeaveCriticalSection(&(pThis->m_Camera.m_cCriticalSection));

return 1;

}


2)单帧抓取需求函数

void SingleGrab()

{

EnterCriticalSection(&m_cCriticalSection));//关键代码段保护

m_bIsSingleGrabRequire = TRUE;//修改抓图需求标志

LeaveCriticalSection(&m_cCriticalSection));

WaitForSingleObject(m_hEvent, INFINIE);//等待事件通知

return;

}


4、单帧抓取函数冲突

当主线程和子线程同时调用SingleGrab单帧抓取函数时,会存在冲突。

实际上,这种情况经常出现。比如,在子线程中进行连续采图(实时显示)时,

主线程中有单帧抓取需求(图像处理)。

解决这个问题可以采用再开辟一段图像缓存,将连续采图和单帧采图的图像缓冲和

需求标志分离,各自独立,从而解决该冲突。


5、显示窗口绑定

1)halcon显示窗口绑定代码:

CRect rect;

GetDlgItem(IDC_IMAGE_FRAME)->GetWindowRect(rect); //获取窗口大小

open_window(0,0,rect.Width()-1,rect.Height()-1,(Hlong)(GetDlgItem(IDC_IMAGE_FRAME)->mWnd),"visible","",&m_hHalconWnd);

2)参数说明

IDC_IMAGE_FRAME 控件资源号 可以选择picture control控件;

m_hHalconWnd窗口句柄,类型Htuple;



你可能感兴趣的:(多线程halcon调用实现)