Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(wallet): Update recipient data in send sign modal #17164

Merged
merged 1 commit into from
Feb 6, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
68 changes: 63 additions & 5 deletions storybook/pages/SendSignModalPage.qml
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,49 @@ SplitView {
readonly property var accountsModel: WalletAccountsModel {}
readonly property var selectedAccount: selectedAccountEntry.item

readonly property var recipientModel: ListModel {
readonly property var data: [
{
modelName: "Wallet A",
name: "Hot wallet",
emoji: "🚗",
colorId: Constants.walletAccountColors.army,
color: "#216266",
ens: "",
address: "0x7F47C2e98a4BBf5487E6fb082eC2D9Ab0E6d8881",
},
{
modelName: "Wallet B",
name: "helloworld",
emoji: "😋",
colorId: Constants.walletAccountColors.primary,
color: "#2A4AF5",
ens: "",
address: "0x7F47C2e18a4BBf5487E6fb082eC2D9Ab0E6d7240",
},
{
modelName: "ENS",
name: "Family (ens)",
emoji: "🎨",
colorId: Constants.walletAccountColors.magenta,
color: "#EC266C",
ens: "bation.eth",
address: "0x7F47C2e98a4BBf5487E6fb082eC2D9Ab0E6d8882",
},
{
modelName: "Address",
name: "",
emoji: "",
colorId: "",
color: "",
ens: "",
address: "0x7F47C2e98a4BBf5487E6fb082eC2D9Ab0E6d8883",
},
]
Component.onCompleted: append(data)
}
readonly property var selectedRecipient: selectedRecipientEntry.item

readonly property var networksModel: NetworksModel.flatNetworks
readonly property var selectedNetwork: selectedNetworkEntry.item
}
Expand All @@ -46,6 +89,13 @@ SplitView {
value: ctrlAccount.currentValue
}

ModelEntry {
id: selectedRecipientEntry
sourceModel: priv.recipientModel
key: "address"
value: ctrlRecipient.currentValue
}

