BSHA3  0.17.99
P2P Blockchain, based on Bitcoin
splashscreen.cpp
Go to the documentation of this file.
1 // Copyright (c) 2011-2018 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 #if defined(HAVE_CONFIG_H)
7 #endif
8 
9 #include <qt/splashscreen.h>
10 
11 #include <qt/networkstyle.h>
12 
13 #include <clientversion.h>
14 #include <interfaces/handler.h>
15 #include <interfaces/node.h>
16 #include <interfaces/wallet.h>
17 #include <ui_interface.h>
18 #include <util.h>
19 #include <version.h>
20 
21 #include <QApplication>
22 #include <QCloseEvent>
23 #include <QDesktopWidget>
24 #include <QPainter>
25 #include <QRadialGradient>
26 
27 #include <boost/bind.hpp>
28 
29 SplashScreen::SplashScreen(interfaces::Node& node, Qt::WindowFlags f, const NetworkStyle *networkStyle) :
30  QWidget(0, f), curAlignment(0), m_node(node)
31 {
32  // set reference point, paddings
33  int paddingRight = 50;
34  int paddingTop = 50;
35  int titleVersionVSpace = 17;
36  int titleCopyrightVSpace = 40;
37 
38  float fontFactor = 1.0;
39  float devicePixelRatio = 1.0;
40 #if QT_VERSION > 0x050100
41  devicePixelRatio = static_cast<QGuiApplication*>(QCoreApplication::instance())->devicePixelRatio();
42 #endif
43 
44  // define text to place
45  QString titleText = tr(PACKAGE_NAME);
46  QString versionText = QString("Version %1").arg(QString::fromStdString(FormatFullVersion()));
47  QString copyrightText = QString::fromUtf8(CopyrightHolders(strprintf("\xc2\xA9 %u-%u ", 2009, COPYRIGHT_YEAR)).c_str());
48  QString titleAddText = networkStyle->getTitleAddText();
49 
50  QString font = QApplication::font().toString();
51 
52  // create a bitmap according to device pixelratio
53  QSize splashSize(480*devicePixelRatio,320*devicePixelRatio);
54  pixmap = QPixmap(splashSize);
55 
56 #if QT_VERSION > 0x050100
57  // change to HiDPI if it makes sense
58  pixmap.setDevicePixelRatio(devicePixelRatio);
59 #endif
60 
61  QPainter pixPaint(&pixmap);
62  pixPaint.setPen(QColor(100,100,100));
63 
64  // draw a slightly radial gradient
65  QRadialGradient gradient(QPoint(0,0), splashSize.width()/devicePixelRatio);
66  gradient.setColorAt(0, Qt::white);
67  gradient.setColorAt(1, QColor(247,247,247));
68  QRect rGradient(QPoint(0,0), splashSize);
69  pixPaint.fillRect(rGradient, gradient);
70 
71  // draw the bitcoin icon, expected size of PNG: 1024x1024
72  QRect rectIcon(QPoint(-150,-122), QSize(430,430));
73 
74  const QSize requiredSize(1024,1024);
75  QPixmap icon(networkStyle->getAppIcon().pixmap(requiredSize));
76 
77  pixPaint.drawPixmap(rectIcon, icon);
78 
79  // check font size and drawing with
80  pixPaint.setFont(QFont(font, 33*fontFactor));
81  QFontMetrics fm = pixPaint.fontMetrics();
82  int titleTextWidth = fm.width(titleText);
83  if (titleTextWidth > 176) {
84  fontFactor = fontFactor * 176 / titleTextWidth;
85  }
86 
87  pixPaint.setFont(QFont(font, 33*fontFactor));
88  fm = pixPaint.fontMetrics();
89  titleTextWidth = fm.width(titleText);
90  pixPaint.drawText(pixmap.width()/devicePixelRatio-titleTextWidth-paddingRight,paddingTop,titleText);
91 
92  pixPaint.setFont(QFont(font, 15*fontFactor));
93 
94  // if the version string is too long, reduce size
95  fm = pixPaint.fontMetrics();
96  int versionTextWidth = fm.width(versionText);
97  if(versionTextWidth > titleTextWidth+paddingRight-10) {
98  pixPaint.setFont(QFont(font, 10*fontFactor));
99  titleVersionVSpace -= 5;
100  }
101  pixPaint.drawText(pixmap.width()/devicePixelRatio-titleTextWidth-paddingRight+2,paddingTop+titleVersionVSpace,versionText);
102 
103  // draw copyright stuff
104  {
105  pixPaint.setFont(QFont(font, 10*fontFactor));
106  const int x = pixmap.width()/devicePixelRatio-titleTextWidth-paddingRight;
107  const int y = paddingTop+titleCopyrightVSpace;
108  QRect copyrightRect(x, y, pixmap.width() - x - paddingRight, pixmap.height() - y);
109  pixPaint.drawText(copyrightRect, Qt::AlignLeft | Qt::AlignTop | Qt::TextWordWrap, copyrightText);
110  }
111 
112  // draw additional text if special network
113  if(!titleAddText.isEmpty()) {
114  QFont boldFont = QFont(font, 10*fontFactor);
115  boldFont.setWeight(QFont::Bold);
116  pixPaint.setFont(boldFont);
117  fm = pixPaint.fontMetrics();
118  int titleAddTextWidth = fm.width(titleAddText);
119  pixPaint.drawText(pixmap.width()/devicePixelRatio-titleAddTextWidth-10,15,titleAddText);
120  }
121 
122  pixPaint.end();
123 
124  // Set window title
125  setWindowTitle(titleText + " " + titleAddText);
126 
127  // Resize window and move to center of desktop, disallow resizing
128  QRect r(QPoint(), QSize(pixmap.size().width()/devicePixelRatio,pixmap.size().height()/devicePixelRatio));
129  resize(r.size());
130  setFixedSize(r.size());
131  move(QApplication::desktop()->screenGeometry().center() - r.center());
132 
134  installEventFilter(this);
135 }
136 
138 {
140 }
141 
142 bool SplashScreen::eventFilter(QObject * obj, QEvent * ev) {
143  if (ev->type() == QEvent::KeyPress) {
144  QKeyEvent *keyEvent = static_cast<QKeyEvent *>(ev);
145  if(keyEvent->text()[0] == 'q') {
147  }
148  }
149  return QObject::eventFilter(obj, ev);
150 }
151 
152 void SplashScreen::slotFinish(QWidget *mainWin)
153 {
154  Q_UNUSED(mainWin);
155 
156  /* If the window is minimized, hide() will be ignored. */
157  /* Make sure we de-minimize the splashscreen window before hiding */
158  if (isMinimized())
159  showNormal();
160  hide();
161  deleteLater(); // No more need for this
162 }
163 
164 static void InitMessage(SplashScreen *splash, const std::string &message)
165 {
166  QMetaObject::invokeMethod(splash, "showMessage",
167  Qt::QueuedConnection,
168  Q_ARG(QString, QString::fromStdString(message)),
169  Q_ARG(int, Qt::AlignBottom|Qt::AlignHCenter),
170  Q_ARG(QColor, QColor(55,55,55)));
171 }
172 
173 static void ShowProgress(SplashScreen *splash, const std::string &title, int nProgress, bool resume_possible)
174 {
175  InitMessage(splash, title + std::string("\n") +
176  (resume_possible ? _("(press q to shutdown and continue later)")
177  : _("press q to shutdown")) +
178  strprintf("\n%d", nProgress) + "%");
179 }
180 #ifdef ENABLE_WALLET
181 void SplashScreen::ConnectWallet(std::unique_ptr<interfaces::Wallet> wallet)
182 {
183  m_connected_wallet_handlers.emplace_back(wallet->handleShowProgress(boost::bind(ShowProgress, this, _1, _2, false)));
184  m_connected_wallets.emplace_back(std::move(wallet));
185 }
186 #endif
187 
189 {
190  // Connect signals to client
191  m_handler_init_message = m_node.handleInitMessage(boost::bind(InitMessage, this, _1));
192  m_handler_show_progress = m_node.handleShowProgress(boost::bind(ShowProgress, this, _1, _2, _3));
193 #ifdef ENABLE_WALLET
194  m_handler_load_wallet = m_node.handleLoadWallet([this](std::unique_ptr<interfaces::Wallet> wallet) { ConnectWallet(std::move(wallet)); });
195 #endif
196 }
197 
199 {
200  // Disconnect signals from client
201  m_handler_init_message->disconnect();
202  m_handler_show_progress->disconnect();
203  for (const auto& handler : m_connected_wallet_handlers) {
204  handler->disconnect();
205  }
207  m_connected_wallets.clear();
208 }
209 
210 void SplashScreen::showMessage(const QString &message, int alignment, const QColor &color)
211 {
212  curMessage = message;
213  curAlignment = alignment;
214  curColor = color;
215  update();
216 }
217 
218 void SplashScreen::paintEvent(QPaintEvent *event)
219 {
220  QPainter painter(this);
221  painter.drawPixmap(0, 0, pixmap);
222  QRect r = rect().adjusted(5, 5, -5, -5);
223  painter.setPen(curColor);
224  painter.drawText(r, curAlignment, curMessage);
225 }
226 
227 void SplashScreen::closeEvent(QCloseEvent *event)
228 {
229  m_node.startShutdown(); // allows an "emergency" shutdown during startup
230  event->ignore();
231 }
bool eventFilter(QObject *obj, QEvent *ev)
#define COPYRIGHT_YEAR
void unsubscribeFromCoreSignals()
Disconnect core signals to splash screen.
bool(* handler)(HTTPRequest *req, const std::string &strReq)
Definition: rest.cpp:582
std::unique_ptr< interfaces::Handler > m_handler_show_progress
Definition: splashscreen.h:64
void ConnectWallet(std::unique_ptr< interfaces::Wallet > wallet)
Connect wallet signals to splash screen.
void closeEvent(QCloseEvent *event)
std::unique_ptr< interfaces::Handler > m_handler_load_wallet
Definition: splashscreen.h:65
Class for the splashscreen with information of the running client.
Definition: splashscreen.h:27
std::unique_ptr< interfaces::Handler > m_handler_init_message
Definition: splashscreen.h:63
#define strprintf
Definition: tinyformat.h:1066
virtual void startShutdown()=0
Start shutdown.
std::list< std::unique_ptr< interfaces::Wallet > > m_connected_wallets
Definition: splashscreen.h:66
const QIcon & getAppIcon() const
Definition: networkstyle.h:20
SplashScreen(interfaces::Node &node, Qt::WindowFlags f, const NetworkStyle *networkStyle)
#define PACKAGE_NAME
void subscribeToCoreSignals()
Connect core signals to splash screen.
const QString & getTitleAddText() const
Definition: networkstyle.h:22
void paintEvent(QPaintEvent *event)
void showMessage(const QString &message, int alignment, const QColor &color)
Show message and progress.
std::list< std::unique_ptr< interfaces::Handler > > m_connected_wallet_handlers
Definition: splashscreen.h:67
QString curMessage
Definition: splashscreen.h:58
virtual std::unique_ptr< Handler > handleShowProgress(ShowProgressFn fn)=0
QPixmap pixmap
Definition: splashscreen.h:57
std::string FormatFullVersion()
std::string CopyrightHolders(const std::string &strPrefix)
Definition: util.cpp:1238
virtual std::unique_ptr< Handler > handleLoadWallet(LoadWalletFn fn)=0
void slotFinish(QWidget *mainWin)
Slot to call finish() method as it&#39;s not defined as slot.
QColor curColor
Definition: splashscreen.h:59
const char * titleAddText
interfaces::Node & m_node
Definition: splashscreen.h:62
Top-level interface for a bitcoin node (bsha3d process).
Definition: node.h:35
std::string _(const char *psz)
Translation function.
Definition: util.h:50
virtual std::unique_ptr< Handler > handleInitMessage(InitMessageFn fn)=0