DYTSrouce/src/ui/WorkSpace/AddSurfaceFileDlg.cpp
2025-11-02 11:36:10 +08:00

457 lines
17 KiB
C++

#include "AddSurfaceFileDlg.h"
#include "ui_AddSurfaceFileDlg.h"
#include "workspace/WorkSpaceManager.h"
#include "workspace/WorkSpace.h"
#include "common/SpdLogger.h"
#include <QFileDialog>
#include <QFileInfo>
#include <QColorDialog>
#include <QMessageBox>
#include <QListWidgetItem>
#include <QStandardPaths>
#include <QDir>
AddSurfaceFileDlg::AddSurfaceFileDlg(QWidget *parent)
: BaseAddFileDlg(FileEntryType::Surface, parent)
, ui(new Ui::AddSurfaceFileDlg)
, currentSurfaceIndex_(-1)
, selectedColor_(Qt::blue)
{
SetupUI(ui);
SetTitle(getDialogTitle());
setupConnections();
// Initialize chart properties with default values
chartProperties_.xCount = 7;
chartProperties_.yCount = 0;
chartProperties_.zCount = 7;
chartProperties_.xMin = 0.0;
chartProperties_.xMax = 14000;
chartProperties_.yMin = 0.0;
chartProperties_.yMax = 0.0;
chartProperties_.zMin = 0.0;
chartProperties_.zMax = 70;
chartProperties_.timeParam = 0.0;
chartProperties_.xTitle = "Y Axis";
chartProperties_.yTitle = "Z Axis";
chartProperties_.zTitle = "X Axis";
// Set default UI values
ui->xCountSpinBox->setValue(chartProperties_.xCount);
ui->yCountSpinBox->setValue(chartProperties_.yCount);
ui->zCountSpinBox->setValue(chartProperties_.zCount);
ui->xMinSpinBox->setValue(chartProperties_.xMin);
ui->xMaxSpinBox->setValue(chartProperties_.xMax);
ui->yMinSpinBox->setValue(chartProperties_.yMin);
ui->yMaxSpinBox->setValue(chartProperties_.yMax);
ui->zMinSpinBox->setValue(chartProperties_.zMin);
ui->zMaxSpinBox->setValue(chartProperties_.zMax);
ui->timeParamSpinBox->setValue(chartProperties_.timeParam);
ui->xTitleLineEdit->setText(chartProperties_.xTitle);
ui->yTitleLineEdit->setText(chartProperties_.yTitle);
ui->zTitleLineEdit->setText(chartProperties_.zTitle);
// Initialize color preview
updateColorPreview(ui->surfaceColorButton, selectedColor_);
// Clear surface properties initially
clearSurfaceProperties();
ui->dataFormatGroupBox->setVisible(false);
ui->comboBox_x->setCurrentText("y");
ui->comboBox_y->setCurrentText("z");
ui->comboBox_z->setCurrentText("x");
}
AddSurfaceFileDlg::~AddSurfaceFileDlg()
{
delete ui;
}
void AddSurfaceFileDlg::setupConnections()
{
// File selection connections
connect(ui->browseButton, &QPushButton::clicked, this, &AddSurfaceFileDlg::onSelectFile);
connect(ui->filePathLineEdit, &QLineEdit::textChanged, this, &AddSurfaceFileDlg::onFilePathChanged);
// Surface management connections
connect(ui->surfaceColorButton, &QPushButton::clicked, this, &AddSurfaceFileDlg::onSurfaceColorButtonClicked);
connect(ui->addSurfaceButton, &QPushButton::clicked, this, &AddSurfaceFileDlg::onAddSurfaceClicked);
connect(ui->removeSurfaceButton, &QPushButton::clicked, this, &AddSurfaceFileDlg::onRemoveSurfaceClicked);
connect(ui->surfaceListWidget, &QListWidget::itemClicked, this, &AddSurfaceFileDlg::onSurfaceListItemClicked);
connect(ui->surfaceListWidget, &QListWidget::itemSelectionChanged, this, &AddSurfaceFileDlg::onSurfaceSelectionChanged);
// Surface properties connections
connect(ui->surfaceNameLineEdit, &QLineEdit::textChanged, this, &AddSurfaceFileDlg::onSurfaceNameChanged);
connect(ui->surfaceStartSpinBox, QOverload<int>::of(&QSpinBox::valueChanged), this, &AddSurfaceFileDlg::onSurfaceDataChanged);
connect(ui->surfaceStopSpinBox, QOverload<int>::of(&QSpinBox::valueChanged), this, &AddSurfaceFileDlg::onSurfaceDataChanged);
connect(ui->comboBox_x, QOverload<const QString &>::of(&QComboBox::currentTextChanged), this, &AddSurfaceFileDlg::onSurfaceDataChanged);
connect(ui->comboBox_y, QOverload<const QString &>::of(&QComboBox::currentTextChanged), this, &AddSurfaceFileDlg::onSurfaceDataChanged);
connect(ui->comboBox_z, QOverload<const QString &>::of(&QComboBox::currentTextChanged), this, &AddSurfaceFileDlg::onSurfaceDataChanged);
// Chart properties connections (save to member variables when changed)
connect(ui->xCountSpinBox, QOverload<int>::of(&QSpinBox::valueChanged), [this](int value) { chartProperties_.xCount = value; });
connect(ui->yCountSpinBox, QOverload<int>::of(&QSpinBox::valueChanged), [this](int value) { chartProperties_.yCount = value; });
connect(ui->zCountSpinBox, QOverload<int>::of(&QSpinBox::valueChanged), [this](int value) { chartProperties_.zCount = value; });
connect(ui->xMinSpinBox, QOverload<double>::of(&QDoubleSpinBox::valueChanged), [this](double value) { chartProperties_.xMin = value; });
connect(ui->xMaxSpinBox, QOverload<double>::of(&QDoubleSpinBox::valueChanged), [this](double value) { chartProperties_.xMax = value; });
connect(ui->yMinSpinBox, QOverload<double>::of(&QDoubleSpinBox::valueChanged), [this](double value) { chartProperties_.yMin = value; });
connect(ui->yMaxSpinBox, QOverload<double>::of(&QDoubleSpinBox::valueChanged), [this](double value) { chartProperties_.yMax = value; });
connect(ui->zMinSpinBox, QOverload<double>::of(&QDoubleSpinBox::valueChanged), [this](double value) { chartProperties_.zMin = value; });
connect(ui->zMaxSpinBox, QOverload<double>::of(&QDoubleSpinBox::valueChanged), [this](double value) { chartProperties_.zMax = value; });
connect(ui->timeParamSpinBox, QOverload<int>::of(&QSpinBox::valueChanged), [this](int value) { chartProperties_.timeParam = value; });
connect(ui->xTitleLineEdit, &QLineEdit::textChanged, [this](const QString& text) { chartProperties_.xTitle = text; });
connect(ui->yTitleLineEdit, &QLineEdit::textChanged, [this](const QString& text) { chartProperties_.yTitle = text; });
connect(ui->zTitleLineEdit, &QLineEdit::textChanged, [this](const QString& text) { chartProperties_.zTitle = text; });
// Dialog button connections
connect(ui->buttonBox, &QDialogButtonBox::accepted, this, &AddSurfaceFileDlg::accept);
connect(ui->buttonBox, &QDialogButtonBox::rejected, this, &AddSurfaceFileDlg::reject);
}
QString AddSurfaceFileDlg::getFileFilter() const
{
return tr("Surface Data Files (*.txt *.dat *.csv);;All Files (*.*)");
}
QString AddSurfaceFileDlg::getDialogTitle() const
{
return tr("Add Surface Dialog");
}
bool AddSurfaceFileDlg::validateSpecificParams()
{
if (surfaces_.isEmpty()) {
QMessageBox::warning(this, tr("Warning"), tr("Please add at least one surface."));
return false;
}
// Validate chart properties
if (chartProperties_.xTitle.isEmpty() || chartProperties_.yTitle.isEmpty() || chartProperties_.zTitle.isEmpty()) {
QMessageBox::warning(this, tr("Warning"), tr("Please fill in all axis titles."));
return false;
}
return true;
}
void AddSurfaceFileDlg::updateFileInfo(const QString& filePath)
{
ui->filePathLineEdit->setText(filePath);
}
void AddSurfaceFileDlg::onSelectFile()
{
QString documentsPath = QStandardPaths::writableLocation(QStandardPaths::DocumentsLocation);
QString fileName = QFileDialog::getOpenFileName(this, getDialogTitle(), documentsPath, getFileFilter());
if (!fileName.isEmpty()) {
updateFileInfo(fileName);
}
}
void AddSurfaceFileDlg::onFilePathChanged()
{
// File path changed, could update preview or validation here
}
void AddSurfaceFileDlg::onSurfaceColorButtonClicked()
{
QColor color = QColorDialog::getColor(selectedColor_, this, tr("Select Surface Color"));
if (color.isValid()) {
selectedColor_ = color;
updateColorPreview(ui->surfaceColorButton, selectedColor_);
// Update current surface color if one is selected
if (currentSurfaceIndex_ >= 0 && currentSurfaceIndex_ < surfaces_.size()) {
surfaces_[currentSurfaceIndex_].color = selectedColor_;
// Update list item color
QListWidgetItem* item = ui->surfaceListWidget->item(currentSurfaceIndex_);
if (item) {
QPixmap pixmap(16, 16);
pixmap.fill(selectedColor_);
item->setIcon(QIcon(pixmap));
}
}
}
}
void AddSurfaceFileDlg::onAddSurfaceClicked()
{
FileEntrySurface::SurfaceProperty surface;
surface.name = generateSurfaceName();
surface.color = generateSurfaceColor();
surface.start = 0;
surface.stop = 0;
surface.x = ui->comboBox_x->currentText();
surface.y = ui->comboBox_y->currentText();
surface.z = ui->comboBox_z->currentText();
surfaces_.append(surface);
addSurfaceToList(surface);
// Select the newly added surface
ui->surfaceListWidget->setCurrentRow(surfaces_.size() - 1);
}
void AddSurfaceFileDlg::onRemoveSurfaceClicked()
{
int currentRow = ui->surfaceListWidget->currentRow();
if (currentRow >= 0 && currentRow < surfaces_.size()) {
surfaces_.removeAt(currentRow);
delete ui->surfaceListWidget->takeItem(currentRow);
// Update current surface index
if (currentRow < surfaces_.size()) {
ui->surfaceListWidget->setCurrentRow(currentRow);
} else if (surfaces_.size() > 0) {
ui->surfaceListWidget->setCurrentRow(surfaces_.size() - 1);
} else {
currentSurfaceIndex_ = -1;
clearSurfaceProperties();
}
}
}
void AddSurfaceFileDlg::onSurfaceListItemClicked(QListWidgetItem* item)
{
int row = ui->surfaceListWidget->row(item);
if (row >= 0 && row < surfaces_.size()) {
saveSurfaceProperties(); // Save current surface properties
currentSurfaceIndex_ = row;
updateSurfaceProperties(); // Load new surface properties
}
}
void AddSurfaceFileDlg::onSurfaceSelectionChanged()
{
int currentRow = ui->surfaceListWidget->currentRow();
if (currentRow >= 0 && currentRow < surfaces_.size()) {
saveSurfaceProperties(); // Save current surface properties
currentSurfaceIndex_ = currentRow;
updateSurfaceProperties(); // Load new surface properties
} else {
currentSurfaceIndex_ = -1;
clearSurfaceProperties();
}
}
void AddSurfaceFileDlg::onSurfaceNameChanged()
{
if (currentSurfaceIndex_ >= 0 && currentSurfaceIndex_ < surfaces_.size()) {
QString newName = ui->surfaceNameLineEdit->text();
surfaces_[currentSurfaceIndex_].name = newName;
// Update list item text
QListWidgetItem* item = ui->surfaceListWidget->item(currentSurfaceIndex_);
if (item) {
item->setText(newName);
}
}
}
void AddSurfaceFileDlg::onSurfaceDataChanged()
{
if (currentSurfaceIndex_ >= 0 && currentSurfaceIndex_ < surfaces_.size()) {
surfaces_[currentSurfaceIndex_].start = ui->surfaceStartSpinBox->value();
surfaces_[currentSurfaceIndex_].stop = ui->surfaceStopSpinBox->value();
surfaces_[currentSurfaceIndex_].x = ui->comboBox_x->currentText();
surfaces_[currentSurfaceIndex_].y = ui->comboBox_y->currentText();
surfaces_[currentSurfaceIndex_].z = ui->comboBox_z->currentText();
}
}
void AddSurfaceFileDlg::updateColorPreview(QPushButton* button, const QColor& color)
{
if (button && color.isValid()) {
QString styleSheet = QString("QPushButton { background-color: %1; }").arg(color.name());
button->setStyleSheet(styleSheet);
}
}
void AddSurfaceFileDlg::addSurfaceToList(const FileEntrySurface::SurfaceProperty& surface)
{
QListWidgetItem* item = new QListWidgetItem(surface.name);
// Set color icon
QPixmap pixmap(16, 16);
pixmap.fill(surface.color);
item->setIcon(QIcon(pixmap));
ui->surfaceListWidget->addItem(item);
}
void AddSurfaceFileDlg::updateSurfaceProperties()
{
if (currentSurfaceIndex_ >= 0 && currentSurfaceIndex_ < surfaces_.size()) {
const auto& surface = surfaces_[currentSurfaceIndex_];
ui->surfaceNameLineEdit->blockSignals(true);
ui->surfaceNameLineEdit->setText(surface.name);
ui->surfaceNameLineEdit->blockSignals(false);
ui->surfaceStartSpinBox->blockSignals(true);
ui->surfaceStartSpinBox->setValue(surface.start);
ui->surfaceStartSpinBox->blockSignals(false);
ui->surfaceStopSpinBox->blockSignals(true);
ui->surfaceStopSpinBox->setValue(surface.stop);
ui->surfaceStopSpinBox->blockSignals(false);
ui->comboBox_x->blockSignals(true);
ui->comboBox_x->setCurrentText(surface.x);
ui->comboBox_x->blockSignals(false);
ui->comboBox_y->blockSignals(true);
ui->comboBox_y->setCurrentText(surface.y);
ui->comboBox_y->blockSignals(false);
ui->comboBox_z->blockSignals(true);
ui->comboBox_z->setCurrentText(surface.z);
ui->comboBox_z->blockSignals(false);
selectedColor_ = surface.color;
updateColorPreview(ui->surfaceColorButton, selectedColor_);
ui->surfacePropertiesGroupBox->setEnabled(true);
} else {
clearSurfaceProperties();
}
}
void AddSurfaceFileDlg::saveSurfaceProperties()
{
if (currentSurfaceIndex_ >= 0 && currentSurfaceIndex_ < surfaces_.size()) {
surfaces_[currentSurfaceIndex_].name = ui->surfaceNameLineEdit->text();
surfaces_[currentSurfaceIndex_].start = ui->surfaceStartSpinBox->value();
surfaces_[currentSurfaceIndex_].stop = ui->surfaceStopSpinBox->value();
surfaces_[currentSurfaceIndex_].color = selectedColor_;
}
}
void AddSurfaceFileDlg::clearSurfaceProperties()
{
ui->surfaceNameLineEdit->clear();
ui->surfaceStartSpinBox->setValue(0);
ui->surfaceStopSpinBox->setValue(0);
selectedColor_ = QColor(61, 38, 168);
updateColorPreview(ui->surfaceColorButton, selectedColor_);
ui->surfacePropertiesGroupBox->setEnabled(false);
}
QString AddSurfaceFileDlg::generateSurfaceName() const
{
return QString("Surface %1").arg(surfaces_.size() + 1);
}
QColor AddSurfaceFileDlg::generateSurfaceColor() const
{
// Generate different colors for each surface
static const QColor colors[] = { QColor(61, 38, 168),
Qt::blue, Qt::red, Qt::green, Qt::magenta, Qt::cyan, Qt::yellow,
Qt::darkBlue, Qt::darkRed, Qt::darkGreen, Qt::darkMagenta, Qt::darkCyan, Qt::darkYellow
};
int colorIndex = surfaces_.size() % (sizeof(colors) / sizeof(colors[0]));
return colors[colorIndex];
}
AddSurfaceFileDlg::SurfaceParams AddSurfaceFileDlg::GetSurfaceParams() const
{
SurfaceParams params;
params.xColumn = ui->xColumnSpinBox->value();
params.yColumn = ui->yColumnSpinBox->value();
params.zColumn = ui->zColumnSpinBox->value();
params.separator = ui->separatorLineEdit->text();
params.xGridSize = ui->xGridSizeSpinBox->value();
params.yGridSize = ui->yGridSizeSpinBox->value();
params.hasHeader = ui->hasHeaderCheckBox->isChecked();
return params;
}
QString AddSurfaceFileDlg::GetSelectedFilePath() const
{
return ui->filePathLineEdit->text();
}
QString AddSurfaceFileDlg::GetDescription() const
{
return getDescription(); // 使用基类的getDescription方法
}
void AddSurfaceFileDlg::accept()
{
QString sName = ui->NameLineEdit->text();
// Validate table-specific parameters
if (sName.isEmpty()) {
QMessageBox::warning(this, tr("Warning"), tr("Please enter a Surface name."));
return;
}
if (!validateSpecificParams()) {
return;
}
// Save current surface properties before creating FileEntry
saveSurfaceProperties();
// Create FileEntrySurface
auto fileEntry = std::dynamic_pointer_cast<FileEntrySurface>(CreateFileEntrySurface(GetSelectedFilePath()));
if (!fileEntry) {
QMessageBox::critical(this, tr("Error"), tr("Failed to create surface file entry."));
return;
}
fileEntry->SetName(sName);
// Set chart properties
fileEntry->SetChartProperties(chartProperties_);
// Set surface properties
for (const auto& surface : surfaces_) {
fileEntry->AddSurfaceProperty(surface);
}
// Set description
//fileEntry->SetDescription(GetDescription());
// Add to workspace
WorkSpace* workspace = WorkSpaceManager::Get().GetCurrent();
if (!workspace) {
QMessageBox::critical(this, tr("Error"), tr("Unable to get current workspace"));
return;
}
// Add FileEntrySurface to workspace using SetFileEntry method
auto result = workspace->SetFileEntry(fileEntry);
if (result != WorkSpace::FileEntryResult::Ok) {
QString errorMsg;
switch (result) {
case WorkSpace::FileEntryResult::LimitExceeded:
errorMsg = tr("Surface file count has reached the limit (9 files)");
break;
case WorkSpace::FileEntryResult::Duplicate:
errorMsg = tr("File already exists");
break;
case WorkSpace::FileEntryResult::CopyFailed:
errorMsg = tr("File copy failed");
break;
case WorkSpace::FileEntryResult::InvalidFile:
errorMsg = tr("Invalid file");
break;
default:
errorMsg = tr("Failed to add file");
break;
}
QMessageBox::warning(this, tr("Error"), errorMsg);
return;
}
LOG_INFO("Added surface file to workspace: {}", GetSelectedFilePath().toUtf8().constData());
QDialog::accept();
}