/ packages / DApp / src / componentsMobile / ProposeMobile.tsx
ProposeMobile.tsx
  1  import { useContractFunction } from '@usedapp/core'
  2  import React, { useState } from 'react'
  3  import styled from 'styled-components'
  4  import {
  5    CardCommunity,
  6    VoteHistoryTable,
  7    VoteHistoryTableCell,
  8    VoteHistoryTableColumnCell,
  9    VoteHistoryTableColumnCellDate,
 10  } from '../components/card/CardCommunity'
 11  import { PublicKeyInput } from '../components/PublicKeyInput'
 12  import { CommunitySkeleton } from '../components/skeleton/CommunitySkeleton'
 13  import { VotePropose } from '../components/votes/VotePropose'
 14  import { Warning } from '../components/votes/VoteWarning'
 15  import { ColumnFlexDiv, MobileBlock, MobileHeading, MobileTop, WrapperTopSmall } from '../constants/styles'
 16  import { useCommunityDetails } from '../hooks/useCommunityDetails'
 17  import { useContracts } from '../hooks/useContracts'
 18  import { useProposeWarning } from '../hooks/useProposeWarning'
 19  import { CommunityDetail } from '../models/community'
 20  import { BigNumber } from 'ethers'
 21  import { ButtonPrimary } from '../components/Button'
 22  import { HeaderVotingMobile } from './VotingMobile'
 23  import { ConnectMobile } from './ConnectMobile'
 24  import { VoteProposeWrap, WarningWrap } from '../components/card/ProposeModal'
 25  import { HistoryLink } from './CardVoteMobile'
 26  
 27  interface ProposeBlockProps {
 28    communityFound: CommunityDetail
 29    proposingAmount: number
 30    setProposingAmount: (amount: number) => void
 31    send: (...args: any) => void
 32  }
 33  
 34  function ProposeBlock({ communityFound, proposingAmount, setProposingAmount, send }: ProposeBlockProps) {
 35    const warning = useProposeWarning(communityFound)
 36    return (
 37      <>
 38        <MobileBlock>
 39          <WarningWrap>{warning.text && <Warning icon={warning.icon} text={warning.text} />}</WarningWrap>
 40          {communityFound.validForAddition && (
 41            <VoteProposeWrap>
 42              <ProposingHeadingMobile>{` Add ${communityFound.name}?`}</ProposingHeadingMobile>
 43              <VotePropose
 44                setProposingAmount={setProposingAmount}
 45                proposingAmount={proposingAmount}
 46                disabled={!communityFound}
 47              />
 48            </VoteProposeWrap>
 49          )}
 50        </MobileBlock>
 51        {communityFound.validForAddition && (
 52          <ProposingBtn
 53            disabled={!communityFound || !proposingAmount || !!warning.text}
 54            onClick={() => send(1, communityFound.publicKey, BigNumber.from(proposingAmount))}
 55          >
 56            Confirm vote to add community
 57          </ProposingBtn>
 58        )}
 59      </>
 60    )
 61  }
 62  
 63  export function ProposeMobile() {
 64    const [proposingAmount, setProposingAmount] = useState(0)
 65    const [communityFound, setCommunityFound] = useState<CommunityDetail | undefined>(undefined)
 66    const [publicKey, setPublicKey] = useState('')
 67    const loading = useCommunityDetails(publicKey, setCommunityFound)
 68    const { votingContract } = useContracts()
 69    const { send } = useContractFunction(votingContract, 'initializeVotingRoom')
 70  
 71    const [showHistory, setShowHistory] = useState(false)
 72    const isDisabled = communityFound ? communityFound.votingHistory.length === 0 : false
 73  
 74    return (
 75      <ColumnFlexDiv>
 76        <HeaderVotingMobile>
 77          <ConnectMobile />
 78          <MobileTop>
 79            <ProposingHeading>Add community to directory</ProposingHeading>
 80            <PublicKeyInput onPublicKeyChange={setPublicKey} />
 81            {communityFound ? (
 82              <WrapperTopSmall>
 83                <CardCommunity community={communityFound} />
 84              </WrapperTopSmall>
 85            ) : (
 86              loading &&
 87              publicKey && (
 88                <WrapperTopSmall>
 89                  <CommunitySkeleton />
 90                </WrapperTopSmall>
 91              )
 92            )}
 93          </MobileTop>
 94        </HeaderVotingMobile>
 95  
 96        {/* {!publicKey && (
 97          <MobileBlock>
 98            <ProposingInfo>
 99              <span>ℹ️</span>
100              <InfoText>To propose a community, it must have at least 42 members and have a ENS domain.</InfoText>
101            </ProposingInfo>
102          </MobileBlock>
103        )} */}
104  
105        {communityFound && (
106          <ProposeBlock
107            communityFound={communityFound}
108            proposingAmount={proposingAmount}
109            send={send}
110            setProposingAmount={setProposingAmount}
111          />
112        )}
113        <HistoryWrap>
114          {!isDisabled && communityFound && (
115            <HistoryLink
116              className={showHistory ? 'opened' : ''}
117              onClick={() => setShowHistory(!showHistory)}
118              disabled={isDisabled}
119            >
120              Voting history
121            </HistoryLink>
122          )}
123          {showHistory && communityFound && (
124            <VoteHistoryTable>
125              <tbody>
126                <tr>
127                  <VoteHistoryTableColumnCellDate>Date</VoteHistoryTableColumnCellDate>
128                  <VoteHistoryTableColumnCell>Type</VoteHistoryTableColumnCell>
129                  <VoteHistoryTableColumnCell>Result</VoteHistoryTableColumnCell>
130                </tr>
131                {communityFound.votingHistory.map((vote) => {
132                  return (
133                    <tr key={vote.ID}>
134                      <VoteHistoryTableCell>{vote.date.toLocaleDateString()}</VoteHistoryTableCell>
135                      <VoteHistoryTableCell>{vote.type}</VoteHistoryTableCell>
136                      <VoteHistoryTableCell>{vote.result}</VoteHistoryTableCell>
137                    </tr>
138                  )
139                })}
140              </tbody>
141            </VoteHistoryTable>
142          )}
143        </HistoryWrap>
144      </ColumnFlexDiv>
145    )
146  }
147  
148  const ProposingHeading = styled(MobileHeading)`
149    margin-bottom: 8px;
150  `
151  
152  const ProposingHeadingMobile = styled(ProposingHeading)`
153    margin-bottom: 16px;
154  `
155  
156  const ProposingBtn = styled(ButtonPrimary)`
157    width: calc(100% - 32px);
158    padding: 10px 0;
159  `
160  const HistoryWrap = styled.div`
161    width: 100%;
162    padding: 0 16px;
163    align-self: flex-start;
164  `