Status Flags added

This commit is contained in:
Sally Marcher 2025-07-22 12:20:34 +02:00
parent d820980920
commit 4368db004d
11 changed files with 274 additions and 13 deletions

View file

@ -7,7 +7,7 @@ set(CMAKE_AUTOUIC ON)
set(CMAKE_AUTOMOC ON)
set(CMAKE_AUTORCC ON)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD 23)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
find_package(QT NAMES Qt6 REQUIRED COMPONENTS Widgets Network Core5Compat Charts)
@ -36,6 +36,7 @@ if(${QT_VERSION_MAJOR} GREATER_EQUAL 6)
${PROJECT_SOURCES}
systemconfiguration.h systemconfiguration.cpp systemconfiguration.ui
connectionconfiguration.h connectionconfiguration.cpp connectionconfiguration.ui
viewdebugstatus.h viewdebugstatus.cpp viewdebugstatus.ui
)
# Define target properties for Android with Qt 6 as:

View file

@ -10,8 +10,11 @@ MainWindow::MainWindow(QWidget *parent)
spinner = ui->spinner;
connect(ui->actionConfiguration, SIGNAL(triggered()), &systemConfigWindow, SLOT(show()));
connect(ui->actionConnConfiguration, SIGNAL(triggered()), &connConf, SLOT(show()));
connect(ui->actionDebugStatus, SIGNAL(triggered()), &vdebug, SLOT(show()));
connect(&ctrl, &ShimLCController::connectionStateChanged, this, &MainWindow::updateConnectionState);
connect(ui->actionReconnect, &QAction::triggered, this, &MainWindow::reconnect);
connect(&ctrl, &ShimLCController::newConfigAv, this, &MainWindow::updateAvDevices);
connect(&ctrl, &ShimLCController::newStatusAv, this, &MainWindow::updateStatus);
spinner->setRoundness(70.0);
spinner->setMinimumTrailOpacity(15.0);
@ -74,3 +77,32 @@ void MainWindow::reconnect()
ctrl.reconnect(&settings);
ctrl.updateConfig();
}
void MainWindow::updateAvDevices()
{
ui->pumpsSelectorBox->clear();
for(int i=0; i<ctrl.configuration.pumps.length(); i++)
ui->pumpsSelectorBox->addItem(QString("%1").arg(QString("ABC").at(i)));
ui->detectorSelectorBox->clear();
foreach(LCPort item, ctrl.configuration.detectors)
ui->detectorSelectorBox->addItem(QString("Port %1: %2").arg(item.port).arg(item.name));
ctrl.updateStatus();
}
void MainWindow::updateStatus()
{
// Stats
vdebug.updateStatus(ctrl.lastStatus);
// Autospampler
ui->autoSamplerStatus->setText(QString("Rack: %1").arg(ctrl.lastStatus.autosampler.rack));
// Pumps
ui->pumpPress->display(ctrl.lastStatus.pump[ui->pumpsSelectorBox->currentIndex()].actPressure);
ui->pumpFlow->setValue(ctrl.lastStatus.pump[ui->pumpsSelectorBox->currentIndex()].setFlow); // TODO: Not update if currently highlighted
// Detectors
ui->detectorNmSpinBox->setValue(ctrl.lastStatus.detector[ui->detectorSelectorBox->currentIndex()].waveLen1);
}

View file

@ -8,6 +8,7 @@
#include "connectionconfiguration.h"
#include "zoomablechart.h"
#include "zoomablechartview.h"
#include "viewdebugstatus.h"
#include "QtWaitingSpinner/waitingspinnerwidget.h"
QT_BEGIN_NAMESPACE
@ -30,11 +31,14 @@ private:
ShimLCController ctrl{this};
SystemConfiguration systemConfigWindow{&ctrl, this};
ConnectionConfiguration connConf{&settings, &ctrl, this};
ViewDebugStatus vdebug{};
ZoomableChart* mainChart = nullptr;
WaitingSpinnerWidget* spinner = nullptr;
private slots:
void updateConnectionState(QAbstractSocket::SocketState state);
void reconnect();
void updateAvDevices();
void updateStatus();
};
#endif // MAINWINDOW_H

