#include "mainwindow.h"
#include "../model/componentmodel.h"
#include "../model/perechentablemodel.h"
#include "../model/specificationpcbtablemodel.h"
#include "../model/specificationtablemodel.h"
#include "../model/vedomosttablemodel.h"
#include "../model/simplelisttablemodel.h"
#include "../model/titleinscriptionsmodel.h"
#include "../model/projectparamtablemodel.h"
#include "../controller/altiumparser.h"
#include "../controller/maincontroller.h"
#include "../controller/pdfcontroller.h"
#include "projectsettingsdialog.h"
#include <QFileDialog>
#include <QMessageBox>
#include <QCloseEvent>
#include <QFileInfo>
#include <QDebug> // Added for qDebug
#include <QMap>
#include <QDesktopServices>
#include <QUrl>
#include <QCoreApplication>
#include <QIcon>

MainWindow::MainWindow(MainController *controller, QWidget *parent): QMainWindow(parent), m_controller(controller), m_isParsing(false){
  setUp();
  updateWindowTitle();
  
  // Устанавливаем иконку окна
  setWindowIcon(QIcon(":/assets/icon2.png"));
  
  // Отключаем все элементы интерфейса кроме создания/открытия проекта
  disableInterfaceExceptProjectActions();
  
  show();
}

MainWindow::~MainWindow() {}

void MainWindow::setUp(){
    setWidgets();
    setUpLayout();
    setUpConnections();
}


void MainWindow::setWidgets(){
    m_editWidget = new EditPDFWidget(m_controller, this);
    m_pdfWidget = new PreviewPdfWidget(this);
    m_dataView = new ImportedDataView(m_controller->componentTableModel(), m_controller->projectParamTableModel(), m_controller->pcbMaterialModel(), this);
    
    // Передаем MainController в PreviewPdfWidget
    m_pdfWidget->setMainController(m_controller);
    
    // Подключаем сигнал изменения типа документа от EditPDFWidget к PreviewPdfWidget
    connect(m_editWidget, &EditPDFWidget::documentTypeChanged,
            m_pdfWidget, &PreviewPdfWidget::onDocumentTypeChanged);
    
    // Передаем данные в EditPDFWidget
    qDebug() << "MainWindow::setWidgets: Передаем ComponentTableModel:" << m_controller->componentTableModel();
    qDebug() << "MainWindow::setWidgets: Компонентов в модели:" << m_controller->componentTableModel()->getComponents().size();
    m_editWidget->setData(m_controller->componentTableModel(), m_controller->projectParamTableModel());
    
    // Подключаем сигнал изменения варианта от ComponentsPreview после создания m_dataView
    if (m_dataView && m_dataView->getComponentsPreview()) {
        connect(m_dataView->getComponentsPreview(), &ComponentsPreview::variantChanged,
                [this](const QString &variant) {
                    qDebug() << "MainWindow: Получен сигнал variantChanged:" << variant;
                    // Обновляем вариант в настройках проекта
                    m_controller->projectSettingsModel()->setCurrentVariant(variant);
                    // Обновляем текущий вариант в контроллере
                    m_controller->setCurrentVariant(variant);
                    // Перезагружаем компоненты с новым вариантом
                    m_controller->loadComponentsFromDatabase();
                    // Сохраняем настройки в базу данных
                    m_controller->saveProjectSettingsToDatabase();
                });
    }
    
    // Инициализация элементов для асинхронного парсинга
    m_progressBar = new QProgressBar(this);
    m_progressBar->setVisible(false);
    m_progressBar->setRange(0, 100);
    m_progressBar->setValue(0);
    
    m_cancelParsingAction = new QAction(tr("Отменить парсинг"), this);
    m_cancelParsingAction->setVisible(false);
}

void MainWindow::setUpLayout(){
    //Меню

    m_centralWidget = new QWidget(this);
    QHBoxLayout* mainLayout = new QHBoxLayout(m_centralWidget);
    mainLayout->addWidget(m_editWidget);

    setCentralWidget(m_centralWidget);

    // Устанавливаем менюбар
    m_menuBar = new QMenuBar(this);
    setMenuBar(m_menuBar);
    m_fileMenu = m_menuBar->addMenu(tr("&Файл"));
    QAction* undoAction = m_fileMenu->addAction("Отменить", this, &MainWindow::onUndo, QKeySequence::Undo);
    QAction* redoAction = m_fileMenu->addAction("Повторить", this, &MainWindow::onRedo, QKeySequence::Redo);
    undoAction->setEnabled(false);
    redoAction->setEnabled(false);
    m_fileMenu->addSeparator();
    m_fileMenu->addAction("&Новый проект", this, &MainWindow::onFileNew, QKeySequence::New);
    m_fileMenu->addAction("&Открыть проект", this, &MainWindow::onFileOpen, QKeySequence::Open);
    m_fileMenu->addAction("&Сохранить проект", this, &MainWindow::onFileSave, QKeySequence::Save);
    m_fileMenu->addAction("Сохранить &как...", this, &MainWindow::onFileSaveAs, QKeySequence::SaveAs);
    m_fileMenu->addSeparator();
    m_fileMenu->addAction("&Импорт Altium файла", this, &MainWindow::onFileImportAltium);
    m_fileMenu->addSeparator();
    m_fileMenu->addAction("&Настройки проекта", this, &MainWindow::onProjectSettings);
    m_fileMenu->addSeparator();
    m_fileMenu->addAction("&Выход", this, &MainWindow::onFileExit, QKeySequence::Quit);
    m_exportMenu = m_menuBar->addMenu(tr("&Экспорт"));
    // Подменю для экспорта в PDF
    QMenu* pdfMenu = m_exportMenu->addMenu(tr("Экспорт в &PDF"));
    pdfMenu->addAction("&Спецификация (PDF)", this, &MainWindow::onExportSpecification);
    pdfMenu->addAction("&Перечень элементов (PDF)", this, &MainWindow::onExportPerechen);
    pdfMenu->addAction("&Ведомость покупных изделий (PDF)", this, &MainWindow::onExportPurchaseList);
    pdfMenu->addAction("Спецификация &PCB (PDF)", this, &MainWindow::onExportSpecificationPcb);
    pdfMenu->addSeparator();
    pdfMenu->addAction("Экспорт &всех в PDF", this, &MainWindow::onExportAll);
    // Подменю для экспорта в CSV
    QMenu* csvMenu = m_exportMenu->addMenu(tr("Экспорт в &CSV"));
    csvMenu->addAction("&Спецификация (CSV)", this, &MainWindow::onExportSpecificationToCsv);
    csvMenu->addAction("&Перечень элементов (CSV)", this, &MainWindow::onExportPerechenToCsv);
    csvMenu->addAction("&Ведомость покупных изделий (CSV)", this, &MainWindow::onExportPurchaseListToCsv);
    csvMenu->addAction("Спецификация &PCB (CSV)", this, &MainWindow::onExportSpecificationPcbToCsv);
    csvMenu->addAction("&Бланк заказа (CSV)", this, &MainWindow::onExportSimpleListToCsv);
    m_viewMenu = m_menuBar->addMenu(tr("&Вид"));
    QAction* dataPanelAction = m_viewMenu->addAction(tr("&Панель данных"), this, &MainWindow::onViewDataPanel);
    dataPanelAction->setCheckable(true);
    dataPanelAction->setChecked(true);
    
    QAction* pdfPreviewAction = m_viewMenu->addAction(tr("&PDF Превью"), this, &MainWindow::onViewPdfPreview);
    pdfPreviewAction->setCheckable(true);
    pdfPreviewAction->setChecked(true);
    
    m_viewMenu->addSeparator();
    m_viewMenu->addAction(tr("&Сбросить расположение"), this, &MainWindow::onViewResetLayout);
    m_helpMenu = m_menuBar->addMenu(tr("&Справка"));
    m_helpMenu->addAction("&О программе", this, &MainWindow::onHelpAbout);
    m_helpMenu->addAction("&Руководство", this, &MainWindow::onHelpManual);


    //панель инструментов - первая строка
    m_toolBar = new QToolBar(this);
    addToolBar(m_toolBar);
    m_toolBar->setMovable(false);
    m_toolBar->addAction(tr("&Новый проект"), this, &MainWindow::onFileNew);
    m_toolBar->addAction(tr("&Открыть проект"), this, &MainWindow::onFileOpen);
    m_toolBar->addAction(tr("&Сохранить проект"), this, &MainWindow::onFileSave);
    m_toolBar->addAction(tr("Сохранить &как..."), this, &MainWindow::onFileSaveAs);
    m_toolBar->addSeparator();
    m_toolBar->addAction(tr("&Настройки проекта"), this, &MainWindow::onProjectSettings);
    m_toolBar->addAction(tr("&Импорт Altium файла"), this, &MainWindow::onFileImportAltium);
    m_toolBar->addSeparator();
    // Экспорт в PDF
    m_toolBar->addAction(tr("Экспорт всех (PDF)"), this, &MainWindow::onExportAll);
    m_toolBar->addAction(tr("Спецификация (PDF)"), this, &MainWindow::onExportSpecification);
    m_toolBar->addAction(tr("Перечень (PDF)"), this, &MainWindow::onExportPerechen);
    m_toolBar->addAction(tr("Ведомость (PDF)"), this, &MainWindow::onExportPurchaseList);
    m_toolBar->addAction(tr("Спецификация PCB (PDF)"), this, &MainWindow::onExportSpecificationPcb);
    
    //панель инструментов - вторая строка
    m_toolBar2 = new QToolBar(this);
    addToolBar(m_toolBar2);
    m_toolBar2->setMovable(false);
    // Экспорт в CSV
    m_toolBar2->addAction(tr("Спецификация (CSV)"), this, &MainWindow::onExportSpecificationToCsv);
    m_toolBar2->addAction(tr("Перечень (CSV)"), this, &MainWindow::onExportPerechenToCsv);
    m_toolBar2->addAction(tr("Ведомость (CSV)"), this, &MainWindow::onExportPurchaseListToCsv);
    m_toolBar2->addAction(tr("Спецификация PCB (CSV)"), this, &MainWindow::onExportSpecificationPcbToCsv);
    m_toolBar2->addAction(tr("Бланк заказа (CSV)"), this, &MainWindow::onExportSimpleListToCsv);
    m_toolBar2->addSeparator();
    QAction* undoToolAction = m_toolBar2->addAction(tr("&Отменить"), this, &MainWindow::onUndo);
    QAction* redoToolAction = m_toolBar2->addAction(tr("&Повторить"), this, &MainWindow::onRedo);
    undoToolAction->setEnabled(false);
    redoToolAction->setEnabled(false);
    m_toolBar2->addSeparator();
    // Добавляем кнопку отмены парсинга во второй тулбар
    m_toolBar2->addAction(m_cancelParsingAction);

    //Статусбар
    m_statusBar = new QStatusBar(this);
    setStatusBar(m_statusBar);
    
    // Добавляем прогресс-бар в статус-бар
    m_statusBar->addPermanentWidget(m_progressBar);

    //Панель данных
    m_dataPanelDockWidget = new QDockWidget(tr("Панель данных"), this);
    m_dataPanelDockWidget->setWidget(m_dataView);

    //ПДФ Превью
    m_pdfPanelDockWidget = new QDockWidget(tr("PDF Превью"), this);
    m_pdfPanelDockWidget->setWidget(m_pdfWidget);

    //Добавляем панели в главное окно
    addDockWidget(Qt::RightDockWidgetArea, m_dataPanelDockWidget);
    addDockWidget(Qt::RightDockWidgetArea, m_pdfPanelDockWidget);
    
    // Накладываем панели друг на друга в виде табов
    tabifyDockWidget(m_dataPanelDockWidget, m_pdfPanelDockWidget);
    
    // Показываем первую панель по умолчанию
    m_dataPanelDockWidget->raise();
    
    // Обновляем состояние меню "Вид"
    updateViewMenuState();
}

