2025-03-27T17:31:17

This commit is contained in:
yuntang 2025-03-27 17:31:19 +08:00
parent 86dbbe706d
commit 6021f8132a
13 changed files with 7929 additions and 110 deletions

View File

@ -19,7 +19,9 @@ SOURCES += \
data/filemanager.cpp \
data/peakpoint.cpp \
global.cpp \
logger/logger.cpp \
rightwidget.cpp \
thirdparty/easylogging/easylogging++.cc \
ui/analysissettingform.cpp \
ui/centralwidget.cpp \
main.cpp \
@ -37,7 +39,9 @@ HEADERS += \
data/peakpoint.h \
defines.h \
global.h \
logger/logger.h \
rightwidget.h \
thirdparty/easylogging/easylogging++.h \
ui/analysissettingform.h \
ui/centralwidget.h \
mainwindow.h \
@ -57,6 +61,8 @@ FORMS += \
INCLUDEPATH += serialport \
ui \
logger \
thirdparty/easylogging \
thirdparty/qcustomplot \
data
@ -67,3 +73,6 @@ else: unix:!android: target.path = /opt/$${TARGET}/bin
RESOURCES += \
images.qrc
DISTFILES += \
logger/log.conf

View File

@ -3,9 +3,9 @@
#include "peakpoint.h"
QVector<FileManager::ExperimentData>PeakPoint:: _dataVtr;
double PeakPoint::_leftPointX,PeakPoint::_rightPointX;
float PeakPoint::_leftPointX,PeakPoint::_rightPointX;
QPointF PeakPoint::_peakPoint;
QPointF PeakPoint::_leftSelectedPoint,PeakPoint::_rightSelectedPoint;
QPointF PeakPoint::_leftSelectedPoint,PeakPoint::_rightSelectedPoint;
void PeakPoint::setExperimentData(const QVector<FileManager::ExperimentData> &dataVtr)
{
@ -20,14 +20,14 @@ QPointF PeakPoint::findPeakPoint(){
}
QPointF uniquePeak;
// 初始化为 double 类型能表示的最小负数,确保能处理负数 y 值
double maxY = 0.0;
// 初始化为 float 类型能表示的最小负数,确保能处理负数 y 值
float maxY = 0.0;
bool findFlag = false;
// 直接在遍历过程中找出最大波峰
for (int i = 1; i < n - 1; ++i) {
const double currentX = _dataVtr.at(i).sampleTemp;
const double currentY = _dataVtr.at(i).dsc;
const float currentX = _dataVtr.at(i).sampleTemp;
const float currentY = _dataVtr.at(i).dsc;
if(currentX < _leftPointX){
continue;
@ -36,8 +36,8 @@ QPointF PeakPoint::findPeakPoint(){
break;
}
const double preY = _dataVtr.at(i - 1).dsc;
const double lastY = _dataVtr.at(i + 1).dsc;
const float preY = _dataVtr.at(i - 1).dsc;
const float lastY = _dataVtr.at(i + 1).dsc;
findFlag = false;
if(currentY >= preY && currentY >= lastY){
@ -47,7 +47,7 @@ QPointF PeakPoint::findPeakPoint(){
}
if(findFlag){
double absY = std::abs(currentY);
float absY = std::abs(currentY);
if(absY >= maxY){
maxY = absY;
uniquePeak = QPointF(currentX,currentY);
@ -60,17 +60,16 @@ QPointF PeakPoint::findPeakPoint(){
return uniquePeak;
}
QPair<QPointF, QPointF> PeakPoint::calculateMaxDiffPointDetail(
const PeakPoint::MaxDiffPointDetailType type)
{
#if 1
double maxDiff = std::numeric_limits<double>::min();
float maxDiff = std::numeric_limits<float>::min();
QPointF currentPoint,lastPoint;
for (int i = 0; i < _dataVtr.size() - 1; ++i) {
const double currentX = _dataVtr.at(i).sampleTemp;
const double currentY = _dataVtr.at(i).dsc;
const float currentX = _dataVtr.at(i).sampleTemp;
const float currentY = _dataVtr.at(i).dsc;
if(type == MaxDiffPointDetailType::Left){
if(currentX <= _leftPointX){
@ -88,9 +87,9 @@ QPair<QPointF, QPointF> PeakPoint::calculateMaxDiffPointDetail(
}
}
//
const double lastX = _dataVtr.at(i + 1).sampleTemp;
const double lastY = _dataVtr.at(i + 1).dsc;
double diff = std::abs(currentY - lastY);
const float lastX = _dataVtr.at(i + 1).sampleTemp;
const float lastY = _dataVtr.at(i + 1).dsc;
float diff = std::abs(currentY - lastY);
if(diff > maxDiff){
maxDiff = diff;
@ -116,14 +115,14 @@ QPair<QPointF, QPointF> PeakPoint::calculateMaxDiffPointRight()
return calculateMaxDiffPointDetail(MaxDiffPointDetailType::Right);
}
double PeakPoint::findClosestY(double targetX)
float PeakPoint::findClosestY(float targetX)
{
double minDiff = std::numeric_limits<double>::max();
double closestY = 0.0;
float minDiff = std::numeric_limits<float>::max();
float closestY = 0.0;
for(FileManager::ExperimentData &ed:_dataVtr){
// 计算当前 x 与目标 x 的差值的绝对值
double diff = std::abs(ed.sampleTemp - targetX);
float diff = std::abs(ed.sampleTemp - targetX);
// 更新最小差值和对应的 y 值
if (diff < minDiff) {
minDiff = diff;
@ -134,7 +133,7 @@ double PeakPoint::findClosestY(double targetX)
return closestY;
}
QPointF PeakPoint::findClosestPointByX(double x) {
QPointF PeakPoint::findClosestPointByX(float x) {
int left = 0;
int right = _dataVtr.size() - 1;
@ -161,7 +160,7 @@ QPointF PeakPoint::findClosestPointByX(double x) {
return targetPoint;
}
void PeakPoint::setRegionPointX(const double left, const double right)
void PeakPoint::setRegionPointX(const float left, const float right)
{
_leftPointX = left;
_rightPointX = right;
@ -169,14 +168,64 @@ void PeakPoint::setRegionPointX(const double left, const double right)
_leftSelectedPoint = findClosestPointByX(_leftPointX);
_rightSelectedPoint = findClosestPointByX(_rightPointX);
findPeakPoint();
updateStartEndPoint();
qDebug()<<"left,right point:"<<_leftSelectedPoint
<<","<<_rightSelectedPoint;
}
QString PeakPoint::textFormat(const double enthalpyValue,
const double peakValue,
const double startPoint,
const double endPoint)
QVector<QPointF> PeakPoint::getPeakPointGroup()
{
QVector<QPointF> pointVtr;
for(FileManager::ExperimentData& ed:_dataVtr) {
if(ed.sampleTemp >= _leftSelectedPoint.x() && ed.sampleTemp <= _rightSelectedPoint.x()){
pointVtr.push_back(QPointF(ed.sampleTemp,ed.dsc));
}
}
return pointVtr;
}
QPair<QPointF, QPointF> PeakPoint::calculateStartAndEndPoint()
{
QPair<QPointF,QPointF> leftMaxDiffPointPair = PeakPoint::calculateMaxDiffPointLeft();
QPair<QPointF,QPointF> rightMaxDiffPointPair = PeakPoint::calculateMaxDiffPointRight();
QPointF startPoint = calculateIntersection(_leftSelectedPoint,_rightSelectedPoint,
leftMaxDiffPointPair.first,leftMaxDiffPointPair.second);
QPointF endPoint = calculateIntersection(_leftSelectedPoint,_rightSelectedPoint,
rightMaxDiffPointPair.first,rightMaxDiffPointPair.second);
return qMakePair(startPoint,endPoint);
}
void PeakPoint::updateStartEndPoint()
{
//需要在a1和a2之间查询是否有高于a1和a2之间的点若存在则重新给a1、a2赋值
for(FileManager::ExperimentData& ed:_dataVtr){
if(ed.sampleTemp > _leftSelectedPoint.x() && ed.sampleTemp < _peakPoint.x()){
if(ed.dsc > _leftSelectedPoint.y()){
_leftSelectedPoint.setX(ed.sampleTemp);
_leftSelectedPoint.setY(ed.dsc);
}
}
if(ed.sampleTemp < _rightSelectedPoint.x() && ed.sampleTemp > _peakPoint.x()){
if(ed.dsc > _rightSelectedPoint.y()){
_rightSelectedPoint.setX(ed.sampleTemp);
_rightSelectedPoint.setY(ed.dsc);
}
}
}
}
QString PeakPoint::textFormat(const float enthalpyValue,
const float peakValue,
const float startPoint,
const float endPoint)
{
return QString("峰的综合信息:\n"
"焓值:%1 J/g \n"
@ -193,28 +242,40 @@ QString PeakPoint::textFormat(const double enthalpyValue,
QPointF PeakPoint::calculateIntersection(const QPointF p1,const QPointF p2,
const QPointF p3, const QPointF p4){
// 直线的一般式: A1x + B1y + C1 = 0 和 A2x + B2y + C2 = 0
double A1 = p2.y() - p1.y();
double B1 = p1.x() - p2.x();
double C1 = A1 * p1.x() + B1 * p1.y();
float A1 = p2.y() - p1.y();
float B1 = p1.x() - p2.x();
float C1 = A1 * p1.x() + B1 * p1.y();
double A2 = p4.y() - p3.y();
double B2 = p3.x() - p4.x();
double C2 = A2 * p3.x() + B2 * p3.y();
float A2 = p4.y() - p3.y();
float B2 = p3.x() - p4.x();
float C2 = A2 * p3.x() + B2 * p3.y();
double determinant = A1 * B2 - A2 * B1;
float determinant = A1 * B2 - A2 * B1;
if (determinant == 0) {
// 两条直线平行或重合,无交点或无限交点
return {0, 0};
} else {
double x = (B2 * C1 - B1 * C2) / determinant;
double y = (A1 * C2 - A2 * C1) / determinant;
float x = (B2 * C1 - B1 * C2) / determinant;
float y = (A1 * C2 - A2 * C1) / determinant;
return {x, y};
}
}
double PeakPoint::calculateArea(const std::vector<QPointF> &points) {
double integral = 0.0;
float PeakPoint::calculateArea() {
//getPoint group
QVector<QPointF> points = getPeakPointGroup();
#if 0
for(QPointF point:points){
qDebug()<<"x,y:"<<QString::number(point.x(),'f',3)<<","
<<QString::number(point.y(),'f',3);
}
#endif
qDebug()<<QString::number(points.at(0).x(),'f',3)<<","<<
QString::number(points.at(points.size() - 1).x(),'f',3);
//calculate Area
float integral = 0.0;
size_t n = points.size();
if (n < 2) {
@ -222,11 +283,20 @@ double PeakPoint::calculateArea(const std::vector<QPointF> &points) {
}
for (size_t i = 1; i < n; ++i) {
double dx = points[i].x() - points[i - 1].x();
double avg_y = (points[i].y() + points[i - 1].y()) / 2.0;
integral += dx * avg_y;
float dx = points[i].x() - points[i - 1].x();
float avg_y = (points[i].y() + points[i - 1].y()) / 2.0;
float step = dx * std::abs(avg_y);
qDebug()<<points[i].x()<<","<<points[i].y()<<"integral:"<<integral<<","<<step;
integral += dx * std::abs(avg_y);
}
return integral;
}

View File

@ -8,16 +8,17 @@
namespace PeakPoint{
void setExperimentData(const QVector<FileManager::ExperimentData>&);
void setRegionPointX(const double,const double);
double findClosestY(double targetX);
void setRegionPointX(const float,const float);
float findClosestY(float targetX);
QPointF findPeakPoint();
QString textFormat(const double enthalpyValue,
const double peakValue,
const double startPoint,
const double endPoint);
QString textFormat(const float enthalpyValue,
const float peakValue,
const float startPoint,
const float endPoint);
QPair<QPointF,QPointF> calculateStartAndEndPoint();
float calculateArea();
//private
void updateStartEndPoint();
QPair<QPointF,QPointF> calculateMaxDiffPointLeft();
QPair<QPointF,QPointF> calculateMaxDiffPointRight();
enum MaxDiffPointDetailType{
@ -28,11 +29,11 @@ QPair<QPointF,QPointF> calculateMaxDiffPointDetail(const MaxDiffPointDetailType
QPointF calculateIntersection(const QPointF p1,const QPointF p2,
const QPointF p3, const QPointF p4);
double calculateArea(const std::vector<QPointF> &points);
QPointF findClosestPointByX(double target);
QPointF findClosestPointByX(float target);
QVector<QPointF> getPeakPointGroup();
extern QVector<FileManager::ExperimentData> _dataVtr;
extern double _leftPointX,_rightPointX;
extern float _leftPointX,_rightPointX;
extern QPointF _peakPoint;
extern QPointF _leftSelectedPoint,_rightSelectedPoint;
}

11
src/logger/log.conf Normal file
View File

@ -0,0 +1,11 @@
*GLOBAL:
ENABLED = true
TO_FILE = true
TO_STANDARD_OUTPUT = true
FORMAT = "[%datetime] %msg"
FILENAME = "log-sdk/%datetime{%Y%M%d}.log"
MILLISECONDS_WIDTH = 3
PERFORMANCE_TRACKING = false
MAX_LOG_FILE_SIZE = 104857600
LOG_FLUSH_THRESHOLD = 0

15
src/logger/logger.cpp Normal file
View File

@ -0,0 +1,15 @@
#include "logger.h"
INITIALIZE_EASYLOGGINGPP
Logger::Logger()
{
el::Configurations conf("log.conf");
el::Loggers::reconfigureAllLoggers(conf);
}
Logger *Logger::instance()
{
static Logger ins;
return &ins;
}

20
src/logger/logger.h Normal file
View File

@ -0,0 +1,20 @@
#ifndef LOGGER_H
#define LOGGER_H
#include "easylogging++.h"
#define logde LOG(DEBUG)
#define loger LOG(ERROR)
#define logfa LOG(FATAL)
#define logFeature LOG(INFO)
#define logMatch LOG(WARNING)
class Logger
{
public:
explicit Logger();
static Logger *instance();
};
#endif // LOGGER_H

View File

@ -8,9 +8,13 @@
#include "realtimedataform.h"
#include "experimentsettingform.h"
#include "filemanager.h"
#include "logger.h"
int main(int argc, char *argv[])
{
Logger::instance();
logde<<"main...";
QApplication::setAttribute(Qt::AA_EnableHighDpiScaling); // 启用高DPI缩放
QApplication a(argc, argv);

File diff suppressed because it is too large Load Diff

4577
src/thirdparty/easylogging/easylogging++.h vendored Normal file

File diff suppressed because it is too large Load Diff

View File

@ -22,8 +22,8 @@ public slots:
void slotRecvLineXCoord(const int,const double);
private slots:
void slotApply();
void slotConfirm();
void slotUndo();
void slotConfirm();
void slotCancel();
private:
QDoubleSpinBox *_leftBorderSpinBox,*_rightBorderSpinBox;

View File

@ -7,6 +7,7 @@
#include "centralwidget.h"
#include "filemanager.h"
#include "peakpoint.h"
#include "logger.h"
CentralWidget::CentralWidget(QWidget *parent)
: QWidget(parent),
@ -73,11 +74,14 @@ CentralWidget::~CentralWidget()
void CentralWidget::setAnalysisMode(const CentralWidget::AnalysisMode mode)
{
#if 0
if(_nanlysisMode == mode){
return;
}else{
_nanlysisMode = mode;
}
#endif
_nanlysisMode = mode;
switch (mode)
{
@ -194,25 +198,20 @@ void CentralWidget::slotAnalysisSettingApply()
PeakPoint::setRegionPointX(x1,x2);
QPointF point = PeakPoint::findPeakPoint();
qDebug()<<"peak point:"<<point;
//enthalpy
double enthalpyValue = PeakPoint::calculateArea();
//peak
QPointF peakPoint = PeakPoint::findPeakPoint();
// qDebug()<<"peak point:"<<point;
//start point and end point
QPair<QPointF, QPointF> startEndPointPair = PeakPoint::calculateStartAndEndPoint();
double enthalpyValue = 1.1;
double peakValue = 3.1;
double startPoint = 4.1;
double endPoint = 5.1;
drawText(point,PeakPoint::textFormat(
enthalpyValue,peakValue,startPoint,endPoint));
#if 0
QString PeakPoint::textFormat(const double enthalpyValue,
const double peakValue,
const double startPoint,
const double endPoint)
#endif
//
break;
drawText(peakPoint,PeakPoint::textFormat(enthalpyValue,
peakPoint.x(),
startEndPointPair.first.x(),
startEndPointPair.second.x()));
//
break;
}
default:
break;
@ -274,16 +273,18 @@ void CentralWidget::contextMenuEvent(QContextMenuEvent *event)
void CentralWidget::setEventHandlerEnable(const bool flag)
{
// 当竖线隐藏时,需要设置不可选择模式。
// _line1->setSelectable(false);
_eventHandler->setEnable(flag);
_line1->setVisible(flag);
logde<<"setEventHandlerEnable..."<<flag;
// todo. 当竖线隐藏时,需要设置不可选择模式。
_eventHandler->setEnable(flag);
_line1->setVisible(flag);
if(AnalysisMode::NumericalLabel != _nanlysisMode){
_line2->setVisible(flag);
}
_customPlot->replot();
}
void CentralWidget::drawText(const QPointF point, const QString text)
{
// double y = PeakPoint::findClosestY(x);
@ -417,6 +418,39 @@ void CentralWidget::fillGraph(const double x1, const double x2)
void CentralWidget::clearAllData()
{
#if 1
// Set lines visiable false.
_line1->setVisible(false);
_line2->setVisible(false);
// Clear the data of graph.
if (_customPlot->graphCount() > 0 && _graph)
{
_graph->setData(QVector<double>(), QVector<double>());
}
_graph->setBrush(QBrush(Qt::transparent));
// Clear graph on plot.
for (int i = _customPlot->graphCount() - 1; i >= 0; --i) {
QCPGraph *graph = _customPlot->graph(i);
if (graph != _graph) {
_customPlot->removeGraph(graph);
}
}
// Delete items.
QList<QCPAbstractItem *> itemsToKeep;
itemsToKeep << _line1 << _line2;
for (int i = _customPlot->itemCount() - 1; i >= 0; --i) {
QCPAbstractItem *item = _customPlot->item(i);
if (!itemsToKeep.contains(item)) {
_customPlot->removeItem(item);
}
}
// 重绘图表以显示更改
_customPlot->replot();
#endif
#if 0
// 删除不需要的 Item
@ -448,39 +482,6 @@ void CentralWidget::clearAllData()
_customPlot->replot();
#endif
#if 1
_line1->setVisible(false);
_line2->setVisible(false);
if (_customPlot->graphCount() > 0 && _graph)
{
// 清除第一个图表上的数据
_graph->setData(QVector<double>(), QVector<double>());
}
// 保留的元素列表
QList<QCPAbstractItem *> itemsToKeep;
itemsToKeep << _line1 << _line2;
// 遍历所有项并移除不在保留列表中的项
// QCPAbstractItem
// QList<QCPAbstractItem *> allItems = _customPlot->item();
for (int i = _customPlot->itemCount() - 1; i >= 0; --i) {
QCPAbstractItem *item = _customPlot->item(i);
if (!itemsToKeep.contains(item)) {
// 从图表中移除项
_customPlot->removeItem(item);
// 删除项,释放内存
// delete item;
}
}
// 重绘图表以显示更改
_customPlot->replot();
#endif
#if 0
// 遍历并删除所有图形元素,除了指定的元素
for (int i = _customPlot->itemCount() - 1; i >= 0; --i) {

View File

@ -67,7 +67,7 @@ bool DragLineHandler::eventFilter(QObject *obj, QEvent *event)
}
else if (event->type() == QEvent::MouseButtonPress)
{
qDebug()<<"mouse press...";
// qDebug()<<"mouse press...";
QMouseEvent *mouseEvent = static_cast<QMouseEvent*>(event);
if (mouseEvent->button() == Qt::LeftButton)
@ -125,7 +125,7 @@ void DragLineHandler::updateSelectedRegion()
int index1 = findClosestIndex(xData, x1);
int index2 = findClosestIndex(xData, x2);
qDebug() << "Selected region: [" << xData[index1] << ", " << xData[index2] << "]";
// qDebug() << "Selected region: [" << xData[index1] << ", " << xData[index2] << "]";
}
int DragLineHandler::findClosestIndex(const QVector<double> &data, double target)

View File

@ -25,7 +25,6 @@ public slots:
void slotRecvPhaseInfo(const QByteArray &);
private slots:
void on_pushButton_deliverData_clicked();
private:
//ui
void uiReset();