ModelEntry {
id: selectedNetworkEntry
sourceModel: priv.networksModel
Expand Down Expand Up @@ -87,7 +137,11 @@ SplitView {
accountEmoji: priv.selectedAccount.emoji
accountColor: Utils.getColorForId(priv.selectedAccount.colorId)

recipientAddress: ctrlRecipient.text
recipientAddress: priv.selectedRecipient.address
recipientName: priv.selectedRecipient.name
recipientEns: priv.selectedRecipient.ens
recipientEmoji: priv.selectedRecipient.emoji
recipientWalletColor: Utils.getColorForId(priv.selectedRecipient.colorId)

networkShortName: priv.selectedNetwork.shortName
networkName: priv.selectedNetwork.chainName
Expand Down Expand Up @@ -189,11 +243,15 @@ SplitView {
currentIndex: 0
}

TextField {
Layout.fillWidth: true
Text {
text: "Selected Recipient"
}
ComboBox {
id: ctrlRecipient
text: "0xA858DDc0445d8131daC4d1DE01f834ffcbA52Ef1"
placeholderText: "Selected recipient"
textRole: "modelName"
valueRole: "address"
model: priv.recipientModel
currentIndex: 0
}

Text {
Expand Down
23 changes: 23 additions & 0 deletions storybook/qmlTests/tests/tst_RecipientViewDelegate.qml
Original file line number Diff line number Diff line change
Expand Up @@ -166,5 +166,28 @@ Item {
compare(delegate.subTitle, "0xC5E4…4e40")
compare(delegate.asset.color, Theme.palette.directColor1)
}

function test_elideAddressInTitle() {
const delegate = createTemporaryObject(testComponent, root, {
address: "0xC5E457F6b85EaE1Fc807081Cc325E482268e4e40",
name: "Adam"
})
verify(delegate)
verify(!delegate.elideAddressInTitle, "Default is disabled")

compare(delegate.title, "Adam")
compare(delegate.subTitle, "0xC5E4…4e40")

delegate.elideAddressInTitle = true

compare(delegate.title, "Adam", "Elide property doesn't affect title until it is an address")
compare(delegate.subTitle, "0xC5E4…4e40")

delegate.name = ""
compare(delegate.title, "0xC5E4…4e40")
delegate.elideAddressInTitle = false
compare(delegate.title, "0xC5E457F6b85EaE1Fc807081Cc325E482268e4e40")

}
}
}
49 changes: 40 additions & 9 deletions storybook/qmlTests/tests/tst_SendSignModal.qml
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,10 @@ Item {
accountColor: Utils.getColorForId(Constants.walletAccountColors.primary)

recipientAddress: "0xA858DDc0445d8131daC4d1DE01f834ffcbA52Ef1"
recipientName: "0x7F47C2e98a4BBf5487E6fb082eC2D9Ab0E6d8882"
recipientEmoji: "😋"
recipientEns: ""
recipientWalletColor: Utils.getColorForId(Constants.walletAccountColors.secondary)

networkShortName: Constants.networkShortChainNames.mainnet
networkName: "Mainnet"
Expand Down Expand Up @@ -340,11 +344,30 @@ Item {
const recipientBox = findChild(controlUnderTest.contentItem, "recipientBox")
verify(!!recipientBox)

const delegate = findChild(recipientBox, "recipientDelegate")
verify(!!delegate)

compare(recipientBox.caption, qsTr("To"))
compare(recipientBox.primaryText, controlUnderTest.recipientAddress)
compare(recipientBox.asset.name, "address")
verify(!recipientBox.asset.isLetterIdenticon)
verify(!recipientBox.asset.isImage)
compare(recipientBox.address, controlUnderTest.recipientAddress)
compare(recipientBox.name, controlUnderTest.recipientName)
compare(recipientBox.ens, controlUnderTest.recipientEns)
compare(recipientBox.emoji, controlUnderTest.recipientEmoji)
compare(recipientBox.walletColor, controlUnderTest.recipientWalletColor)

compare(delegate.title, controlUnderTest.recipientName)
compare(delegate.subTitle, SQUtils.Utils.elideText(controlUnderTest.recipientAddress, 6, 4))
compare(delegate.asset.color, controlUnderTest.recipientWalletColor)
compare(delegate.asset.emoji, controlUnderTest.recipientEmoji)

controlUnderTest.recipientEns = "1234.eth"
compare(delegate.title, controlUnderTest.recipientName)
compare(delegate.subTitle, "1234.eth")

controlUnderTest.recipientEns = ""
controlUnderTest.recipientName = ""

compare(delegate.title, SQUtils.Utils.elideText(controlUnderTest.recipientAddress, 6, 4))
compare(delegate.subTitle, "")
}

function test_recpientContextMenu() {
Expand Down Expand Up @@ -396,11 +419,19 @@ Item {
const accountBox = findChild(controlUnderTest.contentItem, "accountBox")
verify(!!accountBox)

compare(accountBox.caption, qsTr("From"))
compare(accountBox.primaryText, controlUnderTest.accountName)
compare(accountBox.secondaryText, SQUtils.Utils.elideAndFormatWalletAddress(controlUnderTest.accountAddress))
compare(accountBox.asset.emoji, controlUnderTest.accountEmoji)
compare(accountBox.asset.color, controlUnderTest.accountColor)
const delegate = findChild(accountBox, "recipientDelegate")
verify(!!delegate)

compare(accountBox.caption, qsTr("From"))
compare(accountBox.address, controlUnderTest.accountAddress)
compare(accountBox.name, controlUnderTest.accountName)
compare(accountBox.emoji, controlUnderTest.accountEmoji)
compare(accountBox.walletColor, controlUnderTest.accountColor)

compare(delegate.title, controlUnderTest.accountName)
compare(delegate.subTitle, SQUtils.Utils.elideText(controlUnderTest.accountAddress, 6, 4))
compare(delegate.asset.color, controlUnderTest.accountColor)
compare(delegate.asset.emoji, controlUnderTest.accountEmoji)
}

function test_networkInfo() {
Expand Down
5 changes: 3 additions & 2 deletions ui/StatusQ/src/StatusQ/Components/StatusListItem.qml
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ Rectangle {
property Component tagsDelegate
property var inlineTagModel: []
property Component inlineTagDelegate
property bool forceDefaultCursor: false
property bool loading: false
property bool loadingSubTitle: loading
property bool errorMode: false
Expand Down Expand Up @@ -155,7 +156,7 @@ Rectangle {

objectName: root.objectName + "_sensor"
anchors.fill: parent
cursorShape: containsMouse ? Qt.PointingHandCursor : Qt.ArrowCursor
cursorShape: !root.forceDefaultCursor && containsMouse ? Qt.PointingHandCursor : Qt.ArrowCursor
acceptedButtons: Qt.NoButton
hoverEnabled: true

Expand Down Expand Up @@ -254,7 +255,7 @@ Rectangle {
id: statusListItemTitleMouseArea
anchors.fill: parent
enabled: root.enabled
cursorShape: sensor.enabled && containsMouse ? Qt.PointingHandCursor : Qt.ArrowCursor
cursorShape: !root.forceDefaultCursor && sensor.enabled && containsMouse ? Qt.PointingHandCursor : Qt.ArrowCursor
hoverEnabled: true
propagateComposedEvents: root.propagateTitleClicks
onClicked: {
Expand Down
44 changes: 44 additions & 0 deletions ui/app/AppLayouts/Wallet/adaptors/SignSendAdaptor.qml
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@ QObject {
required property string tokenKey
/** amount selected in send modal for sending **/
required property string selectedAmountInBaseUnit
/** recipient address selected in send modal for sending **/
required property string selectedRecipientAddress
/**
Expected model structure:

Expand All @@ -44,6 +46,18 @@ QObject {
**/
required property var tokenBySymbolModel

/**
Expected model structure:

address [string] - address of recipient
name [string] - name of recipient
ens [string] - ens of recipient
emoji [string] - emoji of recipient wallet
color [string] - color of recipient wallet
colorId [string] - colorId of recipient wallet
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
colorId [string] - colorId of recipient wallet
colorId [int] - colorId of recipient wallet

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also in the delegate itself, should be an int, not string

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Method that is always used together with it indicates it is string.
image

**/
required property var recipientModel

/** output property of the account selected **/
readonly property var selectedAccount: selectedAccountEntry.item
/** output property of the network selected **/
Expand All @@ -67,6 +81,29 @@ QObject {
!!selectedAssetContractEntry.item ?
selectedAssetContractEntry.item.address: ""

/** output property of the selected recipient address **/
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

do these need to separate properties here? we can simple expose the item from here do the necessary logic in UI?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

They are passed as separate, because recipient can also be unknown address. In such case item would be empty.
I used separate properties to hide logic of checking for item availability. That way other components don't care whether it is wallet account or saved account or unknown address (only address property).

readonly property string recipientAddress: selectedRecipientEntry.available ? selectedRecipientEntry.item.address : selectedRecipientAddress
/** output property of the selected recipient name **/
readonly property string recipientName: selectedRecipientEntry.available ? selectedRecipientEntry.item.name : ""
/** output property of the selected recipient ens **/
readonly property string recipientEns: selectedRecipientEntry.available ? selectedRecipientEntry.item.ens : ""
/** output property of the selected recipient emoji **/
readonly property string recipientEmoji: selectedRecipientEntry.available ? selectedRecipientEntry.item.emoji : ""
/** output property of the selected recipient color **/
readonly property string recipientWalletColor: {
if (!selectedRecipientEntry.available)
return ""
const color = selectedRecipientEntry.item.color
if (!!color) {
return color
}
const colorId = selectedRecipientEntry.item.colorId
if (!!colorId) {
return Utils.getColorForId(colorId)
}
return ""
}

ModelEntry {
id: selectedAccountEntry
sourceModel: root.accountsModel
Expand Down Expand Up @@ -96,4 +133,11 @@ QObject {
value: root.chainId
key: "chainId"
}

ModelEntry {
id: selectedRecipientEntry
sourceModel: root.recipientModel
key: "address"
value: root.selectedRecipientAddress
}
}
5 changes: 3 additions & 2 deletions ui/app/AppLayouts/Wallet/controls/RecipientViewDelegate.qml
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ StatusListItem {
id: root

property bool useAddressAsLetterIdenticon: false
property bool elideAddressInTitle: false

property string name
property string address
Expand Down Expand Up @@ -42,7 +43,7 @@ StatusListItem {
objectName: root.name

implicitHeight: 64
title: !!root.name ? root.name : d.getSubtitle(false)
title: !!root.name ? root.name : d.getSubtitle(root.elideAddressInTitle)
rightPadding: Theme.halfPadding
subTitle: !!root.name ? d.getSubtitle(true) : ""

Expand Down Expand Up @@ -71,7 +72,7 @@ StatusListItem {
asset.charactersLen: 2
asset.isLetterIdenticon: true
asset.useAcronymForLetterIdenticon: statusListItemIcon.name !== root.address
asset.letterIdenticonBgWithAlpha: true
asset.letterIdenticonBgWithAlpha: !root.emoji
asset.bgColor: Theme.palette.indirectColor1
asset.width: 40
asset.height: 40
Expand Down
60 changes: 60 additions & 0 deletions ui/app/AppLayouts/Wallet/panels/SignAccountInfoBox.qml
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
import QtQuick 2.15
import QtQuick.Controls 2.15
import QtQuick.Layouts 1.15

import StatusQ.Core 0.1
import StatusQ.Core.Theme 0.1

import AppLayouts.Wallet.controls 1.0

import utils 1.0

ColumnLayout {
id: root

property string caption

property alias components: delegate.components
property alias highlighted: delegate.highlighted
property int listItemHeight: 76

required property string address
property string name
property string ens
property string emoji
property string walletColor

StatusBaseText {
text: root.caption
font.pixelSize: Theme.additionalTextSize
}
RecipientViewDelegate {
id: delegate
objectName: "recipientDelegate"

Layout.fillWidth: true
Layout.preferredHeight: root.listItemHeight

address: root.address
name: root.name
ens: root.ens
emoji: root.emoji
walletColor: root.walletColor

elideAddressInTitle: true
useAddressAsLetterIdenticon: !root.name && !root.ens

sensor.enabled: false

statusListItemSubTitle.font.pixelSize: Theme.additionalTextSize
statusListItemTitle.customColor: Theme.palette.directColor1
statusListItemTitle.font.pixelSize: Theme.additionalTextSize
statusListItemTitle.elide: Text.ElideMiddle
border.width: 1
border.color: Theme.palette.baseColor2

asset.bgWidth: 40
asset.bgHeight: 40
rightPadding: Theme.padding
}
}
1 change: 1 addition & 0 deletions ui/app/AppLayouts/Wallet/panels/qmldir
Original file line number Diff line number Diff line change
Expand Up @@ -17,4 +17,5 @@ StickySendModalHeader 1.0 StickySendModalHeader.qml
RecipientSelectorPanel 1.0 RecipientSelectorPanel.qml
SimpleTransactionsFees 1.0 SimpleTransactionsFees.qml
RecipientInfoButtonWithMenu 1.0 RecipientInfoButtonWithMenu.qml
SignAccountInfoBox 1.0 SignAccountInfoBox.qml
SignCollectibleInfoBox 1.0 SignCollectibleInfoBox.qml
Loading