mainwindow.cpp 20 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686
  1. #include "mainwindow.h"
  2. #include <QFileInfo>
  3. #include <QDebug>
  4. #include <QResizeEvent>
  5. #include <QSplitter>
  6. #include <QVariant>
  7. #include <QDockWidget>
  8. #include <QTextEdit>
  9. #include <QStatusBar>
  10. #include <QCloseEvent>
  11. #include <QVBoxLayout>
  12. #include <QTabBar>
  13. #include <QVariant>
  14. #include <QCoreApplication>
  15. #include <QApplication>
  16. #include <QShortcut>
  17. #include <QSystemTrayIcon>
  18. #include <QWindowStateChangeEvent>
  19. #include <QTimer>
  20. #include "toolbox.h"
  21. #include "notebookexplorer.h"
  22. #include "vnotex.h"
  23. #include "notebookmgr.h"
  24. #include "buffermgr.h"
  25. #include "viewarea.h"
  26. #include <core/configmgr.h>
  27. #include <core/sessionconfig.h>
  28. #include <core/coreconfig.h>
  29. #include <core/events.h>
  30. #include <core/fileopenparameters.h>
  31. #include <widgets/dialogs/exportdialog.h>
  32. #include "viewwindow.h"
  33. #include "outlineviewer.h"
  34. #include <utils/widgetutils.h>
  35. #include "navigationmodemgr.h"
  36. #include "messageboxhelper.h"
  37. #include "systemtrayhelper.h"
  38. #include "titletoolbar.h"
  39. using namespace vnotex;
  40. MainWindow::MainWindow(QWidget *p_parent)
  41. : QMainWindow(p_parent)
  42. {
  43. VNoteX::getInst().setMainWindow(this);
  44. NavigationModeMgr::init(this);
  45. setupUI();
  46. setupShortcuts();
  47. loadStateAndGeometry();
  48. // The signal is particularly useful if your application has to do some last-second cleanup.
  49. // Note that no user interaction is possible in this state.
  50. connect(qApp, &QCoreApplication::aboutToQuit,
  51. this, &MainWindow::closeOnQuit);
  52. connect(&VNoteX::getInst(), &VNoteX::exportRequested,
  53. this, &MainWindow::exportNotes);
  54. }
  55. MainWindow::~MainWindow()
  56. {
  57. // Should be desturcted before status bar.
  58. delete m_viewArea;
  59. m_viewArea = nullptr;
  60. }
  61. void MainWindow::kickOffOnStart(const QStringList &p_paths)
  62. {
  63. QTimer::singleShot(300, [this, p_paths]() {
  64. VNoteX::getInst().initLoad();
  65. emit mainWindowStarted();
  66. emit layoutChanged();
  67. demoWidget();
  68. openFiles(p_paths);
  69. });
  70. }
  71. void MainWindow::openFiles(const QStringList &p_files)
  72. {
  73. for (const auto &file : p_files) {
  74. emit VNoteX::getInst().openFileRequested(file, QSharedPointer<FileOpenParameters>::create());
  75. }
  76. }
  77. void MainWindow::setupUI()
  78. {
  79. setupCentralWidget();
  80. setupDocks();
  81. setupToolBar();
  82. setupStatusBar();
  83. setupTipsArea();
  84. setupSystemTray();
  85. activateDock(m_docks[DockIndex::NavigationDock]);
  86. }
  87. void MainWindow::setupStatusBar()
  88. {
  89. m_statusBarHelper.setupStatusBar(this);
  90. connect(&VNoteX::getInst(), &VNoteX::statusMessageRequested,
  91. statusBar(), &QStatusBar::showMessage);
  92. }
  93. void MainWindow::setupTipsArea()
  94. {
  95. connect(&VNoteX::getInst(), &VNoteX::tipsRequested,
  96. this, &MainWindow::showTips);
  97. }
  98. void MainWindow::createTipsArea()
  99. {
  100. if (m_tipsLabel) {
  101. return;
  102. }
  103. m_tipsLabel = new QLabel(this);
  104. m_tipsLabel->setObjectName("MainWindowTipsLabel");
  105. m_tipsLabel->hide();
  106. m_tipsTimer = new QTimer(this);
  107. m_tipsTimer->setSingleShot(true);
  108. m_tipsTimer->setInterval(3000);
  109. connect(m_tipsTimer, &QTimer::timeout,
  110. this, [this]() {
  111. setTipsAreaVisible(false);
  112. });
  113. }
  114. void MainWindow::setupCentralWidget()
  115. {
  116. m_viewArea = new ViewArea(this);
  117. NavigationModeMgr::getInst().registerNavigationTarget(m_viewArea);
  118. connect(&VNoteX::getInst().getBufferMgr(), &BufferMgr::bufferRequested,
  119. m_viewArea, &ViewArea::openBuffer);
  120. connect(m_viewArea, &ViewArea::statusWidgetChanged,
  121. this, [this](QWidget *p_widget) {
  122. if (m_viewAreaStatusWidget) {
  123. // Will hide it.
  124. statusBar()->removeWidget(m_viewAreaStatusWidget);
  125. }
  126. m_viewAreaStatusWidget = p_widget;
  127. if (m_viewAreaStatusWidget) {
  128. statusBar()->addPermanentWidget(m_viewAreaStatusWidget);
  129. m_viewAreaStatusWidget->show();
  130. }
  131. });
  132. connect(m_viewArea, &ViewArea::currentViewWindowChanged,
  133. this, [this]() {
  134. setWindowTitle(getViewAreaTitle());
  135. });
  136. connect(m_viewArea, &ViewArea::currentViewWindowUpdated,
  137. this, [this]() {
  138. setWindowTitle(getViewAreaTitle());
  139. });
  140. {
  141. auto notebookMgr = &VNoteX::getInst().getNotebookMgr();
  142. connect(notebookMgr, &NotebookMgr::notebookAboutToClose,
  143. this, [this](const Notebook *p_notebook) {
  144. m_viewArea->close(p_notebook, true);
  145. });
  146. connect(notebookMgr, &NotebookMgr::notebookAboutToRemove,
  147. this, [this](const Notebook *p_notebook) {
  148. m_viewArea->close(p_notebook, true);
  149. });
  150. }
  151. setCentralWidget(m_viewArea);
  152. }
  153. void MainWindow::setupDocks()
  154. {
  155. setTabPosition(Qt::LeftDockWidgetArea, QTabWidget::West);
  156. setTabPosition(Qt::RightDockWidgetArea, QTabWidget::East);
  157. setTabPosition(Qt::TopDockWidgetArea, QTabWidget::North);
  158. setTabPosition(Qt::BottomDockWidgetArea, QTabWidget::North);
  159. setDockNestingEnabled(true);
  160. // The order of m_docks should be identical with enum DockIndex.
  161. setupNavigationDock();
  162. setupOutlineDock();
  163. for (int i = 1; i < m_docks.size(); ++i) {
  164. tabifyDockWidget(m_docks[i - 1], m_docks[i]);
  165. }
  166. for (auto dock : m_docks) {
  167. connect(dock, &QDockWidget::visibilityChanged,
  168. this, [this]() {
  169. updateTabBarStyle();
  170. emit layoutChanged();
  171. });
  172. }
  173. // Activate the first dock.
  174. activateDock(m_docks[0]);
  175. }
  176. void MainWindow::activateDock(QDockWidget *p_dock)
  177. {
  178. p_dock->show();
  179. Q_FOREACH(QTabBar* tabBar, this->findChildren<QTabBar*>(QString(), Qt::FindDirectChildrenOnly)) {
  180. bool found = false;
  181. for (int i = 0; i < tabBar->count(); ++i) {
  182. if (p_dock == reinterpret_cast<QWidget *>(tabBar->tabData(i).toULongLong())) {
  183. tabBar->setCurrentIndex(i);
  184. found = true;
  185. break;
  186. }
  187. }
  188. if (found) {
  189. break;
  190. }
  191. }
  192. p_dock->setFocus();
  193. }
  194. void MainWindow::setupNavigationDock()
  195. {
  196. auto dock = new QDockWidget(tr("Navigation"), this);
  197. m_docks.push_back(dock);
  198. dock->setObjectName(QStringLiteral("NavigationDock.vnotex"));
  199. dock->setAllowedAreas(Qt::AllDockWidgetAreas);
  200. setupNavigationToolBox();
  201. dock->setWidget(m_navigationToolBox);
  202. dock->setFocusProxy(m_navigationToolBox);
  203. addDockWidget(Qt::LeftDockWidgetArea, dock);
  204. }
  205. void MainWindow::setupOutlineDock()
  206. {
  207. auto dock = new QDockWidget(tr("Outline"), this);
  208. m_docks.push_back(dock);
  209. dock->setObjectName(QStringLiteral("OutlineDock.vnotex"));
  210. dock->setAllowedAreas(Qt::AllDockWidgetAreas);
  211. setupOutlineViewer();
  212. dock->setWidget(m_outlineViewer);
  213. dock->setFocusProxy(m_outlineViewer);
  214. addDockWidget(Qt::LeftDockWidgetArea, dock);
  215. }
  216. void MainWindow::setupNavigationToolBox()
  217. {
  218. m_navigationToolBox = new ToolBox(this);
  219. m_navigationToolBox->setObjectName("NavigationToolBox.vnotex");
  220. NavigationModeMgr::getInst().registerNavigationTarget(m_navigationToolBox);
  221. const auto &themeMgr = VNoteX::getInst().getThemeMgr();
  222. // Notebook explorer.
  223. setupNotebookExplorer(m_navigationToolBox);
  224. m_navigationToolBox->addItem(m_notebookExplorer,
  225. themeMgr.getIconFile("notebook_explorer.svg"),
  226. tr("Notebooks"),
  227. nullptr);
  228. /*
  229. // History explorer.
  230. auto historyExplorer = new QWidget(this);
  231. m_navigationToolBox->addItem(historyExplorer,
  232. themeMgr.getIconFile("history_explorer.svg"),
  233. tr("History"),
  234. nullptr);
  235. // Tag explorer.
  236. auto tagExplorer = new QWidget(this);
  237. m_navigationToolBox->addItem(tagExplorer,
  238. themeMgr.getIconFile("tag_explorer.svg"),
  239. tr("Tags"),
  240. nullptr);
  241. */
  242. }
  243. void MainWindow::setupNotebookExplorer(QWidget *p_parent)
  244. {
  245. m_notebookExplorer = new NotebookExplorer(p_parent);
  246. connect(&VNoteX::getInst(), &VNoteX::newNotebookRequested,
  247. m_notebookExplorer, &NotebookExplorer::newNotebook);
  248. connect(&VNoteX::getInst(), &VNoteX::newNotebookFromFolderRequested,
  249. m_notebookExplorer, &NotebookExplorer::newNotebookFromFolder);
  250. connect(&VNoteX::getInst(), &VNoteX::importNotebookRequested,
  251. m_notebookExplorer, &NotebookExplorer::importNotebook);
  252. connect(&VNoteX::getInst(), &VNoteX::newFolderRequested,
  253. m_notebookExplorer, &NotebookExplorer::newFolder);
  254. connect(&VNoteX::getInst(), &VNoteX::newNoteRequested,
  255. m_notebookExplorer, &NotebookExplorer::newNote);
  256. connect(&VNoteX::getInst(), &VNoteX::importFileRequested,
  257. m_notebookExplorer, &NotebookExplorer::importFile);
  258. connect(&VNoteX::getInst(), &VNoteX::importFolderRequested,
  259. m_notebookExplorer, &NotebookExplorer::importFolder);
  260. connect(&VNoteX::getInst(), &VNoteX::importLegacyNotebookRequested,
  261. m_notebookExplorer, &NotebookExplorer::importLegacyNotebook);
  262. connect(&VNoteX::getInst(), &VNoteX::locateNodeRequested,
  263. m_notebookExplorer, &NotebookExplorer::locateNode);
  264. auto notebookMgr = &VNoteX::getInst().getNotebookMgr();
  265. connect(notebookMgr, &NotebookMgr::notebooksUpdated,
  266. m_notebookExplorer, &NotebookExplorer::loadNotebooks);
  267. connect(notebookMgr, &NotebookMgr::notebookUpdated,
  268. m_notebookExplorer, &NotebookExplorer::reloadNotebook);
  269. connect(notebookMgr, &NotebookMgr::currentNotebookChanged,
  270. m_notebookExplorer, &NotebookExplorer::setCurrentNotebook);
  271. connect(m_notebookExplorer, &NotebookExplorer::notebookActivated,
  272. notebookMgr, &NotebookMgr::setCurrentNotebook);
  273. }
  274. void MainWindow::closeEvent(QCloseEvent *p_event)
  275. {
  276. const int toTray = ConfigMgr::getInst().getSessionConfig().getMinimizeToSystemTray();
  277. bool isExit = m_requestQuit > -1 || toTray == 0;
  278. const int exitCode = m_requestQuit;
  279. m_requestQuit = -1;
  280. #if defined(Q_OS_MACOS)
  281. // Do not support minimized to tray on macOS.
  282. isExit = true;
  283. #endif
  284. bool needShowMessage = false;
  285. if(!isExit && toTray == -1){
  286. int ret = MessageBoxHelper::questionYesNo(MessageBoxHelper::Question,
  287. tr("Do you want to minimize %1 to system tray "
  288. "instead of quitting when closed?").arg(qApp->applicationName()),
  289. tr("You could change the option in Settings later."),
  290. QString(),
  291. this);
  292. if (ret == QMessageBox::Yes) {
  293. ConfigMgr::getInst().getSessionConfig().setMinimizeToSystemTray(true);
  294. needShowMessage = true;
  295. } else if (ret == QMessageBox::No) {
  296. ConfigMgr::getInst().getSessionConfig().setMinimizeToSystemTray(false);
  297. isExit = true;
  298. } else {
  299. p_event->ignore();
  300. return;
  301. }
  302. }
  303. if (isVisible()) {
  304. saveStateAndGeometry();
  305. }
  306. if (isExit || !m_trayIcon->isVisible()) {
  307. // Signal out the close event.
  308. auto event = QSharedPointer<Event>::create();
  309. event->m_response = true;
  310. emit mainWindowClosed(event);
  311. if (!event->m_response.toBool()) {
  312. // Stop the close.
  313. p_event->ignore();
  314. return;
  315. }
  316. QMainWindow::closeEvent(p_event);
  317. qApp->exit(exitCode > -1 ? exitCode : 0);
  318. } else {
  319. hide();
  320. p_event->ignore();
  321. if (needShowMessage) {
  322. m_trayIcon->showMessage(ConfigMgr::c_appName, tr("%1 is still running here.").arg(ConfigMgr::c_appName));
  323. }
  324. }
  325. }
  326. void MainWindow::saveStateAndGeometry()
  327. {
  328. if (m_layoutReset) {
  329. return;
  330. }
  331. SessionConfig::MainWindowStateGeometry sg;
  332. sg.m_mainState = saveState();
  333. sg.m_mainGeometry = saveGeometry();
  334. auto& sessionConfig = ConfigMgr::getInst().getSessionConfig();
  335. sessionConfig.setMainWindowStateGeometry(sg);
  336. }
  337. void MainWindow::loadStateAndGeometry()
  338. {
  339. const auto& sessionConfig = ConfigMgr::getInst().getSessionConfig();
  340. const auto sg = sessionConfig.getMainWindowStateGeometry();
  341. if (!sg.m_mainGeometry.isEmpty()) {
  342. restoreGeometry(sg.m_mainGeometry);
  343. }
  344. if (!sg.m_mainState.isEmpty()) {
  345. // Will also restore the state of dock widgets.
  346. restoreState(sg.m_mainState);
  347. }
  348. }
  349. void MainWindow::resetStateAndGeometry()
  350. {
  351. if (m_layoutReset) {
  352. return;
  353. }
  354. m_layoutReset = true;
  355. SessionConfig::MainWindowStateGeometry sg;
  356. auto& sessionConfig = ConfigMgr::getInst().getSessionConfig();
  357. sessionConfig.setMainWindowStateGeometry(sg);
  358. }
  359. void MainWindow::setContentAreaExpanded(bool p_expanded)
  360. {
  361. for (auto dock : m_docks) {
  362. if (!dock->isFloating()) {
  363. dock->setVisible(!p_expanded);
  364. }
  365. }
  366. }
  367. bool MainWindow::isContentAreaExpanded() const
  368. {
  369. for (auto dock : m_docks) {
  370. if (!dock->isFloating() && dock->isVisible()) {
  371. return false;
  372. }
  373. }
  374. return true;
  375. }
  376. void MainWindow::demoWidget()
  377. {
  378. }
  379. QString MainWindow::getViewAreaTitle() const
  380. {
  381. QString title;
  382. const auto win = m_viewArea->getCurrentViewWindow();
  383. if (win) {
  384. title = win->getName();
  385. }
  386. return title.isEmpty() ? QString() : QString("%1 - %2").arg(title, ConfigMgr::c_appName);
  387. }
  388. void MainWindow::setupOutlineViewer()
  389. {
  390. // Do not provide title here since there is one in the dock title.
  391. m_outlineViewer = new OutlineViewer(QString(), this);
  392. m_outlineViewer->setObjectName("OutlineViewer.vnotex");
  393. NavigationModeMgr::getInst().registerNavigationTarget(m_outlineViewer->getNavigationModeWrapper());
  394. connect(m_viewArea, &ViewArea::currentViewWindowChanged,
  395. this, [this]() {
  396. auto win = m_viewArea->getCurrentViewWindow();
  397. m_outlineViewer->setOutlineProvider(win ? win->getOutlineProvider() : nullptr);
  398. });
  399. connect(m_outlineViewer, &OutlineViewer::focusViewArea,
  400. this, &MainWindow::focusViewArea);
  401. }
  402. const QVector<QDockWidget *> &MainWindow::getDocks() const
  403. {
  404. return m_docks;
  405. }
  406. void MainWindow::focusViewArea()
  407. {
  408. m_viewArea->focus();
  409. }
  410. void MainWindow::setupToolBar()
  411. {
  412. const int sz = ConfigMgr::getInst().getCoreConfig().getToolBarIconSize();
  413. const QSize iconSize(sz, sz);
  414. if (!ConfigMgr::getInst().getSessionConfig().getSystemTitleBarEnabled()) {
  415. // Use unified tool bar as title bar.
  416. auto framelessFlags = Qt::WindowTitleHint | Qt::WindowSystemMenuHint | Qt::WindowMinMaxButtonsHint
  417. | Qt::WindowCloseButtonHint | Qt::WindowFullscreenButtonHint;
  418. auto winFlags = windowFlags();
  419. winFlags |= Qt::CustomizeWindowHint;
  420. winFlags &= ~framelessFlags;
  421. setWindowFlags(winFlags);
  422. auto toolBar = new TitleToolBar(tr("Global"), this);
  423. toolBar->setIconSize(iconSize);
  424. m_toolBarHelper.setupToolBars(this, toolBar);
  425. toolBar->addTitleBarIcons(ToolBarHelper::generateIcon(QStringLiteral("minimize.svg")),
  426. ToolBarHelper::generateIcon(QStringLiteral("maximize.svg")),
  427. ToolBarHelper::generateIcon(QStringLiteral("maximize_restore.svg")),
  428. ToolBarHelper::generateDangerousIcon(QStringLiteral("close.svg")));
  429. } else {
  430. auto toolBar = new QToolBar(tr("Global"), this);
  431. toolBar->setIconSize(iconSize);
  432. m_toolBarHelper.setupToolBars(this, toolBar);
  433. }
  434. // Disable the context menu above tool bar.
  435. setContextMenuPolicy(Qt::NoContextMenu);
  436. }
  437. void MainWindow::closeOnQuit()
  438. {
  439. // No user interaction is available.
  440. emit mainWindowClosedOnQuit();
  441. }
  442. void MainWindow::setupShortcuts()
  443. {
  444. const auto &coreConfig = ConfigMgr::getInst().getCoreConfig();
  445. // Focus Navigation dock.
  446. {
  447. auto keys = coreConfig.getShortcut(CoreConfig::Shortcut::NavigationDock);
  448. auto shortcut = WidgetUtils::createShortcut(keys, this);
  449. if (shortcut) {
  450. auto dock = m_docks[DockIndex::NavigationDock];
  451. dock->setToolTip(QString("%1\t%2").arg(dock->windowTitle(),
  452. QKeySequence(keys).toString(QKeySequence::NativeText)));
  453. connect(shortcut, &QShortcut::activated,
  454. this, [this]() {
  455. activateDock(m_docks[DockIndex::NavigationDock]);
  456. });
  457. }
  458. }
  459. // Focus Outline dock.
  460. {
  461. auto keys = coreConfig.getShortcut(CoreConfig::Shortcut::OutlineDock);
  462. auto shortcut = WidgetUtils::createShortcut(keys, this);
  463. if (shortcut) {
  464. auto dock = m_docks[DockIndex::OutlineDock];
  465. dock->setToolTip(QString("%1\t%2").arg(dock->windowTitle(),
  466. QKeySequence(keys).toString(QKeySequence::NativeText)));
  467. connect(shortcut, &QShortcut::activated,
  468. this, [this]() {
  469. activateDock(m_docks[DockIndex::OutlineDock]);
  470. });
  471. }
  472. }
  473. }
  474. void MainWindow::setStayOnTop(bool p_enabled)
  475. {
  476. bool shown = isVisible();
  477. Qt::WindowFlags flags = windowFlags();
  478. const Qt::WindowFlags magicFlag = Qt::WindowStaysOnTopHint;
  479. if (p_enabled) {
  480. setWindowFlags(flags | magicFlag);
  481. } else {
  482. setWindowFlags(flags ^ magicFlag);
  483. }
  484. if (shown) {
  485. show();
  486. }
  487. }
  488. void MainWindow::setupSystemTray()
  489. {
  490. m_trayIcon = SystemTrayHelper::setupSystemTray(this);
  491. m_trayIcon->show();
  492. }
  493. void MainWindow::restart()
  494. {
  495. m_requestQuit = RESTART_EXIT_CODE;
  496. close();
  497. }
  498. void MainWindow::changeEvent(QEvent *p_event)
  499. {
  500. if (p_event->type() == QEvent::WindowStateChange) {
  501. QWindowStateChangeEvent *eve = static_cast<QWindowStateChangeEvent *>(p_event);
  502. m_windowOldState = eve->oldState();
  503. }
  504. QMainWindow::changeEvent(p_event);
  505. }
  506. void MainWindow::showMainWindow()
  507. {
  508. if (isMinimized()) {
  509. if (m_windowOldState & Qt::WindowMaximized) {
  510. showMaximized();
  511. } else if (m_windowOldState & Qt::WindowFullScreen) {
  512. showFullScreen();
  513. } else {
  514. showNormal();
  515. }
  516. } else {
  517. show();
  518. // Need to call raise() in macOS.
  519. raise();
  520. }
  521. activateWindow();
  522. }
  523. void MainWindow::quitApp()
  524. {
  525. m_requestQuit = 0;
  526. close();
  527. }
  528. void MainWindow::updateTabBarStyle()
  529. {
  530. Q_FOREACH(QTabBar* tabBar, this->findChildren<QTabBar*>(QString(), Qt::FindDirectChildrenOnly)) {
  531. tabBar->setDrawBase(false);
  532. }
  533. }
  534. void MainWindow::exportNotes()
  535. {
  536. auto currentNotebook = m_notebookExplorer->currentNotebook().data();
  537. auto viewWindow = m_viewArea->getCurrentViewWindow();
  538. auto folderNode = m_notebookExplorer->currentExploredFolderNode();
  539. if (folderNode && (folderNode->isRoot() || currentNotebook->isRecycleBinNode(folderNode))) {
  540. folderNode = nullptr;
  541. }
  542. auto noteNode = m_notebookExplorer->currentExploredNode();
  543. if (noteNode && !noteNode->hasContent()) {
  544. noteNode = nullptr;
  545. }
  546. ExportDialog dialog(currentNotebook,
  547. folderNode,
  548. noteNode,
  549. viewWindow ? viewWindow->getBuffer() : nullptr,
  550. this);
  551. dialog.exec();
  552. }
  553. void MainWindow::showTips(const QString &p_message, int p_timeoutMilliseconds)
  554. {
  555. createTipsArea();
  556. m_tipsTimer->stop();
  557. setTipsAreaVisible(false);
  558. if (p_message.isEmpty()) {
  559. return;
  560. }
  561. m_tipsLabel->setText(p_message);
  562. setTipsAreaVisible(true);
  563. m_tipsTimer->start(p_timeoutMilliseconds);
  564. }
  565. void MainWindow::setTipsAreaVisible(bool p_visible)
  566. {
  567. Q_ASSERT(m_tipsLabel);
  568. if (p_visible) {
  569. m_tipsLabel->adjustSize();
  570. int labelW = m_tipsLabel->width();
  571. int labelH = m_tipsLabel->height();
  572. int x = (width() - labelW) / 2;
  573. int y = (height() - labelH) / 2;
  574. if (x < 0) {
  575. x = 0;
  576. }
  577. if (y < 0) {
  578. y = 0;
  579. }
  580. m_tipsLabel->move(x, y);
  581. m_tipsLabel->show();
  582. } else {
  583. m_tipsLabel->hide();
  584. }
  585. }