Qt 使用Visa库与数字仪器仪表TCP/IP通信(SCPI指令自动化测试)

标准数字仪器仪表可通过 GPIB, RS232, USB, LAN接口等与上位机数据通信和控制。如示波器、数字万用表、频率计、台式电源等。通过SCPI协议(字符串形式)与设备通信,串口,USB等接口可以直接用字符串通信,但是LAN通信不同于一般TCP/UDP用ip和端口通信,需要用Visa协议栈通信。Qt开发时只需要把visa动态库和头文件导入即可。

以普源的数字万用表DM3068为例,使用LAN口通信:

根据官方编程文档,通信协议如下:查询当前测量直流电压值发送字符串“:MEASure:VOLTage:DC?

1.获取visa.lib,可以安装 NI-MAX,毕竟调试也需要, 安装 NI-​VISA

2.安装完成后可以去安装目录下拷贝lib库到Qt目录下,需要的文件有:

2.1 C:\Program Files (x86)\IVI Foundation\VISA\WinNT\Include\visa.hvisatype.h

 2.2 C:\Program Files (x86)\IVI Foundation\VISA\WinNT\Lib_x64\msc\visa64.lib

 2.3 拷贝到Qt目录下

 2.4 Qt添加动态库和visa.h头文件

3.现在可以使用了,但是通信需要知道仪器的Ip地址字符串,可以使用安装的NI-MAX查看。打开MAX,连接网线,添加设备,添加仪器IP地址,

完成后会显示仪器名称, 

 把这个复制到Qt 测试程序: 发送测量当前输入的8V电压值.

static ViSession defaultRM;
static ViSession instr;
static ViUInt32 retCount;
static ViUInt32 writeCount;
static ViStatus status;
static unsigned char buffer[100];
static char stringinput[512];

#define DM3068IPSTR  "TCPIP0::192.168.1.30::inst0::INSTR"


MainWindow::MainWindow(QWidget *parent)
    : QMainWindow(parent)
    , ui(new Ui::MainWindow)
{
    ui->setupUi(this);

    //串口检测线程
    spThread = new SerialPortThread();
    connect(spThread,&SerialPortThread::reflashSerialPort, this,&MainWindow::showSerialPort);
    spThread->start();

    status = viOpenDefaultRM(&defaultRM);
    if (status < VI_SUCCESS)
    {
        qDebug() << "Could not open a session to the VISA Resource Manager!\n";
    }

    status = viOpen(defaultRM, DM3068IPSTR, VI_NULL, VI_NULL, &instr);
    if (status < VI_SUCCESS)
    {
        qDebug() << "Cannot open a session to the device.\n";
        goto Close;
    }

     /* Set the timeout to 5 seconds (5000 milliseconds). */
    status = viSetAttribute(instr, VI_ATTR_TMO_VALUE, 5000);

    /* Set the baud rate to 4800 (default is 9600). */
    status = viSetAttribute(instr, VI_ATTR_ASRL_BAUD, 4800);

    /* Set the number of data bits contained in each frame (from 5 to 8).
     * The data bits for  each frame are located in the low-order bits of
     * every byte stored in memory.
     */
    status = viSetAttribute(instr, VI_ATTR_ASRL_DATA_BITS, 8);

    status = viSetAttribute(instr, VI_ATTR_ASRL_PARITY, VI_ASRL_PAR_NONE);

    status = viSetAttribute(instr, VI_ATTR_ASRL_STOP_BITS, VI_ASRL_STOP_ONE);

    status = viSetAttribute(instr, VI_ATTR_TERMCHAR_EN, VI_TRUE);

    /* Set the termination character to 0xA
     */
    status = viSetAttribute(instr, VI_ATTR_TERMCHAR, 0xA);


    strcpy(stringinput, ":MEASure:VOLTage:DC?\n");
    //strcpy(stringinput, "*IDN?\n");
    status = viWrite(instr, (ViBuf)stringinput, (ViUInt32)strlen(stringinput), &writeCount);
    if (status < VI_SUCCESS){
        qDebug() << "Error writing to the device.\n";
        goto Close;
    }

    status = viRead(instr, buffer, 100, &retCount);
    if (status < VI_SUCCESS){
        qDebug() << "Error reading a response from the device.\n";
    }else{
        qDebug() << "Data read:" << retCount << QString::fromLocal8Bit((char*)buffer,retCount);

        ui->textBrowser->setText(QString::fromLocal8Bit((char*)buffer,retCount));
    }

Close:
    status = viClose(instr);
    status = viClose(defaultRM);

}

结果如下:

也可以用NI-MAX调试,


版权声明:本文为wy212670原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
THE END
< <上一篇
下一篇>>