Line data Source code
1 : // Copyright (c) 2011-2013 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 "transactionview.h"
6 :
7 : #include "addresstablemodel.h"
8 : #include "bitcoinunits.h"
9 : #include "csvmodelwriter.h"
10 : #include "editaddressdialog.h"
11 : #include "guiutil.h"
12 : #include "optionsmodel.h"
13 : #include "platformstyle.h"
14 : #include "transactiondescdialog.h"
15 : #include "transactionfilterproxy.h"
16 : #include "transactionrecord.h"
17 : #include "transactiontablemodel.h"
18 : #include "walletmodel.h"
19 :
20 : #include "ui_interface.h"
21 :
22 : #include <QComboBox>
23 : #include <QDateTimeEdit>
24 : #include <QDesktopServices>
25 : #include <QDoubleValidator>
26 : #include <QHBoxLayout>
27 : #include <QHeaderView>
28 : #include <QLabel>
29 : #include <QLineEdit>
30 : #include <QMenu>
31 : #include <QPoint>
32 : #include <QScrollBar>
33 : #include <QSignalMapper>
34 : #include <QTableView>
35 : #include <QUrl>
36 : #include <QVBoxLayout>
37 :
38 0 : TransactionView::TransactionView(const PlatformStyle *platformStyle, QWidget *parent) :
39 : QWidget(parent), model(0), transactionProxyModel(0),
40 0 : transactionView(0)
41 : {
42 : // Build filter row
43 0 : setContentsMargins(0,0,0,0);
44 :
45 0 : QHBoxLayout *hlayout = new QHBoxLayout();
46 0 : hlayout->setContentsMargins(0,0,0,0);
47 :
48 0 : if (platformStyle->getUseExtraSpacing()) {
49 0 : hlayout->setSpacing(5);
50 0 : hlayout->addSpacing(26);
51 : } else {
52 0 : hlayout->setSpacing(0);
53 0 : hlayout->addSpacing(23);
54 : }
55 :
56 0 : watchOnlyWidget = new QComboBox(this);
57 0 : watchOnlyWidget->setFixedWidth(24);
58 0 : watchOnlyWidget->addItem("", TransactionFilterProxy::WatchOnlyFilter_All);
59 0 : watchOnlyWidget->addItem(platformStyle->SingleColorIcon(":/icons/eye_plus"), "", TransactionFilterProxy::WatchOnlyFilter_Yes);
60 0 : watchOnlyWidget->addItem(platformStyle->SingleColorIcon(":/icons/eye_minus"), "", TransactionFilterProxy::WatchOnlyFilter_No);
61 0 : hlayout->addWidget(watchOnlyWidget);
62 :
63 0 : dateWidget = new QComboBox(this);
64 0 : if (platformStyle->getUseExtraSpacing()) {
65 0 : dateWidget->setFixedWidth(121);
66 : } else {
67 0 : dateWidget->setFixedWidth(120);
68 : }
69 0 : dateWidget->addItem(tr("All"), All);
70 0 : dateWidget->addItem(tr("Today"), Today);
71 0 : dateWidget->addItem(tr("This week"), ThisWeek);
72 0 : dateWidget->addItem(tr("This month"), ThisMonth);
73 0 : dateWidget->addItem(tr("Last month"), LastMonth);
74 0 : dateWidget->addItem(tr("This year"), ThisYear);
75 0 : dateWidget->addItem(tr("Range..."), Range);
76 0 : hlayout->addWidget(dateWidget);
77 :
78 0 : typeWidget = new QComboBox(this);
79 0 : if (platformStyle->getUseExtraSpacing()) {
80 0 : typeWidget->setFixedWidth(121);
81 : } else {
82 0 : typeWidget->setFixedWidth(120);
83 : }
84 :
85 0 : typeWidget->addItem(tr("All"), TransactionFilterProxy::ALL_TYPES);
86 0 : typeWidget->addItem(tr("Received with"), TransactionFilterProxy::TYPE(TransactionRecord::RecvWithAddress) |
87 0 : TransactionFilterProxy::TYPE(TransactionRecord::RecvFromOther));
88 0 : typeWidget->addItem(tr("Sent to"), TransactionFilterProxy::TYPE(TransactionRecord::SendToAddress) |
89 0 : TransactionFilterProxy::TYPE(TransactionRecord::SendToOther));
90 0 : typeWidget->addItem(tr("To yourself"), TransactionFilterProxy::TYPE(TransactionRecord::SendToSelf));
91 0 : typeWidget->addItem(tr("Mined"), TransactionFilterProxy::TYPE(TransactionRecord::Generated));
92 0 : typeWidget->addItem(tr("Other"), TransactionFilterProxy::TYPE(TransactionRecord::Other));
93 :
94 0 : hlayout->addWidget(typeWidget);
95 :
96 0 : addressWidget = new QLineEdit(this);
97 : #if QT_VERSION >= 0x040700
98 0 : addressWidget->setPlaceholderText(tr("Enter address or label to search"));
99 : #endif
100 0 : hlayout->addWidget(addressWidget);
101 :
102 0 : amountWidget = new QLineEdit(this);
103 : #if QT_VERSION >= 0x040700
104 0 : amountWidget->setPlaceholderText(tr("Min amount"));
105 : #endif
106 0 : if (platformStyle->getUseExtraSpacing()) {
107 0 : amountWidget->setFixedWidth(97);
108 : } else {
109 0 : amountWidget->setFixedWidth(100);
110 : }
111 0 : amountWidget->setValidator(new QDoubleValidator(0, 1e20, 8, this));
112 0 : hlayout->addWidget(amountWidget);
113 :
114 0 : QVBoxLayout *vlayout = new QVBoxLayout(this);
115 0 : vlayout->setContentsMargins(0,0,0,0);
116 0 : vlayout->setSpacing(0);
117 :
118 0 : QTableView *view = new QTableView(this);
119 0 : vlayout->addLayout(hlayout);
120 0 : vlayout->addWidget(createDateRangeWidget());
121 0 : vlayout->addWidget(view);
122 0 : vlayout->setSpacing(0);
123 0 : int width = view->verticalScrollBar()->sizeHint().width();
124 : // Cover scroll bar width with spacing
125 0 : if (platformStyle->getUseExtraSpacing()) {
126 0 : hlayout->addSpacing(width+2);
127 : } else {
128 0 : hlayout->addSpacing(width);
129 : }
130 : // Always show scroll bar
131 0 : view->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOn);
132 0 : view->setTabKeyNavigation(false);
133 0 : view->setContextMenuPolicy(Qt::CustomContextMenu);
134 :
135 0 : view->installEventFilter(this);
136 :
137 0 : transactionView = view;
138 :
139 : // Actions
140 0 : QAction *copyAddressAction = new QAction(tr("Copy address"), this);
141 0 : QAction *copyLabelAction = new QAction(tr("Copy label"), this);
142 0 : QAction *copyAmountAction = new QAction(tr("Copy amount"), this);
143 0 : QAction *copyTxIDAction = new QAction(tr("Copy transaction ID"), this);
144 0 : QAction *editLabelAction = new QAction(tr("Edit label"), this);
145 0 : QAction *showDetailsAction = new QAction(tr("Show transaction details"), this);
146 :
147 0 : contextMenu = new QMenu();
148 0 : contextMenu->addAction(copyAddressAction);
149 0 : contextMenu->addAction(copyLabelAction);
150 0 : contextMenu->addAction(copyAmountAction);
151 0 : contextMenu->addAction(copyTxIDAction);
152 0 : contextMenu->addAction(editLabelAction);
153 0 : contextMenu->addAction(showDetailsAction);
154 :
155 0 : mapperThirdPartyTxUrls = new QSignalMapper(this);
156 :
157 : // Connect actions
158 0 : connect(mapperThirdPartyTxUrls, SIGNAL(mapped(QString)), this, SLOT(openThirdPartyTxUrl(QString)));
159 :
160 0 : connect(dateWidget, SIGNAL(activated(int)), this, SLOT(chooseDate(int)));
161 0 : connect(typeWidget, SIGNAL(activated(int)), this, SLOT(chooseType(int)));
162 0 : connect(watchOnlyWidget, SIGNAL(activated(int)), this, SLOT(chooseWatchonly(int)));
163 0 : connect(addressWidget, SIGNAL(textChanged(QString)), this, SLOT(changedPrefix(QString)));
164 0 : connect(amountWidget, SIGNAL(textChanged(QString)), this, SLOT(changedAmount(QString)));
165 :
166 0 : connect(view, SIGNAL(doubleClicked(QModelIndex)), this, SIGNAL(doubleClicked(QModelIndex)));
167 0 : connect(view, SIGNAL(customContextMenuRequested(QPoint)), this, SLOT(contextualMenu(QPoint)));
168 :
169 0 : connect(copyAddressAction, SIGNAL(triggered()), this, SLOT(copyAddress()));
170 0 : connect(copyLabelAction, SIGNAL(triggered()), this, SLOT(copyLabel()));
171 0 : connect(copyAmountAction, SIGNAL(triggered()), this, SLOT(copyAmount()));
172 0 : connect(copyTxIDAction, SIGNAL(triggered()), this, SLOT(copyTxID()));
173 0 : connect(editLabelAction, SIGNAL(triggered()), this, SLOT(editLabel()));
174 0 : connect(showDetailsAction, SIGNAL(triggered()), this, SLOT(showDetails()));
175 0 : }
176 :
177 0 : void TransactionView::setModel(WalletModel *model)
178 : {
179 0 : this->model = model;
180 0 : if(model)
181 : {
182 0 : transactionProxyModel = new TransactionFilterProxy(this);
183 0 : transactionProxyModel->setSourceModel(model->getTransactionTableModel());
184 0 : transactionProxyModel->setDynamicSortFilter(true);
185 0 : transactionProxyModel->setSortCaseSensitivity(Qt::CaseInsensitive);
186 0 : transactionProxyModel->setFilterCaseSensitivity(Qt::CaseInsensitive);
187 :
188 0 : transactionProxyModel->setSortRole(Qt::EditRole);
189 :
190 0 : transactionView->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
191 0 : transactionView->setModel(transactionProxyModel);
192 0 : transactionView->setAlternatingRowColors(true);
193 0 : transactionView->setSelectionBehavior(QAbstractItemView::SelectRows);
194 0 : transactionView->setSelectionMode(QAbstractItemView::ExtendedSelection);
195 0 : transactionView->setSortingEnabled(true);
196 0 : transactionView->sortByColumn(TransactionTableModel::Status, Qt::DescendingOrder);
197 0 : transactionView->verticalHeader()->hide();
198 :
199 0 : transactionView->setColumnWidth(TransactionTableModel::Status, STATUS_COLUMN_WIDTH);
200 0 : transactionView->setColumnWidth(TransactionTableModel::Watchonly, WATCHONLY_COLUMN_WIDTH);
201 0 : transactionView->setColumnWidth(TransactionTableModel::Date, DATE_COLUMN_WIDTH);
202 0 : transactionView->setColumnWidth(TransactionTableModel::Type, TYPE_COLUMN_WIDTH);
203 0 : transactionView->setColumnWidth(TransactionTableModel::Amount, AMOUNT_MINIMUM_COLUMN_WIDTH);
204 :
205 0 : columnResizingFixer = new GUIUtil::TableViewLastColumnResizingFixer(transactionView, AMOUNT_MINIMUM_COLUMN_WIDTH, MINIMUM_COLUMN_WIDTH);
206 :
207 0 : if (model->getOptionsModel())
208 : {
209 : // Add third party transaction URLs to context menu
210 0 : QStringList listUrls = model->getOptionsModel()->getThirdPartyTxUrls().split("|", QString::SkipEmptyParts);
211 0 : for (int i = 0; i < listUrls.size(); ++i)
212 : {
213 0 : QString host = QUrl(listUrls[i].trimmed(), QUrl::StrictMode).host();
214 0 : if (!host.isEmpty())
215 : {
216 0 : QAction *thirdPartyTxUrlAction = new QAction(host, this); // use host as menu item label
217 0 : if (i == 0)
218 0 : contextMenu->addSeparator();
219 0 : contextMenu->addAction(thirdPartyTxUrlAction);
220 0 : connect(thirdPartyTxUrlAction, SIGNAL(triggered()), mapperThirdPartyTxUrls, SLOT(map()));
221 0 : mapperThirdPartyTxUrls->setMapping(thirdPartyTxUrlAction, listUrls[i].trimmed());
222 : }
223 0 : }
224 : }
225 :
226 : // show/hide column Watch-only
227 0 : updateWatchOnlyColumn(model->haveWatchOnly());
228 :
229 : // Watch-only signal
230 0 : connect(model, SIGNAL(notifyWatchonlyChanged(bool)), this, SLOT(updateWatchOnlyColumn(bool)));
231 : }
232 0 : }
233 :
234 0 : void TransactionView::chooseDate(int idx)
235 : {
236 0 : if(!transactionProxyModel)
237 0 : return;
238 0 : QDate current = QDate::currentDate();
239 0 : dateRangeWidget->setVisible(false);
240 0 : switch(dateWidget->itemData(idx).toInt())
241 : {
242 : case All:
243 : transactionProxyModel->setDateRange(
244 : TransactionFilterProxy::MIN_DATE,
245 0 : TransactionFilterProxy::MAX_DATE);
246 : break;
247 : case Today:
248 : transactionProxyModel->setDateRange(
249 : QDateTime(current),
250 0 : TransactionFilterProxy::MAX_DATE);
251 0 : break;
252 : case ThisWeek: {
253 : // Find last Monday
254 0 : QDate startOfWeek = current.addDays(-(current.dayOfWeek()-1));
255 : transactionProxyModel->setDateRange(
256 : QDateTime(startOfWeek),
257 0 : TransactionFilterProxy::MAX_DATE);
258 :
259 0 : } break;
260 : case ThisMonth:
261 : transactionProxyModel->setDateRange(
262 : QDateTime(QDate(current.year(), current.month(), 1)),
263 0 : TransactionFilterProxy::MAX_DATE);
264 0 : break;
265 : case LastMonth:
266 : transactionProxyModel->setDateRange(
267 0 : QDateTime(QDate(current.year(), current.month()-1, 1)),
268 0 : QDateTime(QDate(current.year(), current.month(), 1)));
269 0 : break;
270 : case ThisYear:
271 : transactionProxyModel->setDateRange(
272 : QDateTime(QDate(current.year(), 1, 1)),
273 0 : TransactionFilterProxy::MAX_DATE);
274 0 : break;
275 : case Range:
276 0 : dateRangeWidget->setVisible(true);
277 0 : dateRangeChanged();
278 : break;
279 : }
280 : }
281 :
282 0 : void TransactionView::chooseType(int idx)
283 : {
284 0 : if(!transactionProxyModel)
285 0 : return;
286 : transactionProxyModel->setTypeFilter(
287 0 : typeWidget->itemData(idx).toInt());
288 : }
289 :
290 0 : void TransactionView::chooseWatchonly(int idx)
291 : {
292 0 : if(!transactionProxyModel)
293 0 : return;
294 : transactionProxyModel->setWatchOnlyFilter(
295 0 : (TransactionFilterProxy::WatchOnlyFilter)watchOnlyWidget->itemData(idx).toInt());
296 : }
297 :
298 0 : void TransactionView::changedPrefix(const QString &prefix)
299 : {
300 0 : if(!transactionProxyModel)
301 0 : return;
302 0 : transactionProxyModel->setAddressPrefix(prefix);
303 : }
304 :
305 0 : void TransactionView::changedAmount(const QString &amount)
306 : {
307 0 : if(!transactionProxyModel)
308 0 : return;
309 0 : CAmount amount_parsed = 0;
310 0 : if(BitcoinUnits::parse(model->getOptionsModel()->getDisplayUnit(), amount, &amount_parsed))
311 : {
312 0 : transactionProxyModel->setMinAmount(amount_parsed);
313 : }
314 : else
315 : {
316 0 : transactionProxyModel->setMinAmount(0);
317 : }
318 : }
319 :
320 0 : void TransactionView::exportClicked()
321 : {
322 : // CSV is currently the only supported format
323 : QString filename = GUIUtil::getSaveFileName(this,
324 : tr("Export Transaction History"), QString(),
325 0 : tr("Comma separated file (*.csv)"), NULL);
326 :
327 0 : if (filename.isNull())
328 0 : return;
329 :
330 0 : CSVModelWriter writer(filename);
331 :
332 : // name, column, role
333 0 : writer.setModel(transactionProxyModel);
334 0 : writer.addColumn(tr("Confirmed"), 0, TransactionTableModel::ConfirmedRole);
335 0 : if (model && model->haveWatchOnly())
336 0 : writer.addColumn(tr("Watch-only"), TransactionTableModel::Watchonly);
337 0 : writer.addColumn(tr("Date"), 0, TransactionTableModel::DateRole);
338 0 : writer.addColumn(tr("Type"), TransactionTableModel::Type, Qt::EditRole);
339 0 : writer.addColumn(tr("Label"), 0, TransactionTableModel::LabelRole);
340 0 : writer.addColumn(tr("Address"), 0, TransactionTableModel::AddressRole);
341 0 : writer.addColumn(BitcoinUnits::getAmountColumnTitle(model->getOptionsModel()->getDisplayUnit()), 0, TransactionTableModel::FormattedAmountRole);
342 0 : writer.addColumn(tr("ID"), 0, TransactionTableModel::TxIDRole);
343 :
344 0 : if(!writer.write()) {
345 : Q_EMIT message(tr("Exporting Failed"), tr("There was an error trying to save the transaction history to %1.").arg(filename),
346 0 : CClientUIInterface::MSG_ERROR);
347 : }
348 : else {
349 : Q_EMIT message(tr("Exporting Successful"), tr("The transaction history was successfully saved to %1.").arg(filename),
350 0 : CClientUIInterface::MSG_INFORMATION);
351 0 : }
352 : }
353 :
354 0 : void TransactionView::contextualMenu(const QPoint &point)
355 : {
356 0 : QModelIndex index = transactionView->indexAt(point);
357 0 : if(index.isValid())
358 : {
359 0 : contextMenu->exec(QCursor::pos());
360 : }
361 0 : }
362 :
363 0 : void TransactionView::copyAddress()
364 : {
365 0 : GUIUtil::copyEntryData(transactionView, 0, TransactionTableModel::AddressRole);
366 0 : }
367 :
368 0 : void TransactionView::copyLabel()
369 : {
370 0 : GUIUtil::copyEntryData(transactionView, 0, TransactionTableModel::LabelRole);
371 0 : }
372 :
373 0 : void TransactionView::copyAmount()
374 : {
375 0 : GUIUtil::copyEntryData(transactionView, 0, TransactionTableModel::FormattedAmountRole);
376 0 : }
377 :
378 0 : void TransactionView::copyTxID()
379 : {
380 0 : GUIUtil::copyEntryData(transactionView, 0, TransactionTableModel::TxIDRole);
381 0 : }
382 :
383 0 : void TransactionView::editLabel()
384 : {
385 0 : if(!transactionView->selectionModel() ||!model)
386 0 : return;
387 0 : QModelIndexList selection = transactionView->selectionModel()->selectedRows();
388 0 : if(!selection.isEmpty())
389 : {
390 0 : AddressTableModel *addressBook = model->getAddressTableModel();
391 0 : if(!addressBook)
392 0 : return;
393 0 : QString address = selection.at(0).data(TransactionTableModel::AddressRole).toString();
394 0 : if(address.isEmpty())
395 : {
396 : // If this transaction has no associated address, exit
397 0 : return;
398 : }
399 : // Is address in address book? Address book can miss address when a transaction is
400 : // sent from outside the UI.
401 0 : int idx = addressBook->lookupAddress(address);
402 0 : if(idx != -1)
403 : {
404 : // Edit sending / receiving address
405 0 : QModelIndex modelIdx = addressBook->index(idx, 0, QModelIndex());
406 : // Determine type of address, launch appropriate editor dialog type
407 0 : QString type = modelIdx.data(AddressTableModel::TypeRole).toString();
408 :
409 : EditAddressDialog dlg(
410 0 : type == AddressTableModel::Receive
411 : ? EditAddressDialog::EditReceivingAddress
412 0 : : EditAddressDialog::EditSendingAddress, this);
413 0 : dlg.setModel(addressBook);
414 0 : dlg.loadRow(idx);
415 0 : dlg.exec();
416 : }
417 : else
418 : {
419 : // Add sending address
420 : EditAddressDialog dlg(EditAddressDialog::NewSendingAddress,
421 0 : this);
422 0 : dlg.setModel(addressBook);
423 0 : dlg.setAddress(address);
424 0 : dlg.exec();
425 0 : }
426 0 : }
427 : }
428 :
429 0 : void TransactionView::showDetails()
430 : {
431 0 : if(!transactionView->selectionModel())
432 0 : return;
433 0 : QModelIndexList selection = transactionView->selectionModel()->selectedRows();
434 0 : if(!selection.isEmpty())
435 : {
436 0 : TransactionDescDialog dlg(selection.at(0));
437 0 : dlg.exec();
438 0 : }
439 : }
440 :
441 0 : void TransactionView::openThirdPartyTxUrl(QString url)
442 : {
443 0 : if(!transactionView || !transactionView->selectionModel())
444 0 : return;
445 0 : QModelIndexList selection = transactionView->selectionModel()->selectedRows(0);
446 0 : if(!selection.isEmpty())
447 0 : QDesktopServices::openUrl(QUrl::fromUserInput(url.replace("%s", selection.at(0).data(TransactionTableModel::TxHashRole).toString())));
448 : }
449 :
450 0 : QWidget *TransactionView::createDateRangeWidget()
451 : {
452 0 : dateRangeWidget = new QFrame();
453 0 : dateRangeWidget->setFrameStyle(QFrame::Panel | QFrame::Raised);
454 0 : dateRangeWidget->setContentsMargins(1,1,1,1);
455 0 : QHBoxLayout *layout = new QHBoxLayout(dateRangeWidget);
456 0 : layout->setContentsMargins(0,0,0,0);
457 0 : layout->addSpacing(23);
458 0 : layout->addWidget(new QLabel(tr("Range:")));
459 :
460 0 : dateFrom = new QDateTimeEdit(this);
461 0 : dateFrom->setDisplayFormat("dd/MM/yy");
462 0 : dateFrom->setCalendarPopup(true);
463 0 : dateFrom->setMinimumWidth(100);
464 0 : dateFrom->setDate(QDate::currentDate().addDays(-7));
465 0 : layout->addWidget(dateFrom);
466 0 : layout->addWidget(new QLabel(tr("to")));
467 :
468 0 : dateTo = new QDateTimeEdit(this);
469 0 : dateTo->setDisplayFormat("dd/MM/yy");
470 0 : dateTo->setCalendarPopup(true);
471 0 : dateTo->setMinimumWidth(100);
472 0 : dateTo->setDate(QDate::currentDate());
473 0 : layout->addWidget(dateTo);
474 0 : layout->addStretch();
475 :
476 : // Hide by default
477 0 : dateRangeWidget->setVisible(false);
478 :
479 : // Notify on change
480 0 : connect(dateFrom, SIGNAL(dateChanged(QDate)), this, SLOT(dateRangeChanged()));
481 0 : connect(dateTo, SIGNAL(dateChanged(QDate)), this, SLOT(dateRangeChanged()));
482 :
483 0 : return dateRangeWidget;
484 : }
485 :
486 0 : void TransactionView::dateRangeChanged()
487 : {
488 0 : if(!transactionProxyModel)
489 0 : return;
490 : transactionProxyModel->setDateRange(
491 0 : QDateTime(dateFrom->date()),
492 0 : QDateTime(dateTo->date()).addDays(1));
493 : }
494 :
495 0 : void TransactionView::focusTransaction(const QModelIndex &idx)
496 : {
497 0 : if(!transactionProxyModel)
498 0 : return;
499 0 : QModelIndex targetIdx = transactionProxyModel->mapFromSource(idx);
500 0 : transactionView->scrollTo(targetIdx);
501 0 : transactionView->setCurrentIndex(targetIdx);
502 0 : transactionView->setFocus();
503 : }
504 :
505 : // We override the virtual resizeEvent of the QWidget to adjust tables column
506 : // sizes as the tables width is proportional to the dialogs width.
507 0 : void TransactionView::resizeEvent(QResizeEvent* event)
508 : {
509 0 : QWidget::resizeEvent(event);
510 0 : columnResizingFixer->stretchColumnWidth(TransactionTableModel::ToAddress);
511 0 : }
512 :
513 : // Need to override default Ctrl+C action for amount as default behaviour is just to copy DisplayRole text
514 0 : bool TransactionView::eventFilter(QObject *obj, QEvent *event)
515 : {
516 0 : if (event->type() == QEvent::KeyPress)
517 : {
518 0 : QKeyEvent *ke = static_cast<QKeyEvent *>(event);
519 0 : if (ke->key() == Qt::Key_C && ke->modifiers().testFlag(Qt::ControlModifier))
520 : {
521 0 : QModelIndex i = this->transactionView->currentIndex();
522 0 : if (i.isValid() && i.column() == TransactionTableModel::Amount)
523 : {
524 0 : GUIUtil::setClipboard(i.data(TransactionTableModel::FormattedAmountRole).toString());
525 0 : return true;
526 : }
527 : }
528 : }
529 0 : return QWidget::eventFilter(obj, event);
530 : }
531 :
532 : // show/hide column Watch-only
533 0 : void TransactionView::updateWatchOnlyColumn(bool fHaveWatchOnly)
534 : {
535 0 : watchOnlyWidget->setVisible(fHaveWatchOnly);
536 0 : transactionView->setColumnHidden(TransactionTableModel::Watchonly, !fHaveWatchOnly);
537 0 : }
|