an asynchronous open procedure

This commit is contained in:
Kevin Matz 2023-04-16 21:13:11 -04:00
parent eb25959c08
commit a34ada6da5
3 changed files with 25 additions and 32 deletions

View File

@ -30,6 +30,10 @@ DmxWidget::DmxWidget(QObject *parent)
{
connect(this, &DmxWidget::serialDataRead, this, &DmxWidget::parseMessageBuffer);
connect(port_, &QSerialPort::errorOccurred, this, &DmxWidget::serialErrorOccured);
connect(port_, &QSerialPort::readyRead, this, [this]() {
message_rx_buffer_.append(port_->readAll());
emit serialDataRead();
});
}
@ -41,46 +45,32 @@ DmxWidget::~DmxWidget()
void DmxWidget::open()
{
if (!port_->open(QIODeviceBase::ReadWrite))
return;
ENTTEC::Widget::open();
qInfo() << "Port opened on" << port_->portName();
getSerialNumber();
getParameters(0);
if (port_->waitForReadyRead(500) && port_->bytesAvailable() >= 19)
{
char snhead[] = {ENTTEC::Pro::START_DELIMITER,
ENTTEC::Pro::OpGetWidgetSerial,
0x04, 0x00}; // expect 4 bytes of message data
message_rx_buffer_.append(port_->readAll());
if (!message_rx_buffer_.startsWith(snhead))
{
message_rx_buffer_.clear();
close();
return;
auto wait_for = [this](bool &reply) {
reply = false; // reset the reply state variale
for (int i = 0; i < 10; i++) { // serial reply may not be first in the read buffer
port_->waitForReadyRead(100); // wait for the port read buffer to have content
if (reply)
break; // break the loop if a reply was received
}
parseMessageBuffer();
}
else
{
close();
return;
}
return reply;
};
connect(port_, &QSerialPort::readyRead, this, [this]() {
message_rx_buffer_.append(port_->readAll());
emit serialDataRead();
});
emit connectedChanged(isConnected());
if (!port_->open(QIODeviceBase::ReadWrite)) // open the port
return;
ENTTEC::Widget::open(); // open the base class widget
getSerialNumber(); // request a serial number
getParameters(0); // get the metadata while we're here
if (wait_for(reply_serial)) // widget is found if a serial number reply is received
emit connectedChanged(isConnected());
else
close();
}
void DmxWidget::close()
{
port_->close();
disconnect(port_, &QSerialPort::readyRead, nullptr, nullptr);
ENTTEC::Widget::close();
emit connectedChanged(isConnected());
}

View File

@ -754,6 +754,7 @@ void Widget::rxMsgGetWidgetSerialReply(std::shared_ptr<Pro::MsgGetWidgetSerialRe
{
std::scoped_lock lock(mtx_metadata_);
serial_number = msg->serial;
reply_serial = true;
}

View File

@ -125,6 +125,8 @@ protected:
std::vector<uint8_t> user_configuration; //!< User defined configuration data.
OperatingMode usb_mode; //!< The side of the USB the widget is acting on.
bool reply_serial; //!< receiving a serialnumber will set to true
private:
void rxMsgHello();
void rxMsgReprogramFirmware();