View file

@ -40,6 +40,9 @@
<layout class="QGridLayout" name="gridLayout_2">
<item row="2" column="0">
<widget class="QComboBox" name="pumpsSelectorBox">
<property name="enabled">
<bool>true</bool>
</property>
<property name="maximumSize">
<size>
<width>16777215</width>
@ -254,7 +257,11 @@
</widget>
</item>
<item>
<widget class="QComboBox" name="pumpsSelectorBox_2"/>
<widget class="QComboBox" name="detectorSelectorBox">
<property name="enabled">
<bool>true</bool>
</property>
</widget>
</item>
<item>
<layout class="QGridLayout" name="gridLayout_7">
@ -266,10 +273,17 @@
</widget>
</item>
<item row="1" column="0">
<widget class="QLCDNumber" name="lcdNumber_2"/>
<widget class="QLCDNumber" name="detectormAU"/>
</item>
<item row="0" column="0">
<widget class="QDoubleSpinBox" name="pumpFlow_2"/>
<widget class="QDoubleSpinBox" name="detectorNmSpinBox">
<property name="decimals">
<number>0</number>
</property>
<property name="maximum">
<double>10000.000000000000000</double>
</property>
</widget>
</item>
<item row="0" column="1">
<widget class="QLabel" name="label_8">
@ -430,8 +444,15 @@
<addaction name="actionConnConfiguration"/>
<addaction name="actionReconnect"/>
</widget>
<widget class="QMenu" name="menuView">
<property name="title">
<string>View</string>
</property>
<addaction name="actionDebugStatus"/>
</widget>
<addaction name="menuQtChroma"/>
<addaction name="menuConnection"/>
<addaction name="menuView"/>
</widget>
<widget class="QStatusBar" name="statusbar"/>
<action name="actionConfiguration">
@ -457,6 +478,11 @@
<string>Reconnect</string>
</property>
</action>
<action name="actionDebugStatus">
<property name="text">
<string>DebugStatus</string>
</property>
</action>
</widget>
<customwidgets>
<customwidget>

View file

@ -397,7 +397,14 @@ void ShimLCController::parseLcnf(uint32_t idVal)
QString version = QString(snippet.mid(18,4)).split('\x00').at(0);
QString serial = QString(snippet.mid(22,12)).split('\x00').at(0);
qDebug() << "Device Config:" << i+1 << id << name << version << serial;
configuration.append(LCPort(i+1, id, name, version, serial));
if(name.left(2).compare("LC") == 0)
configuration.pumps.append(LCPort(i+1, id, name, version, serial));
else if(name.left(3).compare("SPD") == 0)
configuration.detectors.append(LCPort(i+1, id, name, version, serial));
else if(id != 0)
configuration.other.append(LCPort(i+1, id, name, version, serial));
}
emit newConfigAv();
disconnect(&cmd, &ShimLCCommandStack::dataAvailable, this, &ShimLCController::parseLcnf);
@ -414,6 +421,17 @@ void ShimLCController::parseStatus(uint32_t idVal)
time += data.mid(354+i,1).toHex().toInt(nullptr, 16) << 8*i;
lastStatus.time = time;
// --- STATUS ---
lastStatus.stats.silst = 0;
lastStatus.stats.status1 = 0;
lastStatus.stats.status2 = 0;
for(int i = 0; i<4; i++)
{
lastStatus.stats.silst += data.mid(4+19+i,1).toHex().toUInt(nullptr, 16) << 8*i;
lastStatus.stats.status1 += data.mid(4+587+i,1).toHex().toUInt(nullptr, 16) << 8*i;
lastStatus.stats.status2 += data.mid(4+591+i,1).toHex().toUInt(nullptr, 16) << 8*i;
}
// --- PUMPS ---
// Pressure is at A: data[4:8], B: data[8:12], C:[12:16] encoded in int LE! Unit: wtf... Conversion was done via curve fitting!

View file

