技術(shù)頻道

娓娓工業(yè)
您現(xiàn)在的位置: 中國(guó)傳動(dòng)網(wǎng) > 技術(shù)頻道 > 技術(shù)百科 > 運(yùn)動(dòng)控制卡應(yīng)用開(kāi)發(fā)教程之使用Qt

運(yùn)動(dòng)控制卡應(yīng)用開(kāi)發(fā)教程之使用Qt

時(shí)間:2020-11-27 15:55:27來(lái)源:正運(yùn)動(dòng)技術(shù)

導(dǎo)語(yǔ):?正運(yùn)動(dòng)技術(shù)支持功能強(qiáng)大的Qt動(dòng)態(tài)鏈接庫(kù)以及擁有簡(jiǎn)單易讀的運(yùn)動(dòng)控制庫(kù)函數(shù)手冊(cè)說(shuō)明,代碼移植性強(qiáng),非常方便運(yùn)動(dòng)控制開(kāi)發(fā)上手,能極大縮短開(kāi)發(fā)人員開(kāi)發(fā)智能裝備的時(shí)間周期。

今天,我們來(lái)講解一下正運(yùn)動(dòng)技術(shù)運(yùn)動(dòng)控制卡應(yīng)用開(kāi)發(fā)教程之Qt。

此前,我們與大家分享過(guò)“開(kāi)放式Linux平臺(tái)控制器XPLC516E及其Linux下的Qt開(kāi)發(fā)”,我們知道正運(yùn)動(dòng)部分控制器支持Linux系統(tǒng),支持嵌入式Qt開(kāi)發(fā)。

正運(yùn)動(dòng)技術(shù)支持功能強(qiáng)大的Qt動(dòng)態(tài)鏈接庫(kù)以及擁有簡(jiǎn)單易讀的運(yùn)動(dòng)控制庫(kù)函數(shù)手冊(cè)說(shuō)明,代碼移植性強(qiáng),非常方便運(yùn)動(dòng)控制開(kāi)發(fā)上手,能極大縮短開(kāi)發(fā)人員開(kāi)發(fā)智能裝備的時(shí)間周期。

在正式學(xué)習(xí)之前,我們先了解一下正運(yùn)動(dòng)技術(shù)的運(yùn)動(dòng)控制卡ECI2418和ECI2618。這兩款產(chǎn)品分別是4軸,6軸運(yùn)動(dòng)控制卡。

ECI2418支持4軸脈沖輸入與編碼器反饋,板載24點(diǎn)輸入,16點(diǎn)輸出,2AD,2DA,支持手輪接口,其中特定輸出支持高速PWM控制。

ECI2618支持6軸脈沖輸入與編碼器反饋,板載24點(diǎn)輸入,16點(diǎn)輸出,2AD,2DA,支持手輪接口,其中特定輸出支持高速PWM控制。

ECI2418,ECI2618均使用同一套API函數(shù),均支持C、C++、C#、LabView、Python、Delphi等開(kāi)發(fā)語(yǔ)言,支持VC6.0、VB6.0、Qt、.Net等平臺(tái),支持Windows、Linux、WinCE、iMac等操作系統(tǒng)。

一、運(yùn)動(dòng)控制卡應(yīng)用之Qt開(kāi)發(fā)流程

1、使用Qt軟件新建Qt項(xiàng)目

2、將動(dòng)態(tài)庫(kù)以及相關(guān)文件“l(fā)ibzmotion.so、zaux.cpp、zaux.h、zmotion.h”復(fù)制到新建的Qt項(xiàng)目里面。

在光盤(pán)資料里面,下載上圖圈出的四個(gè)文件,并通過(guò)終端復(fù)制到新建的Qt工程里面。

3、在Qt項(xiàng)目里面添加動(dòng)態(tài)庫(kù)“l(fā)ibzmotion.so”

    A、首先右鍵項(xiàng)目,點(diǎn)擊添加庫(kù)。

    B、選擇外部庫(kù),點(diǎn)擊Next。

    C、點(diǎn)擊瀏覽庫(kù)文件,選擇剛剛復(fù)制進(jìn)去的動(dòng)態(tài)庫(kù),點(diǎn)擊Next。

    D、最后點(diǎn)擊finish即可完成動(dòng)態(tài)庫(kù)添加。

    注意事項(xiàng):Linux環(huán)境下動(dòng)態(tài)庫(kù)的名字必須是lib開(kāi)頭才能識(shí)別。