void MainWindow::setUpConnections(){
    // Подключаем сигналы для асинхронного парсинга
    connect(m_cancelParsingAction, &QAction::triggered, this, [this]() {
        if (m_controller && m_controller->isParsingAsync()) {
            qDebug() << "MainWindow: Отмена парсинга по запросу пользователя";
            m_controller->cancelParsing();
            m_statusBar->showMessage(tr("Парсинг отменен"));
        }
    });
    
    // Подключаем сигналы закрытия док-виджетов для обновления меню
    if (m_dataPanelDockWidget) {
        connect(m_dataPanelDockWidget, &QDockWidget::visibilityChanged, this, &MainWindow::updateViewMenuState);
    }
    if (m_pdfPanelDockWidget) {
        connect(m_pdfPanelDockWidget, &QDockWidget::visibilityChanged, this, &MainWindow::updateViewMenuState);
    }
    
    // Подключаем сигнал изменения варианта от ComponentsPreview
    if (m_dataView && m_dataView->getComponentsPreview()) {
        connect(m_dataView->getComponentsPreview(), &ComponentsPreview::variantChanged,
                [this](const QString &variant) {
                    qDebug() << "MainWindow: Получен сигнал variantChanged:" << variant;
                    // Обновляем вариант в настройках проекта
                    m_controller->projectSettingsModel()->setCurrentVariant(variant);
                    // Обновляем текущий вариант в контроллере
                    m_controller->setCurrentVariant(variant);
                    // Перезагружаем компоненты с новым вариантом
                    m_controller->loadComponentsFromDatabase();
                    // Сохраняем настройки в базу данных
                    m_controller->saveProjectSettingsToDatabase();
                });
    }
}

void MainWindow::onHelpAbout()
{
    QMessageBox::about(this, "О программе", 
                      "PDF Генератор и Парсер Altium\n"
                      "Версия 1.0.0\n\n"
                      "Программа для работы с проектами Altium Designer\n"
                      "и генерации PDF документов.");
}

void MainWindow::onHelpManual()
{
    QMessageBox::information(this, "Руководство", 
                           "Руководство пользователя будет доступно в следующей версии.");
}

void MainWindow::onFileNew(){
    // Проверяем, нужно ли сохранить текущий проект
    if (!askForSave()) {
        return; // Пользователь отменил создание нового проекта
    }
    
    // Открываем диалог сохранения файла проекта
    QString fileName = QFileDialog::getSaveFileName(
        this,
        tr("Создать новый проект"),
        QString(),
        tr("PDF Проекты (*.pdfprj);;База данных (*.db);;Все файлы (*)")
    );
    
    if (!fileName.isEmpty()) {
        m_statusBar->showMessage(tr("Создание нового проекта: %1").arg(fileName));
        
        // Сначала инициализируем глобальную БД для настроек
        if (!m_controller->initializeGlobalDatabase()) {
            QMessageBox::critical(this, tr("Ошибка"), 
                                tr("Не удалось инициализировать глобальную базу данных: %1")
                                .arg(QString(m_controller->lastError())));
            return;
        }
        
        // Очищаем все данные перед созданием нового проекта
        m_controller->clearAllData();
        
        // Сбрасываем текущий вариант
        m_controller->setCurrentVariant("No Variations");
        
        // Инициализируем базу данных проекта
        if (m_controller->initializeDatabase(fileName)) {
            m_currentProjectPath = fileName;
            updateWindowTitle();
            m_dataView->updateView();
            updateStatusBar();
            enableInterface();
            m_statusBar->showMessage(tr("Новый проект создан: %1").arg(fileName));
        } else {
            QMessageBox::critical(this, tr("Ошибка"), 
                                tr("Не удалось создать проект: %1")
                                .arg(QString(m_controller->lastError())));
        }
    }
}

void MainWindow::onFileOpen(){
    // Проверяем, нужно ли сохранить текущий проект
    if (!askForSave()) {
        return; // Пользователь отменил открытие проекта
    }
    
    // Открываем диалог выбора файла проекта
    QString fileName = QFileDialog::getOpenFileName(
        this,
        tr("Открыть проект"),
        QString(),
        tr("PDF Проекты (*.pdfprj);;База данных (*.db);;Все файлы (*)")
    );
    
    if (!fileName.isEmpty()) {
        openProjectFile(fileName);
    }
}

