原创

Qt(C++)调用工业相机Basler的SDK使用示例

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://shazhenyu.blog.csdn.net/article/details/78844664

简介

由于公司采购的AVT相机不足,需要用Basler相机来弥补,所以我也了解了一下Basler这款相机的SDK。由于Basler这边的相机提供的没有提供Qt的示例,所以我做一个分享出来。

本篇的Demo采用的是工业黑白相机。工业应用中,如果我们要处理的是与图像颜色有关,那么我们最好采用彩色工业相机;如果不是,那么我们最好选用黑白工业相机,因为在同样分辨率下的工业相机,黑白工业教学精度比彩色工业相机高,尤其是在看图像边缘的时候,黑白工业相机的效果更好。

开发环境

Qt:  5.6.2vc2013版 

Basler:  5.0.11版

效果图

 

上图只是做了SDK部分接口的获取和设置。相机的触发方式、曝光时间、增益、频率,以及图片的尺寸、灯的触发信号等。

Basler相机SDK接口调用控制类

#ifndef SBASLERCAMERACONTROL_H
#define SBASLERCAMERACONTROL_H

#include <QObject>
#include <pylon/PylonIncludes.h>
#include <QImage>
#include <QTimer>

#define DOUBLE_MAX 100000
#define DOUBLE_MIN 0

using namespace std;
using namespace Pylon;
using namespace GenApi;
class SBaslerCameraControl : public QObject
{
    Q_OBJECT
public:
    explicit SBaslerCameraControl(QObject *parent = 0);
    ~SBaslerCameraControl();

    enum SBaslerCameraControl_Type{
        Type_Basler_Freerun, //设置相机的内触发
        Type_Basler_Line1, //设置相机的外触发
        Type_Basler_ExposureTimeAbs, //设置相机的曝光时间
        Type_Basler_GainRaw, //设置相机的增益
        Type_Basler_AcquisitionFrameRateAbs, //设置相机的频率
        Type_Basler_Width, //图片的宽度
        Type_Basler_Height, //图片的高度
        Type_Basler_LineSource, //灯的触发信号
    };
    void initSome();
    void deleteAll();
    QStringList cameras();
    int OpenCamera(QString cameraSN);
    int CloseCamera();

    void setExposureTime(double time); // 设置曝光时间
    int getExposureTime(); // 获取曝光时间
    int getExposureTimeMin(); // 最小曝光时间
    int getExposureTimeMax(); // 最大曝光时间

    void setFeatureTriggerSourceType(QString type); // 设置种类
    QString getFeatureTriggerSourceType(); // 获取种类:软触发、外触发等等

    void setFeatureTriggerModeType(bool on); // 设置模式触发
    bool getFeatureTriggerModeType(); // 获取模式触发
    void SetCamera(SBaslerCameraControl::SBaslerCameraControl_Type index, double tmpValue = 0.0); // 设置各种参数
    double GetCamera(SBaslerCameraControl::SBaslerCameraControl_Type index); // 获取各种参数

    long GrabImage(QImage& image,int timeout = 2000);
    long StartAcquire(); // 开始采集
    long StopAcquire(); // 结束采集
signals:
    void sigCameraUpdate(QStringList list);
    void sigSizeChange(QSize size);
    void sigCameraCount(int count);
    void sigCurrentImage(QImage img);
private:
    void UpdateCameraList();
    void CopyToImage(CGrabResultPtr pInBuffer, QImage &OutImage);
private slots:
    void onTimerGrabImage();
private:
    CInstantCamera m_basler;
    QStringList m_cameralist;
    QString m_currentMode;
    bool m_isOpenAcquire = false; // 是否开始采集
    bool m_isOpen = false; // 是否打开摄像头
    QSize m_size;
};

#endif // SBASLERCAMERACONTROL_H

源文件:

#include "sbaslercameracontrol.h"
#include <QDateTime>
#include <QDebug>

SBaslerCameraControl::SBaslerCameraControl(QObject *parent) : QObject(parent)
{
}

