added calibration file loading to device config

This commit is contained in:
Blake Leverington 2024-08-06 14:16:57 +02:00
parent 2dbe657e2f
commit 18b22d87d5
12 changed files with 277 additions and 31 deletions

View File

@ -79,6 +79,9 @@ void DataReceiver::readData()
rms.sigma = BYTES2SHORT(tmpBuffer+baseaddr+DATA_PACKET_HEADER_SIZE+DATA_SYNC_HEADER_SIZE+DATA_BLOCK_SIZE + 2); rms.sigma = BYTES2SHORT(tmpBuffer+baseaddr+DATA_PACKET_HEADER_SIZE+DATA_SYNC_HEADER_SIZE+DATA_BLOCK_SIZE + 2);
rms.max = BYTES2SHORT(tmpBuffer+baseaddr+DATA_PACKET_HEADER_SIZE+DATA_SYNC_HEADER_SIZE+DATA_BLOCK_SIZE + 4); rms.max = BYTES2SHORT(tmpBuffer+baseaddr+DATA_PACKET_HEADER_SIZE+DATA_SYNC_HEADER_SIZE+DATA_BLOCK_SIZE + 4);
rms.status = BYTES2SHORT(tmpBuffer+baseaddr+DATA_PACKET_HEADER_SIZE+DATA_SYNC_HEADER_SIZE+DATA_BLOCK_SIZE + 6); rms.status = BYTES2SHORT(tmpBuffer+baseaddr+DATA_PACKET_HEADER_SIZE+DATA_SYNC_HEADER_SIZE+DATA_BLOCK_SIZE + 6);
for (unsigned int ii = 0; ii < 4; ii++)
rms.registers[ii] = BYTES2SHORT(tmpBuffer+baseaddr+DATA_PACKET_HEADER_SIZE+DATA_SYNC_HEADER_SIZE+DATA_BLOCK_SIZE + 8+ii*2);
data_to_push.rms_frame = rms; data_to_push.rms_frame = rms;
dataBuffer.push(data_to_push); dataBuffer.push(data_to_push);

View File

@ -111,10 +111,18 @@
//Slow control snapshot - read all channels of ADC //Slow control snapshot - read all channels of ADC
#define COMMAND_SET_CLUSTER_THRESHOLD 0x4001 #define COMMAND_SET_CLUSTER_THRESHOLD 0x4001
//L: ? //L: 1
//D: [] //D: []
//Send 8 bit beam cluster selection threshold //Send 8 bit beam cluster selection threshold
#define COMMAND_SET_CLUSTER_SIZE 0x4002
//L: 1
#define COMMAND_SET_CALIBRATION_FACTOR 0x4003
//L: 320*16bit
//D: []
// ***DATA TRANSFER - SOCKET 1!!!!*** // ***DATA TRANSFER - SOCKET 1!!!!***
#define COMMAND_DATA_TRANSFER 0x8000 #define COMMAND_DATA_TRANSFER 0x8000

View File

@ -494,4 +494,38 @@ int Device::ctrlSetClusterThreshold(int threshold)
return queryCtrl(COMMAND_SET_CLUSTER_THRESHOLD, txdata, rxdata); return queryCtrl(COMMAND_SET_CLUSTER_THRESHOLD, txdata, rxdata);
} }
int Device::ctrlSetClusterSize(int size)
{
QVector<unsigned short> rxdata;
QVector<unsigned short> txdata;
txdata.append((unsigned short)size);
if (size)
return queryCtrl(COMMAND_SET_CLUSTER_SIZE, txdata, rxdata);
else
return queryCtrl(COMMAND_SET_CLUSTER_SIZE, txdata, rxdata);
}
int Device::ctrlSetCalibrationFactor(int calibrationFactor[320])
{
// Check for null pointer to ensure valid input
if (calibrationFactor == nullptr)
{
// Handle the error case: log it, return an error code, or throw an exception
return -1; // Or handle as appropriate
}
QVector<unsigned short> rxdata;
QVector<unsigned short> txdata;
// Append each calibration factor to txdata
for (int i = 0; i < 320; ++i)
{
txdata.append(static_cast<unsigned short>(calibrationFactor[i]));
}
// Perform the queryCtrl operation with the populated txdata
return queryCtrl(COMMAND_SET_CALIBRATION_FACTOR, txdata, rxdata);
}

