Raven Core  3.0.0
P2P Digital Currency
assettablemodel.cpp
Go to the documentation of this file.
1 // Copyright (c) 2011-2016 The Bitcoin Core developers
2 // Copyright (c) 2017-2019 The Raven Core developers
3 // Distributed under the MIT software license, see the accompanying
4 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
5 
6 #include "assettablemodel.h"
7 #include "assetrecord.h"
8 
9 #include "guiconstants.h"
10 #include "guiutil.h"
11 #include "walletmodel.h"
12 #include "wallet/wallet.h"
13 
14 #include "core_io.h"
15 
16 #include "amount.h"
17 #include "assets/assets.h"
18 #include "validation.h"
19 #include "platformstyle.h"
20 
21 #include <QDebug>
22 #include <QStringList>
23 
24 
25 
27 public:
29  parent(_parent)
30  {
31  }
32 
34 
35  QList<AssetRecord> cachedBalances;
36 
37  // loads all current balances into cache
38  void refreshWallet() {
39  qDebug() << "AssetTablePriv::refreshWallet";
40  cachedBalances.clear();
41  auto currentActiveAssetCache = GetCurrentAssetCache();
42  if (currentActiveAssetCache) {
43  {
44  LOCK(cs_main);
45  std::map<std::string, CAmount> balances;
46  std::map<std::string, std::vector<COutput> > outputs;
47  if (!GetAllMyAssetBalances(outputs, balances)) {
48  qWarning("AssetTablePriv::refreshWallet: Error retrieving asset balances");
49  return;
50  }
51  std::set<std::string> setAssetsToSkip;
52  auto bal = balances.begin();
53  for (; bal != balances.end(); bal++) {
54  // retrieve units for asset
55  uint8_t units = OWNER_UNITS;
56  bool fIsAdministrator = true;
57 
58  if (setAssetsToSkip.count(bal->first))
59  continue;
60 
61  if (!IsAssetNameAnOwner(bal->first)) {
62  // Asset is not an administrator asset
63  CNewAsset assetData;
64  if (!currentActiveAssetCache->GetAssetMetaDataIfExists(bal->first, assetData)) {
65  qWarning("AssetTablePriv::refreshWallet: Error retrieving asset data");
66  return;
67  }
68  units = assetData.units;
69  // If we have the administrator asset, add it to the skip listÃ¥
70  if (balances.count(bal->first + OWNER_TAG)) {
71  setAssetsToSkip.insert(bal->first + OWNER_TAG);
72  } else {
73  fIsAdministrator = false;
74  }
75  } else {
76  // Asset is an administrator asset, if we own assets that is administrators, skip this balance
77  std::string name = bal->first;
78  name.pop_back();
79  if (balances.count(name)) {
80  setAssetsToSkip.insert(bal->first);
81  continue;
82  }
83  }
84  cachedBalances.append(AssetRecord(bal->first, bal->second, units, fIsAdministrator));
85  }
86  }
87  }
88  }
89 
90 
91  int size() {
92  return cachedBalances.size();
93  }
94 
95  AssetRecord *index(int idx) {
96  if (idx >= 0 && idx < cachedBalances.size()) {
97  return &cachedBalances[idx];
98  }
99  return 0;
100  }
101 
102 };
103 
105  QAbstractTableModel(parent),
106  walletModel(parent),
107  priv(new AssetTablePriv(this))
108 {
109  columns << tr("Name") << tr("Quantity");
110 
111  priv->refreshWallet();
112 };
113 
115 {
116  delete priv;
117 };
118 
120  qDebug() << "AssetTableModel::CheckBalanceChanged";
121  // TODO: optimize by 1) updating cache incrementally; and 2) emitting more specific dataChanged signals
122  Q_EMIT layoutAboutToBeChanged();
123  priv->refreshWallet();
124  Q_EMIT dataChanged(index(0, 0, QModelIndex()), index(priv->size(), columns.length()-1, QModelIndex()));
125  Q_EMIT layoutChanged();
126 }
127 
128 int AssetTableModel::rowCount(const QModelIndex &parent) const
129 {
130  Q_UNUSED(parent);
131  return priv->size();
132 }
133 
134 int AssetTableModel::columnCount(const QModelIndex &parent) const
135 {
136  Q_UNUSED(parent);
137  return columns.length();
138 }
139 
140 QVariant AssetTableModel::data(const QModelIndex &index, int role) const
141 {
142  Q_UNUSED(role);
143  if(!index.isValid())
144  return QVariant();
145  AssetRecord *rec = static_cast<AssetRecord*>(index.internalPointer());
146 
147  switch (role)
148  {
149  case AmountRole:
150  return (unsigned long long) rec->quantity;
151  case AssetNameRole:
152  return QString::fromStdString(rec->name);
153  case FormattedAmountRole:
154  return QString::fromStdString(rec->formattedQuantity());
155  case AdministratorRole:
156  {
157  return rec->fIsAdministrator;
158  }
159  case Qt::DecorationRole:
160  {
161  QPixmap pixmap;
162 
163  if (!rec->fIsAdministrator)
164  QVariant();
165 
166  if (darkModeEnabled)
167  pixmap = QPixmap::fromImage(QImage(":/icons/asset_administrator_dark"));
168  else
169  pixmap = QPixmap::fromImage(QImage(":/icons/asset_administrator"));
170 
171  return pixmap;
172  }
173  case Qt::ToolTipRole:
174  return formatTooltip(rec);
175  default:
176  return QVariant();
177  }
178 }
179 
180 QVariant AssetTableModel::headerData(int section, Qt::Orientation orientation, int role) const
181 {
182  if (role == Qt::DisplayRole)
183  {
184  if (section < columns.size())
185  return columns.at(section);
186  } else if (role == Qt::SizeHintRole) {
187  if (section == 0)
188  return QSize(300, 50);
189  else if (section == 1)
190  return QSize(200, 50);
191  } else if (role == Qt::TextAlignmentRole) {
192  return Qt::AlignHCenter + Qt::AlignVCenter;
193  }
194 
195  return QVariant();
196 }
197 
198 QModelIndex AssetTableModel::index(int row, int column, const QModelIndex &parent) const
199 {
200  Q_UNUSED(parent);
201  AssetRecord *data = priv->index(row);
202  if(data)
203  {
204  QModelIndex idx = createIndex(row, column, priv->index(row));
205  return idx;
206  }
207 
208  return QModelIndex();
209 }
210 
212 {
213  QString tooltip = formatAssetName(rec) + QString("\n") + formatAssetQuantity(rec);
214  return tooltip;
215 }
216 
218 {
219  return tr("Asset Name: ") + QString::fromStdString(wtx->name);
220 }
221 
223 {
224  return tr("Asset Quantity: ") + QString::fromStdString(wtx->formattedQuantity());
225 }
AssetTableModel(WalletModel *parent=0)
QModelIndex index(int row, int column, const QModelIndex &parent=QModelIndex()) const
int8_t units
Definition: assettypes.h:102
CCriticalSection cs_main
Global state.
Definition: validation.cpp:72
QString formatAssetName(const AssetRecord *wtx) const
AssetTablePriv(AssetTableModel *_parent)
std::string name
Definition: assetrecord.h:47
QVariant data(const QModelIndex &index, int role) const
QString formatTooltip(const AssetRecord *rec) const
AssetTableModel * parent
#define OWNER_UNITS
Definition: assets.h:34
QString formatAssetQuantity(const AssetRecord *wtx) const
AssetRecord * index(int idx)
QVariant headerData(int section, Qt::Orientation orientation, int role) const
UI model for unspent assets.
Definition: assetrecord.h:16
bool darkModeEnabled
Models assets portion of wallet as table of owned assets.
CAssetsCache * GetCurrentAssetCache()
#define LOCK(cs)
Definition: sync.h:176
bool fIsAdministrator
Definition: assetrecord.h:50
#define OWNER_TAG
Definition: assets.h:32
int columnCount(const QModelIndex &parent) const
int rowCount(const QModelIndex &parent) const
RVN or name of an asset.
QList< AssetRecord > cachedBalances
AssetTablePriv * priv
Interface to Raven wallet from Qt view code.
Definition: walletmodel.h:165
bool GetAllMyAssetBalances(std::map< std::string, std::vector< COutput > > &outputs, std::map< std::string, CAmount > &amounts, const int confirmations, const std::string &prefix)
sets balances with the total quantity of each owned asset
Definition: assets.cpp:3673
Formatted amount, without brackets when unconfirmed.
Net amount of transaction.
QStringList columns
std::string formattedQuantity() const
Definition: assetrecord.h:30
CAmount quantity
Definition: assetrecord.h:48
bool IsAssetNameAnOwner(const std::string &name)
Check if an asset is an owner.
Definition: assets.cpp:296