From d353fd03779e7b35cb97920239ae6113492b845f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=95=D0=B3=D0=BE=D1=80=20=D0=93=D0=B0=D0=BB=D0=BA=D0=B8?= =?UTF-8?q?=D0=BD?= Date: Wed, 13 Jan 2021 19:31:34 +0000 Subject: [PATCH] Add new file --- mainwindow.cpp | 527 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 527 insertions(+) create mode 100644 mainwindow.cpp diff --git a/mainwindow.cpp b/mainwindow.cpp new file mode 100644 index 0000000..8027f35 --- /dev/null +++ b/mainwindow.cpp @@ -0,0 +1,527 @@ +#include "mainwindow.h" +#include "ui_mainwindow.h" +#include + +MainWindow::MainWindow(QWidget *parent) : + QMainWindow(parent), + ui(new Ui::MainWindow), + pre_exit_menu(nullptr), + new_file(new QAction(QIcon(":/catalogA/icons/new_file.png"), "Create New File")), + open_file(new QAction(QIcon(":/catalogA/icons/open_file.png"), "Open File")), + save_file(new QAction(QIcon(":/catalogA/icons/save_file.png"), "Save File")), + save_all_files(new QAction(QIcon(":/catalogA/icons/save_all_files.png"),"Save All Files")), + number(1), + bug_crutch(true) +{ + ui->setupUi(this); + setAcceptDrops(true); + setWindowIcon(QIcon(":/catalogA/icons/icon.ico")); + setWindowTitle("Text Editor"); + + SetupTabWidget(); + SetupFileExplorerDock(); + SetupOpenedDocsDock(); + CreateFile(); + SetupMenuBar(); + SetupToolBar(); + + setCentralWidget(tabs); + tabs->currentWidget()->setFocus(); + highlighter = new Highlighter(":/catalogA/highlights/languages.xml", this); + + connect(new_file, SIGNAL(triggered()), SLOT(CreateFile())); + new_file->setShortcut(Qt::CTRL + Qt::Key_N); + connect(open_file, SIGNAL(triggered()), SLOT(OpenFile())); + open_file->setShortcut(Qt::CTRL + Qt::Key_O); + connect(save_file, SIGNAL(triggered()), SLOT(SaveFile())); + save_file->setShortcut(Qt::CTRL + Qt::Key_S); + connect(save_all_files, SIGNAL(triggered()), SLOT(SaveAllFiles())); +} + +MainWindow::~MainWindow() +{ + delete ui; +} + +void MainWindow::dragEnterEvent(QDragEnterEvent* drag_event) +{ + if (drag_event->mimeData()->hasUrls()) + drag_event->acceptProposedAction(); +} + +void MainWindow::dropEvent(QDropEvent* drop_event) +{ + QList url_list = drop_event->mimeData()->urls(); + foreach (QUrl url, url_list) { + OpenFile(url.url(QUrl::RemoveScheme)); + } +} + +void MainWindow::SetupTabWidget() +{ + tabs = new QTabWidget(this); + tabs->setMovable(true); + tabs->setTabsClosable(true); + tabs->setUsesScrollButtons(true); + connect(tabs, SIGNAL(tabCloseRequested(int)), this, SLOT(CloseFile(int))); + QToolButton* new_tab_button = new QToolButton(this); + new_tab_button->setText("+"); + connect(new_tab_button, SIGNAL(clicked()), SLOT(CreateFile())); + tabs->setCornerWidget(new_tab_button, Qt::TopRightCorner); +} + +void MainWindow::SetupMenuBar() +{ + QMenu* fileMenu = new QMenu("File", this); + QMenu* editMenu = new QMenu("Edit", this); + QMenu* viewMenu = new QMenu("View", this); + + fileMenu->addAction(new_file); + fileMenu->addAction(open_file); + fileMenu->addSeparator(); + fileMenu->addAction(save_file); + fileMenu->addAction("Save As...", this, SLOT(SaveFileAs()), Qt::SHIFT + Qt::CTRL + Qt::Key_S); + fileMenu->addAction(save_all_files); + fileMenu->addSeparator(); + fileMenu->addAction("Close File", this, SLOT(CloseFile()), Qt::CTRL + Qt::Key_W); + fileMenu->addAction("Close All", this, SLOT(CloseAllFiles()), Qt::SHIFT + Qt::CTRL + Qt::Key_W); + fileMenu->addSeparator(); + fileMenu->addAction("Exit", this, SLOT(CloseWindow()), Qt::CTRL + Qt::Key_Q); + + editMenu->addAction("Cut", this, SLOT(slotCut()), Qt::CTRL + Qt::Key_X); + editMenu->addAction("Copy", this, SLOT(slotCopy()), Qt::CTRL + Qt::Key_C); + editMenu->addAction("Paste", this, SLOT(slotPaste()), Qt::CTRL + Qt::Key_V); + editMenu->addAction("Delete", this, SLOT(slotClear()), Qt::CTRL + Qt::Key_Backspace); + editMenu->addAction("Select All", this, SLOT(slotSelectAll()), Qt::CTRL + Qt::Key_A); + + viewMenu->addAction(file_explorer_dock->toggleViewAction()); + viewMenu->addAction(opened_docs_dock->toggleViewAction()); + + ui->menubar->addMenu(fileMenu); + ui->menubar->addMenu(editMenu); + ui->menubar->addMenu(viewMenu); +} + +void MainWindow::SetupToolBar() +{ + ui->mainToolBar->addAction(new_file); + ui->mainToolBar->addAction(open_file); + ui->mainToolBar->addAction(save_file); + ui->mainToolBar->addAction(save_all_files); +} + +void MainWindow::SetupFileExplorerDock() +{ + file_system_model = new QDirModel(this); + file_system_view = new QTreeView(this); + file_system_view->setModel(file_system_model); + file_system_view->setRootIndex(file_system_model->index("/home")); + file_system_view->setColumnHidden(1, true); + file_system_view->setColumnHidden(2, true); + file_system_view->setColumnHidden(3, true); + file_system_view->setHeaderHidden(true); + connect(file_system_view, SIGNAL(doubleClicked(QModelIndex)), SLOT(OpenFile(QModelIndex))); + + file_explorer_dock = new QDockWidget("File explorer", this); + + file_explorer_dock->setWidget(file_system_view); + file_explorer_dock->setFeatures(QDockWidget::DockWidgetClosable); + file_explorer_dock->hide(); + + addDockWidget(Qt::LeftDockWidgetArea, file_explorer_dock); +} + +void MainWindow::SetupOpenedDocsDock() +{ + opened_docs_widget = new QListWidget(this); + + connect(tabs->tabBar(), SIGNAL(tabMoved(int, int)), SLOT(ChangeTabIndexInList(int, int))); + connect(opened_docs_widget, SIGNAL(itemClicked(QListWidgetItem*)),SLOT(UpdateCurrentIndex(QListWidgetItem*))); + connect(opened_docs_widget, SIGNAL(currentRowChanged(int)), tabs, SLOT(setCurrentIndex(int))); + connect(tabs->tabBar(), SIGNAL(currentChanged(int)), SLOT(UpdateCurrentIndex(int))); + connect(tabs->tabBar(), SIGNAL(tabCloseRequested(int)), SLOT(UpdateCurrentIndexOnDelete(int))); + connect(tabs->tabBar(), SIGNAL(tabMoved(int, int)), SLOT(UpdateContains(int, int))); + + opened_docs_dock = new QDockWidget("Opened files", this); + + opened_docs_dock->setWidget(opened_docs_widget); + opened_docs_dock->setFeatures(QDockWidget::DockWidgetClosable); + opened_docs_dock->hide(); + addDockWidget(Qt::RightDockWidgetArea, opened_docs_dock); +} + +void MainWindow::CreateFile() +{ + CodeEditor* new_text_edit = new CodeEditor(this); + int index = tabs->addTab(new_text_edit, "untitled" + QString::number(number)); + tabs->setCurrentIndex(index); + tabs->setTabToolTip(index, ""); + tabs->setTabWhatsThis(index, "No changes"); + connect(new_text_edit, SIGNAL(textChanged()), SLOT(UpdateParameter())); + + file_path_for_exit_menu.push_back(QDir::current()); + file_name_for_exit_menu.push_back("untitled" + QString::number(number)); + number++; + + QListWidgetItem* new_item = new QListWidgetItem; + new_item->setText(tabs->tabText(index)); + new_item->setToolTip(tabs->tabToolTip(index)); + opened_docs_widget->addItem(new_item); + + UpdateCurrentIndex(index); +} + +void MainWindow::OpenFile() +{ + QString filepath = QFileDialog::getOpenFileName(this, "Choose file", "/home"); + if (filepath.isEmpty()) + return; + OpenFile(filepath); +} + +void MainWindow::OpenFile(const QString& filepath) +{ + for (int i = 0; i < tabs->count(); ++i) + if (tabs->tabToolTip(i) == filepath) + { + QMessageBox::warning(this, "Duplicate", "Cannot open one file twice!", + QMessageBox::Ok); + return; + } + + QString filename = filepath.section("/",-1,-1); + QFile file(filepath); + + if (file.open(QIODevice::ReadOnly)) + { + CodeEditor* temp_text = (CodeEditor*)tabs->currentWidget(); + if (temp_text->document()->isEmpty() && + tabs->tabToolTip(tabs->currentIndex()) == "" && + tabs->tabText(tabs->currentIndex()) == "untitled") + { + + DeleteTabFromList(tabs->currentIndex()); + delete tabs->widget(tabs->currentIndex()); + } + + file_path_for_exit_menu.push_back(QFileInfo(file).path()); + file_name_for_exit_menu.push_back(filename); + + CodeEditor* new_text_edit = new CodeEditor(this); + QString content = file.readAll(); + file.close(); + new_text_edit->appendPlainText(content); + int index = tabs->addTab(new_text_edit, filename); + tabs->setCurrentIndex(index); + tabs->setTabToolTip(index, filepath); + tabs->setTabWhatsThis(index, "No changes"); + + QListWidgetItem* new_item = new QListWidgetItem; + new_item->setText(tabs->tabText(index)); + new_item->setToolTip(tabs->tabToolTip(index)); + opened_docs_widget->addItem(new_item); + + QString file_extension = QFileInfo(filename).suffix(); + if (highlighter->setExtension(file_extension)) + { + highlighter->setDocument(new_text_edit->document()); + highlighter->highlightBlock(new_text_edit->toPlainText()); + } + + tabs->setTabWhatsThis(index, "No changes"); + UpdateCurrentIndex(index); + + connect(new_text_edit, SIGNAL(textChanged()), SLOT(UpdateParameter())); + bug_crutch = false; + } + else + { + (new QErrorMessage(this))->showMessage("Cannot open file!"); + return; + } + +} + +void MainWindow::SaveFile() +{ + if (tabs->tabToolTip(tabs->currentIndex()) == "") + { + SaveFileAs(); + return; + } + QString filepath = tabs->tabToolTip(tabs->currentIndex()); + QFile file(filepath); + if (file.open(QIODevice::WriteOnly)) + { + file.write(((CodeEditor*)tabs->currentWidget())->document()->toPlainText().toUtf8()); + file.close(); + tabs->setTabWhatsThis(tabs->currentIndex(), "No changes"); + } + else + { + (new QErrorMessage(this))->showMessage("Cannot save file!"); + return; + } +} + +void MainWindow::SaveFileAs() +{ + QString filename = tabs->tabText(tabs->currentIndex()); + filename.remove('*'); + QString filepath = QFileDialog::getSaveFileName(this, "Save " + filename, "/home/" + filename); + if (filepath.isEmpty()) + return; + if (QFileInfo(filepath).suffix().isEmpty()) + filepath.append(".txt"); + else + { + QFile file(filepath); + if (file.open(QIODevice::WriteOnly)) + { + file.write(((CodeEditor*)tabs->currentWidget())->document()->toPlainText().toUtf8()); + file.close(); + } + else + { + (new QErrorMessage(this))->showMessage("Cannot save file!"); + return; + } + } + + file_path_for_exit_menu.replace(tabs->currentIndex(), QDir(QFileInfo(filepath).path())); + file_name_for_exit_menu.replace(tabs->currentIndex(), (QFileInfo(filepath).fileName())); + + filename = filepath.section("/",-1,-1); + tabs->tabBar()->setTabText(tabs->currentIndex(), filename); + tabs->tabBar()->setTabToolTip(tabs->currentIndex(), filepath); + + QString file_extension = QFileInfo(filename).suffix(); + if (highlighter->setExtension(file_extension)) + { + highlighter->setDocument(((CodeEditor*)tabs->currentWidget())->document()); + highlighter->highlightBlock(((CodeEditor*)tabs->currentWidget())->toPlainText()); + } + + tabs->setTabWhatsThis(tabs->currentIndex(), "No changes"); + + MainWindow::SaveFile(); +} + +void MainWindow::SaveAllFiles() +{ + int current_index = tabs->currentIndex(); + for (int i = 0; i < tabs->count(); ++i) + { + tabs->setCurrentIndex(i); + if (tabs->tabWhatsThis(tabs->currentIndex()) != "No changes") + SaveFile(); + } + tabs->setCurrentIndex(current_index); +} + +void MainWindow::CloseFile(int index_) +{ + if (tabs->tabWhatsThis(tabs->currentIndex()) != "No changes") + { + QMessageBox::StandardButton reply; + reply = QMessageBox::question(this, "Saving changes", "Save changes before closing?", + QMessageBox::Yes | QMessageBox::No); + if (reply == QMessageBox::Yes) + { + SaveFile(); + } + } + + file_path_for_exit_menu.remove(index_); + file_name_for_exit_menu.removeAt(index_); + + delete tabs->widget(index_); + + DeleteTabFromList(index_); + + if (!tabs->count()) + CreateFile(); + tabs->currentWidget()->setFocus(); +} + +void MainWindow::CloseFile() +{ + CloseFile(tabs->currentIndex()); +} + +void MainWindow::CloseAllFiles() +{ + bool checker = false; + for (int i = 0; i < tabs->count(); ++i) + { + if (tabs->tabWhatsThis(i) != "No changes") + { + checker = true; + break; + } + } + if (checker) + { + QMessageBox::StandardButton reply = QMessageBox::question( + this, "Save all changes", "Save all changes before closing?", + QMessageBox::Yes | QMessageBox::No); + if (reply == QMessageBox::Yes) + SaveAllFiles(); + } + + file_path_for_exit_menu.clear(); + file_name_for_exit_menu.clear(); + number = 1; + + while (tabs->count() > 0) + delete tabs->widget(0); + + opened_docs_widget->clear(); + + CreateFile(); + tabs->currentWidget()->setFocus(); +} + +void MainWindow::CloseWindow() +{ + if(pre_exit_menu) + delete pre_exit_menu; + pre_exit_menu = new ExitMenu(this); + pre_exit_menu->setWindowTitle("Save all changes?"); + + QVector temp_path; + QStringList temp_file_names; + + for(int i = 0; i < tabs->count(); i++) + { + if(tabs->tabText(i).contains('*')) + { + temp_path.push_back(file_path_for_exit_menu[i]); + temp_file_names.push_back(file_name_for_exit_menu[i]); + } + } + + if(!temp_path.isEmpty()) + { + pre_exit_menu->Fill(temp_path, temp_file_names); + int event = pre_exit_menu->exec(); + if(event == QDialog::Accepted) + SaveAllFiles(); + if(event != -1) + QApplication::quit(); + } + else + QApplication::quit(); +} + +void MainWindow::closeEvent(QCloseEvent* event) +{ + event->ignore(); + CloseWindow(); +} + +void::MainWindow::UpdateParameter() +{ + QString file = tabs->tabBar()->tabText(tabs->currentIndex()); + QString file_extension = QFileInfo(file).suffix(); + if (!file_extension.isEmpty()) + { + if (highlighter->setExtension(file_extension)) + { + if(bug_crutch) + { + tabs->setTabWhatsThis(tabs->currentIndex(), "Changed"); + tabs->setTabText(tabs->currentIndex(), tabs->tabText(tabs->currentIndex()) + "*"); + disconnect(sender(), SIGNAL(textChanged()), this, SLOT(UpdateParameter())); + } + else + bug_crutch = true; + return; + } + } + + tabs->setTabWhatsThis(tabs->currentIndex(), "Changed"); + tabs->setTabText(tabs->currentIndex(), tabs->tabText(tabs->currentIndex()) + "*"); + disconnect(sender(), SIGNAL(textChanged()), this, SLOT(UpdateParameter())); +} + + +void MainWindow::OpenFile(QModelIndex file_index) +{ + if (!file_system_model->isDir(file_index)) + OpenFile(file_system_model->filePath(file_index)); +} + +void MainWindow::DeleteTabFromList(int index) +{ + QListWidgetItem* temp_item = opened_docs_widget->takeItem(index); + delete temp_item; +} + +void MainWindow::ChangeTabIndexInList(int old_index, int new_index) +{ + QListWidgetItem* first_item = opened_docs_widget->takeItem(old_index); + opened_docs_widget->insertItem(new_index, first_item); +} + +void MainWindow::UpdateCurrentIndex(QListWidgetItem* current_item) +{ + int index = current_item->listWidget()->row(current_item); + tabs->setCurrentIndex(index); +} + +void MainWindow::UpdateCurrentIndex(int new_selection_index) +{ + opened_docs_widget->setCurrentRow(new_selection_index); + + QString file = tabs->tabBar()->tabText(new_selection_index); + QString file_extension = QFileInfo(file).suffix(); + if (!file_extension.isEmpty()) + { + if (highlighter->setExtension(file_extension)) + { + highlighter->setDocument(((CodeEditor*)tabs->currentWidget())->document()); + highlighter->highlightBlock(((CodeEditor*)tabs->currentWidget())->toPlainText()); + } + } +} + +void MainWindow::UpdateCurrentIndexOnDelete(int) +{ + opened_docs_widget->setCurrentRow(opened_docs_widget->count() - 1); +} + +void MainWindow::slotCopy() +{ + ((CodeEditor*)tabs->currentWidget())->copy(); +} + +void MainWindow::slotCut() +{ + ((CodeEditor*)tabs->currentWidget())->cut(); +} + +void MainWindow::slotSelectAll() +{ + ((CodeEditor*)tabs->currentWidget())->selectAll(); +} + +void MainWindow::slotPaste() +{ + ((CodeEditor*)tabs->currentWidget())->paste(); +} + +void MainWindow::slotClear() +{ + ((CodeEditor*)tabs->currentWidget())->clear(); +} + +void MainWindow::UpdateContains(int from, int to) +{ + QDir temp = file_path_for_exit_menu.at(from); + file_path_for_exit_menu.replace(from, file_path_for_exit_menu.at(to)); + file_path_for_exit_menu.replace(to, temp); + QString temp_file_name = file_name_for_exit_menu.at(from); + file_name_for_exit_menu.replace(from, file_name_for_exit_menu.at(to)); + file_name_for_exit_menu.replace(to, temp_file_name); +} \ No newline at end of file -- GitLab