SBaslerCameraControl::~SBaslerCameraControl()
{
}

void SBaslerCameraControl::initSome()
{
    qDebug() << "SBaslerCameraControl: PylonInitialize initSome" ;
    PylonInitialize();
    CTlFactory &TlFactory = CTlFactory::GetInstance();
    TlInfoList_t lstInfo;
    int n = TlFactory.EnumerateTls(lstInfo);

    TlInfoList_t::const_iterator it;
    for ( it = lstInfo.begin(); it != lstInfo.end(); ++it ) {
        qDebug() << "FriendlyName: " << it->GetFriendlyName() << "FullName: " << it->GetFullName();
        qDebug() << "VendorName: " << it->GetVendorName() << "DeviceClass: " << it->GetDeviceClass() ;
    }
    UpdateCameraList();
    emit sigCameraCount(n);
    qDebug() << "SBasler Camera Count: " << n;
}

void SBaslerCameraControl::deleteAll()
{
    //停止采集
    if(m_isOpenAcquire) {
        StopAcquire();
    }
    //关闭摄像头
    CloseCamera();
    //关闭库
    qDebug() << "SBaslerCameraControl deleteAll: PylonTerminate" ;
    PylonTerminate();
    qDebug() << "SBaslerCameraControl deleteAll: Close" ;
}

QStringList SBaslerCameraControl::cameras()
{
    return m_cameralist;
}

void SBaslerCameraControl::UpdateCameraList()
{
    CTlFactory& TLFactory = CTlFactory::GetInstance();
    ITransportLayer * pTl = TLFactory.CreateTl("BaslerGigE");
    DeviceInfoList_t devices;
    int n = pTl->EnumerateDevices(devices);
    CInstantCameraArray cameraArray(devices.size());
    if(n == 0) {
        qDebug() << "Cannot find Any camera!";
        return;
    }
    for (int i=0 ; i<cameraArray.GetSize() ; i++) {
        cameraArray[i].Attach(TLFactory.CreateDevice(devices[i]));
        string sn = cameraArray[i].GetDeviceInfo().GetSerialNumber();
        m_cameralist << QString::fromStdString(sn);
    }
    emit sigCameraUpdate(m_cameralist);
}

void SBaslerCameraControl::CopyToImage(CGrabResultPtr pInBuffer, QImage &OutImage)
{
    uchar* buff = (uchar*)pInBuffer->GetBuffer();
    int nHeight = pInBuffer->GetHeight();
    int nWidth = pInBuffer->GetWidth();
    if(m_size != QSize(nWidth, nHeight)) {
        m_size = QSize(nWidth, nHeight);
        emit sigSizeChange(m_size);
    }
    QImage imgBuff(buff, nWidth, nHeight, QImage::Format_Indexed8);
    OutImage = imgBuff;
    if(pInBuffer->GetPixelType() == PixelType_Mono8) {
        uchar* pCursor = OutImage.bits();
        if ( OutImage.bytesPerLine() != nWidth ) {
            for ( int y=0; y<nHeight; ++y ) {
                pCursor = OutImage.scanLine( y );
                for ( int x=0; x<nWidth; ++x ) {
                    *pCursor =* buff;
                    ++pCursor;
                    ++buff;
                }
            }
        } else {
            memcpy( OutImage.bits(), buff, nWidth * nHeight );
        }
    }
}

void SBaslerCameraControl::onTimerGrabImage()
{
    if(m_isOpenAcquire) {
        QImage image;
        GrabImage(image, 5);
        if(!image.isNull()) {
            emit sigCurrentImage(image);
        }
        QTimer::singleShot(5, this, SLOT(onTimerGrabImage()));
    }
}

int SBaslerCameraControl::OpenCamera(QString cameraSN)
{
    try {
        CDeviceInfo cInfo;
        String_t str = String_t(cameraSN.toStdString().c_str());
        cInfo.SetSerialNumber(str);
        m_basler.Attach(CTlFactory::GetInstance().CreateDevice(cInfo));
        m_basler.Open();
        //获取触发模式
        getFeatureTriggerSourceType();
        m_isOpen = true;
    } catch (GenICam::GenericException &e) {
        OutputDebugString(L"OpenCamera Error\n");
        m_isOpen = false;
        return -2;
    }
    return 0;
}