View File

@ -34,22 +34,32 @@ public:
int gain; //0 (low) or 1 (high); TO BE DONE int gain; //0 (low) or 1 (high); TO BE DONE
int dma_bunch; int dma_bunch;
int eth_bunch; int eth_bunch;
int threshold; int threshold; //cluster amplitude threshold
int max_sensors() int clustersize; //clustering channel size lower limit
int calibrationFactor[320];
{
switch(hardware_ver)
{
case 1: return 2; break;
case 2: return 5; break;
default: qCritical("Unsupported hardware version!"); return 0; break;
}
}
int max_channels() {return 64*max_sensors();}
int nr_channels() {return 64*nr_sensors;}
DeviceConfig() : own_ip{10,0,7,1}, device_ip{10,0,7,2}, DeviceConfig() : own_ip{10,0,7,1}, device_ip{10,0,7,2},
device_id{0}, hardware_ver{0}, master{1}, plane{0}, position{0}, nr_sensors{0}, device_id{0}, hardware_ver{0}, master{1}, plane{0}, position{0}, nr_sensors{0},
period{65535}, tint{1}, master_delay{1}, slave_delay{1}, gain{0}, dma_bunch{1}, eth_bunch{1}, threshold{10} {} period{65535}, tint{1}, master_delay{1}, slave_delay{1}, gain{0}, dma_bunch{1}, eth_bunch{1}, threshold{10}, clustersize{4}
{
// Initialize calibrationFactor array with default value 8192
for (int i = 0; i < 320; i++) {
calibrationFactor[i] = 8192;
}
}
int max_sensors()
{
switch (hardware_ver) {
case 1: return 2; break;
case 2: return 5; break;
default: qCritical("Unsupported hardware version!"); return 0; break;
}
}
int max_channels() { return 64 * max_sensors(); }
int nr_channels() { return 64 * nr_sensors; }
}; };
@ -103,6 +113,8 @@ protected:
int ctrlSetMasterDelay(int tint); int ctrlSetMasterDelay(int tint);
int ctrlSetSlaveDelay(int tint); int ctrlSetSlaveDelay(int tint);
int ctrlSetClusterThreshold(int threshold); int ctrlSetClusterThreshold(int threshold);
int ctrlSetClusterSize(int clustersize);
int ctrlSetCalibrationFactor(int calibrationFactor[320]);
protected slots: protected slots:
void onConnected(); void onConnected();

View File

@ -11,6 +11,9 @@ Sensors=5
Master=1 Master=1
MasterDelay=61 MasterDelay=61
SlaveDelay=34 SlaveDelay=34
Threshold=10
Size=4
CalibFile=
[Device1] [Device1]
IP=10.0.7.18 IP=10.0.7.18
@ -21,6 +24,9 @@ Sensors=5
Master=0 Master=0
MasterDelay=7 MasterDelay=7
SlaveDelay=1 SlaveDelay=1
Threshold=10
Size=4
CalibFile=
[Trigger] [Trigger]
Period=9000 Period=9000

View File