void MainWindow::openProjectFile(const QString &fileName) {
    if (fileName.isEmpty()) {
        return;
    }
    
    // Проверяем существование файла
    QFileInfo fileInfo(fileName);
    if (!fileInfo.exists()) {
        QMessageBox::critical(this, tr("Ошибка"), 
                            tr("Файл не найден: %1").arg(fileName));
        return;
    }
    
    // Проверяем расширение файла
    QString extension = fileInfo.suffix().toLower();
    if (extension != "pdfprj" && extension != "db") {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Неизвестный тип файла: %1\nОжидается файл проекта (.pdfprj)").arg(extension));
        return;
    }
    
    m_statusBar->showMessage(tr("Открытие проекта: %1").arg(fileName));
    
    // Глобальная БД уже должна быть инициализирована в main.cpp
    // Если по какой-то причине она не инициализирована, попробуем инициализировать
    // Но сначала проверим, не открыта ли она уже
    // (повторная инициализация может вызвать ошибку, поэтому пропускаем, если уже открыта)
    
    // Инициализируем базу данных проекта с выбранным файлом
    if (m_controller->initializeDatabase(fileName)) {
            // Сначала загружаем настройки проекта, чтобы установить правильный текущий вариант
            m_controller->loadProjectSettingsFromDatabase();
            
            // Затем загружаем компоненты с правильным текущим вариантом
            if (m_controller->loadComponentsFromDatabase()) {
                // Загружаем параметры проекта
                m_controller->loadProjectParamsFromDatabase();
                
                // Загружаем перечень элементов напрямую в модель MainController
                QByteArray tableData = m_controller->loadPerechenTableFromDatabase();
                if (!tableData.isEmpty()) {
                    PerechenTableModel *perechenModel = m_controller->perechenTableModel();
                    if (perechenModel) {
                        perechenModel->loadFromDatabase(tableData);
                        qDebug() << "MainWindow::onFileOpen: Таблица перечня загружена из БД в MainController";
                    } else {
                        qDebug() << "MainWindow::onFileOpen: PerechenTableModel недоступен в MainController";
                    }
                } else {
                    qDebug() << "MainWindow::onFileOpen: Данные таблицы перечня не найдены в БД";
                }
                
                // Загружаем спецификацию ПП напрямую в модель MainController
                QByteArray specPCBTableData = m_controller->loadSpecificationPCBTableFromDatabase();
                if (!specPCBTableData.isEmpty()) {
                    SpecificationPCBTableModel *specPCBModel = m_controller->specificationPCBTableModel();
                    if (specPCBModel) {
                        specPCBModel->loadFromDatabase(specPCBTableData);
                        qDebug() << "MainWindow::onFileOpen: Таблица спецификации ПП загружена из БД в MainController";
                    } else {
                        qDebug() << "MainWindow::onFileOpen: SpecificationPCBTableModel недоступен в MainController";
                    }
                } else {
                    qDebug() << "MainWindow::onFileOpen: Данные таблицы спецификации ПП не найдены в БД";
                }
                
                // Загружаем спецификацию материалов напрямую в модель MainController
                QByteArray specTableData = m_controller->loadSpecificationTableFromDatabase();
                if (!specTableData.isEmpty()) {
                    SpecificationTableModel *specModel = m_controller->specificationTableModel();
                    if (specModel) {
                        specModel->loadFromDatabase(specTableData);
                        qDebug() << "MainWindow::onFileOpen: Таблица спецификации материалов загружена из БД в MainController";
                    } else {
                        qDebug() << "MainWindow::onFileOpen: SpecificationTableModel недоступен в MainController";
                    }
                } else {
                    qDebug() << "MainWindow::onFileOpen: Данные таблицы спецификации материалов не найдены в БД";
                }
                
                // Загружаем ведомость покупных изделий напрямую в модель MainController
                QByteArray vedomostTableData = m_controller->loadVedomostTableFromDatabase();
                if (!vedomostTableData.isEmpty()) {
                    VedomostTableModel *vedomostModel = m_controller->vedomostTableModel();
                    if (vedomostModel) {
                        vedomostModel->loadFromDatabase(vedomostTableData);
                        qDebug() << "MainWindow::onFileOpen: Таблица ведомости покупных изделий загружена из БД в MainController";
                    } else {
                        qDebug() << "MainWindow::onFileOpen: VedomostTableModel недоступен в MainController";
                    }
                } else {
                    qDebug() << "MainWindow::onFileOpen: Данные таблицы ведомости покупных изделий не найдены в БД";
                }
                
                // Загружаем бланк заказа напрямую в модель MainController
                QByteArray simpleListTableData = m_controller->loadSimpleListTableFromDatabase();
                if (!simpleListTableData.isEmpty()) {
                    SimpleListTableModel *simpleListModel = m_controller->simpleListTableModel();
                    if (simpleListModel) {
                        simpleListModel->loadFromDatabase(simpleListTableData);
                        qDebug() << "MainWindow::onFileOpen: Таблица бланка заказа загружена из БД в MainController";
                    } else {
                        qDebug() << "MainWindow::onFileOpen: SimpleListTableModel недоступен в MainController";
                    }
                } else {
                    qDebug() << "MainWindow::onFileOpen: Данные таблицы бланка заказа не найдены в БД";
                }
                
                // Загружаем надписи титульного листа в MainController
                QMap<int, QString> inscriptions;
                if (m_controller->loadTitleInscriptionsFromDatabase(inscriptions)) {
                    TitleInscriptionsModel *titleModel = m_controller->titleInscriptionsModel();
                    if (titleModel) {
                        titleModel->setAllInscriptions(inscriptions);
                        qDebug() << "MainWindow::onFileOpen: Надписи титульного листа загружены в MainController";
                    } else {
                        qDebug() << "MainWindow::onFileOpen: TitleInscriptionsModel недоступен в MainController";
                    }
                } else {
                    qDebug() << "MainWindow::onFileOpen: Надписи титульного листа не найдены в БД";
                }
                
                m_currentProjectPath = fileName;
                updateWindowTitle();
                updateStatusBar();
                enableInterface();
                m_statusBar->showMessage(tr("Проект успешно загружен: %1").arg(fileName));
                
                // Обновляем все представления документов, включая таблицу перечня
                m_editWidget->updateAllViews();
                
                // Обновляем представление компонентов
                m_dataView->updateView();
                
                // Принудительно обновляем ComponentsPreview с правильным вариантом
                if (m_dataView && m_dataView->getComponentsPreview()) {
                    QString currentVariant = m_controller->projectSettingsModel()->currentVariant();
                    qDebug() << "MainWindow: Устанавливаем текущий вариант в ComponentsPreview:" << currentVariant;
                    // Используем QTimer::singleShot для обеспечения полной загрузки модели
                    QTimer::singleShot(100, [this, currentVariant]() {
                        if (m_dataView && m_dataView->getComponentsPreview()) {
                            m_dataView->getComponentsPreview()->setCurrentVariant(currentVariant);
                        }
                    });
                }
            } else {
                QMessageBox::warning(this, tr("Предупреждение"), 
                                   tr("Проект загружен, но данные не найдены"));
            }
        } else {
            QMessageBox::critical(this, tr("Ошибка"), 
                                tr("Не удалось открыть проект: %1")
                                .arg(QString(m_controller->lastError())));
        }
}

bool MainWindow::onFileSave(){
    // Сохраняем текущий проект
    if (m_currentProjectPath.isEmpty()) {
        // Если путь не установлен, вызываем "Сохранить как"
        onFileSaveAs();
        return !m_currentProjectPath.isEmpty(); // Возвращаем true если файл был сохранен
    } else {
        // Сохраняем основные данные в текущую БД (без свойств и вариантов)
        bool success = true;
        success &= m_controller->saveComponentsToDatabase();
        success &= m_controller->saveProjectParamsToDatabase();
        success &= m_controller->saveProjectSettingsToDatabase();
        
        // Сохраняем надписи титульного листа из MainController
        TitleInscriptionsModel *titleModel = m_controller->titleInscriptionsModel();
        if (titleModel) {
            QMap<int, QString> inscriptions = titleModel->getAllInscriptions();
            success &= m_controller->saveTitleInscriptionsToDatabase(inscriptions);
            qDebug() << "MainWindow::onFileSave: Надписи титульного листа сохранены из MainController";
        } else {
            qDebug() << "MainWindow::onFileSave: TitleInscriptionsModel недоступен в MainController";
        }
        
        // Сохраняем перечень элементов из модели MainController
        PerechenTableModel *perechenModel = m_controller->perechenTableModel();
        if (perechenModel) {
            QByteArray tableData = perechenModel->saveToDatabase();
            if (!tableData.isEmpty()) {
                success &= m_controller->savePerechenTableToDatabase(tableData);
                qDebug() << "MainWindow::onFileSave: Таблица перечня сохранена из MainController";
            } else {
                qDebug() << "MainWindow::onFileSave: Данные таблицы перечня пусты";
            }
        } else {
            qDebug() << "MainWindow::onFileSave: PerechenTableModel недоступен в MainController";
        }
        
        // Сохраняем спецификацию ПП из модели MainController
        SpecificationPCBTableModel *specPCBModel = m_controller->specificationPCBTableModel();
        if (specPCBModel) {
            QByteArray tableData = specPCBModel->saveToDatabase();
            if (!tableData.isEmpty()) {
                success &= m_controller->saveSpecificationPCBTableToDatabase(tableData);
                qDebug() << "MainWindow::onFileSave: Таблица спецификации ПП сохранена из MainController";
            } else {
                qDebug() << "MainWindow::onFileSave: Данные таблицы спецификации ПП пусты";
            }
        } else {
            qDebug() << "MainWindow::onFileSave: SpecificationPCBTableModel недоступен в MainController";
        }
        
        // Сохраняем спецификацию материалов из модели MainController
        SpecificationTableModel *specModel = m_controller->specificationTableModel();
        if (specModel) {
            QByteArray tableData = specModel->saveToDatabase();
            if (!tableData.isEmpty()) {
                success &= m_controller->saveSpecificationTableToDatabase(tableData);
                qDebug() << "MainWindow::onFileSave: Таблица спецификации материалов сохранена из MainController";
            } else {
                qDebug() << "MainWindow::onFileSave: Данные таблицы спецификации материалов пусты";
            }
        } else {
            qDebug() << "MainWindow::onFileSave: SpecificationTableModel недоступен в MainController";
        }
        
        // Сохраняем ведомость покупных изделий из модели MainController
        VedomostTableModel *vedomostModel = m_controller->vedomostTableModel();
        if (vedomostModel) {
            QByteArray tableData = vedomostModel->saveToDatabase();
            if (!tableData.isEmpty()) {
                success &= m_controller->saveVedomostTableToDatabase(tableData);
                qDebug() << "MainWindow::onFileSave: Таблица ведомости покупных изделий сохранена из MainController";
            } else {
                qDebug() << "MainWindow::onFileSave: Данные таблицы ведомости покупных изделий пусты";
            }
        } else {
            qDebug() << "MainWindow::onFileSave: VedomostTableModel недоступен в MainController";
        }
        
        // Сохраняем бланк заказа из модели MainController
        SimpleListTableModel *simpleListModel = m_controller->simpleListTableModel();
        if (simpleListModel) {
            QByteArray tableData = simpleListModel->saveToDatabase();
            if (!tableData.isEmpty()) {
                success &= m_controller->saveSimpleListTableToDatabase(tableData);
                qDebug() << "MainWindow::onFileSave: Таблица бланка заказа сохранена из MainController";
            } else {
                qDebug() << "MainWindow::onFileSave: Данные таблицы бланка заказа пусты";
            }
        } else {
            qDebug() << "MainWindow::onFileSave: SimpleListTableModel недоступен в MainController";
        }
        
        if (success) {
            m_statusBar->showMessage(tr("Проект сохранен: %1").arg(m_currentProjectPath));
            return true;
        } else {
            QMessageBox::critical(this, tr("Ошибка"), 
                                tr("Не удалось сохранить проект: %1")
                                .arg(QString(m_controller->lastError())));
            return false;
        }
    }
}