@ -135,6 +135,21 @@ struct LCPump
float setFlow;
};
/* Combined status struct
* SIL Status, Status 1 and Status 2 Params
* The label lists contain the label for the corrosponding bit (1, 2, 4, 8 ...)
* Empty String means unknown
*/
struct Stats
{
uint32_t silst;
uint32_t status1;
uint32_t status2;
const QStringList silst_labels = {"INSTALED", "INJECT", "TRANSMIT", "RINSE", "?16", "ERROR", "STOP"};
const QStringList status1_labels = {"READY", "CTONOTREADY", "RUN", "PAUSE", "?16", "HOLD", "ERROR", "?128", "ACTIVATE", "?512", "?1024", "PURGE", "?4096", "?8192", "WAITCTO", "SLEEP", "WARNING", "?131072", "PUMPAON", "PUMPBON", "PUMPCON", "PUMPDON", "?4194304", "?8388608", "?16777216", "?33554432", "CTOAON", "CTOBON", "CTOCON", "CTODON"};
const QStringList status2_labels = {"PPURGING_A", "PPURGING_B", "PPURGING_C", "PPURGING_D", "?16", "PUMPON", "OVENON", "?128", "?256", "?512", "?1024", "?2048", "?4096", "?8192", "?16384", "?32768", "?65536", "?131072", "?262144", "INJECT_READY", "?1048576", "?2097152", "?4194304", "?8388608", "?16777216", "?33554432", "?67108864", "IPURGING_R0", "IPURGING_R1", "IPURGING_R2", "IPURGING_RNS", "IPURGING_INJ"};
};
/* Param [Unit] | Range | Step | Default ... Desc
* WAVE [nm] | 190 - 600 | 1 | 254 ... Wavelength 1 (D2)
* WAVE2 [nm] | 190 - 600 | 1 | 254 ... Wavelength 2 (D2)
@ -160,6 +175,22 @@ struct LCStatus
LCDetector detector[2]{};
LCAutosampler autosampler{};
float totalFlow = 0; // Total flow rate in gradient pumping
uint num_pumps = 0; // Set by
uint num_detectors = 0;
Stats stats;
};
// Config struct - TODO: Catigorize compleatly!
struct LCconfiguration
{
QList<LCPort> pumps{};
QList<LCPort> detectors{};
QList<LCPort> other{};
void clear() {
pumps.clear();
detectors.clear();
other.clear();
}
};
class CmdVal : public QObject
@ -226,7 +257,8 @@ public:
void updateConfig();
void updateStatus();
void reconnect(QSettings *settings);
QList<LCPort> configuration{};
LCconfiguration configuration{};
LCStatus lastStatus{};
explicit ShimLCController(QObject *parent = nullptr);
~ShimLCController();
@ -242,7 +274,6 @@ private:
uint32_t ids[2]; // 0 - config / 1 - status
ShimLCCommandStack cmd{};
QByteArray data{};
LCStatus lastStatus{};
};
#endif // SHIMLCCONTROLLER_H

View file

@ -18,11 +18,22 @@ SystemConfiguration::~SystemConfiguration()
void SystemConfiguration::updateTable()
{
qDebug("Hi");
for(int i = 0; i<12; i++)
foreach(LCPort device, cmd->configuration.detectors)
{
config_view_model.tableData[i][0] = cmd->configuration.at(i).name;
config_view_model.tableData[i][1] = cmd->configuration.at(i).version;
config_view_model.tableData[i][2] = cmd->configuration.at(i).serial;
config_view_model.tableData[device.port][0] = device.name;
config_view_model.tableData[device.port][1] = device.version;
config_view_model.tableData[device.port][2] = device.serial;
}
foreach(LCPort device, cmd->configuration.pumps)
{
config_view_model.tableData[device.port][0] = device.name;
config_view_model.tableData[device.port][1] = device.version;
config_view_model.tableData[device.port][2] = device.serial;
}
foreach(LCPort device, cmd->configuration.other)
{
config_view_model.tableData[device.port][0] = device.name;
config_view_model.tableData[device.port][1] = device.version;
config_view_model.tableData[device.port][2] = device.serial;
}
}

View file

@ -22,7 +22,7 @@ public:
for (int row = 0; row < 12; ++row) {
QList<QString> rowData;
for (int col = 0; col < 3; ++col) {
rowData.append(QString("Loading..."));
rowData.append(QString("-"));
}
tableData.append(rowData);
}

47
viewdebugstatus.cpp Normal file
View file

@ -0,0 +1,47 @@
#include "viewdebugstatus.h"
#include "ui_viewdebugstatus.h"
ViewDebugStatus::ViewDebugStatus(QWidget *parent)
: QDialog(parent)
, ui(new Ui::ViewDebugStatus)
{
ui->setupUi(this);
ui->listWidget->addItem("No data!");
}
ViewDebugStatus::~ViewDebugStatus()
{
delete ui;
}
void ViewDebugStatus::updateStatus(LCStatus &status)
{
ui->listWidget->clear();
uint32_t i = 0;
ui->listWidget->addItem(QString(">> SILST = %1").arg(status.stats.silst));
foreach(QString itm, status.stats.silst_labels)
{
if(status.stats.silst & (0b1 << i))
ui->listWidget->addItem(QString("\t%1").arg(itm));
i++;
}
i = 0;
ui->listWidget->addItem(QString(">> STATUS1 = %1").arg(status.stats.status1));
foreach(QString itm, status.stats.status1_labels)
{
if(status.stats.status1 & (0b1 << i))
ui->listWidget->addItem(QString("\t%1").arg(itm));
i++;
}
i = 0;
ui->listWidget->addItem(QString(">> STATUS2 = %1").arg(status.stats.status2));
foreach(QString itm, status.stats.status2_labels)
{
if(status.stats.status2 & (0b1 << i))
ui->listWidget->addItem(QString("\t%1").arg(itm));
i++;
}
}

24
viewdebugstatus.h Normal file
View file

@ -0,0 +1,24 @@
#ifndef VIEWDEBUGSTATUS_H
#define VIEWDEBUGSTATUS_H
#include <QDialog>
#include "shimlccontroller.h"
namespace Ui {
class ViewDebugStatus;
}
class ViewDebugStatus : public QDialog
{
Q_OBJECT
public:
explicit ViewDebugStatus(QWidget *parent = nullptr);
~ViewDebugStatus();
void updateStatus(LCStatus &status);
private:
Ui::ViewDebugStatus *ui;
};
#endif // VIEWDEBUGSTATUS_H

67
viewdebugstatus.ui Normal file
View file

@ -0,0 +1,67 @@
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>ViewDebugStatus</class>
<widget class="QDialog" name="ViewDebugStatus">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>400</width>
<height>300</height>
</rect>
</property>
<property name="windowTitle">
<string>Dialog</string>
</property>
<layout class="QVBoxLayout" name="verticalLayout">
<item>
<widget class="QListWidget" name="listWidget"/>
</item>
<item>
<widget class="QDialogButtonBox" name="buttonBox">
<property name="orientation">
<enum>Qt::Horizontal</enum>
</property>
<property name="standardButtons">
<set>QDialogButtonBox::Cancel|QDialogButtonBox::Ok</set>
</property>
</widget>
</item>
</layout>
</widget>
<resources/>
<connections>
<connection>
<sender>buttonBox</sender>
<signal>accepted()</signal>
<receiver>ViewDebugStatus</receiver>
<slot>accept()</slot>
<hints>
<hint type="sourcelabel">
<x>248</x>
<y>254</y>
</hint>
<hint type="destinationlabel">
<x>157</x>
<y>274</y>
</hint>
</hints>
</connection>
<connection>
<sender>buttonBox</sender>
<signal>rejected()</signal>
<receiver>ViewDebugStatus</receiver>
<slot>reject()</slot>
<hints>
<hint type="sourcelabel">
<x>316</x>
<y>260</y>
</hint>
<hint type="destinationlabel">
<x>286</x>
<y>274</y>
</hint>
</hints>
</connection>
</connections>
</ui>