@ -1,6 +1,12 @@
#include "dialogdevices.h" #include "dialogdevices.h"
#include "ui_dialogdevices.h" #include "ui_dialogdevices.h"
#include "helpers.h" #include "helpers.h"
#include <QFileDialog>
#include <QMessageBox>
#include <QFile>
#include <QTextStream>
#include <QVector>
#include <QPushButton> // Include QPushButton header for button creation
DialogDevices::DialogDevices(QWidget *parent) : DialogDevices::DialogDevices(QWidget *parent) :
QDialog(parent), QDialog(parent),
@ -28,7 +34,7 @@ void DialogDevices::showEvent(QShowEvent * event)
ui->spinNrDevices->setValue(deviceSettings->value("NrDevices", int(1)).toInt()); ui->spinNrDevices->setValue(deviceSettings->value("NrDevices", int(1)).toInt());
ui->tableDevices->setColumnCount(9); ui->tableDevices->setColumnCount(12);
QStringList h_header; QStringList h_header;
h_header.append("IP Address"); h_header.append("IP Address");
h_header.append("Hardware ver."); h_header.append("Hardware ver.");
@ -39,6 +45,11 @@ void DialogDevices::showEvent(QShowEvent * event)
h_header.append("Master dly"); h_header.append("Master dly");
h_header.append("Slave dly"); h_header.append("Slave dly");
h_header.append("Threshold"); h_header.append("Threshold");
h_header.append("ClusterSize");
h_header.append("CalibFile"); // Column for showing file path
h_header.append("Select Calib File"); // New column for the button
ui->tableDevices->setHorizontalHeaderLabels(h_header); ui->tableDevices->setHorizontalHeaderLabels(h_header);
importSettings(); importSettings();
@ -59,6 +70,66 @@ void DialogDevices::accept()
QDialog::accept(); QDialog::accept();
} }
void DialogDevices::selectCalibrationFile(int dev_nr)
{
// Open a file dialog to select a calibration file
QString filename = QFileDialog::getOpenFileName(this, "Select Calibration File", "", "Text Files (*.txt);;All Files (*)");
if (filename.isEmpty())
{
return; // User canceled the dialog
}
// Set the file name in the table for the corresponding device
QTableWidgetItem* calibItem = new QTableWidgetItem(filename);
ui->tableDevices->setItem(dev_nr, 10, calibItem);
// Load calibration data from the file
QVector<unsigned short> calibrationData;
QFile file(filename);
if (!file.open(QIODevice::ReadOnly | QIODevice::Text))
{
QMessageBox::critical(this, "Error", "Could not open file for reading");
return;
}
QTextStream in(&file);
while (!in.atEnd())
{
QString line = in.readLine();
bool ok;
unsigned short value = line.toUShort(&ok);
if (ok)
{
calibrationData.append(value);
}
else
{
calibrationData.append(32768); // assume calibration range is 0 = and 1 = 65536
QMessageBox::warning(this, "Warning", "Invalid data in file. Skipping line.");
}
}
file.close();
// Store the calibration data for the device
applyCalibrationDataToDevice(dev_nr, calibrationData);
}
void DialogDevices::applyCalibrationDataToDevice(int dev_nr, const QVector<unsigned short>& data)
{
// Implementation for applying the calibration data to the specific device
// For example, updating device settings or performing calculations
qDebug() << "Calibration data loaded for Device" << dev_nr << ":" << data;
// Example: Set the calibration data in your application logic
// deviceSettings->setValue("Device%1/CalibrationData", data); // if storing in settings
}
void DialogDevices::importSettings() void DialogDevices::importSettings()
{ {
int nr_devices = ui->spinNrDevices->value(); int nr_devices = ui->spinNrDevices->value();
@ -92,6 +163,19 @@ void DialogDevices::importSettings()
ui->tableDevices->setItem(dev_nr, 7, newItem ); ui->tableDevices->setItem(dev_nr, 7, newItem );
newItem = new QTableWidgetItem(deviceSettings->value("ClusThresh","10").toString()); newItem = new QTableWidgetItem(deviceSettings->value("ClusThresh","10").toString());
ui->tableDevices->setItem(dev_nr, 8, newItem ); ui->tableDevices->setItem(dev_nr, 8, newItem );
newItem = new QTableWidgetItem(deviceSettings->value("ClusSize","4").toString());
ui->tableDevices->setItem(dev_nr, 9, newItem );
// Add an item for the calibration file path (optional, for display)
newItem = new QTableWidgetItem(deviceSettings->value("CalibFile", "").toString());
ui->tableDevices->setItem(dev_nr, 10, newItem);
// Add a button for selecting calibration files
QPushButton* calibButton = new QPushButton("Select File");
ui->tableDevices->setCellWidget(dev_nr, 11, calibButton); // Column index 11 for button
// Connect the button to a slot with the sensor index as a parameter
connect(calibButton, &QPushButton::clicked, this, [this, dev_nr]() { selectCalibrationFile(dev_nr); });
} }
} }
@ -218,6 +302,19 @@ int DialogDevices::validateAndSave()
data_ok = 0; data_ok = 0;
ui->tableDevices->item(dev_nr,8)->setText(generated); ui->tableDevices->item(dev_nr,8)->setText(generated);
//now cluster size
user_data = ui->tableDevices->item(dev_nr,9)->text();
num_value = user_data.toInt();
if (num_value < 1)
num_value = 1;
if (num_value > 255)
num_value = 255;
generated = QString("%1").arg(num_value);
//if the strings are identical, save the value and return 1
if (generated.compare(user_data) != 0)
data_ok = 0;
ui->tableDevices->item(dev_nr,9)->setText(generated);
} }
//now store the data //now store the data
@ -243,9 +340,9 @@ int DialogDevices::validateAndSave()
deviceSettings->setValue("MasterDelay", ui->tableDevices->item(dev_nr,6)->text()); deviceSettings->setValue("MasterDelay", ui->tableDevices->item(dev_nr,6)->text());
deviceSettings->setValue("SlaveDelay", ui->tableDevices->item(dev_nr,7)->text()); deviceSettings->setValue("SlaveDelay", ui->tableDevices->item(dev_nr,7)->text());
deviceSettings->setValue("Threshold", ui->tableDevices->item(dev_nr,8)->text()); deviceSettings->setValue("Threshold", ui->tableDevices->item(dev_nr,8)->text());
deviceSettings->setValue("Size", ui->tableDevices->item(dev_nr,9)->text());
deviceSettings->setValue("CalibFile", ui->tableDevices->item(dev_nr, 10)->text());
} }
return 1; return 1;
} }
@ -256,3 +353,23 @@ void DialogDevices::on_spinNrDevices_valueChanged(int arg1)
if (initialized) if (initialized)
importSettings(); importSettings();
} }
QVector<QVector<int>> DialogDevices::getAllCalibrationFactors() const {
QVector<QVector<int>> calibrationFactors;
for (int row = 0; row < ui->tableDevices->rowCount(); ++row) {
QVector<int> factors(320, 8192); // Initialize with default value of 8192
QTableWidgetItem* item = ui->tableDevices->item(row, 10); // Assuming column 10 is for calibration factors
if (item) {
QStringList factorStrings = item->text().split(',', Qt::SkipEmptyParts);
for (int i = 0; i < factorStrings.size() && i < 320; ++i) {
bool ok;
int factor = factorStrings[i].toInt(&ok);
if (ok && factor >= 0 && factor <= 65535) {
factors[i] = factor;
}
}
}
calibrationFactors.append(factors);
}
return calibrationFactors;
}

