AVT MakoManta面阵相机开发小结

时间: 2023-07-11 admin 互联网

AVT Mako/Manta面阵相机开发小结

AVT Mako/Manta面阵相机开发小结

开发环境:VS2015+Qt5.8,以官方所给asynchronousopencvrecorder的demo为例。

核心代码初解:

获取相机

VmbErrorType err = m_ApiController.StartUp(); 

初始化某个相机参数,m_cameras为列表容器,nRow为int,可以手动设置。

err = m_ApiController.StartContinuousImageAcquisition(m_cameras[nRow]);

以上函数关键代码,设置FPS,曝光时间,ROI区域等,更多的可以通过相机软件保存相机参数,到参数文件里面找相应的特征名。

     m_FPS = 100.0;FeaturePtr pFeatureFPS ;res = SP_ACCESS( m_pCamera )->GetFeatureByName("AcquisitionFrameRateAbs", pFeatureFPS);if( VmbErrorSuccess != res){res = SP_ACCESS( m_pCamera )->GetFeatureByName("AcquisitionFrameRate", pFeatureFPS);}if( VmbErrorSuccess == res ){res = SP_ACCESS(pFeatureFPS)->GetValue( m_FPS );}m_exposure = 2200.0;FeaturePtr pFeature_exposure;res = SP_ACCESS(m_pCamera)->GetFeatureByName("Exposure Time", pFeature_exposure);if (VmbErrorSuccess != res){res = SP_ACCESS(m_pCamera)->GetFeatureByName("ExposureTimeAbs", pFeature_exposure);}if (VmbErrorSuccess == res){res = SP_ACCESS(pFeature_exposure)->SetValue(m_exposure);}	FeaturePtr offset_x;res = SP_ACCESS(m_pCamera)->GetFeatureByName("OffsetX", offset_x);if (VmbErrorSuccess == res){res = SP_ACCESS(offset_x)->SetValue(m_offset_x);}FeaturePtr offset_y;res = SP_ACCESS(m_pCamera)->GetFeatureByName("OffsetY", offset_y);if (VmbErrorSuccess == res){res = SP_ACCESS(offset_y)->SetValue(m_offset_y);}

图片大小可在ApiController.h里面设置

    VmbInt64_t    m_nWidth = 360;VmbInt64_t    m_nHeight = 180;

python用于inceptionv 3分类,c++用于产生图片。为了节约开发时间,c++将图片写入固定目录,然后python读取固定目录检测,为了两边线程的安全,用了比较蠢的办法:读取txt!两边同时判断。隐掉的部分可用于格式化批量保存图片。

void AsynchronousOpenCVRecorder::OnFrameReady(int status)
{if (true == m_bIsStreaming){// Pick up frameFramePtr pFrame = m_ApiController.GetFrame();if (SP_ISNULL(pFrame)){Log("frame pointer is NULL, late frame ready message");return;}// See if it is not corruptif (VmbFrameStatusComplete == status){if (!m_pVideoRecorder.isNull()){m_pVideoRecorder->enqueueFrame(*pFrame);}VmbUchar_t *pBuffer;VmbErrorType err = SP_ACCESS(pFrame)->GetImage(pBuffer);if (VmbErrorSuccess == err){VmbUint32_t nSize;err = SP_ACCESS(pFrame)->GetImageSize(nSize);if (VmbErrorSuccess == err){VmbPixelFormatType ePixelFormat = m_ApiController.GetPixelFormat();if (!m_Image.isNull()){QFile f1("test.txt");f1.open(QIODevice::Text | QIODevice::ReadOnly);if (f1.readLine() == QByteArray("0")){f1.close();CopyToImage(pBuffer, ePixelFormat, m_Image);cv::Mat mat;mat = cv::Mat(m_Image.height(), m_Image.width(), CV_8UC3, (void*)m_Image.constBits(), m_Image.bytesPerLine());/*char image[128];n++;sprintf(image, "F:/new/new_wet2_%d%s",n, ".jpg");bool mark = cv::imwrite(image ,mat);*/bool mark=cv::imwrite("C://Users//惠普//Desktop//磁瓦检测项目1//class_transfer_learning//test.jpg", mat);if (mark){const QSize s = ui.m_LabelStream->size();ui.m_LabelStream->setPixmap(QPixmap::fromImage(m_Image).scaled(s, Qt::KeepAspectRatio));QFile f2("test2.txt");f2.open(QIODevice::Text | QIODevice::ReadOnly);if (f2.readLine() == QByteArray("0")){ui.label_4->setText(QString::fromLocal8Bit("不正常"));}else{ui.label_4->setText(QString::fromLocal8Bit("正常"));}//Sleep(100);QFile f("test.txt");QString b = "1";f.open(QIODevice::Text | QIODevice::ReadWrite);f.write(b.toLatin1(), b.length());f.close();}}}}}}else{// If we receive an incomplete image we do nothing but loggingLog("Failure in receiving image", VmbErrorOther);}// And queue it to continue streamingm_ApiController.QueueFrame(pFrame);}
}

开启视频录制线程:

    m_pVideoRecorder = OpenCVRecorderPtr(new OpenCVRecorder("AsynchronousOpenCVRecorder.avi", FPS, Width, Height));m_pVideoRecorder->start();

线程核心代码:

     while( ! m_StopThread ){FrameStorePtr tmp;{// two class events unlock the queue// first if a frame arrives enqueueFrame wakes the condition// second if the thread is stopped we are woken up// the while loop is necessary because a condition can be woken up by the systemQMutexLocker local_lock( &m_ClassLock );while(! m_StopThread && m_FrameQueue.empty() ){m_FramesAvailable.wait( local_lock.mutex() );}if( ! m_StopThread){tmp = m_FrameQueue.front();m_FrameQueue.pop_front();}}// scope for the lock, from now one we don't need the class lockif( ! m_StopThread){convertImage( *tmp );m_VideoWriter << m_ConvertImage;}}

VS+QT exe图标问题:

在Qt Designer里面

这样虽然UI有图标了,但是生成exe却没有。
新建一个.rc文件,写入

IDI_ICON1 ICON DISCARDABLE "AVT.ico"

并把.rc和.ico添加到工程里面即可

软件自启动:

找到VS的输出路径,添加相应的dll文件,双击exe文件确认是否可以运行,再发送到桌面快捷方式,这个时候进入 C:\ProgramData\Microsoft\Windows\Start Menu\Programs\StartUp 路径(win10),把快捷方式拖到里面就可以了。