|
|
|
|
|
#include "nmWxDFNLoadFromFile.h"
|
|
|
|
|
|
#include <QVBoxLayout>
|
|
|
|
|
|
#include <QHBoxLayout>
|
|
|
|
|
|
#include <QHeaderView>
|
|
|
|
|
|
#include <QCoreApplication>
|
|
|
|
|
|
#include <QFileDialog>
|
|
|
|
|
|
#include <QComboBox>
|
|
|
|
|
|
#include <QMessageBox>
|
|
|
|
|
|
#include <QTextStream>
|
|
|
|
|
|
|
|
|
|
|
|
#include "nmDataAnalyzeManager.h"
|
|
|
|
|
|
#include "nmDataFracture.h"
|
|
|
|
|
|
#include "nmGuiPlot.h"
|
|
|
|
|
|
#include "nmObjLineCrack.h"
|
|
|
|
|
|
#include "ZxPlot.h"
|
|
|
|
|
|
|
|
|
|
|
|
#include "ExcelUtils.h"
|
|
|
|
|
|
|
|
|
|
|
|
// 构造函数
|
|
|
|
|
|
nmWxDFNLoadFromFile::nmWxDFNLoadFromFile(QWidget* pParent)
|
|
|
|
|
|
: iDlgBase(pParent)
|
|
|
|
|
|
{
|
|
|
|
|
|
this->setWindowTitle(tr("Load from file..."));
|
|
|
|
|
|
this->setMinimumSize(861, 708);
|
|
|
|
|
|
|
|
|
|
|
|
QString appDir = QCoreApplication::applicationDirPath();
|
|
|
|
|
|
appDir = appDir.section('/', 0, -2); // 获取上一级目录
|
|
|
|
|
|
m_sLastOpenedFilePath = appDir + "/Temp/DFN";
|
|
|
|
|
|
|
|
|
|
|
|
this->initUI();
|
|
|
|
|
|
this->initConnections();
|
|
|
|
|
|
|
|
|
|
|
|
// 初始化Type到Unit的映射
|
|
|
|
|
|
this->initUnitMappings();
|
|
|
|
|
|
|
|
|
|
|
|
this->setupTable();
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
nmWxDFNLoadFromFile::~nmWxDFNLoadFromFile()
|
|
|
|
|
|
{
|
|
|
|
|
|
// 所有Qt对象会自动被父对象删除
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::initUI()
|
|
|
|
|
|
{
|
|
|
|
|
|
QVBoxLayout* pMainLayout = new QVBoxLayout(this);
|
|
|
|
|
|
|
|
|
|
|
|
// 创建水平布局容器
|
|
|
|
|
|
QHBoxLayout* pTopHorizontalLayout = new QHBoxLayout();
|
|
|
|
|
|
|
|
|
|
|
|
// 1. 数据源部分
|
|
|
|
|
|
m_pSourceGroup = new QGroupBox(tr("Data Source"), this);
|
|
|
|
|
|
m_pSourceGroup->setFixedSize(337, 106);
|
|
|
|
|
|
|
|
|
|
|
|
// 使用垂直布局作为主布局(包含按钮行和文件路径行)
|
|
|
|
|
|
QVBoxLayout* pSourceMainLayout = new QVBoxLayout(m_pSourceGroup);
|
|
|
|
|
|
|
|
|
|
|
|
// 1.1 导入文件按钮部分(水平布局)
|
|
|
|
|
|
QHBoxLayout* pLoadButtonLayout = new QHBoxLayout();
|
|
|
|
|
|
m_pLoadTxtButton = new QPushButton(this);
|
|
|
|
|
|
m_pLoadExcelButton = new QPushButton(this);
|
|
|
|
|
|
m_pCopyButton = new QPushButton(this);
|
|
|
|
|
|
|
|
|
|
|
|
QString appDir = QCoreApplication::applicationDirPath();
|
|
|
|
|
|
appDir = appDir.section('/', 0, -2); // 获取上一级目录
|
|
|
|
|
|
|
|
|
|
|
|
// 设置按钮图标
|
|
|
|
|
|
QIcon loadTXTIcon(appDir + "/Res/Icon/NmDFNLoadTXT.png");
|
|
|
|
|
|
QIcon loadExcelIcon(appDir + "/Res/Icon/NmDFNLoadExcel.png");
|
|
|
|
|
|
QIcon loadCopyIcon(appDir + "/Res/Icon/NmDFNLoadCopy.png");
|
|
|
|
|
|
|
|
|
|
|
|
m_pLoadTxtButton->setIcon(loadTXTIcon);
|
|
|
|
|
|
m_pLoadExcelButton->setIcon(loadExcelIcon);
|
|
|
|
|
|
m_pCopyButton->setIcon(loadCopyIcon);
|
|
|
|
|
|
|
|
|
|
|
|
// 设置图标大小
|
|
|
|
|
|
int iconSize = 32;
|
|
|
|
|
|
m_pLoadTxtButton->setIconSize(QSize(iconSize, iconSize));
|
|
|
|
|
|
m_pLoadExcelButton->setIconSize(QSize(iconSize, iconSize));
|
|
|
|
|
|
m_pCopyButton->setIconSize(QSize(iconSize, iconSize));
|
|
|
|
|
|
|
|
|
|
|
|
int iButtonWidth = 88;
|
|
|
|
|
|
int iButtonHeight = 41;
|
|
|
|
|
|
m_pLoadTxtButton->setFixedSize(iButtonWidth, iButtonHeight);
|
|
|
|
|
|
m_pLoadExcelButton->setFixedSize(iButtonWidth, iButtonHeight);
|
|
|
|
|
|
m_pCopyButton->setFixedSize(iButtonWidth, iButtonHeight);
|
|
|
|
|
|
|
|
|
|
|
|
pLoadButtonLayout->addWidget(m_pLoadTxtButton);
|
|
|
|
|
|
pLoadButtonLayout->addWidget(m_pLoadExcelButton);
|
|
|
|
|
|
pLoadButtonLayout->addWidget(m_pCopyButton);
|
|
|
|
|
|
pLoadButtonLayout->addStretch();
|
|
|
|
|
|
|
|
|
|
|
|
// 1.2 文件路径部分(水平布局)
|
|
|
|
|
|
QHBoxLayout* pFilePathLayout = new QHBoxLayout();
|
|
|
|
|
|
m_pFilePathEdit = new QLineEdit(this);
|
|
|
|
|
|
|
|
|
|
|
|
m_pBrowseButton = new QPushButton("...", this);
|
|
|
|
|
|
m_pBrowseButton->setFixedWidth(30); // 固定宽度
|
|
|
|
|
|
|
|
|
|
|
|
pFilePathLayout->addWidget(m_pFilePathEdit);
|
|
|
|
|
|
pFilePathLayout->addWidget(m_pBrowseButton);
|
|
|
|
|
|
|
|
|
|
|
|
// 将两个水平布局添加到垂直主布局(按钮在上,文件路径在下)
|
|
|
|
|
|
pSourceMainLayout->addLayout(pLoadButtonLayout);
|
|
|
|
|
|
pSourceMainLayout->addLayout(pFilePathLayout);
|
|
|
|
|
|
|
|
|
|
|
|
pTopHorizontalLayout->addWidget(m_pSourceGroup);
|
|
|
|
|
|
|
|
|
|
|
|
// 2. 分隔符部分
|
|
|
|
|
|
m_pSeparatorGroup = new QGroupBox(tr("Separators"), this);
|
|
|
|
|
|
m_pSeparatorGroup->setFixedSize(233,106); // 固定大小
|
|
|
|
|
|
|
|
|
|
|
|
// 使用复选框代替单选按钮
|
|
|
|
|
|
m_pSpaceCheck = new QCheckBox(tr("Space"), this);
|
|
|
|
|
|
m_pTabCheck = new QCheckBox(tr("Tab"), this);
|
|
|
|
|
|
m_pOtherLabel = new QLabel(tr("Others:"),this);
|
|
|
|
|
|
|
|
|
|
|
|
// 默认全部启用
|
|
|
|
|
|
m_pSpaceCheck->setChecked(true);
|
|
|
|
|
|
m_pTabCheck->setChecked(true);
|
|
|
|
|
|
|
|
|
|
|
|
m_pOtherSeparatorEdit = new QLineEdit(this);
|
|
|
|
|
|
m_pOtherSeparatorEdit->setMaximumWidth(50);
|
|
|
|
|
|
m_pOtherSeparatorEdit->setText(";"); // 默认自定义分隔符为分号
|
|
|
|
|
|
|
|
|
|
|
|
QVBoxLayout* pSepLayout = new QVBoxLayout(m_pSeparatorGroup);
|
|
|
|
|
|
pSepLayout->addWidget(m_pSpaceCheck);
|
|
|
|
|
|
pSepLayout->addWidget(m_pTabCheck);
|
|
|
|
|
|
|
|
|
|
|
|
QHBoxLayout* pOtherLayout = new QHBoxLayout();
|
|
|
|
|
|
pOtherLayout->addWidget(m_pOtherLabel);
|
|
|
|
|
|
pOtherLayout->addWidget(m_pOtherSeparatorEdit);
|
|
|
|
|
|
pOtherLayout->addStretch();
|
|
|
|
|
|
|
|
|
|
|
|
pSepLayout->addLayout(pOtherLayout);
|
|
|
|
|
|
pTopHorizontalLayout->addWidget(m_pSeparatorGroup);
|
|
|
|
|
|
|
|
|
|
|
|
// 3. 信息提示 - 现在放在GroupBox中
|
|
|
|
|
|
m_pInfoGroup = new QGroupBox(tr("Info"), this);
|
|
|
|
|
|
m_pInfoGroup->setFixedSize(255,106); // 固定大小
|
|
|
|
|
|
m_pInfoLabel = new QLabel(
|
|
|
|
|
|
tr("You need to assign at least 4 required types: X1, Y1, X2, Y2."),
|
|
|
|
|
|
this);
|
|
|
|
|
|
m_pInfoLabel->setWordWrap(true);
|
|
|
|
|
|
m_pInfoLabel->setAlignment(Qt::AlignLeft | Qt::AlignVCenter);
|
|
|
|
|
|
|
|
|
|
|
|
QVBoxLayout* pInfoLayout = new QVBoxLayout(m_pInfoGroup);
|
|
|
|
|
|
pInfoLayout->addWidget(m_pInfoLabel);
|
|
|
|
|
|
pTopHorizontalLayout->addWidget(m_pInfoGroup);
|
|
|
|
|
|
|
|
|
|
|
|
pTopHorizontalLayout->addStretch();
|
|
|
|
|
|
|
|
|
|
|
|
// 将水平布局添加到主布局
|
|
|
|
|
|
pMainLayout->addLayout(pTopHorizontalLayout);
|
|
|
|
|
|
|
|
|
|
|
|
// 4. 列类型分配表格
|
|
|
|
|
|
QWidget* pTableContainer = new QWidget(this);
|
|
|
|
|
|
QHBoxLayout* pTableLayout = new QHBoxLayout(pTableContainer);
|
|
|
|
|
|
pTableLayout->setContentsMargins(0, 0, 0, 0); // 去掉布局边距
|
|
|
|
|
|
|
|
|
|
|
|
m_pColumnTable = new QTableWidget();
|
|
|
|
|
|
m_pColumnTable->setStyleSheet("border: none;"); // 去掉表格的边框
|
|
|
|
|
|
|
|
|
|
|
|
pTableLayout->addWidget(m_pColumnTable);
|
|
|
|
|
|
//pTableLayout->addStretch();
|
|
|
|
|
|
|
|
|
|
|
|
// 设置容器的边框样式
|
|
|
|
|
|
pTableContainer->setStyleSheet("border: 1px solid #d3d3d3;");
|
|
|
|
|
|
|
|
|
|
|
|
pMainLayout->addWidget(pTableContainer);
|
|
|
|
|
|
|
|
|
|
|
|
// 5. 按钮区域
|
|
|
|
|
|
QHBoxLayout* pButtonLayout = new QHBoxLayout();
|
|
|
|
|
|
m_pOkButton = new QPushButton(tr("OK"), this);
|
|
|
|
|
|
m_pCancelButton = new QPushButton(tr("Cancel"), this);
|
|
|
|
|
|
|
|
|
|
|
|
pButtonLayout->addStretch();
|
|
|
|
|
|
pButtonLayout->addWidget(m_pOkButton);
|
|
|
|
|
|
pButtonLayout->addWidget(m_pCancelButton);
|
|
|
|
|
|
pMainLayout->addLayout(pButtonLayout);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::initConnections()
|
|
|
|
|
|
{
|
|
|
|
|
|
connect(m_pOkButton, SIGNAL(clicked()), this, SLOT(onOkClicked()));
|
|
|
|
|
|
connect(m_pCancelButton, SIGNAL(clicked()), this, SLOT(onCancelClicked()));
|
|
|
|
|
|
|
|
|
|
|
|
connect(m_pLoadTxtButton, SIGNAL(clicked()), this, SLOT(onLoadTxtClicked()));
|
|
|
|
|
|
connect(m_pLoadExcelButton, SIGNAL(clicked()), this, SLOT(onLoadExcelClicked()));
|
|
|
|
|
|
connect(m_pBrowseButton, SIGNAL(clicked()), this, SLOT(onBrowseClicked()));
|
|
|
|
|
|
|
|
|
|
|
|
connect(m_pColumnTable, SIGNAL(cellClicked(int, int)), this, SLOT(onTableClicked(int, int)));
|
|
|
|
|
|
connect(m_pColumnTable, SIGNAL(cellChanged(int, int)), this, SLOT(onCellChanged(int, int)));
|
|
|
|
|
|
|
|
|
|
|
|
// 添加分隔符复选框的信号连接
|
|
|
|
|
|
connect(m_pSpaceCheck, SIGNAL(stateChanged(int)), this, SLOT(updateSeparators()));
|
|
|
|
|
|
connect(m_pTabCheck, SIGNAL(stateChanged(int)), this, SLOT(updateSeparators()));
|
|
|
|
|
|
connect(m_pOtherSeparatorEdit, SIGNAL(textChanged(QString)), this, SLOT(updateSeparators()));
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::initUnitMappings()
|
|
|
|
|
|
{
|
|
|
|
|
|
// 设置Type到单位选项的映射
|
|
|
|
|
|
m_typeToUnitOptions["X1"] = QStringList() << "cm" << "mm" << "m" << "0.1in" << "ft" << "mile";
|
|
|
|
|
|
m_typeToUnitOptions["Y1"] = QStringList() << "cm" << "mm" << "m" << "0.1in" << "ft" << "mile";
|
|
|
|
|
|
m_typeToUnitOptions["X2"] = QStringList() << "cm" << "mm" << "m" << "0.1in" << "ft" << "mile";
|
|
|
|
|
|
m_typeToUnitOptions["Y2"] = QStringList() << "cm" << "mm" << "m" << "0.1in" << "ft" << "mile";
|
|
|
|
|
|
m_typeToUnitOptions["Wf"] = QStringList() << "cm" << "mm" << "m" << "0.1in" << "ft" << "mile";
|
|
|
|
|
|
m_typeToUnitOptions["Fc"] = QStringList() << "md.ft" << "md.m" << "m^3";
|
|
|
|
|
|
m_typeToUnitOptions["o"] = QStringList(); // 空选项
|
|
|
|
|
|
m_typeToUnitOptions["UnDefined"] = QStringList(); // 空选项
|
|
|
|
|
|
|
|
|
|
|
|
// 设置Type到默认单位的映射
|
|
|
|
|
|
m_typeToDefaultUnit["X1"] = "m";
|
|
|
|
|
|
m_typeToDefaultUnit["Y1"] = "m";
|
|
|
|
|
|
m_typeToDefaultUnit["X2"] = "m";
|
|
|
|
|
|
m_typeToDefaultUnit["Y2"] = "m";
|
|
|
|
|
|
m_typeToDefaultUnit["Wf"] = "m";
|
|
|
|
|
|
m_typeToDefaultUnit["Fc"] = "md.m";
|
|
|
|
|
|
m_typeToDefaultUnit["o"] = ""; // 空
|
|
|
|
|
|
m_typeToDefaultUnit["UnDefined"] = ""; // 空
|
|
|
|
|
|
|
|
|
|
|
|
// 按顺序设置所有Type选项
|
|
|
|
|
|
m_allTypeOptions << "X1" << "Y1" << "X2" << "Y2" << "Fc" << "Wf" << "o" << "UnDefined";
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::setupTable()
|
|
|
|
|
|
{
|
|
|
|
|
|
// 设置表格为3行0列(只有表头行,没有数据列)
|
|
|
|
|
|
m_pColumnTable->setRowCount(3); // Column, Type, Unit
|
|
|
|
|
|
m_pColumnTable->setColumnCount(0); // 初始没有列
|
|
|
|
|
|
|
|
|
|
|
|
// 设置垂直表头
|
|
|
|
|
|
QStringList verticalHeaders;
|
|
|
|
|
|
verticalHeaders << "Column" << "Type" << "Unit";
|
|
|
|
|
|
m_pColumnTable->setVerticalHeaderLabels(verticalHeaders);
|
|
|
|
|
|
|
|
|
|
|
|
// 设置表头样式
|
|
|
|
|
|
QHeaderView* verticalHeader = m_pColumnTable->verticalHeader();
|
|
|
|
|
|
QHeaderView* horizontalHeader = m_pColumnTable->horizontalHeader();
|
|
|
|
|
|
verticalHeader->setVisible(true);
|
|
|
|
|
|
horizontalHeader->setVisible(false);
|
|
|
|
|
|
|
|
|
|
|
|
// 关键修复:确保在设置数据前应用尺寸
|
|
|
|
|
|
verticalHeader->setMinimumSectionSize(20); // 行高
|
|
|
|
|
|
horizontalHeader->setMinimumSectionSize(100); // 列宽
|
|
|
|
|
|
|
|
|
|
|
|
// 锁定尺寸策略
|
|
|
|
|
|
m_pColumnTable->verticalHeader()->setResizeMode(QHeaderView::Fixed);
|
|
|
|
|
|
m_pColumnTable->horizontalHeader()->setResizeMode(QHeaderView::Fixed);
|
|
|
|
|
|
|
|
|
|
|
|
m_pColumnTable->verticalHeader()->setDefaultAlignment(Qt::AlignCenter);
|
|
|
|
|
|
m_pColumnTable->horizontalHeader()->setDefaultAlignment(Qt::AlignCenter);
|
|
|
|
|
|
|
|
|
|
|
|
// 设置默认行高
|
|
|
|
|
|
//m_pColumnTable->verticalHeader()->setDefaultSectionSize(25);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::onLoadTxtClicked()
|
|
|
|
|
|
{
|
|
|
|
|
|
QString filePath = QFileDialog::getOpenFileName(
|
|
|
|
|
|
this,
|
|
|
|
|
|
tr("Open Text File"),
|
|
|
|
|
|
m_sLastOpenedFilePath,
|
|
|
|
|
|
tr("Text Files (*.txt);;All Files (*)")
|
|
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
|
|
if (filePath.isEmpty()) {
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 检查文件扩展名
|
|
|
|
|
|
if (!filePath.endsWith(".txt", Qt::CaseInsensitive)) {
|
|
|
|
|
|
QMessageBox::warning(this, tr("Error"),
|
|
|
|
|
|
tr("Please select a text file (.txt)"));
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
m_sLastOpenedFilePath = filePath;
|
|
|
|
|
|
m_pFilePathEdit->setText(filePath);
|
|
|
|
|
|
|
|
|
|
|
|
// 读取文件内容
|
|
|
|
|
|
QStringList lines = readFileContent(filePath);
|
|
|
|
|
|
if (lines.isEmpty()) {
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 解析内容
|
|
|
|
|
|
QRegExp separatorRegex = buildSeparatorRegex();
|
|
|
|
|
|
QList<QStringList> parsedData;
|
|
|
|
|
|
|
|
|
|
|
|
for (int i = 0; i < lines.size(); ++i) {
|
|
|
|
|
|
parsedData << lines[i].split(separatorRegex, QString::SkipEmptyParts);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 处理数据
|
|
|
|
|
|
clearDataRows();
|
|
|
|
|
|
setupTableColumns(parsedData.isEmpty() ? 0 : parsedData[0].size());
|
|
|
|
|
|
populateDataRows(parsedData);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::onLoadExcelClicked()
|
|
|
|
|
|
{
|
|
|
|
|
|
QString filePath = QFileDialog::getOpenFileName(
|
|
|
|
|
|
this,
|
|
|
|
|
|
tr("Open Excel File"),
|
|
|
|
|
|
m_sLastOpenedFilePath,
|
|
|
|
|
|
tr("Excel Files (*.xls *.xlsx);;All Files (*)")
|
|
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
|
|
if (filePath.isEmpty()) {
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 检查文件扩展名
|
|
|
|
|
|
if (!filePath.endsWith(".xls", Qt::CaseInsensitive) &&
|
|
|
|
|
|
!filePath.endsWith(".xlsx", Qt::CaseInsensitive)) {
|
|
|
|
|
|
QMessageBox::warning(this, tr("Error"),
|
|
|
|
|
|
tr("Please select an Excel file (.xls or .xlsx)"));
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
m_sLastOpenedFilePath = filePath;
|
|
|
|
|
|
m_pFilePathEdit->setText(filePath);
|
|
|
|
|
|
|
|
|
|
|
|
// 解析Excel数据
|
|
|
|
|
|
QList<QStringList> excelData = parseExcelData(filePath);
|
|
|
|
|
|
if (excelData.isEmpty()) {
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 处理数据
|
|
|
|
|
|
clearDataRows();
|
|
|
|
|
|
setupTableColumns(excelData.isEmpty() ? 0 : excelData[0].size());
|
|
|
|
|
|
populateDataRows(excelData);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::onBrowseClicked()
|
|
|
|
|
|
{
|
|
|
|
|
|
QString filePath = QFileDialog::getOpenFileName(
|
|
|
|
|
|
this,
|
|
|
|
|
|
tr("Open Text File"),
|
|
|
|
|
|
m_sLastOpenedFilePath,
|
|
|
|
|
|
tr("Text Files (*.txt);;All Files (*)")
|
|
|
|
|
|
);
|
|
|
|
|
|
|
|
|
|
|
|
if (filePath.isEmpty()) {
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 检查文件扩展名
|
|
|
|
|
|
if (!filePath.endsWith(".txt", Qt::CaseInsensitive)) {
|
|
|
|
|
|
QMessageBox::warning(this, tr("Error"),
|
|
|
|
|
|
tr("Please select a text file (.txt)"));
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
m_sLastOpenedFilePath = filePath;
|
|
|
|
|
|
m_pFilePathEdit->setText(filePath);
|
|
|
|
|
|
|
|
|
|
|
|
// 读取文件内容
|
|
|
|
|
|
QStringList lines = readFileContent(filePath);
|
|
|
|
|
|
if (lines.isEmpty()) {
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 解析内容
|
|
|
|
|
|
QRegExp separatorRegex = buildSeparatorRegex();
|
|
|
|
|
|
QList<QStringList> parsedData;
|
|
|
|
|
|
|
|
|
|
|
|
for (int i = 0; i < lines.size(); ++i) {
|
|
|
|
|
|
parsedData << lines[i].split(separatorRegex, QString::SkipEmptyParts);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 处理数据
|
|
|
|
|
|
clearDataRows();
|
|
|
|
|
|
setupTableColumns(parsedData.isEmpty() ? 0 : parsedData[0].size());
|
|
|
|
|
|
populateDataRows(parsedData);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::onTableClicked(int row, int col)
|
|
|
|
|
|
{
|
|
|
|
|
|
// 先检查是否有未关闭的下拉框,并保存值
|
|
|
|
|
|
closeOpenComboBox();
|
|
|
|
|
|
|
|
|
|
|
|
// 仅处理Type行(1)和Unit行(2)
|
|
|
|
|
|
if (row != 1 && row != 2) return;
|
|
|
|
|
|
|
|
|
|
|
|
// 获取当前单元格的文本
|
|
|
|
|
|
QTableWidgetItem* item = m_pColumnTable->item(row, col);
|
|
|
|
|
|
if (!item) return;
|
|
|
|
|
|
QString currentText = item->text();
|
|
|
|
|
|
|
|
|
|
|
|
// 移除可能已存在的单元格控件(确保是QComboBox类型)
|
|
|
|
|
|
QComboBox* existingCombo = qobject_cast<QComboBox*>(m_pColumnTable->cellWidget(row, col));
|
|
|
|
|
|
if (existingCombo) {
|
|
|
|
|
|
disconnect(existingCombo, 0, this, 0); // 断开原有信号连接
|
|
|
|
|
|
delete existingCombo;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 创建下拉框
|
|
|
|
|
|
QComboBox* comboBox = new QComboBox();
|
|
|
|
|
|
|
|
|
|
|
|
// 根据行设置不同的选项
|
|
|
|
|
|
if (row == 1) { // Type行
|
|
|
|
|
|
comboBox->addItems(m_allTypeOptions);
|
|
|
|
|
|
} else { // Unit行 - 根据Type动态生成选项
|
|
|
|
|
|
// 获取当前列的Type值
|
|
|
|
|
|
QTableWidgetItem* typeItem = m_pColumnTable->item(1, col);
|
|
|
|
|
|
QString typeValue = typeItem ? typeItem->text() : "UnDefined";
|
|
|
|
|
|
|
|
|
|
|
|
// 获取对应的单位选项列表
|
|
|
|
|
|
QStringList unitOptions = m_typeToUnitOptions.value(typeValue);
|
|
|
|
|
|
comboBox->addItems(unitOptions);
|
|
|
|
|
|
|
|
|
|
|
|
// 如果Unit为空,设置默认值
|
|
|
|
|
|
if (currentText.isEmpty()) {
|
|
|
|
|
|
QString defaultUnit = m_typeToDefaultUnit.value(typeValue);
|
|
|
|
|
|
int defaultIndex = comboBox->findText(defaultUnit);
|
|
|
|
|
|
if (defaultIndex >= 0) {
|
|
|
|
|
|
comboBox->setCurrentIndex(defaultIndex);
|
|
|
|
|
|
// 同时更新表格中的Unit值
|
|
|
|
|
|
item->setText(defaultUnit);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 设置当前选中项(兼容Qt 4)
|
|
|
|
|
|
int index = comboBox->findText(currentText);
|
|
|
|
|
|
if (index >= 0) {
|
|
|
|
|
|
comboBox->setCurrentIndex(index);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 设置样式并添加到单元格
|
|
|
|
|
|
comboBox->setStyleSheet("text-align: center;");
|
|
|
|
|
|
m_pColumnTable->setCellWidget(row, col, comboBox);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::onCellChanged(int row, int col)
|
|
|
|
|
|
{
|
|
|
|
|
|
// 仅处理Type行(1)的变更
|
|
|
|
|
|
if (row != 1) return;
|
|
|
|
|
|
|
|
|
|
|
|
// 获取新的Type值
|
|
|
|
|
|
QTableWidgetItem* typeItem = m_pColumnTable->item(1, col);
|
|
|
|
|
|
if (!typeItem) return;
|
|
|
|
|
|
QString newType = typeItem->text();
|
|
|
|
|
|
|
|
|
|
|
|
// 获取对应的默认Unit
|
|
|
|
|
|
QString defaultUnit = m_typeToDefaultUnit.value(newType, "");
|
|
|
|
|
|
|
|
|
|
|
|
// 更新Unit行
|
|
|
|
|
|
QTableWidgetItem* unitItem = m_pColumnTable->item(2, col);
|
|
|
|
|
|
if (unitItem) {
|
|
|
|
|
|
unitItem->setText(defaultUnit);
|
|
|
|
|
|
} else {
|
|
|
|
|
|
unitItem = new QTableWidgetItem(defaultUnit);
|
|
|
|
|
|
unitItem->setTextAlignment(Qt::AlignCenter);
|
|
|
|
|
|
m_pColumnTable->setItem(2, col, unitItem);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::closeOpenComboBox()
|
|
|
|
|
|
{
|
|
|
|
|
|
// 遍历所有单元格,关闭已打开的下拉框
|
|
|
|
|
|
for (int r = 0; r < m_pColumnTable->rowCount(); ++r) {
|
|
|
|
|
|
for (int c = 0; c < m_pColumnTable->columnCount(); ++c) {
|
|
|
|
|
|
QWidget* widget = m_pColumnTable->cellWidget(r, c);
|
|
|
|
|
|
if (widget && qobject_cast<QComboBox*>(widget)) {
|
|
|
|
|
|
QComboBox* comboBox = static_cast<QComboBox*>(widget);
|
|
|
|
|
|
QString selectedText = comboBox->currentText();
|
|
|
|
|
|
|
|
|
|
|
|
// 保存值到表格项
|
|
|
|
|
|
QTableWidgetItem* item = m_pColumnTable->item(r, c);
|
|
|
|
|
|
if (item) {
|
|
|
|
|
|
item->setText(selectedText);
|
|
|
|
|
|
} else {
|
|
|
|
|
|
item = new QTableWidgetItem(selectedText);
|
|
|
|
|
|
item->setTextAlignment(Qt::AlignCenter);
|
|
|
|
|
|
m_pColumnTable->setItem(r, c, item);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 移除下拉框
|
|
|
|
|
|
m_pColumnTable->setCellWidget(r, c, nullptr);
|
|
|
|
|
|
delete comboBox;
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::updateSeparators()
|
|
|
|
|
|
{
|
|
|
|
|
|
// 检查是否有文件加载
|
|
|
|
|
|
QString filePath = m_pFilePathEdit->text();
|
|
|
|
|
|
if (filePath.isEmpty()) {
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 重新加载文件以应用新的分隔符
|
|
|
|
|
|
//loadTextFile(filePath);
|
|
|
|
|
|
|
|
|
|
|
|
// 如果是文本文件,重新加载以应用新的分隔符
|
|
|
|
|
|
if (filePath.endsWith(".txt", Qt::CaseInsensitive)) {
|
|
|
|
|
|
// 读取文件内容
|
|
|
|
|
|
QStringList lines = readFileContent(filePath);
|
|
|
|
|
|
if (lines.isEmpty()) {
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 解析内容
|
|
|
|
|
|
QRegExp separatorRegex = buildSeparatorRegex();
|
|
|
|
|
|
QList<QStringList> parsedData;
|
|
|
|
|
|
|
|
|
|
|
|
for (int i = 0; i < lines.size(); ++i) {
|
|
|
|
|
|
parsedData << lines[i].split(separatorRegex, QString::SkipEmptyParts);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 处理数据
|
|
|
|
|
|
clearDataRows();
|
|
|
|
|
|
setupTableColumns(parsedData.isEmpty() ? 0 : parsedData[0].size());
|
|
|
|
|
|
populateDataRows(parsedData);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::onOkClicked()
|
|
|
|
|
|
{
|
|
|
|
|
|
|
|
|
|
|
|
QVector<DFNData> vecDatas;
|
|
|
|
|
|
|
|
|
|
|
|
// 检查是否有足够的数据行(至少4行:表头+1行数据)
|
|
|
|
|
|
if (m_pColumnTable->rowCount() < 4) {
|
|
|
|
|
|
QMessageBox::warning(this, tr("Error"), tr("No data rows found"));
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 检查列数是否足够
|
|
|
|
|
|
if (m_pColumnTable->columnCount() == 0) {
|
|
|
|
|
|
QMessageBox::warning(this, tr("Error"), tr("No columns defined"));
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 首先收集每列的类型和单位信息
|
|
|
|
|
|
QVector<QString> columnTypes;
|
|
|
|
|
|
|
|
|
|
|
|
for (int col = 0; col < m_pColumnTable->columnCount(); ++col) {
|
|
|
|
|
|
QTableWidgetItem* typeItem = m_pColumnTable->item(1, col);
|
|
|
|
|
|
|
|
|
|
|
|
QString type = typeItem ? typeItem->text() : "UnDefined";
|
|
|
|
|
|
|
|
|
|
|
|
columnTypes.append(type);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 检查是否设置了必需的列(X1, Y1, X2, Y2)
|
|
|
|
|
|
bool hasX1 = columnTypes.contains("X1");
|
|
|
|
|
|
bool hasY1 = columnTypes.contains("Y1");
|
|
|
|
|
|
bool hasX2 = columnTypes.contains("X2");
|
|
|
|
|
|
bool hasY2 = columnTypes.contains("Y2");
|
|
|
|
|
|
|
|
|
|
|
|
if (!hasX1 || !hasY1 || !hasX2 || !hasY2) {
|
|
|
|
|
|
QMessageBox::warning(this, tr("Error"),
|
|
|
|
|
|
tr("Required columns (X1, Y1, X2, Y2) are not all defined"));
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 从第4行开始读取数据(前3行是表头)
|
|
|
|
|
|
for (int row = 3; row < m_pColumnTable->rowCount(); ++row) {
|
|
|
|
|
|
DFNData dataRow;
|
|
|
|
|
|
|
|
|
|
|
|
// 检查是否定义了Fc、Wf、o列
|
|
|
|
|
|
bool hasFc = columnTypes.contains("Fc");
|
|
|
|
|
|
bool hasWf = columnTypes.contains("Wf");
|
|
|
|
|
|
bool hasO = columnTypes.contains("o");
|
|
|
|
|
|
|
|
|
|
|
|
// 定义默认值
|
|
|
|
|
|
const double defaultFc = 0.1;
|
|
|
|
|
|
const double defaultWf = 0.00328084;
|
|
|
|
|
|
const double defaultO = 10.0;
|
|
|
|
|
|
|
|
|
|
|
|
// 在循环内部处理
|
|
|
|
|
|
for (int col = 0; col < m_pColumnTable->columnCount(); ++col) {
|
|
|
|
|
|
QTableWidgetItem* item = m_pColumnTable->item(row, col);
|
|
|
|
|
|
QString value = item ? item->text() : "";
|
|
|
|
|
|
QString type = columnTypes[col];
|
|
|
|
|
|
|
|
|
|
|
|
bool ok;
|
|
|
|
|
|
double numValue = value.toDouble(&ok);
|
|
|
|
|
|
|
|
|
|
|
|
if (type == "X1") {
|
|
|
|
|
|
if (ok) dataRow.x1 = numValue;
|
|
|
|
|
|
}
|
|
|
|
|
|
else if (type == "Y1") {
|
|
|
|
|
|
if (ok) dataRow.y1 = numValue;
|
|
|
|
|
|
}
|
|
|
|
|
|
else if (type == "X2") {
|
|
|
|
|
|
if (ok) dataRow.x2 = numValue;
|
|
|
|
|
|
}
|
|
|
|
|
|
else if (type == "Y2") {
|
|
|
|
|
|
if (ok) dataRow.y2 = numValue;
|
|
|
|
|
|
}
|
|
|
|
|
|
else if (type == "Fc") {
|
|
|
|
|
|
if (ok) dataRow.fc = numValue;
|
|
|
|
|
|
}
|
|
|
|
|
|
else if (type == "Wf") {
|
|
|
|
|
|
if (ok) dataRow.wf = numValue;
|
|
|
|
|
|
}
|
|
|
|
|
|
else if (type == "o") {
|
|
|
|
|
|
if (ok) dataRow.o = numValue;
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 如果用户未分配该列,则填充默认值
|
|
|
|
|
|
if (!hasFc) dataRow.fc = defaultFc;
|
|
|
|
|
|
if (!hasWf) dataRow.wf = defaultWf;
|
|
|
|
|
|
if (!hasO) dataRow.o = defaultO;
|
|
|
|
|
|
|
|
|
|
|
|
vecDatas.append(dataRow);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 清空原来的DFN图元数据
|
|
|
|
|
|
if (!nmDataAnalyzeManager::getCurrentInstance()->getDFNFractureDataList().isEmpty()) {
|
|
|
|
|
|
nmGuiPlot* pCurPlot = nmDataAnalyzeManager::getCurrentInstance()->getPlot();
|
|
|
|
|
|
pCurPlot->deleteAllDFNPlots();
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 遍历vecDatas,将数据存入数据中心
|
|
|
|
|
|
foreach (const DFNData &data, vecDatas) {
|
|
|
|
|
|
nmDataFracture* pFractrue = nmDataAnalyzeManager::getCurrentInstance()->createFracture();
|
|
|
|
|
|
// 裂缝名称
|
|
|
|
|
|
pFractrue->setFractureName("DFN");
|
|
|
|
|
|
// 裂缝位置信息
|
|
|
|
|
|
QPointF pt1(data.x1,data.y1);
|
|
|
|
|
|
QPointF pt2(data.x2,data.y2);
|
|
|
|
|
|
QVector<QPointF> vecPts;
|
|
|
|
|
|
vecPts.append(pt1);
|
|
|
|
|
|
vecPts.append(pt2);
|
|
|
|
|
|
pFractrue->setFracturePoints(vecPts);
|
|
|
|
|
|
// 裂缝流动类型,默认为无限导流
|
|
|
|
|
|
nmDataAttribute tempAttr = pFractrue->getFractureFlowModel();
|
|
|
|
|
|
tempAttr.setValue(tr("Finite Conductivity"));
|
|
|
|
|
|
pFractrue->setFractureFlowModel(tempAttr);
|
|
|
|
|
|
// 裂缝导流能力
|
|
|
|
|
|
tempAttr = pFractrue->getFractureDfc();
|
|
|
|
|
|
tempAttr.setValue(data.fc);
|
|
|
|
|
|
pFractrue->setFractureDfc(tempAttr);
|
|
|
|
|
|
// TODO:裂缝宽度
|
|
|
|
|
|
// TODO:裂缝孔隙度
|
|
|
|
|
|
|
|
|
|
|
|
// 新增:裂缝类型,区分普通裂缝和DFN生成的裂缝
|
|
|
|
|
|
tempAttr = pFractrue->getFractureType();
|
|
|
|
|
|
tempAttr.setValue(tr("DFN"));
|
|
|
|
|
|
pFractrue->setFractureType(tempAttr);
|
|
|
|
|
|
|
|
|
|
|
|
nmGuiPlot* pCurPlot = nmDataAnalyzeManager::getCurrentInstance()->getPlot();
|
|
|
|
|
|
if (pCurPlot != nullptr) {
|
|
|
|
|
|
// 添加一条裂缝
|
|
|
|
|
|
QString sName = pFractrue->getFractureName();
|
|
|
|
|
|
QVector<QPointF> vecFracurePts =pFractrue->getFracturePoints();
|
|
|
|
|
|
|
|
|
|
|
|
// 转换坐标
|
|
|
|
|
|
QVector<QPointF> vecConvertPoints = pCurPlot->m_pPlot->getPosForValue(vecFracurePts);
|
|
|
|
|
|
|
|
|
|
|
|
nmObjLineCrack* pFractrePlot = (nmObjLineCrack*)pCurPlot->appendOneObj(NMOT_Line_Fracture, sName,vecConvertPoints);
|
|
|
|
|
|
if(pFractrePlot == nullptr) {
|
|
|
|
|
|
continue;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 绑定边界数据到图元对象上
|
|
|
|
|
|
pFractrePlot->setFractureData(pFractrue);
|
|
|
|
|
|
|
|
|
|
|
|
pFractrePlot->setPen(QPen(QBrush(QColor("#00bfff")), 0.4f, Qt::SolidLine));
|
|
|
|
|
|
|
|
|
|
|
|
pFractrePlot->setLockForDFN();
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 如果一切正常,接受对话框
|
|
|
|
|
|
this->accept();
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void nmWxDFNLoadFromFile::onCancelClicked()
|
|
|
|
|
|
{
|
|
|
|
|
|
this->reject();
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// 清除数据行(保留表头行)
|
|
|
|
|
|
void nmWxDFNLoadFromFile::clearDataRows()
|
|
|
|
|
|
{
|
|
|
|
|
|
while (m_pColumnTable->rowCount() > 3) {
|
|
|
|
|
|
m_pColumnTable->removeRow(3);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 构建分隔符正则表达式
|
|
|
|
|
|
QRegExp nmWxDFNLoadFromFile::buildSeparatorRegex() const
|
|
|
|
|
|
{
|
|
|
|
|
|
QStringList separators;
|
|
|
|
|
|
if (m_pSpaceCheck->isChecked()) {
|
|
|
|
|
|
separators << " ";
|
|
|
|
|
|
}
|
|
|
|
|
|
if (m_pTabCheck->isChecked()) {
|
|
|
|
|
|
separators << "\\t";
|
|
|
|
|
|
}
|
|
|
|
|
|
if (!m_pOtherSeparatorEdit->text().isEmpty()) {
|
|
|
|
|
|
separators << QRegExp::escape(m_pOtherSeparatorEdit->text());
|
|
|
|
|
|
}
|
|
|
|
|
|
return QRegExp(QString("[%1]+").arg(separators.join("")));
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 设置表格列
|
|
|
|
|
|
void nmWxDFNLoadFromFile::setupTableColumns(int columnCount)
|
|
|
|
|
|
{
|
|
|
|
|
|
m_pColumnTable->setColumnCount(columnCount);
|
|
|
|
|
|
|
|
|
|
|
|
for (int col = 0; col < columnCount; ++col) {
|
|
|
|
|
|
// Column行
|
|
|
|
|
|
QTableWidgetItem* colItem = new QTableWidgetItem(QString("Column %1").arg(col + 1));
|
|
|
|
|
|
colItem->setFlags((colItem->flags() & ~Qt::ItemIsEditable) | Qt::ItemIsSelectable | Qt::ItemIsEnabled);
|
|
|
|
|
|
m_pColumnTable->setItem(0, col, colItem);
|
|
|
|
|
|
|
|
|
|
|
|
// Type行
|
|
|
|
|
|
QString defaultType = (col < m_allTypeOptions.size()) ? m_allTypeOptions[col] : "UnDefined";
|
|
|
|
|
|
m_pColumnTable->setItem(1, col, new QTableWidgetItem(defaultType));
|
|
|
|
|
|
|
|
|
|
|
|
// Unit行
|
|
|
|
|
|
QString defaultUnit = m_typeToDefaultUnit.value(defaultType, "");
|
|
|
|
|
|
m_pColumnTable->setItem(2, col, new QTableWidgetItem(defaultUnit));
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 填充数据行
|
|
|
|
|
|
void nmWxDFNLoadFromFile::populateDataRows(const QList<QStringList>& dataLines)
|
|
|
|
|
|
{
|
|
|
|
|
|
for (int row = 0; row < dataLines.size(); ++row) {
|
|
|
|
|
|
const QStringList& values = dataLines[row];
|
|
|
|
|
|
m_pColumnTable->insertRow(row + 3);
|
|
|
|
|
|
|
|
|
|
|
|
for (int col = 0; col < values.size(); ++col) {
|
|
|
|
|
|
QTableWidgetItem* item = new QTableWidgetItem(values[col]);
|
|
|
|
|
|
item->setFlags((item->flags() & ~Qt::ItemIsEditable) | Qt::ItemIsSelectable | Qt::ItemIsEnabled);
|
|
|
|
|
|
m_pColumnTable->setItem(row + 3, col, item);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 读取文本文件内容
|
|
|
|
|
|
QStringList nmWxDFNLoadFromFile::readFileContent(const QString& filePath)
|
|
|
|
|
|
{
|
|
|
|
|
|
QStringList lines;
|
|
|
|
|
|
QFile file(filePath);
|
|
|
|
|
|
if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) {
|
|
|
|
|
|
QMessageBox::warning(this, tr("Error"), tr("Could not open file"));
|
|
|
|
|
|
return lines;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
QTextStream in(&file);
|
|
|
|
|
|
while (!in.atEnd()) {
|
|
|
|
|
|
QString line = in.readLine().trimmed();
|
|
|
|
|
|
if (!line.isEmpty()) {
|
|
|
|
|
|
lines << line;
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
file.close();
|
|
|
|
|
|
return lines;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 解析Excel数据
|
|
|
|
|
|
QList<QStringList> nmWxDFNLoadFromFile::parseExcelData(QString filePath)
|
|
|
|
|
|
{
|
|
|
|
|
|
QList<QStringList> result;
|
|
|
|
|
|
ExcelUtils excelUtils;
|
|
|
|
|
|
QString log;
|
|
|
|
|
|
VVecVariant data;
|
|
|
|
|
|
|
|
|
|
|
|
if (!excelUtils.loadExcel(data, NULL, filePath, log)) {
|
|
|
|
|
|
QMessageBox::warning(this, tr("Import Error"), tr("Failed to import Excel : \n") + log);
|
|
|
|
|
|
return result;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 转换VVecVariant到QList<QStringList>
|
|
|
|
|
|
for (int i = 0; i < data.size(); ++i) {
|
|
|
|
|
|
QStringList row;
|
|
|
|
|
|
for (int j = 0; j < data[i].size(); ++j) {
|
|
|
|
|
|
row << data[i][j].toString();
|
|
|
|
|
|
}
|
|
|
|
|
|
result << row;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
return result;
|
|
|
|
|
|
}
|