Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Write ASCII Character and read response using serialport
Forum Updated to NodeBB v4.3 + New Features

Write ASCII Character and read response using serialport

Scheduled Pinned Locked Moved Solved General and Desktop
15 Posts 3 Posters 2.0k Views 2 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • H Offline
    H Offline
    H.dragon
    wrote on last edited by H.dragon
    #4

    Sorry for the late reply.
    After reading @mrjj 's answer, I added readyRead.

    // Constructor
    MotorPort::MotorPort(QSerialPort* parent) : QSerialPort(parent)
    {
        // Connect signals to slots.
        connect(this, SIGNAL(readyRead()), this, SLOT(getData()));
    
        // Default port connection parameters.
    
        defaultBaudRate = QSerialPort::Baud9600;
        defaultDataBits = QSerialPort::Data8;
        defaultStopBits = QSerialPort::OneStop;
        defaultParity   = QSerialPort::NoParity;
    
    }
    
    // Destructor
    MotorPort::~MotorPort()
    {
    
    }
    
    bool MotorPort::openMotorPort(const QString &portName)
    {
        setPortName(portName);
        setBaudRate(defaultBaudRate);
        setDataBits(defaultDataBits);
        setStopBits(defaultStopBits);
        setParity(defaultParity);
        bool openning;
        opening = open(QIODevice::ReadWrite);
        return openning;
    }
    
    void MotorPort::getData()
    {
        Output = QIODevice::readAll(); // Output(QByteArray) is private member of MotorPort
    }
    
    QByteArray MotorPort::getresponse()
    {
        QByteArray buffer = "?";
        write(buffer);
        getData();
        return Output;
    }
    

    and in mainwindow.cpp

    bool open = rls->openMotorPort("COM5");
    if (open==true)
    {
        ui->statusencoder->append("success");
        QByteArray data=rls->getresponse();
        ui->statusencoder->append(QString(data));
        int array[10]; //I tried to choose return value type as int
        for (int i=0;i<10;i++)
         {
                array[i]=7;
                ui->statusencoder->append(QString::number(array[i]));
                array[i]=data[i];
                ui->statusencoder->append(QString::number(array[i]));
          }
    
    }
    

    After running this code, My QTextBrowser(statusencoder) shows like this one

    success
    
    7
    0
    7
    0
    7
    0
    7
    0
    7
    0
    7
    0
    7
    0
    7
    0
    7
    0
    7
    0
    

    the reference software says encoder's position is 3.032mm. so I expect any different value. but QByteArray data seems to be NULL. Am I still making code wrong?

    1 Reply Last reply
    0
    • mrjjM Offline
      mrjjM Offline
      mrjj
      Lifetime Qt Champion
      wrote on last edited by mrjj
      #5

      Hi
      Its asynchronous so i think the issue lies here

      QByteArray MotorPort::getresponse()
      {
          QByteArray buffer = "?";
          write(buffer); // send 
          getData();// you just call it so might be nothing to read yet.  its not called by serialport due to incoming data
          return Output;
      }
      

      So you cant really do it this way. it has to be like this

      You send something
      Serialport issues one or more readyRead signals
      in getData you read and append to a buffer

      Output += QIODevice::readAll(); // note the plus

      then when data contains a CR, we know you got full set.
      Then you can send signal to mainWindow that data is ready.
      and it that slot in main window, you can then use the data.

      I know it seems a bit complicated but thats how async programming is.

      If you really find it hard to get work, you can use the blocking api of QSrialport
      https://doc.qt.io/qt-5/qtserialport-creadersync-example.html

      But do note that this LAGS the GUI. gui will not redraw etc while code is running and that is
      why the async way with signal and slot is preferred.

      H 1 Reply Last reply
      5
      • mrjjM mrjj

        Hi
        Its asynchronous so i think the issue lies here

        QByteArray MotorPort::getresponse()
        {
            QByteArray buffer = "?";
            write(buffer); // send 
            getData();// you just call it so might be nothing to read yet.  its not called by serialport due to incoming data
            return Output;
        }
        

        So you cant really do it this way. it has to be like this

        You send something
        Serialport issues one or more readyRead signals
        in getData you read and append to a buffer

        Output += QIODevice::readAll(); // note the plus

        then when data contains a CR, we know you got full set.
        Then you can send signal to mainWindow that data is ready.
        and it that slot in main window, you can then use the data.

        I know it seems a bit complicated but thats how async programming is.

        If you really find it hard to get work, you can use the blocking api of QSrialport
        https://doc.qt.io/qt-5/qtserialport-creadersync-example.html

        But do note that this LAGS the GUI. gui will not redraw etc while code is running and that is
        why the async way with signal and slot is preferred.

        H Offline
        H Offline
        H.dragon
        wrote on last edited by
        #6

        @mrjj
        Hi. I read your answer but It is a little difficult for me to understand the concept of asynchronous, I googled it and some functions, I changed MotorPort::getresponse() like below. then it works

        QByteArray MotorPort::getresponse()
        {
            QByteArray buffer = "?";
            write(buffer);
            waitForReadyRead(500);
            return Output;
        }
        

        Is this the solution of your answer? Actually I don't think I fully understood your answer.
        Anyway, Thank you mrjj!

        mrjjM 1 Reply Last reply
        1
        • H H.dragon

          @mrjj
          Hi. I read your answer but It is a little difficult for me to understand the concept of asynchronous, I googled it and some functions, I changed MotorPort::getresponse() like below. then it works

          QByteArray MotorPort::getresponse()
          {
              QByteArray buffer = "?";
              write(buffer);
              waitForReadyRead(500);
              return Output;
          }
          

          Is this the solution of your answer? Actually I don't think I fully understood your answer.
          Anyway, Thank you mrjj!

          mrjjM Offline
          mrjjM Offline
          mrjj
          Lifetime Qt Champion
          wrote on last edited by
          #7

          @H-dragon
          Hi
          asynchronous means it will happen at another point in time (than right now) and yes it can be
          difficult to handle.

          You used the blocking call
          waitForReadyRead(500);
          so yes that was what i meant in the second part of the answer.
          Even now you kinda mix sync and async but it seems that it fires in right order
          so it works :)

          1 Reply Last reply
          3
          • H Offline
            H Offline
            H.dragon
            wrote on last edited by H.dragon
            #8

            @mrjj
            HI.
            Can I ask you one last question?

            QByteArray MotorPort::getresponse()
            {
                QByteArray buffer = "?";
                write(buffer);
                waitForReadyRead(500);
                return Output;
            }
            

            How the private member Output gets some data from serialport when I call the function getresponse(), although there isnt the function getData()? As I know, the waitForReadyRead(500) blocks the cell until new data is available.
            Is that because I connected signal to slots? (connect(this, SIGNAL(readyRead()), this, SLOT(getData()));)
            Thank you for your continued kindness :)

            mrjjM 1 Reply Last reply
            0
            • H H.dragon

              @mrjj
              HI.
              Can I ask you one last question?

              QByteArray MotorPort::getresponse()
              {
                  QByteArray buffer = "?";
                  write(buffer);
                  waitForReadyRead(500);
                  return Output;
              }
              

              How the private member Output gets some data from serialport when I call the function getresponse(), although there isnt the function getData()? As I know, the waitForReadyRead(500) blocks the cell until new data is available.
              Is that because I connected signal to slots? (connect(this, SIGNAL(readyRead()), this, SLOT(getData()));)
              Thank you for your continued kindness :)

              mrjjM Offline
              mrjjM Offline
              mrjj
              Lifetime Qt Champion
              wrote on last edited by
              #9

              @H-dragon
              Hi
              Yes its due to the readyRead signal calling getData() and fill Output.
              So we kinda mixed async and sync calls.
              But docs says
              "This function blocks until new data is available for reading and the readyRead() signal has been emitted. "
              https://doc.qt.io/qt-5/qserialport.html#waitForReadyRead

              so it does come in right order and then it worked.

              1 Reply Last reply
              4
              • H Offline
                H Offline
                H.dragon
                wrote on last edited by
                #10

                @mrjj
                Hi. Thanks to you, I completed my GUI work. I really appreciate it.
                But while writing codes, I came up with a question.
                In your second answer, you changed Output = QIODevice::readAll() to Output += QIODevice::readAll().
                Can you explain why the former doesn't work(my gui terminate)? is it related with asynchronous?

                mrjjM 1 Reply Last reply
                0
                • H H.dragon

                  @mrjj
                  Hi. Thanks to you, I completed my GUI work. I really appreciate it.
                  But while writing codes, I came up with a question.
                  In your second answer, you changed Output = QIODevice::readAll() to Output += QIODevice::readAll().
                  Can you explain why the former doesn't work(my gui terminate)? is it related with asynchronous?

                  mrjjM Offline
                  mrjjM Offline
                  mrjj
                  Lifetime Qt Champion
                  wrote on last edited by mrjj
                  #11

                  Hi
                  Good to hear
                  Well there is only a small difference

                  This overwrites all that already is in Output
                  Output = QIODevice::readAll()

                  This Adds to what is already is in Output
                  Output += QIODevice::readAll().

                  The last is the best due to the following reason.

                  When you sent something big enough over serial - it will result in multiple pieces of data
                  so the readyRead() will trigger more than one time.

                  So in such cases,
                  one has to add the incoming data to a buffer as to collect it all

                  • before using it.
                    and that is what
                    Output += QIODevice::readAll().
                    does. Add data to the Output buffer.

                  So that is something to keep in mind.

                  1 Reply Last reply
                  3
                  • H Offline
                    H Offline
                    H.dragon
                    wrote on last edited by
                    #12

                    @mrjj
                    Do I understand well?
                    for example, let's say something big data (123456789) is divided into multiple pieces(123, 456, 789).

                    If I use Output = QIODevice::readAll(), it can cause follow situation
                    readyRead()
                    Output is 123
                    readyRead()
                    Output is 456
                    readyRead()
                    Output is 789

                    but when I use Output+=QIODevice::readAll(),
                    readyRead()
                    Output is 123
                    readyRead()
                    Output is 123456
                    readyRead()
                    Output is 123456789

                    The reason += is the best is It can prevent the former situation. right?

                    mrjjM 1 Reply Last reply
                    0
                    • H H.dragon

                      @mrjj
                      Do I understand well?
                      for example, let's say something big data (123456789) is divided into multiple pieces(123, 456, 789).

                      If I use Output = QIODevice::readAll(), it can cause follow situation
                      readyRead()
                      Output is 123
                      readyRead()
                      Output is 456
                      readyRead()
                      Output is 789

                      but when I use Output+=QIODevice::readAll(),
                      readyRead()
                      Output is 123
                      readyRead()
                      Output is 123456
                      readyRead()
                      Output is 123456789

                      The reason += is the best is It can prevent the former situation. right?

                      mrjjM Offline
                      mrjjM Offline
                      mrjj
                      Lifetime Qt Champion
                      wrote on last edited by
                      #13

                      @H-dragon
                      Hi
                      Yes that is exactly like that.

                      When it will be broken up depends on the hardware. some have bigger buffers than others and
                      so on but it does happen.

                      H 1 Reply Last reply
                      1
                      • mrjjM mrjj

                        @H-dragon
                        Hi
                        Yes that is exactly like that.

                        When it will be broken up depends on the hardware. some have bigger buffers than others and
                        so on but it does happen.

                        H Offline
                        H Offline
                        H.dragon
                        wrote on last edited by
                        #14

                        Thanks!!

                        mrjjM 1 Reply Last reply
                        1
                        • H H.dragon

                          Thanks!!

                          mrjjM Offline
                          mrjjM Offline
                          mrjj
                          Lifetime Qt Champion
                          wrote on last edited by
                          #15

                          @H-dragon

                          Np.

                          In your concrete use case, all feedback from the hardware ends with CR
                          so its easy to spot when you have read all data.

                          In other cases one has to look at size to know if
                          all has been read.

                          1 Reply Last reply
                          1

                          • Login

                          • Login or register to search.
                          • First post
                            Last post
                          0
                          • Categories
                          • Recent
                          • Tags
                          • Popular
                          • Users
                          • Groups
                          • Search
                          • Get Qt Extensions
                          • Unsolved