Files
pay/guis/desktop/AccountDetails.qml
T

430 lines
16 KiB
QML
Raw Permalink Normal View History

2020-11-04 18:33:50 +01:00
/*
* This file is part of the Flowee project
* Copyright (C) 2021-2025 Tom Zander <tom@flowee.org>
2020-11-04 18:33:50 +01:00
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
2022-11-26 10:46:57 +01:00
import QtQuick
2025-06-18 17:48:29 +02:00
import QtQuick.Controls.Basic as QQC2
2022-11-26 10:46:57 +01:00
import QtQuick.Layouts
2022-11-14 21:19:31 +01:00
import "../Flowee" as Flowee
2020-11-04 18:33:50 +01:00
Item {
2020-11-04 18:33:50 +01:00
id: root
property QtObject account: portfolio.current
2021-11-30 22:19:40 +01:00
focus: true
2021-01-29 10:27:24 +01:00
2021-11-02 11:41:55 +01:00
Connections {
target: portfolio
function onCurrentChanged() {
// The model in this case follows the UI, so we need to have this not very
// declarative code.
// When a new model is offered, copy the UI settings into it.
if (root.account.isDecrypted) {
root.account.secrets.showChangeChain = changeAddresses.checked
root.account.secrets.showUsedAddresses = usedAddresses.checked
}
2021-11-02 11:41:55 +01:00
}
}
2021-11-09 20:52:58 +01:00
Component.onCompleted: {
if (root.account.isDecrypted) {
root.account.secrets.showChangeChain = changeAddresses.checked
root.account.secrets.showUsedAddresses = usedAddresses.checked
}
2021-11-09 20:52:58 +01:00
}
2025-02-03 16:57:13 +01:00
Item {
// non-layoutable items.
2025-06-19 14:47:19 +02:00
Flowee.Popup {
2025-02-03 16:57:13 +01:00
id: qrPopup
width: 270
height: 270
x: (root.width - width) / 2
y: 100
modal: true
closePolicy: QQC2.Popup.CloseOnEscape | QQC2.Popup.CloseOnPressOutsideParent
background: Rectangle {
color: palette.light
border.color: palette.midlight
border.width: 1
radius: 5
}
Flowee.QRWidget {
id: seedQr
qrSize: 250
textVisible: false
useRawString: true
anchors.centerIn: parent
}
}
}
2021-11-02 11:41:55 +01:00
2024-05-28 23:23:31 +02:00
Flowee.Label {
2021-07-31 14:16:28 +02:00
id: walletDetailsLabel
2021-10-30 15:23:43 +02:00
text: qsTr("Wallet Details")
2021-07-31 14:16:28 +02:00
font.pointSize: 18
color: "white"
2021-07-31 17:19:34 +02:00
anchors.horizontalCenter: parent.horizontalCenter
}
2021-05-08 14:40:08 +02:00
Flowee.CloseIcon {
id: closeIcon
2021-07-31 14:16:28 +02:00
anchors.bottom: walletDetailsLabel.bottom
2021-10-29 18:20:42 +02:00
anchors.margins: 6
anchors.right: parent.right
onClicked: accountOverlay.state = "showTransactions"
2025-05-04 19:42:50 +02:00
color: "#bbbbbb"
2021-10-29 18:20:42 +02:00
}
2021-07-31 14:16:28 +02:00
GridLayout {
id: basicProperties
2021-10-29 18:20:42 +02:00
anchors.top: walletDetailsLabel.bottom
anchors.topMargin: 20
x: 20
width: parent.width - 30
columns: 2
rowSpacing: 10
2021-10-29 18:20:42 +02:00
2024-05-28 23:23:31 +02:00
Flowee.Label {
2021-10-29 18:20:42 +02:00
text: qsTr("Name") + ":"
2021-07-31 14:16:28 +02:00
}
2021-11-02 19:38:36 +01:00
Flowee.TextField {
2021-10-29 18:20:42 +02:00
id: accountNameEdit
text: root.account.name
onTextEdited: root.account.name = text
Layout.fillWidth: true
2021-10-30 16:12:41 +02:00
focus: true
2021-07-31 14:16:28 +02:00
}
2022-07-14 20:48:05 +02:00
}
2022-10-21 16:39:43 +02:00
2021-07-31 14:16:28 +02:00
Flickable {
2021-10-29 18:20:42 +02:00
id: scrollablePage
anchors.top: basicProperties.bottom
2021-10-29 18:20:42 +02:00
anchors.left: parent.left
anchors.right: parent.right
2021-07-31 14:16:28 +02:00
anchors.bottom: parent.bottom
2021-10-29 18:20:42 +02:00
anchors.margins: 10
2021-07-31 14:16:28 +02:00
clip: true
2021-10-29 18:20:42 +02:00
2022-10-21 16:42:59 +02:00
contentHeight: detailsPane.height + 10 + addressesList.height + 10 + hdDetails.height + 10
2022-10-21 16:39:43 +02:00
GridLayout {
2021-10-29 18:20:42 +02:00
id: detailsPane
width: parent.width - 20
x: 10
2022-10-21 16:39:43 +02:00
columns: 2
2021-07-31 14:16:28 +02:00
2024-05-28 23:23:31 +02:00
Flowee.Label {
2023-05-16 22:00:47 +02:00
id: syncLabel
2022-10-21 16:39:43 +02:00
Layout.columnSpan: 2
2023-05-16 22:00:47 +02:00
property string time: ""
2021-11-03 13:58:31 +01:00
text: {
2022-04-06 20:58:47 +02:00
var height = root.account.lastBlockSynched
if (height < 1)
2021-11-03 13:58:31 +01:00
return ""
2023-05-16 22:00:47 +02:00
var time = "";
if (syncLabel.time !== "")
time = " (" + syncLabel.time + ")";
2022-04-06 20:58:47 +02:00
return qsTr("Sync Status") + ": " + height + " / " + Pay.chainHeight + time;
2021-11-03 13:58:31 +01:00
}
2024-01-25 19:47:55 +01:00
Connections {
target: root.account;
function onLastBlockSynchedChanged() {
if (timeTimer.interval === 30000) {
// if it just changed, fetch the new time shortly thereafter.
// this makes us show the latest time much more often when doing a sync.
timeTimer.stop();
timeTimer.interval = 500;
timeTimer.start();
}
}
}
2023-05-16 22:00:47 +02:00
Timer {
// the lastBlockSynchedTime does not change,
// but since we render it as '12 minutes ago'
// we need to actually re-interpret that
// ever so often to keep the relative time.
2024-01-25 19:47:55 +01:00
id: timeTimer
2023-05-16 22:00:47 +02:00
running: !root.account.isArchived
interval: 30000 // 30 sec
repeat: true
triggeredOnStart: true
onTriggered: {
syncLabel.time = Pay.formatDateTime(
root.account.lastBlockSynchedTime);
2024-01-25 19:47:55 +01:00
interval = 30000; // 30 sec
2023-05-16 22:00:47 +02:00
}
}
2021-07-31 17:19:34 +02:00
}
2022-12-16 19:57:43 +01:00
Flowee.AccountTypeLabel {
2022-10-21 16:39:43 +02:00
Layout.columnSpan: 2
2022-12-16 19:57:43 +01:00
account: root.account
2021-10-29 18:20:42 +02:00
}
2024-05-28 23:23:31 +02:00
Flowee.Label {
2022-10-21 16:39:43 +02:00
id: xpubLabel
// at the moment I don't see a point if making this translatable. Let me know if that should change!
text: "xpub" + ":"
visible: root.account.isHDWallet
}
Flowee.LabelWithClipboard {
Layout.fillWidth: true
visible: xpubLabel.visible
text: root.account.xpub
2021-07-31 14:16:28 +02:00
}
2021-10-29 18:20:42 +02:00
2024-05-28 23:23:31 +02:00
Flowee.Label {
2022-10-21 16:39:43 +02:00
id: encLabel
text: qsTr("Encryption") + ":"
visible: encStatus.visible
2021-07-31 14:16:28 +02:00
}
2022-10-21 16:39:43 +02:00
WalletEncryptionStatus {
id: encStatus
Layout.fillWidth: true
account: root.account
2021-07-31 14:16:28 +02:00
}
2022-10-21 16:39:43 +02:00
2024-05-28 23:23:31 +02:00
Flowee.Label {
2022-10-21 16:39:43 +02:00
id: pwdLabel
text: qsTr("Password") + ":"
visible: encStatus.visible
}
Flowee.TextField {
id: passwordField
onAccepted: decryptButton.clicked()
enabled: !root.account.isDecrypted
Layout.fillWidth: true
echoMode: TextInput.Password
visible: pwdLabel.visible
}
Item {
visible: pwdLabel.visible
Layout.fillWidth: true
Layout.columnSpan: 2
implicitHeight: Math.max(decryptWarning.implicitHeight, decryptButton.implicitHeight)
Flowee.WarningLabel {
id: decryptWarning
anchors.left: parent.left
anchors.leftMargin: 20
anchors.right: decryptButton.left
anchors.rightMargin: 10
anchors.baseline: decryptButton.baseline
}
Flowee.Button {
id: decryptButton
anchors.right: parent.right
2022-12-10 23:37:25 +01:00
text: qsTr("Open")
2022-10-21 16:39:43 +02:00
enabled: passwordField.text.length > 3
onClicked: {
var rc = root.account.decrypt(passwordField.text);
if (rc) {
// decrypt went Ok
decryptWarning.text = ""
passwordField.text = ""
}
else {
decryptWarning.text = qsTr("Invalid PIN")
passwordField.forceActiveFocus();
}
}
}
2021-07-31 14:16:28 +02:00
}
Flowee.CheckBox {
id: balanceSetting
checked: root.account.countBalance
onCheckedChanged: root.account.countBalance = checked
visible: !portfolio.singleAccountSetup
}
Flowee.CheckBoxLabel {
Layout.fillWidth: true
buddy: balanceSetting
text: qsTr("Include balance in total")
visible: balanceSetting.visible
}
2023-05-16 19:55:52 +02:00
Flowee.CheckBox {
id: privateCB
checked: root.account.isPrivate
onClicked: root.account.isPrivate = checked
visible: balanceSetting.visible
2023-05-16 19:55:52 +02:00
}
Flowee.CheckBoxLabel {
Layout.fillWidth: true
buddy: privateCB
text: qsTr("Hide in private mode")
visible: balanceSetting.visible
2023-05-16 19:55:52 +02:00
}
2021-07-31 14:16:28 +02:00
}
2021-11-02 19:38:36 +01:00
Flowee.GroupBox {
2021-10-29 18:20:42 +02:00
id: addressesList
2021-07-31 14:16:28 +02:00
width: parent.width
2021-10-29 18:20:42 +02:00
anchors.top: detailsPane.bottom
2022-10-21 16:39:43 +02:00
anchors.topMargin: 10
2021-10-29 18:20:42 +02:00
title: qsTr("Address List")
2021-10-30 15:23:43 +02:00
collapsed: !root.account.isSingleAddressAccount
visible: root.account.isDecrypted || !root.account.needsPinToOpen
2021-07-31 14:16:28 +02:00
2021-11-02 19:35:38 +01:00
Flowee.CheckBox {
2021-11-02 11:41:55 +01:00
id: changeAddresses
2021-10-29 18:20:42 +02:00
text: qsTr("Change Addresses")
2021-11-01 18:51:10 +01:00
visible: root.account.isHDWallet
2021-11-02 11:41:55 +01:00
onClicked: root.account.secrets.showChangeChain = checked
toolTipText: qsTr("Switches between addresses others can pay you on, and addresses the wallet uses to send change back to yourself.")
2021-10-29 18:20:42 +02:00
}
2021-11-02 19:35:38 +01:00
Flowee.CheckBox {
2021-11-02 11:41:55 +01:00
id: usedAddresses
2021-10-29 18:20:42 +02:00
text: qsTr("Used Addresses");
2021-11-01 18:51:10 +01:00
visible: !root.account.isSingleAddressAccount
2021-11-02 11:41:55 +01:00
onClicked: root.account.secrets.showUsedAddresses = checked
toolTipText: qsTr("Switches between unused and used Bitcoin addresses")
2021-10-29 18:20:42 +02:00
}
Flowee.WalletSecretsView {
2021-11-30 22:19:40 +01:00
id: historyView
2021-10-29 18:20:42 +02:00
Layout.fillWidth: true
2023-05-30 19:19:57 +02:00
clip: true
2024-05-28 23:23:31 +02:00
QQC2.ScrollBar.vertical: Flowee.ScrollThumb {
2021-11-30 22:19:40 +01:00
id: thumb
minimumSize: 20 / activityView.height
visible: size < 0.9
}
account: root.account
2023-02-09 11:37:26 +01:00
implicitHeight: root.account.isSingleAddressAccount ? contentHeight : scrollablePage.height / 10 * 7
2021-07-31 14:16:28 +02:00
}
}
2021-11-02 19:38:36 +01:00
Flowee.GroupBox {
2021-10-30 16:12:41 +02:00
id: hdDetails
width: parent.width
anchors.top: addressesList.bottom
anchors.topMargin: 20
2021-10-30 16:12:41 +02:00
title: qsTr("Backup details")
2022-07-14 20:48:05 +02:00
visible: root.account.isHDWallet
2021-10-30 16:12:41 +02:00
collapsed: true
Item {
width: parent.width
2022-07-14 20:48:05 +02:00
implicitHeight: {
if (root.account.isDecrypted)
return grid.height + helpText.height + warningText.height + 20
return infoText.height
}
2021-10-30 16:12:41 +02:00
GridLayout {
id: grid
2022-07-14 20:48:05 +02:00
visible: root.account.isDecrypted
2021-10-30 16:12:41 +02:00
width: parent.width
2025-02-03 16:57:13 +01:00
columns: 3
2024-05-28 23:23:31 +02:00
Flowee.Label {
2021-11-09 21:34:40 +01:00
text: qsTr("Seed-phrase") + ":"
2021-10-30 16:12:41 +02:00
}
2024-05-28 23:23:31 +02:00
QQC2.TextArea {
2021-10-30 16:12:41 +02:00
readOnly: true
text: root.account.mnemonic
Layout.fillWidth: true
2021-11-01 18:51:10 +01:00
selectByMouse: true
mouseSelectionMode: TextEdit.SelectWords
wrapMode: TextEdit.WordWrap
padding: 0
MouseArea {
anchors.fill: parent
acceptedButtons: Qt.RightButton
onClicked: menu.popup(parent);
QQC2.Menu {
id: menu
QQC2.MenuItem {
text: qsTr("Copy")
onTriggered: Pay.copyToClipboard(root.account.mnemonic)
}
}
}
2021-10-30 16:12:41 +02:00
}
2025-02-03 16:57:13 +01:00
Image {
Layout.maximumWidth: 20
Layout.maximumHeight: 20
source: "qrc:/qr-code" + (Pay.useDarkSkin ? "-light.svg" : ".svg");
MouseArea {
anchors.fill: parent
onClicked: {
seedQr.qrText = root.account.mnemonic
qrPopup.open();
}
}
}
Flowee.Label {
text: qsTr("Password") + ":"
visible: root.account.mnemonicPwd !== ""
}
Flowee.Label {
2025-02-03 16:57:13 +01:00
Layout.columnSpan: 2
text: root.account.mnemonicPwd
visible: text !== ""
}
2024-05-28 23:23:31 +02:00
Flowee.Label {
text: qsTr("Seed format") + ":"
visible: root.account.isElectrumMnemonic
}
2024-05-28 23:23:31 +02:00
Flowee.Label {
2025-02-03 16:57:13 +01:00
Layout.columnSpan: 2
id: seedPhraseFormat
font.bold: true
2023-10-19 18:13:32 +03:00
text: "Electrum"
visible: root.account.isElectrumMnemonic
}
2024-05-28 23:23:31 +02:00
Flowee.Label {
2021-10-30 16:12:41 +02:00
text: qsTr("Derivation") + ":"
}
Flowee.LabelWithClipboard {
2025-02-03 16:57:13 +01:00
Layout.columnSpan: 2
2021-10-30 16:12:41 +02:00
text: root.account.hdDerivationPath
}
}
2024-05-28 23:23:31 +02:00
Flowee.Label {
2021-10-30 16:12:41 +02:00
id: helpText
2022-07-14 20:48:05 +02:00
visible: grid.visible
2021-10-30 16:12:41 +02:00
width: parent.width
anchors.top: grid.bottom
anchors.topMargin: 10
2021-11-09 21:34:40 +01:00
text: qsTr("Please save the seed-phrase on paper, in the right order, with the derivation path. This seed will allow you to recover your wallet in case of computer failure.")
2021-10-30 16:12:41 +02:00
textFormat: Text.StyledText
wrapMode: Text.WrapAtWordBoundaryOrAnywhere
}
2024-05-28 23:23:31 +02:00
Flowee.Label {
2021-10-30 16:12:41 +02:00
id: warningText
2022-07-14 20:48:05 +02:00
visible: grid.visible
2021-10-30 16:12:41 +02:00
width: parent.width
anchors.top: helpText.bottom
anchors.topMargin: 10
2021-11-09 21:34:40 +01:00
text: qsTr("<b>Important</b>: Never share your seed-phrase with others!")
2021-10-30 16:12:41 +02:00
textFormat: Text.StyledText
wrapMode: Text.WrapAtWordBoundaryOrAnywhere
}
2024-05-28 23:23:31 +02:00
Flowee.Label {
2022-07-14 20:48:05 +02:00
id: infoText
visible: !root.account.isDecrypted
width: parent.width
text: qsTr("This wallet is protected by password (pin-to-pay). To see the backup details you need to provide the password.")
textFormat: Text.StyledText
wrapMode: Text.WrapAtWordBoundaryOrAnywhere
}
2021-10-30 16:12:41 +02:00
}
}
2021-07-31 14:16:28 +02:00
}
2021-11-30 22:19:40 +01:00
Keys.forwardTo: Flowee.ListViewKeyHandler {
target: historyView
}
2020-11-04 18:33:50 +01:00
}