diff options
Diffstat (limited to 'src/qt/transactiontablemodel.cpp')
-rw-r--r-- | src/qt/transactiontablemodel.cpp | 86 |
1 files changed, 46 insertions, 40 deletions
diff --git a/src/qt/transactiontablemodel.cpp b/src/qt/transactiontablemodel.cpp index e6d483364c..b68ceaedbb 100644 --- a/src/qt/transactiontablemodel.cpp +++ b/src/qt/transactiontablemodel.cpp @@ -25,6 +25,8 @@ #include <QDateTime> #include <QDebug> #include <QIcon> +#include <QLatin1Char> +#include <QLatin1String> #include <QList> @@ -96,18 +98,20 @@ public: */ QList<TransactionRecord> cachedWallet; - bool fQueueNotifications = false; + /** True when model finishes loading all wallet transactions on start */ + bool m_loaded = false; + /** True when transactions are being notified, for instance when scanning */ + bool m_loading = false; std::vector< TransactionNotification > vQueueNotifications; void NotifyTransactionChanged(const uint256 &hash, ChangeType status); - void ShowProgress(const std::string &title, int nProgress); + void DispatchNotifications(); /* Query entire wallet anew from core. */ void refreshWallet(interfaces::Wallet& wallet) { - qDebug() << "TransactionTablePriv::refreshWallet"; - cachedWallet.clear(); + assert(!m_loaded); { for (const auto& wtx : wallet.getWalletTxs()) { if (TransactionRecord::showTransaction()) { @@ -115,6 +119,8 @@ public: } } } + m_loaded = true; + DispatchNotifications(); } /* Update our model of the wallet incrementally, to synchronize our model of the wallet @@ -249,12 +255,12 @@ TransactionTableModel::TransactionTableModel(const PlatformStyle *_platformStyle fProcessingQueuedTransactions(false), platformStyle(_platformStyle) { + subscribeToCoreSignals(); + columns << QString() << QString() << tr("Date") << tr("Type") << tr("Label") << BitcoinUnits::getAmountColumnTitle(walletModel->getOptionsModel()->getDisplayUnit()); priv->refreshWallet(walletModel->wallet()); connect(walletModel->getOptionsModel(), &OptionsModel::displayUnitChanged, this, &TransactionTableModel::updateDisplayUnit); - - subscribeToCoreSignals(); } TransactionTableModel::~TransactionTableModel() @@ -409,9 +415,9 @@ QVariant TransactionTableModel::txAddressDecoration(const TransactionRecord *wtx QString TransactionTableModel::formatTxToAddress(const TransactionRecord *wtx, bool tooltip) const { QString watchAddress; - if (tooltip) { + if (tooltip && wtx->involvesWatchAddress) { // Mark transactions involving watch-only addresses by adding " (watch-only)" - watchAddress = wtx->involvesWatchAddress ? QString(" (") + tr("watch-only") + QString(")") : ""; + watchAddress = QLatin1String(" (") + tr("watch-only") + QLatin1Char(')'); } switch(wtx->type) @@ -526,27 +532,30 @@ QVariant TransactionTableModel::data(const QModelIndex &index, int role) const return QVariant(); TransactionRecord *rec = static_cast<TransactionRecord*>(index.internalPointer()); - switch(role) - { + const auto column = static_cast<ColumnIndex>(index.column()); + switch (role) { case RawDecorationRole: - switch(index.column()) - { + switch (column) { case Status: return txStatusDecoration(rec); case Watchonly: return txWatchonlyDecoration(rec); + case Date: return {}; + case Type: return {}; case ToAddress: return txAddressDecoration(rec); - } - break; + case Amount: return {}; + } // no default case, so the compiler can warn about missing cases + assert(false); case Qt::DecorationRole: { QIcon icon = qvariant_cast<QIcon>(index.data(RawDecorationRole)); return platformStyle->TextColorIcon(icon); } case Qt::DisplayRole: - switch(index.column()) - { + switch (column) { + case Status: return {}; + case Watchonly: return {}; case Date: return formatTxDate(rec); case Type: @@ -555,12 +564,11 @@ QVariant TransactionTableModel::data(const QModelIndex &index, int role) const return formatTxToAddress(rec, false); case Amount: return formatTxAmount(rec, true, BitcoinUnits::SeparatorStyle::ALWAYS); - } - break; + } // no default case, so the compiler can warn about missing cases + assert(false); case Qt::EditRole: // Edit role is used for sorting, so return the unformatted values - switch(index.column()) - { + switch (column) { case Status: return QString::fromStdString(rec->status.sortKey); case Date: @@ -573,8 +581,8 @@ QVariant TransactionTableModel::data(const QModelIndex &index, int role) const return formatTxToAddress(rec, true); case Amount: return qint64(rec->credit + rec->debit); - } - break; + } // no default case, so the compiler can warn about missing cases + assert(false); case Qt::ToolTipRole: return formatTooltip(rec); case Qt::TextAlignmentRole: @@ -717,7 +725,7 @@ void TransactionTablePriv::NotifyTransactionChanged(const uint256 &hash, ChangeT TransactionNotification notification(hash, status, showTransaction); - if (fQueueNotifications) + if (!m_loaded || m_loading) { vQueueNotifications.push_back(notification); return; @@ -725,36 +733,34 @@ void TransactionTablePriv::NotifyTransactionChanged(const uint256 &hash, ChangeT notification.invoke(parent); } -void TransactionTablePriv::ShowProgress(const std::string &title, int nProgress) +void TransactionTablePriv::DispatchNotifications() { - if (nProgress == 0) - fQueueNotifications = true; + if (!m_loaded || m_loading) return; - if (nProgress == 100) + if (vQueueNotifications.size() > 10) { // prevent balloon spam, show maximum 10 balloons + bool invoked = QMetaObject::invokeMethod(parent, "setProcessingQueuedTransactions", Qt::QueuedConnection, Q_ARG(bool, true)); + assert(invoked); + } + for (unsigned int i = 0; i < vQueueNotifications.size(); ++i) { - fQueueNotifications = false; - if (vQueueNotifications.size() > 10) { // prevent balloon spam, show maximum 10 balloons - bool invoked = QMetaObject::invokeMethod(parent, "setProcessingQueuedTransactions", Qt::QueuedConnection, Q_ARG(bool, true)); + if (vQueueNotifications.size() - i <= 10) { + bool invoked = QMetaObject::invokeMethod(parent, "setProcessingQueuedTransactions", Qt::QueuedConnection, Q_ARG(bool, false)); assert(invoked); } - for (unsigned int i = 0; i < vQueueNotifications.size(); ++i) - { - if (vQueueNotifications.size() - i <= 10) { - bool invoked = QMetaObject::invokeMethod(parent, "setProcessingQueuedTransactions", Qt::QueuedConnection, Q_ARG(bool, false)); - assert(invoked); - } - vQueueNotifications[i].invoke(parent); - } - vQueueNotifications.clear(); + vQueueNotifications[i].invoke(parent); } + vQueueNotifications.clear(); } void TransactionTableModel::subscribeToCoreSignals() { // Connect signals to wallet m_handler_transaction_changed = walletModel->wallet().handleTransactionChanged(std::bind(&TransactionTablePriv::NotifyTransactionChanged, priv, std::placeholders::_1, std::placeholders::_2)); - m_handler_show_progress = walletModel->wallet().handleShowProgress(std::bind(&TransactionTablePriv::ShowProgress, priv, std::placeholders::_1, std::placeholders::_2)); + m_handler_show_progress = walletModel->wallet().handleShowProgress([this](const std::string&, int progress) { + priv->m_loading = progress < 100; + priv->DispatchNotifications(); + }); } void TransactionTableModel::unsubscribeFromCoreSignals() |