海康工业相机拍照存图控制台demo

#include <stdio.h>
#include <Windows.h>
#include <process.h>
#include <conio.h>
#include "MvCameraControl.h"

bool g_bExit = false;
unsigned int g_nPayloadSize = 0;

// ch:等待按键输入 | en:Wait for key press
void WaitForKeyPress(void)
{
	while(!_kbhit())
	{
		Sleep(10);
	}
	_getch();
}

bool PrintDeviceInfo(MV_CC_DEVICE_INFO* pstMVDevInfo)
{
	if (NULL == pstMVDevInfo)
	{
		printf("The Pointer of pstMVDevInfo is NULL!\n");
		return false;
	}
	if (pstMVDevInfo->nTLayerType == MV_GIGE_DEVICE)
	{
		int nIp1 = ((pstMVDevInfo->SpecialInfo.stGigEInfo.nCurrentIp & 0xff000000) >> 24);
		int nIp2 = ((pstMVDevInfo->SpecialInfo.stGigEInfo.nCurrentIp & 0x00ff0000) >> 16);
		int nIp3 = ((pstMVDevInfo->SpecialInfo.stGigEInfo.nCurrentIp & 0x0000ff00) >> 8);
		int nIp4 = (pstMVDevInfo->SpecialInfo.stGigEInfo.nCurrentIp & 0x000000ff);

		// ch:打印当前相机ip和用户自定义名字 | en:print current ip and user defined name
		printf("CurrentIp: %d.%d.%d.%d\n" , nIp1, nIp2, nIp3, nIp4);
		printf("UserDefinedName: %s\n" , pstMVDevInfo->SpecialInfo.stGigEInfo.chUserDefinedName);
		printf("chModelName: %s\n\n" , pstMVDevInfo->SpecialInfo.stGigEInfo.chModelName);
	}
	else if (pstMVDevInfo->nTLayerType == MV_USB_DEVICE)
	{
		printf("UserDefinedName: %s\n", pstMVDevInfo->SpecialInfo.stUsb3VInfo.chUserDefinedName);
		printf("Serial Number: %s\n", pstMVDevInfo->SpecialInfo.stUsb3VInfo.chSerialNumber);
		printf("Device Number: %d\n\n", pstMVDevInfo->SpecialInfo.stUsb3VInfo.nDeviceNumber);
	}
	else
	{
		printf("Not support.\n");
	}

	return true;
}
int SaveNum = 0;
int SaveImageToBmp(void* handle,MV_FRAME_OUT stOutFrame)
{
	int nRet = MV_OK;
	MV_SAVE_IMAGE_PARAM_EX pstSaveFileParam;
	memset(&pstSaveFileParam, 0, sizeof( MV_SAVE_IMAGE_PARAM_EX));                       
	//源数据                 
	pstSaveFileParam.pData         = stOutFrame.pBufAddr;                //原始图像数据
	pstSaveFileParam.nDataLen      = stOutFrame.stFrameInfo.nFrameLen;    //原始图像数据长度
	pstSaveFileParam.enPixelType   = stOutFrame.stFrameInfo.enPixelType;  //原始图像数据的像素格式
	pstSaveFileParam.nWidth        = stOutFrame.stFrameInfo.nWidth;       //图像宽
	pstSaveFileParam.nHeight       = stOutFrame.stFrameInfo.nHeight;      //图像高 
	pstSaveFileParam.nJpgQuality  = 80;									  //JPEG图片编码质量  
	//目标数据
	pstSaveFileParam.enImageType   = MV_Image_Bmp;            //需要保存的图像类型,转换成JPEG格式
	pstSaveFileParam.nBufferSize  = stOutFrame.stFrameInfo.nWidth*stOutFrame.stFrameInfo.nHeight*3+2048;                 //存储节点的大小
	unsigned char* pImage = (unsigned char*)malloc(stOutFrame.stFrameInfo.nWidth*stOutFrame.stFrameInfo.nHeight * 3 + 2048);
	pstSaveFileParam.pImageBuffer  = pImage;                   //输出数据缓冲区,存放转换之后的图片数据         
	nRet = MV_CC_SaveImageEx2(handle, &pstSaveFileParam);
	if(MV_OK != nRet)
	{
		return nRet;
	}
	char chImageName[256] = {0};
	if (MV_Image_Bmp == pstSaveFileParam.enImageType)
	{
		SaveNum++;
		sprintf_s(chImageName, 256, "%d_Image_w%d_h%d_fn%03d.bmp", SaveNum, pstSaveFileParam.nWidth, pstSaveFileParam.nHeight, stOutFrame.stFrameInfo.nFrameNum);
	}
	//将转换之后图片数据保存成文件
	FILE* fp = fopen(chImageName, "wb");
	fwrite(pImage, 1, pstSaveFileParam.nImageLen, fp);
	fclose(fp);
	free(pImage);
	return MV_OK;
}