int SBaslerCameraControl::CloseCamera()
{
    if(!m_isOpen) {
        return -1;
    }
    try {
        if(m_basler.IsOpen()) {
            m_basler.DetachDevice();
            m_basler.Close();
        }
    } catch (GenICam::GenericException &e) {
        OutputDebugString(LPCWSTR(e.GetDescription()));
        return -2;
    }
    return 0;
}

void SBaslerCameraControl::setExposureTime(double time)
{
    SetCamera(Type_Basler_ExposureTimeAbs, time);
}

int SBaslerCameraControl::getExposureTime()
{
    return QString::number(GetCamera(Type_Basler_ExposureTimeAbs)).toInt();
}

int SBaslerCameraControl::getExposureTimeMin()
{
    return DOUBLE_MIN;
}

int SBaslerCameraControl::getExposureTimeMax()
{
    return DOUBLE_MAX;
}

void SBaslerCameraControl::setFeatureTriggerSourceType(QString type)
{
    //停止采集
    if(m_isOpenAcquire) {
        StopAcquire();
    }
    if(type == "Freerun") {
        SetCamera(Type_Basler_Freerun);
    } else if(type == "Line1"){
        SetCamera(Type_Basler_Line1);
    }
}

QString SBaslerCameraControl::getFeatureTriggerSourceType()
{
    INodeMap &cameraNodeMap = m_basler.GetNodeMap();
    CEnumerationPtr  ptrTriggerSel = cameraNodeMap.GetNode ("TriggerSelector");
    ptrTriggerSel->FromString("FrameStart");
    CEnumerationPtr  ptrTrigger  = cameraNodeMap.GetNode ("TriggerMode");
    ptrTrigger->SetIntValue(1);
    CEnumerationPtr  ptrTriggerSource = cameraNodeMap.GetNode ("TriggerSource");

    String_t str = ptrTriggerSource->ToString();
    m_currentMode = QString::fromLocal8Bit(str.c_str());
    return m_currentMode;
}

void SBaslerCameraControl::setFeatureTriggerModeType(bool on)
{
    INodeMap &cameraNodeMap = m_basler.GetNodeMap();
    CEnumerationPtr  ptrTriggerSel = cameraNodeMap.GetNode ("TriggerSelector");
    ptrTriggerSel->FromString("FrameStart");
    CEnumerationPtr  ptrTrigger  = cameraNodeMap.GetNode ("TriggerMode");
    ptrTrigger->SetIntValue(on?1:0);
}

bool SBaslerCameraControl::getFeatureTriggerModeType()
{
    INodeMap &cameraNodeMap = m_basler.GetNodeMap();
    CEnumerationPtr  ptrTriggerSel = cameraNodeMap.GetNode ("TriggerSelector");
    ptrTriggerSel->FromString("FrameStart");
    CEnumerationPtr  ptrTrigger  = cameraNodeMap.GetNode ("TriggerMode");
    return ptrTrigger->GetIntValue() == 1;
}

