#pragma once #include #include #include #include "interact/SlicePlaneMath.hpp" // geopro::render::interact::SliceAxis #include "repo/CategoryConfig.hpp" #include "repo/RepoTypes.hpp" class QTreeWidget; class QTreeWidgetItem; class QComboBox; class QDateEdit; class QLabel; class QToolButton; class QTimer; class QWidget; namespace geopro::data { class DatasetFieldDictionary; } namespace geopro::app { class DateRangeEdit; // 单个数据类型大类段(spec §7):段头(标题/折叠 + 装置类型/日期筛选 + 「+新增三维体」)+ 段体(可勾选数据树)。 // 勾选数据行 = 渲染(帘面/体素/切片);段头生成按钮据当前勾选源发 generateVolumeRequested。 class CategorySection : public QWidget { Q_OBJECT public: CategorySection(const CategorySpec& spec, geopro::data::DatasetFieldDictionary* dict, QWidget* parent = nullptr); // 对象树同源的扁平 GS/TM 节点(段体容器分层用;Task 12 接入真实结构,当前仅存储)。 void setStructure(const std::vector& nodes); void setDatasets(const std::vector& rows); void setChecked(const QString& dsId, bool on); // 按 dsId 勾选/取消(新建切片自动勾选等场景) // 渲染中:该行复选框替换为等待 spinner(busy=true)/复原(false)。busy 期间保持勾选、动画由定时器驱动。 void setBusy(const QString& dsId, bool busy); void clearAllBusy(); // 撤回本段所有 spinner(失败兜底) void selectItem(const QString& dsId); // 程序化选中某行(VTK→list 反向联动);空/未找到=清选中 QStringList checkedIds() const { return checkedDsIds(); } // 当前勾选 ds(异常显隐同步用) void refreshArrayFilter() { refreshArrayCombo(); } // 装置枚举异步加载后重填下拉 const CategorySpec& spec() const { return spec_; } bool isExpanded() const; // 段头展开态(供外层按折叠状态重分配 stretch,实现"折叠向上收") void ensureExpanded(); // 展开本段(折叠则展开):滚动定位前确保目标行可见 QTreeWidget* listWidget() const { return list_; } // 段体树(外层滚动定位用) QTreeWidgetItem* itemFor(const QString& dsId) const; // 按 dsId 取行(无则 nullptr) bool hasRenderableRows() const; // 段体是否含可渲染数据行(非 container 容器节点),供单列动态显隐 signals: void checkedDatasetsChanged(const QStringList& dsIds); // 数据行勾选=渲染 void collapsedChanged(); // 折叠/展开切换 → 外层 CategoryAnalysisTab 重排各段 stretch void generateVolumeRequested(const QString& dsTypeCode, const QStringList& sourceDsIds); // 段头「+新增三维体」 void radarImportRequested(bool impulse); // 三维体段头「+导入雷达测线」(false=规范化 .head/.data, true=Impulse .iprb) void detailRequested(const QString& dsId, const QString& ddCode, const QString& name); // 双击/右键=详情 void deleteDatasetRequested(const QString& dsId, const QString& ddCode); // 右键删除(切片/异常) // ── 三维体段右键操作(迁自旧 Column3DAnalysis,全接)── void sliceRequested(geopro::render::interact::SliceAxis axis, const QString& volumeDsId); // 体→生成切片(轴+目标体) void colorScaleRequested(const QString& dsId); // 体/切片→色阶 void radarGainModeRequested(const QString& dsId, int mode); // 雷达体→显示增益模式(0关/1AGC/2保幅tpow) void sliceSaveRequested(const QString& dsId); // 切片→保存位姿 void sliceSaveAsRequested(const QString& dsId); // 切片→另存 void sliceExportImageRequested(const QString& dsId); // 切片→导出图片 void sliceExportDatRequested(const QString& dsId); // 切片→导出 dat void anomalyVisibilityChanged(const QString& dsId, bool vis); // 异常→显示/隐藏 void datasetSelected(const QString& dsId, const QString& ddCode); // 树选中行→VTK 高亮联动(切片/异常) private: void showContextMenu(const QPoint& pos); // 段体树右键菜单(详情 + 删除) void rebuildList(); // 据 rows_(经装置/日期筛选)重建段体树并复原勾选 void refreshArrayCombo(); // 据当前 rows_ 重填装置类型下拉项(经字典 value→中文) void emitChecked(); // 收集勾选 → checkedDatasetsChanged QStringList checkedDsIds() const; bool passesFilters(const geopro::data::DsRow& row) const; // 装置类型 + 采集时间范围 CategorySpec spec_; geopro::data::DatasetFieldDictionary* dict_ = nullptr; std::vector rows_; std::vector structure_; QToolButton* header_ = nullptr; // 折叠头(标题 + 箭头) QWidget* body_ = nullptr; // 段体容器(折叠时隐藏) QComboBox* arrayCombo_ = nullptr; // 装置类型筛选(仅 hasArrayTypeFilter) DateRangeEdit* dateRange_ = nullptr; // 采集时间范围筛选(起止双日历,可清空) QTreeWidget* list_ = nullptr; QTimer* spinTimer_ = nullptr; // 驱动 busy 行 spinner 旋转(有 busy 行时运行) int spinAngle_ = 0; // 当前 spinner 角度(度) }; } // namespace geopro::app