+
setReviewing(true)}
/>
{extrinsic && (
@@ -80,11 +97,15 @@ const VoteAction: React.FC = () => {
description: e.message,
})
}}
- onClose={() => setReviewing(false)}
+ onClose={() => {
+ setReviewing(false)
+ setRemoveVoteId(null)
+ }}
open={reviewing}
/>
)}
+
)
}
diff --git a/apps/multisig/src/layouts/NewTransaction/Vote/mode/VoteSplitAbstain.tsx b/apps/multisig/src/layouts/NewTransaction/Vote/mode/VoteSplitAbstain.tsx
new file mode 100644
index 00000000..a2b58d36
--- /dev/null
+++ b/apps/multisig/src/layouts/NewTransaction/Vote/mode/VoteSplitAbstain.tsx
@@ -0,0 +1,54 @@
+import { BaseToken } from '@domains/chains'
+import { VoteDetailsForm } from '@domains/referenda'
+import { AmountFlexibleInput } from '@components/AmountFlexibleInput'
+import { parseUnits } from '@util/numbers'
+import BN from 'bn.js'
+
+interface VoteSplitAbstainProps {
+ token?: BaseToken
+ setVoteDetails: React.Dispatch
>
+}
+
+enum VoteDirection {
+ Abstain = 'abstain',
+ Aye = 'aye',
+ Nay = 'nay',
+}
+
+export default function VoteSplitAbstain({ token, setVoteDetails }: VoteSplitAbstainProps) {
+ const handleAmountChange = (amount: string, field: VoteDirection) => {
+ if (!token) return
+
+ let balance = new BN(0)
+ try {
+ balance = parseUnits(amount, token.decimals)
+ } catch (e) {
+ // if failed to parse, input is likely '' or invalid number, hence we default to BN(0)
+ balance = new BN(0)
+ }
+
+ setVoteDetails(prev => {
+ const prevBal = prev.details.SplitAbstain[field]
+ if (balance.eq(prevBal)) return prev
+
+ const updatedVal = { ...prev }
+ updatedVal.details.SplitAbstain[field] = balance
+ return updatedVal
+ })
+ }
+
+ return (
+ <>
+ {Object.values(VoteDirection).map(direction => (
+ handleAmountChange(amount, direction)}
+ />
+ ))}
+ >
+ )
+}
diff --git a/apps/multisig/src/layouts/NewTransaction/Vote/mode/VoteStandard.tsx b/apps/multisig/src/layouts/NewTransaction/Vote/mode/VoteStandard.tsx
index a1922bea..4fa3fa8c 100644
--- a/apps/multisig/src/layouts/NewTransaction/Vote/mode/VoteStandard.tsx
+++ b/apps/multisig/src/layouts/NewTransaction/Vote/mode/VoteStandard.tsx
@@ -1,17 +1,18 @@
+import React from 'react'
import { AmountFlexibleInput } from '@components/AmountFlexibleInput'
import { BaseToken } from '@domains/chains'
-import { StandardVoteParams, VoteDetails } from '@domains/referenda'
+import { StandardVoteParams, VoteDetailsForm } from '@domains/referenda'
import ConvictionsDropdown from '../ConvictionsDropdown'
import { parseUnits } from '@util/numbers'
import BN from 'bn.js'
type Props = {
token?: BaseToken
- onChange: (v: VoteDetails['details']) => void
+ setVoteDetails: React.Dispatch>
params: StandardVoteParams
}
-const VoteStandard = ({ params, onChange, token }: Props) => {
+const VoteStandard = ({ params, setVoteDetails, token }: Props) => {
const handleAmountChange = (amount: string) => {
if (!token) return
@@ -23,23 +24,11 @@ const VoteStandard = ({ params, onChange, token }: Props) => {
balance = new BN(0)
}
if (balance.eq(params.balance)) return
- onChange({
- Standard: {
- balance,
- vote: params.vote,
- },
- })
- }
- const handleConvictionChange = (conviction: number) => {
- onChange({
- Standard: {
- balance: params.balance,
- vote: {
- conviction,
- aye: params.vote.aye,
- },
- },
+ setVoteDetails(prev => {
+ const updatedVal = { ...prev }
+ updatedVal.details.Standard.balance = balance
+ return updatedVal
})
}
@@ -52,7 +41,7 @@ const VoteStandard = ({ params, onChange, token }: Props) => {
leadingLabel="Amount to vote"
setAmount={handleAmountChange}
/>
-
+
>
)
}
diff --git a/apps/multisig/src/layouts/Overview/Transactions/VoteTransactionDetails.tsx b/apps/multisig/src/layouts/Overview/Transactions/VoteTransactionDetails.tsx
index 2deb9815..be82bb13 100644
--- a/apps/multisig/src/layouts/Overview/Transactions/VoteTransactionDetails.tsx
+++ b/apps/multisig/src/layouts/Overview/Transactions/VoteTransactionDetails.tsx
@@ -1,54 +1,71 @@
+import { useMemo } from 'react'
import { Transaction, TransactionType } from '@domains/multisig'
import { css } from '@emotion/css'
import { ExternalLink } from '@talismn/icons'
import AmountRow from '@components/AmountRow'
import { createConvictionsOpts } from '../../NewTransaction/Vote/ConvictionsDropdown'
import { VoteDetails } from '../../../domains/referenda'
+import clsx from 'clsx'
+import BN from 'bn.js'
type Props = {
t: Transaction
}
-// TODO: make this component support UI for Abstain and Split vote types
-const VotePill: React.FC<{ details: VoteDetails['details'] }> = ({ details }) => (
-
+// TODO: make this component support UI for Split vote types
+export const VotePill: React.FC<{ voteDetails: VoteDetails }> = ({ voteDetails }) => {
+ const { method, convictionVote } = voteDetails
+
+ const getLabelAndColor = (): Record
=> {
+ if (method === 'removeVote') {
+ return { label: 'Remove', color: 'bg-white' }
+ } else if (convictionVote === 'SplitAbstain') {
+ return { label: 'Abstain', color: 'bg-[#B9D9FF]' }
+ } else if (voteDetails.details.Standard?.vote.aye) {
+ return { label: 'Aye', color: 'bg-[#21C91D]' }
+ }
+ return { label: 'Nay', color: 'bg-[#F34A4A]' }
+ }
+
+ const { label, color } = getLabelAndColor()
+
+ return (
- {details.Standard?.vote.aye ? 'Aye' : 'Nay'}
-
-)
+ >
+
+ {label}
+
+ )
+}
export const VoteTransactionHeaderContent: React.FC