void SBaslerCameraControl::SetCamera(SBaslerCameraControl::SBaslerCameraControl_Type index, double tmpValue)
{
    INodeMap &cameraNodeMap = m_basler.GetNodeMap();
    switch (index) {
    case Type_Basler_Freerun: {
        CEnumerationPtr  ptrTriggerSel = cameraNodeMap.GetNode ("TriggerSelector");
        ptrTriggerSel->FromString("FrameStart");
        CEnumerationPtr  ptrTrigger  = cameraNodeMap.GetNode ("TriggerMode");
#ifdef Real_Freerun
        ptrTrigger->SetIntValue(0);
#else //Software
        ptrTrigger->SetIntValue(1);
        CEnumerationPtr  ptrTriggerSource = cameraNodeMap.GetNode ("TriggerSource");
        ptrTriggerSource->FromString("Software");
#endif
    } break;
    case Type_Basler_Line1: {
        CEnumerationPtr  ptrTriggerSel = cameraNodeMap.GetNode ("TriggerSelector");
        ptrTriggerSel->FromString("FrameStart");
        CEnumerationPtr  ptrTrigger  = cameraNodeMap.GetNode ("TriggerMode");
        ptrTrigger->SetIntValue(1);
        CEnumerationPtr  ptrTriggerSource = cameraNodeMap.GetNode ("TriggerSource");
        ptrTriggerSource->FromString("Line1");
    } break;
    case Type_Basler_ExposureTimeAbs: {
        const CFloatPtr exposureTime = cameraNodeMap.GetNode("ExposureTimeAbs");
        exposureTime->SetValue(tmpValue);
    } break;
    case Type_Basler_GainRaw: {
        const CIntegerPtr cameraGen = cameraNodeMap.GetNode("GainRaw");
        cameraGen->SetValue(tmpValue);
    } break;
    case Type_Basler_AcquisitionFrameRateAbs: {
        const CBooleanPtr frameRate = cameraNodeMap.GetNode("AcquisitionFrameRateEnable");
        frameRate->SetValue(TRUE);
        const CFloatPtr frameRateABS = cameraNodeMap.GetNode("AcquisitionFrameRateAbs");
        frameRateABS->SetValue(tmpValue);
    } break;
    case Type_Basler_Width: {
        const CIntegerPtr widthPic = cameraNodeMap.GetNode("Width");
        widthPic->SetValue(tmpValue);
    } break;
    case Type_Basler_Height: {
        const CIntegerPtr heightPic = cameraNodeMap.GetNode("Height");
        heightPic->SetValue(tmpValue);
    } break;
    case Type_Basler_LineSource: {
        CEnumerationPtr  ptrLineSource = cameraNodeMap.GetNode ("LineSource");
        ptrLineSource->SetIntValue(2);
    } break;
    default:
        break;
    }
}

double SBaslerCameraControl::GetCamera(SBaslerCameraControl::SBaslerCameraControl_Type index)
{
    INodeMap &cameraNodeMap = m_basler.GetNodeMap();
    switch (index) {
    case Type_Basler_ExposureTimeAbs: {
        const CFloatPtr exposureTime = cameraNodeMap.GetNode("ExposureTimeAbs");
        return exposureTime->GetValue();
    } break;
    case Type_Basler_GainRaw: {
        const CIntegerPtr cameraGen = cameraNodeMap.GetNode("GainRaw");
        return cameraGen->GetValue();
    } break;
    case Type_Basler_AcquisitionFrameRateAbs: {
        const CBooleanPtr frameRate = cameraNodeMap.GetNode("AcquisitionFrameRateEnable");
        frameRate->SetValue(TRUE);
        const CFloatPtr frameRateABS = cameraNodeMap.GetNode("AcquisitionFrameRateAbs");
        return frameRateABS->GetValue();
    } break;
    case Type_Basler_Width: {
        const CIntegerPtr widthPic = cameraNodeMap.GetNode("Width");
        return widthPic->GetValue();
    } break;
    case Type_Basler_Height: {
        const CIntegerPtr heightPic = cameraNodeMap.GetNode("Height");
        return heightPic->GetValue();
    } break;
    default:
        return -1;
        break;
    }
}

long SBaslerCameraControl::StartAcquire()
{
    m_isOpenAcquire = true;
    qDebug() << "SBaslerCameraControl IsGrabbing";
    try {
        qDebug() << "SBaslerCameraControl StartAcquire" << m_currentMode;
         if(m_currentMode == "Freerun")  {
             m_basler.StartGrabbing(GrabStrategy_LatestImageOnly,GrabLoop_ProvidedByInstantCamera);
         } else if(m_currentMode == "Software") {
             m_basler.StartGrabbing(GrabStrategy_LatestImageOnly);
             onTimerGrabImage();
         } else if(m_currentMode == "Line1") {
             m_basler.StartGrabbing(GrabStrategy_OneByOne);
         } else if(m_currentMode == "Line2") {
             m_basler.StartGrabbing(GrabStrategy_OneByOne);
         }
    } catch (GenICam::GenericException &e) {
        OutputDebugString(L"StartAcquire error:");
        return -2;
    }
    return 0;
}