View File

@ -1,9 +1,10 @@
#ifndef DIALOGDEVICES_H #ifndef DIALOGDEVICES_H
#define DIALOGDEVICES_H #define DIALOGDEVICES_H
#include <QDialog> #include <QDialog>
#include <QSettings> #include <QSettings>
#include <QShowEvent> #include <QShowEvent>
#include <QVector> // Include QVector for calibration data storage
namespace Ui { namespace Ui {
class DialogDevices; class DialogDevices;
@ -18,19 +19,23 @@ public:
~DialogDevices(); ~DialogDevices();
QSettings* deviceSettings = NULL; QSettings* deviceSettings = NULL;
QVector<QVector<int>> getAllCalibrationFactors() const; // Declaration of the method
public slots: public slots:
void showEvent(QShowEvent *event); void showEvent(QShowEvent *event);
void accept(); void accept();
protected: protected:
int validateAndSave(); int validateAndSave();
void applyCalibrationDataToDevice(int dev_nr, const QVector<unsigned short>& data); // Function to apply calibration data to a device
void importSettings(); void importSettings();
int last_nr_devices = -1; int last_nr_devices = -1;
int initialized = 0; int initialized = 0;
QVector<QVector<unsigned short>> calibrationData; // Storage for calibration data for each device
private slots: private slots:
void on_spinNrDevices_valueChanged(int arg1); void on_spinNrDevices_valueChanged(int arg1);
void selectCalibrationFile(int dev_nr); // Slot for handling calibration file selection
private: private:
Ui::DialogDevices *ui; Ui::DialogDevices *ui;
}; };
#endif // DIALOGDEVICES_H #endif // DIALOGDEVICES_H

View File

