From 73019c5a6dc61567d468ab4146e63dd454e19c07 Mon Sep 17 00:00:00 2001 From: baiYue Date: Fri, 9 Jan 2026 17:43:58 +0800 Subject: [PATCH] add struct data previewer ui/logic --- common/include/global.h | 13 +- diagramCavas/CMakeLists.txt | 10 + .../include/structDataMeasurementDelegate.h | 55 ++ .../include/structDataMeasurementModel.h | 78 ++ diagramCavas/include/structDataPreviewDlg.h | 66 +- .../include/structDataPropertyDelegate.h | 49 ++ .../include/structDataPropertyModel.h | 77 ++ diagramCavas/include/structDataSource.h | 84 ++ diagramCavas/source/baseInfoDlg.cpp | 6 +- diagramCavas/source/bayInfoDlg.cpp | 7 +- diagramCavas/source/ctExtraInfoDlg.cpp | 42 +- diagramCavas/source/diagramCavas.cpp | 13 +- .../graphicsDataModel/diagramEditorModel.cpp | 2 +- .../graphicsDataModel/fixedPortsModel.cpp | 196 ++++- .../source/graphicsItem/electricPortItem.cpp | 1 + .../graphicsItem/electricSvgItemBus.cpp | 1 + .../source/graphicsItem/graphicsBaseItem.cpp | 1 + diagramCavas/source/measureSettingDlg.cpp | 28 +- diagramCavas/source/monitorConfigDlg.cpp | 1 - diagramCavas/source/propertyContentDlg.cpp | 12 +- diagramCavas/source/ptExtraInfoDlg.cpp | 38 +- .../source/structDataMeasurementDelegate.cpp | 309 +++++++ .../source/structDataMeasurementModel.cpp | 269 +++++++ diagramCavas/source/structDataPreviewDlg.cpp | 751 +++++++++++++++++- .../source/structDataPropertyDelegate.cpp | 210 +++++ .../source/structDataPropertyModel.cpp | 221 ++++++ diagramCavas/source/structDataSource.cpp | 213 +++++ diagramCavas/ui/measureSettingDlg.ui | 182 ++--- diagramCavas/ui/structDataPreviewDlg.ui | 121 ++- diagramUtils/include/dataBase.h | 2 + diagramUtils/source/dataBase.cpp | 175 +++- diagramUtils/source/dataManager.cpp | 51 +- 32 files changed, 2986 insertions(+), 298 deletions(-) create mode 100644 diagramCavas/include/structDataMeasurementDelegate.h create mode 100644 diagramCavas/include/structDataMeasurementModel.h create mode 100644 diagramCavas/include/structDataPropertyDelegate.h create mode 100644 diagramCavas/include/structDataPropertyModel.h create mode 100644 diagramCavas/include/structDataSource.h create mode 100644 diagramCavas/source/structDataMeasurementDelegate.cpp create mode 100644 diagramCavas/source/structDataMeasurementModel.cpp create mode 100644 diagramCavas/source/structDataPropertyDelegate.cpp create mode 100644 diagramCavas/source/structDataPropertyModel.cpp create mode 100644 diagramCavas/source/structDataSource.cpp diff --git a/common/include/global.h b/common/include/global.h index fa7d459..76337bd 100644 --- a/common/include/global.h +++ b/common/include/global.h @@ -374,6 +374,7 @@ struct modelDataInfo //模型数据信息 struct propertyContentInfo //单个属性结构 { + QString proTag; QString proName; //名称 QString proType; //类型 QWidget* proEditer = NULL; //编辑窗口对象 @@ -903,8 +904,6 @@ struct MeasurementInfo //量测 { QString tag; //量测tag QString name; //量测名称 - QString equipment; //设备名称 - QString channel; //设备端子 int type; //量测类型 0:遥测 1:遥信 2:遥控 int size; //量测size QUuid bayUuid; //所属间隔 @@ -913,6 +912,7 @@ struct MeasurementInfo //量测 //通讯 int nSource; //数据来源 1:cl3611 2:104 QString sStation; //子站名称 + QString sDevice; //设备名称 QString sChannel; //通道名(cl3611) 遥测:TMx(1-8); P; Q; S; PF; F; deltaF; UAB; UBC; UCA; 遥信: TSxx(01-10); 遥控: TCx; int nPacket; //包号(104) int nOffset; //偏移量(104) @@ -941,6 +941,7 @@ struct ExtraProperty QString bay_name; QString component_name; QString group_name; + QString type_name; //层级索引 QString grid_tag; @@ -950,6 +951,7 @@ struct ExtraProperty QString bay_tag; QUuid component_uuid; QString group_tag; + QString type_tag; // 数据源配置 QString sourceType; // "property", "measurement" @@ -1015,6 +1017,13 @@ struct ExtraProperty } }; +struct ExtraPropertyLevelInfo { //层级关系item信息 + QString displayText; // 显示文本 + QString nameValue; // 名称值 + QString tagValue; // 标签值 + bool isRequired; // 是否必填 + QString placeholder; // 缺省占位符 +}; //================================================== struct baseComponentInfo //基模图元数据 { diff --git a/diagramCavas/CMakeLists.txt b/diagramCavas/CMakeLists.txt index a8c8e4f..1255d9b 100644 --- a/diagramCavas/CMakeLists.txt +++ b/diagramCavas/CMakeLists.txt @@ -43,6 +43,11 @@ set(DIAGRAMCAVAS_HEADER_FILES include/diagramConnectSetting.h include/structDataPreviewDlg.h include/titleBar.h + include/structDataSource.h + include/structDataMeasurementModel.h + include/structDataPropertyModel.h + include/structDataMeasurementDelegate.h + include/structDataPropertyDelegate.h include/diagramEditor/editPanel.h include/diagramEditor/editView.h include/diagramEditor/editScene.h @@ -168,6 +173,11 @@ set(DIAGRAMCAVAS_SOURCE_FILES source/diagramConnectSetting.cpp source/structDataPreviewDlg.cpp source/titleBar.cpp + source/structDataSource.cpp + source/structDataMeasurementModel.cpp + source/structDataPropertyModel.cpp + source/structDataMeasurementDelegate.cpp + source/structDataPropertyDelegate.cpp source/diagramEditor/editPanel.cpp source/diagramEditor/editView.cpp source/diagramEditor/editScene.cpp diff --git a/diagramCavas/include/structDataMeasurementDelegate.h b/diagramCavas/include/structDataMeasurementDelegate.h new file mode 100644 index 0000000..7902e11 --- /dev/null +++ b/diagramCavas/include/structDataMeasurementDelegate.h @@ -0,0 +1,55 @@ +#ifndef STRUCTDATAMEASUREMENTDELEGATE_H +#define STRUCTDATAMEASUREMENTDELEGATE_H +/** + * 结构预览ui的量测类型model + * */ +#include + +class StructDataSource; +struct MeasurementInfo; +struct ExtraProperty; +class QCompleter; + +class StructDataMeasurementDelegate : public QStyledItemDelegate +{ + Q_OBJECT + +public: + StructDataMeasurementDelegate(QObject* parent = nullptr); + + QWidget* createEditor(QWidget* parent, + const QStyleOptionViewItem& option, + const QModelIndex& index) const override; + + void setEditorData(QWidget* editor, const QModelIndex& index) const override; + + void setModelData(QWidget* editor, QAbstractItemModel* model,const QModelIndex& index) const override; + + void updateEditorGeometry(QWidget* editor,const QStyleOptionViewItem& option,const QModelIndex& index) const override; + + QString displayText(const QVariant& value, const QLocale& locale) const override; + + // 提供工具提示 + QString displayText(const QVariant& value, const QLocale& locale,const QModelIndex& index) const; + + void setConnectParaCompleter(QCompleter* p) {_connectCompleter = p;} //设置连接参数输入的completer +public slots: + void onConnectParamChanged(const QString& str) const; +protected: + bool eventFilter(QObject *obj, QEvent *event) override; +private: + QWidget* createConnectParaEditor(QWidget* parent) const; + + QWidget* createTextEditor(QWidget* parent) const; + + QWidget* createMeasurementTypeEditor(QWidget* parent) const; + QWidget* createSizeEditor(QWidget* parent) const; + QWidget* createSourceEditor(QWidget* parent) const; + QWidget* createNumberEditor(QWidget* parent) const; + + QWidget* createEnableEditor(QWidget* parent) const; +private: + QCompleter* _connectCompleter = nullptr; //自动补全的completer +}; + +#endif diff --git a/diagramCavas/include/structDataMeasurementModel.h b/diagramCavas/include/structDataMeasurementModel.h new file mode 100644 index 0000000..a692b65 --- /dev/null +++ b/diagramCavas/include/structDataMeasurementModel.h @@ -0,0 +1,78 @@ +#ifndef STRUCTDATAMEASUREMENTMODEL_H +#define STRUCTDATAMEASUREMENTMODEL_H +/** + * 结构预览ui的量测类型model + * */ +#include + +class StructDataSource; +struct MeasurementInfo; +struct ExtraProperty; + +class StructDataMeasurementModel : public QAbstractTableModel +{ + Q_OBJECT + +public: + enum Columns { + ColName = 0, + ColTag = 1, + ColCode = 2, + ColSourceType = 3, + ColConnectPara = 4, + ColType = 5, + ColSize = 6, + ColSource = 7, + ColStation = 8, + ColEquipment = 9, + ColChannel = 10, + ColPacket = 11, + ColOffset = 12, + ColEnable = 13, + ColumnCount + }; + + StructDataMeasurementModel(StructDataSource* dataManager, QObject* parent = nullptr); + + void setPropertyCodes(const QStringList& codes); + + void setProperties(const QVector& properties); + + int rowCount(const QModelIndex& parent = QModelIndex()) const override; + + int columnCount(const QModelIndex& parent = QModelIndex()) const override; + + QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override; + + bool setData(const QModelIndex& index, const QVariant& value, int role = Qt::EditRole) override; + + Qt::ItemFlags flags(const QModelIndex& index) const override; + + QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const override; + + QVector getDisplayedProperties() const; + + QStringList getDisplayedCodes() const; + + int findRowByCode(const QString& code) const; + + void refreshRow(const QString& code); + +private slots: + void onPropertyUpdated(const ExtraProperty& updatedProp, bool isNew); +signals: + void propertiesLoaded(int count); + void propertyModified(int row, const ExtraProperty& prop); +private: + ExtraProperty* getProperty(int displayRow) const; + QVariant getMeasurementData(const ExtraProperty& prop, int col) const; + bool updateMeasurementData(MeasurementInfo* data, int col, const QVariant& value); + QString getTypeText(int type) const; + QString getSourceText(int source) const; + int getSourceInt(QString) const; +private: + StructDataSource* m_dataManager = nullptr; + QStringList m_propertyCodes; +}; + +#endif diff --git a/diagramCavas/include/structDataPreviewDlg.h b/diagramCavas/include/structDataPreviewDlg.h index 8748b20..4fe3bc2 100644 --- a/diagramCavas/include/structDataPreviewDlg.h +++ b/diagramCavas/include/structDataPreviewDlg.h @@ -5,6 +5,7 @@ **/ #include +#include "dataManager.h" QT_BEGIN_NAMESPACE namespace Ui { class structDataPreviewDlg; } @@ -13,6 +14,18 @@ QT_END_NAMESPACE class QStandardItemModel; class TitleBar; class ExtraPropertyManager; +struct ExtraProperty; +class QStandardItem; +class QTreeView; +class QAbstractItemModel; +class StructDataSource; +class StructDataMeasurementModel; +class StructDataPropertyModel; +class StructDataPropertyDelegate; +class StructDataMeasurementDelegate; +class QStatusBar; +class QCompleter; +class QStringListModel; class StructDataPreviewDlg : public QDialog { @@ -22,20 +35,26 @@ public: ~StructDataPreviewDlg(); void initial(); + void loadData(); void showMaximized(); void showNormal(); void setExtraPropertyManager(ExtraPropertyManager* p) {_pExtraProManager = p;} void showDlg(); + QVector getGroupProperties(QStandardItem* groupItem); //获取属性组的所有属性 + QString getGroupSourceType(QStandardItem* groupItem); + void addItemToView(const ExtraProperty& property, + const QString& displayMode, // "name" 或 "tag" + QStandardItem* root, + QStandardItem* pItem); + void updateRecommandLst(QStringList); //更新当前推荐列表 public slots: void onExitClicked(); void onSaveClicked(); - void onGridClicked(); //网 - void onZoneClicked(); //区 - void onStationClicked(); //站 - void onBayClicked(); //间隔 - void onDeviceClicked(); //设备 - void onPropertyClicked(); //属性 + + void onLevelButtonClicked(int nLevel); + void onTreeSelectionChanged(const QModelIndex& current, const QModelIndex& previous); + void onPropertyModified(int row, const ExtraProperty& prop); protected: void showEvent(QShowEvent *event) override; void resizeEvent(QResizeEvent *event) override; @@ -43,12 +62,47 @@ private slots: void toggleMaximize(); private: void clearItems(); + QString getLevelType(int index); + void expandToLevel(QTreeView* treeView, int targetLevel); // 展开到指定层级 + void expandToLevelRecursive(QTreeView* treeView, + QAbstractItemModel* model, + const QModelIndex& parent, + int currentDepth, + int targetLevel); + int getNodeLevel(QAbstractItemModel* model, const QModelIndex& index); // 获取节点的层级(从存储的数据中读取) + int getDepthFromRoot(QAbstractItemModel* model, const QModelIndex& index); // 获取节点从根开始的深度 + QStandardItem* processGroupLevel(QStandardItem* componentItem,const ExtraProperty& property); // 处理group层级 + void processCategoryLevel(QStandardItem* groupItem,const ExtraProperty& property); // 处理category层级 + void updateCategoryProperties(QStandardItem* categoryItem,const ExtraProperty& property); // 更新category节点的属性列表 + void loadCategoryProperties(QStandardItem* categoryItem); + QVector getCategoryPropertiesFromDataManager(const QVariantMap& categoryData); + void setupPropertyTable(const QVector& properties,const QString& categoryName,const QString& groupName); //设置参量的model + void setupMeasurementTable(const QVector& properties,const QString& categoryName,const QString& groupName); //设置量测的model + void updateCategoryAfterPropertyModified(QStandardItem* categoryItem, const ExtraProperty& updatedProp); //回调更新节点 + void saveCurrentIfModified(); + void saveAll(); + void clearTableView(); + void setupPropertyColumns(); + void setupMeasurementColumns(); + void updateTableTitle(const QString& dataType, const QString& categoryName,const QString& groupName, int count); private: Ui::structDataPreviewDlg *ui; QStandardItemModel* _treeModel; TitleBar* m_titleBar; QRect m_normalGeometry; // 记录正常状态的位置和大小 ExtraPropertyManager* _pExtraProManager; //使用外部的manager + StructDataSource* m_dataSource; + bool m_currentModified = false; + QStandardItem* m_currentCategoryItem; //当前操作对象 + StructDataMeasurementModel* m_measurementTableModel; + StructDataPropertyModel* m_propertyTableModel; + StructDataPropertyDelegate* m_propertyDelegate; + StructDataMeasurementDelegate* m_measurementDelegate; + QStatusBar* m_statusBar; + + QStringList _curRecommandLst; //当前推荐列表 + QCompleter* _recommandCompleter; //自动填充器 + QStringListModel* _strLstModel; //自动填充模型 }; #endif diff --git a/diagramCavas/include/structDataPropertyDelegate.h b/diagramCavas/include/structDataPropertyDelegate.h new file mode 100644 index 0000000..1c0b5fc --- /dev/null +++ b/diagramCavas/include/structDataPropertyDelegate.h @@ -0,0 +1,49 @@ +#ifndef STRUCTDATAPROPERTYDELEGATE_H +#define STRUCTDATAPROPERTYDELEGATE_H +/** + * 结构预览ui的参量类型代理 + * */ +#include + +class StructDataSource; +struct MeasurementInfo; +struct ExtraProperty; +class QCompleter; + +class StructDataPropertyDelegate : public QStyledItemDelegate +{ + Q_OBJECT + +public: + StructDataPropertyDelegate(QObject* parent = nullptr); + + QWidget* createEditor(QWidget* parent,const QStyleOptionViewItem& option,const QModelIndex& index) const override; + + void setEditorData(QWidget* editor, const QModelIndex& index) const override; + + void setModelData(QWidget* editor, QAbstractItemModel* model,const QModelIndex& index) const override; + + void updateEditorGeometry(QWidget* editor,const QStyleOptionViewItem& option,const QModelIndex& index) const override; + QString displayText(const QVariant& value, const QLocale& locale) const override; + + void setConnectParaCompleter(QCompleter* p) {_connectCompleter = p;} //设置连接参数输入的completer +private: + QWidget* createConnectParaEditor(QWidget* parent) const; + + QWidget* createDefaultValueEditor(QWidget* parent, const QModelIndex& index) const; + + QWidget* createLengthPrecisionEditor(QWidget* parent) const; + + void setDefaultValueEditorData(QWidget* editor, const QVariant& value, const QModelIndex& index) const; + + QVariant getDefaultValueEditorData(QWidget* editor, const QModelIndex& index) const; +public slots: + void onConnectParamChanged(const QString& str) const; + +protected: + bool eventFilter(QObject *obj, QEvent *event) override; +private: + QCompleter* _connectCompleter = nullptr; //自动补全的completer +}; + +#endif diff --git a/diagramCavas/include/structDataPropertyModel.h b/diagramCavas/include/structDataPropertyModel.h new file mode 100644 index 0000000..2ed6fd9 --- /dev/null +++ b/diagramCavas/include/structDataPropertyModel.h @@ -0,0 +1,77 @@ +#ifndef STRUCTDATAPROPERTYMODEL_H +#define STRUCTDATAPROPERTYMODEL_H +/** + * 结构预览ui的参量类型model + * */ + +#include + +class StructDataSource; +struct ExtraProperty; +struct propertyStateInfo; + +class StructDataPropertyModel : public QAbstractTableModel +{ + Q_OBJECT + +public: + enum Columns { + ColName = 0, + ColTag = 1, + ColCode = 2, + ColSourceType = 3, + ColConnectPara = 4, + ColModelName = 5, + ColDataType = 6, + ColDefaultValue = 7, + ColLengthPrecision = 8, + ColumnCount + }; + + StructDataPropertyModel(StructDataSource* dataManager, QObject* parent = nullptr); + + // 设置要显示的code列表 + void setPropertyCodes(const QStringList& codes); + + // 设置要显示的属性 + void setProperties(const QVector& properties); + + int rowCount(const QModelIndex& parent = QModelIndex()) const override; + + int columnCount(const QModelIndex& parent = QModelIndex()) const override; + + QVariant data(const QModelIndex& index, int role = Qt::DisplayRole) const override; + + bool setData(const QModelIndex& index, const QVariant& value, int role = Qt::EditRole) override; + + Qt::ItemFlags flags(const QModelIndex& index) const override; + + QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const override; + + // 获取当前显示的属性 + QVector getDisplayedProperties() const; + + // 获取当前显示的code列表 + QStringList getDisplayedCodes() const; + + // 根据code查找行 + int findRowByCode(const QString& code) const; + + // 刷新指定code的行 + void refreshRow(const QString& code); +private slots: + void onPropertyUpdated(const ExtraProperty& updatedProp, bool isNew); +signals: + void propertyModified(int row, const ExtraProperty& prop); +private: + ExtraProperty* getProperty(int displayRow) const; + + QVariant getPropertyData(const ExtraProperty& prop, int col) const; + + bool updatePropertyData(propertyStateInfo* data, int col, const QVariant& value); + +private: + StructDataSource* m_dataManager = nullptr; + QStringList m_propertyCodes; // 存储当前显示的属性code列表 +}; +#endif diff --git a/diagramCavas/include/structDataSource.h b/diagramCavas/include/structDataSource.h new file mode 100644 index 0000000..97a636a --- /dev/null +++ b/diagramCavas/include/structDataSource.h @@ -0,0 +1,84 @@ +#ifndef STRUCTDATASOURCE_H +#define STRUCTDATASOURCE_H +/** + * *******结构化数据源接口****** + **/ +#include +struct ExtraProperty; +struct propertyStateInfo; +struct MeasurementInfo; +struct modelDataInfo; + +class StructDataSource : public QObject +{ + Q_OBJECT + +public: + StructDataSource(QObject* parent = nullptr); + + // 根据code获取属性 + ExtraProperty* getPropertyByCode(const QString& code); + + // 根据tag获取属性 + ExtraProperty* getPropertyByTag(const QString& tag); + + // 根据group获取属性列表 + QVector getPropertiesByGroup(const QString& groupTag, const QString& modelName = ""); + + // 根据sourceType获取属性列表 + QVector getPropertiesBySourceType(const QString& sourceType); + + // 添加或更新属性 + bool addOrUpdateProperty(const ExtraProperty& prop); + + // 更新单个属性 + bool updateProperty(const ExtraProperty& updatedProp); + + // 更新connect_para + bool updateConnectPara(const QString& code, const QString& newConnectPara); + + // 批量更新 + void updateProperties(const QVector& updatedProps); + + // 删除属性 + bool removeProperty(const QString& code); + + // 批量删除 + int removeProperties(const QVector& codes); + + // 保存到文件 + void saveAll(); + + // 加载数据 + void loadExtrapro(QMap vec); + + void loadPropertyData(QMap map); + + void loadMeasurementData(QMap map); + + // 获取所有属性的code列表 + QStringList getAllCodes() const; + + // 获取所有属性 + QVector getAllProperties() const; + + // 获取property数据 + propertyStateInfo* getPropertyData(const ExtraProperty& prop); + + // 获取measurement数据 + MeasurementInfo* getMeasurementData(const ExtraProperty& prop); + + // 验证数据 + bool validateProperty(const ExtraProperty& prop); + +signals: + void propertyUpdated(const ExtraProperty& prop, bool isNew); + void propertyRemoved(const ExtraProperty& prop); + void dataChanged(); +public: + QMap allProperties; +private: + QMap m_propertyData; + QMap m_measurementData; +}; +#endif diff --git a/diagramCavas/source/baseInfoDlg.cpp b/diagramCavas/source/baseInfoDlg.cpp index 260cf6a..409e739 100644 --- a/diagramCavas/source/baseInfoDlg.cpp +++ b/diagramCavas/source/baseInfoDlg.cpp @@ -40,17 +40,17 @@ void BaseInfoDlg::createGroupView(groupStateInfo infos) for(auto &info:lstGrid) { - ui->cb_grid->addItem(info.name,info.id); + ui->cb_grid->addItem(info.tagname,info.id); } for(auto &info:lstZone) { - ui->cb_zone->addItem(info.name,info.id); + ui->cb_zone->addItem(info.tagname,info.id); } for(auto &info:lstStation) { - ui->cb_station->addItem(info.name,info.id); + ui->cb_station->addItem(info.tagname,info.id); } } diff --git a/diagramCavas/source/bayInfoDlg.cpp b/diagramCavas/source/bayInfoDlg.cpp index 1367c34..cd31ff4 100644 --- a/diagramCavas/source/bayInfoDlg.cpp +++ b/diagramCavas/source/bayInfoDlg.cpp @@ -40,9 +40,10 @@ void BayInfoDlg::createGroupView(groupStateInfo infos) { for(auto& info:infos.info) { propertyContentInfo inf; + inf.proTag = info.tagName; inf.proName = info.name; inf.proType = info.type; - _mapPro.insert(info.name,inf); + _mapPro.insert(info.tagName,inf); } } @@ -256,10 +257,10 @@ void BayInfoDlg::addMeasure(MeasurementInfo info,int mode) QTableWidgetItem* nameItem = new QTableWidgetItem(info.name); ui->tableWidget_local->setItem(row, 1, nameItem); - QTableWidgetItem* deviceItem = new QTableWidgetItem(info.equipment); + QTableWidgetItem* deviceItem = new QTableWidgetItem(info.sDevice); ui->tableWidget_local->setItem(row, 2, deviceItem); - QTableWidgetItem* channelItem = new QTableWidgetItem(info.channel); + QTableWidgetItem* channelItem = new QTableWidgetItem(info.sChannel); ui->tableWidget_local->setItem(row, 3, channelItem); QString sType; diff --git a/diagramCavas/source/ctExtraInfoDlg.cpp b/diagramCavas/source/ctExtraInfoDlg.cpp index 4657435..7240079 100644 --- a/diagramCavas/source/ctExtraInfoDlg.cpp +++ b/diagramCavas/source/ctExtraInfoDlg.cpp @@ -28,9 +28,10 @@ void CtExtraInfoDlg::createGroupView(groupStateInfo infos) { for(auto& info:infos.info) { propertyContentInfo inf; + inf.proTag = info.tagName; inf.proName = info.name; inf.proType = info.type; - _mapPro.insert(info.name,inf); + _mapPro.insert(info.tagName,inf); } } @@ -41,44 +42,45 @@ QMap CtExtraInfoDlg::getPropertyValue(BaseProperty* p for(auto &pro:_mapPro) { propertyStateInfo info; + info.tagName = pro.proTag; info.type = pro.proType; info.name = pro.proName; - if(info.name == "额定电流(A)" || info.name == "in_a") //此处应为类型名 + if(info.name == "额定电流(A)" || info.tagName == "in_a") //此处应为类型名 { info.defaultValue = ui->le_ratedCurrent->text(); } - else if(info.name == "工频耐压(V/1min)" || info.name == "uac_v_1min") + else if(info.name == "工频耐压(V/1min)" || info.tagName == "uac_v_1min") { info.defaultValue = ui->le_pfwv_ct->text(); } - else if(info.name == "冲击耐压(V)" || info.name == "uimp_v") + else if(info.name == "冲击耐压(V)" || info.tagName == "uimp_v") { info.defaultValue = ui->le_iwv_ct->text(); } - else if(info.name == "动稳定电流(A)" || info.name == "dsc_a") + else if(info.name == "动稳定电流(A)" || info.tagName == "dsc_a") { info.defaultValue = ui->le_dsc_ct->text(); } - else if(info.name == "仪表保安系数" || info.name == "fs") + else if(info.name == "仪表保安系数" || info.tagName == "fs") { info.defaultValue = ui->le_isf->text(); } - else if(info.name == "热稳定电流(A)" || info.name == "ith_a") + else if(info.name == "热稳定电流(A)" || info.tagName == "ith_a") { info.defaultValue = ui->le_sttc->text(); } - else if(info.name == "额定频率(Hz)" || info.name == "fn_hz") + else if(info.name == "额定频率(Hz)" || info.tagName == "fn_hz") { info.defaultValue = ui->le_rf_ct->text(); } - else if(info.name == "相数" || info.name == "phase_num") + else if(info.name == "相数" || info.tagName == "phase_num") { if(ui->rb_tpt_ct->isChecked()) info.defaultValue = 1; else info.defaultValue = 0; } - else if(info.name == "CT绕组" || info.name == "ct_winding") + else if(info.name == "CT绕组" || info.tagName == "ct_winding") { QJsonObject object; QJsonArray arr; @@ -96,7 +98,7 @@ QMap CtExtraInfoDlg::getPropertyValue(BaseProperty* p object["winding"] = arr; info.defaultValue = object; } - map.insert(pro.proName,info); + map.insert(pro.proTag,info); } pPro->setDataChanged(true); return map; @@ -107,44 +109,44 @@ void CtExtraInfoDlg::setPropertyValue(QVariant var) QMap map = var.value>(); for(auto &info:map) { - if(info.name == "额定电流(A)" || info.name == "in_a") //此处应为类型名 + if(info.name == "额定电流(A)" || info.tagName == "in_a") //此处应为类型名 { ui->le_ratedCurrent->setText(QString::number(info.defaultValue.toDouble())); } - else if(info.name == "工频耐压(V/1min)" || info.name == "uac_v_1min") + else if(info.name == "工频耐压(V/1min)" || info.tagName == "uac_v_1min") { ui->le_pfwv_ct->setText(QString::number(info.defaultValue.toDouble())); } - else if(info.name == "冲击耐压(V)" || info.name == "uimp_v") + else if(info.name == "冲击耐压(V)" || info.tagName == "uimp_v") { ui->le_iwv_ct->setText(QString::number(info.defaultValue.toDouble())); } - else if(info.name == "动稳定电流(A)" || info.name == "dsc_a") + else if(info.name == "动稳定电流(A)" || info.tagName == "dsc_a") { ui->le_dsc_ct->setText(QString::number(info.defaultValue.toDouble())); } - else if(info.name == "仪表保安系数" || info.name == "fs") + else if(info.name == "仪表保安系数" || info.tagName == "fs") { if(info.defaultValue.toString() == "null") ui->le_isf->setText(0); ui->le_isf->setText(QString::number(info.defaultValue.toDouble())); } - else if(info.name == "热稳定电流(A)" || info.name == "ith_a") + else if(info.name == "热稳定电流(A)" || info.tagName == "ith_a") { ui->le_sttc->setText(QString::number(info.defaultValue.toDouble())); } - else if(info.name == "额定频率(Hz)" || info.name == "fn_hz") + else if(info.name == "额定频率(Hz)" || info.tagName == "fn_hz") { ui->le_rf_ct->setText(QString::number(info.defaultValue.toDouble())); } - else if(info.name == "相数" || info.name == "phase_num") + else if(info.name == "相数" || info.tagName == "phase_num") { if(info.defaultValue.toInt() == 1) ui->rb_tpt_ct->setChecked(true); else ui->rb_zst_ct->setChecked(true); } - else if(info.name == "CT绕组" || info.name == "ct_winding") + else if(info.name == "CT绕组" || info.tagName == "ct_winding") { QString jsonString = info.defaultValue.toString(); QJsonDocument jsonDocument = QJsonDocument::fromJson(jsonString.toUtf8().data()); diff --git a/diagramCavas/source/diagramCavas.cpp b/diagramCavas/source/diagramCavas.cpp index c6d4c6a..38d166a 100644 --- a/diagramCavas/source/diagramCavas.cpp +++ b/diagramCavas/source/diagramCavas.cpp @@ -74,6 +74,16 @@ void DiagramCavas::updateSubPos() void DiagramCavas::passRecommmandHttpData(HttpRecommandInfo info) { + if(_structDataPreviewDlg){ //数据预览dlg + QStringList lst; + for(auto &str:info.lstRecommand){ + QString sCompleteName = info.sInput+str; + if(!lst.contains(sCompleteName)) + lst.append(sCompleteName); + } + _structDataPreviewDlg->updateRecommandLst(lst); + } + //=============================================== QMdiSubWindow* pSub = currentSubWindow(); if(!pSub) return; @@ -162,6 +172,7 @@ void DiagramCavas::initial() Qt::AutoConnection); _structDataPreviewDlg = new StructDataPreviewDlg(this); _structDataPreviewDlg->setExtraPropertyManager(_extraPropertyManager); + _structDataPreviewDlg->loadData(); } void DiagramCavas::onSignal_addDrawingPanel(PowerEntity* pItem,DiagramMode mode,QString parent) @@ -529,7 +540,7 @@ void DiagramCavas::onSignal_openNetSetting() void DiagramCavas::onSignal_openStructDataPreview() { if(_structDataPreviewDlg) - _structDataPreviewDlg->show(); + _structDataPreviewDlg->showDlg(); } void DiagramCavas::removePanel(PowerEntity* pEntity) diff --git a/diagramCavas/source/graphicsDataModel/diagramEditorModel.cpp b/diagramCavas/source/graphicsDataModel/diagramEditorModel.cpp index 730270f..34c39ed 100644 --- a/diagramCavas/source/graphicsDataModel/diagramEditorModel.cpp +++ b/diagramCavas/source/graphicsDataModel/diagramEditorModel.cpp @@ -580,7 +580,7 @@ void DiagramEditorModel::generatePreview() } } - for(auto iter = baysCompo.begin();iter != baysCompo.end();++iter){ + for(auto iter = baysCompo.begin();iter != baysCompo.end();++iter){ //与间隔相连的线路都被计入间隔 //QMultiMap mapId = generateOutConnection(iter.value(),2); QList lstFrom; //处理进出链接 diff --git a/diagramCavas/source/graphicsDataModel/fixedPortsModel.cpp b/diagramCavas/source/graphicsDataModel/fixedPortsModel.cpp index bd858a0..86997d6 100644 --- a/diagramCavas/source/graphicsDataModel/fixedPortsModel.cpp +++ b/diagramCavas/source/graphicsDataModel/fixedPortsModel.cpp @@ -706,6 +706,9 @@ void FixedPortsModel::loadNodeDataFromDataBase() QString sMeta = info.context["metaModel"].toString(); pData->setMetaModelName(sMeta); + double dVoltage = info.context["extraInfo"].toDouble(); + pData->setVoltageLevel(dVoltage); + QJsonArray nodesJsonArray = info.context["subList"].toArray(); QList> lst; for (QJsonValueRef nodeJson : nodesJsonArray) @@ -889,6 +892,7 @@ void FixedPortsModel::saveNode(int nPageId) QList lstGrid = DataBase::GetInstance()->getAllGrid(); QList lstZone = DataBase::GetInstance()->getAllZone(); QList lstStation = DataBase::GetInstance()->getAllStation(); + QMap groupMap = DataBase::GetInstance()->AttributeGroup(); //属性组名 for(auto& bay:_bayItem) { @@ -993,6 +997,50 @@ void FixedPortsModel::saveNode(int nPageId) } //层级关系与连接参数 + BayProperty* bayPro = nullptr; //本data对应的bay + QMap mapBay = allBayItem(); + for(auto& item:mapBay){ + AbstractProperty* pPro = item->getProperty(); + BayProperty* pBayPro = dynamic_cast(pPro); + if(pBayPro){ + QList lstCompo = pBayPro->getLstComponent(); //获取间隔下的component,找到本component对应的间隔 + for(auto& id:lstCompo){ + if(id == pData->uuid()){ + bayPro = pBayPro; + break; + } + } + } + } + QString sGridTag; + QString sGridName; + QString sZoneTag; + QString sZoneName; + QString sStationTag; + QString sStationName; + for(auto& gridInfo:lstGrid){ + if(pData->grid() == gridInfo.tagname){ + sGridTag= gridInfo.tagname; + sGridName= gridInfo.name; + break; + } + } + + for(auto& zoneInfo:lstZone){ + if(pData->zone() == zoneInfo.tagname){ + sZoneTag = zoneInfo.tagname; + sZoneName = zoneInfo.name; + break; + } + } + + for(auto& stationInfo:lstStation){ + if(pData->station() == stationInfo.tagname){ + sStationTag = stationInfo.tagname; + sStationName = stationInfo.name; + break; + } + } for(auto &val:dataInfo.groupInfo) { if(val.groupName == "component" || val.groupName == "bay") @@ -1001,40 +1049,58 @@ void FixedPortsModel::saveNode(int nPageId) auto mapPro = val.mapInfo[pData->uuid()]; for(auto& pro:mapPro) { - QString sCode; - ExtraProperty extraPro; + ExtraProperty extraPro; //层级信息 extraPro.name = pro.name; extraPro.tag = pro.tagName; + extraPro.grid_tag = sGridTag; + extraPro.grid_name = sGridName; + extraPro.zone_tag = sZoneTag; + extraPro.zone_name = sZoneName; + extraPro.station_tag = sStationTag; + extraPro.station_name = sStationName; - for(auto& gridInfo:lstGrid){ - if(pData->grid() == gridInfo.tagname){ - extraPro.grid_tag = gridInfo.tagname; - extraPro.grid_name = gridInfo.name; + extraPro.currentLevel = QString::number(pData->getVoltageLevel())+"kv"; + extraPro.page_tag = _widget->pageName(); //暂时相同 + if(bayPro){ + extraPro.bay_name = bayPro->name(); + extraPro.bay_tag = bayPro->tag(); + } + extraPro.component_name = pData->name(); + extraPro.component_uuid = pData->uuid(); + extraPro.group_tag = val.groupName; + + for(auto& groupInfo:groupMap){ + if(val.groupName == groupInfo.groupType){ + extraPro.group_name = groupInfo.groupName; break; } } + extraPro.type_name = "参量"; + extraPro.type_tag = "parameter"; - for(auto& zoneInfo:lstZone){ - if(pData->zone() == zoneInfo.tagname){ - extraPro.zone_tag = zoneInfo.tagname; - extraPro.zone_name = zoneInfo.name; - break; - } - } + extraPro.code = extraPro.getFullName(); + extraPro.sourceType = "property"; + extraPro.sourceConfig.insert("modelName",pData->modelName()); + //取data:模型.属性组.id.属性名 - for(auto& stationInfo:lstStation){ - if(pData->station() == stationInfo.tagname){ - extraPro.station_tag = stationInfo.tagname; - extraPro.station_name = stationInfo.name; - break; - } - } + bool exist = DataBase::GetInstance()->ifExtraPropertyExist(extraPro.code); + if(exist) + DataBase::GetInstance()->updateExtraProperty(extraPro); + else + DataBase::GetInstance()->insertExtraProperty(extraPro); } } } QMap mapMeasure = pData->getMeasurement(); //量测 + QList lstTemp= DataBase::GetInstance()->getCompoExtraProperty(pData->uuid()); //component中的层级关系 + QList lstExtra; + for(auto& info:lstTemp){ + if(info.group_tag != "bay") //只对量测判断 + continue; + lstExtra.append(info); + } QList lstDataBase = DataBase::GetInstance()->getMeasurement(pData->uuid()); //数据库中现有量测 for(auto& info:mapMeasure) @@ -1046,7 +1112,7 @@ void FixedPortsModel::saveNode(int nPageId) if(info.nSource == 1){ //3611 objDataSource["type"] = 1; objIoAddress["station"] = info.sStation; - objIoAddress["device"] = info.equipment; + objIoAddress["device"] = info.sDevice; objIoAddress["channel"] = info.sChannel; } else if(info.nSource == 2){ //104 @@ -1096,12 +1162,72 @@ void FixedPortsModel::saveNode(int nPageId) break; } } + + for(int i = 0;i < lstExtra.size();++i){ //同步层级信息计数 + if(lstExtra[i].name == info.name){ + lstExtra.removeAt(i); + break; + } + } + + ExtraProperty extraPro; //层级信息 + extraPro.name = info.name; + extraPro.tag = tempTag; + extraPro.grid_tag = sGridTag; + extraPro.grid_name = sGridName; + extraPro.zone_tag = sZoneTag; + extraPro.zone_name = sZoneName; + extraPro.station_tag = sStationTag; + extraPro.station_name = sStationName; + + extraPro.currentLevel = QString::number(pData->getVoltageLevel())+"kv"; + extraPro.page_tag = _widget->pageName(); //暂时相同 + if(bayPro){ + extraPro.bay_name = bayPro->name(); + extraPro.bay_tag = bayPro->tag(); + } + extraPro.component_name = pData->name(); + extraPro.component_uuid = pData->uuid(); + extraPro.group_tag = "bay"; + + for(auto& groupInfo:groupMap){ + if("bay" == groupInfo.groupType){ + extraPro.group_name = groupInfo.groupName; + break; + } + } + + if(tpe == 0){ + extraPro.type_name = "遥测"; + extraPro.type_tag = "telemetry"; + } + else if(tpe == 1){ + extraPro.type_name = "遥信"; + extraPro.type_tag = "telesignal"; + } + else if(tpe == 2){ + extraPro.type_name = "遥控"; + extraPro.type_tag = "telecontrol"; + } + extraPro.code = extraPro.getFullName(); + extraPro.sourceType = "measurement"; + //取data 量测tag + + bool exist = DataBase::GetInstance()->ifExtraPropertyExist(extraPro.code); + if(exist) + DataBase::GetInstance()->updateExtraProperty(extraPro); + else + DataBase::GetInstance()->insertExtraProperty(extraPro); } for(auto& info:lstDataBase) //操作的记录小于数据库中的记录,删除库中多出的记录 { DataBase::GetInstance()->delteMeasurement(info.name,info.componentUuid); } + + for(auto& info:lstExtra){ //删除库中多出的层级信息 + DataBase::GetInstance()->deleteExtraProperty(info.code); + } } if(pData->type() == 8){ @@ -1797,7 +1923,8 @@ void FixedPortsModel::onWizardFinished(QMap mapIte if(pBus){ QString sBus = pBus->getName(); if(sBus == pPro->name()){ - pPro->setVoltageLevel(pBus->getVoltage()); //设置本体电压层级 + double dVol = pBus->getVoltage(); + pPro->setVoltageLevel(dVol); //设置本体电压层级 pPro->setSubList(pBus->getSubList()); //将子列表转移到item } } @@ -1812,13 +1939,33 @@ void FixedPortsModel::onWizardFinished(QMap mapIte if(pTrans){ QString sTrans = pTrans->getName(); if(sTrans == pPro->name()){ - pPro->setVoltageLevel(pTrans->getVoltage()); //设置本体电压 + double dVol = pTrans->getVoltage(); + pPro->setVoltageLevel(dVol); //设置本体电压 pPro->setSubList(pTrans->getSubList()); //将子列表转移到item } } } } } + else{ //其他设备 + for(auto item:mapBlock){ + auto p = item->getBlockData(); //获取blockitem对应的data + if(p->getType() == 2){ + DiagramEditorBayBlock* pBlock = dynamic_cast(p.data()); + if(pBlock){ + QString sBlock = pBlock->getName(); + QString sBay = pPro->getBay(); + if(sBlock == sBay){ + double dVol = pBlock->getVoltage(); + pPro->setVoltageLevel(dVol); //设置本体电压 + break; + } + } + } + } + } + + cloneItem->setProperty(pPro); _scene->addItem(cloneItem); cloneItem->setPos(pItem->pos()); @@ -2051,6 +2198,7 @@ void FixedPortsModel::addProjectItemByBaseData(DrawingPanel* pPanel,GraphicsBase pPro->setPath(pBase->getBay()); pPro->setSubList(pBase->getSubList()); //传递sublist pPro->setBay(pBase->getBay()); + pPro->setVoltageLevel(pBase->getVoltageLevel()); QString sMeta = pBase->metaModelName(); QString sModel = pBase->modelName(); @@ -2918,7 +3066,7 @@ void FixedPortsModel::generateMonitorConfig(MonitorPanel* pPanel) for(auto& attr: iter.value().info){ monitorItemAttributeInfo info; info.sGroup = iter.key(); - info.sTag = attr.name; //***暂时使用相同 051121 by + info.sTag = attr.tagName; info.sName = attr.name; info.nConnectType = 0; lstInfo.append(info); diff --git a/diagramCavas/source/graphicsItem/electricPortItem.cpp b/diagramCavas/source/graphicsItem/electricPortItem.cpp index 1fb8ee7..5607a16 100644 --- a/diagramCavas/source/graphicsItem/electricPortItem.cpp +++ b/diagramCavas/source/graphicsItem/electricPortItem.cpp @@ -54,6 +54,7 @@ void ElectricPortItem::updateConnectData() obj["port"] = arr; obj["metaModel"] = _property->metaModelName(); + obj["extraInfo"] = _property->getVoltageLevel(); _property->setContext(obj); } } diff --git a/diagramCavas/source/graphicsItem/electricSvgItemBus.cpp b/diagramCavas/source/graphicsItem/electricSvgItemBus.cpp index 6c449fd..622ae31 100644 --- a/diagramCavas/source/graphicsItem/electricSvgItemBus.cpp +++ b/diagramCavas/source/graphicsItem/electricSvgItemBus.cpp @@ -57,6 +57,7 @@ void ElectricSvgItemBus::updateConnectData() obj["port"] = arr; obj["metaModel"] = _property->metaModelName(); obj["subList"] = _property->saveSubToJsonArr(); + obj["extraInfo"] = _property->getVoltageLevel(); _property->setContext(obj); } } diff --git a/diagramCavas/source/graphicsItem/graphicsBaseItem.cpp b/diagramCavas/source/graphicsItem/graphicsBaseItem.cpp index 7196b1d..3b62892 100644 --- a/diagramCavas/source/graphicsItem/graphicsBaseItem.cpp +++ b/diagramCavas/source/graphicsItem/graphicsBaseItem.cpp @@ -679,6 +679,7 @@ void GraphicsProjectModelItem::updateConnectData() obj["port"] = arr; obj["metaModel"] = _property->metaModelName(); obj["subList"] = _property->saveSubToJsonArr(); + obj["extraInfo"] = _property->getVoltageLevel(); _property->setContext(obj); } } diff --git a/diagramCavas/source/measureSettingDlg.cpp b/diagramCavas/source/measureSettingDlg.cpp index 318ecfd..fda0c7b 100644 --- a/diagramCavas/source/measureSettingDlg.cpp +++ b/diagramCavas/source/measureSettingDlg.cpp @@ -59,8 +59,6 @@ void MeasureSettingDlg::initial() void MeasureSettingDlg::showDlg() { _curMode = 0; - //ui->cb_tag->setEditable(true); - //ui->cb_name->setEditable(true); clearData(); QStringList lstTag; QStringList lstName; @@ -81,24 +79,8 @@ void MeasureSettingDlg::showDlg() ui->cb_tag->addItems(lstTag); ui->cb_name->addItems(lstName); - /*QStringList lstDevice; - if(_pBay){ - FixedPortsModel* pModel = _pBay->getModelController(); - if(pModel){ - auto map = pModel->allItems(); - for(auto& pItem:map){ - auto pPro = pItem->getProperty(); - if(pPro){ - lstDevice.append(pPro->tag()); //根据本图的图元获取对应设备名 - } - } - } - }*/ - ui->cb_equip->clear(); - ui->cb_equip->addItem(curItemName); BaseProperty* pro = _pBay->getProperty(); if(pro){ - ui->cb_equip->setCurrentText(pro->tag()); ui->le_s1->setText(pro->station()); ui->le_s2->setText(pro->station()); } @@ -108,21 +90,17 @@ void MeasureSettingDlg::showDlg() void MeasureSettingDlg::showDlg(MeasurementInfo info) { show(); - //ui->cb_tag->setEditable(false); - //ui->cb_name->setEditable(false); _curMode = 1; clearData(); ui->cb_tag->setCurrentText(info.tag); ui->cb_name->setCurrentText(info.name); - ui->cb_equip->setCurrentText(info.equipment); - ui->le_port->setText(info.channel); ui->cb_type->setCurrentIndex(info.type); ui->le_size->setText(QString::number(info.size)); if(info.nSource == 1){ //3611 ui->cb_rule->setCurrentIndex(0); ui->le_s1->setText(info.sStation); - ui->le_d1->setText(info.equipment); + ui->le_d1->setText(info.sDevice); if(info.type == 0){ //遥测 ui->cb_channelYC->setCurrentText(info.sChannel); } @@ -201,7 +179,6 @@ void MeasureSettingDlg::clearData() ui->cb_tag->clear(); if(ui->cb_name->count()) ui->cb_name->clear(); - ui->le_port->clear(); ui->le_size->clear(); ui->cb_type->setCurrentIndex(0); ui->cb_rule->setCurrentIndex(0); @@ -224,14 +201,13 @@ void MeasureSettingDlg::onOkClicked() MeasurementInfo info; info.tag = ui->cb_tag->currentText(); info.name = ui->cb_name->currentText(); - info.equipment = ui->cb_equip->currentText(); - info.channel = ui->le_port->text(); info.type = ui->cb_type->currentIndex(); info.size = ui->le_size->text().toInt(); info.nSource = ui->cb_rule->currentData().toInt(); if(info.nSource == 1){ //cl3611 info.sStation = ui->le_s1->text(); + info.sDevice = ui->le_d1->text(); } else if(info.nSource == 2){ info.sStation = ui->le_s2->text(); diff --git a/diagramCavas/source/monitorConfigDlg.cpp b/diagramCavas/source/monitorConfigDlg.cpp index a408487..c0cb98a 100644 --- a/diagramCavas/source/monitorConfigDlg.cpp +++ b/diagramCavas/source/monitorConfigDlg.cpp @@ -57,7 +57,6 @@ void MonitorConfigDlg::initial() onConnectParamChanged(text); } }); - //connect(ui->le_query,&QLineEdit::textChanged, this,&MonitorConfigDlg::onConnectParamChanged); } void MonitorConfigDlg::updateSelectedItems() diff --git a/diagramCavas/source/propertyContentDlg.cpp b/diagramCavas/source/propertyContentDlg.cpp index 565dbf4..2437970 100644 --- a/diagramCavas/source/propertyContentDlg.cpp +++ b/diagramCavas/source/propertyContentDlg.cpp @@ -26,7 +26,7 @@ void PropertyContentDlg::createGroupView(groupStateInfo infos) // 动态生成字段 for(auto& info:infos.info) { - QLabel* label = new QLabel(info.name,this); + QLabel* label = new QLabel(info.tagName,this); QWidget* editor = createEditor(info); formLayout->addRow(label, editor); } @@ -155,12 +155,13 @@ QWidget* PropertyContentDlg::createEditor(propertyStateInfo pro) } if(pWidget) { - pWidget->setProperty("name",pro.name); + pWidget->setProperty("name",pro.tagName); propertyContentInfo info; + info.proTag = pro.tagName; info.proName = pro.name; info.proType = pro.type; info.proEditer = pWidget; - _mapPro.insert(pro.name,info); + _mapPro.insert(pro.tagName,info); } return pWidget; } @@ -174,6 +175,7 @@ QMap PropertyContentDlg::getPropertyValue(BasePropert propertyStateInfo info; info.type = pro.proType; info.name = pro.proName; + info.tagName = pro.proTag; if(pro.proEditer != nullptr) { if(pro.proType.contains("SMALLINT") || pro.proType.contains("INTEGER")) @@ -254,7 +256,7 @@ QMap PropertyContentDlg::getPropertyValue(BasePropert if(lineEdit) info.defaultValue = lineEdit->text(); } - map.insert(pro.proName,info); + map.insert(pro.proTag,info); } } @@ -278,7 +280,7 @@ void PropertyContentDlg::setPropertyValue(QVariant var) _curValue = map; for(auto &info:map) { - propertyContentInfo pro = _mapPro[info.name]; + propertyContentInfo pro = _mapPro[info.tagName]; if(info.type.contains("SMALLINT") || info.type.contains("INTEGER")) { QSpinBox* spin = qobject_cast(pro.proEditer); diff --git a/diagramCavas/source/ptExtraInfoDlg.cpp b/diagramCavas/source/ptExtraInfoDlg.cpp index d1a2949..dbf6392 100644 --- a/diagramCavas/source/ptExtraInfoDlg.cpp +++ b/diagramCavas/source/ptExtraInfoDlg.cpp @@ -28,9 +28,10 @@ void PtExtraInfoDlg::createGroupView(groupStateInfo infos) { for(auto& info:infos.info) { propertyContentInfo inf; + inf.proTag = info.tagName; inf.proName = info.name; inf.proType = info.type; - _mapPro.insert(info.name,inf); + _mapPro.insert(info.tagName,inf); } } @@ -43,38 +44,39 @@ QMap PtExtraInfoDlg::getPropertyValue(BaseProperty* p propertyStateInfo info; info.type = pro.proType; info.name = pro.proName; - if(info.name == "额定电压(V)" || info.name == "un_v") //此处应为类型名 + info.tagName = pro.proTag; + if(info.name == "额定电压(V)" || info.tagName == "un_v") { info.defaultValue = ui->le_ratedVol->text(); } - else if(info.name == "工频耐压(V/1min)" || info.name == "uac_v_1min") + else if(info.name == "工频耐压(V/1min)" || info.tagName == "uac_v_1min") { info.defaultValue = ui->le_pfwv_pt->text(); } - else if(info.name == "冲击耐压(V)" || info.name == "uimp_v") + else if(info.name == "冲击耐压(V)" || info.tagName == "uimp_v") { info.defaultValue = ui->le_iwv_pt->text(); } - else if(info.name == "额定电压因数" || info.name == "rvf") + else if(info.name == "额定电压因数" || info.tagName == "rvf") { info.defaultValue = ui->le_ratedVolFactor->text(); } - else if(info.name == "一次绕组接线接地方式" || info.name == "pwcc") + else if(info.name == "一次绕组接线接地方式" || info.tagName == "pwcc") { info.defaultValue = ui->le_pwwgm->text(); } - else if(info.name == "额定频率(Hz)" || info.name == "fn_hz") + else if(info.name == "额定频率(Hz)" || info.tagName == "fn_hz") { info.defaultValue = ui->le_rf_pt->text(); } - else if(info.name == "相数" || info.name == "phase_num") + else if(info.name == "相数" || info.tagName == "phase_num") { if(ui->rb_tpt_pt->isChecked()) info.defaultValue = 1; else info.defaultValue = 0; } - else if(info.name == "PT二次绕组" || info.name == "pt_sec_winding") + else if(info.name == "PT二次绕组" || info.tagName == "pt_sec_winding") { QJsonObject object; QJsonArray arr; @@ -93,7 +95,7 @@ QMap PtExtraInfoDlg::getPropertyValue(BaseProperty* p object["winding"] = arr; info.defaultValue = object; } - map.insert(pro.proName,info); + map.insert(pro.proTag,info); } pPro->setDataChanged(true); return map; @@ -104,38 +106,38 @@ void PtExtraInfoDlg::setPropertyValue(QVariant var) QMap map = var.value>(); for(auto &info:map) { - if(info.name == "额定电压(V)" || info.name == "un_v") //此处应为类型名 + if(info.name == "额定电压(V)" || info.tagName == "un_v") { ui->le_ratedVol->setText(QString::number(info.defaultValue.toDouble())); } - else if(info.name == "工频耐压(V/1min)" || info.name == "uac_v_1min") + else if(info.name == "工频耐压(V/1min)" || info.tagName == "uac_v_1min") { ui->le_pfwv_pt->setText(QString::number(info.defaultValue.toDouble())); } - else if(info.name == "冲击耐压(V)" || info.name == "uimp_v") + else if(info.name == "冲击耐压(V)" || info.tagName == "uimp_v") { ui->le_iwv_pt->setText(QString::number(info.defaultValue.toDouble())); } - else if(info.name == "额定电压因数" || info.name == "rvf") + else if(info.name == "额定电压因数" || info.tagName == "rvf") { ui->le_ratedVolFactor->setText(QString::number(info.defaultValue.toDouble())); } - else if(info.name == "一次绕组接线接地方式" || info.name == "pwcc") + else if(info.name == "一次绕组接线接地方式" || info.tagName == "pwcc") { ui->le_pwwgm->setText(info.defaultValue.toString()); } - else if(info.name == "额定频率(Hz)" || info.name == "fn_hz") + else if(info.name == "额定频率(Hz)" || info.tagName == "fn_hz") { ui->le_rf_pt->setText(QString::number(info.defaultValue.toDouble())); } - else if(info.name == "相数" || info.name == "phase_num") + else if(info.name == "相数" || info.tagName == "phase_num") { if(info.defaultValue.toInt() == 1) ui->rb_tpt_pt->setChecked(true); else ui->rb_spt_pt->setChecked(true); } - else if(info.name == "PT二次绕组" || info.name == "pt_sec_winding") + else if(info.name == "PT二次绕组" || info.tagName == "pt_sec_winding") { QString jsonString = info.defaultValue.toString(); QJsonDocument jsonDocument = QJsonDocument::fromJson(jsonString.toUtf8().data()); diff --git a/diagramCavas/source/structDataMeasurementDelegate.cpp b/diagramCavas/source/structDataMeasurementDelegate.cpp new file mode 100644 index 0000000..5918515 --- /dev/null +++ b/diagramCavas/source/structDataMeasurementDelegate.cpp @@ -0,0 +1,309 @@ +#include +#include +#include +#include +#include +#include +#include "structDataMeasurementDelegate.h" +#include "structDataMeasurementModel.h" +#include "uiCommunicationBus.h" + +StructDataMeasurementDelegate::StructDataMeasurementDelegate(QObject* parent) : QStyledItemDelegate(parent) {} + +QWidget* StructDataMeasurementDelegate::createEditor(QWidget* parent, + const QStyleOptionViewItem& option, + const QModelIndex& index) const { + Q_UNUSED(option); + + int column = index.column(); + + switch (column) { + case StructDataMeasurementModel::ColConnectPara: + return createConnectParaEditor(parent); + + case StructDataMeasurementModel::ColType: + return createMeasurementTypeEditor(parent); + case StructDataMeasurementModel::ColSize: + return createSizeEditor(parent); + case StructDataMeasurementModel::ColSource: + return createSourceEditor(parent); + case StructDataMeasurementModel::ColStation: + return createTextEditor(parent); + case StructDataMeasurementModel::ColEquipment: + return createTextEditor(parent); + case StructDataMeasurementModel::ColChannel: + return createTextEditor(parent); + case StructDataMeasurementModel::ColPacket: + return createNumberEditor(parent); + case StructDataMeasurementModel::ColOffset: + return createNumberEditor(parent); + case StructDataMeasurementModel::ColEnable: + return createEnableEditor(parent); + } + + return nullptr; +} + +void StructDataMeasurementDelegate::setEditorData(QWidget* editor, const QModelIndex& index) const { + int column = index.column(); + QVariant value = index.data(Qt::EditRole); + + switch (column) { + case StructDataMeasurementModel::ColConnectPara: + if (QLineEdit* lineEdit = qobject_cast(editor)) { + lineEdit->setText(value.toString()); + } + break; + case StructDataMeasurementModel::ColType: + if (QComboBox* comboBox = qobject_cast(editor)) { + int typeValue = value.toInt(); + comboBox->setCurrentIndex(qBound(0, typeValue, 2)); + } + break; + case StructDataMeasurementModel::ColSize: + if (QSpinBox* spinBox = qobject_cast(editor)) { + spinBox->setValue(value.toInt()); + } + break; + case StructDataMeasurementModel::ColSource: + if (QComboBox* comboBox = qobject_cast(editor)) { + int sourceValue = value.toInt(); + int index = (sourceValue == 1) ? 0 : 1; // 1: cl3611, 2: 104 + comboBox->setCurrentIndex(index); + } + break; + case StructDataMeasurementModel::ColStation: + if (QLineEdit* lineEdit = qobject_cast(editor)) { + lineEdit->setText(value.toString()); + } + break; + case StructDataMeasurementModel::ColEquipment: + if (QLineEdit* lineEdit = qobject_cast(editor)) { + lineEdit->setText(value.toString()); + } + break; + case StructDataMeasurementModel::ColChannel: + if (QLineEdit* lineEdit = qobject_cast(editor)) { + lineEdit->setText(value.toString()); + } + break; + case StructDataMeasurementModel::ColPacket: + if (QSpinBox* spinBox = qobject_cast(editor)) { + spinBox->setValue(value.toInt()); + } + break; + case StructDataMeasurementModel::ColOffset: + if (QSpinBox* spinBox = qobject_cast(editor)) { + spinBox->setValue(value.toInt()); + } + break; + + case StructDataMeasurementModel::ColEnable: + if (QComboBox* comboBox = qobject_cast(editor)) { + bool res = value.toBool(); + int index = (res) ? 0 : 1; // 0: 启用, 1: 禁用 + comboBox->setCurrentIndex(index); + } + break; + } +} + +void StructDataMeasurementDelegate::setModelData(QWidget* editor, QAbstractItemModel* model, + const QModelIndex& index) const { + int column = index.column(); + QVariant newValue; + + switch (column) { + case StructDataMeasurementModel::ColConnectPara: + if (QLineEdit* lineEdit = qobject_cast(editor)) { + newValue = lineEdit->text().trimmed(); + } + break; + case StructDataMeasurementModel::ColEquipment: + if (QLineEdit* lineEdit = qobject_cast(editor)) { + newValue = lineEdit->text().trimmed(); + } + break; + case StructDataMeasurementModel::ColChannel: + if (QLineEdit* lineEdit = qobject_cast(editor)) { + newValue = lineEdit->text().trimmed(); + } + break; + case StructDataMeasurementModel::ColStation: + if (QLineEdit* lineEdit = qobject_cast(editor)) { + newValue = lineEdit->text().trimmed(); + } + break; + case StructDataMeasurementModel::ColType: + if (QComboBox* comboBox = qobject_cast(editor)) { + newValue = comboBox->currentIndex(); // 0:遥测, 1:遥信, 2:遥控 + } + break; + + case StructDataMeasurementModel::ColSize: + if (QSpinBox* spinBox = qobject_cast(editor)) { + newValue = spinBox->value(); + } + break; + case StructDataMeasurementModel::ColPacket: + if (QSpinBox* spinBox = qobject_cast(editor)) { + newValue = spinBox->value(); + } + break; + case StructDataMeasurementModel::ColOffset: + if (QSpinBox* spinBox = qobject_cast(editor)) { + newValue = spinBox->value(); + } + break; + + case StructDataMeasurementModel::ColSource: + if (QComboBox* comboBox = qobject_cast(editor)) { + // 转换文本为数值:cl3611 -> 0, 104 -> 1 + QString text = comboBox->currentText(); + newValue = (text == "cl3611") ? 0 : 1; + } + break; + + case StructDataMeasurementModel::ColEnable: + if (QComboBox* comboBox = qobject_cast(editor)) { + // 转换文本为数值:启用 -> 1, 禁用-> 0 + QString text = comboBox->currentText(); + newValue = (text == "启用") ? true : false; + } + break; + } + + if (!newValue.isNull()) { + model->setData(index, newValue, Qt::EditRole); + } +} + +void StructDataMeasurementDelegate::updateEditorGeometry(QWidget* editor, + const QStyleOptionViewItem& option, + const QModelIndex& index) const +{ + Q_UNUSED(index); + editor->setGeometry(option.rect); +} + +QString StructDataMeasurementDelegate::displayText(const QVariant& value, const QLocale& locale) const { + Q_UNUSED(locale); + + // 特殊列显示格式化 + if (value.userType() == QMetaType::Bool) { + return value.toBool() ? "启用" : "禁用"; + } + + return QStyledItemDelegate::displayText(value, locale); +} + +// 提供工具提示 +QString StructDataMeasurementDelegate::displayText(const QVariant& value, const QLocale& locale, + const QModelIndex& index) const { + int column = index.column(); + + if (column == StructDataMeasurementModel::ColType) { + int type = value.toInt(); + switch (type) { + case 0: return "遥测"; + case 1: return "遥信"; + case 2: return "遥控"; + default: return QString::number(type); + } + } else if (column == StructDataMeasurementModel::ColSource) { + int source = value.toInt(); + switch (source) { + case 1: return "cl3611"; + case 2: return "104"; + default: return QString::number(source); + } + } else if (column == StructDataMeasurementModel::ColEnable) { + bool enabled = value.toBool(); + return enabled ? "启用" : "禁用"; + } + + return displayText(value, locale); +} + +void StructDataMeasurementDelegate::onConnectParamChanged(const QString& str) const +{ + QVariantMap map; + map.insert("input",str); + UiCommunicationBus::instance()->sendHttpRequest("/measurement/recommend",QVariant(),"GET",map); +} + +bool StructDataMeasurementDelegate::eventFilter(QObject *obj, QEvent *event) +{ + if (QLineEdit *editor = qobject_cast(obj)){ + if (event->type() == QEvent::KeyPress) { + QKeyEvent *keyEvent = static_cast(event); + + if (keyEvent->key() == Qt::Key_Space) { + qDebug() << "eventFilter:space"; + onConnectParamChanged(editor->text()); + _connectCompleter->complete(); + return true; + } + + if (keyEvent->text() == ".") { + qDebug() << "eventFilter:dot"; + // 返回false让事件继续传播 + } + } + } + + return QStyledItemDelegate::eventFilter(obj, event); +} + + +QWidget* StructDataMeasurementDelegate::createConnectParaEditor(QWidget* parent) const { + QLineEdit* lineEdit = new QLineEdit(parent); + lineEdit->setMaxLength(150); + lineEdit->installEventFilter(const_cast(this)); + lineEdit->setPlaceholderText("空格获取初始值"); + lineEdit->setCompleter(_connectCompleter); + + connect(lineEdit, &QLineEdit::textChanged, this, [=](const QString &text) { + if (text.endsWith(".")) { + onConnectParamChanged(text); + } + }); + + return lineEdit; +} + +QWidget* StructDataMeasurementDelegate::createTextEditor(QWidget* parent) const { + QLineEdit* lineEdit = new QLineEdit(parent); + lineEdit->setMaxLength(100); + return lineEdit; +} + +QWidget* StructDataMeasurementDelegate::createMeasurementTypeEditor(QWidget* parent) const { + QComboBox* comboBox = new QComboBox(parent); + comboBox->addItems({"遥测", "遥信", "遥控"}); + return comboBox; +} + +QWidget* StructDataMeasurementDelegate::createSizeEditor(QWidget* parent) const { + QSpinBox* spinBox = new QSpinBox(parent); + spinBox->setRange(1, 1000); + return spinBox; +} + +QWidget* StructDataMeasurementDelegate::createSourceEditor(QWidget* parent) const { + QComboBox* comboBox = new QComboBox(parent); + comboBox->addItems({"cl3611", "104"}); + return comboBox; +} + +QWidget* StructDataMeasurementDelegate::createNumberEditor(QWidget* parent) const { + QSpinBox* spinBox = new QSpinBox(parent); + spinBox->setRange(0, 9999); + return spinBox; +} + +QWidget* StructDataMeasurementDelegate::createEnableEditor(QWidget* parent) const { + QComboBox* comboBox = new QComboBox(parent); + comboBox->addItems({"启用", "禁用"}); + return comboBox; +} diff --git a/diagramCavas/source/structDataMeasurementModel.cpp b/diagramCavas/source/structDataMeasurementModel.cpp new file mode 100644 index 0000000..f45b38b --- /dev/null +++ b/diagramCavas/source/structDataMeasurementModel.cpp @@ -0,0 +1,269 @@ +#include "structDataMeasurementModel.h" +#include "structDataSource.h" +#include "global.h" + +StructDataMeasurementModel::StructDataMeasurementModel(StructDataSource* dataManager, QObject* parent) + : QAbstractTableModel(parent) + , m_dataManager(dataManager) +{ + connect(m_dataManager, &StructDataSource::propertyUpdated, + this, &StructDataMeasurementModel::onPropertyUpdated); +} + +void StructDataMeasurementModel::setPropertyCodes(const QStringList& codes) { + beginResetModel(); + m_propertyCodes = codes; + endResetModel(); + + emit propertiesLoaded(m_propertyCodes.size()); +} + +void StructDataMeasurementModel::setProperties(const QVector& properties) { + QStringList codes; + for (const auto& prop : properties) { + if (!prop.code.isEmpty()) { + codes.append(prop.code); + } + } + setPropertyCodes(codes); +} + +int StructDataMeasurementModel::rowCount(const QModelIndex& parent) const { + return parent.isValid() ? 0 : m_propertyCodes.size(); +} + +int StructDataMeasurementModel::columnCount(const QModelIndex& parent) const { + return parent.isValid() ? 0 : ColumnCount; +} + +QVariant StructDataMeasurementModel::data(const QModelIndex& index, int role) const { + if (!index.isValid() || index.row() >= m_propertyCodes.size()) { + return QVariant(); + } + + const ExtraProperty* prop = getProperty(index.row()); + if (!prop) { + return QVariant(); + } + + int col = index.column(); + + if (role == Qt::DisplayRole || role == Qt::EditRole) { + switch (col) { + case ColName: return prop->name; + case ColTag: return prop->tag; + case ColCode: return prop->code; + case ColSourceType: return "量测"; + case ColConnectPara: return prop->connect_para; + default: return getMeasurementData(*prop, col); + } + } + else if (role == Qt::UserRole) { + return QVariant::fromValue(*prop); + } + else if (role == Qt::UserRole + 1) { + return prop->code; + } + + return QVariant(); +} + +bool StructDataMeasurementModel::setData(const QModelIndex& index, const QVariant& value, int role) { + if (!index.isValid() || index.row() >= m_propertyCodes.size() || role != Qt::EditRole) { + return false; + } + + ExtraProperty* prop = getProperty(index.row()); + if (!prop) { + return false; + } + + int col = index.column(); + bool changed = false; + ExtraProperty updatedProp = *prop; + + if (col == ColConnectPara) { + if (updatedProp.connect_para != value.toString()) { + updatedProp.connect_para = value.toString(); + changed = true; + } + } else { + MeasurementInfo* data = m_dataManager->getMeasurementData(updatedProp); + if (data) { + changed = updateMeasurementData(data, col, value); + if (changed) { + emit m_dataManager->dataChanged(); + } + } + } + + if (changed) { + if (m_dataManager->updateProperty(updatedProp)) { + emit dataChanged(index, index, {role}); + emit propertyModified(index.row(), updatedProp); + return true; + } + } + + return false; +} + +Qt::ItemFlags StructDataMeasurementModel::flags(const QModelIndex& index) const { + Qt::ItemFlags flags = QAbstractTableModel::flags(index); + + int col = index.column(); + if (col == ColConnectPara || ColType || ColSize || ColSource || ColStation || ColEquipment || ColChannel || ColPacket || ColOffset || ColEnable) { + flags |= Qt::ItemIsEditable; + } + + return flags; +} + +QVariant StructDataMeasurementModel::headerData(int section, Qt::Orientation orientation, int role) const { + if (orientation == Qt::Horizontal && role == Qt::DisplayRole) { + QStringList headers = { + "名称", "标签", "编码", "类型", "连接参数", + "量测类型", "数据包size", "数据来源", "子站", "设备", "通道号","包号(104)","偏移量(104)","开启事件" + }; + return headers.value(section, ""); + } + return QAbstractTableModel::headerData(section, orientation, role); +} + +QVector StructDataMeasurementModel::getDisplayedProperties() const { + QVector result; + for (const QString& code : m_propertyCodes) { + ExtraProperty* prop = m_dataManager->getPropertyByCode(code); + if (prop) { + result.append(*prop); + } + } + return result; +} + +QStringList StructDataMeasurementModel::getDisplayedCodes() const { + return m_propertyCodes; +} + +int StructDataMeasurementModel::findRowByCode(const QString& code) const { + return m_propertyCodes.indexOf(code); +} + +void StructDataMeasurementModel::refreshRow(const QString& code) { + int row = findRowByCode(code); + if (row >= 0) { + QModelIndex start = index(row, 0); + QModelIndex end = index(row, columnCount() - 1); + emit dataChanged(start, end); + } +} + +void StructDataMeasurementModel::onPropertyUpdated(const ExtraProperty& updatedProp, bool isNew) { + Q_UNUSED(isNew); + int row = findRowByCode(updatedProp.code); + if (row >= 0) { + refreshRow(updatedProp.code); + } +} + +ExtraProperty* StructDataMeasurementModel::getProperty(int displayRow) const { + if (displayRow < 0 || displayRow >= m_propertyCodes.size()) { + return nullptr; + } + return m_dataManager->getPropertyByCode(m_propertyCodes[displayRow]); +} + +QVariant StructDataMeasurementModel::getMeasurementData(const ExtraProperty& prop, int col) const { + MeasurementInfo* data = m_dataManager->getMeasurementData(prop); + if (!data) return QVariant(); + + switch (col) { + case ColType: return getTypeText(data->type); + case ColSize: return data->size; + case ColSource: return getSourceText(data->nSource); + case ColStation: return data->sStation; + case ColEquipment: return data->sDevice; + case ColChannel: return data->sChannel; + case ColPacket: return data->nPacket; + case ColOffset: return data->nOffset; + case ColEnable: return data->bEnable ? "启用" : "禁用"; + } + return QVariant(); +} + +bool StructDataMeasurementModel::updateMeasurementData(MeasurementInfo* data, int col, const QVariant& value) { + switch (col) { + case ColType: + if (data->type != value.toInt()) { + data->type = value.toInt(); + return true; + } + break; + case ColSize: + if (data->size != value.toInt()) { + data->size = value.toInt(); + return true; + } + break; + case ColSource: + if (getSourceText(data->nSource) != value.toString()) { + data->nSource = getSourceInt(value.toString()); + return true; + } + break; + case ColStation: + if (data->sStation != value.toString()) { + data->sStation = value.toString(); + return true; + } + break; + case ColEquipment: + if (data->sDevice != value.toString()) { + data->sDevice = value.toString(); + return true; + } + break; + case ColChannel: + if (data->sChannel != value.toString()) { + data->sChannel = value.toString(); + return true; + } + break; + case ColEnable: + if (data->bEnable != value.toBool()) { + data->bEnable = value.toBool(); + return true; + } + break; + } + return false; +} + +QString StructDataMeasurementModel::getTypeText(int type) const { + switch (type) { + case 0: return "遥测"; + case 1: return "遥信"; + case 2: return "遥控"; + default: return QString::number(type); + } +} + +QString StructDataMeasurementModel::getSourceText(int source) const { + switch (source) { + case 1: return "cl3611"; + case 2: return "104"; + default: return QString::number(source); + } +} + +int StructDataMeasurementModel::getSourceInt(QString sType) const { + if(sType == "cl3611"){ + return 0; + } + else if(sType == "104"){ + return 1; + } + else { + return 2; + } +} diff --git a/diagramCavas/source/structDataPreviewDlg.cpp b/diagramCavas/source/structDataPreviewDlg.cpp index 6d9719d..4040d25 100644 --- a/diagramCavas/source/structDataPreviewDlg.cpp +++ b/diagramCavas/source/structDataPreviewDlg.cpp @@ -2,16 +2,37 @@ #include "ui_structDataPreviewDlg.h" #include #include +#include +#include +#include +#include #include "titleBar.h" #include "instance/extraPropertyManager.h" +#include "structDataSource.h" +#include "structDataMeasurementModel.h" +#include "structDataPropertyModel.h" +#include "structDataPropertyDelegate.h" +#include "structDataMeasurementDelegate.h" +#include "dataBase.h" +#include "global.h" StructDataPreviewDlg::StructDataPreviewDlg(QWidget *parent) : QDialog(parent) , ui(new Ui::structDataPreviewDlg) ,_pExtraProManager(nullptr) + ,_treeModel(nullptr) + ,m_currentCategoryItem(nullptr) + ,m_measurementTableModel(nullptr) + ,m_propertyTableModel(nullptr) + ,m_propertyDelegate(nullptr) + ,m_measurementDelegate(nullptr) + ,m_statusBar(nullptr) { ui->setupUi(this); this->setWindowFlags(Qt::FramelessWindowHint | windowFlags()); + m_statusBar = new QStatusBar(this); + ui->mainLayout->addWidget(m_statusBar); + m_statusBar->setMaximumHeight(21); initial(); } @@ -20,6 +41,14 @@ StructDataPreviewDlg::~StructDataPreviewDlg() delete ui; } +void StructDataPreviewDlg::loadData() +{ + if(_pExtraProManager) + m_dataSource->loadExtrapro(_pExtraProManager->geAlltProperty()); + m_dataSource->loadMeasurementData(DataBase::GetInstance()->getAllMeasurements()); + m_dataSource->loadPropertyData(DataManager::instance().modelData()); +} + void StructDataPreviewDlg::initial() { // 创建标题栏 @@ -98,6 +127,53 @@ void StructDataPreviewDlg::initial() connect(m_titleBar, &TitleBar::maximizeClicked, this, &StructDataPreviewDlg::toggleMaximize); connect(m_titleBar, &TitleBar::closeClicked, this, &StructDataPreviewDlg::onExitClicked); + + _treeModel = new QStandardItemModel(this); + _treeModel->setHorizontalHeaderLabels(QStringList() << "属性层级结构"); + ui->tree_level->setModel(_treeModel); + + connect(ui->btn_gird,&QPushButton::clicked,this,[=](){ + onLevelButtonClicked(0); + }); + connect(ui->btn_zone,&QPushButton::clicked,this,[=](){ + onLevelButtonClicked(1); + }); + connect(ui->btn_station,&QPushButton::clicked,this,[=](){ + onLevelButtonClicked(2); + }); + connect(ui->btn_level,&QPushButton::clicked,this,[=](){ + onLevelButtonClicked(3); + }); + connect(ui->btn_bay,&QPushButton::clicked,this,[=](){ + onLevelButtonClicked(4); + }); + connect(ui->btn_device,&QPushButton::clicked,this,[=](){ + onLevelButtonClicked(5); + }); + connect(ui->btn_group,&QPushButton::clicked,this,[=](){ + onLevelButtonClicked(6); + }); + m_dataSource = new StructDataSource(this); + + connect(ui->tree_level->selectionModel(), &QItemSelectionModel::currentChanged, + this, &StructDataPreviewDlg::onTreeSelectionChanged); + + // 连接数据更新信号 + //connect(m_dataSource, &StructDataSource::propertyUpdated,this, &StructDataPreviewDlg::onPropertyUpdated); + + m_propertyDelegate = new StructDataPropertyDelegate(this); + m_measurementDelegate = new StructDataMeasurementDelegate(this); + + _recommandCompleter = new QCompleter(this); + _recommandCompleter->setCaseSensitivity(Qt::CaseInsensitive); + _recommandCompleter->setFilterMode(Qt::MatchContains); + _recommandCompleter->setCompletionMode(QCompleter::PopupCompletion); + _strLstModel = new QStringListModel(this); + + _recommandCompleter->setModel(_strLstModel); + + m_propertyDelegate->setConnectParaCompleter(_recommandCompleter); + m_measurementDelegate->setConnectParaCompleter(_recommandCompleter); } @@ -112,6 +188,467 @@ void StructDataPreviewDlg::clearItems() } } +QString StructDataPreviewDlg::getLevelType(int index) { + switch (index) { + case 0: return "电网"; + case 1: return "区域"; + case 2: return "站点"; + case 3: return "电压等级"; + case 4: return "间隔"; + case 5: return "设备"; + case 6: return "分组"; + default: return "未知层级"; + } +} + +void StructDataPreviewDlg::expandToLevel(QTreeView* treeView, int targetLevel) +{ + if (!treeView || !treeView->model()) { + return; + } + + QAbstractItemModel* model = treeView->model(); + + // 先收缩所有 + treeView->collapseAll(); + + // 递归展开到指定层级 + expandToLevelRecursive(treeView, model, QModelIndex(), 0, targetLevel); +} + +void StructDataPreviewDlg::expandToLevelRecursive(QTreeView* treeView, + QAbstractItemModel* model, + const QModelIndex& parent, + int currentDepth, + int targetLevel) +{ + if (!model || !treeView) { + return; + } + + int rowCount = model->rowCount(parent); + + for (int row = 0; row < rowCount; ++row) { + QModelIndex index = model->index(row, 0, parent); + + // 获取节点的实际层级 + int nodeLevel = getNodeLevel(model, index); + + if (nodeLevel <= targetLevel) { + // 展开当前节点 + treeView->expand(index); + } else { + // 收缩当前节点 + treeView->collapse(index); + } + + // 递归处理子节点 + if (model->hasChildren(index)) { + expandToLevelRecursive(treeView, model, index, currentDepth + 1, targetLevel); + } + } +} + +int StructDataPreviewDlg::getNodeLevel(QAbstractItemModel* model, const QModelIndex& index) +{ + if (!model || !index.isValid()) { + return -1; + } + + // 从UserRole+1中获取层级信息 + QVariant data = model->data(index, Qt::UserRole + 1); + if (data.isValid()) { + QVariantMap nodeData = data.toMap(); + + // 先检查是否是属性节点 + if (nodeData.contains("property")) { + return 7; + } + + // 检查层级索引 + if (nodeData.contains("levelIndex")) { + int levelIndex = nodeData["levelIndex"].toInt(); + return qMin(levelIndex, 7); + } + } + + // 如果没有存储层级信息,通过深度判断 + return getDepthFromRoot(model, index); +} + +QStandardItem* StructDataPreviewDlg::processGroupLevel(QStandardItem* componentItem, + const ExtraProperty& property) { + QString groupDisplayText = (property.group_name.isEmpty() ? + property.group_tag : property.group_name); + + if (groupDisplayText.isEmpty()) { + groupDisplayText = "未命名分组"; + } + + // 查找group节点 + for (int row = 0; row < componentItem->rowCount(); ++row) { + QStandardItem* child = componentItem->child(row, 0); + if (child) { + QVariantMap childData = child->data(Qt::UserRole + 1).toMap(); + QString levelType = childData.value("levelType").toString(); + + if (levelType == "group") { + // 检查是否是同一个group + QString existingGroupTag = childData.value("groupTag", "").toString(); + QString existingModelName = childData.value("modelName", "").toString(); + QString propertyModelName = property.sourceConfig.value("modelName").toString(); + + if (existingGroupTag == property.group_tag) { + if (property.sourceType == "property") { + // 对于property类型,还需要检查modelName + if (existingModelName == propertyModelName) { + return child; + } + } else { + // 对于measurement类型,只需要groupTag匹配 + return child; + } + } + } + } + } + + // 创建新的group节点 + QStandardItem* groupItem = new QStandardItem(groupDisplayText); + QVariantMap groupData; + groupData["levelIndex"] = 6; // 第7层 + groupData["levelType"] = "group"; + groupData["groupName"] = property.group_name; + groupData["groupTag"] = property.group_tag; + groupData["sourceType"] = property.sourceType; + + if (property.sourceType == "property") { + groupData["modelName"] = property.sourceConfig.value("modelName"); + } + + groupData["properties"] = QVariant::fromValue(QVector()); + groupItem->setData(groupData, Qt::UserRole + 1); + + // 设置工具提示 + QString tooltip = QString("分组: %1\n类型: %2") + .arg(groupDisplayText) + .arg(property.sourceType == "property" ? "属性" : "量测"); + groupItem->setToolTip(tooltip); + + componentItem->appendRow(groupItem); + return groupItem; +} + +// 处理category层级 +void StructDataPreviewDlg::processCategoryLevel(QStandardItem* groupItem, + const ExtraProperty& property) { + QString categoryName = property.type_name; + QString paraType = property.type_tag; + + if (categoryName.isEmpty() || paraType.isEmpty()) { + qWarning() << "Invalid category or paraType for property:" << property.code; + return; + } + + // 查找category节点 + for (int row = 0; row < groupItem->rowCount(); ++row) { + QStandardItem* child = groupItem->child(row, 0); + if (child) { + QVariantMap childData = child->data(Qt::UserRole + 1).toMap(); + QString levelType = childData.value("levelType").toString(); + QString childParaType = childData.value("paraType", "").toString(); + + if (levelType == "category" && childParaType == paraType) { + // 找到对应的category节点,更新属性列表 + updateCategoryProperties(child, property); + return; + } + } + } + + // 创建新的category节点 + QStandardItem* categoryItem = new QStandardItem(categoryName); + QVariantMap categoryData; + categoryData["levelType"] = "category"; + categoryData["paraType"] = paraType; + categoryData["sourceType"] = property.sourceType; + categoryData["groupTag"] = property.group_tag; + categoryData["groupName"] = property.group_name; + + if (property.sourceType == "property") { + categoryData["modelName"] = property.sourceConfig.value("modelName"); + } + + // 初始化属性列表 + QVector properties; + properties.append(property); + categoryData["properties"] = QVariant::fromValue(properties); + categoryData["propertyCount"] = 1; + + categoryItem->setData(categoryData, Qt::UserRole + 1); + + // 设置显示文本(包含数量) + categoryItem->setText(QString("%1 (1)").arg(categoryName)); + + // 设置工具提示 + QString tooltip = QString("分类: %1\n参量类型: %2\n属性数量: 1") + .arg(categoryName) + .arg(categoryName); + categoryItem->setToolTip(tooltip); + + groupItem->appendRow(categoryItem); +} + +// 更新category节点的属性列表 +void StructDataPreviewDlg::updateCategoryProperties(QStandardItem* categoryItem, + const ExtraProperty& property) { + QVariantMap categoryData = categoryItem->data(Qt::UserRole + 1).toMap(); + QVector properties = categoryData["properties"].value>(); + + // 检查属性是否已存在 + bool exists = false; + for (const auto& prop : properties) { + if (prop.code == property.code) { + exists = true; + break; + } + } + + if (!exists) { + properties.append(property); + categoryData["properties"] = QVariant::fromValue(properties); + + int newCount = properties.size(); + categoryData["propertyCount"] = newCount; + + // 更新显示文本 + QString baseName = property.type_name; + categoryItem->setText(QString("%1 (%2)").arg(baseName).arg(newCount)); + + // 更新工具提示 + QString tooltip = QString("属性数量: %1") + .arg(newCount); + categoryItem->setToolTip(tooltip); + + categoryItem->setData(categoryData, Qt::UserRole + 1); + } +} + +void StructDataPreviewDlg::loadCategoryProperties(QStandardItem* categoryItem) { + m_currentCategoryItem = categoryItem; + + // 保存当前修改 + saveCurrentIfModified(); + + // 从category节点获取属性列表 + QVariantMap categoryData = categoryItem->data(Qt::UserRole + 1).toMap(); + QVector properties = categoryData["properties"].value>(); + + if (properties.isEmpty()) { + // 如果没有属性,从DataManager重新获取 + properties = getCategoryPropertiesFromDataManager(categoryData); + } + + if (properties.isEmpty()) { + clearTableView(); + QString categoryName = categoryItem->text(); + ui->tableTitle->setText(QString("分类: %1").arg(categoryName)); + return; + } + + // 重置修改状态 + m_currentModified = false; + //updateWindowTitle(); + + // 获取group和category信息 + QString categoryName = categoryItem->text(); + QString groupName = categoryItem->parent() ? categoryItem->parent()->text() : ""; + QString sourceType = categoryData.value("sourceType").toString(); + + // 根据sourceType显示表格 + if (sourceType == "property") { + setupPropertyTable(properties, categoryName, groupName); + } else if (sourceType == "measurement") { + setupMeasurementTable(properties, categoryName, groupName); + } + + ui->tableView->setVisible(true); +} + +QVector StructDataPreviewDlg::getCategoryPropertiesFromDataManager(const QVariantMap& categoryData) { + QString groupTag = categoryData.value("groupTag").toString(); + QString modelName = categoryData.value("modelName").toString(); + QString paraType = categoryData.value("paraType").toString(); + QString sourceType = categoryData.value("sourceType").toString(); + QString componentUuid = categoryData.value("component_uuid").toString(); + + QVector result; + + for (auto it = m_dataSource->allProperties.begin(); + it != m_dataSource->allProperties.end(); ++it) { + const ExtraProperty& prop = it.value(); + + bool match = (prop.group_tag == groupTag) && + (prop.sourceType == sourceType) && + (prop.type_tag == paraType) && + (prop.component_uuid.toString() == componentUuid); + + if (sourceType == "property") { + match = match && (prop.sourceConfig.value("modelName").toString() == modelName); + } + + if (match) { + result.append(prop); + } + } + + return result; +} + +void StructDataPreviewDlg::setupPropertyTable(const QVector& properties, + const QString& categoryName, + const QString& groupName) { + if (!m_propertyTableModel) { + m_propertyTableModel = new StructDataPropertyModel(m_dataSource, this); + connect(m_propertyTableModel, &StructDataPropertyModel::propertyModified, + this, &StructDataPreviewDlg::onPropertyModified); + } + + m_propertyTableModel->setProperties(properties); + ui->tableView->setModel(m_propertyTableModel); + + // 使用Property代理 + ui->tableView->setItemDelegate(m_propertyDelegate); + + setupPropertyColumns(); + updateTableTitle("属性", categoryName, groupName, properties.size()); +} + +void StructDataPreviewDlg::setupMeasurementTable(const QVector& properties, + const QString& categoryName, + const QString& groupName) { + if (!m_measurementTableModel) { + m_measurementTableModel = new StructDataMeasurementModel(m_dataSource, this); + connect(m_measurementTableModel, &StructDataMeasurementModel::propertyModified, + this, &StructDataPreviewDlg::onPropertyModified); + } + + m_measurementTableModel->setProperties(properties); + ui->tableView->setModel(m_measurementTableModel); + + if (!m_measurementDelegate) { + m_measurementDelegate = new StructDataMeasurementDelegate(this); + } + ui->tableView->setItemDelegate(m_measurementDelegate); + + setupMeasurementColumns(); + + // 去除数量显示 + QString cleanCategoryName = categoryName; + int bracketPos = cleanCategoryName.indexOf(" ("); + if (bracketPos != -1) { + cleanCategoryName = cleanCategoryName.left(bracketPos); + } + + ui->tableTitle->setText(QString("分组: %1 - 分类: %2").arg(groupName).arg(cleanCategoryName)); +} + +void StructDataPreviewDlg::updateCategoryAfterPropertyModified(QStandardItem* categoryItem, const ExtraProperty& updatedProp) { + QVariantMap categoryData = categoryItem->data(Qt::UserRole + 1).toMap(); + QVector properties = categoryData["properties"].value>(); + + // 更新属性列表 + bool found = false; + for (auto& prop : properties) { + if (prop.code == updatedProp.code) { + prop = updatedProp; + found = true; + break; + } + } + + if (found) { + categoryData["properties"] = QVariant::fromValue(properties); + categoryItem->setData(categoryData, Qt::UserRole + 1); + } +} + +void StructDataPreviewDlg::saveCurrentIfModified() +{ + if (m_currentModified && m_currentCategoryItem) { + int result = QMessageBox::question(this, "切换分类", + "当前分类有未保存的修改,是否保存?", + QMessageBox::Save | QMessageBox::Discard | QMessageBox::Cancel); + + if (result == QMessageBox::Save) { + saveAll(); + } else if (result == QMessageBox::Cancel) { + ui->tree_level->selectionModel()->select(ui->tree_level->selectionModel()->currentIndex(), + QItemSelectionModel::Select); + } + } +} + +void StructDataPreviewDlg::saveAll() { + m_dataSource->saveAll(); + m_currentModified = false; + //updateWindowTitle(); + m_statusBar->showMessage("保存成功", 2000); +} + +void StructDataPreviewDlg::clearTableView() { + ui->tableTitle->setText("未选择分类"); + ui->tableView->setModel(nullptr); + ui->tableView->setVisible(false); + m_currentCategoryItem = nullptr; +} + +void StructDataPreviewDlg::setupPropertyColumns() { + ui->tableView->setColumnWidth(StructDataPropertyModel::ColName, 120); + ui->tableView->setColumnWidth(StructDataPropertyModel::ColTag, 100); + ui->tableView->setColumnWidth(StructDataPropertyModel::ColCode, 200); + ui->tableView->setColumnWidth(StructDataPropertyModel::ColSourceType, 60); + ui->tableView->setColumnWidth(StructDataPropertyModel::ColConnectPara, 400); + ui->tableView->setColumnWidth(StructDataPropertyModel::ColModelName, 100); + ui->tableView->setColumnWidth(StructDataPropertyModel::ColDataType, 80); + ui->tableView->setColumnWidth(StructDataPropertyModel::ColDefaultValue, 100); + ui->tableView->setColumnWidth(StructDataPropertyModel::ColLengthPrecision, 80); +} + +void StructDataPreviewDlg::setupMeasurementColumns() { + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColName, 120); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColTag, 100); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColCode, 200); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColSourceType, 60); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColConnectPara, 400); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColEquipment, 100); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColChannel, 60); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColType, 60); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColSize, 60); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColSource, 60); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColStation, 80); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColPacket, 50); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColOffset, 60); + ui->tableView->setColumnWidth(StructDataMeasurementModel::ColEnable, 50); +} + +void StructDataPreviewDlg::updateTableTitle(const QString& dataType, const QString& categoryName, + const QString& groupName, int count) { + ui->tableTitle->setText(QString("%1分组: %2 - %3").arg(dataType).arg(groupName).arg(categoryName)); +} + +int StructDataPreviewDlg::getDepthFromRoot(QAbstractItemModel* model, const QModelIndex& index) { + int depth = 0; + QModelIndex parent = index.parent(); + + while (parent.isValid()) { + depth++; + parent = parent.parent(); + } + + return depth; +} + void StructDataPreviewDlg::onExitClicked() { hide(); @@ -122,34 +659,47 @@ void StructDataPreviewDlg::onSaveClicked() } -void StructDataPreviewDlg::onGridClicked() +void StructDataPreviewDlg::onLevelButtonClicked(int nLevel) { - + // 展开到指定层级 + expandToLevel(ui->tree_level,nLevel); } -void StructDataPreviewDlg::onZoneClicked() -{ +void StructDataPreviewDlg::onTreeSelectionChanged(const QModelIndex& current, const QModelIndex& previous) { + Q_UNUSED(previous); + if (!current.isValid()) { + clearTableView(); + return; + } + + QStandardItem* item = _treeModel->itemFromIndex(current); + if (!item) { + clearTableView(); + return; + } + + QVariantMap itemData = item->data(Qt::UserRole + 1).toMap(); + QString levelType = itemData.value("levelType", "").toString(); + + if (levelType == "category") { + // 点击分类节点,从category节点获取属性 + loadCategoryProperties(item); + }else{ + clearTableView(); + } } -void StructDataPreviewDlg::onStationClicked() -{ +void StructDataPreviewDlg::onPropertyModified(int row, const ExtraProperty& prop) { + m_currentModified = true; + //updateWindowTitle(); -} - -void StructDataPreviewDlg::onBayClicked() -{ - -} - -void StructDataPreviewDlg::onDeviceClicked() -{ - -} - -void StructDataPreviewDlg::onPropertyClicked() -{ + // 更新树中category的属性数量 + if (m_currentCategoryItem) { + updateCategoryAfterPropertyModified(m_currentCategoryItem, prop); + } + m_statusBar->showMessage(QString("属性'%1'已修改").arg(prop.name), 2000); } void StructDataPreviewDlg::showEvent(QShowEvent *event) @@ -178,10 +728,169 @@ void StructDataPreviewDlg::showDlg() { if(_pExtraProManager) { - QMap mapPro = _pExtraProManager->geAlltProperty(); + show(); + clearItems(); + auto& mapExtra = m_dataSource->allProperties; + QStandardItem* root = _treeModel->invisibleRootItem(); + for(auto& pro:mapExtra){ + QStandardItem* propertyItem = new QStandardItem(); + addItemToView(pro,"name",root,propertyItem); + } + + ui->tree_level->expandAll(); } } +QVector StructDataPreviewDlg::getGroupProperties(QStandardItem* groupItem) { + if (!groupItem) return QVector(); + + QVariantMap data = groupItem->data(Qt::UserRole + 1).toMap(); + if (data.contains("properties")) { + return data["properties"].value>(); + } + + return QVector(); +} + +// 获取group节点的sourceType +QString getGroupSourceType(QStandardItem* groupItem) { + if (!groupItem) return ""; + + QVariantMap data = groupItem->data(Qt::UserRole + 1).toMap(); + return data.value("sourceType", "").toString(); +} + +void StructDataPreviewDlg::addItemToView(const ExtraProperty& property, + const QString& displayMode, // "name" 或 "tag" + QStandardItem* root, + QStandardItem* pItem) +{ + // 设置叶子节点的显示文本(使用name或tag) + if (displayMode == "name") { + pItem->setText(property.name.isEmpty() ? "未命名属性" : property.name); + } else { + pItem->setText(property.tag.isEmpty() ? "unknown_property" : property.tag); + } + + // 在叶子节点存储完整的属性信息 + QVariantMap propertyData; + propertyData["property"] = QVariant::fromValue(property); + propertyData["displayMode"] = displayMode; + propertyData["code"] = property.code; + pItem->setData(propertyData, Qt::UserRole + 1); + + QVector levels = { + {(displayMode == "name") ? property.grid_name : property.grid_tag, + property.grid_name, property.grid_tag, true, + (displayMode == "name") ? "未命名电网" : "unknown_grid"}, + + {(displayMode == "name") ? property.zone_name : property.zone_tag, + property.zone_name, property.zone_tag, true, + (displayMode == "name") ? "未命名区域" : "unknown_zone"}, + + {(displayMode == "name") ? property.station_name : property.station_tag, + property.station_name, property.station_tag, true, + (displayMode == "name") ? "未命名站点" : "unknown_station"}, + + {property.currentLevel, + property.currentLevel, property.currentLevel, false, + (displayMode == "name") ? "通用层级" : "common_level"}, + + {(displayMode == "name") ? property.bay_name : property.bay_tag, + property.bay_name, property.bay_tag, false, + (displayMode == "name") ? "间隔" : "bay"}, + + {property.component_name.isEmpty() ? + (displayMode == "name") ? "未命名设备" : property.component_uuid.toString() : + (displayMode == "name") ? property.component_name : property.component_uuid.toString(), + property.component_name, property.component_uuid.toString(), true, + (displayMode == "name") ? "未命名设备" : "unknown_component"} + }; + + QStandardItem* currentParent = root; + + for (size_t i = 0; i < levels.size(); ++i) { + const auto& level = levels[i]; + bool isRequired = level.isRequired; + bool isEmpty = (displayMode == "name") ? + (level.nameValue.isEmpty() && level.displayText.isEmpty()) : + (level.tagValue.isEmpty() && level.displayText.isEmpty()); + + if (!isRequired && isEmpty) { + continue; + } + + // 确定显示文本 + QString displayText = level.displayText; + bool isMissing = false; + + if (displayText.isEmpty()) { + if (isRequired) { + displayText = level.placeholder; + isMissing = true; + } else { + // 可选层级为空,跳过 + continue; + } + } + + // 查找当前层级是否已存在 + QStandardItem* foundChild = nullptr; + + for (int row = 0; row < currentParent->rowCount(); ++row) { + QStandardItem* child = currentParent->child(row, 0); + if (child && child->text() == displayText) { + // 检查是否为同一层级 + QVariantMap childData = child->data(Qt::UserRole + 1).toMap(); + int childLevelIndex = childData["levelIndex"].toInt(); + + if (childLevelIndex == static_cast(i)) { + foundChild = child; + break; + } + } + } + + if (foundChild) { + currentParent = foundChild; + } else { + QStandardItem* newNode = new QStandardItem(displayText); + QVariantMap levelData; + levelData["levelIndex"] = static_cast(i); + levelData["levelType"] = getLevelType(i); + + newNode->setData(levelData, Qt::UserRole + 1); + currentParent->appendRow(newNode); + currentParent = newNode; + } + } + + // 现在currentParent是component节点 + // 处理group层级(第7层) + QStandardItem* groupItem = processGroupLevel(currentParent, property); + + // 处理category层级(在group下) + processCategoryLevel(groupItem, property); + +} + +void StructDataPreviewDlg::updateRecommandLst(QStringList lst) +{ + for(auto& newName:lst){ + if(!newName.isEmpty()){ + if(!_curRecommandLst.contains(newName)){ + _curRecommandLst.append(newName); + } + } + } + _strLstModel->setStringList(_curRecommandLst); + if (_recommandCompleter->popup()->isVisible()) { + _recommandCompleter->popup()->hide(); + } + _recommandCompleter->complete(); // 重新显示补全列表 +} + + void StructDataPreviewDlg::resizeEvent(QResizeEvent *event) { QDialog::resizeEvent(event); diff --git a/diagramCavas/source/structDataPropertyDelegate.cpp b/diagramCavas/source/structDataPropertyDelegate.cpp new file mode 100644 index 0000000..71dbd08 --- /dev/null +++ b/diagramCavas/source/structDataPropertyDelegate.cpp @@ -0,0 +1,210 @@ +#include +#include +#include +#include +#include +#include +#include +#include "structDataPropertyDelegate.h" +#include "structDataPropertyModel.h" +#include "uiCommunicationBus.h" + +StructDataPropertyDelegate::StructDataPropertyDelegate(QObject* parent) : QStyledItemDelegate(parent) {} + +QWidget* StructDataPropertyDelegate::createEditor(QWidget* parent, + const QStyleOptionViewItem& option, + const QModelIndex& index) const { + Q_UNUSED(option); + + int column = index.column(); + + switch (column) { + case StructDataPropertyModel::ColConnectPara: + return createConnectParaEditor(parent); + + case StructDataPropertyModel::ColDefaultValue: + return createDefaultValueEditor(parent, index); + + case StructDataPropertyModel::ColLengthPrecision: + return createLengthPrecisionEditor(parent); + } + + return nullptr; +} + +void StructDataPropertyDelegate::setEditorData(QWidget* editor, const QModelIndex& index) const { + int column = index.column(); + QVariant value = index.data(Qt::EditRole); + + switch (column) { + case StructDataPropertyModel::ColConnectPara: + if (QLineEdit* lineEdit = qobject_cast(editor)) { + lineEdit->setText(value.toString()); + } + break; + + case StructDataPropertyModel::ColDefaultValue: + setDefaultValueEditorData(editor, value, index); + break; + + case StructDataPropertyModel::ColLengthPrecision: + if (QSpinBox* spinBox = qobject_cast(editor)) { + spinBox->setValue(value.toInt()); + } + break; + } +} + +void StructDataPropertyDelegate::setModelData(QWidget* editor, QAbstractItemModel* model, + const QModelIndex& index) const { + int column = index.column(); + QVariant newValue; + + switch (column) { + case StructDataPropertyModel::ColConnectPara: + if (QLineEdit* lineEdit = qobject_cast(editor)) { + newValue = lineEdit->text().trimmed(); + } + break; + + case StructDataPropertyModel::ColDefaultValue: + newValue = getDefaultValueEditorData(editor, index); + break; + + case StructDataPropertyModel::ColLengthPrecision: + if (QSpinBox* spinBox = qobject_cast(editor)) { + newValue = spinBox->value(); + } + break; + } + + if (!newValue.isNull()) { + model->setData(index, newValue, Qt::EditRole); + } +} + +void StructDataPropertyDelegate::updateEditorGeometry(QWidget* editor, + const QStyleOptionViewItem& option, + const QModelIndex& index) const { + Q_UNUSED(index); + editor->setGeometry(option.rect); +} + +QString StructDataPropertyDelegate::displayText(const QVariant& value, const QLocale& locale) const { + Q_UNUSED(locale); + + // 格式化显示文本 + if (value.userType() == QMetaType::Bool) { + return value.toBool() ? "是" : "否"; + } + + return QStyledItemDelegate::displayText(value, locale); +} + +QWidget* StructDataPropertyDelegate::createConnectParaEditor(QWidget* parent) const { + QLineEdit* lineEdit = new QLineEdit(parent); + lineEdit->setMaxLength(150); + lineEdit->installEventFilter(const_cast(this)); + lineEdit->setPlaceholderText("空格获取初始值"); + lineEdit->setCompleter(_connectCompleter); + + connect(lineEdit, &QLineEdit::textChanged, this, [=](const QString &text) { + if (text.endsWith(".")) { + onConnectParamChanged(text); + } + }); + + return lineEdit; +} + +QWidget* StructDataPropertyDelegate::createDefaultValueEditor(QWidget* parent, const QModelIndex& index) const { + // 根据数据类型创建不同的编辑器 + QString dataType = index.sibling(index.row(), StructDataPropertyModel::ColDataType).data().toString().toLower(); + + if (dataType == "int" || dataType == "integer") { + QSpinBox* spinBox = new QSpinBox(parent); + spinBox->setRange(-999999, 999999); + return spinBox; + } else if (dataType == "float" || dataType == "double") { + QDoubleSpinBox* spinBox = new QDoubleSpinBox(parent); + spinBox->setRange(-999999.0, 999999.0); + spinBox->setDecimals(3); + return spinBox; + } else if (dataType == "bool" || dataType == "boolean") { + QComboBox* comboBox = new QComboBox(parent); + comboBox->addItems({"false", "true"}); + return comboBox; + } else { + // 字符串或其他类型 + QLineEdit* lineEdit = new QLineEdit(parent); + return lineEdit; + } +} + +QWidget* StructDataPropertyDelegate::createLengthPrecisionEditor(QWidget* parent) const { + QSpinBox* spinBox = new QSpinBox(parent); + spinBox->setRange(0, 999); + spinBox->setSpecialValueText("无限制"); + return spinBox; +} + +void StructDataPropertyDelegate::setDefaultValueEditorData(QWidget* editor, const QVariant& value, const QModelIndex& index) const { + QString dataType = index.sibling(index.row(), StructDataPropertyModel::ColDataType).data().toString().toLower(); + + if (QSpinBox* spinBox = qobject_cast(editor)) { + spinBox->setValue(value.toInt()); + } else if (QDoubleSpinBox* doubleSpinBox = qobject_cast(editor)) { + doubleSpinBox->setValue(value.toDouble()); + } else if (QComboBox* comboBox = qobject_cast(editor)) { + bool boolValue = value.toBool(); + comboBox->setCurrentIndex(boolValue ? 1 : 0); + } else if (QLineEdit* lineEdit = qobject_cast(editor)) { + lineEdit->setText(value.toString()); + } +} + +QVariant StructDataPropertyDelegate::getDefaultValueEditorData(QWidget* editor, const QModelIndex& index) const { + QString dataType = index.sibling(index.row(), StructDataPropertyModel::ColDataType).data().toString().toLower(); + + if (QSpinBox* spinBox = qobject_cast(editor)) { + return spinBox->value(); + } else if (QDoubleSpinBox* doubleSpinBox = qobject_cast(editor)) { + return doubleSpinBox->value(); + } else if (QComboBox* comboBox = qobject_cast(editor)) { + return comboBox->currentIndex() == 1; + } else if (QLineEdit* lineEdit = qobject_cast(editor)) { + return lineEdit->text(); + } + + return QVariant(); +} + +void StructDataPropertyDelegate::onConnectParamChanged(const QString& str) const +{ + QVariantMap map; + map.insert("input",str); + UiCommunicationBus::instance()->sendHttpRequest("/measurement/recommend",QVariant(),"GET",map); +} + +bool StructDataPropertyDelegate::eventFilter(QObject *obj, QEvent *event) +{ + if (QLineEdit *editor = qobject_cast(obj)){ + if (event->type() == QEvent::KeyPress) { + QKeyEvent *keyEvent = static_cast(event); + + if (keyEvent->key() == Qt::Key_Space) { + qDebug() << "eventFilter:space"; + onConnectParamChanged(editor->text()); + _connectCompleter->complete(); + return true; + } + + if (keyEvent->text() == ".") { + qDebug() << "eventFilter:dot"; + // 返回false让事件继续传播 + } + } + } + + return QStyledItemDelegate::eventFilter(obj, event); +} diff --git a/diagramCavas/source/structDataPropertyModel.cpp b/diagramCavas/source/structDataPropertyModel.cpp new file mode 100644 index 0000000..d54877d --- /dev/null +++ b/diagramCavas/source/structDataPropertyModel.cpp @@ -0,0 +1,221 @@ +#include "structDataPropertyModel.h" +#include "structDataSource.h" +#include "global.h" + + +StructDataPropertyModel::StructDataPropertyModel(StructDataSource* dataManager, QObject* parent) + : QAbstractTableModel(parent) + , m_dataManager(dataManager) +{ + connect(m_dataManager, &StructDataSource::propertyUpdated, + this, &StructDataPropertyModel::onPropertyUpdated); +} + +// 设置要显示的code列表 +void StructDataPropertyModel::setPropertyCodes(const QStringList& codes) { + beginResetModel(); + m_propertyCodes = codes; + endResetModel(); + + //emit propertiesLoaded(m_propertyCodes.size()); +} + +// 设置要显示的属性 +void StructDataPropertyModel::setProperties(const QVector& properties) { + QStringList codes; + for (const auto& prop : properties) { + if (!prop.code.isEmpty()) { + codes.append(prop.code); + } + } + setPropertyCodes(codes); +} + +int StructDataPropertyModel::rowCount(const QModelIndex& parent) const { + return parent.isValid() ? 0 : m_propertyCodes.size(); +} + +int StructDataPropertyModel::columnCount(const QModelIndex& parent) const { + return parent.isValid() ? 0 : ColumnCount; +} + +QVariant StructDataPropertyModel::data(const QModelIndex& index, int role) const { + if (!index.isValid() || index.row() >= m_propertyCodes.size()) { + return QVariant(); + } + + const ExtraProperty* prop = getProperty(index.row()); + if (!prop) { + return QVariant(); + } + + int col = index.column(); + + if (role == Qt::DisplayRole || role == Qt::EditRole) { + switch (col) { + case ColName: return prop->name; + case ColTag: return prop->tag; + case ColCode: return prop->code; + case ColSourceType: return "属性"; + case ColConnectPara: return prop->connect_para; + case ColModelName: return prop->sourceConfig.value("modelName"); + default: return getPropertyData(*prop, col); + } + } + else if (role == Qt::UserRole) { + return QVariant::fromValue(*prop); + } + else if (role == Qt::UserRole + 1) { + return prop->code; // 返回code用于查找 + } + + return QVariant(); +} + +bool StructDataPropertyModel::setData(const QModelIndex& index, const QVariant& value, int role) { + if (!index.isValid() || index.row() >= m_propertyCodes.size() || role != Qt::EditRole) { + return false; + } + + ExtraProperty* prop = getProperty(index.row()); + if (!prop) { + return false; + } + + int col = index.column(); + bool changed = false; + ExtraProperty updatedProp = *prop; // 创建副本 + + if (col == ColConnectPara) { + // 连接参数自由文本输入 + QString newValue = value.toString().trimmed(); + if (updatedProp.connect_para != newValue) { + updatedProp.connect_para = newValue; + changed = true; + } + } else { + // 修改属性数据 + propertyStateInfo* data = m_dataManager->getPropertyData(updatedProp); + if (data) { + changed = updatePropertyData(data, col, value); + if (changed) { + emit m_dataManager->dataChanged(); + } + } + } + + if (changed) { + // 更新到DataManager + if (m_dataManager->updateProperty(updatedProp)) { + emit dataChanged(index, index, {role}); + emit propertyModified(index.row(), updatedProp); + return true; + } + } + + return false; +} + +Qt::ItemFlags StructDataPropertyModel::flags(const QModelIndex& index) const { + Qt::ItemFlags flags = QAbstractTableModel::flags(index); + + int col = index.column(); + if (col == ColConnectPara || + col == ColLengthPrecision || + col == ColDefaultValue) { + flags |= Qt::ItemIsEditable; + } + + return flags; +} + +QVariant StructDataPropertyModel::headerData(int section, Qt::Orientation orientation, int role) const { + if (orientation == Qt::Horizontal && role == Qt::DisplayRole) { + QStringList headers = { + "名称", "标签", "编码", "类型", "连接参数", + "模型名", "数据类型", "默认值", "长度精度" + }; + return headers.value(section, ""); + } + return QAbstractTableModel::headerData(section, orientation, role); +} + +// 获取当前显示的属性 +QVector StructDataPropertyModel::getDisplayedProperties() const { + QVector result; + for (const QString& code : m_propertyCodes) { + ExtraProperty* prop = m_dataManager->getPropertyByCode(code); + if (prop) { + result.append(*prop); + } + } + return result; +} + +// 获取当前显示的code列表 +QStringList StructDataPropertyModel::getDisplayedCodes() const { + return m_propertyCodes; +} + +// 根据code查找行 +int StructDataPropertyModel::findRowByCode(const QString& code) const { + return m_propertyCodes.indexOf(code); +} + +// 刷新指定code的行 +void StructDataPropertyModel::refreshRow(const QString& code) { + int row = findRowByCode(code); + if (row >= 0) { + QModelIndex start = index(row, 0); + QModelIndex end = index(row, columnCount() - 1); + emit dataChanged(start, end); + } +} + +void StructDataPropertyModel::onPropertyUpdated(const ExtraProperty& updatedProp, bool isNew) { + Q_UNUSED(isNew); + + // 如果这个属性在当前显示列表中,刷新对应行 + int row = findRowByCode(updatedProp.code); + if (row >= 0) { + refreshRow(updatedProp.code); + } +} + +ExtraProperty* StructDataPropertyModel::getProperty(int displayRow) const { + if (displayRow < 0 || displayRow >= m_propertyCodes.size()) { + return nullptr; + } + return m_dataManager->getPropertyByCode(m_propertyCodes[displayRow]); +} + +QVariant StructDataPropertyModel::getPropertyData(const ExtraProperty& prop, int col) const { + propertyStateInfo* data = m_dataManager->getPropertyData(prop); + if (!data) return QVariant(); + + switch (col) { + case ColDataType: return data->type; + case ColDefaultValue: return data->defaultValue; + case ColLengthPrecision: return data->lengthPrecision; + } + return QVariant(); +} + +bool StructDataPropertyModel::updatePropertyData(propertyStateInfo* data, int col, const QVariant& value) { + switch (col) { + case ColLengthPrecision: + if (data->lengthPrecision != value.toInt()) { + data->lengthPrecision = value.toInt(); + return true; + } + break; + case ColDefaultValue: + if (data->defaultValue != value) { + data->defaultValue = value; + return true; + } + break; + } + return false; +} + diff --git a/diagramCavas/source/structDataSource.cpp b/diagramCavas/source/structDataSource.cpp new file mode 100644 index 0000000..77957cf --- /dev/null +++ b/diagramCavas/source/structDataSource.cpp @@ -0,0 +1,213 @@ +#include "structDataSource.h" +#include "global.h" + +StructDataSource::StructDataSource(QObject* parent) : QObject(parent) { + +} + +// 根据code获取属性 +ExtraProperty* StructDataSource::getPropertyByCode(const QString& code) { + auto it = allProperties.find(code); + if (it != allProperties.end()) { + return &it.value(); + } + return nullptr; +} + +// 根据tag获取属性 +ExtraProperty* StructDataSource::getPropertyByTag(const QString& tag) { + for (auto it = allProperties.begin(); it != allProperties.end(); ++it) { + if (it.value().tag == tag) { + return &it.value(); + } + } + return nullptr; +} + +// 根据group获取属性列表 +QVector StructDataSource::getPropertiesByGroup(const QString& groupTag, const QString& modelName) { + QVector result; + for (auto it = allProperties.begin(); it != allProperties.end(); ++it) { + const ExtraProperty& prop = it.value(); + if (prop.group_tag == groupTag && + (modelName.isEmpty() || prop.sourceConfig.value("modelName").toString() == modelName)) { + result.append(prop); + } + } + return result; +} + +// 根据sourceType获取属性列表 +QVector StructDataSource::getPropertiesBySourceType(const QString& sourceType) { + QVector result; + for (auto it = allProperties.begin(); it != allProperties.end(); ++it) { + if (it.value().sourceType == sourceType) { + result.append(it.value()); + } + } + return result; +} + +// 添加或更新属性 +bool StructDataSource::addOrUpdateProperty(const ExtraProperty& prop) { + if (prop.code.isEmpty()) { + qWarning() << "Property code is empty"; + return false; + } + + bool isNew = !allProperties.contains(prop.code); + allProperties[prop.code] = prop; + + emit propertyUpdated(prop, isNew); + return true; +} + +// 更新单个属性 +bool StructDataSource::updateProperty(const ExtraProperty& updatedProp) { + if (updatedProp.code.isEmpty()) { + qWarning() << "Property code is empty"; + return false; + } + + if (!allProperties.contains(updatedProp.code)) { + qWarning() << "Property not found:" << updatedProp.code; + return false; + } + + allProperties[updatedProp.code] = updatedProp; + emit propertyUpdated(updatedProp, false); + return true; +} + +// 更新connect_para +bool StructDataSource::updateConnectPara(const QString& code, const QString& newConnectPara) { + auto it = allProperties.find(code); + if (it != allProperties.end()) { + it.value().connect_para = newConnectPara; + emit propertyUpdated(it.value(), false); + return true; + } + return false; +} + +// 批量更新 +void StructDataSource::updateProperties(const QVector& updatedProps) { + for (const auto& prop : updatedProps) { + updateProperty(prop); + } +} + +// 删除属性 +bool StructDataSource::removeProperty(const QString& code) { + if (allProperties.contains(code)) { + ExtraProperty removedProp = allProperties[code]; + allProperties.remove(code); + emit propertyRemoved(removedProp); + return true; + } + return false; +} + +// 批量删除 +int StructDataSource::removeProperties(const QVector& codes) { + int count = 0; + for (const QString& code : codes) { + if (removeProperty(code)) { + count++; + } + } + return count; +} + +// 保存到文件 +void StructDataSource::saveAll() { + +} + +// 加载数据 + +// 获取所有属性的code列表 +QStringList StructDataSource::getAllCodes() const { + return allProperties.keys(); +} + +// 获取所有属性 +QVector StructDataSource::getAllProperties() const { + return allProperties.values(); +} + +// 获取property数据 +propertyStateInfo* StructDataSource::getPropertyData(const ExtraProperty& prop) { + QString modelName = prop.sourceConfig.value("modelName").toString(); + QString groupTag = prop.group_tag; + QUuid componentUuid = prop.component_uuid; + QString propertyTag = prop.tag; + + auto itModel = m_propertyData.find(modelName); + if (itModel == m_propertyData.end()) return nullptr; + + auto itGroup = itModel->groupInfo.find(groupTag); + if (itGroup == itModel->groupInfo.end()) return nullptr; + + auto itComponent = itGroup->mapInfo.find(componentUuid); + if (itComponent == itGroup->mapInfo.end()) return nullptr; + + auto itProperty = itComponent->find(propertyTag); + if (itProperty == itComponent->end()) return nullptr; + + return &itProperty.value(); +} + +// 获取measurement数据 +MeasurementInfo* StructDataSource::getMeasurementData(const ExtraProperty& prop) { + auto it = m_measurementData.find(prop.tag); + if (it != m_measurementData.end()) { + return &it.value(); + } + return nullptr; +} + +// 验证数据 +bool StructDataSource::validateProperty(const ExtraProperty& prop) { + if (prop.code.isEmpty()) { + qWarning() << "Property code is empty"; + return false; + } + + if (prop.name.isEmpty()) { + qWarning() << "Property name is empty:" << prop.code; + return false; + } + + if (prop.tag.isEmpty()) { + qWarning() << "Property tag is empty:" << prop.code; + return false; + } + + if (prop.sourceType.isEmpty()) { + qWarning() << "Property sourceType is empty:" << prop.code; + return false; + } + + if (prop.sourceType != "property" && prop.sourceType != "measurement") { + qWarning() << "Invalid sourceType:" << prop.sourceType << "for property:" << prop.code; + return false; + } + + return true; +} + +void StructDataSource::loadExtrapro(QMap vec) +{ + allProperties = vec; +} + +void StructDataSource::loadPropertyData(QMap map) +{ + m_propertyData = map; +} + +void StructDataSource::loadMeasurementData(QMap map) +{ + m_measurementData = map; +} diff --git a/diagramCavas/ui/measureSettingDlg.ui b/diagramCavas/ui/measureSettingDlg.ui index 7987f3e..71e9c44 100644 --- a/diagramCavas/ui/measureSettingDlg.ui +++ b/diagramCavas/ui/measureSettingDlg.ui @@ -206,101 +206,17 @@ QTabBar::tab:selected { 10 - - + + - 端子: - - - - - - - 数据大小(size): - - - - - - - - 0 - 0 - - - - - 80 - 16777215 - - - - - - - - 标签(tag): + 名称: Qt::AlignmentFlag::AlignLeading|Qt::AlignmentFlag::AlignLeft|Qt::AlignmentFlag::AlignVCenter - - - - 设备: - - - - - - - - 150 - 0 - - - - - - - - - 150 - 0 - - - - - - - - - 150 - 0 - - - - - - - - 类型: - - - - - - - (唯一标识) - - - Qt::AlignmentFlag::AlignLeading|Qt::AlignmentFlag::AlignLeft|Qt::AlignmentFlag::AlignVCenter - - - - + @@ -325,27 +241,14 @@ QTabBar::tab:selected { - - + + - 名称: - - - Qt::AlignmentFlag::AlignLeading|Qt::AlignmentFlag::AlignLeft|Qt::AlignmentFlag::AlignVCenter + 类型: - - - - - 150 - 0 - - - - - + Qt::Orientation::Vertical @@ -358,6 +261,75 @@ QTabBar::tab:selected { + + + + + 150 + 0 + + + + + + + + 标签(tag): + + + Qt::AlignmentFlag::AlignLeading|Qt::AlignmentFlag::AlignLeft|Qt::AlignmentFlag::AlignVCenter + + + + + + + + 0 + 0 + + + + + 150 + 0 + + + + + + + + + 0 + 0 + + + + + 80 + 16777215 + + + + + + + + 数据大小(size): + + + + + + + (唯一标识) + + + Qt::AlignmentFlag::AlignLeading|Qt::AlignmentFlag::AlignLeft|Qt::AlignmentFlag::AlignVCenter + + + diff --git a/diagramCavas/ui/structDataPreviewDlg.ui b/diagramCavas/ui/structDataPreviewDlg.ui index 31db230..4eea1a6 100644 --- a/diagramCavas/ui/structDataPreviewDlg.ui +++ b/diagramCavas/ui/structDataPreviewDlg.ui @@ -150,6 +150,9 @@ QPushButton:hover { } + + 2 + 0 @@ -237,6 +240,31 @@ QPushButton:hover { + + + + + 20 + 20 + + + + + 20 + 20 + + + + + 20 + 20 + + + + + + + @@ -312,31 +340,6 @@ QPushButton:hover { - - - - - 20 - 20 - - - - - 20 - 20 - - - - - 20 - 20 - - - - - - - @@ -359,7 +362,7 @@ QPushButton:hover { - + 0 @@ -380,7 +383,71 @@ QPushButton:hover { Qt::Orientation::Vertical - + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 0 + 21 + + + + + 16777215 + 21 + + + + QWidget { + background: qlineargradient(x1:0, y1:0, x2:0, y2:1, + stop:0 #f8fafc, + stop:1 #f1f5f9); + color: rgb(6, 6, 6); +} + + + + + + + + + + + + + Qt::Orientation::Vertical + + + QSizePolicy::Policy::Preferred + + + + 0 + 0 + + + + + + diff --git a/diagramUtils/include/dataBase.h b/diagramUtils/include/dataBase.h index 09efed9..ad3d183 100644 --- a/diagramUtils/include/dataBase.h +++ b/diagramUtils/include/dataBase.h @@ -73,11 +73,13 @@ public: bool delteMeasurement(QString name,QUuid componentId); bool ifMeasureExist(QString name,QUuid componentId); QList getMeasurement(QUuid componentId); + QMap getAllMeasurements(); /*********************************************************************************/ bool insertExtraProperty(ExtraProperty); //属性层级与连接信息 bool updateExtraProperty(ExtraProperty); bool deleteExtraProperty(QString code); bool ifExtraPropertyExist(QString code); + QList getCompoExtraProperty(QUuid uid); //获取component中的层级信息 QList getAllExtraProperty(); /*********************************************************************************/ bool deleteComponentById(int id); diff --git a/diagramUtils/source/dataBase.cpp b/diagramUtils/source/dataBase.cpp index 2b2ffed..ea55225 100644 --- a/diagramUtils/source/dataBase.cpp +++ b/diagramUtils/source/dataBase.cpp @@ -306,7 +306,7 @@ bool DataBase::insertDynamicProperty(QUuid uuid,groupStateValue groupValue) for(auto &pro:groupValue.mapInfo[uuid]) { - strPros += QString(",")+pro.name; + strPros += QString(",")+pro.tagName; strPronouns += QString(",?"); if(pro.defaultValue.userType() == qMetaTypeId()) //json特殊处理 { @@ -338,7 +338,7 @@ bool DataBase::updateDynamicProperty(QUuid uuid,groupStateValue groupValue) QVariantList params; for(auto &pro:groupValue.mapInfo[uuid]) { - setClauses.append(QString("%1 = ?").arg(pro.name)); + setClauses.append(QString("%1 = ?").arg(pro.tagName)); if(pro.defaultValue.userType() == qMetaTypeId()) //json特殊处理 { QJsonDocument contextDoc(pro.defaultValue.toJsonObject()); @@ -1519,8 +1519,7 @@ QList DataBase::getMeasurement(QUuid componentId) info.nSource = objData["type"].toInt(); QJsonObject objIoAddress = objData["io_address"].toObject(); info.sStation = objData["station"].toString(); - info.equipment = objIoAddress["device"].toString(); - info.channel = objIoAddress["channel"].toString(); + info.sDevice = objIoAddress["device"].toString(); info.sChannel = objIoAddress["channel"].toString(); info.nPacket = objIoAddress["packet"].toInt(); info.nOffset = objIoAddress["offset"].toInt(); @@ -1557,10 +1556,76 @@ QList DataBase::getMeasurement(QUuid componentId) return lst; } } + +QMap DataBase::getAllMeasurements() +{ + QMap lst; + QString strSQL = "SELECT tag, name, type, data_source, event_plan, size, bay_uuid, component_uuid FROM measurement"; + + try + { + QSqlQuery query = executeSQL(strSQL); + while (query.next()) + { + MeasurementInfo info; + info.tag = query.value(0).toString(); + info.name = query.value(1).toString(); + info.type = query.value(2).toInt(); + + QString conData = query.value(3).toString(); + QJsonObject objData = QstringToJson(conData); + + QString sEvent = query.value(4).toString(); + QJsonObject objEvent = QstringToJson(sEvent); + + info.size = query.value(5).toInt(); + info.bayUuid = QUuid(query.value(6).toString()); + info.componentUuid = QUuid(query.value(7).toString()); + + info.nSource = objData["type"].toInt(); + QJsonObject objIoAddress = objData["io_address"].toObject(); + info.sStation = objData["station"].toString(); + info.sDevice = objIoAddress["device"].toString(); + info.sChannel = objIoAddress["channel"].toString(); + info.nPacket = objIoAddress["packet"].toInt(); + info.nOffset = objIoAddress["offset"].toInt(); + + info.bEnable = objEvent["enable"].toBool(); + QJsonObject objCause = objEvent["cause"].toObject(); + if(objCause.contains("upup")){ + info.mapTE.insert("upup",objCause["upup"].toDouble()); + } + if(objCause.contains("up")){ + info.mapTE.insert("up",objCause["up"].toDouble()); + } + if(objCause.contains("down")){ + info.mapTE.insert("down",objCause["down"].toDouble()); + } + if(objCause.contains("downdown")){ + info.mapTE.insert("downdown",objCause["downdown"].toDouble()); + } + info.sEdge = objCause["edge"].toString(); + QJsonObject objAction = objEvent["action"].toObject(); + info.sCommand = objAction["command"].toString(); + + QJsonArray arrPara = objAction["parameters"].toArray(); + for(const QJsonValue ¶Value:arrPara){ + info.lstParameter.append(paraValue.toString()); + } + lst.insert(info.tag,info); + } + query.clear(); + return lst; + } + catch (const std::exception& e) + { + return lst; + } +} /*****************************************************************************/ bool DataBase::insertExtraProperty(ExtraProperty pro) { - QString strSQL = "INSERT INTO properties_setting(code, tag, name, grid_name, zone_name, station_name, current_level, bay_name, component_name, group_name, grid_tag, zone_tag, station_tag, page_tag, bay_tag, component_uuid, group_tag, source_type, source_config, connect_para) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"; + QString strSQL = "INSERT INTO properties_setting(code, tag, name, grid_name, zone_name, station_name, current_level, bay_name, component_name, group_name, type_name, grid_tag, zone_tag, station_tag, page_tag, bay_tag, component_uuid, group_tag, type_tag, source_type, source_config, connect_para) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)"; QJsonDocument configDoc(QJsonObject::fromVariantMap(pro.sourceConfig)); QString strConfig = configDoc.toJson(QJsonDocument::Compact); @@ -1575,6 +1640,7 @@ bool DataBase::insertExtraProperty(ExtraProperty pro) params.append(pro.bay_name); params.append(pro.component_name); params.append(pro.group_name); + params.append(pro.type_name); params.append(pro.grid_tag); params.append(pro.zone_tag); @@ -1583,6 +1649,7 @@ bool DataBase::insertExtraProperty(ExtraProperty pro) params.append(pro.bay_tag); params.append(pro.component_uuid.toString()); params.append(pro.group_tag); + params.append(pro.type_tag); params.append(pro.sourceType); params.append(strConfig); params.append(pro.connect_para); @@ -1661,10 +1728,61 @@ bool DataBase::ifExtraPropertyExist(QString code) return false; } +QList DataBase::getCompoExtraProperty(QUuid uid) +{ + QList lst; + QString strSQL = "SELECT code, tag, name, grid_name, zone_name, station_name, current_level, bay_name, component_name, group_name, type_name, grid_tag, zone_tag, station_tag, page_tag, bay_tag, component_uuid, group_tag, type_tag, source_type, source_config, connect_para FROM properties_setting WHERE component_uuid = ?"; + QVariantList params; + params.append(uid); + + try + { + QSqlQuery query = executeSQL(strSQL,false,params); + while (query.next()) + { + ExtraProperty info; + info.code = query.value(0).toString(); + info.tag = query.value(1).toString(); + info.name = query.value(2).toString(); + info.grid_name = query.value(3).toString(); + info.zone_name = query.value(4).toString(); + info.station_name = query.value(5).toString(); + info.currentLevel = query.value(6).toString(); + info.bay_name = query.value(7).toString(); + info.component_name = query.value(8).toString(); + info.group_name = query.value(9).toString(); + info.type_name = query.value(10).toString(); + + info.grid_tag = query.value(11).toString(); + info.zone_tag = query.value(12).toString(); + info.station_tag = query.value(13).toString(); + info.page_tag = query.value(14).toString(); + info.bay_tag = query.value(15).toString(); + info.component_uuid = QUuid(query.value(16).toString()); + info.group_tag = query.value(17).toString(); + info.type_tag = query.value(18).toString(); + + info.sourceType = query.value(19).toString(); + QString sConfig = query.value(20).toString(); + QJsonObject objConfig = QstringToJson(sConfig); + info.sourceConfig = objConfig.toVariantMap(); + info.connect_para = query.value(21).toString(); + + lst.append(info); + } + query.clear(); + return lst; + } + catch (const std::exception& e) + { + return lst; + } +} + QList DataBase::getAllExtraProperty() { QList lst; - QString strSQL = "SELECT code, tag, name, grid_name, zone_name, station_name, current_level, bay_name, component_name, group_name, grid_tag, zone_tag, station_tag, page_tag, bay_tag, component_uuid, group_tag, source_type, source_config, connect_para FROM properties_setting"; + QString strSQL = "SELECT code, tag, name, grid_name, zone_name, station_name, current_level, bay_name, component_name, group_name, type_name, grid_tag, zone_tag, station_tag, page_tag, bay_tag, component_uuid, group_tag, type_tag, source_type, source_config, connect_para FROM properties_setting"; try { @@ -1682,19 +1800,22 @@ QList DataBase::getAllExtraProperty() info.bay_name = query.value(7).toString(); info.component_name = query.value(8).toString(); info.group_name = query.value(9).toString(); + info.type_name = query.value(10).toString(); - info.grid_tag = query.value(10).toString(); - info.zone_tag = query.value(11).toString(); - info.station_tag = query.value(12).toString(); - info.page_tag = query.value(13).toString(); - info.bay_tag = query.value(14).toString(); - info.component_uuid = QUuid(query.value(15).toString()); - info.group_tag = query.value(16).toString(); - info.sourceType = query.value(17).toString(); - QString sConfig = query.value(18).toString(); + info.grid_tag = query.value(11).toString(); + info.zone_tag = query.value(12).toString(); + info.station_tag = query.value(13).toString(); + info.page_tag = query.value(14).toString(); + info.bay_tag = query.value(15).toString(); + info.component_uuid = QUuid(query.value(16).toString()); + info.group_tag = query.value(17).toString(); + info.type_tag = query.value(18).toString(); + + info.sourceType = query.value(19).toString(); + QString sConfig = query.value(20).toString(); QJsonObject objConfig = QstringToJson(sConfig); info.sourceConfig = objConfig.toVariantMap(); - info.connect_para = query.value(19).toString(); + info.connect_para = query.value(21).toString(); lst.append(info); } @@ -2535,7 +2656,7 @@ QMap DataBase::selectGroupPropertyByState(const QString QStringList paramList; for(auto &pro:mapPro) { - paramList.append(pro.name); + paramList.append(pro.tagName); } QString strSQL = QString("SELECT %1 FROM %2").arg(paramList.join(", ")).arg(tableName); QMap map; @@ -2550,15 +2671,16 @@ QMap DataBase::selectGroupPropertyByState(const QString for(auto &proVal:mapPro) { propertyStateInfo pro; - if(proVal.name == "global_uuid" && tableName != "baseProperty") //除基础属性组,其他组不显示uuid todo:组名适配 + if(proVal.tagName == "global_uuid" && tableName != "baseProperty") //除基础属性组,其他组不显示uuid todo:组名适配 { - uuid = QUuid(query.value(proVal.name).toString()); + uuid = QUuid(query.value(proVal.tagName).toString()); continue; } - else if(proVal.name == "global_uuid" && tableName == "baseProperty") + else if(proVal.tagName == "global_uuid" && tableName == "baseProperty") { - uuid = QUuid(query.value(proVal.name).toString()); + uuid = QUuid(query.value(proVal.tagName).toString()); } + pro.tagName = proVal.tagName; pro.name = proVal.name; pro.type = proVal.type; pro.isVisibe = proVal.isVisibe; @@ -2566,8 +2688,8 @@ QMap DataBase::selectGroupPropertyByState(const QString pro.defaultValue = query.value(proVal.name).toJsonObject(); } else*/ - pro.defaultValue = query.value(proVal.name ); - info.insert(proVal.name ,pro); + pro.defaultValue = query.value(proVal.tagName ); + info.insert(proVal.tagName ,pro); } map.insert(uuid,info); } @@ -2586,7 +2708,7 @@ PropertyValueInfo DataBase::selectGroupPropertyByValue(const QString& tableName, QStringList paramList; for(auto &pro:value) { - paramList.append(pro.name); + paramList.append(pro.tagName); } QString strSQL = QString("SELECT %1 FROM %2 WHERE global_uuid = ?").arg(paramList.join(", ")).arg(tableName); QVariantList params; @@ -2601,11 +2723,12 @@ PropertyValueInfo DataBase::selectGroupPropertyByValue(const QString& tableName, for(auto &proVal:value) { propertyStateInfo pro; + pro.tagName = proVal.tagName; pro.name = proVal.name; pro.type = proVal.type; pro.isVisibe = proVal.isVisibe; - pro.defaultValue = query.value(proVal.name ); - map.insert(proVal.name,pro); + pro.defaultValue = query.value(proVal.tagName ); + map.insert(proVal.tagName,pro); } } query.clear(); diff --git a/diagramUtils/source/dataManager.cpp b/diagramUtils/source/dataManager.cpp index 473f945..7649b03 100644 --- a/diagramUtils/source/dataManager.cpp +++ b/diagramUtils/source/dataManager.cpp @@ -24,6 +24,7 @@ DataManager::~DataManager() void DataManager::initialModelState(bool refresh) { QMap model = DataBase::GetInstance()->getAllProjectModel(); + QMap mapAttribute = DataBase::GetInstance()->Attribute(); if(refresh) { @@ -57,7 +58,14 @@ void DataManager::initialModelState(bool refresh) propertyStateInfo propertyInfo; QJsonObject node = nodeJson.toObject(); - QString propertyName = node["name"].toString(); + QString propertyTag = node["name"].toString(); + QString propertyName; + for(auto& info:mapAttribute){ + if(info.attribute == propertyTag){ + propertyName = info.attributeName; + break; + } + } int nState = node["checked"].toInt(); QString dataType = node["type"].toString(); QVariant defaultValue = node["defaultValue"].toVariant(); @@ -65,6 +73,7 @@ void DataManager::initialModelState(bool refresh) int nIsVisible = node["isVisible"].toInt(); if(nState) { + propertyInfo.tagName = propertyTag; propertyInfo.name = propertyName; propertyInfo.type = dataType; propertyInfo.defaultValue = defaultValue; @@ -89,7 +98,14 @@ void DataManager::initialModelState(bool refresh) propertyStateInfo propertyInfo; QJsonObject node = nodeJson.toObject(); - QString propertyName = node["name"].toString(); + QString propertyTag = node["name"].toString(); + QString propertyName; + for(auto& info:mapAttribute){ + if(info.attribute == propertyTag){ + propertyName = info.attributeName; + break; + } + } int nState = node["checked"].toInt(); QString dataType = node["type"].toString(); QVariant defaultValue = node["defaultValue"].toVariant(); @@ -97,7 +113,7 @@ void DataManager::initialModelState(bool refresh) int nIsVisible = node["isVisible"].toInt(); if(nState) { - //todo:别名赋值 + propertyInfo.tagName = propertyTag; propertyInfo.name = propertyName; propertyInfo.type = dataType; propertyInfo.defaultValue = defaultValue; @@ -118,6 +134,7 @@ void DataManager::initialModelState(bool refresh) void DataManager::initialModelData(bool refresh) { QMap model = DataBase::GetInstance()->getAllProjectModel(); + QMap mapAttribute = DataBase::GetInstance()->Attribute(); if(!refresh){ QMap::Iterator iter; for(iter = model.begin();iter != model.end(); ++iter) //遍历模型 @@ -143,24 +160,32 @@ void DataManager::initialModelData(bool refresh) propertyStateInfo propertyInfo; QJsonObject node = nodeJson.toObject(); - QString propertyName = node["name"].toString(); + QString propertyTag = node["name"].toString(); + QString propertyName; + for(auto& info:mapAttribute){ + if(info.attribute == propertyTag){ + propertyName = info.attributeName; + break; + } + } int nState = node["checked"].toInt(); QString dataType = node["type"].toString(); QVariant defaultValue = node["defaultValue"].toVariant(); int nIsVisible = node["isVisible"].toInt(); + propertyInfo.tagName = propertyTag; propertyInfo.name = propertyName; propertyInfo.type = dataType; propertyInfo.isVisibe = nIsVisible; if(nState) { - mapPro.insert(propertyName,propertyInfo); + mapPro.insert(propertyTag,propertyInfo); } } if(!mapPro.contains("global_uuid")) //不包含uuid则手动添加 { propertyStateInfo uuidInfo; - uuidInfo.name = "global_uuid"; //全局id未添加到属性状态中,手动添加 + uuidInfo.tagName = "global_uuid"; //全局id未添加到属性状态中,手动添加 mapPro.insert("global_uuid",uuidInfo); } @@ -182,22 +207,30 @@ void DataManager::initialModelData(bool refresh) propertyStateInfo propertyInfo; QJsonObject node = nodeJson.toObject(); - QString propertyName = node["name"].toString(); + QString propertyTag = node["name"].toString(); + QString propertyName; + for(auto& info:mapAttribute){ + if(info.attribute == propertyTag){ + propertyName = info.attributeName; + break; + } + } int nState = node["checked"].toInt(); QString dataType = node["type"].toString(); QVariant defaultValue = node["defaultValue"].toVariant(); int nIsVisible = node["isVisible"].toInt(); + propertyInfo.tagName = propertyTag; propertyInfo.name = propertyName; propertyInfo.type = dataType; propertyInfo.isVisibe = nIsVisible; if(nState) { - mapPro.insert(propertyName,propertyInfo); + mapPro.insert(propertyTag,propertyInfo); } } propertyStateInfo uuidInfo; - uuidInfo.name = "global_uuid"; //全局id未添加到属性状态中,手动添加 + uuidInfo.tagName = "global_uuid"; //全局id未添加到属性状态中,手动添加 mapPro.insert("global_uuid",uuidInfo); groupValue.mapInfo = DataBase::GetInstance()->selectGroupPropertyByState(it->tableName,mapPro); //返回表中属性值