Bitcoin Core  0.20.99
P2P Digital Currency
bitcoingui.cpp
Go to the documentation of this file.
1 // Copyright (c) 2011-2020 The Bitcoin Core developers
2 // Distributed under the MIT software license, see the accompanying
3 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
4 
5 #include <qt/bitcoingui.h>
6 
7 #include <qt/bitcoinunits.h>
8 #include <qt/clientmodel.h>
10 #include <qt/guiconstants.h>
11 #include <qt/guiutil.h>
12 #include <qt/modaloverlay.h>
13 #include <qt/networkstyle.h>
14 #include <qt/notificator.h>
15 #include <qt/openuridialog.h>
16 #include <qt/optionsdialog.h>
17 #include <qt/optionsmodel.h>
18 #include <qt/platformstyle.h>
19 #include <qt/rpcconsole.h>
20 #include <qt/utilitydialog.h>
21 
22 #ifdef ENABLE_WALLET
23 #include <qt/walletcontroller.h>
24 #include <qt/walletframe.h>
25 #include <qt/walletmodel.h>
26 #include <qt/walletview.h>
27 #endif // ENABLE_WALLET
28 
29 #ifdef Q_OS_MAC
30 #include <qt/macdockiconhandler.h>
31 #endif
32 
33 #include <chain.h>
34 #include <chainparams.h>
35 #include <interfaces/handler.h>
36 #include <interfaces/node.h>
37 #include <ui_interface.h>
38 #include <util/system.h>
39 #include <util/translation.h>
40 #include <validation.h>
41 
42 #include <QAction>
43 #include <QApplication>
44 #include <QComboBox>
45 #include <QDateTime>
46 #include <QDragEnterEvent>
47 #include <QListWidget>
48 #include <QMenu>
49 #include <QMenuBar>
50 #include <QMessageBox>
51 #include <QMimeData>
52 #include <QProgressDialog>
53 #include <QScreen>
54 #include <QSettings>
55 #include <QShortcut>
56 #include <QStackedWidget>
57 #include <QStatusBar>
58 #include <QStyle>
59 #include <QSystemTrayIcon>
60 #include <QTimer>
61 #include <QToolBar>
62 #include <QUrlQuery>
63 #include <QVBoxLayout>
64 #include <QWindow>
65 
66 
67 const std::string BitcoinGUI::DEFAULT_UIPLATFORM =
68 #if defined(Q_OS_MAC)
69  "macosx"
70 #elif defined(Q_OS_WIN)
71  "windows"
72 #else
73  "other"
74 #endif
75  ;
76 
77 BitcoinGUI::BitcoinGUI(interfaces::Node& node, const PlatformStyle *_platformStyle, const NetworkStyle *networkStyle, QWidget *parent) :
78  QMainWindow(parent),
79  m_node(node),
80  trayIconMenu{new QMenu()},
81  platformStyle(_platformStyle),
82  m_network_style(networkStyle)
83 {
84  QSettings settings;
85  if (!restoreGeometry(settings.value("MainWindowGeometry").toByteArray())) {
86  // Restore failed (perhaps missing setting), center the window
87  move(QGuiApplication::primaryScreen()->availableGeometry().center() - frameGeometry().center());
88  }
89 
90 #ifdef ENABLE_WALLET
92 #endif // ENABLE_WALLET
93  QApplication::setWindowIcon(m_network_style->getTrayAndWindowIcon());
94  setWindowIcon(m_network_style->getTrayAndWindowIcon());
96 
97  rpcConsole = new RPCConsole(node, _platformStyle, nullptr);
98  helpMessageDialog = new HelpMessageDialog(node, this, false);
99 #ifdef ENABLE_WALLET
100  if(enableWallet)
101  {
103  walletFrame = new WalletFrame(_platformStyle, this);
104  setCentralWidget(walletFrame);
105  } else
106 #endif // ENABLE_WALLET
107  {
108  /* When compiled without wallet or -disablewallet is provided,
109  * the central widget is the rpc console.
110  */
111  setCentralWidget(rpcConsole);
112  Q_EMIT consoleShown(rpcConsole);
113  }
114 
115  // Accept D&D of URIs
116  setAcceptDrops(true);
117 
118  // Create actions for the toolbar, menu bar and tray/dock icon
119  // Needs walletFrame to be initialized
120  createActions();
121 
122  // Create application menu bar
123  createMenuBar();
124 
125  // Create the toolbars
126  createToolBars();
127 
128  // Create system tray icon and notification
129  if (QSystemTrayIcon::isSystemTrayAvailable()) {
130  createTrayIcon();
131  }
132  notificator = new Notificator(QApplication::applicationName(), trayIcon, this);
133 
134  // Create status bar
135  statusBar();
136 
137  // Disable size grip because it looks ugly and nobody needs it
138  statusBar()->setSizeGripEnabled(false);
139 
140  // Status bar notification icons
141  QFrame *frameBlocks = new QFrame();
142  frameBlocks->setContentsMargins(0,0,0,0);
143  frameBlocks->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Preferred);
144  QHBoxLayout *frameBlocksLayout = new QHBoxLayout(frameBlocks);
145  frameBlocksLayout->setContentsMargins(3,0,3,0);
146  frameBlocksLayout->setSpacing(3);
148  labelWalletEncryptionIcon = new QLabel();
149  labelWalletHDStatusIcon = new QLabel();
153  if(enableWallet)
154  {
155  frameBlocksLayout->addStretch();
156  frameBlocksLayout->addWidget(unitDisplayControl);
157  frameBlocksLayout->addStretch();
158  frameBlocksLayout->addWidget(labelWalletEncryptionIcon);
159  frameBlocksLayout->addWidget(labelWalletHDStatusIcon);
160  }
161  frameBlocksLayout->addWidget(labelProxyIcon);
162  frameBlocksLayout->addStretch();
163  frameBlocksLayout->addWidget(connectionsControl);
164  frameBlocksLayout->addStretch();
165  frameBlocksLayout->addWidget(labelBlocksIcon);
166  frameBlocksLayout->addStretch();
167 
168  // Progress bar and label for blocks download
169  progressBarLabel = new QLabel();
170  progressBarLabel->setVisible(false);
172  progressBar->setAlignment(Qt::AlignCenter);
173  progressBar->setVisible(false);
174 
175  // Override style sheet for progress bar for styles that have a segmented progress bar,
176  // as they make the text unreadable (workaround for issue #1071)
177  // See https://doc.qt.io/qt-5/gallery.html
178  QString curStyle = QApplication::style()->metaObject()->className();
179  if(curStyle == "QWindowsStyle" || curStyle == "QWindowsXPStyle")
180  {
181  progressBar->setStyleSheet("QProgressBar { background-color: #e8e8e8; border: 1px solid grey; border-radius: 7px; padding: 1px; text-align: center; } QProgressBar::chunk { background: QLinearGradient(x1: 0, y1: 0, x2: 1, y2: 0, stop: 0 #FF8000, stop: 1 orange); border-radius: 7px; margin: 0px; }");
182  }
183 
184  statusBar()->addWidget(progressBarLabel);
185  statusBar()->addWidget(progressBar);
186  statusBar()->addPermanentWidget(frameBlocks);
187 
188  // Install event filter to be able to catch status tip events (QEvent::StatusTip)
189  this->installEventFilter(this);
190 
191  // Initially wallet actions should be disabled
193 
194  // Subscribe to notifications from core
196 
199  });
202  });
203 
204  modalOverlay = new ModalOverlay(enableWallet, this->centralWidget());
207 #ifdef ENABLE_WALLET
208  if(enableWallet) {
210  }
211 #endif
212 
213 #ifdef Q_OS_MAC
214  m_app_nap_inhibitor = new CAppNapInhibitor;
215 #endif
216 
218 }
219 
221 {
222  // Unsubscribe from notifications from core
224 
225  QSettings settings;
226  settings.setValue("MainWindowGeometry", saveGeometry());
227  if(trayIcon) // Hide tray icon, as deleting will let it linger until quit (on Ubuntu)
228  trayIcon->hide();
229 #ifdef Q_OS_MAC
230  delete m_app_nap_inhibitor;
231  delete appMenuBar;
233 #endif
234 
235  delete rpcConsole;
236 }
237 
239 {
240  QActionGroup *tabGroup = new QActionGroup(this);
241 
242  overviewAction = new QAction(platformStyle->SingleColorIcon(":/icons/overview"), tr("&Overview"), this);
243  overviewAction->setStatusTip(tr("Show general overview of wallet"));
244  overviewAction->setToolTip(overviewAction->statusTip());
245  overviewAction->setCheckable(true);
246  overviewAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_1));
247  tabGroup->addAction(overviewAction);
248 
249  sendCoinsAction = new QAction(platformStyle->SingleColorIcon(":/icons/send"), tr("&Send"), this);
250  sendCoinsAction->setStatusTip(tr("Send coins to a Bitcoin address"));
251  sendCoinsAction->setToolTip(sendCoinsAction->statusTip());
252  sendCoinsAction->setCheckable(true);
253  sendCoinsAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_2));
254  tabGroup->addAction(sendCoinsAction);
255 
256  sendCoinsMenuAction = new QAction(sendCoinsAction->text(), this);
257  sendCoinsMenuAction->setStatusTip(sendCoinsAction->statusTip());
258  sendCoinsMenuAction->setToolTip(sendCoinsMenuAction->statusTip());
259 
260  receiveCoinsAction = new QAction(platformStyle->SingleColorIcon(":/icons/receiving_addresses"), tr("&Receive"), this);
261  receiveCoinsAction->setStatusTip(tr("Request payments (generates QR codes and bitcoin: URIs)"));
262  receiveCoinsAction->setToolTip(receiveCoinsAction->statusTip());
263  receiveCoinsAction->setCheckable(true);
264  receiveCoinsAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_3));
265  tabGroup->addAction(receiveCoinsAction);
266 
267  receiveCoinsMenuAction = new QAction(receiveCoinsAction->text(), this);
268  receiveCoinsMenuAction->setStatusTip(receiveCoinsAction->statusTip());
269  receiveCoinsMenuAction->setToolTip(receiveCoinsMenuAction->statusTip());
270 
271  historyAction = new QAction(platformStyle->SingleColorIcon(":/icons/history"), tr("&Transactions"), this);
272  historyAction->setStatusTip(tr("Browse transaction history"));
273  historyAction->setToolTip(historyAction->statusTip());
274  historyAction->setCheckable(true);
275  historyAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_4));
276  tabGroup->addAction(historyAction);
277 
278 #ifdef ENABLE_WALLET
279  // These showNormalIfMinimized are needed because Send Coins and Receive Coins
280  // can be triggered from the tray menu, and need to show the GUI to be useful.
281  connect(overviewAction, &QAction::triggered, [this]{ showNormalIfMinimized(); });
282  connect(overviewAction, &QAction::triggered, this, &BitcoinGUI::gotoOverviewPage);
283  connect(sendCoinsAction, &QAction::triggered, [this]{ showNormalIfMinimized(); });
284  connect(sendCoinsAction, &QAction::triggered, [this]{ gotoSendCoinsPage(); });
285  connect(sendCoinsMenuAction, &QAction::triggered, [this]{ showNormalIfMinimized(); });
286  connect(sendCoinsMenuAction, &QAction::triggered, [this]{ gotoSendCoinsPage(); });
287  connect(receiveCoinsAction, &QAction::triggered, [this]{ showNormalIfMinimized(); });
288  connect(receiveCoinsAction, &QAction::triggered, this, &BitcoinGUI::gotoReceiveCoinsPage);
289  connect(receiveCoinsMenuAction, &QAction::triggered, [this]{ showNormalIfMinimized(); });
290  connect(receiveCoinsMenuAction, &QAction::triggered, this, &BitcoinGUI::gotoReceiveCoinsPage);
291  connect(historyAction, &QAction::triggered, [this]{ showNormalIfMinimized(); });
292  connect(historyAction, &QAction::triggered, this, &BitcoinGUI::gotoHistoryPage);
293 #endif // ENABLE_WALLET
294 
295  quitAction = new QAction(tr("E&xit"), this);
296  quitAction->setStatusTip(tr("Quit application"));
297  quitAction->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_Q));
298  quitAction->setMenuRole(QAction::QuitRole);
299  aboutAction = new QAction(tr("&About %1").arg(PACKAGE_NAME), this);
300  aboutAction->setStatusTip(tr("Show information about %1").arg(PACKAGE_NAME));
301  aboutAction->setMenuRole(QAction::AboutRole);
302  aboutAction->setEnabled(false);
303  aboutQtAction = new QAction(tr("About &Qt"), this);
304  aboutQtAction->setStatusTip(tr("Show information about Qt"));
305  aboutQtAction->setMenuRole(QAction::AboutQtRole);
306  optionsAction = new QAction(tr("&Options..."), this);
307  optionsAction->setStatusTip(tr("Modify configuration options for %1").arg(PACKAGE_NAME));
308  optionsAction->setMenuRole(QAction::PreferencesRole);
309  optionsAction->setEnabled(false);
310  toggleHideAction = new QAction(tr("&Show / Hide"), this);
311  toggleHideAction->setStatusTip(tr("Show or hide the main Window"));
312 
313  encryptWalletAction = new QAction(tr("&Encrypt Wallet..."), this);
314  encryptWalletAction->setStatusTip(tr("Encrypt the private keys that belong to your wallet"));
315  encryptWalletAction->setCheckable(true);
316  backupWalletAction = new QAction(tr("&Backup Wallet..."), this);
317  backupWalletAction->setStatusTip(tr("Backup wallet to another location"));
318  changePassphraseAction = new QAction(tr("&Change Passphrase..."), this);
319  changePassphraseAction->setStatusTip(tr("Change the passphrase used for wallet encryption"));
320  signMessageAction = new QAction(tr("Sign &message..."), this);
321  signMessageAction->setStatusTip(tr("Sign messages with your Bitcoin addresses to prove you own them"));
322  verifyMessageAction = new QAction(tr("&Verify message..."), this);
323  verifyMessageAction->setStatusTip(tr("Verify messages to ensure they were signed with specified Bitcoin addresses"));
324  m_load_psbt_action = new QAction(tr("Load PSBT..."), this);
325  m_load_psbt_action->setStatusTip(tr("Load Partially Signed Bitcoin Transaction"));
326 
327  openRPCConsoleAction = new QAction(tr("Node window"), this);
328  openRPCConsoleAction->setStatusTip(tr("Open node debugging and diagnostic console"));
329  // initially disable the debug window menu item
330  openRPCConsoleAction->setEnabled(false);
331  openRPCConsoleAction->setObjectName("openRPCConsoleAction");
332 
333  usedSendingAddressesAction = new QAction(tr("&Sending addresses"), this);
334  usedSendingAddressesAction->setStatusTip(tr("Show the list of used sending addresses and labels"));
335  usedReceivingAddressesAction = new QAction(tr("&Receiving addresses"), this);
336  usedReceivingAddressesAction->setStatusTip(tr("Show the list of used receiving addresses and labels"));
337 
338  openAction = new QAction(tr("Open &URI..."), this);
339  openAction->setStatusTip(tr("Open a bitcoin: URI"));
340 
341  m_open_wallet_action = new QAction(tr("Open Wallet"), this);
342  m_open_wallet_action->setEnabled(false);
343  m_open_wallet_action->setStatusTip(tr("Open a wallet"));
344  m_open_wallet_menu = new QMenu(this);
345 
346  m_close_wallet_action = new QAction(tr("Close Wallet..."), this);
347  m_close_wallet_action->setStatusTip(tr("Close wallet"));
348 
349  m_create_wallet_action = new QAction(tr("Create Wallet..."), this);
350  m_create_wallet_action->setEnabled(false);
351  m_create_wallet_action->setStatusTip(tr("Create a new wallet"));
352 
353  showHelpMessageAction = new QAction(tr("&Command-line options"), this);
354  showHelpMessageAction->setMenuRole(QAction::NoRole);
355  showHelpMessageAction->setStatusTip(tr("Show the %1 help message to get a list with possible Bitcoin command-line options").arg(PACKAGE_NAME));
356 
357  m_mask_values_action = new QAction(tr("&Mask values"), this);
358  m_mask_values_action->setShortcut(QKeySequence(Qt::CTRL + Qt::SHIFT + Qt::Key_M));
359  m_mask_values_action->setStatusTip(tr("Mask the values in the Overview tab"));
360  m_mask_values_action->setCheckable(true);
361 
362  connect(quitAction, &QAction::triggered, qApp, QApplication::quit);
363  connect(aboutAction, &QAction::triggered, this, &BitcoinGUI::aboutClicked);
364  connect(aboutQtAction, &QAction::triggered, qApp, QApplication::aboutQt);
365  connect(optionsAction, &QAction::triggered, this, &BitcoinGUI::optionsClicked);
366  connect(toggleHideAction, &QAction::triggered, this, &BitcoinGUI::toggleHidden);
367  connect(showHelpMessageAction, &QAction::triggered, this, &BitcoinGUI::showHelpMessageClicked);
368  connect(openRPCConsoleAction, &QAction::triggered, this, &BitcoinGUI::showDebugWindow);
369  // prevents an open debug window from becoming stuck/unusable on client shutdown
370  connect(quitAction, &QAction::triggered, rpcConsole, &QWidget::hide);
371 
372 #ifdef ENABLE_WALLET
373  if(walletFrame)
374  {
375  connect(encryptWalletAction, &QAction::triggered, walletFrame, &WalletFrame::encryptWallet);
376  connect(backupWalletAction, &QAction::triggered, walletFrame, &WalletFrame::backupWallet);
377  connect(changePassphraseAction, &QAction::triggered, walletFrame, &WalletFrame::changePassphrase);
378  connect(signMessageAction, &QAction::triggered, [this]{ showNormalIfMinimized(); });
379  connect(signMessageAction, &QAction::triggered, [this]{ gotoSignMessageTab(); });
380  connect(m_load_psbt_action, &QAction::triggered, [this]{ gotoLoadPSBT(); });
381  connect(verifyMessageAction, &QAction::triggered, [this]{ showNormalIfMinimized(); });
382  connect(verifyMessageAction, &QAction::triggered, [this]{ gotoVerifyMessageTab(); });
385  connect(openAction, &QAction::triggered, this, &BitcoinGUI::openClicked);
386  connect(m_open_wallet_menu, &QMenu::aboutToShow, [this] {
387  m_open_wallet_menu->clear();
388  for (const std::pair<const std::string, bool>& i : m_wallet_controller->listWalletDir()) {
389  const std::string& path = i.first;
390  QString name = path.empty() ? QString("["+tr("default wallet")+"]") : QString::fromStdString(path);
391  // Menu items remove single &. Single & are shown when && is in
392  // the string, but only the first occurrence. So replace only
393  // the first & with &&.
394  name.replace(name.indexOf(QChar('&')), 1, QString("&&"));
395  QAction* action = m_open_wallet_menu->addAction(name);
396 
397  if (i.second) {
398  // This wallet is already loaded
399  action->setEnabled(false);
400  continue;
401  }
402 
403  connect(action, &QAction::triggered, [this, path] {
404  auto activity = new OpenWalletActivity(m_wallet_controller, this);
405  connect(activity, &OpenWalletActivity::opened, this, &BitcoinGUI::setCurrentWallet);
406  connect(activity, &OpenWalletActivity::finished, activity, &QObject::deleteLater);
407  activity->open(path);
408  });
409  }
410  if (m_open_wallet_menu->isEmpty()) {
411  QAction* action = m_open_wallet_menu->addAction(tr("No wallets available"));
412  action->setEnabled(false);
413  }
414  });
415  connect(m_close_wallet_action, &QAction::triggered, [this] {
417  });
418  connect(m_create_wallet_action, &QAction::triggered, [this] {
419  auto activity = new CreateWalletActivity(m_wallet_controller, this);
420  connect(activity, &CreateWalletActivity::created, this, &BitcoinGUI::setCurrentWallet);
421  connect(activity, &CreateWalletActivity::finished, activity, &QObject::deleteLater);
422  activity->create();
423  });
424 
425  connect(m_mask_values_action, &QAction::toggled, this, &BitcoinGUI::setPrivacy);
426  }
427 #endif // ENABLE_WALLET
428 
429  connect(new QShortcut(QKeySequence(Qt::CTRL + Qt::SHIFT + Qt::Key_C), this), &QShortcut::activated, this, &BitcoinGUI::showDebugWindowActivateConsole);
430  connect(new QShortcut(QKeySequence(Qt::CTRL + Qt::SHIFT + Qt::Key_D), this), &QShortcut::activated, this, &BitcoinGUI::showDebugWindow);
431 }
432 
434 {
435 #ifdef Q_OS_MAC
436  // Create a decoupled menu bar on Mac which stays even if the window is closed
437  appMenuBar = new QMenuBar();
438 #else
439  // Get the main window's menu bar on other platforms
440  appMenuBar = menuBar();
441 #endif
442 
443  // Configure the menus
444  QMenu *file = appMenuBar->addMenu(tr("&File"));
445  if(walletFrame)
446  {
447  file->addAction(m_create_wallet_action);
448  file->addAction(m_open_wallet_action);
449  file->addAction(m_close_wallet_action);
450  file->addSeparator();
451  file->addAction(openAction);
452  file->addAction(backupWalletAction);
453  file->addAction(signMessageAction);
454  file->addAction(verifyMessageAction);
455  file->addAction(m_load_psbt_action);
456  file->addSeparator();
457  }
458  file->addAction(quitAction);
459 
460  QMenu *settings = appMenuBar->addMenu(tr("&Settings"));
461  if(walletFrame)
462  {
463  settings->addAction(encryptWalletAction);
464  settings->addAction(changePassphraseAction);
465  settings->addSeparator();
466  settings->addAction(m_mask_values_action);
467  settings->addSeparator();
468  }
469  settings->addAction(optionsAction);
470 
471  QMenu* window_menu = appMenuBar->addMenu(tr("&Window"));
472 
473  QAction* minimize_action = window_menu->addAction(tr("Minimize"));
474  minimize_action->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_M));
475  connect(minimize_action, &QAction::triggered, [] {
476  QApplication::activeWindow()->showMinimized();
477  });
478  connect(qApp, &QApplication::focusWindowChanged, [minimize_action] (QWindow* window) {
479  minimize_action->setEnabled(window != nullptr && (window->flags() & Qt::Dialog) != Qt::Dialog && window->windowState() != Qt::WindowMinimized);
480  });
481 
482 #ifdef Q_OS_MAC
483  QAction* zoom_action = window_menu->addAction(tr("Zoom"));
484  connect(zoom_action, &QAction::triggered, [] {
485  QWindow* window = qApp->focusWindow();
486  if (window->windowState() != Qt::WindowMaximized) {
487  window->showMaximized();
488  } else {
489  window->showNormal();
490  }
491  });
492 
493  connect(qApp, &QApplication::focusWindowChanged, [zoom_action] (QWindow* window) {
494  zoom_action->setEnabled(window != nullptr);
495  });
496 #endif
497 
498  if (walletFrame) {
499 #ifdef Q_OS_MAC
500  window_menu->addSeparator();
501  QAction* main_window_action = window_menu->addAction(tr("Main Window"));
502  connect(main_window_action, &QAction::triggered, [this] {
503  GUIUtil::bringToFront(this);
504  });
505 #endif
506  window_menu->addSeparator();
507  window_menu->addAction(usedSendingAddressesAction);
508  window_menu->addAction(usedReceivingAddressesAction);
509  }
510 
511  window_menu->addSeparator();
512  for (RPCConsole::TabTypes tab_type : rpcConsole->tabs()) {
513  QAction* tab_action = window_menu->addAction(rpcConsole->tabTitle(tab_type));
514  tab_action->setShortcut(rpcConsole->tabShortcut(tab_type));
515  connect(tab_action, &QAction::triggered, [this, tab_type] {
516  rpcConsole->setTabFocus(tab_type);
517  showDebugWindow();
518  });
519  }
520 
521  QMenu *help = appMenuBar->addMenu(tr("&Help"));
522  help->addAction(showHelpMessageAction);
523  help->addSeparator();
524  help->addAction(aboutAction);
525  help->addAction(aboutQtAction);
526 }
527 
529 {
530  if(walletFrame)
531  {
532  QToolBar *toolbar = addToolBar(tr("Tabs toolbar"));
533  appToolBar = toolbar;
534  toolbar->setContextMenuPolicy(Qt::PreventContextMenu);
535  toolbar->setMovable(false);
536  toolbar->setToolButtonStyle(Qt::ToolButtonTextBesideIcon);
537  toolbar->addAction(overviewAction);
538  toolbar->addAction(sendCoinsAction);
539  toolbar->addAction(receiveCoinsAction);
540  toolbar->addAction(historyAction);
541  overviewAction->setChecked(true);
542 
543 #ifdef ENABLE_WALLET
544  QWidget *spacer = new QWidget();
545  spacer->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
546  toolbar->addWidget(spacer);
547 
548  m_wallet_selector = new QComboBox();
549  m_wallet_selector->setSizeAdjustPolicy(QComboBox::AdjustToContents);
550  connect(m_wallet_selector, static_cast<void (QComboBox::*)(int)>(&QComboBox::currentIndexChanged), this, &BitcoinGUI::setCurrentWalletBySelectorIndex);
551 
552  m_wallet_selector_label = new QLabel();
553  m_wallet_selector_label->setText(tr("Wallet:") + " ");
555 
558 
559  m_wallet_selector_label_action->setVisible(false);
560  m_wallet_selector_action->setVisible(false);
561 #endif
562  }
563 }
564 
566 {
567  this->clientModel = _clientModel;
568  if(_clientModel)
569  {
570  // Create system tray menu (or setup the dock menu) that late to prevent users from calling actions,
571  // while the client has not yet fully loaded
573 
574  // Keep up to date with client
577  connect(_clientModel, &ClientModel::networkActiveChanged, this, &BitcoinGUI::setNetworkActive);
578 
579  modalOverlay->setKnownBestHeight(_clientModel->getHeaderTipHeight(), QDateTime::fromTime_t(_clientModel->getHeaderTipTime()));
581  connect(_clientModel, &ClientModel::numBlocksChanged, this, &BitcoinGUI::setNumBlocks);
582 
583  // Receive and report messages from client model
584  connect(_clientModel, &ClientModel::message, [this](const QString &title, const QString &message, unsigned int style){
585  this->message(title, message, style);
586  });
587 
588  // Show progress dialog
589  connect(_clientModel, &ClientModel::showProgress, this, &BitcoinGUI::showProgress);
590 
591  rpcConsole->setClientModel(_clientModel);
592 
593  updateProxyIcon();
594 
595 #ifdef ENABLE_WALLET
596  if(walletFrame)
597  {
598  walletFrame->setClientModel(_clientModel);
599  }
600 #endif // ENABLE_WALLET
602 
603  OptionsModel* optionsModel = _clientModel->getOptionsModel();
604  if (optionsModel && trayIcon) {
605  // be aware of the tray icon disable state change reported by the OptionsModel object.
607 
608  // initialize the disable state of the tray icon with the current value in the model.
609  setTrayIconVisible(optionsModel->getHideTrayIcon());
610  }
611  } else {
612  // Disable possibility to show main window via action
613  toggleHideAction->setEnabled(false);
614  if(trayIconMenu)
615  {
616  // Disable context menu on tray icon
617  trayIconMenu->clear();
618  }
619  // Propagate cleared model to child objects
620  rpcConsole->setClientModel(nullptr);
621 #ifdef ENABLE_WALLET
622  if (walletFrame)
623  {
624  walletFrame->setClientModel(nullptr);
625  }
626 #endif // ENABLE_WALLET
628  }
629 }
630 
631 #ifdef ENABLE_WALLET
632 void BitcoinGUI::setWalletController(WalletController* wallet_controller)
633 {
634  assert(!m_wallet_controller);
635  assert(wallet_controller);
636 
637  m_wallet_controller = wallet_controller;
638 
639  m_create_wallet_action->setEnabled(true);
640  m_open_wallet_action->setEnabled(true);
642 
643  connect(wallet_controller, &WalletController::walletAdded, this, &BitcoinGUI::addWallet);
644  connect(wallet_controller, &WalletController::walletRemoved, this, &BitcoinGUI::removeWallet);
645 
646  for (WalletModel* wallet_model : m_wallet_controller->getOpenWallets()) {
647  addWallet(wallet_model);
648  }
649 }
650 
651 void BitcoinGUI::addWallet(WalletModel* walletModel)
652 {
653  if (!walletFrame) return;
654  if (!walletFrame->addWallet(walletModel)) return;
655  const QString display_name = walletModel->getDisplayName();
657  rpcConsole->addWallet(walletModel);
658  m_wallet_selector->addItem(display_name, QVariant::fromValue(walletModel));
659  if (m_wallet_selector->count() == 2) {
660  m_wallet_selector_label_action->setVisible(true);
661  m_wallet_selector_action->setVisible(true);
662  }
663 }
664 
665 void BitcoinGUI::removeWallet(WalletModel* walletModel)
666 {
667  if (!walletFrame) return;
668 
669  labelWalletHDStatusIcon->hide();
671 
672  int index = m_wallet_selector->findData(QVariant::fromValue(walletModel));
673  m_wallet_selector->removeItem(index);
674  if (m_wallet_selector->count() == 0) {
676  } else if (m_wallet_selector->count() == 1) {
677  m_wallet_selector_label_action->setVisible(false);
678  m_wallet_selector_action->setVisible(false);
679  }
680  rpcConsole->removeWallet(walletModel);
681  walletFrame->removeWallet(walletModel);
683 }
684 
685 void BitcoinGUI::setCurrentWallet(WalletModel* wallet_model)
686 {
687  if (!walletFrame) return;
688  walletFrame->setCurrentWallet(wallet_model);
689  for (int index = 0; index < m_wallet_selector->count(); ++index) {
690  if (m_wallet_selector->itemData(index).value<WalletModel*>() == wallet_model) {
691  m_wallet_selector->setCurrentIndex(index);
692  break;
693  }
694  }
696 }
697 
698 void BitcoinGUI::setCurrentWalletBySelectorIndex(int index)
699 {
700  WalletModel* wallet_model = m_wallet_selector->itemData(index).value<WalletModel*>();
701  if (wallet_model) setCurrentWallet(wallet_model);
702 }
703 
704 void BitcoinGUI::removeAllWallets()
705 {
706  if(!walletFrame)
707  return;
710 }
711 #endif // ENABLE_WALLET
712 
714 {
715  overviewAction->setEnabled(enabled);
716  sendCoinsAction->setEnabled(enabled);
717  sendCoinsMenuAction->setEnabled(enabled);
718  receiveCoinsAction->setEnabled(enabled);
719  receiveCoinsMenuAction->setEnabled(enabled);
720  historyAction->setEnabled(enabled);
721  encryptWalletAction->setEnabled(enabled);
722  backupWalletAction->setEnabled(enabled);
723  changePassphraseAction->setEnabled(enabled);
724  signMessageAction->setEnabled(enabled);
725  verifyMessageAction->setEnabled(enabled);
726  usedSendingAddressesAction->setEnabled(enabled);
727  usedReceivingAddressesAction->setEnabled(enabled);
728  openAction->setEnabled(enabled);
729  m_close_wallet_action->setEnabled(enabled);
730 }
731 
733 {
734  assert(QSystemTrayIcon::isSystemTrayAvailable());
735 
736 #ifndef Q_OS_MAC
737  if (QSystemTrayIcon::isSystemTrayAvailable()) {
738  trayIcon = new QSystemTrayIcon(m_network_style->getTrayAndWindowIcon(), this);
739  QString toolTip = tr("%1 client").arg(PACKAGE_NAME) + " " + m_network_style->getTitleAddText();
740  trayIcon->setToolTip(toolTip);
741  }
742 #endif
743 }
744 
746 {
747 #ifndef Q_OS_MAC
748  // return if trayIcon is unset (only on non-macOSes)
749  if (!trayIcon)
750  return;
751 
752  trayIcon->setContextMenu(trayIconMenu.get());
753  connect(trayIcon, &QSystemTrayIcon::activated, this, &BitcoinGUI::trayIconActivated);
754 #else
755  // Note: On macOS, the Dock icon is used to provide the tray's functionality.
757  connect(dockIconHandler, &MacDockIconHandler::dockIconClicked, this, &BitcoinGUI::macosDockIconActivated);
758  trayIconMenu->setAsDockMenu();
759 #endif
760 
761  // Configuration of the tray icon (or Dock icon) menu
762 #ifndef Q_OS_MAC
763  // Note: On macOS, the Dock icon's menu already has Show / Hide action.
764  trayIconMenu->addAction(toggleHideAction);
765  trayIconMenu->addSeparator();
766 #endif
767  if (enableWallet) {
768  trayIconMenu->addAction(sendCoinsMenuAction);
770  trayIconMenu->addSeparator();
771  trayIconMenu->addAction(signMessageAction);
772  trayIconMenu->addAction(verifyMessageAction);
773  trayIconMenu->addSeparator();
774  }
775  trayIconMenu->addAction(optionsAction);
777 #ifndef Q_OS_MAC // This is built-in on macOS
778  trayIconMenu->addSeparator();
779  trayIconMenu->addAction(quitAction);
780 #endif
781 }
782 
783 #ifndef Q_OS_MAC
784 void BitcoinGUI::trayIconActivated(QSystemTrayIcon::ActivationReason reason)
785 {
786  if(reason == QSystemTrayIcon::Trigger)
787  {
788  // Click on system tray icon triggers show/hide of the main window
789  toggleHidden();
790  }
791 }
792 #else
793 void BitcoinGUI::macosDockIconActivated()
794 {
795  show();
796  activateWindow();
797 }
798 #endif
799 
801 {
803 }
804 
806 {
807  if(!clientModel)
808  return;
809 
810  HelpMessageDialog dlg(m_node, this, true);
811  dlg.exec();
812 }
813 
815 {
817  Q_EMIT consoleShown(rpcConsole);
818 }
819 
821 {
823  showDebugWindow();
824 }
825 
827 {
828  helpMessageDialog->show();
829 }
830 
831 #ifdef ENABLE_WALLET
832 void BitcoinGUI::openClicked()
833 {
834  OpenURIDialog dlg(this);
835  if(dlg.exec())
836  {
837  Q_EMIT receivedURI(dlg.getURI());
838  }
839 }
840 
841 void BitcoinGUI::gotoOverviewPage()
842 {
843  overviewAction->setChecked(true);
845 }
846 
847 void BitcoinGUI::gotoHistoryPage()
848 {
849  historyAction->setChecked(true);
851 }
852 
853 void BitcoinGUI::gotoReceiveCoinsPage()
854 {
855  receiveCoinsAction->setChecked(true);
857 }
858 
859 void BitcoinGUI::gotoSendCoinsPage(QString addr)
860 {
861  sendCoinsAction->setChecked(true);
863 }
864 
865 void BitcoinGUI::gotoSignMessageTab(QString addr)
866 {
868 }
869 
870 void BitcoinGUI::gotoVerifyMessageTab(QString addr)
871 {
873 }
874 void BitcoinGUI::gotoLoadPSBT()
875 {
877 }
878 #endif // ENABLE_WALLET
879 
881 {
883  QString icon;
884  switch(count)
885  {
886  case 0: icon = ":/icons/connect_0"; break;
887  case 1: case 2: case 3: icon = ":/icons/connect_1"; break;
888  case 4: case 5: case 6: icon = ":/icons/connect_2"; break;
889  case 7: case 8: case 9: icon = ":/icons/connect_3"; break;
890  default: icon = ":/icons/connect_4"; break;
891  }
892 
893  QString tooltip;
894 
895  if (m_node.getNetworkActive()) {
896  tooltip = tr("%n active connection(s) to Bitcoin network", "", count) + QString(".<br>") + tr("Click to disable network activity.");
897  } else {
898  tooltip = tr("Network activity disabled.") + QString("<br>") + tr("Click to enable network activity again.");
899  icon = ":/icons/network_disabled";
900  }
901 
902  // Don't word-wrap this (fixed-width) tooltip
903  tooltip = QString("<nobr>") + tooltip + QString("</nobr>");
904  connectionsControl->setToolTip(tooltip);
905 
907 }
908 
910 {
912 }
913 
914 void BitcoinGUI::setNetworkActive(bool networkActive)
915 {
917 }
918 
920 {
921  int64_t headersTipTime = clientModel->getHeaderTipTime();
922  int headersTipHeight = clientModel->getHeaderTipHeight();
923  int estHeadersLeft = (GetTime() - headersTipTime) / Params().GetConsensus().nPowTargetSpacing;
924  if (estHeadersLeft > HEADER_HEIGHT_DELTA_SYNC)
925  progressBarLabel->setText(tr("Syncing Headers (%1%)...").arg(QString::number(100.0 / (headersTipHeight+estHeadersLeft)*headersTipHeight, 'f', 1)));
926 }
927 
929 {
931  return;
932 
933  OptionsDialog dlg(this, enableWallet);
934  dlg.setCurrentTab(tab);
936  dlg.exec();
937 }
938 
939 void BitcoinGUI::setNumBlocks(int count, const QDateTime& blockDate, double nVerificationProgress, bool header, SynchronizationState sync_state)
940 {
941 // Disabling macOS App Nap on initial sync, disk and reindex operations.
942 #ifdef Q_OS_MAC
943  if (sync_state == SynchronizationState::POST_INIT) {
944  m_app_nap_inhibitor->enableAppNap();
945  } else {
946  m_app_nap_inhibitor->disableAppNap();
947  }
948 #endif
949 
950  if (modalOverlay)
951  {
952  if (header)
953  modalOverlay->setKnownBestHeight(count, blockDate);
954  else
955  modalOverlay->tipUpdate(count, blockDate, nVerificationProgress);
956  }
957  if (!clientModel)
958  return;
959 
960  // Prevent orphan statusbar messages (e.g. hover Quit in main menu, wait until chain-sync starts -> garbled text)
961  statusBar()->clearMessage();
962 
963  // Acquire current block source
964  enum BlockSource blockSource = clientModel->getBlockSource();
965  switch (blockSource) {
967  if (header) {
969  return;
970  }
971  progressBarLabel->setText(tr("Synchronizing with network..."));
973  break;
974  case BlockSource::DISK:
975  if (header) {
976  progressBarLabel->setText(tr("Indexing blocks on disk..."));
977  } else {
978  progressBarLabel->setText(tr("Processing blocks on disk..."));
979  }
980  break;
982  progressBarLabel->setText(tr("Reindexing blocks on disk..."));
983  break;
984  case BlockSource::NONE:
985  if (header) {
986  return;
987  }
988  progressBarLabel->setText(tr("Connecting to peers..."));
989  break;
990  }
991 
992  QString tooltip;
993 
994  QDateTime currentDate = QDateTime::currentDateTime();
995  qint64 secs = blockDate.secsTo(currentDate);
996 
997  tooltip = tr("Processed %n block(s) of transaction history.", "", count);
998 
999  // Set icon state: spinning if catching up, tick otherwise
1000  if (secs < MAX_BLOCK_TIME_GAP) {
1001  tooltip = tr("Up to date") + QString(".<br>") + tooltip;
1002  labelBlocksIcon->setPixmap(platformStyle->SingleColorIcon(":/icons/synced").pixmap(STATUSBAR_ICONSIZE, STATUSBAR_ICONSIZE));
1003 
1004 #ifdef ENABLE_WALLET
1005  if(walletFrame)
1006  {
1008  modalOverlay->showHide(true, true);
1009  }
1010 #endif // ENABLE_WALLET
1011 
1012  progressBarLabel->setVisible(false);
1013  progressBar->setVisible(false);
1014  }
1015  else
1016  {
1017  QString timeBehindText = GUIUtil::formatNiceTimeOffset(secs);
1018 
1019  progressBarLabel->setVisible(true);
1020  progressBar->setFormat(tr("%1 behind").arg(timeBehindText));
1021  progressBar->setMaximum(1000000000);
1022  progressBar->setValue(nVerificationProgress * 1000000000.0 + 0.5);
1023  progressBar->setVisible(true);
1024 
1025  tooltip = tr("Catching up...") + QString("<br>") + tooltip;
1026  if(count != prevBlocks)
1027  {
1028  labelBlocksIcon->setPixmap(platformStyle->SingleColorIcon(QString(
1029  ":/movies/spinner-%1").arg(spinnerFrame, 3, 10, QChar('0')))
1032  }
1033  prevBlocks = count;
1034 
1035 #ifdef ENABLE_WALLET
1036  if(walletFrame)
1037  {
1040  }
1041 #endif // ENABLE_WALLET
1042 
1043  tooltip += QString("<br>");
1044  tooltip += tr("Last received block was generated %1 ago.").arg(timeBehindText);
1045  tooltip += QString("<br>");
1046  tooltip += tr("Transactions after this will not yet be visible.");
1047  }
1048 
1049  // Don't word-wrap this (fixed-width) tooltip
1050  tooltip = QString("<nobr>") + tooltip + QString("</nobr>");
1051 
1052  labelBlocksIcon->setToolTip(tooltip);
1053  progressBarLabel->setToolTip(tooltip);
1054  progressBar->setToolTip(tooltip);
1055 }
1056 
1057 void BitcoinGUI::message(const QString& title, QString message, unsigned int style, bool* ret, const QString& detailed_message)
1058 {
1059  // Default title. On macOS, the window title is ignored (as required by the macOS Guidelines).
1060  QString strTitle{PACKAGE_NAME};
1061  // Default to information icon
1062  int nMBoxIcon = QMessageBox::Information;
1063  int nNotifyIcon = Notificator::Information;
1064 
1065  bool prefix = !(style & CClientUIInterface::MSG_NOPREFIX);
1066  style &= ~CClientUIInterface::MSG_NOPREFIX;
1067 
1068  QString msgType;
1069  if (!title.isEmpty()) {
1070  msgType = title;
1071  } else {
1072  switch (style) {
1074  msgType = tr("Error");
1075  if (prefix) message = tr("Error: %1").arg(message);
1076  break;
1078  msgType = tr("Warning");
1079  if (prefix) message = tr("Warning: %1").arg(message);
1080  break;
1082  msgType = tr("Information");
1083  // No need to prepend the prefix here.
1084  break;
1085  default:
1086  break;
1087  }
1088  }
1089 
1090  if (!msgType.isEmpty()) {
1091  strTitle += " - " + msgType;
1092  }
1093 
1094  if (style & CClientUIInterface::ICON_ERROR) {
1095  nMBoxIcon = QMessageBox::Critical;
1096  nNotifyIcon = Notificator::Critical;
1097  } else if (style & CClientUIInterface::ICON_WARNING) {
1098  nMBoxIcon = QMessageBox::Warning;
1099  nNotifyIcon = Notificator::Warning;
1100  }
1101 
1102  if (style & CClientUIInterface::MODAL) {
1103  // Check for buttons, use OK as default, if none was supplied
1104  QMessageBox::StandardButton buttons;
1105  if (!(buttons = (QMessageBox::StandardButton)(style & CClientUIInterface::BTN_MASK)))
1106  buttons = QMessageBox::Ok;
1107 
1109  QMessageBox mBox(static_cast<QMessageBox::Icon>(nMBoxIcon), strTitle, message, buttons, this);
1110  mBox.setTextFormat(Qt::PlainText);
1111  mBox.setDetailedText(detailed_message);
1112  int r = mBox.exec();
1113  if (ret != nullptr)
1114  *ret = r == QMessageBox::Ok;
1115  } else {
1116  notificator->notify(static_cast<Notificator::Class>(nNotifyIcon), strTitle, message);
1117  }
1118 }
1119 
1121 {
1122  QMainWindow::changeEvent(e);
1123 #ifndef Q_OS_MAC // Ignored on Mac
1124  if(e->type() == QEvent::WindowStateChange)
1125  {
1127  {
1128  QWindowStateChangeEvent *wsevt = static_cast<QWindowStateChangeEvent*>(e);
1129  if(!(wsevt->oldState() & Qt::WindowMinimized) && isMinimized())
1130  {
1131  QTimer::singleShot(0, this, &BitcoinGUI::hide);
1132  e->ignore();
1133  }
1134  else if((wsevt->oldState() & Qt::WindowMinimized) && !isMinimized())
1135  {
1136  QTimer::singleShot(0, this, &BitcoinGUI::show);
1137  e->ignore();
1138  }
1139  }
1140  }
1141 #endif
1142 }
1143 
1144 void BitcoinGUI::closeEvent(QCloseEvent *event)
1145 {
1146 #ifndef Q_OS_MAC // Ignored on Mac
1148  {
1150  {
1151  // close rpcConsole in case it was open to make some space for the shutdown window
1152  rpcConsole->close();
1153 
1154  QApplication::quit();
1155  }
1156  else
1157  {
1158  QMainWindow::showMinimized();
1159  event->ignore();
1160  }
1161  }
1162 #else
1163  QMainWindow::closeEvent(event);
1164 #endif
1165 }
1166 
1167 void BitcoinGUI::showEvent(QShowEvent *event)
1168 {
1169  // enable the debug window when the main window shows up
1170  openRPCConsoleAction->setEnabled(true);
1171  aboutAction->setEnabled(true);
1172  optionsAction->setEnabled(true);
1173 }
1174 
1175 #ifdef ENABLE_WALLET
1176 void BitcoinGUI::incomingTransaction(const QString& date, int unit, const CAmount& amount, const QString& type, const QString& address, const QString& label, const QString& walletName)
1177 {
1178  // On new transaction, make an info balloon
1179  QString msg = tr("Date: %1\n").arg(date) +
1180  tr("Amount: %1\n").arg(BitcoinUnits::formatWithUnit(unit, amount, true));
1181  if (m_node.getWallets().size() > 1 && !walletName.isEmpty()) {
1182  msg += tr("Wallet: %1\n").arg(walletName);
1183  }
1184  msg += tr("Type: %1\n").arg(type);
1185  if (!label.isEmpty())
1186  msg += tr("Label: %1\n").arg(label);
1187  else if (!address.isEmpty())
1188  msg += tr("Address: %1\n").arg(address);
1189  message((amount)<0 ? tr("Sent transaction") : tr("Incoming transaction"),
1191 }
1192 #endif // ENABLE_WALLET
1193 
1194 void BitcoinGUI::dragEnterEvent(QDragEnterEvent *event)
1195 {
1196  // Accept only URIs
1197  if(event->mimeData()->hasUrls())
1198  event->acceptProposedAction();
1199 }
1200 
1201 void BitcoinGUI::dropEvent(QDropEvent *event)
1202 {
1203  if(event->mimeData()->hasUrls())
1204  {
1205  for (const QUrl &uri : event->mimeData()->urls())
1206  {
1207  Q_EMIT receivedURI(uri.toString());
1208  }
1209  }
1210  event->acceptProposedAction();
1211 }
1212 
1213 bool BitcoinGUI::eventFilter(QObject *object, QEvent *event)
1214 {
1215  // Catch status tip events
1216  if (event->type() == QEvent::StatusTip)
1217  {
1218  // Prevent adding text from setStatusTip(), if we currently use the status bar for displaying other stuff
1219  if (progressBarLabel->isVisible() || progressBar->isVisible())
1220  return true;
1221  }
1222  return QMainWindow::eventFilter(object, event);
1223 }
1224 
1225 #ifdef ENABLE_WALLET
1226 bool BitcoinGUI::handlePaymentRequest(const SendCoinsRecipient& recipient)
1227 {
1228  // URI has to be valid
1229  if (walletFrame && walletFrame->handlePaymentRequest(recipient))
1230  {
1232  gotoSendCoinsPage();
1233  return true;
1234  }
1235  return false;
1236 }
1237 
1238 void BitcoinGUI::setHDStatus(bool privkeyDisabled, int hdEnabled)
1239 {
1240  labelWalletHDStatusIcon->setPixmap(platformStyle->SingleColorIcon(privkeyDisabled ? ":/icons/eye" : hdEnabled ? ":/icons/hd_enabled" : ":/icons/hd_disabled").pixmap(STATUSBAR_ICONSIZE,STATUSBAR_ICONSIZE));
1241  labelWalletHDStatusIcon->setToolTip(privkeyDisabled ? tr("Private key <b>disabled</b>") : hdEnabled ? tr("HD key generation is <b>enabled</b>") : tr("HD key generation is <b>disabled</b>"));
1242  labelWalletHDStatusIcon->show();
1243  // eventually disable the QLabel to set its opacity to 50%
1244  labelWalletHDStatusIcon->setEnabled(hdEnabled);
1245 }
1246 
1247 void BitcoinGUI::setEncryptionStatus(int status)
1248 {
1249  switch(status)
1250  {
1252  labelWalletEncryptionIcon->hide();
1253  encryptWalletAction->setChecked(false);
1254  changePassphraseAction->setEnabled(false);
1255  encryptWalletAction->setEnabled(true);
1256  break;
1257  case WalletModel::Unlocked:
1258  labelWalletEncryptionIcon->show();
1260  labelWalletEncryptionIcon->setToolTip(tr("Wallet is <b>encrypted</b> and currently <b>unlocked</b>"));
1261  encryptWalletAction->setChecked(true);
1262  changePassphraseAction->setEnabled(true);
1263  encryptWalletAction->setEnabled(false);
1264  break;
1265  case WalletModel::Locked:
1266  labelWalletEncryptionIcon->show();
1268  labelWalletEncryptionIcon->setToolTip(tr("Wallet is <b>encrypted</b> and currently <b>locked</b>"));
1269  encryptWalletAction->setChecked(true);
1270  changePassphraseAction->setEnabled(true);
1271  encryptWalletAction->setEnabled(false);
1272  break;
1273  }
1274 }
1275 
1276 void BitcoinGUI::updateWalletStatus()
1277 {
1278  if (!walletFrame) {
1279  return;
1280  }
1281  WalletView * const walletView = walletFrame->currentWalletView();
1282  if (!walletView) {
1283  return;
1284  }
1285  WalletModel * const walletModel = walletView->getWalletModel();
1286  setEncryptionStatus(walletModel->getEncryptionStatus());
1287  setHDStatus(walletModel->wallet().privateKeysDisabled(), walletModel->wallet().hdEnabled());
1288 }
1289 #endif // ENABLE_WALLET
1290 
1292 {
1293  std::string ip_port;
1294  bool proxy_enabled = clientModel->getProxyInfo(ip_port);
1295 
1296  if (proxy_enabled) {
1297  if (labelProxyIcon->pixmap() == nullptr) {
1298  QString ip_port_q = QString::fromStdString(ip_port);
1299  labelProxyIcon->setPixmap(platformStyle->SingleColorIcon(":/icons/proxy").pixmap(STATUSBAR_ICONSIZE, STATUSBAR_ICONSIZE));
1300  labelProxyIcon->setToolTip(tr("Proxy is <b>enabled</b>: %1").arg(ip_port_q));
1301  } else {
1302  labelProxyIcon->show();
1303  }
1304  } else {
1305  labelProxyIcon->hide();
1306  }
1307 }
1308 
1310 {
1311  QString window_title = PACKAGE_NAME;
1312 #ifdef ENABLE_WALLET
1313  if (walletFrame) {
1314  WalletModel* const wallet_model = walletFrame->currentWalletModel();
1315  if (wallet_model && !wallet_model->getWalletName().isEmpty()) {
1316  window_title += " - " + wallet_model->getDisplayName();
1317  }
1318  }
1319 #endif
1320  if (!m_network_style->getTitleAddText().isEmpty()) {
1321  window_title += " - " + m_network_style->getTitleAddText();
1322  }
1323  setWindowTitle(window_title);
1324 }
1325 
1326 void BitcoinGUI::showNormalIfMinimized(bool fToggleHidden)
1327 {
1328  if(!clientModel)
1329  return;
1330 
1331  if (!isHidden() && !isMinimized() && !GUIUtil::isObscured(this) && fToggleHidden) {
1332  hide();
1333  } else {
1334  GUIUtil::bringToFront(this);
1335  }
1336 }
1337 
1339 {
1340  showNormalIfMinimized(true);
1341 }
1342 
1344 {
1345  if (m_node.shutdownRequested())
1346  {
1347  if(rpcConsole)
1348  rpcConsole->hide();
1349  qApp->quit();
1350  }
1351 }
1352 
1353 void BitcoinGUI::showProgress(const QString &title, int nProgress)
1354 {
1355  if (nProgress == 0) {
1356  progressDialog = new QProgressDialog(title, QString(), 0, 100);
1358  progressDialog->setWindowModality(Qt::ApplicationModal);
1359  progressDialog->setMinimumDuration(0);
1360  progressDialog->setAutoClose(false);
1361  progressDialog->setValue(0);
1362  } else if (nProgress == 100) {
1363  if (progressDialog) {
1364  progressDialog->close();
1365  progressDialog->deleteLater();
1366  progressDialog = nullptr;
1367  }
1368  } else if (progressDialog) {
1369  progressDialog->setValue(nProgress);
1370  }
1371 }
1372 
1373 void BitcoinGUI::setTrayIconVisible(bool fHideTrayIcon)
1374 {
1375  if (trayIcon)
1376  {
1377  trayIcon->setVisible(!fHideTrayIcon);
1378  }
1379 }
1380 
1382 {
1383  if (modalOverlay && (progressBar->isVisible() || modalOverlay->isLayerVisible()))
1385 }
1386 
1387 static bool ThreadSafeMessageBox(BitcoinGUI* gui, const bilingual_str& message, const std::string& caption, unsigned int style)
1388 {
1389  bool modal = (style & CClientUIInterface::MODAL);
1390  // The SECURE flag has no effect in the Qt GUI.
1391  // bool secure = (style & CClientUIInterface::SECURE);
1392  style &= ~CClientUIInterface::SECURE;
1393  bool ret = false;
1394 
1395  QString detailed_message; // This is original message, in English, for googling and referencing.
1396  if (message.original != message.translated) {
1397  detailed_message = BitcoinGUI::tr("Original message:") + "\n" + QString::fromStdString(message.original);
1398  }
1399 
1400  // In case of modal message, use blocking connection to wait for user to click a button
1401  bool invoked = QMetaObject::invokeMethod(gui, "message",
1402  modal ? GUIUtil::blockingGUIThreadConnection() : Qt::QueuedConnection,
1403  Q_ARG(QString, QString::fromStdString(caption)),
1404  Q_ARG(QString, QString::fromStdString(message.translated)),
1405  Q_ARG(unsigned int, style),
1406  Q_ARG(bool*, &ret),
1407  Q_ARG(QString, detailed_message));
1408  assert(invoked);
1409  return ret;
1410 }
1411 
1413 {
1414  // Connect signals to client
1415  m_handler_message_box = m_node.handleMessageBox(std::bind(ThreadSafeMessageBox, this, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3));
1416  m_handler_question = m_node.handleQuestion(std::bind(ThreadSafeMessageBox, this, std::placeholders::_1, std::placeholders::_3, std::placeholders::_4));
1417 }
1418 
1420 {
1421  // Disconnect signals from client
1422  m_handler_message_box->disconnect();
1423  m_handler_question->disconnect();
1424 }
1425 
1427 {
1428  assert(m_mask_values_action);
1429  return m_mask_values_action->isChecked();
1430 }
1431 
1433  optionsModel(nullptr),
1434  menu(nullptr)
1435 {
1437  setToolTip(tr("Unit to show amounts in. Click to select another unit."));
1438  QList<BitcoinUnits::Unit> units = BitcoinUnits::availableUnits();
1439  int max_width = 0;
1440  const QFontMetrics fm(font());
1441  for (const BitcoinUnits::Unit unit : units)
1442  {
1443  max_width = qMax(max_width, GUIUtil::TextWidth(fm, BitcoinUnits::longName(unit)));
1444  }
1445  setMinimumSize(max_width, 0);
1446  setAlignment(Qt::AlignRight | Qt::AlignVCenter);
1447  setStyleSheet(QString("QLabel { color : %1 }").arg(platformStyle->SingleColor().name()));
1448 }
1449 
1452 {
1453  onDisplayUnitsClicked(event->pos());
1454 }
1455 
1458 {
1459  menu = new QMenu(this);
1461  {
1462  QAction *menuAction = new QAction(QString(BitcoinUnits::longName(u)), this);
1463  menuAction->setData(QVariant(u));
1464  menu->addAction(menuAction);
1465  }
1466  connect(menu, &QMenu::triggered, this, &UnitDisplayStatusBarControl::onMenuSelection);
1467 }
1468 
1471 {
1472  if (_optionsModel)
1473  {
1474  this->optionsModel = _optionsModel;
1475 
1476  // be aware of a display unit change reported by the OptionsModel object.
1478 
1479  // initialize the display units label with the current value in the model.
1480  updateDisplayUnit(_optionsModel->getDisplayUnit());
1481  }
1482 }
1483 
1486 {
1487  setText(BitcoinUnits::longName(newUnits));
1488 }
1489 
1492 {
1493  QPoint globalPos = mapToGlobal(point);
1494  menu->exec(globalPos);
1495 }
1496 
1499 {
1500  if (action)
1501  {
1502  optionsModel->setDisplayUnit(action->data());
1503  }
1504 }
virtual bool privateKeysDisabled()=0
void subscribeToCoreSignals()
Connect core signals to GUI client.
void unsubscribeFromCoreSignals()
Disconnect core signals from GUI client.
void showEvent(QShowEvent *event) override
bool handlePaymentRequest(const SendCoinsRecipient &recipient)
void message(const QString &title, const QString &message, unsigned int style)
Fired when a message should be reported to the user.
void setNetworkActive(bool networkActive)
Set network state shown in the UI.
Definition: bitcoingui.cpp:914
void addWallet(WalletModel *const walletModel)
WalletModel * currentWalletModel() const
QAction * receiveCoinsAction
Definition: bitcoingui.h:143
UnitDisplayStatusBarControl * unitDisplayControl
Definition: bitcoingui.h:120
Local Bitcoin RPC console.
Definition: rpcconsole.h:36
QMenuBar * appMenuBar
Definition: bitcoingui.h:130
Unit
Bitcoin units.
Definition: bitcoinunits.h:41
interfaces::Wallet & wallet() const
Definition: walletmodel.h:146
QAction * m_mask_values_action
Definition: bitcoingui.h:160
QAction * signMessageAction
Definition: bitcoingui.h:139
void receivedURI(const QString &uri)
Signal raised when a URI was entered or dragged to the GUI.
SynchronizationState
Current sync state passed to tip changed callbacks.
Definition: validation.h:108
QAction * aboutAction
Definition: bitcoingui.h:142
virtual bool getNetworkActive()=0
Get network active.
void updateNetworkState()
Update UI with latest network info from model.
Definition: bitcoingui.cpp:880
QLabel * labelWalletHDStatusIcon
Definition: bitcoingui.h:122
void showNormalIfMinimized()
Show window if hidden, unminimize when minimized, rise when obscured or show if hidden and fToggleHid...
Definition: bitcoingui.h:305
UnitDisplayStatusBarControl(const PlatformStyle *platformStyle)
QProgressDialog * progressDialog
Definition: bitcoingui.h:128
static bool isWalletEnabled()
void hideTrayIconChanged(bool)
void consoleShown(RPCConsole *console)
Signal raised when RPC console shown.
void createTrayIcon()
Create system tray icon and notification.
Definition: bitcoingui.cpp:732
Bilingual messages:
Definition: translation.h:16
void showDebugWindow()
Show debug window.
Definition: bitcoingui.cpp:814
GUIUtil::ClickableLabel * labelProxyIcon
Definition: bitcoingui.h:123
virtual double getVerificationProgress()=0
Get verification progress.
ClientModel * clientModel
Definition: bitcoingui.h:117
void createToolBars()
Create the toolbars.
Definition: bitcoingui.cpp:528
int TextWidth(const QFontMetrics &fm, const QString &text)
Returns the distance in pixels appropriate for drawing a subsequent character after text...
Definition: guiutil.cpp:871
NodeContext & m_node
Definition: chain.cpp:382
void setCurrentWallet(WalletModel *wallet_model)
Definition: walletframe.cpp:82
QAction * m_load_psbt_action
Definition: bitcoingui.h:141
ModalOverlay * modalOverlay
Definition: bitcoingui.h:170
void createTrayIconMenu()
Create system tray menu (or setup the dock menu)
Definition: bitcoingui.cpp:745
RPCConsole * rpcConsole
Definition: bitcoingui.h:168
QAction * m_wallet_selector_action
Definition: bitcoingui.h:159
QAction * overviewAction
Definition: bitcoingui.h:132
void opened(WalletModel *wallet_model)
const char * prefix
Definition: rest.cpp:648
QAction * verifyMessageAction
Definition: bitcoingui.h:140
QAction * quitAction
Definition: bitcoingui.h:134
static constexpr int HEADER_HEIGHT_DELTA_SYNC
The required delta of headers to the estimated number of available headers until we show the IBD prog...
Definition: modaloverlay.h:13
QAction * m_open_wallet_action
Definition: bitcoingui.h:155
void usedReceivingAddresses()
Show used receiving addresses.
QAction * m_close_wallet_action
Definition: bitcoingui.h:157
static bool ThreadSafeMessageBox(BitcoinGUI *gui, const bilingual_str &message, const std::string &caption, unsigned int style)
QAction * historyAction
Definition: bitcoingui.h:133
void tipUpdate(int count, const QDateTime &blockDate, double nVerificationProgress)
Qt::ConnectionType blockingGUIThreadConnection()
Get connection type to call object slot in GUI thread with invokeMethod.
Definition: guiutil.cpp:344
void setWalletActionsEnabled(bool enabled)
Enable or disable all wallet-related actions.
Definition: bitcoingui.cpp:713
void networkActiveChanged(bool networkActive)
QAction * aboutQtAction
Definition: bitcoingui.h:150
#define PACKAGE_NAME
Controller between interfaces::Node, WalletModel instances and the GUI.
OptionsModel * getOptionsModel()
QIcon SingleColorIcon(const QString &filename) const
Colorize an icon (given filename) with the icon color.
void encryptWallet(bool status)
Encrypt the wallet.
std::string translated
Definition: translation.h:18
QMenu * m_open_wallet_menu
Definition: bitcoingui.h:156
macOS-specific Dock icon handler.
Mask of all available buttons in CClientUIInterface::MessageBoxFlags This needs to be updated...
Definition: ui_interface.h:64
Bitcoin GUI main class.
Definition: bitcoingui.h:65
bool isLayerVisible() const
Definition: modaloverlay.h:36
HelpMessageDialog * helpMessageDialog
Definition: bitcoingui.h:169
QLabel * progressBarLabel
Definition: bitcoingui.h:126
QSystemTrayIcon * trayIcon
Definition: bitcoingui.h:165
void numBlocksChanged(int count, const QDateTime &blockDate, double nVerificationProgress, bool header, SynchronizationState sync_state)
virtual std::vector< std::unique_ptr< Wallet > > getWallets()=0
Return interfaces for accessing wallets (if any).
QAction * showHelpMessageAction
Definition: bitcoingui.h:153
Notify user of potential problem.
Definition: notificator.h:39
Modal overlay to display information about the chain-sync state.
Definition: modaloverlay.h:20
bool isPrivacyModeActivated() const
const QString & getTitleAddText() const
Definition: networkstyle.h:22
void changeEvent(QEvent *e) override
static QString longName(int unit)
Long name.
void numConnectionsChanged(int count)
Signals for UI communication.
Definition: ui_interface.h:32
void removeAllWallets()
GUIUtil::ClickableLabel * connectionsControl
Definition: bitcoingui.h:124
QAction * backupWalletAction
Definition: bitcoingui.h:148
void setOptionsModel(OptionsModel *optionsModel)
Lets the control know about the Options Model (and its signals)
void dropEvent(QDropEvent *event) override
void bringToFront(QWidget *w)
Definition: guiutil.cpp:372
std::map< std::string, bool > listWalletDir() const
Returns all wallet names in the wallet dir mapped to whether the wallet is loaded.
QString tabTitle(TabTypes tab_type) const
void openOptionsDialogWithTab(OptionsDialog::Tab tab)
Open the OptionsDialog on the specified tab index.
Definition: bitcoingui.cpp:928
EncryptionStatus getEncryptionStatus() const
int getDisplayUnit() const
Definition: optionsmodel.h:81
virtual std::unique_ptr< Handler > handleMessageBox(MessageBoxFn fn)=0
Force blocking, modal message box dialog (not just OS notification)
Definition: ui_interface.h:68
void showOutOfSyncWarning(bool fShow)
void setClientModel(ClientModel *model)
Definition: rpcconsole.cpp:558
void gotoHistoryPage()
Switch to history (transactions) page.
QAction * usedReceivingAddressesAction
Definition: bitcoingui.h:138
int64_t CAmount
Amount in satoshis (Can be negative)
Definition: amount.h:12
void setClientModel(ClientModel *clientModel)
Set the client model.
Definition: bitcoingui.cpp:565
WalletModel * getWalletModel()
Definition: walletview.h:45
void showModalOverlay()
const NetworkStyle *const m_network_style
Definition: bitcoingui.h:181
WalletController * m_wallet_controller
Definition: bitcoingui.h:114
void gotoOverviewPage()
Switch to overview (home) page.
const PlatformStyle * platformStyle
Definition: bitcoingui.h:180
QAction * toggleHideAction
Definition: bitcoingui.h:146
virtual bool hdEnabled()=0
void showProgress(const QString &title, int nProgress)
Show progress dialog e.g.
static MacDockIconHandler * instance()
void setDisplayUnit(const QVariant &value)
Updates current unit in memory, settings and emits displayUnitChanged(newUnit) signal.
void setClientModel(ClientModel *clientModel)
Definition: walletframe.cpp:37
bool isObscured(QWidget *w)
Definition: guiutil.cpp:363
QAction * m_wallet_selector_label_action
Definition: bitcoingui.h:158
int getNumConnections(unsigned int flags=CONNECTIONS_ALL) const
Return number of connections, default is in- and outbound (total)
Definition: clientmodel.cpp:67
OptionsModel * optionsModel
Definition: bitcoingui.h:336
void created(WalletModel *wallet_model)
QLabel * m_wallet_selector_label
Definition: bitcoingui.h:162
enum BlockSource getBlockSource() const
Returns enum BlockSource of the current importing/syncing state.
void setKnownBestHeight(int count, const QDateTime &blockDate)
void optionsClicked()
Show configuration dialog.
Definition: bitcoingui.cpp:800
void setNumBlocks(int count, const QDateTime &blockDate, double nVerificationProgress, bool headers, SynchronizationState sync_state)
Set number of blocks and last block date shown in the UI.
Definition: bitcoingui.cpp:939
void closeWallet(WalletModel *wallet_model, QWidget *parent=nullptr)
void gotoVerifyMessageTab(QString addr="")
Show Sign/Verify Message dialog and switch to verify message tab.
void handleCloseWindowShortcut(QWidget *w)
Definition: guiutil.cpp:390
void notify(Class cls, const QString &title, const QString &text, const QIcon &icon=QIcon(), int millisTimeout=10000)
Show notification message.
const char * name
Definition: rest.cpp:41
QToolBar * appToolBar
Definition: bitcoingui.h:131
BlockSource
Definition: clientmodel.h:31
WalletFrame * walletFrame
Definition: bitcoingui.h:118
void updateDisplayUnit(int newUnits)
When Display Units are changed on OptionsModel it will refresh the display text of the control on the...
WalletView * currentWalletView() const
QAction * usedSendingAddressesAction
Definition: bitcoingui.h:137
void setTabFocus(enum TabTypes tabType)
set which tab has the focus (is visible)
int64_t nPowTargetSpacing
Definition: params.h:78
BitcoinGUI(interfaces::Node &node, const PlatformStyle *platformStyle, const NetworkStyle *networkStyle, QWidget *parent=nullptr)
Definition: bitcoingui.cpp:77
void setTrayIconVisible(bool)
When hideTrayIcon setting is changed in OptionsModel hide or show the icon accordingly.
void toggleVisibility()
bool enableWallet
Definition: bitcoingui.h:92
void setModel(OptionsModel *model)
QAction * openRPCConsoleAction
Definition: bitcoingui.h:151
std::vector< TabTypes > tabs() const
Definition: rpcconsole.h:68
void detectShutdown()
called by a timer to check if ShutdownRequested() has been set
Cross-platform desktop notification client.
Definition: notificator.h:24
void clicked(const QPoint &point)
Emitted when the label is clicked.
QLabel * labelWalletEncryptionIcon
Definition: bitcoingui.h:121
GUIUtil::ClickableLabel * labelBlocksIcon
Definition: bitcoingui.h:125
void setCurrentTab(OptionsDialog::Tab tab)
Informational message.
Definition: notificator.h:38
GUIUtil::ClickableProgressBar * progressBar
Definition: bitcoingui.h:127
void updateWindowTitle()
UniValue help(const JSONRPCRequest &jsonRequest)
Definition: server.cpp:135
void showHelpMessageClicked()
Show help message dialog.
Definition: bitcoingui.cpp:826
QString getWalletName() const
void walletAdded(WalletModel *wallet_model)
Notificator * notificator
Definition: bitcoingui.h:167
void displayUnitChanged(int unit)
void PolishProgressDialog(QProgressDialog *dialog)
Definition: guiutil.cpp:859
void changePassphrase()
Change encrypted wallet passphrase.
Model for Bitcoin network client.
Definition: clientmodel.h:46
An error occurred.
Definition: notificator.h:40
const QIcon & getTrayAndWindowIcon() const
Definition: networkstyle.h:21
void mousePressEvent(QMouseEvent *event) override
So that it responds to left-button clicks.
QAction * receiveCoinsMenuAction
Definition: bitcoingui.h:144
ClickableProgressBar ProgressBar
Definition: guiutil.h:256
void gotoSignMessageTab(QString addr="")
Show Sign/Verify Message dialog and switch to sign message tab.
virtual bool shutdownRequested()=0
Return whether shutdown was requested.
QAction * sendCoinsAction
Definition: bitcoingui.h:135
void showHide(bool hide=false, bool userRequested=false)
QAction * m_create_wallet_action
Definition: bitcoingui.h:154
QKeySequence tabShortcut(TabTypes tab_type) const
static const int STATUSBAR_ICONSIZE
Definition: guiconstants.h:17
void message(const QString &title, QString message, unsigned int style, bool *ret=nullptr, const QString &detailed_message=QString())
Notify the user of an event from the core network or transaction handling code.
QColor SingleColor() const
Definition: platformstyle.h:25
void requestedSyncWarningInfo()
Notify that the user has requested more information about the out-of-sync warning.
QAction * openAction
Definition: bitcoingui.h:152
static QList< Unit > availableUnits()
Get list of units, for drop-down box.
void trayIconActivated(QSystemTrayIcon::ActivationReason reason)
Handle tray icon clicked.
Definition: bitcoingui.cpp:784
void gotoLoadPSBT()
Load Partially Signed Bitcoin Transaction.
bool getMinimizeOnClose() const
Definition: optionsmodel.h:80
void updateProxyIcon()
Set the proxy-enabled icon as shown in the UI.
QAction * changePassphraseAction
Definition: bitcoingui.h:149
virtual int64_t getLastBlockTime()=0
Get last block time.
void gotoSendCoinsPage(QString addr="")
Switch to send coins page.
virtual std::unique_ptr< Handler > handleQuestion(QuestionFn fn)=0
void gotoReceiveCoinsPage()
Switch to receive coins page.
std::vector< WalletModel * > getOpenWallets() const
Returns wallet models currently open.
const std::unique_ptr< QMenu > trayIconMenu
Definition: bitcoingui.h:166
void setPrivacy(bool privacy)
std::string original
Definition: translation.h:17
Interface from Qt to configuration data structure for Bitcoin client.
Definition: optionsmodel.h:36
std::unique_ptr< interfaces::Handler > m_handler_question
Definition: bitcoingui.h:116
const CChainParams & Params()
Return the currently selected parameters.
bool getMinimizeToTray() const
Definition: optionsmodel.h:79
Interface to Bitcoin wallet from Qt view code.
Definition: walletmodel.h:51
QString getURI()
QAction * sendCoinsMenuAction
Definition: bitcoingui.h:136
bool eventFilter(QObject *object, QEvent *event) override
Do not prepend error/warning prefix.
Definition: ui_interface.h:71
int prevBlocks
Keep track of previous number of blocks, to detect progress.
Definition: bitcoingui.h:177
void toggleHidden()
Simply calls showNormalIfMinimized(true) for use in SLOT() macro.
interfaces::Node & m_node
Definition: bitcoingui.h:113
int spinnerFrame
Definition: bitcoingui.h:178
void walletRemoved(WalletModel *wallet_model)
void removeWallet(WalletModel *const walletModel)
static int count
Definition: tests.c:45
bool addWallet(WalletModel *walletModel)
Definition: walletframe.cpp:46
void setNumConnections(int count)
Set number of connections shown in the UI.
Definition: bitcoingui.cpp:909
QString getDisplayName() const
"Help message" dialog box
Definition: utilitydialog.h:24
void backupWallet()
Backup the wallet.
void closeEvent(QCloseEvent *event) override
QComboBox * m_wallet_selector
Definition: bitcoingui.h:163
Preferences dialog.
Definition: optionsdialog.h:35
void clicked(const QPoint &point)
Emitted when the progressbar is clicked.
virtual int getNumBlocks()=0
Get num blocks.
QString formatNiceTimeOffset(qint64 secs)
Definition: guiutil.cpp:778
static QString formatWithUnit(int unit, const CAmount &amount, bool plussign=false, SeparatorStyle separators=separatorStandard)
Format as string (with unit)
void createContextMenu()
Creates context menu, its actions, and wires up all the relevant signals for mouse events...
void showDebugWindowActivateConsole()
Show debug window and set focus to the console.
Definition: bitcoingui.cpp:820
void createActions()
Create the main UI actions.
Definition: bitcoingui.cpp:238
QAction * optionsAction
Definition: bitcoingui.h:145
QAction * encryptWalletAction
Definition: bitcoingui.h:147
void aboutClicked()
Show about dialog.
Definition: bitcoingui.cpp:805
const Consensus::Params & GetConsensus() const
Definition: chainparams.h:60
void removeWallet(WalletModel *wallet_model)
Definition: walletframe.cpp:92
int getHeaderTipHeight() const
Definition: clientmodel.cpp:81
void updateHeadersSyncProgressLabel()
Definition: bitcoingui.cpp:919
int64_t GetTime()
Return system time (or mocked time, if set)
Definition: time.cpp:23
static const std::string DEFAULT_UIPLATFORM
Definition: bitcoingui.h:70
virtual void setNetworkActive(bool active)=0
Set network active.
int64_t getHeaderTipTime() const
Definition: clientmodel.cpp:96
Top-level interface for a bitcoin node (bitcoind process).
Definition: node.h:42
static constexpr int64_t MAX_BLOCK_TIME_GAP
Maximum gap between node time and block time used for the "Catching up..." mode in GUI...
Definition: chain.h:38
A container for embedding all wallet-related controls into BitcoinGUI.
Definition: walletframe.h:29
void showProgress(const QString &title, int nProgress)
void usedSendingAddresses()
Show used sending addresses.
bool getHideTrayIcon() const
Definition: optionsmodel.h:78
void onDisplayUnitsClicked(const QPoint &point)
Shows context menu with Display Unit options by the mouse coordinates.
void createMenuBar()
Create the menu bar and sub-menus.
Definition: bitcoingui.cpp:433
void onMenuSelection(QAction *action)
Tells underlying optionsModel to update its current display unit.
std::unique_ptr< interfaces::Handler > m_handler_message_box
Definition: bitcoingui.h:115
Predefined combinations for certain default usage cases.
Definition: ui_interface.h:77
#define SPINNER_FRAMES
Definition: guiconstants.h:43
void dragEnterEvent(QDragEnterEvent *event) override
bool getProxyInfo(std::string &ip_port) const