long SBaslerCameraControl::StopAcquire()
{
    m_isOpenAcquire = false;
    qDebug() << "SBaslerCameraControl StopAcquire";
    try {
        if (m_basler.IsGrabbing()) {
            m_basler.StopGrabbing();
        }
    } catch (GenICam::GenericException &e) {
        OutputDebugString(LPCWSTR(e.GetDescription()));
        return -2;
    }
    return 0;
}

long SBaslerCameraControl::GrabImage(QImage &image, int timeout)
{
    try  {
        if (!m_basler.IsGrabbing()) {
            StartAcquire();
        }
        CGrabResultPtr ptrGrabResult;
        if(m_currentMode == "Freerun")  {
        } else if(m_currentMode == "Software") {
            if (m_basler.WaitForFrameTriggerReady(1000, TimeoutHandling_Return)) {
                m_basler.ExecuteSoftwareTrigger();
                m_basler.RetrieveResult(timeout, ptrGrabResult,TimeoutHandling_Return);
            }
        } else if(m_currentMode == "Line1") {
            m_basler.RetrieveResult(timeout, ptrGrabResult, TimeoutHandling_Return);
        } else if(m_currentMode == "Line2") {
            m_basler.RetrieveResult(timeout, ptrGrabResult, TimeoutHandling_Return);
        }
        if (ptrGrabResult->GrabSucceeded()) {
            if (!ptrGrabResult.IsValid()) { OutputDebugString(L"GrabResult not Valid Error\n"); return -1; }
            EPixelType pixelType = ptrGrabResult->GetPixelType();
            switch (pixelType) {
            case PixelType_Mono8: {
                CopyToImage(ptrGrabResult, image);
            } break;
            case PixelType_BayerRG8: { qDebug() << "what: PixelType_BayerRG8"; }  break;
            default:  qDebug() << "what: default"; break;
            }
        } else {
            OutputDebugString(L"Grab Error!!!");
            return -3;
        }
    } catch (GenICam::GenericException &e) {
        OutputDebugString(L"GrabImage Error\n");
        return -2;
    }  catch(...)  {
        OutputDebugString(L"ZP 11 Shot GetParam Try 12 No know Error\n");
        return -1;
    }
    return 0;
}

如何调用

#ifndef MAINWINDOW_H
#define MAINWINDOW_H

#include <QMainWindow>
#include "BaslerCamera/sbaslercameracontrol.h"

namespace Ui {
class MainWindow;
}

class MainWindow : public QMainWindow
{
    Q_OBJECT

public:
    explicit MainWindow(QWidget *parent = 0);
    ~MainWindow();

private slots:
    void on_pushButton_GetExTime_clicked();
    void on_pushButton_SetExTime_clicked();
    void on_pushButton_SetMode_clicked();
    void on_pushButton_GetMode_clicked();
    void on_pushButton_CFMode_clicked();
    void on_comboBox_CFMode_activated(int index);
    void on_pushButton_Start_clicked();
    void on_pushButtonRotate_clicked();
private:
    Ui::MainWindow *ui;
    SBaslerCameraControl* m_control = Q_NULLPTR;
    QMatrix m_matrix;
};

#endif // MAINWINDOW_H

源文件:

#include "mainwindow.h"
#include "ui_mainwindow.h"
#include <QDebug>

MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    m_control = new SBaslerCameraControl(this);
    m_control->initSome();
    connect(m_control, &SBaslerCameraControl::sigCurrentImage, [=](QImage img){
        QPixmap pix = QPixmap::fromImage(img).transformed(m_matrix);
        ui->label->setPixmap(pix);
        ui->widget_pic->setFixedSize(pix.size());
    });
    connect(m_control, &SBaslerCameraControl::sigSizeChange, [=](QSize size){
        // 默认大小641,494
        ui->label_size->setText(QString("\345\260\272\345\257\270:%0*%1").arg(QString::number(size.width())).arg(QString::number(size.height()))); // 尺寸
        ui->widget_pic->setFixedSize(size);
    });
    m_control->OpenCamera(m_control->cameras().first());
}

MainWindow::~MainWindow()
{
    m_control->CloseCamera();
    m_control->deleteAll();
    delete ui;
}

void MainWindow::on_pushButton_GetExTime_clicked()
{
    ui->label_exTime->setText(QString::number(m_control->getExposureTime()));
}

void MainWindow::on_pushButton_SetExTime_clicked()
{
    m_control->setExposureTime(ui->lineEdit_exTime->text().toDouble());
}

void MainWindow::on_pushButton_SetMode_clicked()
{
    m_control->setFeatureTriggerSourceType(ui->lineEdit_SetMode->text());
}

void MainWindow::on_pushButton_GetMode_clicked()
{
    ui->label_Mode->setText(m_control->getFeatureTriggerSourceType());
}

void MainWindow::on_pushButton_CFMode_clicked()
{
    ui->label_CFMode->setText(m_control->getFeatureTriggerModeType()?"Open":"Close");
}

void MainWindow::on_comboBox_CFMode_activated(int index)
{
    m_control->setFeatureTriggerModeType(index == 0);
}

void MainWindow::on_pushButton_Start_clicked()
{
    if(ui->pushButton_Start->text() == "\345\274\200\345\247\213\351\207\207\351\233\206") {// 开始采集
        m_control->StartAcquire();
        ui->pushButton_Start->setText("\347\273\223\346\235\237\351\207\207\351\233\206");// 结束采集
    } else {
        m_control->StopAcquire();
        ui->pushButton_Start->setText("\345\274\200\345\247\213\351\207\207\351\233\206");// 开始采集
    }
}

void MainWindow::on_pushButtonRotate_clicked()
{
    m_matrix.rotate(90);
}

pro文件

(注意:引用库文件的路径哦)

#-------------------------------------------------
#
# Project created by QtCreator 2017-12-14T17:55:52
#
#-------------------------------------------------

QT       += core gui

greaterThan(QT_MAJOR_VERSION, 4): QT += widgets

TARGET = Demo_BaslerCamera
TEMPLATE = app

CONFIG   += c++11

#--------------------------------------------Basler-------------------------------------------
INCLUDEPATH += $$PWD/include
LIBS += -L$$PWD/lib/Win32 -lGCBase_MD_VC120_v3_0_Basler_pylon_v5_0 -lGenApi_MD_VC120_v3_0_Basler_pylon_v5_0 -lPylonBase_MD_VC120_v5_0 -lPylonC_MD_VC120 -lPylonGUI_MD_VC120_v5_0 -lPylonUtility_MD_VC120_v5_0
#----------------------------------------------------------------------------------------------

SOURCES += main.cpp\
        mainwindow.cpp \
    BaslerCamera/sbaslercameracontrol.cpp

HEADERS  += mainwindow.h \
    BaslerCamera/sbaslercameracontrol.h

FORMS    += mainwindow.ui

 

我把代码已经上传到

码云

https://gitee.com/sand_teacher_younger_brother/Demo_BaslerCamera

以上是Basler相机小Demo。如有问题直接在博客下提问,有时间的小伙伴也可以参与到项目中来……

 

版权声明:当你的才华还撑不起你的野心时,那你就应该静下心来学习。作者:沙师弟专栏 

原文地址:https://blog.csdn.net/u014597198/article/details/78844664

文章最后发布于: 2017-12-19 16:56:24
展开阅读全文

没有更多推荐了,返回首页

©️2019 CSDN 皮肤主题: 代码科技 设计师: Amelia_0503

分享到微信朋友圈

×

扫一扫,手机浏览