4、在Qt項(xiàng)目里面添加頭文件“zmotion.h、zaux.h”

    A、首先右鍵Headers,點(diǎn)擊Add Existing Files...

    B、找到剛剛復(fù)制放進(jìn)項(xiàng)目的zmotion.h文件,雙擊zmotion.h即可添加頭文件zmotion.h到項(xiàng)目中。

    C、重復(fù)上面兩個(gè)步驟,將zaux.h文件也添加到項(xiàng)目中。

5、在Qt項(xiàng)目里面添加cpp源文件"zaux.cpp”

    A、首先右鍵Sources,點(diǎn)擊Add Existing Files...

    B、找到剛剛復(fù)制放進(jìn)項(xiàng)目的zaux.cpp文件,雙擊zaux.cpp文件即可添加源文件zaux.cpp到項(xiàng)目中。

6、在mainwindow.h中添加 #include “zmotion.h”、 #include “zaux.h”和定義控制器的連接句柄g_handle。

7、使用link按鈕的槽函數(shù)用以太網(wǎng)連接控制器

    A、在Qt的ui設(shè)計(jì)界面中添加一個(gè)按鈕重命名為L(zhǎng)ink,右擊Link按鈕點(diǎn)擊Go to slot...跳轉(zhuǎn)到該按鈕的槽函數(shù)。

    B、查閱ZMotion PC 編程手冊(cè),了解用以太網(wǎng)連接控制器接口函數(shù)的用法 。

    C、參考光盤(pán)資料里面的PC編程手冊(cè)中ZAux_OpenEth函數(shù)的用法在槽函數(shù)中編寫(xiě)代碼,進(jìn)行功能實(shí)現(xiàn)。

8、控制器實(shí)現(xiàn)插補(bǔ)運(yùn)動(dòng),代碼實(shí)現(xiàn)過(guò)程。

    A、在Qt的ui設(shè)計(jì)界面中添加一個(gè)按鈕重命名為move,右擊move按鈕點(diǎn)擊Go to slot...跳轉(zhuǎn)到該按鈕的槽函數(shù)。

    B、查閱ZMotion PC 編程手冊(cè),了解用以插補(bǔ)運(yùn)動(dòng)接口函數(shù)的用法 。

    C、根據(jù)PC編程手冊(cè)中ZAux_Direct_Move函數(shù)的用法在槽函數(shù)中編寫(xiě)代碼,進(jìn)行功能實(shí)現(xiàn)。

9、運(yùn)動(dòng)程序設(shè)計(jì)完畢,點(diǎn)擊運(yùn)行按鈕。

    注意:上位機(jī)用以太網(wǎng)連接控制器時(shí),需要控制器和PC在同一網(wǎng)段下才能連接成功。

二、運(yùn)動(dòng)控制卡應(yīng)用之Qt例程講解

    1、在正運(yùn)動(dòng)技術(shù)的光盤(pán)資料里有很多Qt的例程,通過(guò)這些例程可以更容易的上手正運(yùn)動(dòng)技術(shù)的控制器。以下是一個(gè)詳細(xì)例程的講解。

    2、例程的單軸運(yùn)動(dòng)的功能說(shuō)明

        a、通過(guò)以太網(wǎng)鏈接到指定IP的控制器;

        b、設(shè)置運(yùn)動(dòng)軸參數(shù);

        c、選擇運(yùn)動(dòng)軸對(duì)象;

        d、選擇運(yùn)動(dòng)方式,實(shí)現(xiàn)持續(xù)運(yùn)動(dòng)和寸動(dòng);

    3、例程的單軸運(yùn)動(dòng)的具體實(shí)現(xiàn)

        (1)實(shí)現(xiàn)以網(wǎng)口方式鏈接控制器

            A、在下拉框中手動(dòng)添加IP:進(jìn)入uI設(shè)計(jì)界面雙擊下拉框加入控制器Ip,方法如下。

            B、參考ZMotion PC函數(shù)編程手冊(cè),熟悉ZAux_OpenEth()接口用法。

            C、通過(guò)Open按鈕的槽函數(shù)( on_pushButton_OpenEth_clicked()),調(diào)用動(dòng)態(tài)庫(kù)(zmotion.so)提供的鏈接控制器接口(ZAux_OpenEth()),實(shí)現(xiàn)與控制器的鏈接。

