Split society candidates (#4857)

* Split society candidates

* trigger

* head

* Head to top

* loading

* Unneeded ?.
This commit is contained in:
Jaco Greeff 2021-03-16 10:15:17 +01:00 committed by GitHub
parent 1245eb2118
commit 5437017736
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
11 changed files with 93 additions and 38 deletions

View File

@ -1,3 +1,3 @@
18
19
0.45.2
0.71.2

View File

@ -12,8 +12,8 @@ import { AddressSmall } from '@polkadot/react-components';
import { useApi, useCall } from '@polkadot/react-hooks';
import { FormatBalance } from '@polkadot/react-query';
import Votes from '../Overview/Votes';
import CandidateVoting from './CandidateVoting';
import Votes from './Votes';
interface Props {
allMembers: string[];

View File

@ -0,0 +1,47 @@
// Copyright 2017-2021 @polkadot/app-society authors & contributors
// SPDX-License-Identifier: Apache-2.0
import React from 'react';
import { Button } from '@polkadot/react-components';
import { useToggle } from '@polkadot/react-hooks';
import { useTranslation } from '../translate';
import BidNew from './BidNew';
import Bids from './Bids';
import AllCandidates from './Candidates';
interface Props {
allMembers: string[];
className?: string;
isMember: boolean;
ownMembers: string[];
}
function Candidates ({ allMembers, className = '', isMember, ownMembers }: Props): React.ReactElement<Props> {
const { t } = useTranslation();
const [isBidOpen, toggleBidOpen] = useToggle();
return (
<div className={className}>
<Button.Group>
<Button
icon='plus'
label={t<string>('Submit bid')}
onClick={toggleBidOpen}
/>
{isBidOpen && (
<BidNew onClose={toggleBidOpen} />
)}
</Button.Group>
<AllCandidates
allMembers={allMembers}
isMember={isMember}
ownMembers={ownMembers}
/>
<Bids />
</div>
);
}
export default React.memo(Candidates);

View File

@ -28,19 +28,29 @@ function Members ({ className = '', info }: Props): React.ReactElement<Props> {
]);
const filtered = useMemo(
() => (members || []).filter((member) => !info || !info.hasDefender || !member.accountId.eq(info.defender)),
() => members && info
? members
.filter((member) => !info.hasDefender || !member.accountId.eq(info.defender))
.sort((a, b) =>
!info.head?.eq(a.accountId)
? 1
: !info.head?.eq(b.accountId)
? -1
: 0
)
: undefined,
[info, members]
);
return (
<Table
className={className}
empty={info && t<string>('No active members')}
empty={info && filtered && t<string>('No active members')}
header={headerRef.current}
>
{filtered.map((member): React.ReactNode => (
{info && filtered && filtered.map((member): React.ReactNode => (
<Member
isHead={info?.head?.eq(member.accountId)}
isHead={info.head?.eq(member.accountId)}
key={member.accountId.toString()}
value={member}
/>

View File

@ -6,54 +6,31 @@ import type { DeriveSociety } from '@polkadot/api-derive/types';
import React from 'react';
import styled from 'styled-components';
import { Button } from '@polkadot/react-components';
import { useApi, useCall, useToggle } from '@polkadot/react-hooks';
import { useApi, useCall } from '@polkadot/react-hooks';
import { useTranslation } from '../translate';
import useMembers from '../useMembers';
import BidNew from './BidNew';
import Bids from './Bids';
import Candidates from './Candidates';
import Defender from './Defender';
import Members from './Members';
import Summary from './Summary';
interface Props {
className?: string;
isMember: boolean;
ownMembers: string[];
}
function Overview ({ className }: Props): React.ReactElement<Props> {
const { t } = useTranslation();
function Overview ({ className, isMember, ownMembers }: Props): React.ReactElement<Props> {
const { api } = useApi();
const info = useCall<DeriveSociety>(api.derive.society.info);
const { allMembers, isMember, ownMembers } = useMembers();
const [isBidOpen, toggleBidOpen] = useToggle();
return (
<div className={className}>
<Summary info={info} />
<Button.Group>
<Button
icon='plus'
label={t<string>('Submit bid')}
onClick={toggleBidOpen}
/>
{isBidOpen && (
<BidNew onClose={toggleBidOpen} />
)}
</Button.Group>
<Defender
info={info}
isMember={isMember}
ownMembers={ownMembers}
/>
<Members info={info} />
<Candidates
allMembers={allMembers}
isMember={isMember}
ownMembers={ownMembers}
/>
<Bids />
</div>
);
}

View File

@ -1,14 +1,16 @@
// Copyright 2017-2021 @polkadot/app-society authors & contributors
// SPDX-License-Identifier: Apache-2.0
import React, { useRef } from 'react';
import React, { useMemo } from 'react';
import { Route, Switch } from 'react-router';
import { Tabs } from '@polkadot/react-components';
import Candidates from './Candidates';
import Overview from './Overview';
import { useTranslation } from './translate';
import useCounter from './useCounter';
import useMembers from './useMembers';
interface Props {
basePath: string;
@ -19,25 +21,44 @@ export { useCounter };
function SocietyApp ({ basePath, className }: Props): React.ReactElement<Props> {
const { t } = useTranslation();
const candidateCount = useCounter();
const { allMembers, isMember, ownMembers } = useMembers();
const itemsRef = useRef([
const items = useMemo(() => [
{
isRoot: true,
name: 'overview',
text: t<string>('Society overview')
},
{
count: candidateCount,
name: 'candidates',
text: t<string>('Candidates')
}
]);
], [candidateCount, t]);
return (
<main className={className}>
<header>
<Tabs
basePath={basePath}
items={itemsRef.current}
items={items}
/>
</header>
<Switch>
<Route component={Overview} />
<Route path={`${basePath}/candidates`}>
<Candidates
allMembers={allMembers}
isMember={isMember}
ownMembers={ownMembers}
/>
</Route>
<Route>
<Overview
isMember={isMember}
ownMembers={ownMembers}
/>
</Route>
</Switch>
</main>
);