void MainWindow::onFileSaveAs(){
    // Открываем диалог сохранения файла проекта
    QString fileName = QFileDialog::getSaveFileName(
        this,
        tr("Сохранить проект как"),
        QString(),
        tr("PDF Проекты (*.pdfprj);;База данных (*.db);;Все файлы (*)")
    );
    
    if (!fileName.isEmpty()) {
        m_statusBar->showMessage(tr("Сохранение проекта: %1").arg(fileName));
        
        // Инициализируем новую базу данных
        if (m_controller->initializeDatabase(fileName)) {
            // Сохраняем основные данные в новую БД (без свойств и вариантов)
            bool success = true;
            success &= m_controller->saveComponentsToDatabase();
            success &= m_controller->saveProjectParamsToDatabase();
            success &= m_controller->saveProjectSettingsToDatabase();
            
            // Сохраняем надписи титульного листа из MainController
            TitleInscriptionsModel *titleModel = m_controller->titleInscriptionsModel();
            if (titleModel) {
                QMap<int, QString> inscriptions = titleModel->getAllInscriptions();
                success &= m_controller->saveTitleInscriptionsToDatabase(inscriptions);
                qDebug() << "MainWindow::onFileSaveAs: Надписи титульного листа сохранены из MainController";
            } else {
                qDebug() << "MainWindow::onFileSaveAs: TitleInscriptionsModel недоступен в MainController";
            }
            
            // Сохраняем перечень элементов из модели MainController
            PerechenTableModel *perechenModel = m_controller->perechenTableModel();
            if (perechenModel) {
                QByteArray tableData = perechenModel->saveToDatabase();
                if (!tableData.isEmpty()) {
                    success &= m_controller->savePerechenTableToDatabase(tableData);
                    qDebug() << "MainWindow::onFileSaveAs: Таблица перечня сохранена из MainController";
                } else {
                    qDebug() << "MainWindow::onFileSaveAs: Данные таблицы перечня пусты";
                }
            } else {
                qDebug() << "MainWindow::onFileSaveAs: PerechenTableModel недоступен в MainController";
            }
            
            // Сохраняем спецификацию ПП из модели MainController
            SpecificationPCBTableModel *specPCBModel = m_controller->specificationPCBTableModel();
            if (specPCBModel) {
                QByteArray tableData = specPCBModel->saveToDatabase();
                if (!tableData.isEmpty()) {
                    success &= m_controller->saveSpecificationPCBTableToDatabase(tableData);
                    qDebug() << "MainWindow::onFileSaveAs: Таблица спецификации ПП сохранена из MainController";
                } else {
                    qDebug() << "MainWindow::onFileSaveAs: Данные таблицы спецификации ПП пусты";
                }
            } else {
                qDebug() << "MainWindow::onFileSaveAs: SpecificationPCBTableModel недоступен в MainController";
            }
            
            // Сохраняем спецификацию материалов из модели MainController
            SpecificationTableModel *specModel = m_controller->specificationTableModel();
            if (specModel) {
                QByteArray tableData = specModel->saveToDatabase();
                if (!tableData.isEmpty()) {
                    success &= m_controller->saveSpecificationTableToDatabase(tableData);
                    qDebug() << "MainWindow::onFileSaveAs: Таблица спецификации материалов сохранена из MainController";
                            } else {
                qDebug() << "MainWindow::onFileSaveAs: Данные таблицы спецификации материалов пусты";
            }
        } else {
            qDebug() << "MainWindow::onFileSaveAs: SpecificationTableModel недоступен в MainController";
        }
        
            // Сохраняем ведомость покупных изделий из модели MainController
            VedomostTableModel *vedomostModel = m_controller->vedomostTableModel();
            if (vedomostModel) {
                QByteArray tableData = vedomostModel->saveToDatabase();
                if (!tableData.isEmpty()) {
                    success &= m_controller->saveVedomostTableToDatabase(tableData);
                    qDebug() << "MainWindow::onFileSaveAs: Таблица ведомости покупных изделий сохранена из MainController";
                } else {
                    qDebug() << "MainWindow::onFileSaveAs: Данные таблицы ведомости покупных изделий пусты";
                }
            } else {
                qDebug() << "MainWindow::onFileSaveAs: VedomostTableModel недоступен в MainController";
            }
            
            // Сохраняем бланк заказа из модели MainController
            SimpleListTableModel *simpleListModel = m_controller->simpleListTableModel();
            if (simpleListModel) {
                QByteArray tableData = simpleListModel->saveToDatabase();
                if (!tableData.isEmpty()) {
                    success &= m_controller->saveSimpleListTableToDatabase(tableData);
                    qDebug() << "MainWindow::onFileSaveAs: Таблица бланка заказа сохранена из MainController";
                } else {
                    qDebug() << "MainWindow::onFileSaveAs: Данные таблицы бланка заказа пусты";
                }
            } else {
                qDebug() << "MainWindow::onFileSaveAs: SimpleListTableModel недоступен в MainController";
            }
            
            if (success) {
                m_currentProjectPath = fileName;
                updateWindowTitle();
                updateStatusBar();
                enableInterface();
                m_statusBar->showMessage(tr("Проект сохранен: %1").arg(fileName));
            } else {
                QMessageBox::critical(this, tr("Ошибка"), 
                                    tr("Не удалось сохранить проект: %1")
                    .arg(QString(m_controller->lastError())));
            }
        } else {
            QMessageBox::critical(this, tr("Ошибка"), 
                                tr("Не удалось создать файл проекта: %1")
                                .arg(QString(m_controller->lastError())));
        }
    }
}

void MainWindow::onFileImportAltium(){
    // Проверяем, есть ли открытый проект
    if (m_currentProjectPath.isEmpty() || 
        !m_controller || !m_controller->isDatabaseOpen()) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Для импорта Altium файла необходимо сначала создать или открыть проект.\n\n"
                              "Пожалуйста, создайте новый проект или откройте существующий."));
        return;
    }
    
    // Открываем диалог выбора файла
    QString fileName = QFileDialog::getOpenFileName(
        this,
        tr("Выберите Altium файл"),
        QString(),
        tr("Altium проекты (*.PrjPCB);;Altium файлы (*.prjpcb *.sch *.schdoc *.pcb *.pcbdoc);;Все файлы (*)")
    );
    
    if (!fileName.isEmpty()) {
        m_statusBar->showMessage(tr("Импорт файла: %1").arg(fileName));
        
        // Парсинг теперь выполняется через MainController
        if (m_controller) {
            // Отключаем старые соединения
            disconnect(m_controller, nullptr, this, nullptr);
            
            // Подключаем сигналы через MainController
            connect(m_controller, &MainController::parsingStarted, this, &MainWindow::onParsingStarted);
            connect(m_controller, &MainController::parsingProgress, this, &MainWindow::onParsingProgress);
            connect(m_controller, &MainController::parsingFinished, this, &MainWindow::onParsingFinished);
            connect(m_controller, &MainController::error, this, &MainWindow::onParsingError);
            
            // Запускаем парсинг через MainController
            m_controller->parseFileAsync(fileName);
        } else {
            QMessageBox::critical(this, tr("Ошибка"), tr("Контроллер не инициализирован"));
        }
    }
}
void MainWindow::onFileExit(){
    if (askForSave()) {
        close();
    }
}

void MainWindow::closeEvent(QCloseEvent *event)
{
    if (askForSave()) {
        event->accept();
    } else {
        event->ignore();
    }
}