@ -6,39 +6,51 @@
<rect> <rect>
<x>0</x> <x>0</x>
<y>0</y> <y>0</y>
<width>573</width> <width>1085</width>
<height>233</height> <height>233</height>
</rect> </rect>
</property> </property>
<property name="sizePolicy">
<sizepolicy hsizetype="Expanding" vsizetype="Expanding">
<horstretch>0</horstretch>
<verstretch>0</verstretch>
</sizepolicy>
</property>
<property name="windowTitle"> <property name="windowTitle">
<string>Devices</string> <string>Devices</string>
</property> </property>
<property name="sizeGripEnabled">
<bool>true</bool>
</property>
<widget class="QDialogButtonBox" name="buttonBox"> <widget class="QDialogButtonBox" name="buttonBox">
<property name="geometry"> <property name="geometry">
<rect> <rect>
<x>210</x> <x>720</x>
<y>190</y> <y>190</y>
<width>341</width> <width>341</width>
<height>32</height> <height>32</height>
</rect> </rect>
</property> </property>
<property name="orientation"> <property name="orientation">
<enum>Qt::Horizontal</enum> <enum>Qt::Orientation::Horizontal</enum>
</property> </property>
<property name="standardButtons"> <property name="standardButtons">
<set>QDialogButtonBox::Cancel|QDialogButtonBox::Ok</set> <set>QDialogButtonBox::StandardButton::Cancel|QDialogButtonBox::StandardButton::Ok</set>
</property> </property>
</widget> </widget>
<widget class="QWidget" name="verticalLayoutWidget"> <widget class="QWidget" name="verticalLayoutWidget">
<property name="geometry"> <property name="geometry">
<rect> <rect>
<x>20</x> <x>10</x>
<y>10</y> <y>10</y>
<width>531</width> <width>1061</width>
<height>171</height> <height>171</height>
</rect> </rect>
</property> </property>
<layout class="QVBoxLayout" name="verticalLayout"> <layout class="QVBoxLayout" name="verticalLayout">
<property name="sizeConstraint">
<enum>QLayout::SizeConstraint::SetNoConstraint</enum>
</property>
<item> <item>
<layout class="QHBoxLayout" name="horizontalLayout_2"> <layout class="QHBoxLayout" name="horizontalLayout_2">
<item> <item>
@ -58,7 +70,11 @@
</layout> </layout>
</item> </item>
<item> <item>
<widget class="QTableWidget" name="tableDevices"/> <widget class="QTableWidget" name="tableDevices">
<attribute name="horizontalHeaderCascadingSectionResizes">
<bool>true</bool>
</attribute>
</widget>
</item> </item>
</layout> </layout>
</widget> </widget>

View File

@ -195,8 +195,9 @@ void EventBuilder::logDataToFile()
* - number of boards: N = 1 x unsigned short * - number of boards: N = 1 x unsigned short
* - number of channels per each board Cn: N x unsigned short * - number of channels per each board Cn: N x unsigned short
* - N times the following sequence: * - N times the following sequence:
* - SyncFrame S = 1 x SyncFrame (== 16 bytes) * - SyncFrame S = 1 x SyncFrame (== 16 bytes 4 unsigned shorts and 2 int)
* - Data D = Cn x unsigned short * - Data D = Cn x unsigned short
* - RMSframe R = 1 x RMSframe(== 8 unsigned shorts == 16 bytes)
*/ */
logFile.write((const char*)&totalBoards, sizeof(unsigned short)); logFile.write((const char*)&totalBoards, sizeof(unsigned short));

View File

