From 3248d37f29fe53053b84227c2af5b40b222d43f9 Mon Sep 17 00:00:00 2001 From: PinkDev Date: Tue, 2 May 2017 22:30:22 -0700 Subject: [PATCH] Pinkcoin 2.1 Update Pinkcoin 2.1 Update New Features: UI Upgrade (80%) Side-Staking (Accessible from UI and RPC) RPC Getnodes --- pinkcoin-qt.pro | 4 +- src/bitcoinrpc.cpp | 44 +- src/bitcoinrpc.h | 11 +- src/clientversion.h | 4 +- src/db.cpp | 1 + src/db.h | 3 + src/init.cpp | 49 + src/init.h | 1 + src/main.cpp | 9 +- src/net.cpp | 10 +- src/qt/addressbookpage.cpp | 123 ++- src/qt/addressbookpage.h | 3 +- src/qt/addresstablemodel.cpp | 181 +++- src/qt/addresstablemodel.h | 13 +- src/qt/bitcoin.cpp | 5 +- src/qt/bitcoin.qrc | 19 +- src/qt/bitcoingui.cpp | 382 ++++++- src/qt/bitcoingui.h | 32 +- src/qt/bitcoinunits.cpp | 10 +- src/qt/bitcoinunits.h | 4 +- src/qt/clabel.h | 35 + src/qt/editaddressdialog.cpp | 44 +- src/qt/editaddressdialog.h | 4 +- src/qt/forms/addressbookpage.ui | 272 ++--- src/qt/forms/editaddressdialog.ui | 31 +- src/qt/forms/messagepage.ui | 401 +++---- src/qt/forms/overviewpage.ui | 1568 ++++++++++++++------------- src/qt/forms/sendcoinsdialog.ui | 1525 +++++++++++++------------- src/qt/forms/sendmessagesdialog.ui | 7 +- src/qt/locale/bitcoin_nl.ts | 150 +-- src/qt/overviewpage.cpp | 30 +- src/qt/res/icons/address-book.png | Bin 1916 -> 6850 bytes src/qt/res/icons/address-book_s.png | Bin 0 -> 7259 bytes src/qt/res/icons/bitcoin.icns | Bin 0 -> 68186 bytes src/qt/res/icons/close.png | Bin 0 -> 438 bytes src/qt/res/icons/close_s.png | Bin 0 -> 429 bytes src/qt/res/icons/history.png | Bin 1432 -> 2376 bytes src/qt/res/icons/history_s.png | Bin 0 -> 2489 bytes src/qt/res/icons/max.png | Bin 0 -> 642 bytes src/qt/res/icons/message.png | Bin 0 -> 3206 bytes src/qt/res/icons/message_s.png | Bin 0 -> 3324 bytes src/qt/res/icons/min.png | Bin 0 -> 297 bytes src/qt/res/icons/min_s.png | Bin 0 -> 256 bytes src/qt/res/icons/overview.png | Bin 7455 -> 2528 bytes src/qt/res/icons/overview_s.png | Bin 0 -> 2635 bytes src/qt/res/icons/receive.png | Bin 1437 -> 2832 bytes src/qt/res/icons/receive_s.png | Bin 0 -> 2959 bytes src/qt/res/icons/send.png | Bin 1487 -> 3069 bytes src/qt/res/icons/send_s.png | Bin 0 -> 3259 bytes src/qt/res/icons/sidestake.png | Bin 0 -> 5381 bytes src/qt/res/icons/sidestake_s.png | Bin 0 -> 5733 bytes src/qt/transactionrecord.cpp | 2 +- src/qt/transactiontablemodel.cpp | 29 +- src/qt/walletmodel.cpp | 35 + src/qt/walletmodel.h | 2 + src/rpcnet.cpp | 22 + src/rpcwallet.cpp | 151 +++ src/stakedb.cpp | 339 ++++++ src/stakedb.h | 79 ++ src/wallet.cpp | 123 ++- src/wallet.h | 29 +- 61 files changed, 3712 insertions(+), 2074 deletions(-) create mode 100644 src/qt/clabel.h create mode 100644 src/qt/res/icons/address-book_s.png create mode 100644 src/qt/res/icons/bitcoin.icns create mode 100644 src/qt/res/icons/close.png create mode 100644 src/qt/res/icons/close_s.png create mode 100644 src/qt/res/icons/history_s.png create mode 100644 src/qt/res/icons/max.png create mode 100644 src/qt/res/icons/message.png create mode 100644 src/qt/res/icons/message_s.png create mode 100644 src/qt/res/icons/min.png create mode 100644 src/qt/res/icons/min_s.png create mode 100644 src/qt/res/icons/overview_s.png create mode 100644 src/qt/res/icons/receive_s.png create mode 100644 src/qt/res/icons/send_s.png create mode 100644 src/qt/res/icons/sidestake.png create mode 100644 src/qt/res/icons/sidestake_s.png create mode 100644 src/stakedb.cpp create mode 100644 src/stakedb.h diff --git a/pinkcoin-qt.pro b/pinkcoin-qt.pro index a498fed..3e2d533 100644 --- a/pinkcoin-qt.pro +++ b/pinkcoin-qt.pro @@ -193,7 +193,7 @@ contains(BITCOIN_NEED_QT_PLUGINS, 1) { INCLUDEPATH += src/leveldb/include src/leveldb/helpers LIBS += $$PWD/src/leveldb/libleveldb.a $$PWD/src/leveldb/libmemenv.a -SOURCES += src/txdb-leveldb.cpp +SOURCES += src/txdb-leveldb.cpp !win32 { # we use QMAKE_CXXFLAGS_RELEASE even without RELEASE=1 because we use RELEASE to indicate linking preferences not -O preferences genleveldb.commands = cd $$PWD/src/leveldb && CC=$$QMAKE_CC CXX=$$QMAKE_CXX $(MAKE) OPT=\"$$QMAKE_CXXFLAGS $$QMAKE_CXXFLAGS_RELEASE\" libleveldb.a libmemenv.a @@ -275,6 +275,7 @@ HEADERS += src/qt/bitcoingui.h \ src/db.h \ src/txdb.h \ src/walletdb.h \ + src/stakedb.h \ src/script.h \ src/stealth.h \ src/init.h \ @@ -357,6 +358,7 @@ SOURCES += src/qt/bitcoin.cpp src/qt/bitcoingui.cpp \ src/addrman.cpp \ src/db.cpp \ src/walletdb.cpp \ + src/stakedb.cpp \ src/qt/clientmodel.cpp \ src/qt/guiutil.cpp \ src/qt/transactionrecord.cpp \ diff --git a/src/bitcoinrpc.cpp b/src/bitcoinrpc.cpp index 3d13125..992c732 100644 --- a/src/bitcoinrpc.cpp +++ b/src/bitcoinrpc.cpp @@ -242,6 +242,7 @@ static const CRPCCommand vRPCCommands[] = { "getbestblockhash", &getbestblockhash, true, false }, { "getblockcount", &getblockcount, true, false }, { "getconnectioncount", &getconnectioncount, true, false }, + { "getnodes", &getnodes, true, false }, { "getpeerinfo", &getpeerinfo, true, false }, { "getdifficulty", &getdifficulty, true, false }, { "getinfo", &getinfo, true, false }, @@ -319,6 +320,11 @@ static const CRPCCommand vRPCCommands[] = { "scanforstealthtxns", &scanforstealthtxns, false, false}, { "getwalletinfo", &getwalletinfo, true, false}, + { "addstakeout", &addstakeout, false, false}, + { "delstakeout", &delstakeout, false, false}, + { "liststakeout", &liststakeout, false, false}, + { "getstakeoutinfo", &getstakeoutinfo, false, false}, + { "smsgenable", &smsgenable, false, false}, { "smsgdisable", &smsgdisable, false, false}, { "smsglocalkeys", &smsglocalkeys, false, false}, @@ -332,11 +338,6 @@ static const CRPCCommand vRPCCommands[] = { "smsginbox", &smsginbox, false, false}, { "smsgoutbox", &smsgoutbox, false, false}, { "smsgbuckets", &smsgbuckets, false, false}, - - - - - }; CRPCTable::CRPCTable() @@ -1333,6 +1334,13 @@ int CommandLineRPC(int argc, char *argv[]) throw runtime_error("too few parameters"); string strMethod = argv[1]; +/* string strOut; + if (specialOutput(strMethod, *strOut)) + { + strPrint = strOut; + return nRet; + } +*/ // Parameters default to strings std::vector strParams(&argv[2], &argv[argc]); Array params = RPCConvertValues(strMethod, strParams); @@ -1378,7 +1386,33 @@ int CommandLineRPC(int argc, char *argv[]) } return nRet; } +/* +void specialOutput(std::string strMethod, std::string *strOut) +{ + bool ret = false; + + if (strMethod = "getnodes") + { + if (fHelp || params.size() != 0) + throw runtime_error( + "getnodes\n" + "Returns each connected network node as addnodes in conf friendly format."); + + vector vstats; + CopyNodeStats(vstats); + Value ret = NULL; + string pNode = ""; + + BOOST_FOREACH(const CNodeStats& stats, vstats) { + pNode += "addnode=" + stats.addrName + crlf; + } + ret.push_back(pNode); + return ret; + } + +} +*/ diff --git a/src/bitcoinrpc.h b/src/bitcoinrpc.h index c26679b..2f451d2 100644 --- a/src/bitcoinrpc.h +++ b/src/bitcoinrpc.h @@ -15,6 +15,7 @@ class CBlockIndex; #include "json/json_spirit_reader_template.h" #include "json/json_spirit_writer_template.h" #include "json/json_spirit_utils.h" +#include "wallet.h" #include "util.h" #include "checkpoints.h" @@ -70,6 +71,7 @@ json_spirit::Object JSONRPCError(int code, const std::string& message); void ThreadRPCServer(void* parg); int CommandLineRPC(int argc, char *argv[]); +//bool specialOutput(std::string strMethod, std::string *strOut); /** Convert parameter values for RPC call from strings to command-specific JSON objects. */ json_spirit::Array RPCConvertValues(const std::string &strMethod, const std::vector &strParams); @@ -97,6 +99,7 @@ class CRPCCommand rpcfn_type actor; bool okSafeMode; bool unlocked; + bool fGetNodes; }; /** @@ -144,8 +147,11 @@ extern uint256 ParseHashO(const json_spirit::Object& o, std::string strKey); extern std::vector ParseHexV(const json_spirit::Value& v, std::string strName); extern std::vector ParseHexO(const json_spirit::Object& o, std::string strKey); +//extern std::string getnodes(const json_spirit::Array& params, bool fHelp); + extern json_spirit::Value getconnectioncount(const json_spirit::Array& params, bool fHelp); // in rpcnet.cpp extern json_spirit::Value getpeerinfo(const json_spirit::Array& params, bool fHelp); +extern json_spirit::Value getnodes(const json_spirit::Array& params, bool fHelp); extern json_spirit::Value dumpwallet(const json_spirit::Array& params, bool fHelp); extern json_spirit::Value importwallet(const json_spirit::Array& params, bool fHelp); extern json_spirit::Value dumpprivkey(const json_spirit::Array& params, bool fHelp); // in rpcdump.cpp @@ -229,7 +235,10 @@ extern json_spirit::Value clearwallettransactions(const json_spirit::Array& para extern json_spirit::Value scanforalltxns(const json_spirit::Array& params, bool fHelp); extern json_spirit::Value scanforstealthtxns(const json_spirit::Array& params, bool fHelp); - +extern json_spirit::Value addstakeout(const json_spirit::Array& params, bool fHelp); +extern json_spirit::Value delstakeout(const json_spirit::Array& params, bool fHelp); +extern json_spirit::Value liststakeout(const json_spirit::Array& params, bool fHelp); +extern json_spirit::Value getstakeoutinfo(const json_spirit::Array& params, bool fHelp); extern json_spirit::Value smsgenable(const json_spirit::Array& params, bool fHelp); extern json_spirit::Value smsgdisable(const json_spirit::Array& params, bool fHelp); diff --git a/src/clientversion.h b/src/clientversion.h index 7230ed7..1a1ef8b 100644 --- a/src/clientversion.h +++ b/src/clientversion.h @@ -7,9 +7,9 @@ // These need to be macros, as version.cpp's and bitcoin-qt.rc's voodoo requires it #define CLIENT_VERSION_MAJOR 2 -#define CLIENT_VERSION_MINOR 0 +#define CLIENT_VERSION_MINOR 1 #define CLIENT_VERSION_REVISION 0 -#define CLIENT_VERSION_BUILD 5 +#define CLIENT_VERSION_BUILD 0 // Converts the parameter X to a string after macro replacement on X has been performed. // Don't merge these into one macro! diff --git a/src/db.cpp b/src/db.cpp index f288c82..7215a0f 100644 --- a/src/db.cpp +++ b/src/db.cpp @@ -20,6 +20,7 @@ using namespace boost; unsigned int nWalletDBUpdated; +unsigned int nStakeDBUpdated; diff --git a/src/db.h b/src/db.h index 9a8af31..564bec5 100644 --- a/src/db.h +++ b/src/db.h @@ -25,9 +25,12 @@ class CWallet; class CWalletTx; extern unsigned int nWalletDBUpdated; +extern unsigned int nStakeDBUpdated; void ThreadFlushWalletDB(void* parg); +void ThreadFlushStakeDB(void* parg); bool BackupWallet(const CWallet& wallet, const std::string& strDest); +bool BackupStakeDB(const CWallet& stakeDB, const std::string& strDest); class CDBEnv diff --git a/src/init.cpp b/src/init.cpp index 68129c7..60a906c 100644 --- a/src/init.cpp +++ b/src/init.cpp @@ -4,6 +4,7 @@ // file COPYING or http://www.opensource.org/licenses/mit-license.php. #include "txdb.h" #include "walletdb.h" +#include "stakedb.h" #include "bitcoinrpc.h" #include "net.h" #include "init.h" @@ -30,6 +31,7 @@ using namespace std; using namespace boost; CWallet* pwalletMain; +CWallet* pstakeDB; CClientUIInterface uiInterface; bool fConfChange; unsigned int nNodeLifespan; @@ -93,7 +95,9 @@ void Shutdown(void* parg) bitdb.Flush(true); boost::filesystem::remove(GetPidFile()); UnregisterWallet(pwalletMain); + UnregisterWallet(pstakeDB); delete pwalletMain; + delete pstakeDB; NewThread(ExitTimeout, NULL); MilliSleep(50); printf("Pinkcoin exited\n\n"); @@ -528,11 +532,16 @@ bool AppInit2(boost::thread_group& threadGroup) std::string strDataDir = GetDataDir().string(); std::string strWalletFileName = GetArg("-wallet", "wallet.dat"); + std::string strStakeDBFileName = GetArg("-stakedb", "stake.dat"); // strWalletFileName must be a plain filename without a directory if (strWalletFileName != boost::filesystem::basename(strWalletFileName) + boost::filesystem::extension(strWalletFileName)) return InitError(strprintf(_("Wallet %s resides outside data directory %s."), strWalletFileName.c_str(), strDataDir.c_str())); + // strStakeDBFileName must be a plain filename without a directory + if (strStakeDBFileName != boost::filesystem::basename(strStakeDBFileName) + boost::filesystem::extension(strStakeDBFileName)) + return InitError(strprintf(_("Wallet %s resides outside data directory %s."), strStakeDBFileName.c_str(), strDataDir.c_str())); + // Make sure only a single Bitcoin process is using the data directory. boost::filesystem::path pathLockFile = GetDataDir() / ".lock"; FILE* file = fopen(pathLockFile.string().c_str(), "a"); // empty lock file; created if it doesn't exist. @@ -614,6 +623,19 @@ bool AppInit2(boost::thread_group& threadGroup) return InitError(_("wallet.dat corrupt, salvage failed")); } + if (filesystem::exists(GetDataDir() / strStakeDBFileName)) + { + CDBEnv::VerifyResult r = bitdb.Verify(strStakeDBFileName, CStakeDB::Recover); + if (r == CDBEnv::RECOVER_OK) + { + string msg = strprintf(_("Warning: stake.dat corrupt, data salvaged!" + " Original stake.dat saved as stake.{timestamp}.bak in %s;"), strDataDir.c_str()); + uiInterface.ThreadSafeMessageBox(msg, _("Pinkcoin"), CClientUIInterface::OK | CClientUIInterface::ICON_EXCLAMATION | CClientUIInterface::MODAL); + } + if (r == CDBEnv::RECOVER_FAIL) + return InitError(_("wallet.dat corrupt, salvage failed")); + } + // ********************************************************* Step 6: network initialization int nSocksVersion = GetArg("-socks", 5); @@ -795,6 +817,7 @@ bool AppInit2(boost::thread_group& threadGroup) printf("Loading wallet...\n"); nStart = GetTimeMillis(); bool fFirstRun = true; + bool fFirstStakeOut = true; pwalletMain = new CWallet(strWalletFileName); DBErrors nLoadWalletRet = pwalletMain->LoadWallet(fFirstRun); if (nLoadWalletRet != DB_LOAD_OK) @@ -819,6 +842,31 @@ bool AppInit2(boost::thread_group& threadGroup) strErrors << _("Error loading wallet.dat") << "\n"; } + pstakeDB = new CWallet(strStakeDBFileName); + + SDBErrors nLoadStakeDBRet = pstakeDB->LoadStakeDB(fFirstStakeOut); + if (nLoadStakeDBRet != SDB_LOAD_OK) + { + if (nLoadStakeDBRet == SDB_CORRUPT) + strErrors << _("Error loading stake.dat: StakeDB corrupted") << "\n"; + else if (nLoadStakeDBRet == SDB_NONCRITICAL_ERROR) + { + string msg(_("Warning: error reading stake.dat! Side-stake entries might be missing or incorrect.")); + uiInterface.ThreadSafeMessageBox(msg, _("Pinkcoin"), CClientUIInterface::OK | CClientUIInterface::ICON_EXCLAMATION | CClientUIInterface::MODAL); + } + else if (nLoadStakeDBRet == SDB_TOO_NEW) + strErrors << _("Error loading stake.dat: StakeDB requires newer version of Pinkcoin") << "\n"; + else if (nLoadStakeDBRet == SDB_NEED_REWRITE) + { + strErrors << _("StakeDB needed to be rewritten: restart Pinkcoin to complete") << "\n"; + printf("%s", strErrors.str().c_str()); + return InitError(strErrors.str()); + } + else + strErrors << _("Error loading stake.dat") << "\n"; + } + + if (GetBoolArg("-upgradewallet", fFirstRun)) { int nMaxVersion = GetArg("-upgradewallet", 0); @@ -852,6 +900,7 @@ bool AppInit2(boost::thread_group& threadGroup) printf(" wallet %15dms\n", GetTimeMillis() - nStart); RegisterWallet(pwalletMain); + RegisterWallet(pstakeDB); CBlockIndex *pindexRescan = pindexBest; if (GetBoolArg("-rescan")) diff --git a/src/init.h b/src/init.h index 93bd3ac..8ff55b2 100644 --- a/src/init.h +++ b/src/init.h @@ -12,6 +12,7 @@ namespace boost { } // namespace boost extern CWallet* pwalletMain; +extern CWallet* pstakeDB; void StartShutdown(); void Shutdown(void* parg); bool AppInit2(boost::thread_group& threadGroup); diff --git a/src/main.cpp b/src/main.cpp index 8e7594c..b2b1654 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -82,7 +82,7 @@ const string strMessageMagic = "Pinkcoin Signed Message:\n"; int64_t nTransactionFee = MIN_TX_FEE; int64_t nReserveBalance = 0; int64_t nMinimumInputValue = 0; -int64_t nMinimumStakeValue = 1; // Don't stake old 0 reward blocks. +int64_t nMinimumStakeValue = 0; // Don't stake old 0 reward blocks. extern enum Checkpoints::CPMode CheckpointsMode; @@ -494,6 +494,8 @@ bool CTransaction::CheckTransaction() const if (::GetSerializeSize(*this, SER_NETWORK, PROTOCOL_VERSION) > MAX_BLOCK_SIZE) return DoS(100, error("CTransaction::CheckTransaction() : size limits failed")); + + // Check for negative or overflow output values int64_t nValueOut = 0; for (unsigned int i = 0; i < vout.size(); i++) @@ -1001,10 +1003,10 @@ int64_t GetProofOfStakeReward(int64_t nCoinAge, int64_t nFees, int nHeight, unsi if (IsFlashStakeReward(nTime)) { nSubsidy = 150 * COIN / (1 + (nHeight / nHalvingPoint / YEARLY_BLOCKCOUNT)); - printf("/n/nIsFlashStake/n/n"); + printf("\n\nIsFlashStake\n\n"); } else { nSubsidy = 100 * COIN / (1 + (nHeight / nHalvingPoint / YEARLY_BLOCKCOUNT)); - printf("/n/nIs NOT FlashStake/n/n"); + printf("\n\nIs NOT FlashStake\n\n"); } } @@ -1409,6 +1411,7 @@ bool CTransaction::FetchInputs(CTxDB& txdb, const map& mapTes const CTxOut& CTransaction::GetOutputFor(const CTxIn& input, const MapPrevTx& inputs) const { + MapPrevTx::const_iterator mi = inputs.find(input.prevout.hash); if (mi == inputs.end()) throw std::runtime_error("CTransaction::GetOutputFor() : prevout.hash not found"); diff --git a/src/net.cpp b/src/net.cpp index 19c9e0a..55b9de3 100644 --- a/src/net.cpp +++ b/src/net.cpp @@ -23,7 +23,7 @@ using namespace std; using namespace boost; -static const int MAX_OUTBOUND_CONNECTIONS = 16; +static const int MAX_OUTBOUND_CONNECTIONS = 64; void ThreadMessageHandler2(void* parg); void ThreadSocketHandler2(void* parg); @@ -1269,8 +1269,12 @@ void MapPort() // The second name should resolve to a list of seed addresses. static const char *strDNSSeed[][2] = { - {"pinkarmy.ml", "pinkarmy.ml"}, - + {"primary", "pinkarmy.ml"}, + {"frankfurt", "frankfurt.pinkarmy.ml"}, + {"paris", "paris.pinkarmy.ml"}, + {"singapore", "singapore.pinkarmy.ml"}, + {"sydney", "sydney.pinkarmy.ml"}, + {"tokyo", "tokyo.pinkarmy.ml"}, }; void ThreadDNSAddressSeed(void* parg) diff --git a/src/qt/addressbookpage.cpp b/src/qt/addressbookpage.cpp index 0618513..fb60e12 100644 --- a/src/qt/addressbookpage.cpp +++ b/src/qt/addressbookpage.cpp @@ -61,6 +61,11 @@ AddressBookPage::AddressBookPage(Mode mode, Tabs tab, QWidget *parent) : ui->deleteButton->setVisible(false); ui->signMessage->setVisible(true); break; + case StakingTab: + ui->labelExplanation->setVisible(false); + ui->signMessage->setVisible(false); + ui->verifyMessage->setVisible(false); + ui->deleteButton->setVisible(true); } // Context menu actions @@ -133,21 +138,55 @@ void AddressBookPage::setModel(AddressTableModel *model) proxyModel->setFilterRole(AddressTableModel::TypeRole); proxyModel->setFilterFixedString(AddressTableModel::Send); break; + case StakingTab: + proxyModel->setFilterRole(AddressTableModel::TypeRole); + proxyModel->setFilterFixedString(AddressTableModel::Stake); + break; } ui->tableView->setModel(proxyModel); ui->tableView->sortByColumn(0, Qt::AscendingOrder); - bool sTab = true; - if (tab) - sTab = false; + bool recTab = false; + bool stTab = false; + //if (tab == 1) + recTab = (tab == ReceivingTab); + stTab = (tab == StakingTab); // Set column widths - ui->tableView->horizontalHeader()->resizeSection( - AddressTableModel::PMKey, 320); - ui->tableView->horizontalHeader()->setResizeMode( - AddressTableModel::PMKey, QHeaderView::Fixed); - ui->tableView->setColumnHidden( - AddressTableModel::PMKey, sTab); + + if (recTab) + { + ui->tableView->horizontalHeader()->resizeSection( + AddressTableModel::PMKey, 320); + ui->tableView->horizontalHeader()->setResizeMode( + AddressTableModel::PMKey, QHeaderView::Fixed); + ui->tableView->setColumnHidden( + AddressTableModel::PMKey, false); + + } else { + ui->tableView->horizontalHeader()->resizeSection( + AddressTableModel::PMKey, 0); + ui->tableView->horizontalHeader()->setResizeMode( + AddressTableModel::PMKey, QHeaderView::Fixed); + ui->tableView->setColumnHidden( + AddressTableModel::PMKey, true); + } + if (stTab) + { + ui->tableView->horizontalHeader()->resizeSection( + AddressTableModel::Percent, 50); + ui->tableView->horizontalHeader()->setResizeMode( + AddressTableModel::Percent, QHeaderView::Fixed); + ui->tableView->setColumnHidden( + AddressTableModel::Percent, false); + } else { + ui->tableView->horizontalHeader()->resizeSection( + AddressTableModel::Percent, 0); + ui->tableView->horizontalHeader()->setResizeMode( + AddressTableModel::Percent, QHeaderView::Fixed); + ui->tableView->setColumnHidden( + AddressTableModel::Percent, true); + } ui->tableView->horizontalHeader()->resizeSection( AddressTableModel::Address, 320); ui->tableView->horizontalHeader()->setResizeMode( @@ -220,11 +259,22 @@ void AddressBookPage::onEditAction() QModelIndexList indexes = ui->tableView->selectionModel()->selectedRows(); if(indexes.isEmpty()) return; + EditAddressDialog::Mode useMode; + + switch (tab) + { + case SendingTab: + useMode = EditAddressDialog::EditSendingAddress; + break; + case ReceivingTab: + useMode = EditAddressDialog::EditReceivingAddress; + break; + case StakingTab: + useMode = EditAddressDialog::EditStakingAddress; + break; + } - EditAddressDialog dlg( - tab == SendingTab ? - EditAddressDialog::EditSendingAddress : - EditAddressDialog::EditReceivingAddress); + EditAddressDialog dlg(useMode, this); dlg.setModel(model); QModelIndex origIndex = proxyModel->mapToSource(indexes.at(0)); dlg.loadRow(origIndex.row()); @@ -265,14 +315,37 @@ void AddressBookPage::on_newAddressButton_clicked() { if(!model) return; - EditAddressDialog dlg( - tab == SendingTab ? - EditAddressDialog::NewSendingAddress : - EditAddressDialog::NewReceivingAddress, this); - dlg.setModel(model); - if(dlg.exec()) + EditAddressDialog::Mode useMode; + + bool okToContinue = true; + + switch (tab) + { + case SendingTab: + useMode = EditAddressDialog::NewSendingAddress; + break; + case ReceivingTab: + useMode = EditAddressDialog::NewReceivingAddress; + break; + case StakingTab: + int okToSave = QMessageBox::warning(this, "Warning", "Please Note: Most services such as Exchanges do not currently support receiving\n" + "side-stakes. If you set your stakes to go to an exchange or other service, they\n" + "will not credit to your account. Please do not set your stakes to go to a service\n" + "unless you're sure they support the feature.", QMessageBox::Ok, QMessageBox::Cancel); + if (okToSave != QMessageBox::Ok) + okToContinue = false; + useMode = EditAddressDialog::NewStakingAddress; + break; + } + + if (okToContinue) { - newAddressToSelect = dlg.getAddress(); + EditAddressDialog dlg(useMode, this); + dlg.setModel(model); + if(dlg.exec()) + { + newAddressToSelect = dlg.getAddress(); + } } } @@ -319,6 +392,15 @@ void AddressBookPage::selectionChanged() ui->verifyMessage->setEnabled(false); ui->verifyMessage->setVisible(false); break; + case StakingTab: + ui->deleteButton->setEnabled(true); + ui->deleteButton->setVisible(true); + deleteAction->setEnabled(true); + ui->signMessage->setEnabled(false); + ui->signMessage->setVisible(false); + ui->verifyMessage->setEnabled(false); + ui->verifyMessage->setVisible(false); + break; } ui->copyToClipboard->setEnabled(true); ui->showQRCode->setEnabled(true); @@ -377,6 +459,7 @@ void AddressBookPage::exportClicked() writer.addColumn("Label", AddressTableModel::Label, Qt::EditRole); writer.addColumn("Address", AddressTableModel::Address, Qt::EditRole); writer.addColumn("PM KEY", AddressTableModel::PMKey, Qt::EditRole); + writer.addColumn("Percent", AddressTableModel::Percent, Qt::EditRole); if(!writer.write()) { diff --git a/src/qt/addressbookpage.h b/src/qt/addressbookpage.h index 448234f..feef337 100644 --- a/src/qt/addressbookpage.h +++ b/src/qt/addressbookpage.h @@ -26,7 +26,8 @@ class AddressBookPage : public QDialog public: enum Tabs { SendingTab = 0, - ReceivingTab = 1 + ReceivingTab = 1, + StakingTab = 2 }; enum Mode { diff --git a/src/qt/addresstablemodel.cpp b/src/qt/addresstablemodel.cpp index c140697..84ddf3e 100644 --- a/src/qt/addresstablemodel.cpp +++ b/src/qt/addresstablemodel.cpp @@ -12,12 +12,14 @@ const QString AddressTableModel::Send = "S"; const QString AddressTableModel::Receive = "R"; +const QString AddressTableModel::Stake = "X"; struct AddressTableEntry { enum Type { Sending, - Receiving + Receiving, + Staking }; Type type; @@ -25,10 +27,11 @@ struct AddressTableEntry QString address; QString pmkey; bool stealth; + QString percent; AddressTableEntry() {} - AddressTableEntry(Type type, const QString &label, const QString &address, const QString &pmkey, const bool &stealth = false): - type(type), label(label), address(address), pmkey(pmkey), stealth(stealth) {} + AddressTableEntry(Type type, const QString &label, const QString &address, const QString &pmkey, const bool &stealth = false, const QString &nPercent = ""): + type(type), label(label), address(address), pmkey(pmkey), stealth(stealth), percent(nPercent) {} }; struct AddressTableEntryLessThan @@ -72,6 +75,7 @@ class AddressTablePriv std::string a; std::string PMKey = ""; a = address.ToString(); + std::string nPercent = ""; if (fMine) { @@ -82,16 +86,26 @@ class AddressTablePriv printf("Error getting PM Key %i\n", i); } - cachedAddressTable.append(AddressTableEntry(fMine ? AddressTableEntry::Receiving : AddressTableEntry::Sending, + AddressTableEntry::Type tThis = fMine ? AddressTableEntry::Receiving : AddressTableEntry::Sending; + + if (wallet->mapAddressPercent.find(item.first) != wallet->mapAddressPercent.end()) + { + nPercent = wallet->mapAddressPercent[item.first]; + tThis = AddressTableEntry::Staking; + } + + cachedAddressTable.append(AddressTableEntry(tThis, QString::fromStdString(strName), QString::fromStdString(address.ToString()), - QString::fromStdString(PMKey))); + QString::fromStdString(PMKey), false, + QString::fromStdString(nPercent))); } std::set::iterator it; for (it = wallet->stealthAddresses.begin(); it != wallet->stealthAddresses.end(); ++it) { bool fMine = !(it->scan_secret.size() < 1); + cachedAddressTable.append(AddressTableEntry(fMine ? AddressTableEntry::Receiving : AddressTableEntry::Sending, QString::fromStdString(it->label), QString::fromStdString(it->Encoded()), @@ -103,7 +117,7 @@ class AddressTablePriv qSort(cachedAddressTable.begin(), cachedAddressTable.end(), AddressTableEntryLessThan()); } - void updateEntry(const QString &address, const QString &label, bool isMine, int status) + void updateEntry(const QString &address, const QString &label, bool isMine, int status, const QString &percent) { // Find address / label in model QList::iterator lower = qLowerBound( @@ -113,7 +127,8 @@ class AddressTablePriv int lowerIndex = (lower - cachedAddressTable.begin()); int upperIndex = (upper - cachedAddressTable.begin()); bool inModel = (lower != upper); - AddressTableEntry::Type newEntryType = isMine ? AddressTableEntry::Receiving : AddressTableEntry::Sending; + bool isStake = (percent != ""); + AddressTableEntry::Type newEntryType = isStake ? AddressTableEntry::Staking : (isMine ? AddressTableEntry::Receiving : AddressTableEntry::Sending); switch(status) { @@ -128,8 +143,8 @@ class AddressTablePriv parent->beginInsertRows(QModelIndex(), lowerIndex, lowerIndex); std::string pmkey = ""; - std::string a; - a = address.toStdString(); + std::string nPercent = percent.toStdString(); + std::string a = address.toStdString(); int i; if (isMine) { @@ -138,7 +153,7 @@ class AddressTablePriv printf("Can't get PM Key for some reason\n"); } - cachedAddressTable.insert(lowerIndex, AddressTableEntry(newEntryType, label, address, QString::fromStdString(pmkey))); + cachedAddressTable.insert(lowerIndex, AddressTableEntry(newEntryType, label, address, QString::fromStdString(pmkey), false, QString::fromStdString(nPercent))); parent->endInsertRows(); break; } @@ -150,6 +165,8 @@ class AddressTablePriv } lower->type = newEntryType; lower->label = label; + if (percent != "") + lower->percent = percent; parent->emitDataChanged(lowerIndex); break; case CT_DELETED: @@ -186,7 +203,7 @@ class AddressTablePriv AddressTableModel::AddressTableModel(CWallet *wallet, WalletModel *parent) : QAbstractTableModel(parent),walletModel(parent),wallet(wallet),priv(0) { - columns << tr("Label") << tr("Address") << tr("PM Key"); + columns << tr("Label") << tr("Address") << tr("PM Key") << tr("Percent"); priv = new AddressTablePriv(wallet, this); priv->refreshAddressTable(); } @@ -237,6 +254,8 @@ QVariant AddressTableModel::data(const QModelIndex &index, int role) const return rec->address; case PMKey: return rec->pmkey; + case Percent: + return rec->percent; } } else if (role == Qt::FontRole) @@ -256,6 +275,8 @@ QVariant AddressTableModel::data(const QModelIndex &index, int role) const return Send; case AddressTableEntry::Receiving: return Receive; + case AddressTableEntry::Staking: + return Stake; default: break; } } @@ -288,11 +309,36 @@ bool AddressTableModel::setData(const QModelIndex &index, const QVariant &value, { strValue = value.toString().toStdString(); wallet->UpdateStealthAddress(strTemp, strValue, false); + } else if (rec->type == AddressTableEntry::Staking) + { + wallet->SetAddressBookStake(CBitcoinAddress(strTemp).Get(), value.toString().toStdString(), rec->percent.toStdString()); } else { wallet->SetAddressBookName(CBitcoinAddress(strTemp).Get(), value.toString().toStdString()); } + break; + case Percent: + if(rec->percent == value.toString()) + { + editStatus = NO_CHANGES; + return false; + } + + strTemp = rec->address.toStdString(); + if (IsStealthAddress(strTemp)) + { + editStatus = NO_CHANGES; // stealth addresses are not supported with side-staking + return false; + } + + if (!checkStakePercent(rec->address.toStdString(), value.toString().toStdString())) + { + editStatus = INVALID_PERCENTAGE; + return false; + } + + wallet->SetAddressBookStake(CBitcoinAddress(strTemp).Get(), rec->label.toStdString(), value.toString().toStdString()); break; case Address: @@ -333,6 +379,10 @@ bool AddressTableModel::setData(const QModelIndex &index, const QVariant &value, wallet->SetAddressBookName(CBitcoinAddress(value.toString().toStdString()).Get(), rec->label.toStdString()); } } + else if(rec->type == AddressTableEntry::Staking) + { + wallet->SetAddressBookStake(CBitcoinAddress(value.toString().toStdString()).Get(), rec->label.toStdString(), rec->percent.toStdString()); + } break; } return true; @@ -362,7 +412,8 @@ Qt::ItemFlags AddressTableModel::flags(const QModelIndex &index) const // Can edit address and label for sending addresses, // and only label for receiving addresses. if(rec->type == AddressTableEntry::Sending || - (rec->type == AddressTableEntry::Receiving && index.column()==Label)) + (rec->type == AddressTableEntry::Receiving && index.column()==Label) || + rec->type == AddressTableEntry::Staking ) { retval |= Qt::ItemIsEditable; } @@ -383,16 +434,19 @@ QModelIndex AddressTableModel::index(int row, int column, const QModelIndex &par } } -void AddressTableModel::updateEntry(const QString &address, const QString &label, bool isMine, int status) +void AddressTableModel::updateEntry(const QString &address, const QString &label, bool isMine, int status, const QString &percent) { // Update address book model from Bitcoin core - priv->updateEntry(address, label, isMine, status); + priv->updateEntry(address, label, isMine, status, percent); } -QString AddressTableModel::addRow(const QString &type, const QString &label, const QString &address, int addressType) +QString AddressTableModel::addRow(const QString &type, const QString &label, const QString &address, int addressType, const QString &percent) { std::string strLabel = label.toStdString(); std::string strAddress = address.toStdString(); + std::string nPercent = percent.toStdString(); + + editStatus = OK; @@ -420,7 +474,6 @@ QString AddressTableModel::addRow(const QString &type, const QString &label, con sxAddr.label = strLabel; wallet->AddStealthAddress(sxAddr); } - } else { if (!walletModel->validateAddress(address)) @@ -436,11 +489,34 @@ QString AddressTableModel::addRow(const QString &type, const QString &label, con editStatus = DUPLICATE_ADDRESS; return QString(); }; - wallet->SetAddressBookName(CBitcoinAddress(strAddress).Get(), strLabel); } } } + else if(type == Stake) + { + if (!walletModel->validateAddress(address)) + { + editStatus = INVALID_ADDRESS; + return QString(); + }; + if (!checkStakePercent(address.toStdString(), nPercent)) + { + editStatus = INVALID_PERCENTAGE; + return QString(); + } + // Check for duplicate addresses + { + LOCK(wallet->cs_wallet); + if (wallet->mapAddressBook.count(CBitcoinAddress(strAddress).Get())) + { + editStatus = DUPLICATE_ADDRESS; + return QString(); + }; + + wallet->SetAddressBookStake(CBitcoinAddress(strAddress).Get(), strLabel, nPercent); + } + } else if(type == Receive) { // Generate a new address to associate with given label @@ -498,9 +574,12 @@ bool AddressTableModel::removeRows(int row, int count, const QModelIndex &parent // Also refuse to remove receiving addresses. return false; } - { + { LOCK(wallet->cs_wallet); - wallet->DelAddressBookName(CBitcoinAddress(rec->address.toStdString()).Get()); + if (rec->type == AddressTableEntry::Staking) + wallet->DelAddressBookStake(CBitcoinAddress(rec->address.toStdString()).Get()); + else + wallet->DelAddressBookName(CBitcoinAddress(rec->address.toStdString()).Get()); } return true; } @@ -557,3 +636,67 @@ void AddressTableModel::emitDataChanged(int idx) { emit dataChanged(index(idx, 0, QModelIndex()), index(idx, columns.length()-1, QModelIndex())); } + +bool AddressTableModel::checkStakePercent(std::string address, std::string percent) +{ + std::string sPercent = percent; + + if (sPercent == "") + sPercent = "0"; + + std::string sStack = ""; + for (unsigned int i = 0; i < sPercent.length(); i++) sStack += isdigit(sPercent[i]) ? sPercent[i] : (char)NULL; + + if (sPercent != sStack) + { + printf("\nPlease only use whole numbers between 0 and 100 and no special characters for Percentage\n"); + return false; + } + + int nPercent = std::stoi(sPercent); + + + if (nPercent < 0 || nPercent > 100) + { + printf("\nPlease use a percentage between 0 and 100"); + return false; + } + + CBitcoinAddress a(address); + if (!a.IsValid()) + { + printf("\nInvalid Bitcoin Address."); + return false; + } + + int percentAvailable = 100; + + BOOST_FOREACH(CWallet::mapAddress mapPercent, wallet->mapAddressPercent) + { + std::string percent = mapPercent.second; + if (percent == "") + percent = "0"; + + percentAvailable -= std::stoi(percent); + } + + int updatingPercent = 0; + if (wallet->mapAddressPercent.find(a.Get()) != wallet->mapAddressPercent.end()) + { + std::string sUpdatingPercent = wallet->mapAddressPercent[a.Get()]; + if (sUpdatingPercent == "") + sUpdatingPercent = "0"; + + updatingPercent = std::stoi(sUpdatingPercent); + } + + if (nPercent > (percentAvailable + updatingPercent)) + { + printf("\nStake Percentage would increase total Stakeout over 100%\n" + "Please Reduce Stakeout Percentage or Delete another Stakeout to make room.\n" + "Current Available Stakeout Percentage: %s", std::to_string(percentAvailable).c_str()); + return false; + } + + return true; +} diff --git a/src/qt/addresstablemodel.h b/src/qt/addresstablemodel.h index 9908522..1bc24bb 100644 --- a/src/qt/addresstablemodel.h +++ b/src/qt/addresstablemodel.h @@ -28,7 +28,8 @@ class AddressTableModel : public QAbstractTableModel Label = 0, /**< User specified label */ Address = 1, /**< Bitcoin address */ PMKey = 2, - Type = 3 /**< Address type */ + Percent = 3, /**< Stakeout percentage */ + Type = 4 /**< Address type */ }; enum RoleIndex { @@ -42,11 +43,13 @@ class AddressTableModel : public QAbstractTableModel INVALID_ADDRESS, /**< Unparseable address */ DUPLICATE_ADDRESS, /**< Address already in address book */ WALLET_UNLOCK_FAILURE, /**< Wallet could not be unlocked to create new receiving address */ - KEY_GENERATION_FAILURE /**< Generating a new public key for a receiving address failed */ + KEY_GENERATION_FAILURE, /**< Generating a new public key for a receiving address failed */ + INVALID_PERCENTAGE, }; static const QString Send; /**< Specifies send address */ static const QString Receive; /**< Specifies receive address */ + static const QString Stake; /**< Specifies stakeout address */ /** @name Methods overridden from QAbstractTableModel @{*/ @@ -63,12 +66,14 @@ class AddressTableModel : public QAbstractTableModel /* Add an address to the model. Returns the added address on success, and an empty string otherwise. */ - QString addRow(const QString &type, const QString &label, const QString &address, int addressType); + QString addRow(const QString &type, const QString &label, const QString &address, int addressType, const QString &percent = "0"); /* Look up label for address in address book, if not found return empty string. */ QString labelForAddress(const QString &address) const; + bool checkStakePercent(std::string address, std::string percent); + /* Look up row index of an address in the model. Return -1 if not found. */ @@ -92,7 +97,7 @@ class AddressTableModel : public QAbstractTableModel public slots: /* Update address list from core. */ - void updateEntry(const QString &address, const QString &label, bool isMine, int status); + void updateEntry(const QString &address, const QString &label, bool isMine, int status, const QString &percent = ""); void refreshAddresses(); friend class AddressTablePriv; diff --git a/src/qt/bitcoin.cpp b/src/qt/bitcoin.cpp index 0b7188c..28f691a 100644 --- a/src/qt/bitcoin.cpp +++ b/src/qt/bitcoin.cpp @@ -248,10 +248,11 @@ int main(int argc, char *argv[]) ClientModel clientModel(&optionsModel); WalletModel walletModel(pwalletMain, &optionsModel); + WalletModel stakeModel(pstakeDB, &optionsModel); MessageModel messageModel(pwalletMain, &walletModel); window.setClientModel(&clientModel); - window.setWalletModel(&walletModel); + window.setWalletModel(&walletModel, &stakeModel); window.setMessageModel(&messageModel); // If -min option passed, start window minimized. @@ -271,7 +272,7 @@ int main(int argc, char *argv[]) window.hide(); window.setClientModel(0); - window.setWalletModel(0); + window.setWalletModel(0, 0); window.setMessageModel(0); guiref = 0; } diff --git a/src/qt/bitcoin.qrc b/src/qt/bitcoin.qrc index add963f..28bdd45 100644 --- a/src/qt/bitcoin.qrc +++ b/src/qt/bitcoin.qrc @@ -5,8 +5,10 @@ res/icons/pinkcoin-16.png res/icons/pinkcoin-16.png res/icons/address-book.png + res/icons/address-book_s.png res/icons/quit.png res/icons/send.png + res/icons/send_s.png res/icons/connect0_16.png res/icons/connect1_16.png res/icons/connect2_16.png @@ -22,12 +24,17 @@ res/icons/clock5.png res/icons/configure.png res/icons/receive.png + res/icons/receive_s.png res/icons/editpaste.png res/icons/editcopy.png res/icons/add.png res/icons/edit.png + res/icons/message.png + res/icons/message_s.png res/icons/history.png + res/icons/history_s.png res/icons/overview.png + res/icons/overview_s.png res/icons/export.png res/icons/synced.png res/icons/remove.png @@ -44,11 +51,19 @@ res/icons/staking_off.png res/icons/staking_on.png res/icons/pinkcoin-128.png + res/icons/pinkcoin-32.png + res/icons/min.png + res/icons/min_s.png + res/icons/max.png + res/icons/close.png + res/icons/close_s.png + res/icons/sidestake.png + res/icons/sidestake_s.png res/images/about.png res/images/splash.png - res/images/wallet.png + res/images/wallet.png res/movies/update_spinner.mng @@ -94,7 +109,7 @@ locale/bitcoin_zh_CN.qm locale/bitcoin_zh_TW.qm - + res/fonts/Ubuntu-Medium.ttf res/fonts/Ubuntu-Bold.ttf diff --git a/src/qt/bitcoingui.cpp b/src/qt/bitcoingui.cpp index 828cabf..2eef62e 100644 --- a/src/qt/bitcoingui.cpp +++ b/src/qt/bitcoingui.cpp @@ -30,6 +30,8 @@ #include "rpcconsole.h" #include "wallet.h" +#include "clabel.h" + #ifdef Q_OS_MAC #include "macdockiconhandler.h" #endif @@ -38,6 +40,10 @@ #include #include #include +#include +#include +#include +#include #include #include #include @@ -68,6 +74,7 @@ #include #include #include +#include #include @@ -77,12 +84,45 @@ extern int64_t nLastCoinStakeSearchInterval; double GetPoSKernelPS(); ActiveLabel::ActiveLabel(const QString & text, QWidget * parent): - QLabel(parent){} + QLabel(parent){ + + setAttribute(Qt::WA_Hover); + +} + +/* void ActiveLabel::mouseReleaseEvent(QMouseEvent * event) { emit clicked(); } +*/ + +bool ActiveLabel::event(QEvent *e) +{ +// QHoverEvent me = static_cast(e); + if(e->type() == QEvent::HoverMove) + { + //double xpos = me->pos().x(); + //double ypos = me->pos().y(); + emit hovered(); + // qDebug() << Q_FUNC_INFO << QString("xpos %1, ypos %2").arg(xpos).arg(ypos); + return true; + } + else if(e->type() == QEvent::HoverLeave) + { + emit unhovered(); + return true; + } + else if(e->type() == QEvent::MouseButtonRelease) + { + emit clicked(); + return true; + } + + return QLabel::event(e); +} + BitcoinGUI::BitcoinGUI(QWidget *parent): @@ -100,21 +140,34 @@ BitcoinGUI::BitcoinGUI(QWidget *parent): nWeight(0) { setFixedSize(1050, 600); + + #ifdef Q_OS_WIN + setWindowFlags(Qt::FramelessWindowHint | Qt::WindowSystemMenuHint | Qt::WindowMinimizeButtonHint); + #else + setWindowFlags(Qt::FramelessWindowHint | Qt::WindowSystemMenuHint); + #endif + setWindowTitle(tr("Pinkcoin") + " - " + tr("Wallet")); QFontDatabase fontData; fontData.addApplicationFont(":/fonts/Ubuntu-Bold"); + + qApp->setStyleSheet(\ "QMainWindow \ { \ - width:850px;\ \ + padding-left: 0px;\ + padding-right: 0px;\ + padding-bottom: 0px;\ + padding-top: 0px;\ + border: 0px;\ \ } \ \ #frame { } \ - QToolBar QLabel { padding-top: 0px;padding-bottom: 0px;spacing: 10px;} \ - QToolBar QLabel:item { padding-top: 0px;padding-bottom: 0px;spacing: 10px;} \ + QToolBar QLabel { padding-top: 0px;padding-bottom: 0px;spacing: 0px; border:0px;} \ + QToolBar QLabel:item { padding-top: 0px;padding-bottom: 0px;spacing: 0px; border: 0px;} \ \ #spacer2 { background:rgb(26, 0, 13);border:none; } \ #spacer { background:rgb(152, 50, 101);border:none; } \ @@ -130,43 +183,47 @@ BitcoinGUI::BitcoinGUI(QWidget *parent): \ #toolbar \ { \ - border:1px; \ + border:0px; \ height:100%; \ - padding-top:20px; \ - padding-left: 20px; \ - padding-right: 20px;\ - background: rgb(152, 50, 101); \ + padding-top:0px; \ + padding-left: 0px; \ + padding-right: 0px;\ + background: rgb(255, 255, 255); \ text-align: left; \ - color: white; \ + color: black; \ min-width:200px; \ max-width:200px; \ } \ + \ QToolBar QToolButton \ { \ \ font-family:Ubuntu; \ font-size:16px; \ - padding-left:20px; \ - padding-top:5px; \ - padding-bottom:5px; \ - padding-right:20px;\ + border: 0px; \ + padding-left:0px; \ + padding-top:0px; \ + padding-bottom:0px; \ + padding-right:0px;\ width:200px; \ - color: rgb(255,255,255); \ + color: black; \ text-align: left; \ - background-color: rgb(152, 50, 101); \ + background-color: rgb(255, 255, 255); \ } \ - #OverviewButton:hover {background-color: rgb(255, 101, 183); border: none;} \ - #OverviewButton:checked {background-color: rgb(255, 80, 162); border: none;} \ - #SendButton:hover {background-color: rgb(255, 121, 183); border: none;} \ - #SendButton:checked {background-color: rgb(255, 80, 162); border: none;} \ - #ReceiveButton:hover {background-color:rgb(255, 101, 183); border: none;} \ - #ReceiveButton:checked {background-color: rgb(255, 80, 162); border: none;} \ - #HistoryButton:hover {background-color: rgb(255, 101, 183); border: none;} \ - #HistoryButton:checked {background-color: rgb(255, 80, 162); border: none;} \ - #AddressBookButton:hover {background-color: rgb(255, 101, 183); border: none;} \ - #AddressBookButton:checked {background-color: rgb(255, 80, 162); border: none;} \ - #MessageButton:hover {background-color: rgb(255, 101, 183); border: none;} \ - #MessageButton:checked {background-color: rgb(255, 80, 162); border: none;} \ + #OverviewButton:hover {background-color: rgb(255, 141, 183); border: none;} \ + #OverviewButton:checked {background-color: rgb(255, 121, 170); border: none;} \ + #SendButton:hover {background-color: rgb(255, 141, 183); border: none;} \ + #SendButton:checked {background-color: rgb(255, 121, 170); border: none;} \ + #ReceiveButton:hover {background-color:rgb(255, 141, 183); border: none;} \ + #ReceiveButton:checked {background-color: rgb(255, 121, 170); border: none;} \ + #HistoryButton:hover {background-color: rgb(255, 141, 183); border: none;} \ + #HistoryButton:checked {background-color: rgb(255, 121, 170); border: none;} \ + #AddressBookButton:hover {background-color: rgb(255, 141, 183); border: none;} \ + #AddressBookButton:checked {background-color: rgb(255, 121, 170); border: none;} \ + #SideStakeButton:hover {background-color: rgb(255, 141, 183); border: none;} \ + #SideStakeButton:checked {background-color: rgb(255, 121, 170); border: none;} \ + #MessageButton:hover {background-color: rgb(255, 141, 183); border: none;} \ + #MessageButton:checked {background-color: rgb(255, 121, 170); border: none;} \ #labelMiningIcon \ { \ padding-left:5px; \ @@ -222,32 +279,57 @@ BitcoinGUI::BitcoinGUI(QWidget *parent): createTrayIcon(); // Create tabs + overviewPage = new OverviewPage(); transactionsPage = new QWidget(this); QVBoxLayout *vbox = new QVBoxLayout(); + QHBoxLayout *hbox = new QHBoxLayout(); + transactionView = new TransactionView(this); + vbox->addWidget(transactionView); - transactionsPage->setLayout(vbox); + + hbox->setContentsMargins(20, 5 ,0, 0); + hbox->addLayout(vbox); + + transactionsPage->setLayout(hbox); addressBookPage = new AddressBookPage(AddressBookPage::ForEditing, AddressBookPage::SendingTab); receiveCoinsPage = new AddressBookPage(AddressBookPage::ForEditing, AddressBookPage::ReceivingTab); + stakeCoinsPage = new AddressBookPage(AddressBookPage::ForEditing, AddressBookPage::StakingTab); + sendCoinsPage = new SendCoinsDialog(this); messagePage = new MessagePage(this); signVerifyMessageDialog = new SignVerifyMessageDialog(this); centralWidget = new QStackedWidget(this); + centralWidget->setObjectName("StackedWidget"); + centralWidget->setStyleSheet("#StackedWidget{background-color:qlineargradient(spread:pad, x1:0, y1:0, x2:.04, y2:0, stop:0 rgba(255, 121, 170, 255), stop:1 rgba(255, 245, 250, 255));}"); centralWidget->addWidget(overviewPage); centralWidget->addWidget(transactionsPage); + centralWidget->addWidget(stakeCoinsPage); centralWidget->addWidget(addressBookPage); centralWidget->addWidget(receiveCoinsPage); centralWidget->addWidget(sendCoinsPage); centralWidget->addWidget(messagePage); + + setCentralWidget(centralWidget); + QPainterPath painterPath; + painterPath.addRoundedRect(0, 0, 1050, 600, 3, 3); + QPolygon maskPolygon = painterPath.toFillPolygon().toPolygon(); + + QRegion maskedRegion(maskPolygon, Qt::OddEvenFill); + + setMask(maskedRegion); + + //setMask(maskedRegion); + // Create status bar //statusBar(); @@ -382,52 +464,109 @@ void BitcoinGUI::createActions() { QActionGroup *tabGroup = new QActionGroup(this); - overviewAction = new QAction(QIcon(":/icons/overview"), tr("&Overview"), this); + QIcon *iOverView = new QIcon(); + + iOverView->addFile(":/icons/overview", QSize(), QIcon::Normal, QIcon::Off ); + iOverView->addFile(":/icons/overview_s", QSize(), QIcon::Active, QIcon::Off); + iOverView->addFile(":/icons/overview_s", QSize(), QIcon::Active, QIcon::On); + + QIcon *iSend = new QIcon(); + + iSend->addFile(":/icons/send", QSize(), QIcon::Normal, QIcon::Off ); + iSend->addFile(":/icons/send_s", QSize(), QIcon::Active, QIcon::Off); + iSend->addFile(":/icons/send_s", QSize(), QIcon::Active, QIcon::On); + + QIcon *iReceive= new QIcon(); + + iReceive->addFile(":/icons/receiving_addresses", QSize(), QIcon::Normal, QIcon::Off ); + iReceive->addFile(":/icons/receiving_addresses_s", QSize(), QIcon::Active, QIcon::Off); + iReceive->addFile(":/icons/receiving_addresses_s", QSize(), QIcon::Active, QIcon::On); + + QIcon *iSideStake = new QIcon(); + + iSideStake->addFile(":/icons/sidestake", QSize(), QIcon::Normal, QIcon::Off ); + iSideStake->addFile(":/icons/sidestake_s", QSize(), QIcon::Active, QIcon::Off); + iSideStake->addFile(":/icons/sidestake_s", QSize(), QIcon::Active, QIcon::On); + + QIcon *iAddressBook = new QIcon(); + + iAddressBook->addFile(":/icons/address-book", QSize(), QIcon::Normal, QIcon::Off ); + iAddressBook->addFile(":/icons/address-book_s", QSize(), QIcon::Active, QIcon::Off); + iAddressBook->addFile(":/icons/address-book_s", QSize(), QIcon::Active, QIcon::On); + + QIcon *iHistory = new QIcon(); + + iHistory->addFile(":/icons/history", QSize(), QIcon::Normal, QIcon::Off ); + iHistory->addFile(":/icons/history_s", QSize(), QIcon::Active, QIcon::Off); + iHistory->addFile(":/icons/history_s", QSize(), QIcon::Active, QIcon::On); + + QIcon *iMessage = new QIcon(); + + iMessage->addFile(":/icons/message", QSize(), QIcon::Normal, QIcon::Off ); + iMessage->addFile(":/icons/message_s", QSize(), QIcon::Active, QIcon::Off); + iMessage->addFile(":/icons/message_s", QSize(), QIcon::Active, QIcon::On); + + //overviewAction = new QAction(QIcon(":/icons/overview"), tr("&Overview"), this); + overviewAction = new QAction(*iOverView, tr("&Overview"), this); overviewAction->setToolTip(tr("Show general overview of wallet")); overviewAction->setCheckable(true); overviewAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_1)); tabGroup->addAction(overviewAction); - sendCoinsAction = new QAction(QIcon(":/icons/send"), tr("&Send coins"), this); + sendCoinsAction = new QAction(*iSend, tr("&Send coins"), this); sendCoinsAction->setToolTip(tr("Send coins to a Pinkcoin address")); sendCoinsAction->setCheckable(true); sendCoinsAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_2)); tabGroup->addAction(sendCoinsAction); - receiveCoinsAction = new QAction(QIcon(":/icons/receiving_addresses"), tr("&Receive coins"), this); + receiveCoinsAction = new QAction(*iReceive, tr("&Receive coins"), this); receiveCoinsAction->setToolTip(tr("Show the list of addresses for receiving payments")); receiveCoinsAction->setCheckable(true); receiveCoinsAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_3)); tabGroup->addAction(receiveCoinsAction); - historyAction = new QAction(QIcon(":/icons/history"), tr("&Transactions"), this); - historyAction->setToolTip(tr("Browse transaction history")); - historyAction->setCheckable(true); - historyAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_4)); - tabGroup->addAction(historyAction); - - addressBookAction = new QAction(QIcon(":/icons/address-book"), tr("&Address Book"), this); + addressBookAction = new QAction(*iAddressBook, tr("&Address Book"), this); addressBookAction->setToolTip(tr("Edit the list of stored addresses and labels")); addressBookAction->setCheckable(true); - addressBookAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_5)); + addressBookAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_4)); tabGroup->addAction(addressBookAction); - messageAction = new QAction(QIcon(":/icons/edit"), tr("&Messages"), this); + stakeCoinsAction = new QAction(*iSideStake, tr("&Side Stakes"), this); + stakeCoinsAction->setToolTip(tr("Edit the list of addresses for staking out.")); + stakeCoinsAction->setCheckable(true); + stakeCoinsAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_5)); + tabGroup->addAction(stakeCoinsAction); + + historyAction = new QAction(*iHistory, tr("&Transactions"), this); + historyAction->setToolTip(tr("Browse transaction history")); + historyAction->setCheckable(true); + historyAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_6)); + tabGroup->addAction(historyAction); + + messageAction = new QAction(*iMessage, tr("&Messages"), this); messageAction->setToolTip(tr("View and Send Private Messages")); messageAction->setCheckable(true); - messageAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_6)); + messageAction->setShortcut(QKeySequence(Qt::ALT + Qt::Key_7)); tabGroup->addAction(messageAction); connect(overviewAction, SIGNAL(triggered()), this, SLOT(showNormalIfMinimized())); connect(overviewAction, SIGNAL(triggered()), this, SLOT(gotoOverviewPage())); + connect(sendCoinsAction, SIGNAL(triggered()), this, SLOT(showNormalIfMinimized())); connect(sendCoinsAction, SIGNAL(triggered()), this, SLOT(gotoSendCoinsPage())); + connect(receiveCoinsAction, SIGNAL(triggered()), this, SLOT(showNormalIfMinimized())); connect(receiveCoinsAction, SIGNAL(triggered()), this, SLOT(gotoReceiveCoinsPage())); + connect(historyAction, SIGNAL(triggered()), this, SLOT(showNormalIfMinimized())); connect(historyAction, SIGNAL(triggered()), this, SLOT(gotoHistoryPage())); + connect(addressBookAction, SIGNAL(triggered()), this, SLOT(showNormalIfMinimized())); connect(addressBookAction, SIGNAL(triggered()), this, SLOT(gotoAddressBookPage())); + + connect(stakeCoinsAction, SIGNAL(triggered()), this, SLOT(showNormalIfMinimized())); + connect(stakeCoinsAction, SIGNAL(triggered()), this, SLOT(gotoStakeCoinsPage())); + connect(messageAction, SIGNAL(triggered()), this, SLOT(showNormalIfMinimized())); connect(messageAction, SIGNAL(triggered()), this, SLOT(gotoMessagePage())); @@ -461,6 +600,9 @@ void BitcoinGUI::createActions() openRPCConsoleAction = new QAction(QIcon(":/icons/debugwindow"), tr("&Debug window"), this); openRPCConsoleAction->setToolTip(tr("Open debugging and diagnostic console")); + minimizeAction = new QAction(this); + closeAction = new QAction(this); + connect(quitAction, SIGNAL(triggered()), qApp, SLOT(quit())); connect(aboutAction, SIGNAL(triggered()), this, SLOT(aboutClicked())); connect(aboutQtAction, SIGNAL(triggered()), qApp, SLOT(aboutQt())); @@ -473,7 +615,10 @@ void BitcoinGUI::createActions() connect(lockWalletAction, SIGNAL(triggered()), this, SLOT(lockWallet())); connect(signMessageAction, SIGNAL(triggered()), this, SLOT(gotoSignMessageTab())); connect(verifyMessageAction, SIGNAL(triggered()), this, SLOT(gotoVerifyMessageTab())); - + + connect(minimizeAction, SIGNAL(triggered()), this, SLOT(showMinimized())); + connect(closeAction, SIGNAL(triggered()), this, SLOT(close())); + /* zeewolf: Hot swappable wallet themes */ if (themesList.count()>0) { @@ -505,6 +650,51 @@ void BitcoinGUI::createMenuBar() #endif // Configure the menus + +// QLabel* pinkCorner = new QLabel(this); +// pinkCorner->setText("

"); +// appMenuBar->setCornerWidget(pinkCorner, Qt::TopLeftCorner); + appMenuBar->setMaximumWidth(180); + + + QWidget *w = new QWidget(this); + QHBoxLayout *layout = new QHBoxLayout(w); + + QLabel* pinkCorner = new QLabel(w); + pinkCorner->setText("

"); + layout->addWidget(pinkCorner); + + layout->addWidget(appMenuBar); + w->setStyleSheet("background-color: rgba(0,0,0,255)"); + +// labelMinimizeIcon = new ActiveLabel("

", this); +// labelCloseIcon = new ActiveLabel("

", this); + + labelMinimizeIcon = new ActiveLabel(); + labelCloseIcon = new ActiveLabel(); + + labelMinimizeIcon->setText("

"); + labelCloseIcon->setText("

"); + + connect(labelMinimizeIcon, SIGNAL(clicked()), minimizeAction, SLOT(trigger())); + connect(labelMinimizeIcon, SIGNAL(hovered()), this, SLOT(minHover())); + connect(labelMinimizeIcon, SIGNAL(unhovered()), this, SLOT(minUnhover())); + + connect(labelCloseIcon, SIGNAL(clicked()), closeAction, SLOT(trigger())); + connect(labelCloseIcon, SIGNAL(hovered()), this, SLOT(closeHover())); + connect(labelCloseIcon, SIGNAL(unhovered()), this, SLOT(closeUnhover())); + + layout->addStretch(); + + layout->addWidget(labelMinimizeIcon); + layout->addWidget(labelCloseIcon); + + layout->setContentsMargins(0,0,0,0); + + + setMenuWidget(w); + + QMenu *file = appMenuBar->addMenu(tr("&File")); file->addAction(backupWalletAction); file->addAction(signMessageAction); @@ -525,6 +715,10 @@ void BitcoinGUI::createMenuBar() help->addSeparator(); help->addAction(aboutAction); help->addAction(aboutQtAction); + + //appMenuBar->setMaximumWidth(180); + + /* zeewolf: Hot swappable wallet themes */ if (themesList.count()>0) @@ -537,6 +731,39 @@ void BitcoinGUI::createMenuBar() /* zeewolf: Hot swappable wallet themes */ } +/* +bool ActiveLabel::event(QEvent *e) +{ + QHoverEvent me = static_cast(e); + if(e->type() == QEvent::HoverMove) + { + double xpos = me->pos().x(); + double ypos = me->pos().y(); + emit hovered(xpos, ypos); + qDebug() << Q_FUNC_INFO << QString("xpos %1, ypos %2").arg(xpos).arg(ypos); + return true; + } + else if(e->type() == QEvent::HoverLeave) + { + emit unhovered(); + return true; + } + else if(e->type() == QEvent::MouseButtonPress) + { + emit clicked(); + return true; + } + else if(e->type() == QEvent::MouseButtonDblClick) + { + emit doubleClicked(); + return true; + } + + return QLabel::event(e); +} + +*/ + void BitcoinGUI::createToolBars() { @@ -552,14 +779,20 @@ void BitcoinGUI::createToolBars() mainToolbar->widgetForAction(sendCoinsAction)->setObjectName("SendButton"); mainToolbar->addAction(receiveCoinsAction); mainToolbar->widgetForAction(receiveCoinsAction)->setObjectName("ReceiveButton"); - mainToolbar->addAction(historyAction); - mainToolbar->widgetForAction(historyAction)->setObjectName("HistoryButton"); mainToolbar->addAction(addressBookAction); mainToolbar->widgetForAction(addressBookAction)->setObjectName("AddressBookButton"); + mainToolbar->addAction(stakeCoinsAction); + mainToolbar->widgetForAction(stakeCoinsAction)->setObjectName("SideStakeButton"); + mainToolbar->addAction(historyAction); + mainToolbar->widgetForAction(historyAction)->setObjectName("HistoryButton"); mainToolbar->addAction(messageAction); mainToolbar->widgetForAction(messageAction)->setObjectName("MessageButton"); mainToolbar->setContextMenuPolicy(Qt::NoContextMenu); + mainToolbar->layout()->setContentsMargins(0,0,0,0); + + + //connect(mainToolbar, SIGNAL(orientationChanged(Qt::Orientation)), this, SLOT(mainToolbarOrientation(Qt::Orientation))); //mainToolbarOrientation(mainToolbar->orientation()); } @@ -601,13 +834,15 @@ void BitcoinGUI::setClientModel(ClientModel *clientModel) rpcConsole->setClientModel(clientModel); addressBookPage->setOptionsModel(clientModel->getOptionsModel()); + stakeCoinsPage->setOptionsModel(clientModel->getOptionsModel()); receiveCoinsPage->setOptionsModel(clientModel->getOptionsModel()); } } -void BitcoinGUI::setWalletModel(WalletModel *walletModel) +void BitcoinGUI::setWalletModel(WalletModel *walletModel, WalletModel *stakeModel) { this->walletModel = walletModel; + this->stakeModel = stakeModel; if(walletModel) { // Report errors from wallet thread @@ -633,6 +868,8 @@ void BitcoinGUI::setWalletModel(WalletModel *walletModel) connect(walletModel, SIGNAL(requireUnlock()), this, SLOT(unlockWallet())); } + if(stakeModel) + stakeCoinsPage->setModel(stakeModel->getAddressTableModel()); } void BitcoinGUI::setMessageModel(MessageModel *messageModel) @@ -717,6 +954,26 @@ void BitcoinGUI::aboutClicked() dlg.exec(); } +void BitcoinGUI::minHover() +{ + labelMinimizeIcon->setText("

"); +} + +void BitcoinGUI::minUnhover() +{ + labelMinimizeIcon->setText("

"); +} + +void BitcoinGUI::closeHover() +{ + labelCloseIcon->setText("

"); +} + +void BitcoinGUI::closeUnhover() +{ + labelCloseIcon->setText("

"); +} + void BitcoinGUI::setNumConnections(int count) { QString icon; @@ -996,6 +1253,13 @@ void BitcoinGUI::gotoAddressBookPage() } +void BitcoinGUI::gotoStakeCoinsPage() +{ + stakeCoinsAction->setChecked(true); + centralWidget->setCurrentWidget(stakeCoinsPage); + +} + void BitcoinGUI::gotoReceiveCoinsPage() { receiveCoinsAction->setChecked(true); @@ -1428,3 +1692,29 @@ void BitcoinGUI::keyPressEvent(QKeyEvent * e) } /* zeewolf: Hot swappable wallet themes */ + + +void BitcoinGUI::mousePressEvent(QMouseEvent* event) +{ + if(event->button() == Qt::LeftButton) + { + mMoving = true; + mLastMousePosition = event->pos(); + } +} + +void BitcoinGUI::mouseMoveEvent(QMouseEvent* event) +{ + if( event->buttons().testFlag(Qt::LeftButton) && mMoving) + { + this->move(this->pos() + (event->pos() - mLastMousePosition)); + } +} + +void BitcoinGUI::mouseReleaseEvent(QMouseEvent* event) +{ + if(event->button() == Qt::LeftButton) + { + mMoving = false; + } +} diff --git a/src/qt/bitcoingui.h b/src/qt/bitcoingui.h index af0e220..00cb2e8 100644 --- a/src/qt/bitcoingui.h +++ b/src/qt/bitcoingui.h @@ -40,9 +40,12 @@ class ActiveLabel : public QLabel signals: void clicked(); + void hovered(); + void unhovered(); protected: - void mouseReleaseEvent (QMouseEvent * event) ; + bool event(QEvent *e); +// void mouseReleaseEvent (QMouseEvent * event) ; }; @@ -66,7 +69,7 @@ class BitcoinGUI : public QMainWindow The wallet model represents a bitcoin wallet, and offers access to the list of transactions, address book and sending functionality. */ - void setWalletModel(WalletModel *walletModel); + void setWalletModel(WalletModel *walletModel, WalletModel *stakeModel); /** Set the message model. The message model represents encryption message database, and offers access to the list of messages, address book and sending functionality. @@ -79,9 +82,14 @@ class BitcoinGUI : public QMainWindow void dragEnterEvent(QDragEnterEvent *event); void dropEvent(QDropEvent *event); + void mouseMoveEvent(QMouseEvent* event); + void mousePressEvent(QMouseEvent* event); + void mouseReleaseEvent(QMouseEvent* event); + private: ClientModel *clientModel; WalletModel *walletModel; + WalletModel *stakeModel; MessageModel *messageModel; QStackedWidget *centralWidget; @@ -90,11 +98,14 @@ class BitcoinGUI : public QMainWindow QWidget *transactionsPage; AddressBookPage *addressBookPage; AddressBookPage *receiveCoinsPage; + AddressBookPage *stakeCoinsPage; MessagePage *messagePage; SendCoinsDialog *sendCoinsPage; SignVerifyMessageDialog *signVerifyMessageDialog; ActiveLabel *labelEncryptionIcon; + ActiveLabel *labelMinimizeIcon; + ActiveLabel *labelCloseIcon; QLabel *labelStakingIcon; QLabel *labelConnectionsIcon; QLabel *labelBlocksIcon; @@ -109,6 +120,7 @@ class BitcoinGUI : public QMainWindow QAction *historyAction; QAction *quitAction; QAction *sendCoinsAction; + QAction *stakeCoinsAction; QAction *addressBookAction; QAction *messageAction; QAction *signMessageAction; @@ -123,6 +135,10 @@ class BitcoinGUI : public QMainWindow QAction *changePassphraseAction; QAction *unlockWalletAction; QAction *lockWalletAction; + QAction *minimizeAction; + QAction *minimizeActionUnhover; + QAction *closeAction; + QAction *closeActionUnhover; QAction *aboutQtAction; QAction *openRPCConsoleAction; @@ -151,6 +167,9 @@ class BitcoinGUI : public QMainWindow /** Create system tray (notification) icon */ void createTrayIcon(); + QPoint mLastMousePosition; + bool mMoving; + public slots: /** Set number of connections shown in the UI */ void setNumConnections(int count); @@ -183,6 +202,8 @@ private slots: void gotoOverviewPage(); /** Switch to history (transactions) page */ void gotoHistoryPage(); + /** Switch to Side Stake page */ + void gotoStakeCoinsPage(); /** Switch to address book page */ void gotoAddressBookPage(); /** Switch to receive coins page */ @@ -201,6 +222,12 @@ private slots: void optionsClicked(); /** Show about dialog */ void aboutClicked(); + + void minHover(); + void minUnhover(); + + void closeHover(); + void closeUnhover(); #ifndef Q_OS_MAC /** Handle tray icon clicked */ void trayIconActivated(QSystemTrayIcon::ActivationReason reason); @@ -244,3 +271,4 @@ private slots: }; #endif + diff --git a/src/qt/bitcoinunits.cpp b/src/qt/bitcoinunits.cpp index c42408d..33fc524 100644 --- a/src/qt/bitcoinunits.cpp +++ b/src/qt/bitcoinunits.cpp @@ -85,7 +85,7 @@ int BitcoinUnits::decimals(int unit) } } -QString BitcoinUnits::format(int unit, qint64 n, bool fPlus) +QString BitcoinUnits::format(int unit, qint64 n, bool fPlus, int maxPrecision) { // Note: not using straight sprintf here because we do NOT want // localized number formatting. @@ -99,9 +99,11 @@ QString BitcoinUnits::format(int unit, qint64 n, bool fPlus) QString quotient_str = QString::number(quotient); QString remainder_str = QString::number(remainder).rightJustified(num_decimals, '0'); + + // Right-trim excess zeros after the decimal point int nTrim = 0; - for (int i = remainder_str.size()-1; i>=2 && (remainder_str.at(i) == '0'); --i) + for (int i = remainder_str.size()-1; i>=2 && (remainder_str.at(i) == '0') || i>=maxPrecision; --i) ++nTrim; remainder_str.chop(nTrim); @@ -112,9 +114,9 @@ QString BitcoinUnits::format(int unit, qint64 n, bool fPlus) return quotient_str + QString(".") + remainder_str; } -QString BitcoinUnits::formatWithUnit(int unit, qint64 amount, bool plussign) +QString BitcoinUnits::formatWithUnit(int unit, qint64 amount, bool plussign, int maxPrecision) { - return format(unit, amount, plussign) + QString(" ") + name(unit); + return format(unit, amount, plussign, maxPrecision) + QString(" ") + name(unit); } bool BitcoinUnits::parse(int unit, const QString &value, qint64 *val_out) diff --git a/src/qt/bitcoinunits.h b/src/qt/bitcoinunits.h index 9b7c9e1..c2908af 100644 --- a/src/qt/bitcoinunits.h +++ b/src/qt/bitcoinunits.h @@ -41,9 +41,9 @@ class BitcoinUnits: public QAbstractListModel //! Number of decimals left static int decimals(int unit); //! Format as string - static QString format(int unit, qint64 amount, bool plussign=false); + static QString format(int unit, qint64 amount, bool plussign=false, int maxPrecision = 8); //! Format as string (with unit) - static QString formatWithUnit(int unit, qint64 amount, bool plussign=false); + static QString formatWithUnit(int unit, qint64 amount, bool plussign=false, int maxPrecision = 8); //! Parse string to coin amount static bool parse(int unit, const QString &value, qint64 *val_out); ///@} diff --git a/src/qt/clabel.h b/src/qt/clabel.h new file mode 100644 index 0000000..20b8131 --- /dev/null +++ b/src/qt/clabel.h @@ -0,0 +1,35 @@ +#ifndef CUSTOMLABEL_H +#define CUSTOMLABEL_H + +#include + +class CustomLabel : public QLabel +{ + Q_OBJECT +public: + CustomLabel(QWidget* parent = nullptr) : QLabel(parent){ } + +public slots: + +signals: + + +private: + QString holdText; + +protected: + void enterEvent(QEvent *ev) override + { + holdText = this->text(); + this->setText(""); + //setStyleSheet("QLabel { background-color : blue; }"); + } + + void leaveEvent(QEvent *ev) override + { + this->setText(holdText); + //setStyleSheet("QLabel { background-color : green; }"); + } +}; + +#endif diff --git a/src/qt/editaddressdialog.cpp b/src/qt/editaddressdialog.cpp index bb02805..4ea448e 100644 --- a/src/qt/editaddressdialog.cpp +++ b/src/qt/editaddressdialog.cpp @@ -22,10 +22,28 @@ EditAddressDialog::EditAddressDialog(Mode mode, QWidget *parent) : ui->addressEdit->setVisible(false); ui->stealthCB->setEnabled(true); ui->stealthCB->setVisible(true); + ui->Percent->setVisible(false); + ui->spinPercent->setVisible(false); break; case NewSendingAddress: setWindowTitle(tr("New sending address")); ui->stealthCB->setVisible(false); + ui->Percent->setVisible(false); + ui->spinPercent->setVisible(false); + break; + case NewStakingAddress: + setWindowTitle(tr("New Address for Side-Stake")); + ui->Percent->setVisible(true); + ui->spinPercent->setEnabled(true); + ui->spinPercent->setVisible(true); + ui->stealthCB->setVisible(false); + break; + case EditStakingAddress: + setWindowTitle(tr("New Address for Side-Stake")); + ui->Percent->setVisible(true); + ui->spinPercent->setEnabled(true); + ui->spinPercent->setVisible(true); + ui->stealthCB->setVisible(false); break; case EditReceivingAddress: setWindowTitle(tr("Edit receiving address")); @@ -33,10 +51,14 @@ EditAddressDialog::EditAddressDialog(Mode mode, QWidget *parent) : ui->addressEdit->setVisible(true); ui->stealthCB->setEnabled(false); ui->stealthCB->setVisible(true); + ui->Percent->setVisible(false); + ui->spinPercent->setVisible(false); break; case EditSendingAddress: setWindowTitle(tr("Edit sending address")); ui->stealthCB->setVisible(false); + ui->Percent->setVisible(false); + ui->spinPercent->setVisible(false); break; } @@ -58,6 +80,7 @@ void EditAddressDialog::setModel(AddressTableModel *model) mapper->setModel(model); mapper->addMapping(ui->labelEdit, AddressTableModel::Label); mapper->addMapping(ui->addressEdit, AddressTableModel::Address); + mapper->addMapping(ui->spinPercent, AddressTableModel::Percent); mapper->addMapping(ui->stealthCB, AddressTableModel::Type); } @@ -75,17 +98,30 @@ bool EditAddressDialog::saveCurrentRow() { case NewReceivingAddress: case NewSendingAddress: - { + { int typeInd = ui->stealthCB->isChecked() ? AddressTableModel::AT_Stealth : AddressTableModel::AT_Normal; address = model->addRow( mode == NewSendingAddress ? AddressTableModel::Send : AddressTableModel::Receive, ui->labelEdit->text(), ui->addressEdit->text(), typeInd); - } + } + break; + case NewStakingAddress: + { + + address = model->addRow( + AddressTableModel::Stake, + ui->labelEdit->text(), + ui->addressEdit->text(), + AddressTableModel::AT_Normal, + ui->spinPercent->cleanText()); + + } break; case EditReceivingAddress: case EditSendingAddress: + case EditStakingAddress: if(mapper->submit()) { address = ui->addressEdit->text(); @@ -129,6 +165,10 @@ void EditAddressDialog::accept() QMessageBox::critical(this, windowTitle(), tr("New key generation failed."), QMessageBox::Ok, QMessageBox::Ok); + case AddressTableModel::INVALID_PERCENTAGE: + QMessageBox::warning(this, windowTitle(), + tr("Percentage exceeds available limit."), + QMessageBox::Ok, QMessageBox::Ok); break; } diff --git a/src/qt/editaddressdialog.h b/src/qt/editaddressdialog.h index 0e4183b..f3b076b 100644 --- a/src/qt/editaddressdialog.h +++ b/src/qt/editaddressdialog.h @@ -22,8 +22,10 @@ class EditAddressDialog : public QDialog enum Mode { NewReceivingAddress, NewSendingAddress, + NewStakingAddress, EditReceivingAddress, - EditSendingAddress + EditSendingAddress, + EditStakingAddress }; explicit EditAddressDialog(Mode mode, QWidget *parent = 0); diff --git a/src/qt/forms/addressbookpage.ui b/src/qt/forms/addressbookpage.ui index 14e18d5..5151c03 100644 --- a/src/qt/forms/addressbookpage.ui +++ b/src/qt/forms/addressbookpage.ui @@ -6,163 +6,183 @@ 0 0 - 760 + 813 380 Address Book - + - - - These are your Pinkcoin addresses for receiving payments. You may want to give a different one to each sender so you can keep track of who is paying you. + + + Qt::Horizontal - - Qt::PlainText + + QSizePolicy::Fixed - - true + + + 20 + 0 + - + - - - Qt::CustomContextMenu - - - Double-click to edit address or label - - - false - - - true - - - QAbstractItemView::SingleSelection - - - QAbstractItemView::SelectRows - - - true - - - false - - - - - - - - - Create a new address - - - &New Address - - - - :/icons/add:/icons/add - - - + - - - Copy the currently selected address to the system clipboard - + - &Copy Address - - - - :/icons/editcopy:/icons/editcopy + These are your Pinkcoin addresses for receiving payments. You may want to give a different one to each sender so you can keep track of who is paying you. - - - - - - Show &QR Code + + Qt::PlainText - - - :/icons/qrcode:/icons/qrcode + + true - - - Sign a message to prove you own a Pinkcoin address - - - Sign &Message - - - - :/icons/edit:/icons/edit + + + Qt::CustomContextMenu - - - - - Verify a message to ensure it was signed with a specified Pinkcoin address + Double-click to edit address or label - - &Verify Message + + false - - - :/icons/transaction_0:/icons/transaction_0 + + true - - - - - - Delete the currently selected address from the list + + QAbstractItemView::SingleSelection - - &Delete + + QAbstractItemView::SelectRows - - - :/icons/remove:/icons/remove + + true + + false + - - - Qt::Horizontal - - - - 40 - 20 - - - - - - - - - 0 - 0 - - - - QDialogButtonBox::Ok - - + + + + + Create a new address + + + &New Address + + + + :/icons/add:/icons/add + + + + + + + Copy the currently selected address to the system clipboard + + + &Copy Address + + + + :/icons/editcopy:/icons/editcopy + + + + + + + Show &QR Code + + + + :/icons/qrcode:/icons/qrcode + + + + + + + Sign a message to prove you own a Pinkcoin address + + + Sign &Message + + + + :/icons/edit:/icons/edit + + + + + + + Verify a message to ensure it was signed with a specified Pinkcoin address + + + &Verify Message + + + + :/icons/transaction_0:/icons/transaction_0 + + + + + + + Delete the currently selected address from the list + + + &Delete + + + + :/icons/remove:/icons/remove + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + 0 + 0 + + + + QDialogButtonBox::Ok + + + + diff --git a/src/qt/forms/editaddressdialog.ui b/src/qt/forms/editaddressdialog.ui index 62529b4..1843155 100644 --- a/src/qt/forms/editaddressdialog.ui +++ b/src/qt/forms/editaddressdialog.ui @@ -53,13 +53,42 @@ - + &Stealth Address + + + + Percent + + + + + + + + 0 + 0 + + + + + 0 + 0 + + + + % + + + 100 + + + diff --git a/src/qt/forms/messagepage.ui b/src/qt/forms/messagepage.ui index 477a7da..e9970ba 100644 --- a/src/qt/forms/messagepage.ui +++ b/src/qt/forms/messagepage.ui @@ -13,219 +13,242 @@ Address Book - + - - - These are your sent and received private messages. Click on an item to read it. + + + Qt::Horizontal - - Qt::PlainText + + QSizePolicy::Fixed - - true + + + 20 + 0 + - + - - - Qt::CustomContextMenu - - - Click on a message to view it - - - false - - - true - - - QAbstractItemView::SingleSelection - - - QAbstractItemView::SelectRows - - - true - - - false - - - - - + - - - + + + These are your sent and received private messages. Click on an item to read it. + + + Qt::PlainText + + + true - - - 2 - - - 0 - - - 6 - - - 0 - - - 0 - - - - - - - &Back - - - - :/icons/quit:/icons/quit - - - - - - - Contact: - - - - - - - - - - - - - - Qt::Horizontal - - - - 40 - 20 - - - - - - - - - - QListView { -selection-background-color: rgb(234, 255, 249); -} - - - - - - - - - - - 0 - 100 - + + + Qt::CustomContextMenu + + + Click on a message to view it + + + false + + + true + + + QAbstractItemView::SingleSelection + + QAbstractItemView::SelectRows + + + true + + + false + - - - - - &Conversation - - - - :/icons/add:/icons/add - - - - - - - Sign a message to prove you own a Pinkcoin address - - - &Send - - - - :/icons/send:/icons/send - - - - - - - Copy the currently selected address to the system clipboard - - - &Copy From Address - - - - :/icons/editcopy:/icons/editcopy - - - + + + 0 + - - - Copy the currently selected address to the system clipboard - - - Copy To &Address - - - - :/icons/editcopy:/icons/editcopy + + + + + + 2 + + + 0 + + + 6 + + + 0 + + + 0 + + + + + + + &Back + + + + :/icons/quit:/icons/quit + + + + + + + Contact: + + + + + + + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + QListView { +selection-background-color: rgb(234, 255, 249); +} + + + + + + + - - - Delete the currently selected address from the list - - - &Delete - - - - :/icons/remove:/icons/remove + + + + 0 + 100 + - - - Qt::Horizontal - - - - 40 - 20 - - - + + + + + &Conversation + + + + :/icons/add:/icons/add + + + + + + + Sign a message to prove you own a Pinkcoin address + + + &Send + + + + :/icons/send:/icons/send + + + + + + + Copy the currently selected address to the system clipboard + + + &Copy From Address + + + + :/icons/editcopy:/icons/editcopy + + + + + + + Copy the currently selected address to the system clipboard + + + Copy To &Address + + + + :/icons/editcopy:/icons/editcopy + + + + + + + Delete the currently selected address from the list + + + &Delete + + + + :/icons/remove:/icons/remove + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + diff --git a/src/qt/forms/overviewpage.ui b/src/qt/forms/overviewpage.ui index f1bc9da..b5951e0 100644 --- a/src/qt/forms/overviewpage.ui +++ b/src/qt/forms/overviewpage.ui @@ -13,70 +13,119 @@ Form - + + QWidget#OverviewPage{ +background-color:qlineargradient(spread:pad, x1:0, y1:0, x2:.04, y2:0, stop:0 rgba(225, 225, 225, 255), stop:1 rgba(250, 250, 250, 250)) +} + + + + 0 + + + 9 + - + + + 0 + + + 0 + - - - + + + Qt::Horizontal - - QFrame::StyledPanel + + QSizePolicy::Fixed - - QFrame::Raised + + + 20 + 0 + - - - 0 - - - 0 - - - 0 - - - 0 - - - 0 - - - - - QFrame::StyledPanel + + + + + + + + + + + QFrame::StyledPanel + + + QFrame::Raised + + + + 0 - - QFrame::Raised + + 0 - - - - - QFormLayout::ExpandingFieldsGrow - - - Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop - - - Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop - - - 0 - - - 0 - - - - - Spendable - - + + 0 + + + 0 + + + 0 + + + + + QFrame::StyledPanel + + + QFrame::Raised + + + + + + 6 + + + QLayout::SetDefaultConstraint + + + 0 + + + + + + 36 + + + + My Wallet + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + - + The displayed information may be out of date. Your wallet automatically synchronizes with the BitBay network after a connection is established, but this process has not completed yet. @@ -92,741 +141,698 @@ - - - - - 75 - true - - - - IBeamCursor - - - Your current spendable balance - - - top: -5px; - - - 0 - - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse - - - - - - - Qt::Vertical - - - - 20 - 10 - - - - - - - - - - - - - 0 - 0 - 0 - - - - - - - - - 0 - 0 - 0 - - - - - - - - - 120 - 120 - 120 - - - - - - - - Stake - - - - - - - - - - - - 0 - 0 - 0 - - - - - - - - - 0 - 0 - 0 - - - - - - - - - 120 - 120 - 120 - - - - - - - - - 75 - true - - - - IBeamCursor - - - Total of coins that was staked, and do not yet count toward the current balance - - - 0 - - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse - - - - - - - Qt::Vertical - - - - 20 - 10 - - - - - - - - - - - - - 0 - 0 - 0 - - - - - - - - - 0 - 0 - 0 - - - - - - - - - 120 - 120 - 120 - - - - - - - - - 75 - true - - - - IBeamCursor - - - Your current total balance - - - 0 - - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse - - - - - - - Qt::Vertical - - - - 20 - 10 - - - - - - - - - - - - - 0 - 0 - 0 - - - - - - - - - 0 - 0 - 0 - - - - - - - - - 120 - 120 - 120 - - - - - - - - <html><head/><body><p>Unconfirmed</p></body></html> - - - - - - - - - - - - 0 - 0 - 0 - - - - - - - - - 0 - 0 - 0 - - - - - - - - - 120 - 120 - 120 - - - - - - - - - 75 - true - - - - IBeamCursor - - - Total of transactions that have yet to be confirmed, and do not yet count toward the current balance - - - Qt::LeftToRight - - - 0 - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse - - - - - - - Qt::Vertical - - - - 20 - 10 - - - - - - - - - - - - - 0 - 0 - 0 - - - - - - - 0 - 0 - 0 - - - - - - - - - 0 - 0 - 0 - - - - - - - 0 - 0 - 0 - - - - - - - - - 120 - 120 - 120 - - - - - - - 120 - 120 - 120 - - - - - - - - Immature: - - - - - - - - 75 - true - - - - 0 - - - - - - - Qt::Vertical - - - - 20 - 10 - - - - - - - - Total Minted - - - - - - - - 75 - true - - - - 0 - - - - - - - Qt::Vertical - - - - 20 - 10 - - - - - - - - Current BTC Value - - - - - - - - 75 - true - - - - 0 - - - - - - - Qt::Vertical - - - - 20 - 40 - - - - - - - - - - - - - 0 - 0 - 0 - - - - - - - - - 0 - 0 - 0 - - - - - - - - - 120 - 120 - 120 - - - - - - - - Total - - - - - - - - - - - - Qt::AlignCenter - - - - - - - Qt::Vertical - - - - 20 - 40 - - - - - - - - - - - - - - - - - - - 350 - 0 - - - - - - - QFrame::StyledPanel - - - QFrame::Raised - - - - 0 - - - 0 - - - 0 - - - 0 - - - 0 - - - - - - 0 - 10 - - - - QFrame::StyledPanel - - - QFrame::Raised - - - - 9 - - - - - - <b>Recent transactions</b> - - + + + 0 + + + + + Current BTC Value + + + + + + + + + + + + 0 + 0 + 0 + + + + + + + + + 0 + 0 + 0 + + + + + + + + + 120 + 120 + 120 + + + + + + + + + 75 + true + + + + IBeamCursor + + + Total of transactions that have yet to be confirmed, and do not yet count toward the current balance + + + Qt::LeftToRight + + + 0 + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + + + + Qt::Vertical + + + + 20 + 10 + + + + + + + + Qt::Vertical + + + + 20 + 10 + + + + + + + + Qt::Vertical + + + + 20 + 10 + + + + + + + + Spendable + + + + + + + Total Minted + + + + + + + + + + + + 0 + 0 + 0 + + + + + + + + + 0 + 0 + 0 + + + + + + + + + 120 + 120 + 120 + + + + + + + + Stake + + + + + + + Qt::Vertical + + + + 20 + 10 + + + + + + + + + + + + + 0 + 0 + 0 + + + + + + + + + 0 + 0 + 0 + + + + + + + + + 120 + 120 + 120 + + + + + + + + Total + + + + + + + Qt::Vertical + + + + 20 + 10 + + + + + + + + + 75 + true + + + + IBeamCursor + + + Your current spendable balance + + + top: -5px; + + + 0 + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + 75 + true + + + + 0 + + + + + + + + 75 + true + + + + 0 + + + + + + + + 75 + true + + + + 0 + + + + + + + + + + + + 0 + 0 + 0 + + + + + + + 0 + 0 + 0 + + + + + + + + + 0 + 0 + 0 + + + + + + + 0 + 0 + 0 + + + + + + + + + 120 + 120 + 120 + + + + + + + 120 + 120 + 120 + + + + + + + + Immature: + + + + + + + + + + + + 0 + 0 + 0 + + + + + + + + + 0 + 0 + 0 + + + + + + + + + 120 + 120 + 120 + + + + + + + + <html><head/><body><p>Unconfirmed</p></body></html> + + + + + + + + + + + + 0 + 0 + 0 + + + + + + + + + 0 + 0 + 0 + + + + + + + + + 120 + 120 + 120 + + + + + + + + + 75 + true + + + + IBeamCursor + + + Total of coins that was staked, and do not yet count toward the current balance + + + 0 + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + + + + + + + + + 0 + 0 + 0 + + + + + + + + + 0 + 0 + 0 + + + + + + + + + 120 + 120 + 120 + + + + + + + + + 75 + true + + + + IBeamCursor + + + Your current total balance + + + 0 + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + - - - The displayed information may be out of date. Your wallet automatically synchronizes with the BitBay network after a connection is established, but this process has not completed yet. - - - QLabel { color: red; } - + - (out of sync) - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + - - - Qt::Horizontal - - - - 40 - 20 - - - + + + + + + 350 + 0 + + + + + + + QFrame::StyledPanel + + + QFrame::Raised + + + + 0 + + + 0 + + + 0 + + + 0 + + + 0 + + + + + + 0 + 10 + + + + QFrame::StyledPanel + + + QFrame::Raised + + + + 9 + + + + + + + <b>Recent transactions</b> + + + + + + + The displayed information may be out of date. Your wallet automatically synchronizes with the BitBay network after a connection is established, but this process has not completed yet. + + + QLabel { color: red; } + + + (out of sync) + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + + QListView { background: transparent; } + + + QFrame::NoFrame + + + Qt::ScrollBarAlwaysOff + + + Qt::ScrollBarAlwaysOff + + + QAbstractItemView::NoSelection + + + + + listTransactions + + + + + + + - - - - - QListView { background: transparent; } - - - QFrame::NoFrame - - - Qt::ScrollBarAlwaysOff - - - Qt::ScrollBarAlwaysOff - - - QAbstractItemView::NoSelection - - - - - listTransactions - - - - - - - - - - - 1 - 0 - - - - - 200 - 150 - - - - - 400 - 200 - - - - <html><head/><body><img src=":/icons/pinkcoin-128"/></span></body></html> - - - Qt::AlignCenter - - + + + + + + diff --git a/src/qt/forms/sendcoinsdialog.ui b/src/qt/forms/sendcoinsdialog.ui index 591fdd3..0bb7114 100644 --- a/src/qt/forms/sendcoinsdialog.ui +++ b/src/qt/forms/sendcoinsdialog.ui @@ -6,857 +6,870 @@ 0 0 - 850 - 400 + 859 + 623 Send Coins - + 8 - - - - 0 - 0 - + + + Qt::Horizontal - + + QSizePolicy::Fixed + + - 16777215 - 16777215 + 20 + 0 - - QFrame::StyledPanel - - - QFrame::Sunken + + + + + + 0 - - - 6 - - - 0 - - - 0 - - - 0 - - - 6 - - - + + + + + 0 + 0 + + + + + 16777215 + 16777215 + + + + QFrame::StyledPanel + + + QFrame::Sunken + + - 0 + 6 - 10 + 0 - 10 + 0 + + + 0 + + + 6 - - - 15 - - - - - - 0 - 0 - - - - - 75 - true - - - - font-weight:bold; - - - Coin Control Features - - - - - - - + - 8 + 0 - + + 10 + + 10 - - - - - - Inputs... - - - - - - - automatically selected - - - 5 + + + 15 - + + + + + 0 + 0 + + + + + 75 + true + + + + font-weight:bold; + + + Coin Control Features + + + + - - - - 75 - true - - - - color:red;font-weight:bold; - - - Insufficient funds! + + + 8 - - 5 + + 10 - + + + + + + + Inputs... + + + + + + + automatically selected + + + 5 + + + + + + + + 75 + true + + + + color:red;font-weight:bold; + + + Insufficient funds! + + + 5 + + + + + + + Qt::Horizontal + + + + 40 + 1 + + + + + - - - Qt::Horizontal + + + + 0 + 0 + - + - 40 - 1 + 0 + 0 - - - - - - - - - 0 - 0 - - - - - 0 - 0 - - - - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - 20 + + + + + + 0 0 + + 0 + - 10 + 0 - - - 10 - - - 14 - - - 10 + + + 20 - 4 - - - 6 + 0 - - - - font-weight:bold; - - - Quantity: - - - 0 - - - - - - - - Monospace - 10 - - - - IBeamCursor - - - Qt::ActionsContextMenu - - - 0 - - - 0 - - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse - - - - - - - font-weight:bold; - - - Bytes: - - - - - - - - Monospace - 10 - - - - IBeamCursor - - - Qt::ActionsContextMenu - - - 0 - - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse - - - - - - - - + 10 - - 14 - - - 6 - - - 4 - - - 6 - - - - - font-weight:bold; - - - Amount: - - - 0 - - - - - - - - Monospace - 10 - - - - IBeamCursor - - - Qt::ActionsContextMenu - - - 0.00 PINK - - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse - - - - - - - font-weight:bold; - - - Priority: - - + + + + 10 + + + 14 + + + 10 + + + 4 + + + 6 + + + + + font-weight:bold; + + + Quantity: + + + 0 + + + + + + + + Monospace + 10 + + + + IBeamCursor + + + Qt::ActionsContextMenu + + + 0 + + + 0 + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + + + + font-weight:bold; + + + Bytes: + + + + + + + + Monospace + 10 + + + + IBeamCursor + + + Qt::ActionsContextMenu + + + 0 + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + - - - - - Monospace - 10 - - - - IBeamCursor - - - Qt::ActionsContextMenu - - - medium - - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse - - - - - - - - - 10 - - - 14 - - - 6 - - - 4 - - - 6 - - - - - font-weight:bold; - - - Fee: - - - 0 - - - - - - - - Monospace - 10 - - - - IBeamCursor - - - Qt::ActionsContextMenu - - - 0.00 PINK - - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse - - - - - - - font-weight:bold; - - - Low Output: - - - - - - - - Monospace - 10 - - - - IBeamCursor - - - Qt::ActionsContextMenu - - - no - - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse - - - - - - - - - QFormLayout::AllNonFixedFieldsGrow - - - 10 - - - 14 - - - 6 - - - 4 - - - 6 - - - - - font-weight:bold; - - - After Fee: - - - 0 - - - - - - - - Monospace - 10 - - - - IBeamCursor - - - Qt::ActionsContextMenu - - - 0.00 PINK - - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse - - + + + + 10 + + + 14 + + + 6 + + + 4 + + + 6 + + + + + font-weight:bold; + + + Amount: + + + 0 + + + + + + + + Monospace + 10 + + + + IBeamCursor + + + Qt::ActionsContextMenu + + + 0.00 PINK + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + + + + font-weight:bold; + + + Priority: + + + + + + + + Monospace + 10 + + + + IBeamCursor + + + Qt::ActionsContextMenu + + + medium + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + - - - - font-weight:bold; - - - Change - - + + + + 10 + + + 14 + + + 6 + + + 4 + + + 6 + + + + + font-weight:bold; + + + Fee: + + + 0 + + + + + + + + Monospace + 10 + + + + IBeamCursor + + + Qt::ActionsContextMenu + + + 0.00 PINK + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + + + + font-weight:bold; + + + Low Output: + + + + + + + + Monospace + 10 + + + + IBeamCursor + + + Qt::ActionsContextMenu + + + no + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + - - - - - Monospace - 10 - - - - IBeamCursor - - - Qt::ActionsContextMenu - - - 0.00 PINK - - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse - - + + + + QFormLayout::AllNonFixedFieldsGrow + + + 10 + + + 14 + + + 6 + + + 4 + + + 6 + + + + + font-weight:bold; + + + After Fee: + + + 0 + + + + + + + + Monospace + 10 + + + + IBeamCursor + + + Qt::ActionsContextMenu + + + 0.00 PINK + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + + + + font-weight:bold; + + + Change + + + + + + + + Monospace + 10 + + + + IBeamCursor + + + Qt::ActionsContextMenu + + + 0.00 PINK + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + - - - - - - - - 12 - - - QLayout::SetDefaultConstraint - - - 5 - - - 5 - - - - - SplitBlock - - - - - - - false - - - - 0 - 0 - - - - - 100 - 16777215 - - - - - - - - false - - - - 75 - true - - - - Block Size: - - - - - - - false - - - 0.00 PINK - - - - - - - Return Change - - - - Custom Change Address + + + 12 - - - - - - false + + QLayout::SetMinimumSize - - - 0 - 0 - + + 0 - - - - - - - 0 - 0 - - - - - 0 - 0 - - - - + + 5 - - 3 + + 0 - + + + + SplitBlock + + + + + + + false + + + + 0 + 0 + + + + + 100 + 16777215 + + + + + + + + false + + + + 75 + true + + + + Block Size: + + + + + + + false + + + 0.00 PINK + + + + + + + Return Change + + + + + + + Custom Change Address + + + + + + + false + + + + 0 + 0 + + + + + + + + + 0 + 0 + + + + + 0 + 0 + + + + + + + 3 + + + + - - - - Qt::Vertical - - - - 800 - 1 - - - - - - - - - - - - true - - - - - 0 - 0 - 830 - 163 - - - - - 0 - - - 0 - - - 0 - - - 0 - - - - - 6 - - - - - - - Qt::Vertical - - - - 20 - 40 - - - - - - - - - - - - - - Send to multiple recipients at once - - - Add &Recipient - - - - :/icons/add:/icons/add - - - false - - - - - 0 - 0 - - - - Remove all transaction fields - - - Clear &All - - - - :/icons/remove:/icons/remove - - - 300 - - - false + + + true + + + + 0 + 0 + 811 + 398 + + + + + 0 + + + 0 + + + 0 + + + 0 + + + + + 6 + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + - - - 3 - + - - - - 0 - 0 - + + + Send to multiple recipients at once - Balance: + Add &Recipient + + + + :/icons/add:/icons/add + + + false - + - + 0 0 - - IBeamCursor + + Remove all transaction fields - 0 PINK + Clear &All + + + + :/icons/remove:/icons/remove - - Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + 300 + + + false + + + + + + + 3 + + + + + + 0 + 0 + + + + Balance: + + + + + + + + 0 + 0 + + + + IBeamCursor + + + 0 PINK + + + Qt::LinksAccessibleByMouse|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse + + + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + + + 150 + 0 + + + + Confirm the send action + + + S&end + + + + :/icons/send:/icons/send + + + true - - - - Qt::Horizontal - - - - 40 - 20 - - - - - - - - - 150 - 0 - - - - Confirm the send action - - - S&end - - - - :/icons/send:/icons/send - - - true - - - diff --git a/src/qt/forms/sendmessagesdialog.ui b/src/qt/forms/sendmessagesdialog.ui index e3a99b7..2c838b2 100644 --- a/src/qt/forms/sendmessagesdialog.ui +++ b/src/qt/forms/sendmessagesdialog.ui @@ -13,10 +13,13 @@ Send Messages - + 8 + + + @@ -106,7 +109,7 @@ 0 0 830 - 279 + 291 diff --git a/src/qt/locale/bitcoin_nl.ts b/src/qt/locale/bitcoin_nl.ts index 756ff24..49b413d 100644 --- a/src/qt/locale/bitcoin_nl.ts +++ b/src/qt/locale/bitcoin_nl.ts @@ -47,7 +47,7 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d Double-click to edit address or label - Dubbelklik om het adres of label te wijzigen + Dubbelklik om het adres of label te wijzipink @@ -67,7 +67,7 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d These are your Pinkcoin addresses for receiving payments. You may want to give a different one to each sender so you can keep track of who is paying you. - Dit zijn al jou Pinkcoin adressen om betalingen mee te ontvangen. Je kunt iedere verzender een apart adres geven zodat je kunt volgen wie jou betaald. + Dit zijn al jou Pinkcoin adressen om betalinpink mee te ontvanpink. Je kunt iedere verzender een apart adres geven zodat je kunt volpink wie jou betaald. @@ -137,7 +137,7 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d Could not write to file %1. - Kan niet schrijven naar bestand %1 + Kan niet schrijven naat bestand %1 @@ -183,7 +183,7 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d Serves to disable the trivial sendmoney when OS account compromised. Provides no real security. - Bedoeld om het command 'sendmoney' uit te schakelen indien het besturingssysteem (OS) niet meer veilig is. Dit geeft geen echte beveiliging. + Bedoeld om het command 'sendmoney' uit te schakelen indien het OS niet meer veilig is. Geeft geen echte beveiliging. @@ -248,7 +248,7 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d IMPORTANT: Any previous backups you have made of your wallet file should be replaced with the newly generated, encrypted wallet file. For security reasons, previous backups of the unencrypted wallet file will become useless as soon as you start using the new, encrypted wallet. - BELANGRIJK: Elke eerder gemaakte backup van uw portemonneebestand dient u te vervangen door het nieuw gegenereerde, versleutelde portemonneebestand. Om veiligheidsredenen zullen eerdere backups van het niet-versleutelde portemonneebestand onbruikbaar worden zodra u uw nieuwe, versleutelde portemonnee begint te gebruiken. + BELANGRIJK: Elke eerder gemaakte backup van uw portemonneebestand dient u te vervanpink door het nieuw gegenereerde, versleutelde portemonneebestand. Om veiligheidsredenen zullen eerdere backups van het niet-versleutelde portemonneebestand onbruikbaar worden zodra u uw nieuwe, versleutelde, portemonnee begint te gebruiken. @@ -265,7 +265,7 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d Pinkcoin will close now to finish the encryption process. Remember that encrypting your wallet cannot fully protect your coins from being stolen by malware infecting your computer. - Pinkcoin zal nu sluiten om het versleutel proces te voltooien. Onthou dat het versleutelen van je portemonnee je niet volledig beschermt tegen diefstal van munten door malware op je computer. + Pinkcoin zal nu sluiten om het versleutel proces te voltooien. Onthou dat het versleutelen van je portemonnee je niet volledig beschermt tepink diefstal van munten door malware op je computer. @@ -301,12 +301,12 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d Wallet decryption failed - Portemonnee-ontsleuteling is mislukt + Portemonnee-ontsleuteling mislukt Wallet passphrase was successfully changed. - Portemonnee-ontsleuteling is met succes gewijzigd. + Portemonneewachtwoord is met succes gewijzigd. @@ -359,7 +359,7 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d Show the list of addresses for receiving payments - Toon de lijst met adressen voor het ontvangen van betalingen + Toon de lijst aan adressen voor ontvanpink betalinpink @@ -419,7 +419,7 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d Downloaded %1 of %2 blocks of transaction history (%3% done). - %1 van %2 aan transactiegeschiedenis blokken gedownload (%3% klaar). + %1 van %2 aan transactie historie blokken gedownload (%3% klaar). @@ -439,7 +439,7 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d Export the data in the current tab to a file - Exporteer de data op het huidige tabblad naar een bestand + Exporteer de data in de huidige tab naar een bestand @@ -449,7 +449,7 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d Backup wallet to another location - Maak een Backup-portemonnee op een andere locatie + Backup portemonnee naar een andere locatie @@ -514,12 +514,12 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d &Settings - &Instellingen + &Instellinpink &Help - &Help + &Hulp @@ -546,37 +546,37 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d %n active connection(s) to Pinkcoin network - %n actieve verbinding naar Pinkcoin netwerk%n actieve verbindingen naar Pinkcoin netwerk + %n actieve verbinding naar Pinkcoin netwerk%n actieve verbindinpink naar Pinkcoin netwerk Downloaded %1 blocks of transaction history. - %1 blokken van transactiegeschiedenis gedownload. + %1 blokken van transactie geschiedenis gedownload. Staking.<br>Your weight is %1<br>Network weight is %2<br>Expected time to earn reward is %3 - Staking. <br> Uw gewicht wordt %1 <br> Netwerkgewicht is %2 <br> Verwachte tijd om een beloning te verdienen is %3 + Staking. <br> Uw gewicht wordt %1 <br> Network gewicht is %2 <br> Verwachte tijd om beloning te verdienen is %3 Not staking because wallet is locked - Niet staking omdat de portemonnee beveiligd is + Niet staking omdat portemonnee aan het beveiligd is Not staking because wallet is offline - Niet staking omdat de portemonnee offline is + Niet staking omdat portemonnee aan het offline is Not staking because wallet is syncing - Niet staking omdat de portemonnee aan het synchroniseren is. + Niet staking omdat portemonnee aan het synchroniseren is. Not staking because you don't have mature coins - Niet staking omdat je geen volwassen munten hebt + Niet staking omdat je geen mature munten hebt @@ -601,7 +601,7 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d %n day(s) ago - %n dag geleden%n dagen geleden + %n dag geleden%n dapink geleden @@ -616,7 +616,7 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d Last received block was generated %1. - Laatst ontvangen blok is gegenereerd op %1. + Laatst ontvanpink blok is gegenereerd op %1. @@ -626,12 +626,12 @@ Dit product bevat software ontwikkeld door het OpenSSL Project voor gebruik in d Confirm transaction fee - Bevestig transactiekosten + Bevestig transactie kosten Sent transaction - Transactie verzonden + Verzonden transactie @@ -691,7 +691,7 @@ Adres: %4 There was an error trying to save the wallet data to the new location. - Er is een fout opgetreden bij het opslaan van de wallet data naar de nieuwe locatie. + Er was een fout opgetreden bij het opslaan van de wallet data naar de nieuwe locatie. @@ -711,7 +711,7 @@ Adres: %4 %n day(s) - %n dag%n dagen + %n dag%n dapink @@ -782,7 +782,7 @@ Adres: %4 Change: - Wijzigen: + Wijzipink: @@ -822,7 +822,7 @@ Adres: %4 Confirmations - Bevestigingen + Bevestiginpink @@ -972,7 +972,7 @@ Dit betekend een fee van minimaal %1 per kb is noodzakelijk. Dit betekent dat een vergoeding van ten minste 2% is vereist. -Bedragen onder 0.546 keer het minimum vergoeding worden weergegeven als DUST. +Bedrapink onder 0.546 keer het minimum vergoeding worden weergegeven als DUST. @@ -1099,7 +1099,7 @@ Dit betekend dat een fee van %2 is vereist. Set language, for example "de_DE" (default: system locale) - Stel taal in, bijvoorbeeld "de_DE" (standaard: systeeminstellingen) + Stel taal in, bijvoorbeeld "de_DE" (standaard: systeeminstellinpink) @@ -1127,7 +1127,7 @@ Dit betekend dat een fee van %2 is vereist. Optional transaction fee per kB that helps make sure your transactions are processed quickly. Most transactions are 1 kB. Fee 0.01 recommended. - Optioneel transactiekost per kB dat helpt ervoor zorgen dat uw transacties snel worden verwerkt. De meeste transacties zijn 1 kB. Fee 0.01 aanbevolen. + Optioneel transactiekosten per kB dat helpt ervoor zorpink dat uw transacties worden snel verwerkt. De meeste transacties zijn 1 kB. Fee 0.01 aanbevolen. @@ -1147,7 +1147,7 @@ Dit betekend dat een fee van %2 is vereist. Automatically start Pinkcoin after logging in to the system. - Automatisch starten van Pinkcoin na inloggen van het systeem. + Automatisch starten van Pinkcoin na inlogpink van het systeem. @@ -1462,7 +1462,7 @@ Dit betekend dat een fee van %2 is vereist. PNG Images (*.png) - PNG Afbeeldingen (*.png) + PNG Afbeeldinpink (*.png) @@ -1554,7 +1554,7 @@ Dit betekend dat een fee van %2 is vereist. Show the Pinkcoin-Qt help message to get a list with possible Pinkcoin command-line options. - Laat het Pinkcoin-QT help bericht zien om een lijst te krijgen met mogelijke Pinkcoin command-regel opties. + Laat het Pinkcoin-QT help bericht zien om een lijst te krijpink met mogelijke Pinkcoin command-regel opties. @@ -1708,7 +1708,7 @@ Dit betekend dat een fee van %2 is vereist. Change - Wijzigen + Wijzipink @@ -1728,7 +1728,7 @@ Dit betekend dat een fee van %2 is vereist. Remove all transaction fields - Verwijder alles uit de transactievelden + Verwijder alles in de invulvelden @@ -1892,7 +1892,7 @@ Dit betekend dat een fee van %2 is vereist. Enter a label for this address to add it to your address book - Vul een label in voor dit adres om het toe te voegen aan uw adresboek + Vul een label in voor dit adres om het toe te voepink aan uw adresboek @@ -1940,7 +1940,7 @@ Dit betekend dat een fee van %2 is vereist. Signatures - Sign / Verify a Message - Handtekeningen - Onderteken een bericht / Verifiëer een handtekening + Handtekeninpink - Onderteken een bericht / Verifiëer een handtekening @@ -2145,7 +2145,7 @@ Dit betekend dat een fee van %2 is vereist. %1 confirmations - %1 bevestigingen + %1 bevestiginpink @@ -2189,7 +2189,7 @@ Dit betekend dat een fee van %2 is vereist. own address - eigen adres + eipink adres @@ -2337,7 +2337,7 @@ Dit betekend dat een fee van %2 is vereist. Confirmed (%1 confirmations) - Bevestigd (%1 bevestigingen) + Bevestigd (%1 bevestiginpink) @@ -2357,7 +2357,7 @@ Dit betekend dat een fee van %2 is vereist. Confirming (%1 of %2 recommended confirmations) - Bevestigen.. (%1 van de %2 bevestigingen) + Bevestipink.. (%1 van de %2 bevestiginpink) @@ -2372,7 +2372,7 @@ Dit betekend dat een fee van %2 is vereist. This block was not received by any other nodes and will probably not be accepted! - Dit blok is niet ontvangen bij andere nodes en zal waarschijnlijk niet worden geaccepteerd! + Dit blok is niet ontvanpink bij andere nodes en zal waarschijnlijk niet worden geaccepteerd! @@ -2382,12 +2382,12 @@ Dit betekend dat een fee van %2 is vereist. Received with - Ontvangen met + Ontvanpink met Received from - Ontvangen van + Ontvanpink van @@ -2412,12 +2412,12 @@ Dit betekend dat een fee van %2 is vereist. Transaction status. Hover over this field to show number of confirmations. - Transactiestatus. Houd de muiscursor boven dit veld om het aantal bevestigingen te laten zien. + Transactiestatus. Houd de muiscursor boven dit veld om het aantal bevestiginpink te laten zien. Date and time that the transaction was received. - Datum en tijd waarop deze transactie is ontvangen. + Datum en tijd waarop deze transactie is ontvanpink. @@ -2427,7 +2427,7 @@ Dit betekend dat een fee van %2 is vereist. Destination address of transaction. - Ontvangend adres van transactie. + Ontvanpinkd adres van transactie. @@ -2476,7 +2476,7 @@ Dit betekend dat een fee van %2 is vereist. Received with - Ontvangen met + Ontvanpink met @@ -2677,22 +2677,22 @@ Dit betekend dat een fee van %2 is vereist. Listen for connections on <port> (default: 51717 or testnet: 51977) - Luister voor verbindingen op <poort> (standaard: 51717 of testnet: 51977) + Luister voor verbindinpink op <poort> (standaard: 51717 of testnet: 51977) Maintain at most <n> connections to peers (default: 125) - Onderhoud maximaal <n> verbindingen naar peers (standaard: 125) + Onderhoud maximaal <n> verbindinpink naar peers (standaard: 125) Connect to a node to retrieve peer addresses, and disconnect - Verbind naar een node om adressen van anderen op te halen, en verbreek vervolgens de verbinding + Verbind naar een node om adressen van anderen op te halen, en verbreek vervolpinks de verbinding Specify your own public address - Specificeer uw eigen publieke adres + Specificeer uw eipink publieke adres @@ -2707,12 +2707,12 @@ Dit betekend dat een fee van %2 is vereist. Threshold for disconnecting misbehaving peers (default: 100) - Drempel om verbinding te verbreken met peers die zich misdragen (standaard: 100) + Drempel om verbinding te verbreken naar zich misdrapinkde peers (standaard: 100) Number of seconds to keep misbehaving peers from reconnecting (default: 86400) - Aantal seconden dat zich misdragende peers niet opnieuw mogen verbinden (standaard: 86400) + Aantal seconden dat zich misdrapinkde peers niet opnieuw mopink verbinden (standaard: 86400) @@ -2732,7 +2732,7 @@ Dit betekend dat een fee van %2 is vereist. Error: This transaction requires a transaction fee of at least %s because of its amount, complexity, or use of recently received funds - Fout: Deze transactie vereist een transactie vergoeding van ten minste %s vanwege de hoeveelheid, complexiteit, of het gebruik van recent ontvangen gelden + Fout: Deze transactie vereist een transactie vergoeding van ten minste %s vanwege de hoeveelheid, complexiteit, of het gebruik van recent ontvanpink gelden @@ -2777,7 +2777,7 @@ Dit betekend dat een fee van %2 is vereist. Accept connections from outside (default: 1 if no -proxy or -connect) - Accepteer verbindingen van buitenaf (standaard: 1 als geen -proxy of -connect is opgegeven) + Accepteer verbindinpink van buitenaf (standaard: 1 als geen -proxy of -connect is opgegeven) @@ -2787,7 +2787,7 @@ Dit betekend dat een fee van %2 is vereist. Error initializing database environment %s! To recover, BACKUP THAT DIRECTORY, then remove everything from it except for wallet.dat. - Fout bij het ​​initialiseren van de database omgeving %s! Om te herstellen, maak een BACKUP van die directory, verwijder dan alles uit die directory, BEHALVE wallet.dat. + Fout bij het ​​initialiseren van de database omgeving %s! Om te herstellen, BACKUP die directory, verwijder dan alles van behalve het wallet.dat. @@ -2812,7 +2812,7 @@ Dit betekend dat een fee van %2 is vereist. Warning: wallet.dat corrupt, data salvaged! Original wallet.dat saved as wallet.{timestamp}.bak in %s; if your balance or transactions are incorrect you should restore from a backup. - Waarschuwing: wallet.dat is corrupt, data is veiliggesteld! Originele wallet.dat is opgeslagen als wallet.{tijdstip}.bak in %s; als uw balans of transacties incorrect zijn dient u een backup terug te zetten. + Waarschuwing: wallet.dat is corrupt, data is veiliggesteld! Originele wallet.dat is opgeslapink als wallet.{tijdstip}.bak in %s; als uw balans of transacties incorrect zijn dient u een backup terug te zetten. @@ -2832,7 +2832,7 @@ Dit betekend dat een fee van %2 is vereist. Discover own IP address (default: 1 when listening and no -externalip) - Ontdek eigen IP-adres (standaard: 1 als er wordt geluisterd en geen -externalip is opgegeven) + Ontdek eipink IP-adres (standaard: 1 als er wordt geluisterd en geen -externalip is opgegeven) @@ -2949,12 +2949,12 @@ Dit betekend dat een fee van %2 is vereist. Use proxy to reach tor hidden services (default: same as -proxy) - Gebruik proxy om tor verborgen diensten te bereiken (standaard: zelfde als -proxy) + Gebruik proxy tor verborpink diensten (standaard: zelfde als -proxy) Username for JSON-RPC connections - Gebruikersnaam voor JSON-RPC-verbindingen + Gebruikersnaam voor JSON-RPC-verbindinpink @@ -2964,7 +2964,7 @@ Dit betekend dat een fee van %2 is vereist. WARNING: syncronized checkpoint violation detected, but skipped! - WAARSCHUWING: gesynchroniseerd checkpoint overtreding is geconstateerd, maar overgeslagen! + WAARSCHUWING: gesynchroniseerd checkpoint overtreding is geconstateerd, maar overgeslapink! @@ -2984,7 +2984,7 @@ Dit betekend dat een fee van %2 is vereist. Password for JSON-RPC connections - Wachtwoord voor JSON-RPC-verbindingen + Wachtwoord voor JSON-RPC-verbindinpink @@ -3001,12 +3001,12 @@ for example: alertnotify=echo %%s | mail -s "Pinkcoin Alert" admin@foo %s, u moet een rpcpassword instellen in het configuratiebestand: %s -Het wordt aanbevolen het volgende willekeurig wachtwoord te gebruiken: +Het wordt aanbevolen de volpinkde willekeurig wachtwoord gebruiken: rpcuser = pinkcoinrpc rpcpassword = %s (je hoeft niet dit wachtwoord te onthouden) De gebruikersnaam en het wachtwoord MAG NIET hetzelfde zijn. -Als het bestand niet bestaat, maakt u met leesbare-alleen-eigenaar bestandsbeheermachtigingen. +Als het bestand niet bestaat, maakt u met leesbare-alleen-eigenaar bestandsbeheermachtiginpink. Het wordt ook aanbevolen om alertnotify instellen zodat u een melding van problemen; bijvoorbeeld: alertnotify = echo %%s | mail -s "Pinkcoin Alert" admin@foo.com @@ -3023,12 +3023,12 @@ bijvoorbeeld: alertnotify = echo %%s | mail -s "Pinkcoin Alert" admin@ When creating transactions, ignore inputs with value less than this (default: 0.01) - Bij het maken van transacties, negeer inputs met waarde minder dan dit (standaard: 0,01) + Bij het maken van transacties, negeer inganpink met waarde minder dan dit (standaard: 0,01) Allow JSON-RPC connections from specified IP address - Sta JSON-RPC verbindingen van opgegeven IP-adres toe + Sta JSON-RPC verbindinpink van opgegeven IP-adres toe @@ -3038,12 +3038,12 @@ bijvoorbeeld: alertnotify = echo %%s | mail -s "Pinkcoin Alert" admin@ Execute command when the best block changes (%s in cmd is replaced by block hash) - Voer commando uit zodra het beste blok verandert (%s in cmd wordt vervangen door blockhash) + Voer commando uit zodra het beste blok verandert (%s in cmd wordt vervanpink door blockhash) Execute command when a wallet transaction changes (%s in cmd is replaced by TxID) - Voer opdracht uit zodra een portemonneetransactie verandert (%s in cmd wordt vervangen door TxID) + Voer opdracht uit zodra een portemonneetransactie verandert (%s in cmd wordt vervanpink door TxID) @@ -3058,7 +3058,7 @@ bijvoorbeeld: alertnotify = echo %%s | mail -s "Pinkcoin Alert" admin@ Execute command when a relevant alert is received (%s in cmd is replaced by message) - Voer opdracht uit zodra een relevante waarschuwing wordt ontvangen (%s in cmd wordt vervangen door bericht) + Voer opdracht uit zodra een relevante waarschuwing wordt ontvanpink (%s in cmd wordt vervanpink door bericht) @@ -3093,7 +3093,7 @@ bijvoorbeeld: alertnotify = echo %%s | mail -s "Pinkcoin Alert" admin@ Use OpenSSL (https) for JSON-RPC connections - Gebruik OpenSSL (https) voor JSON-RPC-verbindingen + Gebruik OpenSSL (https) voor JSON-RPC-verbindinpink @@ -3133,7 +3133,7 @@ bijvoorbeeld: alertnotify = echo %%s | mail -s "Pinkcoin Alert" admin@ Cannot obtain a lock on data directory %s. Pinkcoin is probably already running. - Kan een slot op data directory %s niet verkrijgen. Pinkcoin wordt waarschijnlijk al uitgevoerd. + Kan een slot op data directory %s niet verkrijpink. Pinkcoin wordt waarschijnlijk al uitgevoerd. @@ -3253,7 +3253,7 @@ bijvoorbeeld: alertnotify = echo %%s | mail -s "Pinkcoin Alert" admin@ Fee per KB to add to transactions you send - Vergoeding per KB toegevoegd aan de transacties die u verzendt + Vergoeding per KB toe te voepink aan de transacties die u verzendt diff --git a/src/qt/overviewpage.cpp b/src/qt/overviewpage.cpp index acf86e0..0a40732 100644 --- a/src/qt/overviewpage.cpp +++ b/src/qt/overviewpage.cpp @@ -114,7 +114,7 @@ class TxViewDelegate : public QAbstractItemDelegate OverviewPage::OverviewPage(QWidget *parent) : QWidget(parent), ui(new Ui::OverviewPage), - currentBalance(-1), + currentBalance(0), currentStake(0), currentUnconfirmedBalance(-1), currentConfirmingBalance(-1), @@ -124,10 +124,11 @@ OverviewPage::OverviewPage(QWidget *parent) : { ui->setupUi(this); + txdelegate->fontID = -1; - QFont overviewHeaders("Ubuntu", 10, QFont::Normal); - QFont overviewSpend("Ubuntu", 20, QFont::Normal); + QFont overviewHeaders("Ubuntu", 14, QFont::Normal); + QFont overviewSpend("Ubuntu", 18, QFont::Normal); QFont overviewBalances("Ubuntu", 14, QFont::Normal); ui->label->setFont(overviewHeaders); @@ -137,15 +138,15 @@ OverviewPage::OverviewPage(QWidget *parent) : ui->labelImmatureText->setFont(overviewHeaders); ui->labelTotalText->setFont(overviewHeaders); - ui->labelBalance->setFont(overviewBalances); + ui->labelBalance->setFont(overviewSpend); ui->labelBalance->setContentsMargins(0,0,0,5); - ui->labelStake->setFont(overviewBalances); + ui->labelStake->setFont(overviewSpend); ui->labelStake->setContentsMargins(0,0,0,5); ui->labelImmature->setFont(overviewBalances); ui->labelImmature->setContentsMargins(0,0,0,5); ui->labelUnconfirmed->setFont(overviewBalances); ui->labelUnconfirmed->setContentsMargins(0,0,0,5); - ui->labelTotal->setFont(overviewBalances); + ui->labelTotal->setFont(overviewSpend); ui->labelTotal->setContentsMargins(0,0,0,5); ui->labelBtcValue->setFont(overviewBalances); ui->labelBtcValue->setContentsMargins(0,0,0,5); @@ -169,6 +170,8 @@ OverviewPage::OverviewPage(QWidget *parent) : // start with displaying the "out of sync" warnings showOutOfSyncWarning(true); + + #if QT_VERSION >= 0x050000 // set a timer for price API nLastPrice = 0; @@ -199,18 +202,18 @@ void OverviewPage::setBalance(qint64 balance, qint64 minted, qint64 stake, qint6 currentUnconfirmedBalance = unconfirmedBalance; currentConfirmingBalance = confirmingBalance; currentImmatureBalance = immatureBalance; - ui->labelBalance->setText(BitcoinUnits::formatWithUnit(unit, balance)); - ui->labelTotalMinted->setText(BitcoinUnits::formatWithUnit(unit, minted)); - ui->labelStake->setText(BitcoinUnits::formatWithUnit(unit, stake)); - ui->labelUnconfirmed->setText(BitcoinUnits::formatWithUnit(unit, unconfirmedBalance)); - ui->labelImmature->setText(BitcoinUnits::formatWithUnit(unit, immatureBalance)); - ui->labelTotal->setText(BitcoinUnits::formatWithUnit(unit, balance + stake + unconfirmedBalance + immatureBalance)); + ui->labelBalance->setText(BitcoinUnits::formatWithUnit(unit, balance, false, 2)); + ui->labelTotalMinted->setText(BitcoinUnits::formatWithUnit(unit, minted, false, 2)); + ui->labelStake->setText(BitcoinUnits::formatWithUnit(unit, stake, false, 2)); + ui->labelUnconfirmed->setText(BitcoinUnits::formatWithUnit(unit, unconfirmedBalance, false, 2)); + ui->labelImmature->setText(BitcoinUnits::formatWithUnit(unit, immatureBalance, false, 2)); + ui->labelTotal->setText(BitcoinUnits::formatWithUnit(unit, balance + stake + unconfirmedBalance + immatureBalance, false, 2)); if (confirmingBalance > unconfirmedBalance) { ui->label_3->setText("Confirming"); - ui->labelUnconfirmed->setText(BitcoinUnits::formatWithUnit(unit, confirmingBalance)); + ui->labelUnconfirmed->setText(BitcoinUnits::formatWithUnit(unit, confirmingBalance, false, 2)); } else { if (ui->label_3->text() != "Unconfirmed") ui->label_3->setText("Unconfirmed"); @@ -264,6 +267,7 @@ void OverviewPage::setModel(WalletModel *model) // update the display unit, to not use the default ("BTC") updateDisplayUnit(); + } void OverviewPage::updateDisplayUnit() diff --git a/src/qt/res/icons/address-book.png b/src/qt/res/icons/address-book.png index d41dbe6539f64829c004d0f7fc9bf0ba1aa4d7df..e654dd3bc237a97789a8c310c04f28e76a985d84 100644 GIT binary patch literal 6850 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 delta 1911 zcmV--2Z;E>HT(`PiBL{Q4GJ0x0000DNk~Le0000W0000W2nGNE0CReJ^Z)<=0drDE zLIAGL9O;oE9DfTF000XU0RWnu7ytkO2XskIMF-mp8VLp+#?&x&000L3NklvU_$nm)#_g5FjCv8xRAjm=Kt%U`n`X6>G;z8EhHxGE|F9Ne9P{7kbh9 z!S+M7Us|ivViDR-0wc(vnIa0sAtaEHkPAr`awW;`CV$!N+1+!_d-{RcN(Cv323fjSr6Fyk{lzZ+~L5ljL<@y#h9*?VCPx#S;&_@~fwA zk(UHJ>1^nvaPxYt@TRrTE2!ny55TfNJ9M4&;zd7u=DCVoaPZJWr7Q^f=?+F%@Po&) zGZXH33CQ|t6fkX4KUlQk*;hAyFW;NOP$)_yZhy0R<9yQFn(0sWQugqcJ5rUoKLI>n z4nPv%G(nL;kw6H%2Xf|ZcwzmE58gJDaor>wjxjNzlj@tomIw2&PMl^mKbOL#n;!Kr z?O{H3m%f++pSp^^4^kaPcP@RUYD;N`VZnvr2&zNDv}`Vnj8RgY$M+XyFxb$7yJ9h! zvwyzxj05Mg>#zkj7#6OiuWf(s`L!#OWiMxY!w4jzF@dVe*fs>lBCK0i#+sQP&UKt) z#{G9?q$jU_QAW!BasawX^1-6YC#%-}u%v7n9lbibZV`|Vc)|R<5^R@zs@-@kB0|t1jbAM9YwKJD5yLZ)VYu3;Abo5z-f-&NTP27|) zgp6TD$sjB4U&ZVWLfxezLQZnYC$D^2vO;nbcmEb~iE1axr3## zdoHc*Cm9X)lHi+3I2OU{R*{ojga$|X^Lyv$s69phV9kdDQ3IU$j1PqTAN|EM5@2`X zPubzj;&2~06@g)zI5ibTmVYtg7Lsiv*#cphxDr(KXau1+$d$cI5aoW z7}V^nr?JjYcf;#VQ9{+gv5P0{KLCbfM}O10^LKBj$8M!|{%PLoJ4o9^KT}e?2w@Wn z>L`kYBukj4MUqcLRV19UjVhVA5|f#hna5yH6Y*FC6Zp7$Kd1VK>3=#@Jv3^!S5Hbm zdf6-xi0I((dt3YW>^>bnRLYS*X;k-AVJYKiZYM5}1Je{}nnF^th8Z)^GzqsuCKit) zgh9siS@@Et5a{k8v95zN?-+C*I%fC-@74nQ0RQKvp^4}@cY5!SICVUjf=sE8+CQwx6l^$pMda>S$Y`{sU9E1$%@RS@bA6OUW?d~RGW6_-=R z63`d2IqwfLw!e+{j}LJ+MI)3MruogE_l)$Ocn$aiFmPFey?-14pk$?0yt#0F)w;x? zgS;H-CH2KEsKsSSwv9abZd>;V?Faq*<5++;)n;_6#mLxsMw;sM3rCK2>Cwi$0(%G0 zctwZ50sso0?EJiM*W}*)NJ+``3JOQdSg>g?Q{5U32RdnN33GNV!hjkkYz#BpaVpl= za=34_)8A?nsDC#R^}q?B`(i_RjQ{`+63dsY*z!(d!OGOe{wLCFFcUk7MYI3_002ovPDHLkV1lq~iTwZo diff --git a/src/qt/res/icons/address-book_s.png b/src/qt/res/icons/address-book_s.png new file mode 100644 index 0000000000000000000000000000000000000000..4432d7c9d10a6f89bf2cfb8148162c8ef870b90a GIT binary patch literal 7259 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 M)HT+r*K&^iKeubY`Tzg` literal 0 HcmV?d00001 diff --git a/src/qt/res/icons/bitcoin.icns b/src/qt/res/icons/bitcoin.icns new file mode 100644 index 0000000000000000000000000000000000000000..1b2ecda122ec0cc3a955e2e0a8852c238706974f GIT binary patch literal 68186 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 ZE7&&*bn{3qv{(oVK2KLamvv4FO#mHeu3!KF literal 0 HcmV?d00001 diff --git a/src/qt/res/icons/close_s.png b/src/qt/res/icons/close_s.png new file mode 100644 index 0000000000000000000000000000000000000000..387d17f0deaa906c972a88b12e2464eb67acf0b3 GIT binary patch literal 429 zcmV;e0aE^nP)F6XU=$1{z{bqR%*cc+!p+7-HPh8Z zln$q@*^#hFNk|SNl4KlqDQ{P&MBCV??qGTwgvm|Vyim*bWaag;1g*cB$ zfR;Ocjm$(^@c7dUJqZm3K^Y-V0e?+b9}Q6BLEm=YIM1?bMSC1a&bJZ$X}AVx>bi zauRY?wLA3S)Z1_GsbGPtitPlSdIkoDKmYz#?(F>e=a-s@k^l#vrJT`%bF1-aWFaZB z{`~W+WP8i1%Uf1m-onDf?4joH=igtdWd&<_QzI!IAIEMgao= X1JqTwu4+w}00000NkvXXu0mjfBs8oo literal 0 HcmV?d00001 diff --git a/src/qt/res/icons/history.png b/src/qt/res/icons/history.png index 10ac0e159228d08a8b4425dec4559f19583db936..9d6f70cdbdb96670fd05d5fcbbbaa565cf1c92eb 100644 GIT binary patch literal 2376 zcma);i#yYc1IE9*vW>M^ZZTGe+(i-xnz`55+-qq zB$thbv2ZH273Eeo5n9@oeutH@)A@Lv2iz(*5lfCKlT> zTXpyk@?9gJ{TO(Zzt3Jk^>3=W>Ms8<2%2w58~~sn|65S06?*dzsTNP#=cP6c#lfu1 zmI>ik06_gUX|Kn@#EH)pAI}eaWBZ$;2mP;_Jr2pkhb{DF+*+opRBkMHaywC-$xMxl z8a&`OlzMD{=;U~|2J=qj@-yOUgKzTrDQ?nNM}Vk~&&K>ma4sD*qg}G3%K+tz&)a|q zh$3&*4Nz?6Q2_yn3zZ{z(y~va-){JiFS)s~C!p&KShhhw=1jy8%1<$lrF+w2bsUr* zI!0QaSj}aYJ4jg#MrZ79UH#loo`B7*^M!7oOf_|eR}5NG8e59@eQ-$% z2Mx8P-_q0=fzTc=q~{N?gQjMihm~Ep#|Zq!6}wj_8Wif&+4gj*GORm~(`SGv)f$nNz z@Ysz&^K7HL?9I9OC+drx1^DnUDTO5|fcAxhmxPf`D$G$S`+Env)5Vr<6s#n}SErWP}N7&Kw8R>o- z9;{wOv1Jt=%BI;(JVdDi$J2(Jep*ByO&r4KEZqQy)R9#;?VC8h&7B{w1(w!7~3leJk2HC0V)46WCa|ZbV3jIA`53NuF|6S4C;{TAY~YF-=RLta9Mn4YYLd3eqX*!q?MinW%%8|9N5w21E*HG; zgFlg9t7Ec+I}OeiPKGH;qO=$7i@tTphl+jnnv&iTThR^?kBnxfd zULf_<+luj_9z?ZM-_KuP>xotcaMIB{n^UPkIjw(7J%=w^Go|46SR&G?uH?xUD` z0+8f4Ww%j;e7^&uISsdBKIcu6FbQp!AGsVeBm*HdHak2_&9fjOs;m(>3ddS`Wla_E^ig;RuugAMg#C8gEzrJU z>1*!bVsA9K(LBCrORi7r`W}wf!_)-G>ymj;A4}*;ZLpb5w29RMD=s&t@bHre&G>vz zPpil&h7~jweoZSakUv0ut8zUp)inE6mB!Degn76HqA6P7v1~hJ+lBPfM$rlI%J?Ay zH9vg**qXi676JDA@-3{tQ~RW{`R7cZXc0v8ZOMS68&vFr zG)@}byo|IdXCgDeNYR!Vi=`ohb=sd-1{qFNj2sTaUQ+|eN-*6Rq-0D#HR0*zbc+SS z@|GN?dUxywN{-PpnpgD(^K4U&va2@!GY9^No_Z?evU|u@Xd%|stXEzTgZHX-6V{9R zbhD>2%R5>QSyMS7#B!{p@433P&otLNDdRYDP>1*`w_lqd9a$uPCP97ydR{rRr_HkF zrbV!^IavF`MrrSJEnM$&HEvcD-q*^R^<^|s+A-30H8qEcqgs$pS8oR?H6pY*zfcEh zUq|f5o(6MdPOv4Nw3oi+Xxt&}#Iz`eKiYlB&yw!Uk?nA*ic22OVnKy-%+nzL$u|`* zQH#9MrSbR7gjh(owe>x-2fftb>0kr@L3nhig=0p<^=LF~6zU|_O>1?Xcmr!iRQ*qp z1mr^`diN1SN6gRW5ksnkH+o&3b{~kz(rgH61>T#CQxV4g%eUF`-I2#f>(xb9EC1}Z z+iZNFSW^Mi|$SiFtesbhtF$4H;4UnJqRGm>6~szM(B1eF(nea9p{ z^B6(UxAxM;UE%}0Ko`Q>+4-5Md_E6Ve@aZnAFkdPdK*YEr|TOeBGz-f$i@`oQyrr{ z$Ca81u&hANZj|-v!py^qRoRP9~v3g~^j;EV;jLYtB#1e77y%qoUT3~9v=@MevUY^K}KKkSH03@$~z4wWf%zprQ C#8ImN literal 1432 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 literal 0 HcmV?d00001 diff --git a/src/qt/res/icons/max.png b/src/qt/res/icons/max.png new file mode 100644 index 0000000000000000000000000000000000000000..455be1ea14c5cb7904ce208cd2cf6b982a899b1a GIT binary patch literal 642 zcmV-|0)737P)WFU8GbZ8()Nlj2>E@cM*00HJnL_t(o!|j)`it{wWyC^qm`f*MiCodz$PFX(A+y)Z7}Tq z?uO037Mp=Um<*XO_nw^LG5~}ZhJ+VK2=Hu$GOa3YMwVyM^a$Y!(9Gz|cd z&*#za_gx?W*zI;0kH;V)NRq#w>#0bZ&E~fSS1OeV0BM>=r_+guh(@E)&qSEZ2yM-i4a2yAY48uU7Q1HM!hAhiiuh+ht0{{!p1tCBP c@aF;E0G4Pz|C#zr=l}o!07*qoM6N<$f}{)(OaK4? literal 0 HcmV?d00001 diff --git a/src/qt/res/icons/message.png b/src/qt/res/icons/message.png new file mode 100644 index 0000000000000000000000000000000000000000..5c745e01e8caf64651df1976ebf87e9d968588a4 GIT binary patch literal 3206 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 literal 0 HcmV?d00001 diff --git a/src/qt/res/icons/message_s.png b/src/qt/res/icons/message_s.png new file mode 100644 index 0000000000000000000000000000000000000000..6b577a7f807c730409b548bf840660e52d720e5d GIT binary patch literal 3324 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 literal 0 HcmV?d00001 diff --git a/src/qt/res/icons/min_s.png b/src/qt/res/icons/min_s.png new file mode 100644 index 0000000000000000000000000000000000000000..42316343d511c7619b0841923a19fd47864f387a GIT binary patch literal 256 zcmeAS@N?(olHy`uVBq!ia0vp^3LwnE1SJ1Ryj={WI14-?iy0WWg+Z8+Vb&Z8pdfpR zr>`sfLl!wUY1vuk_EJD0+02lL66gHf+|;}hAeVu`xhOTUBsE2$JhLQ2!QIn0AVn{g z9VlMr>EamTaXdLef^~6%NKca>gG6WGk&~wuYOOhNO@FdUUj?2zopr06uwE6#xJL literal 0 HcmV?d00001 diff --git a/src/qt/res/icons/overview.png b/src/qt/res/icons/overview.png index ee2511f01d0d76a60cd9e7febc4c9218f38e3683..0411ee11616d0cef346f329a8fe962eb67a280a7 100644 GIT binary patch delta 2476 zcmaJ@X*Ao39{ndmlM*EMScX_?YH1a*lv+Y#X;rF9YaL7Ndr1xEAJdGgqN=ng!r-Z) zB-0{FHO-8%)K;Z}mRP2-x0c41#_Kun!+d$~-E+@9_uTvG_vLpk)tn=hr*Y3f51fUm z2y3f+k!tP*07R6doz0~ilWRURZtveISdL`*$exrxbjZf%%$vGQx=a?k93IvVZr9wu zwOu)26m1bVSF|f968XSKf@S*0vQjq1HRB3NRHm!G_(zj0rM20K{zU8J-`pjkl<*M1*Mi_aM}@$9AE|9 z5aWD*7mwn^`=?uiQcQIf&`)R=%8U|xsJ1Zw3oOFvu0wYVG*+IjoxPNP4<5VWDI9xC z1hm77g)$Id$=TguKfXjN2lBQb0V_pVpL!OT;xL})4a#`PL= z^b3EH(!(n472cO?1yZ3L$jm1pwpQ=-h)w_0f^yxOGs-DeM%o|n|3!lqh+vA#a17j;JHw+2 zRwd~5Vm`r$=d%wS*@iSi7=tTM;^m7z=Ru7c0G;cDXdcrCbEtXO!>B(D?a=0yWsnoi zos0{@BooF5eFd-IG<37aKl{J>T7TF8$wq1xH452*z+%HscjLp z>+KE@3`-4}O2(>>CuI3+n4Jh(=iheA5ZX}&7le!&{M%O2aT;O@2(hq+Ef#jDeIXu} zte7IOmsE{+ETkY!^`uXW*R3q+z>C|A@xEMrKaah( zV3qm~Unh`5lRi6mRPl25s8qgA`%zfWgr^DHA0Lu8on5KmjXjp6#xb|W+z?W8BY}^= z!;F!RrPTDEu02yNlyuvW7Jqt1Rk{clTGVPm>ia~uA;hr`b3#V`FpxhgEweeC1jNJEt3uSrkuMJYP=w^JPp`&vM5`J4spX z^=_WV>Fcme$LDwxB|AgROz!9&D3#K0=GjaigJp(N5~XV<&v$-je(QJ%ad|UKB-SH%6Av$CaCi`_Y#ruR8_TX5}r>+U#-FLn4n-`UqQzmnLO ztZa|?F+J)_LlmBQ%t#>H6tXnx(NWCJ1-6_X$DI4*@Bk6_Ac3oS(_V9AK=hI4B5y#x#WvY}7oVnFU zDdS>fzIe-2tcUx5yI;OSd+?n0-YLO#DyK~Jgx-X^b6Z<)eC$M6R`5!odxb}M{nhgH z$UeCH)5!Y?D%7T<0n%SkhWslmwzCZ|G`%^nI6JsRB(#0KS_crj27*uV>oygd`_8*< zf+bML@i**}BfY}!3&6X`D;6EY^sr zf-cD5bL}B%A=}TYU_H*L{1=l-w;Ag^2TTB?Ci%&9nown_`I0H*U*D50lUnQ)$7Drt zmB3GEE|T(|r=QhbpQ?VH2;rD#HorpKq89Z*k?<0w5+i2xqfC_AC59ktPVIFAi?A5J z$QAVfMOStGh{$t#Z*e++_919(aQ|`}d1-bJYwJEdx$!s`=Zpy;6{?%A8Tu$e`*xI# z3##hMfS&?1C6^Cp)X$L`G0^AbM^0{=!7OZxE^?>n?ozh8)%3mS3jiOtO{vG>N%g&NrK@ozs{4*)+N zROj--mS0I8mVP+Hf_2{v44Bhrty|jDC2OcqU+0UDd-s4d!tZa!UhG~i%=UHub2P|! zIJ#e@*(r!yM<~3#Xub{sa4Ybm*207+Lk;VkIMwGWK}5qKLY+^|F0WR zM?)w&Hh>=5%5(2u18Q zmqc_ZeR1AAyZLV2wKk*|o-Eb{B@nc6d5ql8{Rh@O0T}AQTMKNbPBex*@z(5bvGuW| z7tf1iedv@3-jP_PXV9`HYvCy{NY{fKgwP2rkpOS^TUE7KR#IP(m9SE33xj8g=GJb@pGk{u71fkYBw6lXlXPpDHTKT(&jeB{;3rak<< zN-5SeHH&s-TPlQ4oJuA4C+|&lylI7}a2hK-`LtR!&fyAVsx#}f5#LZ?VN0i7)0@9g zX5u-m%?h$w4_zeXyDdtE21+}3ab4H!{_6(9{*zK9K3k2w_-!Ikw{HUY21k1ryGC38 GpZ^WkL3(ij delta 7439 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 diff --git a/src/qt/res/icons/overview_s.png b/src/qt/res/icons/overview_s.png new file mode 100644 index 0000000000000000000000000000000000000000..62ad9baf3df501de75b3f70549267bc3d5c3a6d6 GIT binary patch literal 2635 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 ef5X;Q53sX#w0dmenfyQPzL)|4 literal 0 HcmV?d00001 diff --git a/src/qt/res/icons/receive.png b/src/qt/res/icons/receive.png index 53ad1d1565e74c0f4895b7fbf525dbd58bb663d2..32062e2f2a46a432285b77e4ed4f9f4a6d82e02e 100644 GIT binary patch literal 2832 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 literal 1487 zcmV;=1u*)FP)>3pDMXV*lVvtf2(-?_T5=q)L+C+oIfS}RVMdK^tBQ-WO zji^|W67W$=Ynl>UTWYimVz3mo7`ruFNz^E&m6!O~?sf0Z%sJ=RDSKf9{IQE};~(uw zzB%9d=9f92%=w+1j1m#P%%Oq*Z2)_8puV=YVSs@ExqyP90$T9$2sJmB#NLa@t9T$t zA;1fVpZ!oq7|bNQafDw$fJhx%k%x}9mgI^#7oI-PySAM(jS7a|>_4`4?Sj4prx3a|>G4xkXk!=7Fbg;_j* z3Y-6MDKloBbQvGjpCibW&vgobuaNq0;DVqK00Q6yL>&EYvMWW12ucN>ctbOx3YSlH zoO5hJJ79 zO9!*&<`_`%hyf76<(_(fPGmLCgAGCyz%;xIP#QWM(C`BEWtz*U1!kQD0PENH0PeNp z_yU4PXflCB2ckmeKeO^!r3z^*j^GrzQV4)R5J*$Fbed+tR0Fom?>4^6Q|ouuu<@Fa z0SNTgjVV;jL{_t6)2F=t&x{rYbtm8g3uZI>#MW*9 zV9C|b1KfpH+eQGOOcHCxwU#NDB9hpkm4ZS_L9y^bpQesH^TdRMebS3iF2^iAznSlz z8&j^9d1c35=FfkY5BJtqQ;Js-gkb^1P+Refzqf99p+fG4no0!)L2y~1trBy~k`9_< z7)WzI{#QoFX+?H%mD!U^2N&P?{4N$P`XdMS_Wy*YZ+~VcVCDLo^aK^q;XmYFcVLT_ET<)#;T^0A(eDA{W%+YQL@ z*YU`Q07w&n4?-yP^)s6o+g@SE-#(`Ewr#w=efM7(6E8yO#tSeS00EAESqMV4*@B5! zxo#)RSL|@T2L^slYqE^MzDE5Q1W?jX-|pHoRO4GwyoaYTMgu^A0Xa60^xOM;)0bDT>luSp p_fbuLiIbcle4g?DpVKcL;NROra-e_cBVYgk002ovPDHLkV1h7LxF-Mr diff --git a/src/qt/res/icons/send_s.png b/src/qt/res/icons/send_s.png new file mode 100644 index 0000000000000000000000000000000000000000..c8f6ee221c83545e584765a600086a319d73d37b GIT binary patch literal 3259 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 O10dkd^eb_0;r|1zMe%t6 literal 0 HcmV?d00001 diff --git a/src/qt/res/icons/sidestake.png b/src/qt/res/icons/sidestake.png new file mode 100644 index 0000000000000000000000000000000000000000..704dff66bbce3e74d45fcfc8ba087bd6bf8a9a3b GIT binary patch literal 5381 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 w)}getOptionsModel()->getDisplayUnit(), wtx->credit + wtx->debit); + QString str; + + + if(wtx->type == TransactionRecord::StakeMint) + { + const uint256 txID = wtx->hash; + qint64 nReward = walletModel->getStake(txID); + if (nReward > 0) + str = BitcoinUnits::format(walletModel->getOptionsModel()->getDisplayUnit(), nReward); + else + str = BitcoinUnits::format(walletModel->getOptionsModel()->getDisplayUnit(), wtx->credit + wtx->debit); + } + else + str = BitcoinUnits::format(walletModel->getOptionsModel()->getDisplayUnit(), wtx->credit + wtx->debit); + + if(showUnconfirmed) { if(!wtx->status.countsForBalance) @@ -571,7 +586,19 @@ QVariant TransactionTableModel::data(const QModelIndex &index, int role) const case LabelRole: return walletModel->getAddressTableModel()->labelForAddress(QString::fromStdString(rec->address)); case AmountRole: + { + if (/*!walletModel->isMine(CBitcoinAddress(rec->address)) && */rec->type == TransactionRecord::StakeMint) + { + const uint256 txID = rec->hash; + qint64 nReward = walletModel->getStake(txID); + if (nReward > 0) + return nReward; + else + return rec->credit + rec->debit; + } else { return rec->credit + rec->debit; + } + } case TxIDRole: return QString::fromStdString(rec->getTxID()); case ConfirmedRole: diff --git a/src/qt/walletmodel.cpp b/src/qt/walletmodel.cpp index 0ace2bc..0b1a982 100644 --- a/src/qt/walletmodel.cpp +++ b/src/qt/walletmodel.cpp @@ -60,6 +60,23 @@ qint64 WalletModel::getStake() const return wallet->GetStake(); } +qint64 WalletModel::getStake(const uint256 TxHash) const +{ + int64_t nReward = 0; + uint256 hash = TxHash; + + const CWalletTx& wtx = wallet->mapWallet[hash]; + + if(wtx.IsFromMe()) + return nReward; + + BOOST_FOREACH(const CTxOut& txOut, wtx.vout) + { + nReward += wallet->GetReward(txOut); + } + return nReward; +} + qint64 WalletModel::getImmatureBalance() const { return wallet->GetImmatureBalance(); @@ -130,6 +147,11 @@ void WalletModel::updateAddressBook(const QString &address, const QString &label if(addressTableModel) addressTableModel->updateEntry(address, label, isMine, status); } +void WalletModel::updateAddressBookStake(const QString &address, const QString &label, const QString &percent, int status) +{ + if(addressTableModel) + addressTableModel->updateEntry(address, label, false, status, percent); +} bool WalletModel::validateAddress(const QString &address) { @@ -508,6 +530,17 @@ static void NotifyAddressBookChanged(WalletModel *walletmodel, CWallet *wallet, } } +static void NotifyAddressBookStakeChanged(WalletModel *walletmodel, CWallet *wallet, const CTxDestination &address, const std::string &label, const std::string &percent, ChangeType status) +{ + OutputDebugStringF("NotifyAddressBookChanged %s %s %s status=%i\n", CBitcoinAddress(address).ToString().c_str(), label.c_str(), percent.c_str(), status); + QMetaObject::invokeMethod(walletmodel, "updateAddressBookStake", Qt::QueuedConnection, + Q_ARG(QString, QString::fromStdString(CBitcoinAddress(address).ToString())), + Q_ARG(QString, QString::fromStdString(label)), + Q_ARG(QString, QString::fromStdString(percent)), + Q_ARG(int, status)); + +} + static void NotifyTransactionChanged(WalletModel *walletmodel, CWallet *wallet, const uint256 &hash, ChangeType status) { if (fDebug) @@ -522,6 +555,7 @@ void WalletModel::subscribeToCoreSignals() // Connect signals to wallet wallet->NotifyStatusChanged.connect(boost::bind(&NotifyKeyStoreStatusChanged, this, _1)); wallet->NotifyAddressBookChanged.connect(boost::bind(NotifyAddressBookChanged, this, _1, _2, _3, _4, _5)); + wallet->NotifyAddressBookStakeChanged.connect(boost::bind(NotifyAddressBookStakeChanged, this, _1, _2, _3, _4, _5)); wallet->NotifyTransactionChanged.connect(boost::bind(NotifyTransactionChanged, this, _1, _2, _3)); } @@ -530,6 +564,7 @@ void WalletModel::unsubscribeFromCoreSignals() // Disconnect signals from wallet wallet->NotifyStatusChanged.disconnect(boost::bind(&NotifyKeyStoreStatusChanged, this, _1)); wallet->NotifyAddressBookChanged.disconnect(boost::bind(NotifyAddressBookChanged, this, _1, _2, _3, _4, _5)); + wallet->NotifyAddressBookStakeChanged.disconnect(boost::bind(NotifyAddressBookStakeChanged, this, _1, _2, _3, _4, _5)); wallet->NotifyTransactionChanged.disconnect(boost::bind(NotifyTransactionChanged, this, _1, _2, _3)); } diff --git a/src/qt/walletmodel.h b/src/qt/walletmodel.h index 9951c89..9b30a02 100644 --- a/src/qt/walletmodel.h +++ b/src/qt/walletmodel.h @@ -70,6 +70,7 @@ class WalletModel : public QObject qint64 getBalance() const; qint64 getTotalMinted() const; qint64 getStake() const; + qint64 getStake(const uint256 TxHash) const; qint64 getUnconfirmedBalance() const; qint64 getConfirmingBalance() const; qint64 getImmatureBalance() const; @@ -169,6 +170,7 @@ public slots: void updateTransaction(const QString &hash, int status); /* New, updated or removed address book entry */ void updateAddressBook(const QString &address, const QString &label, bool isMine, int status); + void updateAddressBookStake(const QString &address, const QString &label, const QString &percent, int status); /* Current, immature or unconfirmed balance might have changed - emit 'balanceChanged' if so */ void pollBalanceChanged(); diff --git a/src/rpcnet.cpp b/src/rpcnet.cpp index eb1351a..efa6682 100644 --- a/src/rpcnet.cpp +++ b/src/rpcnet.cpp @@ -67,6 +67,28 @@ Value getpeerinfo(const Array& params, bool fHelp) return ret; } + +Value getnodes(const Array& params, bool fHelp) +{ + if (fHelp || params.size() != 0) + throw runtime_error( + "getnodes\n" + "Returns each connected network node as addnodes in conf friendly format."); + + vector vstats; + CopyNodeStats(vstats); + string pNode = ""; + + BOOST_FOREACH(const CNodeStats& stats, vstats) { + if (stats.addrName.rfind(":9134") != string::npos) + { + string ipAddress = stats.addrName.substr(0, stats.addrName.length() - 5); + pNode += "addnode=" + ipAddress + "\n"; + } + } + + return (Value)pNode; +} // ppcoin: send alert. // There is a known deadlock situation with ThreadMessageHandler diff --git a/src/rpcwallet.cpp b/src/rpcwallet.cpp index f516b35..dd5305c 100644 --- a/src/rpcwallet.cpp +++ b/src/rpcwallet.cpp @@ -5,6 +5,7 @@ #include "wallet.h" #include "walletdb.h" +#include "stakedb.h" #include "bitcoinrpc.h" #include "init.h" #include "base58.h" @@ -2364,3 +2365,153 @@ Value getstakesplitthreshold(const Array& params, bool fHelp) return result; } + +Value addstakeout(const Array ¶ms, bool fHelp) +{ + if (fHelp || params.size() != 3) + throw runtime_error( + "addstakeout
\n" + "Creates a rule to send a portion of your stakes to another address.\n" + "Usage: addstakeout
<% of stake>\n"); + + string name = params[0].get_str(); + + if (name.length() > 100) + { + throw runtime_error("Please use a shorter name for this address"); + } + + string a = params[1].get_str(); + CBitcoinAddress address(a); + if (!address.IsValid()) + { + throw runtime_error("Please enter a valid Pinkcoin address."); + } + + string sPercent = params[2].get_str(); + string sStack = ""; + for (unsigned int i = 0; i < sPercent.length(); i++) sStack += isdigit(sPercent[i]) ? sPercent[i] : (char)NULL; + + if (sPercent != sStack) + throw runtime_error("Please only use whole numbers between 0 and 100 and no special characters for Percentage\n"); + + + + int nPercent = stoi(sPercent); + + + if (nPercent < 0 || nPercent > 100) + { + throw runtime_error("Please use a percentage between 0 and 100"); + } + + CStakeDB stakeDB(pstakeDB->strWalletFile); + CTxDestination addr = address.Get(); + + int percentAvailable = 100; + + BOOST_FOREACH(CWallet::mapAddress mapPercent, pstakeDB->mapAddressPercent) + { + string percent = mapPercent.second; + percentAvailable -= stoi(percent); + } + + int updatingPercent = 0; + if (pstakeDB->mapAddressPercent.find(addr) != pstakeDB->mapAddressPercent.end()) + updatingPercent = stoi(pstakeDB->mapAddressPercent[addr]); + + + if (nPercent > (percentAvailable + updatingPercent)) + throw runtime_error("Stake Percentage would increase total Stakeout over 100%\n" + "Please Reduce Stakeout Percentage or Delete another Stakeout to make room.\n" + "Current Available Stakeout Percentage: " + to_string(percentAvailable)); + + if (!stakeDB.WriteStake(a, name, sPercent)) + throw runtime_error("Failed to save stake information, please debug."); + + pstakeDB->mapAddressBook[addr] = name; + pstakeDB->mapAddressPercent[addr] = sPercent; + + string success = "\n Successfully written " + name + ", Pinkcoin Address:" + a + " side-stake " + params[2].get_str() + "% to stake.dat!"; + return success; + +} + +Value delstakeout(const Array ¶ms, bool fHelp) +{ + if (fHelp || params.size() != 1) + throw runtime_error( + "delstakeout
\n" + "Deletes stakeout address from stake database.\n"); + + string a = params[0].get_str(); + CBitcoinAddress address(a); + + if (!address.IsValid()) + throw runtime_error("Invalid address"); + + if (pstakeDB->mapAddressBook.find(address.Get()) == pstakeDB->mapAddressBook.end()) + throw runtime_error("Address not in stake database"); + + string xName = pstakeDB->mapAddressBook[address.Get()]; + string xPercent= pstakeDB->mapAddressPercent[address.Get()]; + + CStakeDB stakeDB(pstakeDB->strWalletFile); + + if (!stakeDB.EraseStake(a)) + throw runtime_error("Failed to erase stake. Please debug."); + + pstakeDB->mapAddressBook.erase(address.Get()); + pstakeDB->mapAddressPercent.erase(address.Get()); + + + string success = "\n Successfully deleted " + xName + ", Pinkcoin Address:" + a + " side-stake " + xPercent + "% from stake.dat."; + + return success; +} + +Value liststakeout(const Array ¶ms, bool fHelp) +{ + if (fHelp || params.size() != 0) + throw runtime_error( + "liststakeout\n" + "Returns the current Stakeout entries in stake database.\n"); + + Array stakeOut; + BOOST_FOREACH(CWallet::mapAddress address, pstakeDB->mapAddressBook) + { + Object addressInfo; + LOCK(pstakeDB->cs_wallet); + { + if(pstakeDB->mapAddressBook.find(CBitcoinAddress(address.first).Get()) != pstakeDB->mapAddressBook.end()) + { + + string aName = pstakeDB->mapAddressBook[CBitcoinAddress(address.first).Get()]; + string aPercent = pstakeDB->mapAddressPercent[CBitcoinAddress(address.first).Get()]; + + aPercent = aPercent + "%"; + + addressInfo.push_back(Pair("Name: ", aName)); + addressInfo.push_back(Pair("Address: ", CBitcoinAddress(address.first).ToString())); + addressInfo.push_back(Pair("Percentage: ", aPercent)); + //addressInfo.push_back(pstakeDB->mapAddressBook.find(CBitcoinAddress(address.first).Get())->second); + //addressInfo.push_back(pstakeDB->mapAddressPercent.find(CBitcoinAddress(address.first).Get())->second); + } + } + stakeOut.push_back(addressInfo); + } + + return stakeOut; + +} + +Value getstakeoutinfo(const Array ¶ms, bool fHelp) +{ + if (fHelp || params.size() != 0) + throw runtime_error( + "getstakeoutinfo\n" + "Returns your aggregated Stakeout Data information\n"); + + string success = "Currently under development."; + return success; +} diff --git a/src/stakedb.cpp b/src/stakedb.cpp new file mode 100644 index 0000000..4cabd30 --- /dev/null +++ b/src/stakedb.cpp @@ -0,0 +1,339 @@ +// Copyright (c) 2009-2010 Satoshi Nakamoto +// Copyright (c) 2009-2012 The Bitcoin developers +// Distributed under the MIT/X11 software license, see the accompanying +// file COPYING or http://www.opensource.org/licenses/mit-license.php. + +#include "stakedb.h" +#include "wallet.h" + +#include +#include + +using namespace std; +using namespace boost; + + +static uint64_t nAccountingentryNumber = 0; + +// +// CStakeDB +// + +bool CStakeDB::WriteStake(const string& strAddress, const string& strName, const string& sPercent) +{ + nStakeDBUpdated++; + bool success = true; + + if (!Write(make_pair(string("name"), strAddress), strName)) + success = false; + if (!Write(make_pair(string("percent"), strAddress), sPercent)) + success = false; + return success; +} + +bool CStakeDB::EraseStake(const string& strAddress) +{ + nStakeDBUpdated++; + bool success=true; + + if (!Erase(make_pair(string("name"), strAddress))) + success = false; + if (!Erase(make_pair(string("percent"), strAddress))) + success = false; + + return success; +} + +bool CStakeDB::ReadStake(const string& strAddress, string& strName, string& sPercent) +{ + bool success = true; + + if (!Read(make_pair(string("name"), strAddress), strName)) + success = false; + if (!Read(make_pair(string("percent"), strAddress), sPercent)) + success = false; + + return success; +} + +bool +ReadKeyValue(CWallet* pwallet, CDataStream& ssKey, CDataStream& ssValue, string& strType, string& strErr) +{ + try { + // Unserialize + // Taking advantage of the fact that pair serialization + // is just the two items serialized one after the other + ssKey >> strType; + if (strType == "name") + { + string strAddress; + ssKey >> strAddress; + ssValue >> pwallet->mapAddressBook[CBitcoinAddress(strAddress).Get()]; + } + else if (strType == "percent") + { + string strAddress; + ssKey >> strAddress; + ssValue >> pwallet->mapAddressPercent[CBitcoinAddress(strAddress).Get()]; + } + } catch (...) + { + return false; + } + + return true; + +} + +SDBErrors CStakeDB::LoadWallet(CWallet* pwallet) +{ + pwallet->vchDefaultKey = CPubKey(); + + bool fNoncriticalErrors = false; + SDBErrors result = SDB_LOAD_OK; + + try { + LOCK(pwallet->cs_wallet); + int nMinVersion = 0; + if (Read((string)"minversion", nMinVersion)) + { + if (nMinVersion > CLIENT_VERSION) + return SDB_TOO_NEW; + pwallet->LoadMinVersion(nMinVersion); + } + + // Get cursor + Dbc* pcursor = GetCursor(); + if (!pcursor) + { + printf("Error getting wallet database cursor\n"); + return SDB_CORRUPT; + } + + while (true) + { + // Read next record + CDataStream ssKey(SER_DISK, CLIENT_VERSION); + CDataStream ssValue(SER_DISK, CLIENT_VERSION); + int ret = ReadAtCursor(pcursor, ssKey, ssValue); + if (ret == DB_NOTFOUND) + break; + else if (ret != 0) + { + printf("Error reading next record from wallet database\n"); + return SDB_CORRUPT; + } + + // Try to be tolerant of single corrupt records: + string strType, strErr; + if (!ReadKeyValue(pwallet, ssKey, ssValue, strType, strErr)) + { + printf("\n\nError: Debug ReadKeyValue for StakeDB \n\n"); + } + if (!strErr.empty()) + printf("%s\n", strErr.c_str()); + + } + pcursor->close(); + } + catch (...) + { + result = SDB_CORRUPT; + } + + if (fNoncriticalErrors && result == SDB_LOAD_OK) + result = SDB_NONCRITICAL_ERROR; + + // Any stakedb corruption at all: skip any rewriting or + // upgrading, we don't want to make it worse. + if (result != SDB_LOAD_OK) + return result; + + return result; +} + +void ThreadFlushStakeDB(void* parg) +{ + // Make this thread recognisable as the wallet flushing thread + RenameThread("pinkcoin-stake"); + + const string& strFile = ((const string*)parg)[0]; + static bool fOneThread; + if (fOneThread) + return; + fOneThread = true; + if (!GetBoolArg("-flushwallet", true)) + return; + + unsigned int nLastSeen = nStakeDBUpdated; + unsigned int nLastFlushed = nStakeDBUpdated; + int64_t nLastStakeUpdate = GetTime(); + while (!fShutdown) + { + MilliSleep(500); + + if (nLastSeen != nStakeDBUpdated) + { + nLastSeen = nStakeDBUpdated; + nLastStakeUpdate = GetTime(); + } + + if (nLastFlushed != nStakeDBUpdated && GetTime() - nLastStakeUpdate >= 1) + { + TRY_LOCK(bitdb.cs_db,lockDb); + if (lockDb) + { + // Don't do this if any databases are in use + int nRefCount = 0; + map::iterator mi = bitdb.mapFileUseCount.begin(); + while (mi != bitdb.mapFileUseCount.end()) + { + nRefCount += (*mi).second; + mi++; + } + + if (nRefCount == 0 && !fShutdown) + { + map::iterator mi = bitdb.mapFileUseCount.find(strFile); + if (mi != bitdb.mapFileUseCount.end()) + { + printf("Flushing stake.dat\n"); + nLastFlushed = nStakeDBUpdated; + int64_t nStart = GetTimeMillis(); + + // Flush stake.dat so it's self contained + bitdb.CloseDb(strFile); + bitdb.CheckpointLSN(strFile); + + bitdb.mapFileUseCount.erase(mi++); + printf("Flushed stake.dat %dms\n", GetTimeMillis() - nStart); + } + } + } + } + } +} + +bool BackupStakeDB(const CWallet& stakeDB, const string& strDest) +{ + if (!stakeDB.fFileBacked) + return false; + while (!fShutdown) + { + { + LOCK(bitdb.cs_db); + if (!bitdb.mapFileUseCount.count(stakeDB.strWalletFile) || bitdb.mapFileUseCount[stakeDB.strWalletFile] == 0) + { + // Flush log data to the dat file + bitdb.CloseDb(stakeDB.strWalletFile); + bitdb.CheckpointLSN(stakeDB.strWalletFile); + bitdb.mapFileUseCount.erase(stakeDB.strWalletFile); + + // Copy wallet.dat + filesystem::path pathSrc = GetDataDir() / stakeDB.strWalletFile; + filesystem::path pathDest(strDest); + if (filesystem::is_directory(pathDest)) + pathDest /= stakeDB.strWalletFile; + + try { +#if BOOST_VERSION >= 104000 + filesystem::copy_file(pathSrc, pathDest, filesystem::copy_option::overwrite_if_exists); +#else + filesystem::copy_file(pathSrc, pathDest); +#endif + printf("copied wallet.dat to %s\n", pathDest.string().c_str()); + return true; + } catch(const filesystem::filesystem_error &e) { + printf("error copying wallet.dat to %s - %s\n", pathDest.string().c_str(), e.what()); + return false; + } + } + } + MilliSleep(100); + } + return false; +} + +// +// Try to (very carefully!) recover stake.dat if there is a problem. +// +bool CStakeDB::Recover(CDBEnv& dbenv, std::string filename, bool fOnlyKeys) +{ + // Recovery procedure: + // move stake.dat to stake.timestamp.bak + // Call Salvage with fAggressive=true to + // get as much data as possible. + // Rewrite salvaged data to wallet.dat + // Set -rescan so any missing transactions will be + // found. + int64_t now = GetTime(); + std::string newFilename = strprintf("stake.%d.bak", now); + + int result = dbenv.dbenv.dbrename(NULL, filename.c_str(), NULL, + newFilename.c_str(), DB_AUTO_COMMIT); + if (result == 0) + printf("Renamed %s to %s\n", filename.c_str(), newFilename.c_str()); + else + { + printf("Failed to rename %s to %s\n", filename.c_str(), newFilename.c_str()); + return false; + } + + std::vector salvagedData; + bool allOK = dbenv.Salvage(newFilename, true, salvagedData); + if (salvagedData.empty()) + { + printf("Salvage(aggressive) found no records in %s.\n", newFilename.c_str()); + return false; + } + printf("Salvage(aggressive) found %u records\n", salvagedData.size()); + + bool fSuccess = allOK; + Db* pdbCopy = new Db(&dbenv.dbenv, 0); + int ret = pdbCopy->open(NULL, // Txn pointer + filename.c_str(), // Filename + "main", // Logical db name + DB_BTREE, // Database type + DB_CREATE, // Flags + 0); + if (ret > 0) + { + printf("Cannot create database file %s\n", filename.c_str()); + return false; + } + CWallet dummyStakeDB; + + DbTxn* ptxn = dbenv.TxnBegin(); + BOOST_FOREACH(CDBEnv::KeyValPair& row, salvagedData) + { + if (fOnlyKeys) + { + CDataStream ssKey(row.first, SER_DISK, CLIENT_VERSION); + CDataStream ssValue(row.second, SER_DISK, CLIENT_VERSION); + string strType, strErr; + bool fReadOK = ReadKeyValue(&dummyStakeDB, ssKey, ssValue, strType, strErr); +// if (!IsKeyType(strType)) +// continue; + if (!fReadOK) + { + printf("WARNING: CStakeDB::Recover skipping %s: %s\n", strType.c_str(), strErr.c_str()); + continue; + } + } + Dbt datKey(&row.first[0], row.first.size()); + Dbt datValue(&row.second[0], row.second.size()); + int ret2 = pdbCopy->put(ptxn, &datKey, &datValue, DB_NOOVERWRITE); + if (ret2 > 0) + fSuccess = false; + } + ptxn->commit(0); + pdbCopy->close(0); + delete pdbCopy; + + return fSuccess; +} + +bool CStakeDB::Recover(CDBEnv& dbenv, std::string filename) +{ + return CStakeDB::Recover(dbenv, filename, false); +} diff --git a/src/stakedb.h b/src/stakedb.h new file mode 100644 index 0000000..35af0be --- /dev/null +++ b/src/stakedb.h @@ -0,0 +1,79 @@ +// Copyright (c) 2009-2010 Satoshi Nakamoto +// Copyright (c) 2009-2012 The Bitcoin developers +// Distributed under the MIT/X11 software license, see the accompanying +// file COPYING or http://www.opensource.org/licenses/mit-license.php. +#ifndef BITCOIN_STAKEDB_H +#define BITCOIN_STAKEDB_H + +#include "db.h" +#include "base58.h" +#include "stealth.h" + +//class CKeyPool; +//class CAccount; +//class CAccountingentry; + +/** Error statuses for the stake database */ +enum SDBErrors +{ + SDB_LOAD_OK, + SDB_CORRUPT, + SDB_NONCRITICAL_ERROR, + SDB_TOO_NEW, + SDB_LOAD_FAIL, + SDB_NEED_REWRITE +}; + +/** Access to the wallet database (stake.dat) */ +class CStakeDB : public CDB +{ +public: + CStakeDB(std::string strFilename, const char* pszMode="r+") : CDB(strFilename.c_str(), pszMode) + { + } +private: + CStakeDB(const CStakeDB&); + void operator=(const CStakeDB&); +public: + Dbc* GetAtCursor() + { + return GetCursor(); + } + + Dbc* GetTxnCursor() + { + if (!pdb) + return NULL; + + DbTxn* ptxnid = activeTxn; // call TxnBegin first + + Dbc* pcursor = NULL; + int ret = pdb->cursor(ptxnid, &pcursor, 0); + if (ret != 0) + return NULL; + return pcursor; + } + + DbTxn* GetAtActiveTxn() + { + return activeTxn; + } + + bool WriteStake(const std::string& strAddress, const std::string& strName, const std::string& sPercent); + + bool EraseStake(const std::string& strAddress); + + bool ReadStake(const std::string& strAddress, std::string& strName, std::string& sPercent); + + bool WriteMinVersion(int nVersion) + { + return Write(std::string("minversion"), nVersion); + } +public: + SDBErrors ReorderTransactions(CWallet*); + SDBErrors LoadWallet(CWallet* pwallet); + static bool Recover(CDBEnv& dbenv, std::string filename, bool fOnlyKeys); + static bool Recover(CDBEnv& dbenv, std::string filename); +}; + +#endif // BITCOIN_WALLETDB_H diff --git a/src/wallet.cpp b/src/wallet.cpp index 0cc549f..db69a0d 100644 --- a/src/wallet.cpp +++ b/src/wallet.cpp @@ -4,9 +4,11 @@ // file COPYING or http://www.opensource.org/licenses/mit-license.php. #include "txdb.h" +#include "stakedb.h" #include "wallet.h" #include "walletdb.h" #include "crypter.h" +#include "init.h" #include "ui_interface.h" #include "base58.h" #include "kernel.h" @@ -15,7 +17,7 @@ using namespace std; -unsigned int nStakeSplitAge = 1 * 1 * 60 * 60; +//unsigned int nStakeSplitAge = 1 * 1 * 60 * 60; int64_t nStakeCombineThreshold = 1000 * COIN; // CBitcoinAddress addrD4L("2LSrmzJMBSEcBMG7WMNxcdzVMH6tXXQH9M"); @@ -2667,30 +2669,38 @@ bool CWallet::CreateCoinStake(const CKeyStore& keystore, unsigned int nBits, int } // Calculate coin age reward + + int64_t nReward; { uint64_t nCoinAge; CTxDB txdb("r"); if (!txNew.GetCoinAge(txdb, nCoinAge)) return error("CreateCoinStake : failed to calculate coin age"); - int64_t nReward = GetProofOfStakeReward(nCoinAge, nFees, pindexBest->nHeight + 1, txNew.nTime); + nReward = GetProofOfStakeReward(nCoinAge, nFees, pindexBest->nHeight + 1, txNew.nTime); if (nReward <= 0 && pindexBest->nHeight > 16240) return false; - nCredit += nReward; + } + printf("\n\n\n\n***************************IMPORTANT*************************************\n" + "** TRYING NEW CODE **\n" + "*************************************************************************\n\n\n\n"); + + int64_t stakeOutCount = CountStakeOut(); + int64_t stakeOutReward = AggregateStakeOut(txNew, nReward); + + nCredit += nReward - stakeOutReward; // Set output amount - if (txNew.vout.size() == 3) + if (txNew.vout.size() == 3 + stakeOutCount) { txNew.vout[1].nValue = ((nCredit) / 2 / CENT) * CENT; txNew.vout[2].nValue = (nCredit) - txNew.vout[1].nValue; - // txNew.vout[3].nValue = 20 * COIN; } else { txNew.vout[1].nValue = nCredit; - // txNew.vout[2].nValue = 20; } @@ -2711,6 +2721,56 @@ bool CWallet::CreateCoinStake(const CKeyStore& keystore, unsigned int nBits, int return true; } +int64_t CWallet::AggregateStakeOut(CTransaction &txNew, int64_t &nReward) +{ + int64_t percentTotal = 0; + int64_t nRewardPCTotal = 0; + + BOOST_FOREACH(mapAddress mapStake, pstakeDB->mapAddressPercent) + { + int64_t nPercent = (int64_t)stoi(mapStake.second); + CBitcoinAddress stakeOutAddress(mapStake.first); + if (nPercent > 0 && nPercent <= 100 && stakeOutAddress.IsValid()) + { + percentTotal += nPercent; + if (percentTotal <= 100) + { + int64_t nRewardPC = (nReward * nPercent) / 100; + nRewardPCTotal += nRewardPC; + + CScript stakeOut; + stakeOut.SetDestination(stakeOutAddress.Get()); + + txNew.vout.push_back(CTxOut(nRewardPC, stakeOut)); + printf("\nStakeout Coins: %d to Address: %s", nRewardPC, stakeOutAddress.ToString().c_str()); + } else { + printf("\nAttempt to stakeout over 100%%"); + percentTotal -= nPercent; + } + } + } + + return nRewardPCTotal; +} + +int64_t CWallet::CountStakeOut() +{ + int64_t countOut = 0; + int64_t percentTotal = 0; + + BOOST_FOREACH(mapAddress mapStake, pstakeDB->mapAddressPercent) + { + int64_t nPercent = (int64_t)stoi(mapStake.second); + CBitcoinAddress stakeOutAddress(mapStake.first); + if (nPercent > 0 && nPercent <= 100 && stakeOutAddress.IsValid()) + { + percentTotal += nPercent; + if (percentTotal <= 100) countOut++; + } + } + return countOut; +} + // Call after CreateTransaction unless you want to abort bool CWallet::CommitTransaction(CWalletTx& wtxNew, CReserveKey& reservekey) @@ -2859,6 +2919,20 @@ DBErrors CWallet::LoadWallet(bool& fFirstRunRet) return DB_LOAD_OK; } +SDBErrors CWallet::LoadStakeDB(bool& fFirstRunRet) +{ + if (!fFileBacked) + return SDB_LOAD_OK; + fFirstRunRet = false; + SDBErrors nLoadStakeDBRet = CStakeDB(strWalletFile,"cr+").LoadWallet(this); + + if (nLoadStakeDBRet != SDB_LOAD_OK) + return nLoadStakeDBRet; + + NewThread(ThreadFlushStakeDB, &strWalletFile); + return SDB_LOAD_OK; +} + bool CWallet::SetAddressBookName(const CTxDestination& address, const string& strName) { @@ -2907,6 +2981,38 @@ bool CWallet::DelAddressBookName(const CTxDestination& address) return CWalletDB(strWalletFile).EraseName(CBitcoinAddress(address).ToString()); } +bool CWallet::SetAddressBookStake(const CTxDestination& address, const string& strName, const string& strPercent) +{ + ChangeType nMode; + { + LOCK(cs_wallet); // mapAddressBook + std::map::iterator mi = mapAddressBook.find(address); + nMode = (mi == mapAddressBook.end()) ? CT_NEW : CT_UPDATED; + + mapAddressBook[address] = strName; + mapAddressPercent[address] = strPercent; + } + + ///string passPercent = strPercent; + + NotifyAddressBookStakeChanged(this, address, strName, strPercent, nMode); + + return CStakeDB(pstakeDB->strWalletFile).WriteStake(CBitcoinAddress(address).ToString(), strName, strPercent); +} + +bool CWallet::DelAddressBookStake(const CTxDestination& address) +{ + { + LOCK(cs_wallet); // mapAddressBook + + mapAddressBook.erase(address); + mapAddressPercent.erase(address); + } + + NotifyAddressBookStakeChanged(this, address, "", "", CT_DELETED); + + return CStakeDB(pstakeDB->strWalletFile).EraseStake(CBitcoinAddress(address).ToString()); +} void CWallet::PrintWallet(const CBlock& block) { @@ -2960,6 +3066,11 @@ bool GetWalletFile(CWallet* pwallet, string &strWalletFileOut) return true; } +bool GetPStakeDB(CWallet *pstakeDB) +{ + return pstakeDB; +} + // // Mark old keypool keys as used, // and generate all new keys diff --git a/src/wallet.h b/src/wallet.h index a7d5002..dba52e9 100644 --- a/src/wallet.h +++ b/src/wallet.h @@ -17,6 +17,7 @@ #include "script.h" #include "ui_interface.h" #include "util.h" +#include "stakedb.h" #include "walletdb.h" #include "stealth.h" #include "smessage.h" @@ -94,9 +95,11 @@ class CWallet : public CCryptoKeyStore /// fFileBacked (immutable after instantiation) /// strWalletFile (immutable after instantiation) mutable CCriticalSection cs_wallet; + //mutable CCriticalSection cs_stake; bool fFileBacked; std::string strWalletFile; + //std::string strStakeDBFile; std::set setKeyPool; std::map mapKeyMetadata; @@ -142,7 +145,10 @@ class CWallet : public CCryptoKeyStore int64_t nOrderPosNext; std::map mapRequestCount; + + typedef std::pair mapAddress; std::map mapAddressBook; + std::map mapAddressPercent; CPubKey vchDefaultKey; int64_t nTimeFirstKey; @@ -213,12 +219,11 @@ class CWallet : public CCryptoKeyStore bool CreateTransaction(const std::vector >& vecSend, CWalletTx& wtxNew, CReserveKey& reservekey, int64_t& nFeeRet, int32_t& nChangePos, int nSplitBlock, const CCoinControl *coinControl=NULL); bool CreateTransaction(CScript scriptPubKey, int64_t nValue, std::string& sNarr, CWalletTx& wtxNew, CReserveKey& reservekey, int64_t& nFeeRet, const CCoinControl *coinControl=NULL); bool CommitTransaction(CWalletTx& wtxNew, CReserveKey& reservekey); - - - bool GetStakeWeight(const CKeyStore& keystore, uint64_t& nMinWeight, uint64_t& nMaxWeight, uint64_t& nWeight); bool CreateCoinStake(const CKeyStore& keystore, unsigned int nBits, int64_t nSearchInterval, int64_t nFees, CTransaction& txNew, CKey& key); + int64_t AggregateStakeOut(CTransaction &txNew, int64_t &nReward); + int64_t CountStakeOut(); std::string SendMoney(CScript scriptPubKey, int64_t nValue, std::string& sNarr, CWalletTx& wtxNew, bool fAskFee=false); std::string SendMoneyToDestination(const CTxDestination& address, int64_t nValue, std::string& sNarr, CWalletTx& wtxNew, bool fAskFee=false); @@ -300,6 +305,17 @@ class CWallet : public CCryptoKeyStore } return nCredit; } + int64_t GetReward(const CTxOut &txOut) const + { + int64_t nReward = 0; + if (IsMine(txOut)); + { + nReward += GetCredit(txOut); + if (!MoneyRange(nReward)) + printf("CWallet::GetCredit() : value out of range"); + } + return nReward; + } int64_t GetChange(const CTransaction& tx) const { int64_t nChange = 0; @@ -314,11 +330,16 @@ class CWallet : public CCryptoKeyStore void SetBestChain(const CBlockLocator& loc); DBErrors LoadWallet(bool& fFirstRunRet); + SDBErrors LoadStakeDB(bool& fFirstRunRet); bool SetAddressBookName(const CTxDestination& address, const std::string& strName); bool DelAddressBookName(const CTxDestination& address); + bool SetAddressBookStake(const CTxDestination& address, const std::string& strName, const std::string& strPercent); + + bool DelAddressBookStake(const CTxDestination& address); + void UpdatedTransaction(const uint256 &hashTx); void PrintWallet(const CBlock& block); @@ -359,6 +380,7 @@ class CWallet : public CCryptoKeyStore * @note called with lock cs_wallet held. */ boost::signals2::signal NotifyAddressBookChanged; + boost::signals2::signal NotifyAddressBookStakeChanged; /** Wallet transaction added, removed or updated. @@ -942,5 +964,6 @@ class CAccountingentry }; bool GetWalletFile(CWallet* pwallet, std::string &strWalletFileOut); +bool GetPStakeDB(CWallet* pstakeDB); #endif