//以太網(wǎng)連接控制器
void MainWindow::on_pushButton_OpenEth_clicked()
{
    int32 iresult;
    char * tmp_buff = new char[16];
    QString str, str_title;
    /*從下拉框中獲取IP*/
    str = ui->comboBox_IP->currentText();
    QByteArray ba = str.toLatin1();
    tmp_buff = ba.data();
    /*鏈接控制器*/
    iresult = ZAux_OpenEth(tmp_buff,&g_handle);
    if(0 == iresult)
    {
        str_title = ("linked:");
        str_title += tmp_buff;
        setWindowTitle(str_title);
        /*開(kāi)啟定時(shí)器*/
        m_nTimerId = startTimer(10);
    }
    else
    {
        setWindowTitle("no link!");
    }
}

            D、參考ZMotion PC函數(shù)編程手冊(cè),熟悉ZAux_OpenEth()接口用法。

                E、通過(guò)Close按鈕的槽函數(shù)( on_pushButton_CloseEth_clicked()),調(diào)用動(dòng)態(tài)庫(kù)(zmotion.so)提供的斷開(kāi)鏈接控制器的接口(ZAux_Close()),實(shí)現(xiàn)斷開(kāi)與控制器的鏈接。

//斷開(kāi)網(wǎng)口連接
void MainWindow::on_pushButton_CloseEth_clicked()

       if(0 != g_handle)
       {
           /*斷開(kāi)鏈接*/
           ZAux_Close(g_handle);
           g_handle = NULL;
           setWindowTitle("no line");
           /*關(guān)閉定時(shí)器*/
           killTimer(m_nTimerId);
           m_nTimerId=-1;
        }
}


        (2)獲取軸運(yùn)動(dòng)的信息以及輸入輸出口的信息

        A、將X、Y、Z、R單選框設(shè)置到同一個(gè)按鈕組中用于軸選擇。

        B、通過(guò)定時(shí)器超時(shí)處理函數(shù),調(diào)用動(dòng)態(tài)庫(kù)“zmotion.so”提供的獲取軸dpos、vpspeed、idle信息的接口和輸入輸出口狀態(tài)信息獲取接口,實(shí)現(xiàn)對(duì)控制器狀態(tài)的監(jiān)控。