@ -14,7 +14,7 @@ int main(int argc, char *argv[])
QFile styleFile(stylesheetPath); QFile styleFile(stylesheetPath);
if (styleFile.open(QFile::ReadOnly | QFile::Text)) { if (styleFile.open(QFile::ReadOnly | QFile::Text)) {
QString style = QTextStream(&styleFile).readAll(); QString style = QTextStream(&styleFile).readAll();
qApp->setStyleSheet(style); //qApp->setStyleSheet(style);
styleFile.close(); styleFile.close();
} else { } else {
qWarning("Failed to open stylesheet file: %s", qPrintable(stylesheetPath)); qWarning("Failed to open stylesheet file: %s", qPrintable(stylesheetPath));

View File

@ -117,6 +117,10 @@ void MainWindow::setupHardware()
int period_v2 = deviceSettings->value("Period_v2").toInt(); int period_v2 = deviceSettings->value("Period_v2").toInt();
int tint_v2 = deviceSettings->value("Tint_v2").toInt(); int tint_v2 = deviceSettings->value("Tint_v2").toInt();
int gain_v2 = deviceSettings->value("Gain_v2").toInt(); int gain_v2 = deviceSettings->value("Gain_v2").toInt();
// Retrieve device-specific settings from DialogDevices
DialogDevices dlg;
dlg.deviceSettings = deviceSettings;
QVector<QVector<int>> allCalibrationFactors = dlg.getAllCalibrationFactors();
for (int dev_nr = 0; dev_nr < nr_devices; dev_nr++) for (int dev_nr = 0; dev_nr < nr_devices; dev_nr++)
{ {
@ -126,7 +130,7 @@ void MainWindow::setupHardware()
dc.device_id = dev_nr; dc.device_id = dev_nr;
dc.hardware_ver = deviceSettings->value("HardwareVer").toInt(); dc.hardware_ver = deviceSettings->value("HardwareVer").toInt();
ip2num(deviceSettings->value("IP").toString(), ip); ip2num(deviceSettings->value("IP").toString(), ip);
for (int i = 0; i < 4; i++) for (int i = 0; i < 4; i++)//4 bytes
dc.device_ip[i] = ip[i]; dc.device_ip[i] = ip[i];
dc.master = deviceSettings->value("Master").toInt(); dc.master = deviceSettings->value("Master").toInt();
dc.plane = deviceSettings->value("Plane").toInt(); dc.plane = deviceSettings->value("Plane").toInt();
@ -134,7 +138,19 @@ void MainWindow::setupHardware()
dc.nr_sensors = deviceSettings->value("Sensors").toInt(); dc.nr_sensors = deviceSettings->value("Sensors").toInt();
dc.master_delay = deviceSettings->value("MasterDelay").toInt(); dc.master_delay = deviceSettings->value("MasterDelay").toInt();
dc.slave_delay = deviceSettings->value("SlaveDelay").toInt(); dc.slave_delay = deviceSettings->value("SlaveDelay").toInt();
dc.threshold = deviceSettings->value("Threshold").toInt();
dc.clustersize = deviceSettings->value("ClusterSize").toInt();
/*
// Get calibration factors for this device
QVector<int> calibFactors = allCalibrationFactors[dev_nr];
for (int i = 0; i < 320; i++) {
if (i < calibFactors.size() && calibFactors[i] >= 0 && calibFactors[i] <= 65535) {
dc.calibrationFactor[i] = calibFactors[i];
} else {
dc.calibrationFactor[i] = 8192; // Default value if not set or invalid
}
}
*/
switch (dc.hardware_ver) switch (dc.hardware_ver)
{ {
case 1: case 1:
@ -155,6 +171,34 @@ void MainWindow::setupHardware()
theHW->configureDevice(dev_nr, dc); //configure the device and an entry in base address table in the event builder theHW->configureDevice(dev_nr, dc); //configure the device and an entry in base address table in the event builder
} }
dc.threshold = deviceSettings->value("Threshold").toInt();
dc.clustersize = deviceSettings->value("ClusterSize").toInt();
/*
// Assume calibration factors are stored as a list or comma-separated string
QString calibFactorsStr = deviceSettings->value("CalibFactors").toString();
QStringList calibFactorList = calibFactorsStr.split(',', Qt::SkipEmptyParts);
// Clear any existing calibration data
for (int i = 0; i < 320; i++) {
dc.calibrationFactor[i] = 0; // Initialize to 0 or some default
}
// Load calibration factors
int index = 0;
for (const QString& factor : calibFactorList) {
if (index >= 320) break; // Ensure we do not overflow the array
bool ok;
int value = factor.toInt(&ok);
if (ok) {
dc.calibrationFactor[index] = value;
index++;
} else {
qWarning() << "Invalid calibration factor:" << factor;
}
}
*/
//theDisplay.setup(&theHW); //theDisplay.setup(&theHW);
} }

Binary file not shown.