diff --git a/res/icons/AUTHORS b/res/icons/AUTHORS index 2b526d3933a571f76418adb0f1e568b409b62877..4d9fb14b68bb3f39f6b975c51061364f49180887 100644 --- a/res/icons/AUTHORS +++ b/res/icons/AUTHORS @@ -1,8 +1,9 @@ Icons are from the Noun Project. +iconmonstr-info-2-icon.svg: http://iconmonstr.com/license/ noun_2651_cc.svg : Created by Sergey Bakin noun_18704_cc.svg : Created by Ian Mawle noun_22441_cc.svg : Created by Bruno Castro noun_29542_cc.svg : Created by Chris Kerr noun_43022_cc.svg : Created by Jon Prepeluh -noun_63271_cc.svg : Created by Mark Shorter \ No newline at end of file +noun_63271_cc.svg : Created by Mark Shorter diff --git a/res/icons/iconmonstr-info-2-icon.svg b/res/icons/iconmonstr-info-2-icon.svg new file mode 100644 index 0000000000000000000000000000000000000000..3210d181ff59453fc1c662565986fd59c887cb91 --- /dev/null +++ b/res/icons/iconmonstr-info-2-icon.svg @@ -0,0 +1,27 @@ +<?xml version="1.0" encoding="utf-8"?> + + +<!-- The icon can be used freely in both personal and commercial projects with no attribution required, but always appreciated. +You may NOT sub-license, resell, rent, redistribute or otherwise transfer the icon without express written permission from iconmonstr.com --> + + +<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"> + +<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" + + width="512px" height="512px" viewBox="0 0 512 512" enable-background="new 0 0 512 512" xml:space="preserve"> + +<path id="info-2-icon" d="M255.998,90.001c91.74,0,166.002,74.241,166.002,165.998c0,91.741-74.245,166-166.002,166 + + c-91.74,0-165.998-74.243-165.998-166C90,164.259,164.243,90.001,255.998,90.001 M255.998,50.001 + + C142.229,50.001,50,142.229,50,255.999c0,113.771,92.229,206,205.998,206c113.771,0,206.002-92.229,206.002-206 + + C462,142.229,369.77,50.001,255.998,50.001L255.998,50.001z M285.822,367.567h-57.646V230.6h57.646V367.567z M257,202.268 + + c-17.522,0-31.729-14.206-31.729-31.73c0-17.522,14.206-31.729,31.729-31.729c17.524,0,31.728,14.206,31.728,31.729 + + C288.728,188.062,274.524,202.268,257,202.268z"/> + +</svg> + diff --git a/res/icons/icons.qrc b/res/icons/icons.qrc index ac4d8fd4f33bec163dadc27f8d571a55ccb2a3f9..a69d4de1e76266589697e0d723451ce6091c867d 100644 --- a/res/icons/icons.qrc +++ b/res/icons/icons.qrc @@ -1,5 +1,6 @@ <RCC> <qresource prefix="icons"> + <file alias="informations_icon">iconmonstr-info-2-icon.svg</file> <file alias="community_icon">noun_22441_cc.svg</file> <file alias="wot_icon">noun_2651_cc.svg</file> <file alias="members_icon">noun_18704_cc.svg</file> diff --git a/res/ui/informations_tab.ui b/res/ui/informations_tab.ui new file mode 100644 index 0000000000000000000000000000000000000000..bacf3de57d0b1825f0daf2e6f96fa158a9557d1d --- /dev/null +++ b/res/ui/informations_tab.ui @@ -0,0 +1,141 @@ +<?xml version="1.0" encoding="UTF-8"?> +<ui version="4.0"> + <class>InformationsTabWidget</class> + <widget class="QWidget" name="InformationsTabWidget"> + <property name="geometry"> + <rect> + <x>0</x> + <y>0</y> + <width>538</width> + <height>737</height> + </rect> + </property> + <property name="windowTitle"> + <string>Form</string> + </property> + <layout class="QGridLayout" name="gridLayout"> + <item row="0" column="0"> + <widget class="QScrollArea" name="scrollArea"> + <property name="styleSheet"> + <string notr="true">QGroupBox { + border: 1px solid gray; + border-radius: 9px; + margin-top: 0.5em; +} + +QGroupBox::title { + subcontrol-origin: margin; + left: 10px; + padding: 0 3px 0 3px; + font-weight: bold; +}</string> + </property> + <property name="widgetResizable"> + <bool>true</bool> + </property> + <widget class="QWidget" name="scrollAreaWidgetContents"> + <property name="geometry"> + <rect> + <x>0</x> + <y>0</y> + <width>518</width> + <height>717</height> + </rect> + </property> + <layout class="QVBoxLayout" name="verticalLayout_5"> + <item> + <widget class="QGroupBox" name="group_general"> + <property name="styleSheet"> + <string notr="true"/> + </property> + <property name="title"> + <string>General</string> + </property> + <property name="flat"> + <bool>false</bool> + </property> + <layout class="QVBoxLayout" name="verticalLayout_2"> + <item> + <widget class="QLabel" name="label_general"> + <property name="text"> + <string>label_general</string> + </property> + <property name="scaledContents"> + <bool>false</bool> + </property> + <property name="alignment"> + <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> + </property> + </widget> + </item> + </layout> + </widget> + </item> + <item> + <widget class="QGroupBox" name="group_money"> + <property name="title"> + <string>Money</string> + </property> + <layout class="QVBoxLayout" name="verticalLayout_3"> + <item> + <widget class="QLabel" name="label_money"> + <property name="text"> + <string>label_money</string> + </property> + <property name="alignment"> + <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> + </property> + </widget> + </item> + </layout> + </widget> + </item> + <item> + <widget class="QGroupBox" name="group_wot"> + <property name="title"> + <string>WoT</string> + </property> + <layout class="QVBoxLayout" name="verticalLayout_4"> + <item> + <widget class="QLabel" name="label_wot"> + <property name="text"> + <string>label_wot</string> + </property> + <property name="alignment"> + <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> + </property> + </widget> + </item> + </layout> + </widget> + </item> + <item> + <widget class="QGroupBox" name="group_rules"> + <property name="title"> + <string>Rules</string> + </property> + <layout class="QVBoxLayout" name="verticalLayout_6"> + <item> + <widget class="QLabel" name="label_rules"> + <property name="text"> + <string>label_rules</string> + </property> + <property name="alignment"> + <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> + </property> + </widget> + </item> + </layout> + </widget> + </item> + </layout> + </widget> + </widget> + </item> + </layout> + </widget> + <resources> + <include location="../icons/icons.qrc"/> + </resources> + <connections/> +</ui> diff --git a/src/cutecoin/core/community.py b/src/cutecoin/core/community.py index aa02d2b5edaafb3219d297872062f681b6446b92..a3bc61674829ef6fec4c7ad86104a02debdb8e02 100644 --- a/src/cutecoin/core/community.py +++ b/src/cutecoin/core/community.py @@ -141,14 +141,21 @@ class Community(object): return chr(u) def dividend(self): + block = self.get_ud_block() + if block: + return block['dividend'] + else: + return 1 + + def get_ud_block(self): ud = self.request(bma.blockchain.UD) if len(ud['result']['blocks']) > 0: block_number = ud['result']['blocks'][-1] block = self.request(bma.blockchain.Block, req_args={'number': block_number}) - return block['dividend'] + return block else: - return 1 + return False @property def monetary_mass(self): diff --git a/src/cutecoin/gui/currency_tab.py b/src/cutecoin/gui/currency_tab.py index cb69632a3e9f5e581154f99e08805858fa640f68..e8bd759e9d8aee9d653f845b41ba3c99bfdf1e93 100644 --- a/src/cutecoin/gui/currency_tab.py +++ b/src/cutecoin/gui/currency_tab.py @@ -18,6 +18,7 @@ from ..gen_resources.currency_tab_uic import Ui_CurrencyTabWidget from .community_tab import CommunityTabWidget from .transfer import TransferMoneyDialog from ..models.txhistory import HistoryTableModel, TxFilterProxyModel +from .informations_tab import InformationsTabWidget from ..models.wallets import WalletsListModel from ..models.wallet import WalletListModel from ..tools.exceptions import NoPeerAvailable @@ -128,6 +129,11 @@ class CurrencyTabWidget(QWidget, Ui_CurrencyTabWidget): self.tabs_account.addTab(self.tab_community, QIcon(':/icons/community_icon'), "Community") + self.tab_informations = InformationsTabWidget(self.app.current_account, + self.community) + self.tabs_account.addTab(self.tab_informations, + QIcon(':/icons/informations_icon'), + "Informations") blockid = self.community.current_blockid() block_number = blockid['number'] self.status_label.setText("Connected : Block {0}" @@ -307,3 +313,5 @@ QMessageBox.Ok | QMessageBox.Cancel) QModelIndex(), QModelIndex(), []) + if self.tab_informations: + self.tab_informations.refresh() diff --git a/src/cutecoin/gui/informations_tab.py b/src/cutecoin/gui/informations_tab.py new file mode 100644 index 0000000000000000000000000000000000000000..500b7f847fcc8ca6e6fecb7256db104ba2662a6f --- /dev/null +++ b/src/cutecoin/gui/informations_tab.py @@ -0,0 +1,160 @@ +""" +Created on 31 janv. 2015 + +@author: vit +""" + +import logging +from PyQt5.QtWidgets import QWidget +from ..gen_resources.informations_tab_uic import Ui_InformationsTabWidget + + +class InformationsTabWidget(QWidget, Ui_InformationsTabWidget): + """ + classdocs + """ + + def __init__(self, account, community): + """ + Constructor + """ + super().__init__() + self.setupUi(self) + self.community = community + self.account = account + + self.refresh() + + def refresh(self): + # Â try to request money parameters + try: + params = self.community.get_parameters() + except Exception as e: + logging.debug('community get_parameters error : ' + str(e)) + return False + + # Â try to request money variables from last ud block + try: + block = self.community.get_ud_block() + except Exception as e: + logging.debug('community get_ud_block error : ' + str(e)) + return False + + # set infos in label + self.label_general.setText( + """ + <table cellpadding="5"> + <tr><td align="right"><b>{:.2f}</b></div></td><td>{:} {:}</td></tr> + <tr><td align="right"><b>{:.2f}</b></td><td>{:} {:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:.2f}</b></td><td>{:} {:}</td></tr> + <tr><td align="right"><b>{:2.2%}</b></td><td>{:}</td></tr> + </table> + """.format( + self.get_referential_value(block['dividend']), + 'Universal Dividend UD(t) in', + self.get_referential_name(), + self.get_referential_value(block['monetaryMass']), + 'Monetary Mass M(t) in', + self.get_referential_name(), + block['membersCount'], + 'Members N(t)', + self.get_referential_value(block['monetaryMass'] / block['membersCount']), + 'Monetary Mass per member M(t)/N(t) in', + self.get_referential_name(), + block['dividend'] / (block['monetaryMass'] - (block['membersCount'] * block['dividend'])) / block[ + 'membersCount'], + 'Actual % Growth c = UD(t)/[M(t-1)/N(t)]' + ) + ) + + # set infos in label + self.label_money.setText( + """ + <table cellpadding="5"> + <tr><td align="right"><b>{:2.0%}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:} {:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:2.0%}</b></td><td>{:}</td></tr> + </table> + """.format( + params['c'], + 'Growth parameter c', + params['ud0'], + 'Initial Universal Dividend in', + self.community.short_currency, + params['dt'] / 86400, + 'Time period in days between two UD', + params['medianTimeBlocks'], + 'Number of blocks used for calculating median time', + params['avgGenTime'], + 'The average time in seconds for writing 1 block (wished time)', + params['dtDiffEval'], + 'The number of blocks required to evaluate again PoWMin value', + params['blocksRot'], + 'The number of previous blocks to check for personalized difficulty', + params['percentRot'], + 'The percent of previous issuers to reach for personalized difficulty' + ) + ) + + # set infos in label + self.label_wot.setText( + """ + <table cellpadding="5"> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + </table> + """.format( + params['sigDelay'] / 86400, + 'Minimum delay between 2 identical certifications (in days)', + params['sigValidity'] / 86400, + 'Maximum age of a valid signature (in days)', + params['sigQty'], + 'Minimum quantity of signatures to be part of the WoT', + params['sigWoT'], + 'Minimum quantity of valid made certifications to be part of the WoT for distance rule', + params['msValidity'] / 86400, + 'Maximum age of a valid membership (in days)', + params['stepMax'], + 'Maximum distance between each WoT member and a newcomer', + ) + ) + + # set infos in label + self.label_rules.setText( + """ + <table cellpadding="5"> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + <tr><td align="right"><b>{:}</b></td><td>{:}</td></tr> + </table> + """.format( + "{:2.0%} / {:} days".format(params['c'], params['dt'] / 86400), + 'Growth percent (c)', + "UD t+1 = MAX ( UD t ; c * Mt / Nt+1 )", + 'Universal Dividend (formula)', + "UD t+1 = MAX ( {:.2f} {:} ; {:2.0%} * {:.2f} {:} / Nt+1 )".format( + self.get_referential_value(params['ud0']), + self.get_referential_name(), + params['c'], + self.get_referential_value(block['monetaryMass']), + self.get_referential_name() + ), + 'Universal Dividend (computed)' + ) + ) + + def get_referential_value(self, value): + return self.account.units_to_ref(value, self.community) + + def get_referential_name(self): + return self.account.ref_name(self.community.short_currency)