新增道址计数谱实时读取数据,修改道址计数谱逻辑
This commit is contained in:
parent
9a8a102dcf
commit
cad4ee2df7
|
|
@ -299,6 +299,11 @@ void CustomQwtPlot::AddCurve(QwtPlotCurve *curve, bool auto_color)
|
|||
}
|
||||
}
|
||||
|
||||
void CustomQwtPlot::clearCurve()
|
||||
{
|
||||
_curves.clear();
|
||||
}
|
||||
|
||||
QwtPlotMarker *CustomQwtPlot::GetMarker(const QString &marker_name, const QString &postion)
|
||||
{
|
||||
return _markers.value(marker_name).value(postion);
|
||||
|
|
|
|||
|
|
@ -72,6 +72,7 @@ public:
|
|||
QwtPlotCurve* GetCurve(const QString& curve_name);
|
||||
QList<QwtPlotCurve*> GetCurveList() const;
|
||||
void AddCurve(QwtPlotCurve* curve, bool auto_color = true);
|
||||
void clearCurve();
|
||||
|
||||
QwtPlotMarker* GetMarker(const QString& marker_name, const QString& postion);
|
||||
QList<QwtPlotMarker*> GetMarkerList() const;
|
||||
|
|
|
|||
|
|
@ -34,6 +34,8 @@
|
|||
#include "MeasureAnalysisDataTableView.h"
|
||||
#include "DataCalcProcess/GaussPolyCoe.h"
|
||||
#include "EnergyScaleDataModel.h"
|
||||
#include "ParticleCountPlotView.h"
|
||||
#include <array>
|
||||
#include "csv.h"
|
||||
#include <fstream>
|
||||
|
||||
|
|
@ -100,6 +102,10 @@ MainWindow::MainWindow(QWidget* parent)
|
|||
_status_bar = ui->statusbar;
|
||||
_gvfToCsv = new GvfToCsv;
|
||||
_measure_client = new MeasureClient;
|
||||
m_AddressCountTimer = new QTimer(this);
|
||||
m_AddressCountTimer->setInterval(10000);//10秒刷新一次
|
||||
connect(m_AddressCountTimer, &QTimer::timeout, this, &MainWindow::on_AddressCountTimer);
|
||||
|
||||
connect(_measure_client, &MeasureClient::getDeviceListResult, this, &MainWindow::onGetDeviceListResult);
|
||||
connect(_measure_client, &MeasureClient::startMeasureResult, this, &MainWindow::onStartMeasureResult);
|
||||
connect(_measure_client, &MeasureClient::stopMeasureResult, this, &MainWindow::onStopMeasureResult);
|
||||
|
|
@ -611,6 +617,8 @@ void MainWindow::onGvfData(const QByteArray &data)
|
|||
changeParticleEnergyData(particles);
|
||||
//处理能量计数
|
||||
changeEnergyCountData(particles);
|
||||
//处理道址计数谱
|
||||
changeAddressCountView(particles);
|
||||
}
|
||||
|
||||
//处理粒子数据
|
||||
|
|
@ -704,7 +712,15 @@ void MainWindow::changeChannelParticleCount(QList<ParticleData> &data)
|
|||
// 计算本次数据的增量计数
|
||||
for (const auto &info : data) {
|
||||
int channel_num = (info.boardId) * 4 + (info.channelId + 1);
|
||||
deltaCounts[channel_num][info.address]++;
|
||||
uint address = info.address;
|
||||
|
||||
// 道址范围校验(防止越界)
|
||||
if (address >= 4096) {
|
||||
LOG_WARN(QStringLiteral(u"道址%1超出最大范围%2,已跳过").arg(address).arg(4096));
|
||||
continue;
|
||||
}
|
||||
|
||||
deltaCounts[channel_num][address]++;
|
||||
totalParticles++;
|
||||
}
|
||||
|
||||
|
|
@ -739,6 +755,22 @@ void MainWindow::changeChannelParticleCount(QList<ParticleData> &data)
|
|||
uint channel_num = channelIt.key();
|
||||
const auto& addressDeltas = channelIt.value();
|
||||
|
||||
// 关键优化:如果是新通道,初始化4096个道址为0
|
||||
if (!channel_address_counts.contains(channel_num)) {
|
||||
std::array<unsigned long long, 4096> initCounts;
|
||||
initCounts.fill(0); // 所有道址初始化为0
|
||||
channel_address_counts.insert(channel_num, initCounts);
|
||||
}
|
||||
|
||||
// 更新内存中的总计数
|
||||
auto& channelCounts = channel_address_counts[channel_num];
|
||||
for (auto addressIt = addressDeltas.constBegin(); addressIt != addressDeltas.constEnd(); ++addressIt) {
|
||||
uint address = addressIt.key();
|
||||
unsigned long long delta = addressIt.value();
|
||||
channelCounts[address] += delta;
|
||||
}
|
||||
|
||||
// 获取或创建通道文件名
|
||||
QString count_data_filename;
|
||||
if (particle_count_filename_list.contains(channel_num)) {
|
||||
count_data_filename = particle_count_filename_list[channel_num];
|
||||
|
|
@ -749,12 +781,7 @@ void MainWindow::changeChannelParticleCount(QList<ParticleData> &data)
|
|||
newChannelFiles.insert(channel_num, count_data_filename);
|
||||
}
|
||||
|
||||
for (auto addressIt = addressDeltas.constBegin(); addressIt != addressDeltas.constEnd(); ++addressIt) {
|
||||
uint address = addressIt.key();
|
||||
unsigned long long delta = addressIt.value();
|
||||
channel_address_counts[channel_num][address] += delta;
|
||||
}
|
||||
|
||||
// 重写整个CSV文件(Truncate模式)
|
||||
QFile outFile(count_data_filename);
|
||||
if (!outFile.open(QIODevice::WriteOnly | QIODevice::Text | QIODevice::Truncate)) {
|
||||
LOG_ERROR(QStringLiteral(u"无法打开通道%1的计数文件: %2,错误: %3")
|
||||
|
|
@ -771,16 +798,12 @@ void MainWindow::changeChannelParticleCount(QList<ParticleData> &data)
|
|||
// 写入表头
|
||||
out << QStringLiteral(u"道址,计数\n");
|
||||
|
||||
// 写入所有道址的最新总计数(按道址排序)
|
||||
// 关键修改:写入完整的0-4095道址数据
|
||||
QString csvBuffer;
|
||||
csvBuffer.reserve(channel_address_counts[channel_num].size() * 32); // 预分配内存
|
||||
csvBuffer.reserve(4096 * 32); // 预分配足够内存(约128KB)
|
||||
|
||||
// 获取排序后的道址列表
|
||||
QList<uint> sortedAddresses = channel_address_counts[channel_num].keys();
|
||||
std::sort(sortedAddresses.begin(), sortedAddresses.end());
|
||||
|
||||
for (uint address : sortedAddresses) {
|
||||
unsigned long long total = channel_address_counts[channel_num][address];
|
||||
for (int address = 0; address < 4096; ++address) {
|
||||
unsigned long long total = channelCounts[address];
|
||||
csvBuffer += QString("%1,%2\n").arg(address).arg(total);
|
||||
}
|
||||
|
||||
|
|
@ -932,7 +955,60 @@ void MainWindow::changeEnergyCountData(QList<ParticleData> &dataList)
|
|||
{
|
||||
|
||||
}
|
||||
//处理道址计数谱
|
||||
void MainWindow::changeAddressCountView(QList<ParticleData> &dataList)
|
||||
{
|
||||
if (dataList.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
MeasureAnalysisProjectModel* pro_model = ProjectList::Instance()->GetCurrentProjectModel();
|
||||
if (!pro_model) {
|
||||
LOG_ERROR(QStringLiteral(u"当前没有打开的测量项目,无法处理能谱数据"));
|
||||
return;
|
||||
}
|
||||
|
||||
bool status_ok = !pro_model->GetChannelAddressCountDataFilenameList().isEmpty();
|
||||
QString status = status_ok ? QStringLiteral(u"有效") : QStringLiteral(u"无效");
|
||||
QString item_name = QStringLiteral(u"道址计数谱");
|
||||
QStandardItem * particleData = nodeMap[item_name];
|
||||
//获取道址计数谱状态
|
||||
bool bStatus = ProjectList::Instance()->GetNodeStatus(particleData);
|
||||
if(!bStatus)
|
||||
{
|
||||
ProjectList::Instance()->SetNodeStatus(particleData,status,true);
|
||||
m_AddressCountTimer->start();
|
||||
}
|
||||
}
|
||||
|
||||
void MainWindow::on_AddressCountTimer()
|
||||
{
|
||||
QMap<QString, QVariant> data_files_set;
|
||||
//获取道址计数谱
|
||||
auto dockList = _dock_manager->dockWidgetsMap().values();
|
||||
for(auto dock : dockList)
|
||||
{
|
||||
ParticleCountPlotView* view = dynamic_cast<ParticleCountPlotView*>(dock->widget());
|
||||
if(!view) continue;
|
||||
if(view->GetAnalyzeType() == AnalysisType::AddressCountSpectrumView)
|
||||
{
|
||||
MeasureAnalysisProjectModel* project_model = ProjectList::Instance()->GetCurrentProjectModel();
|
||||
if (project_model) {
|
||||
auto file_name_list = project_model->GetChannelAddressCountDataFilenameList();
|
||||
if ( !file_name_list.isEmpty() ) {
|
||||
auto ch_num_list = file_name_list.keys();
|
||||
for(auto ch_num : ch_num_list) {
|
||||
auto file_name = file_name_list[ch_num];
|
||||
if ( !file_name.isEmpty() ) {
|
||||
data_files_set[QStringLiteral(u"通道%1").arg(ch_num)] = file_name;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
view->updateView(data_files_set);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void MainWindow::on_action_stop_measure_triggered()
|
||||
{
|
||||
|
|
@ -942,5 +1018,5 @@ void MainWindow::on_action_stop_measure_triggered()
|
|||
return;
|
||||
}
|
||||
_measure_client->stopMeasure(device_guid);
|
||||
m_AddressCountTimer->stop();
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -5,6 +5,7 @@
|
|||
#include <QMutex>
|
||||
#include "GvfToCsv/GvfToCsv.h"
|
||||
#include "MeasureAnalysisProjectModel.h"
|
||||
#include <QTimer>
|
||||
|
||||
QT_BEGIN_NAMESPACE
|
||||
namespace Ui {
|
||||
|
|
@ -65,7 +66,8 @@ private:
|
|||
void changeParticleEnergyData(QList<ParticleData> &dataList);
|
||||
//处理能量计数
|
||||
void changeEnergyCountData(QList<ParticleData> &dataList);
|
||||
|
||||
//处理道址计数谱
|
||||
void changeAddressCountView(QList<ParticleData> &dataList);
|
||||
signals:
|
||||
void newProject(const QString &project_name);
|
||||
|
||||
|
|
@ -93,7 +95,7 @@ private slots:
|
|||
|
||||
void on_action_stop_measure_triggered();
|
||||
|
||||
|
||||
void on_AddressCountTimer();
|
||||
private:
|
||||
QMutex _mutex_info_output;
|
||||
QPlainTextEdit* _plain_edit_info_output;
|
||||
|
|
@ -115,7 +117,7 @@ private:
|
|||
GvfToCsv *_gvfToCsv = nullptr;
|
||||
|
||||
|
||||
QMap<uint, QMap<uint, unsigned long long>> channel_address_counts; // 通道号 -> 地址 -> 计数
|
||||
QHash<uint, std::array<unsigned long long, 4096>> channel_address_counts; // 改为数组
|
||||
QMap<uint, QString> particle_count_filename_list;
|
||||
//2026-06-11
|
||||
QMap<QString, QStandardItem *> nodeMap;
|
||||
|
|
@ -128,5 +130,8 @@ private:
|
|||
QMap<double, unsigned long long> m_allChannelEnergyStats; // 全通道能量bin -> 计数
|
||||
QMutex m_energyCountMutex; // 保护能量计数数据的互斥锁
|
||||
QHash<QString, std::vector<double>> m_energyScaleCoeffCache;// 能量刻度系数缓存
|
||||
|
||||
//道址计数视图定时器
|
||||
QTimer* m_AddressCountTimer;
|
||||
};
|
||||
#endif // MAINWINDOW_H
|
||||
|
|
|
|||
|
|
@ -116,6 +116,27 @@ void ParticleCountPlotView::SetAnalyzeDataFilename(const QMap<QString, QVariant>
|
|||
}
|
||||
}
|
||||
|
||||
void ParticleCountPlotView::updateView(const QMap<QString, QVariant>& data_files_set)
|
||||
{
|
||||
// 清除现有所有曲线
|
||||
for (QwtPlotCurve* curve : this->_plot->GetCurveList()) {
|
||||
curve->detach();
|
||||
delete curve;
|
||||
}
|
||||
_plot->clearCurve();
|
||||
|
||||
|
||||
// 重新加载数据
|
||||
if (!data_files_set.isEmpty()) {
|
||||
SetAnalyzeDataFilename(data_files_set);
|
||||
}
|
||||
// 清除标记并重绘
|
||||
this->_plot->CleanMarkers();
|
||||
this->_plot->CleanZoneItems();
|
||||
this->_plot->ResetPlot();
|
||||
this->_plot->replot();
|
||||
}
|
||||
|
||||
void ParticleCountPlotView::setupMenu()
|
||||
{
|
||||
this->setContextMenuPolicy(Qt::CustomContextMenu);
|
||||
|
|
|
|||
|
|
@ -25,6 +25,8 @@ public:
|
|||
virtual void InitViewWorkspace(const QString& project_name) override final;
|
||||
virtual void SetAnalyzeDataFilename(const QMap<QString, QVariant>& data_files_set);
|
||||
|
||||
void updateView(const QMap<QString, QVariant>& data_files_set);
|
||||
|
||||
private:
|
||||
void setupMenu();
|
||||
void setupPlot();
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user