void MainWindow::onExportSpecification(){
    qDebug() << "MainWindow::onExportSpecification: Начинаем экспорт спецификации материалов";
    
    // Проверяем, открыт ли проект
    if (m_currentProjectPath.isEmpty()) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Сначала создайте или откройте проект"));
        return;
    }
    
    // Проверяем, есть ли данные для экспорта
    if (!m_controller->specificationTableModel() || 
        m_controller->specificationTableModel()->rowCount() == 0) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Нет данных для экспорта. Сначала сгенерируйте таблицу спецификации."));
        return;
    }
    
    // Формируем имя файла: поле 2 из TitleInscription + " Спецификация"
    QString fileNameBase = "Спецификация";
    TitleInscriptionsModel *titleModel = m_controller->titleInscriptionsModel();
    ProjectParamTableModel *projectParamModel = m_controller->projectParamTableModel();
    if (titleModel && projectParamModel) {
        QString field2Value = PDFController::getInscriptionValueWithProjectParams(titleModel, projectParamModel, 2);
        if (!field2Value.isEmpty() && field2Value != "-- Не выбрано --") {
            fileNameBase = field2Value + " Спецификация";
        }
    }
    
    // Запрашиваем путь для сохранения файла
    QString defaultPath = QCoreApplication::applicationDirPath() + "/" + fileNameBase + ".pdf";
    QString fileName = QFileDialog::getSaveFileName(
        this,
        tr("Экспорт спецификации"),
        defaultPath,
        tr("PDF файлы (*.pdf)")
    );
    
    if (!fileName.isEmpty()) {
        m_statusBar->showMessage(tr("Экспорт спецификации: %1").arg(fileName));
        
        // Экспортируем в PDF через MainController
        if (m_controller->exportSpecificationToPdf(fileName)) {
            m_statusBar->showMessage(tr("Спецификация  успешно экспортирована: %1").arg(fileName));
            
            // Автоматически открываем созданный PDF файл
            QUrl fileUrl = QUrl::fromLocalFile(fileName);
            QDesktopServices::openUrl(fileUrl);
        } else {
            m_statusBar->showMessage(tr("Ошибка экспорта спецификации"));
            QMessageBox::critical(this, tr("Ошибка"), 
                               tr("Не удалось экспортировать спецификацию"));
        }
    }
}

void MainWindow::onExportPerechen(){
    qDebug() << "MainWindow::onExportPerechen: Начинаем экспорт перечня элементов";
    
    // Проверяем, открыт ли проект
    if (m_currentProjectPath.isEmpty()) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Сначала создайте или откройте проект"));
        return;
    }
    
    // Получаем модель перечня из MainController
    PerechenTableModel *perechenModel = m_controller->perechenTableModel();
    if (!perechenModel) {
        QMessageBox::critical(this, tr("Ошибка"), 
                           tr("Модель перечня элементов недоступна"));
        return;
    }
    
    // Проверяем, есть ли данные в модели
    if (perechenModel->rowCount() == 0) {
        QMessageBox::information(this, tr("Информация"), 
                               tr("Таблица перечня элементов пуста. Сначала сгенерируйте таблицу."));
        return;
    }
    
    // Формируем имя файла: поле 2 из TitleInscription + " ПЭ3"
    QString fileNameBase = "ПЭ3";
    TitleInscriptionsModel *titleModel = m_controller->titleInscriptionsModel();
    ProjectParamTableModel *projectParamModel = m_controller->projectParamTableModel();
    if (titleModel && projectParamModel) {
        QString field2Value = PDFController::getInscriptionValueWithProjectParams(titleModel, projectParamModel, 2);
        if (!field2Value.isEmpty() && field2Value != "-- Не выбрано --") {
            fileNameBase = field2Value + " ПЭ3";
        }
    }
    
    // Открываем диалог сохранения файла
    QString defaultPath = QCoreApplication::applicationDirPath() + "/" + fileNameBase + ".pdf";
    QString fileName = QFileDialog::getSaveFileName(
        this,
        tr("Экспорт перечня элементов"),
        defaultPath,
        tr("PDF файлы (*.pdf);;Все файлы (*)")
    );
    
    if (!fileName.isEmpty()) {
        m_statusBar->showMessage(tr("Экспорт перечня элементов: %1").arg(fileName));
        
        // Экспортируем в PDF через MainController
        if (m_controller->exportPerechenToPdf(fileName)) {
            m_statusBar->showMessage(tr("Перечень элементов успешно экспортирован: %1").arg(fileName));
            
            // Автоматически открываем созданный PDF файл
            QUrl fileUrl = QUrl::fromLocalFile(fileName);
            QDesktopServices::openUrl(fileUrl);
        } else {
            m_statusBar->showMessage(tr("Ошибка экспорта перечня элементов"));
            QMessageBox::critical(this, tr("Ошибка"), 
                               tr("Не удалось экспортировать перечень элементов"));
        }
    }
}

void MainWindow::onExportSpecificationPcb(){
    qDebug() << "MainWindow::onExportSpecificationPcb: Начинаем экспорт спецификации PCB";
    
    // Проверяем, открыт ли проект
    if (m_currentProjectPath.isEmpty()) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Сначала создайте или откройте проект"));
        return;
    }
    
    // Получаем модель спецификации PCB из MainController
    SpecificationPCBTableModel *specificationModel = m_controller->specificationPCBTableModel();
    if (!specificationModel) {
        QMessageBox::critical(this, tr("Ошибка"), 
                           tr("Модель спецификации PCB недоступна"));
        return;
    }
    
    // Проверяем, есть ли данные в модели
    if (specificationModel->rowCount() == 0) {
        QMessageBox::information(this, tr("Информация"), 
                               tr("Таблица спецификации PCB пуста. Сначала сгенерируйте таблицу."));
        return;
    }
    
    // Формируем имя файла: поле 2 из TitleInscription + " Спецификация ПП"
    QString fileNameBase = "Спецификация ПП";
    TitleInscriptionsModel *titleModel = m_controller->titleInscriptionsModel();
    ProjectParamTableModel *projectParamModel = m_controller->projectParamTableModel();
    if (titleModel && projectParamModel) {
        QString field2Value = PDFController::getInscriptionValueWithProjectParams(titleModel, projectParamModel, 2);
        if (!field2Value.isEmpty() && field2Value != "-- Не выбрано --") {
            fileNameBase = field2Value + " Спецификация ПП";
        }
    }
    
    // Открываем диалог сохранения файла
    QString defaultPath = QCoreApplication::applicationDirPath() + "/" + fileNameBase + ".pdf";
    QString fileName = QFileDialog::getSaveFileName(
        this,
        tr("Экспорт спецификации PCB"),
        defaultPath,
        tr("PDF файлы (*.pdf);;Все файлы (*)")
    );
    
    if (!fileName.isEmpty()) {
        m_statusBar->showMessage(tr("Экспорт спецификации PCB: %1").arg(fileName));
        
        // Экспортируем в PDF через MainController
        if (m_controller->exportSpecificationPcbToPdf(fileName)) {
            m_statusBar->showMessage(tr("Спецификация PCB успешно экспортирована: %1").arg(fileName));
            
            // Автоматически открываем созданный PDF файл
            QUrl fileUrl = QUrl::fromLocalFile(fileName);
            QDesktopServices::openUrl(fileUrl);
        } else {
            m_statusBar->showMessage(tr("Ошибка экспорта спецификации PCB"));
            QMessageBox::critical(this, tr("Ошибка"), 
                               tr("Не удалось экспортировать спецификацию PCB"));
        }
    }
}

void MainWindow::onExportPurchaseList()
{
    qDebug() << "MainWindow::onExportPurchaseList: Экспорт ведомости покупных изделий";
    
    // Проверяем, открыт ли проект
    if (m_currentProjectPath.isEmpty()) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Сначала создайте или откройте проект"));
        return;
    }
    
    // Проверяем, есть ли данные в модели ведомости
    VedomostTableModel *vedomostModel = m_controller->vedomostTableModel();
    if (!vedomostModel || vedomostModel->rowCount() == 0) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Ведомость покупных изделий пуста. Сначала сгенерируйте таблицу."));
        return;
    }
    
    // Формируем имя файла: поле 2 из TitleInscription + " ВП"
    QString fileNameBase = "ВП";
    TitleInscriptionsModel *titleModel = m_controller->titleInscriptionsModel();
    ProjectParamTableModel *projectParamModel = m_controller->projectParamTableModel();
    if (titleModel && projectParamModel) {
        QString field2Value = PDFController::getInscriptionValueWithProjectParams(titleModel, projectParamModel, 2);
        if (!field2Value.isEmpty() && field2Value != "-- Не выбрано --") {
            fileNameBase = field2Value + " ВП";
        }
    }
    
    // Открываем диалог сохранения файла
    QString defaultPath = QCoreApplication::applicationDirPath() + "/" + fileNameBase + ".pdf";
    QString fileName = QFileDialog::getSaveFileName(
        this,
        tr("Экспорт ведомости покупных изделий"),
        defaultPath,
        tr("PDF файлы (*.pdf);;Все файлы (*)")
    );
    
    if (!fileName.isEmpty()) {
        m_statusBar->showMessage(tr("Экспорт ведомости покупных изделий: %1").arg(fileName));
        
        // Экспортируем ведомость в PDF
        if (m_controller->exportVedomostToPdf(fileName)) {
            m_statusBar->showMessage(tr("Ведомость покупных изделий успешно экспортирована: %1").arg(fileName));
            QMessageBox::information(this, tr("Успех"), 
                                   tr("Ведомость покупных изделий успешно экспортирована:\n%1").arg(fileName));
        } else {
            m_statusBar->showMessage(tr("Ошибка экспорта ведомости покупных изделий"));
            QMessageBox::critical(this, tr("Ошибка"), 
                               tr("Не удалось экспортировать ведомость покупных изделий:\n%1")
                               .arg(m_controller->lastError()));
        }
    }
}