static  unsigned int __stdcall WorkThread(void* pUser)
{
	int nRet = MV_OK;

	MV_FRAME_OUT stOutFrame = {0};
	memset(&stOutFrame, 0, sizeof(MV_FRAME_OUT));
	for(int i=0;i<10;i++)
	{
		nRet = MV_CC_StartGrabbing(pUser);
		nRet = MV_CC_GetImageBuffer(pUser, &stOutFrame, 1000);
		if (nRet == MV_OK)
		{
			printf("Get One Frame: Width[%d], Height[%d], nFrameNum[%d]\n",
				stOutFrame.stFrameInfo.nWidth, stOutFrame.stFrameInfo.nHeight, stOutFrame.stFrameInfo.nFrameNum);
			SaveImageToBmp(pUser,stOutFrame);
		}
		else
		{
			printf("No data[0x%x]\n", nRet);
		}
		if(NULL != stOutFrame.pBufAddr)
		{
			nRet = MV_CC_FreeImageBuffer(pUser, &stOutFrame);
			if(nRet != MV_OK)
			{
				printf("Free Image Buffer fail! nRet [0x%x]\n", nRet);
			}
		}
		nRet = MV_CC_StopGrabbing(pUser);
	}
	Sleep(100);
	// ch:设置触发模式为on | en:Set trigger mode as off
	nRet = MV_CC_SetEnumValue(pUser, "TriggerMode", MV_TRIGGER_MODE_ON);
	if (MV_OK != nRet)
	{
		printf("Set Trigger Mode fail! nRet [0x%x]\n", nRet);
	
	}
	// ch:设置触发源为软触发 | en:Set trigger mode as off
	nRet = MV_CC_SetEnumValue(pUser, "TriggerSource",MV_TRIGGER_SOURCE_SOFTWARE);
	if (MV_OK != nRet)
	{
		printf("Set Trigger Mode fail! nRet [0x%x]\n", nRet);
	
	}
	nRet = MV_CC_StartGrabbing(pUser);
	for(int i=0;i<10;i++)
	{
		nRet = MV_CC_SetCommandValue(pUser,"TriggerSoftware");//相机拍照
		nRet = MV_CC_GetImageBuffer(pUser, &stOutFrame, 1000);
		if (nRet == MV_OK)
		{
			printf("Get One Frame: Width[%d], Height[%d], nFrameNum[%d]\n",
				stOutFrame.stFrameInfo.nWidth, stOutFrame.stFrameInfo.nHeight, stOutFrame.stFrameInfo.nFrameNum);
			SaveImageToBmp(pUser,stOutFrame);
		}
		else
		{
			printf("No data[0x%x]\n", nRet);
		}
		if(NULL != stOutFrame.pBufAddr)
		{
			nRet = MV_CC_FreeImageBuffer(pUser, &stOutFrame);
			if(nRet != MV_OK)
			{
				printf("Free Image Buffer fail! nRet [0x%x]\n", nRet);
			}
		}
	}
	nRet = MV_CC_StopGrabbing(pUser);
	nRet = MV_CC_SetEnumValue(pUser, "TriggerMode", MV_TRIGGER_MODE_OFF);
	return 0;
}

