用OpenCV进行大恒CG400CG410视频采集卡的视频读取
(2013-04-27 16:12:02)
分类: opencv
最近用到红外摄像头,要用到视频采集卡,采用的是大恒CG410的板子,CG410是CG400的升级版,虽然驱动不一样,SDK和适用环境是一样的。这是使用的是win7 32位系统。
大恒的SDK的事例都是都是MFC的代码,奈何我需要的是在控制台下进行摄像头的读取,并转换到OpenCV可以识别的图像数据格式IplImage或者Mat结构,这个使用的是前者。
下面是解决方法:
在项目的库中包含
CGVideo.lib
CGVidEx.lib
头文件记得加入windows.h,因为要使用到windows句柄
代码如下:
1: #include "opencv2/core/core.hpp"
2: #include "opencv2/highgui/highgui.hpp"
3: #include "opencv2/imgproc/imgproc.hpp"
4: #include "opencv2/video/video.hpp"
5: #include <iostream>
6: #include <windows.h>
7:
8: #include "CGVideo.h"
9: #include "CGDef.h"
10: #include "CGVidEx.h"
11:
12: using namespace std;
13: using namespace cv;
14:
15: int main()
16: {
17: //初始化所有成员变量,同时打开图像卡 */
18: CGSTATUS status = CG_OK;
19: HCG hcg = NULL;
20:
21: //打开图像卡 1,返回状态值
22: status = BeginCGCard(1, &hcg);
23:
24: //检验函数执行状态,如果失败,则返回错误状态消息框*/
25: CG_VERIFY(status);
26:
27: //初始化图像卡硬件状态,用户也可以在其他位置初始化图像卡,
28: //但应保证图像卡已经打开,建议用户在应用程序初始化时,同时初始化图像卡硬件。
29: // 设置视频制式(PAL / NTSC),由当前视频源制式决定
30: CGSetVideoStandard(hcg, PAL);
31:
32: // 扫描模式,包括 FRAME、FIELD
33: CGSetScanMode(hcg, FRAME);
34:
35: //晶振,包括CRY_OSC_35M、CRY_OSC_28M
36: //对于DH-CG300图像卡,一般为CRY_OSC_35M,
37: //对于DH-QP300图像卡,一般为CRY_OSC_28M,
38: //其他类型图像卡没有此硬件设置,但可以调用此接口,并返回CG_NOT_SUPPORT_INTERFACE信息
39:
40: CGSelectCryOSC(hcg, CRY_OSC_35M);
41:
42: //视频格式,即采集图像数据描述方式,包括YUV422、RGB888、RGB565、RGB555、RGB8888、ALL8BIT、LIMITED8BIT,
43: //在采集图像到屏幕时,需要保证视频格式和当前系统屏幕位深度一致,而采集到 内存没有此限制。
44: CGSetVideoFormat(hcg, RGB888);
45:
46:
47: //视频源路VIDEO_SOURCE包括视频类型和序号,
48: //各种图像卡支持的视频源路不尽相同,请参看相应硬件说明
49: VIDEO_SOURCE source;
50: source.type = COMPOSITE_VIDEO; //视频类型为复合视频
51: source.nIndex = 0; //序号为0
52: CGSetVideoSource(hcg, source);
53:
54: //视频输入窗口,即视频输入范围,输入窗口取值范围:
55: //对于视频制式为PAL制,水平方向为0-768,垂直方向为0-576
56: //对于视频制式为NTSC制,水平方向为0-768,垂直方向为0-576
57: //视频窗口左上角X坐标和窗口宽度应为4的倍数,左上角Y坐标和窗口高度应为2的倍数
58: CGSetInputWindow(hcg, 0, 0, 768, 576); //视频输入窗口取最大
59:
60:
61: //视频输出窗口,即视频输出范围,输出窗口取值范围必须在输入窗口范围以内,
62: //视频窗口左上角X坐标和窗口宽度应为4的倍数,左上角Y坐标和窗口高度应为2的倍数
63: //在采集到屏幕时,输出窗口的起始位置为图像屏幕输出位置的屏幕坐标,
64: //在采集到内存时,输出窗口的起始位置设置为(0, 0)即可。
65:
66: CGSetOutputWindow(hcg, 0, 0, 768, 576);
67:
68: //初始化BITMAPINFO 结构指针
69: BITMAPINFO *pBmpInfo = NULL;
70: BYTE *pInfoBuffer = NULL;
71: BYTE *pImageBuffer = NULL; //BIMTAPINFO 存储缓冲区,m_pBmpInfo即指向此缓冲区
72:
73: BYTE *pStaticBuffer = NULL; //静态内存地址指针
74: HANDLE handle = NULL; //静态内存描述句柄
75:
76: //采集1帧图像到内存,采集完成后停止
77: while (TRUE)
78: {
79: status = CGSnapShot(hcg, 0, 0, TRUE, 1);
80: CG_VERIFY(status);
81:
82: if (CG_SUCCESS(status))
83: {
84: pInfoBuffer = new BYTE[sizeof(BITMAPINFO)];
85: if (pInfoBuffer)
86: {
87: //m_pBmpInfo即指向m_chBmpBuf缓冲区,用户可以自己分配BTIMAPINFO缓冲区
88:
89: pBmpInfo = (BITMAPINFO *)pInfoBuffer;
90:
91:
92: //初始化BITMAPINFO 结构,此结构在保存bmp文件、显示采集图像时使用
93:
94: pBmpInfo->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
95:
96: //图像宽度,一般为输出窗口宽度
97: pBmpInfo->bmiHeader.biWidth = 768;
98:
99: //图像高度,根据扫描模式(FRAME/FIELD)的不同
100: //FRAME制下,一般为输出窗口高度
101: //FIELD制下,一般为输出窗口高度的一半
102: pBmpInfo->bmiHeader.biHeight = 576;
103:
104: //图像位深度,由视频格式确定,
105: //采集图像视频格式有RGB565、RGB555、RGB888、ALL8BIT等,
106: //如果使用CGDateTransfrom函数,则将15,16位数据转换为24位
107: pBmpInfo->bmiHeader.biBitCount = 24;
108:
109: //以下设置一般相同,
110: //对于低于8位的位图,还应设置相应的位图调色板
111: pBmpInfo->bmiHeader.biPlanes = 1;
112: pBmpInfo->bmiHeader.biCompression = BI_RGB;
113: pBmpInfo->bmiHeader.biSizeImage = 0;
114: pBmpInfo->bmiHeader.biXPelsPerMeter = 0;
115: pBmpInfo->bmiHeader.biYPelsPerMeter = 0;
116: pBmpInfo->bmiHeader.biClrUsed = 0;
117: pBmpInfo->bmiHeader.biClrImportant = 0;
118:
119: //分配图像缓冲区,一般用来存储采集图像
120: //用户可以将设备静态内存的图像数据直接通过指针或
121: //用CGDataTransfrom函数拷贝到图像缓冲区,然后做进一步的处理,
122: //一般图像缓冲区大小由输出窗口大小和视频格式确定。
123: pImageBuffer = new BYTE[768 * 576 * 3];
124: if (pImageBuffer)
125: {
126: //锁定指定位置的静态内存,
127: //偏移由图像大小和图像序号确定,锁定大小为图像大小
128: //用户可以在任何时候锁定指定位置的静态内存,然后通过pLinearAddr指针访问相应的内存。
129: status = CGStaticMemLock(0, 768 * 576 * 3, &handle, (VOID **)&pStaticBuffer);
130: if (CG_SUCCESS(status))
131: {
132:
133: //将静态内存中的图像传递到用户缓冲区,同时进行格式转换。
134: //如果静态内存中图像为15、16、32位,则转换为24位。
135: //由于图像卡采集到静态内存的图像数据是正向存放,
136: //而Windows中处理的位图数据需要倒置,因此一般还要将图像倒置。
137: CGDataTransform(pImageBuffer, //图像缓冲区
138: pStaticBuffer, //静态内存
139: 768, //图像宽度
140: 576, //图像高度
141: 24, //图像位深度
142: TRUE //是否倒置图像
143: );
144: CGStaticMemUnlock(handle); //解除静态内存锁定
145: }
146:
147: CvSize n_size = cvSize(768,576);
148: IplImage* frame = cvCreateImageHeader( n_size, IPL_DEPTH_8U, 3 );
149: frame->imageData = (char *)pImageBuffer;
150: cvNamedWindow( "test", CV_WINDOW_AUTOSIZE );
151: cvShowImage("test",frame);
152: cvWaitKey(20);
153:
154: delete []pImageBuffer; //释放图像缓冲
155: cvReleaseImage(&frame);
156: }
157:
158: delete []pInfoBuffer; //释放文件信息缓冲
159: }
160: }
161:
162: }
163: // 关闭图像卡1
164: status = EndCGCard(hcg);
165: CG_VERIFY(status);
166: }
关于大恒图像采集卡的使用
昨天终于可以采集图像并显示了,那个高兴啊~
总结了一下使用的步骤(图像采集卡是 大恒 CG410)
使用 CGStartSnap 和 CGEndSnap 组合来控制开始和停止图像采集的步骤如下:
1、定义一个全局的设备句柄
HCG m_hcg;
2、打开图像采集卡
CGSTATUS status = CG_OK;
// 打开图像卡 1
status = BeginCGCard(1, &m_hcg);
// 检验函数执行状态,如果失败,则返回错误状态消息框
CG_VERIFY(status);
3、初始化图像采集卡硬件参数
//保证图像卡已经打开
//设置视频制式(PAL / NTSC),由当前视频源制式决定
CGSetVideoStandard(m_hcg, PAL);
//视频格式,即采集图像数据描述方式,
//YUV422、RGB888、RGB565、RGB555、RGB8888、ALL8BIT、LIMITED8BIT,
//采集图像到屏幕时,需要保证视频格式和当前系统屏幕位深度一致
CGSetVideoFormat(m_hcg, RGB888);
//扫描模式,包括 FRAME、FIELD
CGSetScanMode(m_hcg, FRAME);
// 设置视频源路,
VIDEO_SOURCE source;
source.type = COMPOSITE_VIDEO; //视频类型为复合视频
source.nIndex = 0; //序号为0
CGSetVideoSource(m_hcg, source);
//频输入窗口,即视频输入范围,输入窗口取值范围:
//PAL (0-768,0-576 );NTSC(0-640,0-480)
//视频窗口左上角X坐标和窗口宽度应为4的倍数,左上角Y坐标和窗口高度应为2的倍数
CGSetInputWindow(m_hcg, 0, 0, 768, 576); //视频输入窗口取最大
//视频输出窗口,即视频输出范围,输出窗口取值范围必须在输入窗口范围以内,
//视频窗口左上角X坐标和窗口宽度应为4的倍数,左上角Y坐标和窗口高度应为2的倍数
//在采集到屏幕时,输出窗口的起始位置为图像屏幕输出位置的屏幕坐标,
//在采集到内存时,输出窗口的起始位置设置为(0, 0)即可。
CGSetOutputWindow(m_hcg, 0, 0, 400, 300);
4、启动采集图像到内存
// 启动图像卡采集图像到内存
// 指定图像卡将图像采集到静态内存偏移为0的位置,
// 采集缓冲区大小为2幅图像大小
status = CGStartSnap(m_hcg, 0, TRUE, 2);
CG_VERIFY(status);
//获取当前正在采集的图像场,判定哪一帧图像已经采集完毕,可以进行处理
status = CGGetSnappingNumber(m_hcg, &nStatus);
5、读出图像数据
status = CGStaticMemLock(dwImageSize * nNumber, dwImageSize, &handle, (VOID **)&pStaticBuffer);
if (CG_SUCCESS(status))
{
/*
* 将静态内存中的图像传递到用户缓冲区,同时进行格式转换。
* 如果静态内存中图像为15、16、32位,则转换为24位。
* 由于图像卡采集到静态内存的图像数据是正向存放,
* 而Windows中处理的位图数据需要倒置,因此一般还要将图像倒置。
*/
CGDataTransform(pImageBuffer, pStaticBuffer, 400, 300, 24, TRUE);
CGStaticMemUnlock(handle); //解除静态内存锁定
}
6、结束读取过程
status = CGStopSnap(m_hcg);
CG_VERIFY(status);
7、关闭图像采集卡
CGSTATUS status = CG_OK;
// 关闭图像卡,释放图像卡内部资源
status = EndCGCard(m_hcg);
CG_VERIFY(status);
opencv采集视频推流 视频采集卡 opencv
转载本文章为转载内容,我们尊重原作者对文章享有的著作权。如有内容错误或侵权问题,欢迎原作者联系我们进行内容更正或删除文章。
提问和评论都可以,用心的回复会被更多人看到
评论
发布评论
相关文章
-
vue rtmp视频流视频流直播方案
rtmp视频流的播放组件封装
ide 视频流 播放视频 -
javacv视频采集卡 easycap视频采集卡
EasyCap视频音频采集卡在VS2010环境下视频采集因实验需求,购买了Eas
javacv视频采集卡 环境变量 环境配置 ide