void MainWindow::onExportSpecificationToCsv()
{
    qDebug() << "MainWindow::onExportSpecificationToCsv: Начинаем экспорт спецификации материалов в CSV";
    
    // Проверяем, открыт ли проект
    if (m_currentProjectPath.isEmpty()) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Сначала создайте или откройте проект"));
        return;
    }
    
    // Проверяем, есть ли данные для экспорта
    if (!m_controller->specificationTableModel() || 
        m_controller->specificationTableModel()->rowCount() == 0) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Нет данных для экспорта. Сначала сгенерируйте таблицу спецификации."));
        return;
    }
    
    // Запрашиваем путь для сохранения файла
    QString defaultPath = QCoreApplication::applicationDirPath() + "/Спецификация.csv";
    QString fileName = QFileDialog::getSaveFileName(
        this,
        tr("Экспорт спецификации в CSV"),
        defaultPath,
        tr("CSV файлы (*.csv);;Все файлы (*)")
    );
    
    if (!fileName.isEmpty()) {
        m_statusBar->showMessage(tr("Экспорт спецификации в CSV: %1").arg(fileName));
        
        // Экспортируем в CSV через MainController
        if (m_controller->exportSpecificationToCsv(fileName)) {
            m_statusBar->showMessage(tr("Спецификация успешно экспортирована в CSV: %1").arg(fileName));
            QMessageBox::information(this, tr("Успех"), 
                                   tr("Спецификация успешно экспортирована в CSV:\n%1").arg(fileName));
        } else {
            m_statusBar->showMessage(tr("Ошибка экспорта спецификации в CSV"));
            QMessageBox::critical(this, tr("Ошибка"), 
                               tr("Не удалось экспортировать спецификацию в CSV"));
        }
    }
}

void MainWindow::onExportPerechenToCsv()
{
    qDebug() << "MainWindow::onExportPerechenToCsv: Начинаем экспорт перечня элементов в CSV";
    
    // Проверяем, открыт ли проект
    if (m_currentProjectPath.isEmpty()) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Сначала создайте или откройте проект"));
        return;
    }
    
    // Получаем модель перечня из MainController
    PerechenTableModel *perechenModel = m_controller->perechenTableModel();
    if (!perechenModel) {
        QMessageBox::critical(this, tr("Ошибка"), 
                           tr("Модель перечня элементов недоступна"));
        return;
    }
    
    // Проверяем, есть ли данные в модели
    if (perechenModel->rowCount() == 0) {
        QMessageBox::information(this, tr("Информация"), 
                               tr("Таблица перечня элементов пуста. Сначала сгенерируйте таблицу."));
        return;
    }
    
    // Открываем диалог сохранения файла
    QString defaultPath = QCoreApplication::applicationDirPath() + "/ПереченьЭлементов.csv";
    QString fileName = QFileDialog::getSaveFileName(
        this,
        tr("Экспорт перечня элементов в CSV"),
        defaultPath,
        tr("CSV файлы (*.csv);;Все файлы (*)")
    );
    
    if (!fileName.isEmpty()) {
        m_statusBar->showMessage(tr("Экспорт перечня элементов в CSV: %1").arg(fileName));
        
        // Экспортируем в CSV через MainController
        if (m_controller->exportPerechenToCsv(fileName)) {
            m_statusBar->showMessage(tr("Перечень элементов успешно экспортирован в CSV: %1").arg(fileName));
            QMessageBox::information(this, tr("Успех"), 
                                   tr("Перечень элементов успешно экспортирован в CSV:\n%1").arg(fileName));
        } else {
            m_statusBar->showMessage(tr("Ошибка экспорта перечня элементов в CSV"));
            QMessageBox::critical(this, tr("Ошибка"), 
                               tr("Не удалось экспортировать перечень элементов в CSV"));
        }
    }
}

void MainWindow::onExportSpecificationPcbToCsv()
{
    qDebug() << "MainWindow::onExportSpecificationPcbToCsv: Начинаем экспорт спецификации PCB в CSV";
    
    // Проверяем, открыт ли проект
    if (m_currentProjectPath.isEmpty()) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Сначала создайте или откройте проект"));
        return;
    }
    
    // Получаем модель спецификации PCB из MainController
    SpecificationPCBTableModel *specificationModel = m_controller->specificationPCBTableModel();
    if (!specificationModel) {
        QMessageBox::critical(this, tr("Ошибка"), 
                           tr("Модель спецификации PCB недоступна"));
        return;
    }
    
    // Проверяем, есть ли данные в модели
    if (specificationModel->rowCount() == 0) {
        QMessageBox::information(this, tr("Информация"), 
                               tr("Таблица спецификации PCB пуста. Сначала сгенерируйте таблицу."));
        return;
    }
    
    // Открываем диалог сохранения файла
    QString defaultPath = QCoreApplication::applicationDirPath() + "/СпецификацияПП.csv";
    QString fileName = QFileDialog::getSaveFileName(
        this,
        tr("Экспорт спецификации PCB в CSV"),
        defaultPath,
        tr("CSV файлы (*.csv);;Все файлы (*)")
    );
    
    if (!fileName.isEmpty()) {
        m_statusBar->showMessage(tr("Экспорт спецификации PCB в CSV: %1").arg(fileName));
        
        // Экспортируем в CSV через MainController
        if (m_controller->exportSpecificationPcbToCsv(fileName)) {
            m_statusBar->showMessage(tr("Спецификация PCB успешно экспортирована в CSV: %1").arg(fileName));
            QMessageBox::information(this, tr("Успех"), 
                                   tr("Спецификация PCB успешно экспортирована в CSV:\n%1").arg(fileName));
        } else {
            m_statusBar->showMessage(tr("Ошибка экспорта спецификации PCB в CSV"));
            QMessageBox::critical(this, tr("Ошибка"), 
                               tr("Не удалось экспортировать спецификацию PCB в CSV"));
        }
    }
}

void MainWindow::onExportPurchaseListToCsv()
{
    qDebug() << "MainWindow::onExportPurchaseListToCsv: Экспорт ведомости покупных изделий в CSV";
    
    // Проверяем, открыт ли проект
    if (m_currentProjectPath.isEmpty()) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Сначала создайте или откройте проект"));
        return;
    }
    
    // Проверяем, есть ли данные в модели ведомости
    VedomostTableModel *vedomostModel = m_controller->vedomostTableModel();
    if (!vedomostModel || vedomostModel->rowCount() == 0) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Ведомость покупных изделий пуста. Сначала сгенерируйте таблицу."));
        return;
    }
    
    // Открываем диалог сохранения файла
    QString defaultPath = QCoreApplication::applicationDirPath() + "/ВедомостьПокупныхИзделий.csv";
    QString fileName = QFileDialog::getSaveFileName(
        this,
        tr("Экспорт ведомости покупных изделий в CSV"),
        defaultPath,
        tr("CSV файлы (*.csv);;Все файлы (*)")
    );
    
    if (!fileName.isEmpty()) {
        m_statusBar->showMessage(tr("Экспорт ведомости покупных изделий в CSV: %1").arg(fileName));
        
        // Экспортируем ведомость в CSV
        if (m_controller->exportVedomostToCsv(fileName)) {
            m_statusBar->showMessage(tr("Ведомость покупных изделий успешно экспортирована в CSV: %1").arg(fileName));
            QMessageBox::information(this, tr("Успех"), 
                                   tr("Ведомость покупных изделий успешно экспортирована в CSV:\n%1").arg(fileName));
        } else {
            m_statusBar->showMessage(tr("Ошибка экспорта ведомости покупных изделий в CSV"));
            QMessageBox::critical(this, tr("Ошибка"), 
                               tr("Не удалось экспортировать ведомость покупных изделий в CSV:\n%1")
                               .arg(m_controller->lastError()));
        }
    }
}