int main()
{
	int nRet = MV_OK;
	void* handle = NULL;

	do 
	{
		// ch:枚举设备 | en:Enum device
		MV_CC_DEVICE_INFO_LIST stDeviceList;
		memset(&stDeviceList, 0, sizeof(MV_CC_DEVICE_INFO_LIST));
		nRet = MV_CC_EnumDevices(MV_GIGE_DEVICE | MV_USB_DEVICE, &stDeviceList);
		if (MV_OK != nRet)
		{
			printf("Enum Devices fail! nRet [0x%x]\n", nRet);
			break;
		}

		if (stDeviceList.nDeviceNum > 0)
		{
			for (unsigned int i = 0; i < stDeviceList.nDeviceNum; i++)
			{
				printf("[device %d]:\n", i);
				MV_CC_DEVICE_INFO* pDeviceInfo = stDeviceList.pDeviceInfo[i];
				if (NULL == pDeviceInfo)
				{
					break;
				} 
				PrintDeviceInfo(pDeviceInfo);            
			}  
		} 
		else
		{
			printf("Find No Devices!\n");
			break;
		}

		printf("Please Input camera index:");
		unsigned int nIndex = 0;
		scanf_s("%d", &nIndex);

		if (nIndex >= stDeviceList.nDeviceNum)
		{
			printf("Input error!\n");
			break;
		}

		// ch:选择设备并创建句柄 | en:Select device and create handle
		nRet = MV_CC_CreateHandle(&handle, stDeviceList.pDeviceInfo[nIndex]);
		if (MV_OK != nRet)
		{
			printf("Create Handle fail! nRet [0x%x]\n", nRet);
			break;
		}

		// ch:打开设备 | en:Open device
		nRet = MV_CC_OpenDevice(handle);
		if (MV_OK != nRet)
		{
			printf("Open Device fail! nRet [0x%x]\n", nRet);
			break;
		}

		// ch:探测网络最佳包大小(只对GigE相机有效) | en:Detection network optimal package size(It only works for the GigE camera)
		if (stDeviceList.pDeviceInfo[nIndex]->nTLayerType == MV_GIGE_DEVICE)
		{
			int nPacketSize = MV_CC_GetOptimalPacketSize(handle);
			if (nPacketSize > 0)
			{
				nRet = MV_CC_SetIntValue(handle,"GevSCPSPacketSize",nPacketSize);
				if(nRet != MV_OK)
				{
					printf("Warning: Set Packet Size fail nRet [0x%x]!", nRet);
				}
			}
			else
			{
				printf("Warning: Get Packet Size fail nRet [0x%x]!", nPacketSize);
			}
		}

		// ch:设置触发模式为off | en:Set trigger mode as off
		nRet = MV_CC_SetEnumValue(handle, "TriggerMode", 0);
		if (MV_OK != nRet)
		{
			printf("Set Trigger Mode fail! nRet [0x%x]\n", nRet);
			break;
		}

		// ch:获取数据包大小 | en:Get payload size
		MVCC_INTVALUE stParam;
		memset(&stParam, 0, sizeof(MVCC_INTVALUE));
		nRet = MV_CC_GetIntValue(handle, "PayloadSize", &stParam);
		if (MV_OK != nRet)
		{
			printf("Get PayloadSize fail! nRet [0x%x]\n", nRet);
			break;
		}
		g_nPayloadSize = stParam.nCurValue;

		// ch:开始取流 | en:Start grab image
		nRet = MV_CC_StartGrabbing(handle);
		if (MV_OK != nRet)
		{
			printf("Start Grabbing fail! nRet [0x%x]\n", nRet);
			break;
		}

		unsigned int nThreadID = 0;
		void* hThreadHandle = (void*) _beginthreadex( NULL , 0 , WorkThread , handle, 0 , &nThreadID );
		if (NULL == hThreadHandle)
		{
			break;
		}

		printf("Press a key to stop grabbing.\n");
		WaitForKeyPress();

		g_bExit = true;
		Sleep(1000);

		// ch:停止取流 | en:Stop grab image
		nRet = MV_CC_StopGrabbing(handle);
		if (MV_OK != nRet)
		{
			printf("Stop Grabbing fail! nRet [0x%x]\n", nRet);
			break;
		}

		// ch:关闭设备 | Close device
		nRet = MV_CC_CloseDevice(handle);
		if (MV_OK != nRet)
		{
			printf("ClosDevice fail! nRet [0x%x]\n", nRet);
			break;
		}

		// ch:销毁句柄 | Destroy handle
		nRet = MV_CC_DestroyHandle(handle);
		if (MV_OK != nRet)
		{
			printf("Destroy Handle fail! nRet [0x%x]\n", nRet);
			break;
		}
	} while (0);


	if (nRet != MV_OK)
	{
		if (handle != NULL)
		{
			MV_CC_DestroyHandle(handle);
			handle = NULL;
		}
	}

	printf("Press a key to exit.\n");
	WaitForKeyPress();

	return 0;
}

猜你喜欢

转载自blog.csdn.net/kaizi318/article/details/111519216
今日推荐