//定時(shí)器超時(shí)處理函數(shù)
void MainWindow::timerEvent(QTimerEvent *event)
{
    if(m_nTimerId == event->timerId())
    {
        int idle;
        float fdpos, fvspeed;
        QString str_tmp;
        /*獲取軸狀態(tài)*/
        ZAux_Direct_GetIfIdle(g_handle,AxisGroup->checkedId(),&idle);
        str_tmp = QString("Idle : %1").arg(idle?"stop":"run");
        ui->label_statue->setText(str_tmp);
        /*獲取dpos*/
        ZAux_Direct_GetDpos(g_handle,AxisGroup->checkedId(),&fdpos);
        str_tmp = QString("Dpos : %1").arg(fdpos);
        ui->label_dpos->setText(str_tmp);
        /*獲取vspeed*/
        ZAux_Direct_GetVpSpeed(g_handle,AxisGroup->checkedId(),&fvspeed);
        str_tmp = QString("Vspeed : %1").arg(fvspeed);
        ui->label_vspeed->setText(str_tmp);
        uint8 in, out, i=0,j=0,k=0;
        char  buff[128]={0};
        /*獲取輸入口狀態(tài)*/
        ZAux_GetModbusIn(g_handle, 0, 7, &in);  //獲取in0-in7狀態(tài)
        /*獲取輸出口狀態(tài)*/
        ZAux_GetModbusOut(g_handle, 0, 7, &out);//獲取out0-out7狀態(tài)
        /*十進(jìn)制轉(zhuǎn)二進(jìn)制*/
        for(i=0; i<8; i++)
        {
           buff[i]=in%2;
           in = in/2;
           if(1 >= in)
           {
               buff[i+1]=in;
               break;
           }
        }
        /*更新UI信息*/
        buff[0]? ui->checkBox_IN0->setChecked(true):ui->checkBox_IN0->setChecked(false);
        buff[1]? ui->checkBox_IN1->setChecked(true):ui->checkBox_IN1->setChecked(false);
        buff[2]? ui->checkBox_IN2->setChecked(true):ui->checkBox_IN2->setChecked(false);
        buff[3]? ui->checkBox_IN3->setChecked(true):ui->checkBox_IN3->setChecked(false);
        buff[4]? ui->checkBox_IN4->setChecked(true):ui->checkBox_IN4->setChecked(false);
        buff[5]? ui->checkBox_IN5->setChecked(true):ui->checkBox_IN5->setChecked(false);
        buff[6]? ui->checkBox_IN6->setChecked(true):ui->checkBox_IN6->setChecked(false);
        buff[7]? ui->checkBox_IN7->setChecked(true):ui->checkBox_IN7->setChecked(false);
        memset(buff,0,8);
        /*十進(jìn)制轉(zhuǎn)二進(jìn)制*/
        for(i=0; i<8; i++)
        {
           buff[i]=out%2;
           out = out/2;
           if(1 >= out)
           {
               buff[i+1]=out;
               break;
           }
        }
         /*更新UI信息*/
        buff[0]? ui->checkBox_OUT0->setChecked(true):ui->checkBox_OUT0->setChecked(false);
        buff[1]? ui->checkBox_OUT1->setChecked(true):ui->checkBox_OUT1->setChecked(false);
        buff[2]? ui->checkBox_OUT2->setChecked(true):ui->checkBox_OUT2->setChecked(false);
        buff[3]? ui->checkBox_OUT3->setChecked(true):ui->checkBox_OUT3->setChecked(false);
        buff[4]? ui->checkBox_OUT4->setChecked(true):ui->checkBox_OUT4->setChecked(false);
        buff[5]? ui->checkBox_OUT5->setChecked(true):ui->checkBox_OUT5->setChecked(false);
        buff[6]? ui->checkBox_OUT6->setChecked(true):ui->checkBox_OUT6->setChecked(false);
        buff[7]? ui->checkBox_OUT7->setChecked(true):ui->checkBox_OUT7->setChecked(false);
    }
}

        (3)軸參數(shù)設(shè)置

        通過(guò)參數(shù)生效按鈕的槽函數(shù)“on_ParaSet_clicked()”,調(diào)用動(dòng)態(tài)庫(kù)(zmotion.so)提供的獲取軸參數(shù)設(shè)置接口,對(duì)軸參數(shù)進(jìn)行設(shè)置。

//參數(shù)設(shè)置
void MainWindow::on_ParaSet_clicked()
{
    QString str_tmp;
    float float_tmp;
    int isidle = 0;
    /*獲取軸號(hào)*/
    axis_num = AxisGroup->checkedId();
    /*軸正在運(yùn)行無(wú)法運(yùn)動(dòng)*/
    ZAux_Direct_GetIfIdle(g_handle,axis_num,&isidle);
    if(!isidle)
    {
        return;
    }
    /*設(shè)置units */
    str_tmp = ui->lineEdit_Units->text();
    float_tmp = str_tmp.toFloat();
    ZAux_Direct_SetUnits(g_handle, axis_num, float_tmp);
     /*設(shè)置 speed */
    str_tmp = ui->lineEdit_Speed->text();
    float_tmp = str_tmp.toFloat();
    ZAux_Direct_SetSpeed(g_handle,axis_num,float_tmp);
     /*設(shè)置 accel */
    str_tmp = ui->lineEdit_Accel->text();
    float_tmp = str_tmp.toFloat();
    ZAux_Direct_SetAccel(g_handle,axis_num,float_tmp);
    /*設(shè)置 decel */
    str_tmp = ui->lineEdit_Decel->text();
    float_tmp = str_tmp.toFloat();
    ZAux_Direct_SetDecel(g_handle,axis_num,float_tmp);
    /*設(shè)置sramp */
    str_tmp = ui->lineEdit_Sramp->text();
    float_tmp = str_tmp.toFloat();
    ZAux_Direct_SetSramp(g_handle,axis_num,float_tmp);
}

        (4)單軸寸動(dòng)/持續(xù)運(yùn)動(dòng)

        A、通過(guò)Run按鈕的槽函數(shù)“on_pushButton_Run_clicked()”,調(diào)用動(dòng)態(tài)庫(kù)“zmotion.so”提供的相關(guān)接口函數(shù),對(duì)軸進(jìn)行運(yùn)動(dòng)控制。