void MainWindow::onExportSimpleListToCsv()
{
    qDebug() << "MainWindow::onExportSimpleListToCsv: Экспорт бланка заказа в CSV";
    
    // Проверяем, открыт ли проект
    if (m_currentProjectPath.isEmpty()) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Сначала создайте или откройте проект"));
        return;
    }
    
    // Проверяем, есть ли данные в модели бланка заказа
    SimpleListTableModel *simpleListModel = m_controller->simpleListTableModel();
    if (!simpleListModel || simpleListModel->rowCount() == 0) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Бланк заказа пуст. Сначала сгенерируйте таблицу."));
        return;
    }
    
    // Открываем диалог сохранения файла
    QString defaultPath = QCoreApplication::applicationDirPath() + "/БланкЗаказа.csv";
    QString fileName = QFileDialog::getSaveFileName(
        this,
        tr("Экспорт бланка заказа в CSV"),
        defaultPath,
        tr("CSV файлы (*.csv);;Все файлы (*)")
    );
    
    if (!fileName.isEmpty()) {
        m_statusBar->showMessage(tr("Экспорт бланка заказа в CSV: %1").arg(fileName));
        
        // Экспортируем в CSV через MainController
        if (m_controller->exportSimpleListToCsv(fileName)) {
            QMessageBox::information(this, tr("Успех"), 
                                   tr("Бланк заказа успешно экспортирован в CSV:\n%1").arg(fileName));
            m_statusBar->showMessage(tr("Экспорт бланка заказа в CSV завершен"));
        } else {
            QMessageBox::critical(this, tr("Ошибка"), 
                                tr("Не удалось экспортировать бланк заказа в CSV:\n%1").arg(m_controller->lastError()));
            m_statusBar->showMessage(tr("Ошибка экспорта бланка заказа в CSV"));
        }
    }
}

void MainWindow::onUndo(){}

void MainWindow::onRedo(){}

// Слоты для управления видом
void MainWindow::onViewDataPanel()
{
    if (m_dataPanelDockWidget) {
        if (m_dataPanelDockWidget->isVisible()) {
            m_dataPanelDockWidget->hide();
        } else {
            m_dataPanelDockWidget->show();
            m_dataPanelDockWidget->raise();
        }
        updateViewMenuState();
    }
}

void MainWindow::onViewPdfPreview()
{
    if (m_pdfPanelDockWidget) {
        if (m_pdfPanelDockWidget->isVisible()) {
            m_pdfPanelDockWidget->hide();
        } else {
            m_pdfPanelDockWidget->show();
            m_pdfPanelDockWidget->raise();
        }
        updateViewMenuState();
    }
}

void MainWindow::onProjectSettings()
{
    qDebug() << "MainWindow: Открытие диалога настроек проекта";
    
    // Проверяем, открыт ли проект
    if (m_currentProjectPath.isEmpty()) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Сначала создайте или откройте проект"));
        return;
    }
    
    // Загружаем текущие настройки
    m_controller->loadProjectSettingsFromDatabase();
    
    // Обновляем доступные варианты из модели компонентов ПЕРЕД созданием диалога
    QStringList variants = m_controller->componentTableModel()->variants();
    qDebug() << "MainWindow: Доступные варианты из модели компонентов:" << variants;
    m_controller->projectSettingsModel()->setAvailableVariants(variants);
    
    // Создаем диалог настроек
    ProjectSettingsDialog dialog(m_controller->projectSettingsModel(), 
                               m_controller->designatorMappingModel(), this);
    
    if (dialog.exec() == QDialog::Accepted) {
        // Сохраняем настройки в базу данных
        if (m_controller->saveProjectSettingsToDatabase()) {
            m_statusBar->showMessage(tr("Настройки проекта сохранены"));
            
            // Обновляем текущий вариант в компонентах
            QString newVariant = dialog.getCurrentVariant();
            m_controller->setCurrentVariant(newVariant);
            
            // Перезагружаем компоненты с новым вариантом
            m_controller->loadComponentsFromDatabase();
            
            // Синхронизируем выбор варианта в ComponentsPreview
            if (m_dataView && m_dataView->getComponentsPreview()) {
                m_dataView->getComponentsPreview()->setCurrentVariant(newVariant);
            }
            
        } else {
            QMessageBox::critical(this, tr("Ошибка"), 
                               tr("Не удалось сохранить настройки проекта"));
        }
    }
}

void MainWindow::onViewResetLayout()
{
    // Сбрасываем расположение док-виджетов к исходному состоянию
    if (m_dataPanelDockWidget) {
        m_dataPanelDockWidget->setVisible(true);
        addDockWidget(Qt::RightDockWidgetArea, m_dataPanelDockWidget);
    }
    
    if (m_pdfPanelDockWidget) {
        m_pdfPanelDockWidget->setVisible(true);
        addDockWidget(Qt::RightDockWidgetArea, m_pdfPanelDockWidget);
    }
    
    // Накладываем панели друг на друга в виде табов
    tabifyDockWidget(m_dataPanelDockWidget, m_pdfPanelDockWidget);
    
    // Показываем первую панель по умолчанию
    m_dataPanelDockWidget->raise();
    
    updateViewMenuState();
    m_statusBar->showMessage(tr("Расположение панелей сброшено"));
}

void MainWindow::updateViewMenuState()
{
    if (m_viewMenu) {
        QList<QAction*> actions = m_viewMenu->actions();
        for (QAction* action : actions) {
            if (action->text().contains("Панель данных")) {
                action->setChecked(m_dataPanelDockWidget && m_dataPanelDockWidget->isVisible());
            } else if (action->text().contains("PDF Превью")) {
                action->setChecked(m_pdfPanelDockWidget && m_pdfPanelDockWidget->isVisible());
            }
        }
    }
}

void MainWindow::updateWindowTitle()
{
    QString title = "GostGenerator";
    if (!m_currentProjectPath.isEmpty()) {
        QFileInfo fileInfo(m_currentProjectPath);
        title += " - " + fileInfo.fileName();
    } else {
        title += " - Новый проект";
    }
    setWindowTitle(title);
}

void MainWindow::disableInterfaceExceptProjectActions()
{
    // Отключаем все элементы интерфейса кроме создания/открытия проекта
    
    // Отключаем действия в меню
    if (m_fileMenu) {
        QList<QAction*> actions = m_fileMenu->actions();
        for (QAction* action : actions) {
            if (action->text().contains("Новый проект") || action->text().contains("Открыть проект")) {
                action->setEnabled(true);
            } else {
                action->setEnabled(false);
            }
        }
    }
    
    // Отключаем действия в тулбаре
    if (m_toolBar) {
        QList<QAction*> actions = m_toolBar->actions();
        for (QAction* action : actions) {
            if (action->text().contains("Новый проект") || action->text().contains("Открыть проект")) {
                action->setEnabled(true);
            } else if (action->text().contains("Отменить") || action->text().contains("Повторить")) {
                // Кнопки отмены и повтора всегда отключены
                action->setEnabled(false);
            } else {
                action->setEnabled(false);
            }
        }
    }
    
    // Отключаем действия во втором тулбаре
    if (m_toolBar2) {
        QList<QAction*> actions = m_toolBar2->actions();
        for (QAction* action : actions) {
            if (action->text().contains("Отменить") || action->text().contains("Повторить")) {
                // Кнопки отмены и повтора всегда отключены
                action->setEnabled(false);
            } else {
                action->setEnabled(false);
            }
        }
    }
    
    // Отключаем панели данных
    if (m_dataPanelDockWidget) {
        m_dataPanelDockWidget->setEnabled(false);
    }
    if (m_pdfPanelDockWidget) {
        m_pdfPanelDockWidget->setEnabled(false);
    }
    
    // Отключаем центральный виджет
    if (m_centralWidget) {
        m_centralWidget->setEnabled(false);
    }
    
    updateStatusBar();
}

void MainWindow::enableInterface()
{
    // Включаем все элементы интерфейса
    
    // Включаем действия в меню
    if (m_fileMenu) {
        QList<QAction*> actions = m_fileMenu->actions();
        for (QAction* action : actions) {
            action->setEnabled(true);
        }
    }
    
    // Включаем действия в тулбаре
    if (m_toolBar) {
        QList<QAction*> actions = m_toolBar->actions();
        for (QAction* action : actions) {
            if (action->text().contains("Отменить") || action->text().contains("Повторить")) {
                // Кнопки отмены и повтора всегда отключены
                action->setEnabled(false);
            } else {
                action->setEnabled(true);
            }
        }
    }
    
    // Включаем действия во втором тулбаре
    if (m_toolBar2) {
        QList<QAction*> actions = m_toolBar2->actions();
        for (QAction* action : actions) {
            if (action->text().contains("Отменить") || action->text().contains("Повторить")) {
                // Кнопки отмены и повтора всегда отключены
                action->setEnabled(false);
            } else {
                action->setEnabled(true);
            }
        }
    }
    
    // Включаем панели данных
    if (m_dataPanelDockWidget) {
        m_dataPanelDockWidget->setEnabled(true);
    }
    if (m_pdfPanelDockWidget) {
        m_pdfPanelDockWidget->setEnabled(true);
    }
    
    // Включаем центральный виджет
    if (m_centralWidget) {
        m_centralWidget->setEnabled(true);
    }
    
    updateStatusBar();
}

void MainWindow::updateStatusBar()
{
    if (!m_currentProjectPath.isEmpty()) {
        QFileInfo fileInfo(m_currentProjectPath);
        QString statusText = tr("Проект: %1").arg(fileInfo.fileName());
        
        // Добавляем информацию о количестве компонентов
        if (m_controller && m_controller->componentTableModel()) {
            int componentCount = m_controller->componentTableModel()->getComponents().size();
            statusText += tr(" | Компонентов: %1").arg(componentCount);
        }
        
        m_statusBar->showMessage(statusText);
    } else {
        m_statusBar->showMessage(tr("Проект не открыт. Создайте новый проект или откройте существующий для начала работы."));
    }
}

