Inside Bitcoin
Opening the selected file…
Inside Bitcoin
Opening the selected file…
The code behind the network, with room to understand it.
Release published 2026-10-28 · Snapshot fetched 2026-11-01. Latest stable release at fetch time; development branches and Git history are excluded. Only the selected code window and visible folders load here.
751if (age >= 24h) return QObject::tr("%1 d").arg(age / 24h);752if (age >= 1h) return QObject::tr("%1 h").arg(age / 1h);753if (age >= 1min) return QObject::tr("%1 m").arg(age / 1min);754return QObject::tr("%1 s").arg(age / 1s);755}757QString formatServicesStr(quint64 mask)758{759QStringList strList;761for (const auto& flag : serviceFlagsToStr(mask)) {762strList.append(QString::fromStdString(flag));763}765if (strList.size())766return strList.join(", ");767else768return QObject::tr("None");769}771QString formatPingTime(NodeClock::duration ping_time)772{773return (ping_time == decltype(CNode::m_min_ping_time.load())::max() || ping_time == 0us) ?774QObject::tr("N/A") :775QObject::tr("%1 ms").arg(QString::number(Ticks<std::chrono::milliseconds>(ping_time)));776}778QString formatTimeOffset(int64_t time_offset)779{780return QObject::tr("%1 s").arg(QString::number((int)time_offset, 10));781}783QString formatNiceTimeOffset(qint64 secs)784{785// Represent time from last generated block in human readable text786QString timeBehindText;787const int HOUR_IN_SECONDS = 60*60;788const int DAY_IN_SECONDS = 24*60*60;789const int WEEK_IN_SECONDS = 7*24*60*60;790const int YEAR_IN_SECONDS = 31556952; // Average length of year in Gregorian calendar791if(secs < 60)792{793timeBehindText = QObject::tr("%n second(s)","",secs);794}795else if(secs < 2*HOUR_IN_SECONDS)796{797timeBehindText = QObject::tr("%n minute(s)","",secs/60);798}799else if(secs < 2*DAY_IN_SECONDS)800{801timeBehindText = QObject::tr("%n hour(s)","",secs/HOUR_IN_SECONDS);802}803else if(secs < 2*WEEK_IN_SECONDS)804{805timeBehindText = QObject::tr("%n day(s)","",secs/DAY_IN_SECONDS);806}807else if(secs < YEAR_IN_SECONDS)808{809timeBehindText = QObject::tr("%n week(s)","",secs/WEEK_IN_SECONDS);810}811else812{813qint64 years = secs / YEAR_IN_SECONDS;814qint64 remainder = secs % YEAR_IN_SECONDS;815timeBehindText = QObject::tr("%1 and %2").arg(QObject::tr("%n year(s)", "", years)).arg(QObject::tr("%n week(s)","", remainder/WEEK_IN_SECONDS));816}817return timeBehindText;818}820QString formatBytes(uint64_t bytes)821{822if (bytes < 1'000)823return QObject::tr("%1 B").arg(bytes);824if (bytes < 1'000'000)825return QObject::tr("%1 kB").arg(bytes / 1'000);826if (bytes < 1'000'000'000)827return QObject::tr("%1 MB").arg(bytes / 1'000'000);829return QObject::tr("%1 GB").arg(bytes / 1'000'000'000);830}832qreal calculateIdealFontSize(int width, const QString& text, QFont font, qreal minPointSize, qreal font_size) {833while(font_size >= minPointSize) {834font.setPointSizeF(font_size);835QFontMetrics fm(font);836if (TextWidth(fm, text) < width) {837break;838}839font_size -= 0.5;840}841return font_size;842}844ThemedLabel::ThemedLabel(const PlatformStyle* platform_style, QWidget* parent)845: QLabel{parent}, m_platform_style{platform_style}846{847assert(m_platform_style);848}850void ThemedLabel::setThemedPixmap(const QString& image_filename, int width, int height)851{852m_image_filename = image_filename;853m_pixmap_width = width;854m_pixmap_height = height;855updateThemedPixmap();856}858void ThemedLabel::changeEvent(QEvent* e)859{860if (e->type() == QEvent::PaletteChange) {861updateThemedPixmap();862}864QLabel::changeEvent(e);865}867void ThemedLabel::updateThemedPixmap()868{869setPixmap(m_platform_style->SingleColorIcon(m_image_filename).pixmap(m_pixmap_width, m_pixmap_height));870}872ClickableLabel::ClickableLabel(const PlatformStyle* platform_style, QWidget* parent)873: ThemedLabel{platform_style, parent}874{875}877void ClickableLabel::mouseReleaseEvent(QMouseEvent *event)878{879Q_EMIT clicked(event->pos());880}882void ClickableProgressBar::mouseReleaseEvent(QMouseEvent *event)883{884Q_EMIT clicked(event->pos());885}887bool ItemDelegate::eventFilter(QObject *object, QEvent *event)888{889if (event->type() == QEvent::KeyPress) {890if (static_cast<QKeyEvent*>(event)->key() == Qt::Key_Escape) {891Q_EMIT keyEscapePressed();892}893}894return QItemDelegate::eventFilter(object, event);895}897void PolishProgressDialog(QProgressDialog* dialog)898{899#ifdef Q_OS_MACOS900// Workaround for macOS-only Qt bug; see: QTBUG-65750, QTBUG-70357.901const int margin = TextWidth(dialog->fontMetrics(), ("X"));902dialog->resize(dialog->width() + 2 * margin, dialog->height());903#endif904// QProgressDialog estimates the time the operation will take (based on time905// for steps), and only shows itself if that estimate is beyond minimumDuration.906// The default minimumDuration value is 4 seconds, and it could make users907// think that the GUI is frozen.908dialog->setMinimumDuration(0);909}911int TextWidth(const QFontMetrics& fm, const QString& text)912{913return fm.horizontalAdvance(text);914}916void LogQtInfo()917{918#ifdef QT_STATIC919const std::string qt_link{"static"};920#else921const std::string qt_link{"dynamic"};922#endif923LogInfo("Qt %s (%s), plugin=%s\n", qVersion(), qt_link, QGuiApplication::platformName().toStdString());924const auto static_plugins = QPluginLoader::staticPlugins();925if (static_plugins.empty()) {926LogInfo("No static plugins.\n");927} else {928LogInfo("Static plugins:\n");929for (const QStaticPlugin& p : static_plugins) {930QJsonObject meta_data = p.metaData();931const std::string plugin_class = meta_data.take(QString("className")).toString().toStdString();932const int plugin_version = meta_data.take(QString("version")).toInt();933LogInfo(" %s, version %d\n", plugin_class, plugin_version);934}935}937LogInfo("Style: %s / %s\n", QApplication::style()->objectName().toStdString(), QApplication::style()->metaObject()->className());938LogInfo("System: %s, %s\n", QSysInfo::prettyProductName().toStdString(), QSysInfo::buildAbi().toStdString());939for (const QScreen* s : QGuiApplication::screens()) {940LogInfo("Screen: %s %dx%d, pixel ratio=%.1f\n", s->name().toStdString(), s->size().width(), s->size().height(), s->devicePixelRatio());941}942}944void PopupMenu(QMenu* menu, const QPoint& point, QAction* at_action)945{946// The qminimal plugin does not provide window system integration.947if (QApplication::platformName() == "minimal") return;948menu->popup(point, at_action);949}951QDateTime StartOfDay(const QDate& date)952{953return date.startOfDay();954}956bool HasPixmap(const QLabel* label)957{958return !label->pixmap(Qt::ReturnByValue).isNull();959}961QString MakeHtmlLink(const QString& source, const QString& link)962{963return QString(source).replace(964link,965QLatin1String("<a href=\"") + link + QLatin1String("\">") + link + QLatin1String("</a>"));966}968void PrintSlotException(969const std::exception* exception,970const QObject* sender,971const QObject* receiver)972{973std::string description = sender->metaObject()->className();974description += "->";975if (receiver) {976description += receiver->metaObject()->className();977} else {978description += "anonymous function";979}980PrintExceptionContinue(exception, description);981}983void ShowModalDialogAsynchronously(QDialog* dialog)984{985dialog->setAttribute(Qt::WA_DeleteOnClose);986dialog->setWindowModality(Qt::ApplicationModal);987dialog->show();988}990QString WalletDisplayName(const QString& name)991{992return name.isEmpty() ? "[" + QObject::tr("default wallet") + "]" : name;993}995QString WalletDisplayName(const std::string& name)996{997return WalletDisplayName(QString::fromStdString(name));998}999} // namespace GUIUtil
Independent explanations by MyBitcoinExplorer. Not affiliated with or endorsed by Bitcoin Core. Guides are educational and do not replace the source or its tests.
Bitcoin Core source © its contributors, distributed under the MIT license. Original notices and bundled third-party licenses are retained in the source tree.