//Run按鈕的槽函數(shù)

void MainWindow::on_pushButton_Run_clicked()

{

        QString str_tmp;

        float float_tmp;

        int isidle = 0;

        ZAux_Direct_GetIfIdle(g_handle,axis_num,&isidle);

        if(!isidle)

        {

            qDebug()<<"not stop";

            return;

        }

        /*示波器觸發(fā)*/

        ZAux_Trigger(g_handle);

        /*單軸運(yùn)動(dòng)*/

        if(1 == RunModeGroup->checkedId())//inch

        {

            str_tmp = ui->lineEdit_inchdis->text();

            float_tmp = str_tmp.toFloat();

            ZAux_Direct_Singl_Move(g_handle,axis_num,ui->checkBox_dir->checkState()?-float_tmp:float_tmp);

        }

        else if(0 == RunModeGroup->checkedId())//continue

        {


             ZAux_Direct_Singl_Vmove(g_handle,axis_num,ui->checkBox_dir->checkState()?-1:1);

        }

}

        B、通過(guò)Stop按鈕的槽函數(shù)“on_pushButton_Stop_clicked()”調(diào)用相關(guān)接口實(shí)現(xiàn)停止軸運(yùn)動(dòng)的功能。


//Stop按鈕的槽函數(shù)

void MainWindow::on_pushButton_Stop_clicked()

{

        int isidle = 0;

        ZAux_Direct_GetIfIdle(g_handle,AxisGroup->checkedId(),&isidle);

        if(isidle) return;

        /*單軸停止*/

        ZAux_Direct_Singl_Cancel(g_handle,AxisGroup->checkedId(),2);

}


        (5)編譯運(yùn)行調(diào)試

            在自己開(kāi)發(fā)程序連接的同時(shí),還可以通過(guò)ZDevelop來(lái)調(diào)試與診斷控制器的狀態(tài)。



        配合ZDevelop軟件進(jìn)行調(diào)試,通過(guò)ZDevelop中的軸參數(shù),輸入口,輸出口,示波器,等等小工具可以更直觀(guān)的對(duì)控制器的狀態(tài)進(jìn)行監(jiān)控。

        在示波器窗口中可以看到單軸移動(dòng)300用戶(hù)單位的曲線(xiàn)圖。

        今天,正運(yùn)動(dòng)技術(shù)的運(yùn)動(dòng)控制卡應(yīng)用開(kāi)發(fā)教程之Qt就分享到這里。更多精彩內(nèi)容,請(qǐng)關(guān)注我們的公眾號(hào)。

        本文由正運(yùn)動(dòng)小助手原創(chuàng),歡迎大家轉(zhuǎn)載,共同學(xué)習(xí),一起提高中國(guó)智能制造水平。文章版權(quán)歸正運(yùn)動(dòng)技術(shù)所有,如有轉(zhuǎn)載請(qǐng)注明文章來(lái)源。

    

36.png


標(biāo)簽: 運(yùn)動(dòng)控制卡

點(diǎn)贊

分享到:

上一篇:運(yùn)動(dòng)控制卡應(yīng)用開(kāi)發(fā)教程之VC6.0

下一篇:正運(yùn)動(dòng)技術(shù)XPLC516E 的開(kāi)放式...

中國(guó)傳動(dòng)網(wǎng)版權(quán)與免責(zé)聲明:凡本網(wǎng)注明[來(lái)源:中國(guó)傳動(dòng)網(wǎng)]的所有文字、圖片、音視和視頻文件,版權(quán)均為中國(guó)傳動(dòng)網(wǎng)(www.treenowplaneincome.com)獨(dú)家所有。如需轉(zhuǎn)載請(qǐng)與0755-82949061聯(lián)系。任何媒體、網(wǎng)站或個(gè)人轉(zhuǎn)載使用時(shí)須注明來(lái)源“中國(guó)傳動(dòng)網(wǎng)”,違反者本網(wǎng)將追究其法律責(zé)任。

本網(wǎng)轉(zhuǎn)載并注明其他來(lái)源的稿件,均來(lái)自互聯(lián)網(wǎng)或業(yè)內(nèi)投稿人士,版權(quán)屬于原版權(quán)人。轉(zhuǎn)載請(qǐng)保留稿件來(lái)源及作者,禁止擅自篡改,違者自負(fù)版權(quán)法律責(zé)任。