bool MainWindow::askForSave()
{
    // Проверяем, есть ли несохраненные изменения
    bool hasChanges = false;
    
    if (m_controller && m_controller->componentTableModel()) {
        // Проверяем наличие компонентов
        if (m_controller->componentTableModel()->getComponents().size() > 0) {
            hasChanges = true;
        }
        
        // Проверяем наличие параметров проекта
        if (m_controller->projectParamTableModel() && 
            m_controller->projectParamTableModel()->rowCount() > 0) {
            hasChanges = true;
        }
    }
    
    if (hasChanges) {
        QMessageBox::StandardButton reply = QMessageBox::question(
            this, 
            tr("Сохранение проекта"),
            tr("Сохранить изменения в проекте?"),
            QMessageBox::Save | QMessageBox::Discard | QMessageBox::Cancel
        );
        
        if (reply == QMessageBox::Save) {
            return onFileSave();
        } else if (reply == QMessageBox::Cancel) {
            return false; // Отмена выхода
        }
    }
    return true; // Можно выходить
}

// Слоты для асинхронного парсинга
void MainWindow::onParsingStarted()
{
    m_isParsing = true;
    m_progressBar->setVisible(true);
    m_progressBar->setValue(0);
    m_cancelParsingAction->setVisible(true);
    m_statusBar->showMessage(tr("Начало парсинга файла..."));
}

void MainWindow::onParsingFinished(bool success)
{
    m_isParsing = false;
    m_progressBar->setVisible(false);
    m_cancelParsingAction->setVisible(false);
    
    if (success) {
        m_statusBar->showMessage(tr("Парсинг завершен успешно"));
        
        // Загружаем данные из базы в модели
        if (m_controller) {
            qDebug() << "MainWindow: Загружаем данные из базы после парсинга";
            
            // Загружаем компоненты из базы
            bool componentsLoaded = m_controller->loadComponentsFromDatabase();
            qDebug() << "MainWindow: Компоненты загружены:" << componentsLoaded;
            
            // Загружаем параметры проекта из базы
            bool paramsLoaded = m_controller->loadProjectParamsFromDatabase();
            qDebug() << "MainWindow: Параметры проекта загружены:" << paramsLoaded;
        }
        
        // Обновляем отображение данных
        m_dataView->updateView();
        updateStatusBar();
        
        QMessageBox::information(this, tr("Успех"), 
                               tr("Файл успешно импортирован!\n"
                                  "Найдено компонентов: %1\n\n"
                                  "Не забудьте сохранить проект!")
                               .arg(m_controller->componentTableModel()->getComponents().size()));
    } else {
        m_statusBar->showMessage(tr("Ошибка парсинга файла"));
        
        QString errorMessage = m_controller->lastError();
        if (errorMessage.isEmpty()) {
            errorMessage = tr("Неизвестная ошибка при парсинге файла");
        }
        
        QMessageBox::critical(this, tr("Ошибка импорта"), 
                            tr("Не удалось импортировать файл:\n%1").arg(errorMessage));
    }
}

void MainWindow::onParsingProgress(int percentage)
{
    m_progressBar->setValue(percentage);
    m_statusBar->showMessage(tr("Парсинг файла... %1%").arg(percentage));
}

void MainWindow::onParsingError(const QString &error)
{
    m_statusBar->showMessage(tr("Ошибка парсинга: %1").arg(error));
}

PerechenTableModel* MainWindow::getPerechenTableModel() const
{
    // Теперь получаем модель напрямую из MainController
    if (m_controller) {
        return m_controller->perechenTableModel();
    }
    return nullptr;
}

void MainWindow::onExportAll()
{
    qDebug() << "MainWindow::onExportAll: Начинаем экспорт всех документов";
    
    // Проверяем, открыт ли проект
    if (m_currentProjectPath.isEmpty()) {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Сначала создайте или откройте проект"));
        return;
    }
    
    // Получаем путь к папке, где находится файл проекта (.pdfprj)
    QFileInfo projectFileInfo(m_currentProjectPath);
    QString projectDir = projectFileInfo.absolutePath();
    qDebug() << "MainWindow::onExportAll: Папка проекта:" << projectDir;
    
    // Проверяем, есть ли данные для экспорта
    bool hasData = false;
    QStringList exportedFiles;
    
    // Экспорт спецификации материалов
    if (m_controller->specificationTableModel() && 
        m_controller->specificationTableModel()->rowCount() > 0) {
        // Формируем имя файла: поле 2 из TitleInscription + " Спецификация"
        QString fileNameBase = "Спецификация";
        TitleInscriptionsModel *titleModel = m_controller->titleInscriptionsModel();
        ProjectParamTableModel *projectParamModel = m_controller->projectParamTableModel();
        if (titleModel && projectParamModel) {
            QString field2Value = PDFController::getInscriptionValueWithProjectParams(titleModel, projectParamModel, 2);
            if (!field2Value.isEmpty() && field2Value != "-- Не выбрано --") {
                fileNameBase = field2Value + " Спецификация";
            }
        }
        QString fileName = projectDir + "/" + fileNameBase + ".pdf";
        if (m_controller->exportSpecificationToPdf(fileName)) {
            exportedFiles << fileName;
            hasData = true;
        }
    }
    
    // Экспорт спецификации PCB
    if (m_controller->specificationPCBTableModel() && 
        m_controller->specificationPCBTableModel()->rowCount() > 0) {
        // Формируем имя файла: поле 2 из TitleInscription + " Спецификация ПП"
        QString fileNameBase = "Спецификация ПП";
        TitleInscriptionsModel *titleModel = m_controller->titleInscriptionsModel();
        ProjectParamTableModel *projectParamModel = m_controller->projectParamTableModel();
        if (titleModel && projectParamModel) {
            QString field2Value = PDFController::getInscriptionValueWithProjectParams(titleModel, projectParamModel, 2);
            if (!field2Value.isEmpty() && field2Value != "-- Не выбрано --") {
                fileNameBase = field2Value + " Спецификация ПП";
            }
        }
        QString fileName = projectDir + "/" + fileNameBase + ".pdf";
        if (m_controller->exportSpecificationPcbToPdf(fileName)) {
            exportedFiles << fileName;
            hasData = true;
        }
    }
    
    // Экспорт ведомости покупных изделий
    if (m_controller->vedomostTableModel() && 
        m_controller->vedomostTableModel()->rowCount() > 0) {
        // Формируем имя файла: поле 2 из TitleInscription + " ВП"
        QString fileNameBase = "ВП";
        TitleInscriptionsModel *titleModel = m_controller->titleInscriptionsModel();
        ProjectParamTableModel *projectParamModel = m_controller->projectParamTableModel();
        if (titleModel && projectParamModel) {
            QString field2Value = PDFController::getInscriptionValueWithProjectParams(titleModel, projectParamModel, 2);
            if (!field2Value.isEmpty() && field2Value != "-- Не выбрано --") {
                fileNameBase = field2Value + " ВП";
            }
        }
        QString fileName = projectDir + "/" + fileNameBase + ".pdf";
        if (m_controller->exportVedomostToPdf(fileName)) {
            exportedFiles << fileName;
            hasData = true;
        }
    }
    
    // Экспорт перечня элементов
    if (m_controller->perechenTableModel() && 
        m_controller->perechenTableModel()->rowCount() > 0) {
        // Формируем имя файла: поле 2 из TitleInscription + " ПЭ3"
        QString fileNameBase = "ПЭ3";
        TitleInscriptionsModel *titleModel = m_controller->titleInscriptionsModel();
        ProjectParamTableModel *projectParamModel = m_controller->projectParamTableModel();
        if (titleModel && projectParamModel) {
            QString field2Value = PDFController::getInscriptionValueWithProjectParams(titleModel, projectParamModel, 2);
            if (!field2Value.isEmpty() && field2Value != "-- Не выбрано --") {
                fileNameBase = field2Value + " ПЭ3";
            }
        }
        QString fileName = projectDir + "/" + fileNameBase + ".pdf";
        if (m_controller->exportPerechenToPdf(fileName)) {
            exportedFiles << fileName;
            hasData = true;
        }
    }
    
    if (hasData) {
        QString message = tr("Экспорт завершен успешно!\n\nЭкспортированные файлы:\n");
        for (const QString& file : exportedFiles) {
            message += file + "\n";
        }
        message += tr("\nФайлы сохранены в папке проекта.");
        
        QMessageBox::information(this, tr("Успех"), message);
        m_statusBar->showMessage(tr("Экспорт всех документов завершен"));
        
        // Открываем папку с экспортированными файлами
        QUrl folderUrl = QUrl::fromLocalFile(projectDir);
        QDesktopServices::openUrl(folderUrl);
    } else {
        QMessageBox::warning(this, tr("Предупреждение"), 
                           tr("Нет данных для экспорта. Сначала сгенерируйте таблицы документов."));
    }
}

