From 2b534fc1fbe0e4e3012bcfa8baeb8124d0db416c Mon Sep 17 00:00:00 2001 From: Jaco Greeff Date: Thu, 12 Mar 2020 15:45:59 +0100 Subject: [PATCH] Additional wrappers via React.memo (#2377) * More React.memo * Last non-memo functional components in staking --- packages/apps/src/Apps.tsx | 4 +- packages/apps/src/Content/index.tsx | 4 +- packages/apps/src/SideBar/ChainInfo.tsx | 4 +- packages/apps/src/SideBar/NodeInfo.tsx | 4 +- packages/apps/src/SideBar/index.tsx | 4 +- packages/apps/src/TopBar.tsx | 4 +- packages/apps/src/overlays/Base.tsx | 4 +- packages/page-123code/src/AccountSelector.tsx | 4 +- packages/page-123code/src/Summary.tsx | 4 +- packages/page-accounts/src/Account.tsx | 4 +- packages/page-accounts/src/Banner.tsx | 4 +- packages/page-accounts/src/Overview.tsx | 4 +- packages/page-accounts/src/Vanity/Match.tsx | 4 +- packages/page-accounts/src/modals/Create.tsx | 4 +- packages/page-accounts/src/modals/Qr.tsx | 4 +- .../page-accounts/src/modals/Transfer.tsx | 4 +- packages/page-address-book/src/Address.tsx | 4 +- packages/page-address-book/src/Overview.tsx | 4 +- packages/page-claims/src/Claim.tsx | 4 +- .../page-contracts/src/Contracts/Call.tsx | 4 +- .../page-contracts/src/Contracts/Outcome.tsx | 4 +- packages/page-council/src/index.tsx | 4 +- packages/page-dashboard/src/Entry.tsx | 4 +- packages/page-dashboard/src/index.tsx | 4 +- .../src/Overview/DispatchBlock.tsx | 4 +- .../src/Overview/DispatchEntry.tsx | 4 +- .../src/Overview/DispatchQueue.tsx | 4 +- .../page-democracy/src/Overview/Externals.tsx | 4 +- .../page-democracy/src/Overview/PreImage.tsx | 4 +- .../src/Overview/PreImageButton.tsx | 4 +- .../page-democracy/src/Overview/Proposal.tsx | 4 +- .../src/Overview/ProposalCell.tsx | 4 +- .../page-democracy/src/Overview/Proposals.tsx | 4 +- .../page-democracy/src/Overview/Propose.tsx | 14 +- .../src/Overview/Referendum.tsx | 4 +- .../src/Overview/Referendums.tsx | 4 +- .../page-democracy/src/Overview/Seconding.tsx | 4 +- .../page-democracy/src/Overview/Summary.tsx | 9 +- .../page-democracy/src/Overview/Voting.tsx | 13 +- .../page-democracy/src/Overview/index.tsx | 22 +-- packages/page-explorer/src/BestHash.tsx | 4 +- packages/page-explorer/src/BlockHeader.tsx | 4 +- packages/page-explorer/src/BlockHeaders.tsx | 4 +- .../page-explorer/src/BlockInfo/ByHash.tsx | 7 +- .../page-explorer/src/BlockInfo/ByNumber.tsx | 4 +- .../page-explorer/src/BlockInfo/Events.tsx | 11 +- .../src/BlockInfo/Extrinsics.tsx | 19 +- packages/page-explorer/src/BlockInfo/Logs.tsx | 14 +- .../page-explorer/src/BlockInfo/index.tsx | 6 +- packages/page-explorer/src/Events.tsx | 11 +- packages/page-explorer/src/Forks.tsx | 174 +++++++++--------- packages/page-explorer/src/Main.tsx | 11 +- packages/page-explorer/src/NodeInfo/Peers.tsx | 12 +- .../page-explorer/src/NodeInfo/Summary.tsx | 10 +- packages/page-explorer/src/NodeInfo/index.tsx | 8 +- .../page-explorer/src/NodeInfo/translate.ts | 7 - packages/page-explorer/src/Query.tsx | 12 +- packages/page-explorer/src/Summary.tsx | 10 +- packages/page-explorer/src/SummarySession.tsx | 4 +- packages/page-explorer/src/index.tsx | 30 +-- packages/page-js/src/Output.tsx | 4 +- packages/page-js/src/Playground.tsx | 4 +- .../src/Overview/Parachain.tsx | 4 +- .../src/Overview/Parachains.tsx | 11 +- .../page-parachains/src/Parachain/Details.tsx | 4 +- .../src/Parachain/DispatchQueue.tsx | 4 +- .../page-parachains/src/Parachain/index.tsx | 4 +- .../page-parachains/src/ParachainInfo.tsx | 4 +- packages/page-settings/src/Developer.tsx | 4 +- packages/page-settings/src/SelectUrl.tsx | 32 ++-- .../page-society/src/Overview/Summary.tsx | 4 +- packages/page-society/src/Overview/index.tsx | 4 +- .../src/Actions/Account/InjectKeys.tsx | 4 +- .../Actions/Account/InputValidateAmount.tsx | 10 +- .../Account/InputValidationController.tsx | 4 +- .../Account/InputValidationSessionKey.tsx | 7 +- .../InputValidationUnstakeThreshold.tsx | 4 +- .../src/Actions/Account/Nominate.tsx | 4 +- .../src/Actions/Account/SetSessionKey.tsx | 4 +- packages/page-staking/src/Actions/index.tsx | 4 +- .../page-staking/src/Overview/CurrentList.tsx | 4 +- .../page-staking/src/Overview/Summary.tsx | 4 +- packages/page-staking/src/Overview/index.tsx | 4 +- packages/page-staking/src/Query/Validator.tsx | 4 +- packages/page-staking/src/Query/index.tsx | 4 +- packages/page-staking/src/Targets/Summary.tsx | 4 +- packages/page-staking/src/Targets/index.tsx | 4 +- packages/page-staking/src/index.tsx | 4 +- packages/page-storage/src/Query.tsx | 4 +- packages/page-storage/src/index.tsx | 20 +- packages/page-sudo/src/SetKey.tsx | 4 +- packages/page-toolbox/src/Rpc/Account.tsx | 4 +- packages/page-toolbox/src/Sign.tsx | 4 +- .../react-components/src/AccountIndex.tsx | 4 +- packages/react-components/src/ActionItem.tsx | 2 +- .../react-components/src/AddressToggle.tsx | 5 +- packages/react-components/src/Bubble.tsx | 4 +- .../react-components/src/Button/Group.tsx | 17 +- packages/react-components/src/Call.tsx | 4 +- packages/react-components/src/Card.tsx | 4 +- packages/react-components/src/CardSummary.tsx | 4 +- packages/react-components/src/ChainImg.tsx | 4 +- packages/react-components/src/ChainLock.tsx | 4 +- packages/react-components/src/Columar.tsx | 4 +- packages/react-components/src/CopyButton.tsx | 4 +- packages/react-components/src/Editor.tsx | 4 +- .../react-components/src/FilterOverlay.tsx | 4 +- packages/react-components/src/HelpOverlay.tsx | 4 +- packages/react-components/src/IconLink.tsx | 4 +- .../react-components/src/InfoForInput.tsx | 4 +- .../src/InputAddress/KeyPair.tsx | 4 +- .../src/InputAddressMulti.tsx | 4 +- .../src/InputAddressSimple.tsx | 4 +- .../react-components/src/InputBalance.tsx | 4 +- .../src/InputExtrinsic/LinkedWrapper.tsx | 4 +- packages/react-components/src/InputFile.tsx | 4 +- packages/react-components/src/Inset.tsx | 4 +- packages/react-components/src/LabelHelp.tsx | 4 +- .../react-components/src/LinkExternal.tsx | 4 +- packages/react-components/src/Messages.tsx | 4 +- .../react-components/src/ProposedAction.tsx | 2 +- packages/react-components/src/Spinner.tsx | 4 +- .../react-components/src/Status/index.tsx | 4 +- packages/react-components/src/SummaryBox.tsx | 4 +- packages/react-components/src/Table.tsx | 12 +- packages/react-components/src/Toggle.tsx | 4 +- packages/react-params/src/Param/Bare.tsx | 4 +- packages/react-params/src/Param/Option.tsx | 4 +- packages/react-query/src/FormatBalance.tsx | 4 +- packages/react-signer/src/Qr.tsx | 4 +- packages/react-signer/src/Transaction.tsx | 4 +- packages/react-signer/src/Unlock.tsx | 4 +- packages/react-signer/src/index.tsx | 4 +- 133 files changed, 485 insertions(+), 449 deletions(-) delete mode 100644 packages/page-explorer/src/NodeInfo/translate.ts diff --git a/packages/apps/src/Apps.tsx b/packages/apps/src/Apps.tsx index 0fb3d66153..ac24539623 100644 --- a/packages/apps/src/Apps.tsx +++ b/packages/apps/src/Apps.tsx @@ -103,7 +103,7 @@ function Apps ({ className }: Props): React.ReactElement { ); } -export default styled(Apps)` +export default React.memo(styled(Apps)` align-items: stretch; box-sizing: border-box; display: flex; @@ -219,4 +219,4 @@ export default styled(Apps)` opacity: 1; } } -`; +`); diff --git a/packages/apps/src/Content/index.tsx b/packages/apps/src/Content/index.tsx index 75e47d6d97..7f9b684271 100644 --- a/packages/apps/src/Content/index.tsx +++ b/packages/apps/src/Content/index.tsx @@ -63,7 +63,7 @@ function Content ({ className }: Props): React.ReactElement { ); } -export default styled(Content)` +export default React.memo(styled(Content)` background: #fafafa; display: flex; flex-direction: column; @@ -82,4 +82,4 @@ export default styled(Content)` .connecting { padding: 1rem 0; } -`; +`); diff --git a/packages/apps/src/SideBar/ChainInfo.tsx b/packages/apps/src/SideBar/ChainInfo.tsx index 5f6e513564..a74ba3cc77 100644 --- a/packages/apps/src/SideBar/ChainInfo.tsx +++ b/packages/apps/src/SideBar/ChainInfo.tsx @@ -41,7 +41,7 @@ function ChainInfo ({ className, onClick }: Props): React.ReactElement { ); } -export default styled(ChainInfo)` +export default React.memo(styled(ChainInfo)` border-top: 0.5rem solid transparent; cursor: pointer; padding: 0.75rem 1rem; @@ -75,4 +75,4 @@ export default styled(ChainInfo)` } } } -`; +`); diff --git a/packages/apps/src/SideBar/NodeInfo.tsx b/packages/apps/src/SideBar/NodeInfo.tsx index 7e92836bb6..eb7d640292 100644 --- a/packages/apps/src/SideBar/NodeInfo.tsx +++ b/packages/apps/src/SideBar/NodeInfo.tsx @@ -31,7 +31,7 @@ function NodeInfo ({ className }: Props): React.ReactElement { ); } -export default styled(NodeInfo)` +export default React.memo(styled(NodeInfo)` background: transparent; color: white; font-size: 0.75rem; @@ -49,4 +49,4 @@ export default styled(NodeInfo)` margin-bottom: 0.5rem; } } -`; +`); diff --git a/packages/apps/src/SideBar/index.tsx b/packages/apps/src/SideBar/index.tsx index ac38cfd6d4..56b0c1e4c0 100644 --- a/packages/apps/src/SideBar/index.tsx +++ b/packages/apps/src/SideBar/index.tsx @@ -152,7 +152,7 @@ function SideBar ({ className, collapse, handleResize, isCollapsed, isMenuOpen, const sideBorderWidth = '0.65rem'; -export default styled(SideBar)` +export default React.memo(styled(SideBar)` display: flex; position: relative; transition: width 0.3s linear; @@ -287,4 +287,4 @@ export default styled(SideBar)` top: -2.9rem !important; `} } -`; +`); diff --git a/packages/apps/src/TopBar.tsx b/packages/apps/src/TopBar.tsx index 607ccec1f9..a6845160ce 100644 --- a/packages/apps/src/TopBar.tsx +++ b/packages/apps/src/TopBar.tsx @@ -27,7 +27,7 @@ function TopBar ({ className }: Props): React.ReactElement { ); } -export default styled(TopBar)` +export default React.memo(styled(TopBar)` background: #f2f2f2; font-size: 0.85rem; line-height: 1rem; @@ -53,4 +53,4 @@ export default styled(TopBar)` border-width: 0; } } -`; +`); diff --git a/packages/apps/src/overlays/Base.tsx b/packages/apps/src/overlays/Base.tsx index 9d5e6d5c91..774779015b 100644 --- a/packages/apps/src/overlays/Base.tsx +++ b/packages/apps/src/overlays/Base.tsx @@ -46,7 +46,7 @@ function BaseOverlay ({ children, className, icon, type }: Props): React.ReactEl ); } -export default styled(BaseOverlay)` +export default React.memo(styled(BaseOverlay)` border-bottom: 1px solid transparent; left: 0; line-height: 1.5em; @@ -95,4 +95,4 @@ export default styled(BaseOverlay)` right: 0.75em; top: 0.75em; } -`; +`); diff --git a/packages/page-123code/src/AccountSelector.tsx b/packages/page-123code/src/AccountSelector.tsx index fdfb5e6884..81209d303f 100644 --- a/packages/page-123code/src/AccountSelector.tsx +++ b/packages/page-123code/src/AccountSelector.tsx @@ -40,10 +40,10 @@ function AccountSelector ({ className, onChange }: Props): React.ReactElement | null { ); } -export default styled(Banner)` +export default React.memo(styled(Banner)` padding: 0 0.5rem 0.5rem; .box { @@ -100,4 +100,4 @@ export default styled(Banner)` max-width: 50rem; } } -`; +`); diff --git a/packages/page-accounts/src/Overview.tsx b/packages/page-accounts/src/Overview.tsx index ea5b8de159..650cee4c6e 100644 --- a/packages/page-accounts/src/Overview.tsx +++ b/packages/page-accounts/src/Overview.tsx @@ -153,7 +153,7 @@ function Overview ({ className, onStatusChange }: Props): React.ReactElement | null { ); } -export default styled(Call)` +export default React.memo(styled(Call)` .rpc-toggle { margin-top: 1rem; display: flex; @@ -262,4 +262,4 @@ export default styled(Call)` .clear-all { float: right; } -`; +`); diff --git a/packages/page-contracts/src/Contracts/Outcome.tsx b/packages/page-contracts/src/Contracts/Outcome.tsx index b1fac21f9a..5b33f84cd9 100644 --- a/packages/page-contracts/src/Contracts/Outcome.tsx +++ b/packages/page-contracts/src/Contracts/Outcome.tsx @@ -55,7 +55,7 @@ function Outcome (props: Props): React.ReactElement | null { ); } -export default styled(Outcome)` +export default React.memo(styled(Outcome)` & { .info { display: inline-flex; @@ -101,4 +101,4 @@ export default styled(Outcome)` } } } -`; +`); diff --git a/packages/page-council/src/index.tsx b/packages/page-council/src/index.tsx index 3b11f51de4..52c1095f62 100644 --- a/packages/page-council/src/index.tsx +++ b/packages/page-council/src/index.tsx @@ -57,8 +57,8 @@ function CouncilApp ({ basePath, className }: Props): React.ReactElement ); } -export default styled(CouncilApp)` +export default React.memo(styled(CouncilApp)` .council--hidden { display: none; } -`; +`); diff --git a/packages/page-dashboard/src/Entry.tsx b/packages/page-dashboard/src/Entry.tsx index 661d8de607..30b0d20575 100644 --- a/packages/page-dashboard/src/Entry.tsx +++ b/packages/page-dashboard/src/Entry.tsx @@ -34,8 +34,8 @@ function Entry ({ className, route: { i18n, icon, name } }: Props): React.ReactE ); } -export default styled(Entry)` +export default React.memo(styled(Entry)` .name { margin-top: 0.75rem; } -`; +`); diff --git a/packages/page-dashboard/src/index.tsx b/packages/page-dashboard/src/index.tsx index 9a37ee85cb..2602df762d 100644 --- a/packages/page-dashboard/src/index.tsx +++ b/packages/page-dashboard/src/index.tsx @@ -52,7 +52,7 @@ function DashboardApp ({ className }: Props): React.ReactElement { ); } -export default styled(DashboardApp)` +export default React.memo(styled(DashboardApp)` .routes { display: flex; flex-direction: row; @@ -65,4 +65,4 @@ export default styled(DashboardApp)` text-align: center; } } -`; +`); diff --git a/packages/page-democracy/src/Overview/DispatchBlock.tsx b/packages/page-democracy/src/Overview/DispatchBlock.tsx index dc3705f37c..0e48bcdc19 100644 --- a/packages/page-democracy/src/Overview/DispatchBlock.tsx +++ b/packages/page-democracy/src/Overview/DispatchBlock.tsx @@ -24,7 +24,7 @@ interface Entry { referendumIndex: ReferendumIndex; } -export default function DispatchBlock ({ entries, keyPrefix, storageKey }: Props): React.ReactElement | null { +function DispatchBlock ({ entries, keyPrefix, storageKey }: Props): React.ReactElement | null { const [blockNumber, setBlockNumber] = useState(); const [expanded, setExpanded] = useState([]); @@ -67,3 +67,5 @@ export default function DispatchBlock ({ entries, keyPrefix, storageKey }: Props ); } + +export default React.memo(DispatchBlock); diff --git a/packages/page-democracy/src/Overview/DispatchEntry.tsx b/packages/page-democracy/src/Overview/DispatchEntry.tsx index 51d1fb0e7d..295a74aab5 100644 --- a/packages/page-democracy/src/Overview/DispatchEntry.tsx +++ b/packages/page-democracy/src/Overview/DispatchEntry.tsx @@ -23,7 +23,7 @@ interface Props { referendumIndex: ReferendumIndex; } -export default function DispatchEntry ({ blockNumber, hash, referendumIndex }: Props): React.ReactElement { +function DispatchEntry ({ blockNumber, hash, referendumIndex }: Props): React.ReactElement { const { t } = useTranslation(); const { api } = useApi(); const bestNumber = useCall(api.derive.chain.bestNumber, []) || new BN(0); @@ -65,3 +65,5 @@ export default function DispatchEntry ({ blockNumber, hash, referendumIndex }: P ); } + +export default React.memo(DispatchEntry); diff --git a/packages/page-democracy/src/Overview/DispatchQueue.tsx b/packages/page-democracy/src/Overview/DispatchQueue.tsx index 380a5951fa..bbe619d18d 100644 --- a/packages/page-democracy/src/Overview/DispatchQueue.tsx +++ b/packages/page-democracy/src/Overview/DispatchQueue.tsx @@ -15,7 +15,7 @@ interface Props { className?: string; } -export default function DispatchQueue ({ className }: Props): React.ReactElement | null { +function DispatchQueue ({ className }: Props): React.ReactElement | null { const { t } = useTranslation(); const { api } = useApi(); const queued = useCall<[BlockNumber, Hash, ReferendumIndex][]>(api.query.democracy.dispatchQueue, []); @@ -49,3 +49,5 @@ export default function DispatchQueue ({ className }: Props): React.ReactElement ); } + +export default React.memo(DispatchQueue); diff --git a/packages/page-democracy/src/Overview/Externals.tsx b/packages/page-democracy/src/Overview/Externals.tsx index 0db223f80a..66350d71cf 100644 --- a/packages/page-democracy/src/Overview/Externals.tsx +++ b/packages/page-democracy/src/Overview/Externals.tsx @@ -19,7 +19,7 @@ interface Props { className?: string; } -export default function Externals ({ className }: Props): React.ReactElement | null { +function Externals ({ className }: Props): React.ReactElement | null { const { t } = useTranslation(); const { api } = useApi(); const external = useCall>>(api.query.democracy.nextExternal, []); @@ -84,3 +84,5 @@ export default function Externals ({ className }: Props): React.ReactElement ); } + +export default React.memo(Externals); diff --git a/packages/page-democracy/src/Overview/PreImage.tsx b/packages/page-democracy/src/Overview/PreImage.tsx index 508b88c123..39a69fa0fb 100644 --- a/packages/page-democracy/src/Overview/PreImage.tsx +++ b/packages/page-democracy/src/Overview/PreImage.tsx @@ -89,9 +89,9 @@ function PreImage ({ className, isImminent: propsIsImminent, matchHash, onClose ); } -export default styled(PreImage)` +export default React.memo(styled(PreImage)` .toggleImminent { margin: 0.5rem 0; text-align: right; } -`; +`); diff --git a/packages/page-democracy/src/Overview/PreImageButton.tsx b/packages/page-democracy/src/Overview/PreImageButton.tsx index c3dc888cf9..59d4b6b9cd 100644 --- a/packages/page-democracy/src/Overview/PreImageButton.tsx +++ b/packages/page-democracy/src/Overview/PreImageButton.tsx @@ -18,7 +18,7 @@ interface Props { withoutOr?: boolean; } -export default function PreImageButton ({ hash, isImminent, proposal, withoutOr }: Props): React.ReactElement | null { +function PreImageButton ({ hash, isImminent, proposal, withoutOr }: Props): React.ReactElement | null { const { t } = useTranslation(); const [isPreimageOpen, togglePreimage] = useToggle(); @@ -45,3 +45,5 @@ export default function PreImageButton ({ hash, isImminent, proposal, withoutOr ); } + +export default React.memo(PreImageButton); diff --git a/packages/page-democracy/src/Overview/Proposal.tsx b/packages/page-democracy/src/Overview/Proposal.tsx index 4755391095..c8dede8d10 100644 --- a/packages/page-democracy/src/Overview/Proposal.tsx +++ b/packages/page-democracy/src/Overview/Proposal.tsx @@ -77,7 +77,7 @@ function Proposal ({ className, value: { balance, hash, index, proposal, propose ); } -export default styled(Proposal)` +export default React.memo(styled(Proposal)` .identityIcon { &:first-child { padding-top: 0; @@ -87,4 +87,4 @@ export default styled(Proposal)` margin-bottom: 4px; } } -`; +`); diff --git a/packages/page-democracy/src/Overview/ProposalCell.tsx b/packages/page-democracy/src/Overview/ProposalCell.tsx index e67a848e2d..0e66cdf5ba 100644 --- a/packages/page-democracy/src/Overview/ProposalCell.tsx +++ b/packages/page-democracy/src/Overview/ProposalCell.tsx @@ -31,7 +31,7 @@ function formatDocs (meta?: FunctionMetadataLatest): React.ReactNode | null { return strings.slice(0, firstEmpty).join(' '); } -export default function ProposalCell ({ className, proposal, proposalHash }: Props): React.ReactElement { +function ProposalCell ({ className, proposal, proposalHash }: Props): React.ReactElement { const { t } = useTranslation(); if (!proposal) { @@ -59,3 +59,5 @@ export default function ProposalCell ({ className, proposal, proposalHash }: Pro ); } + +export default React.memo(ProposalCell); diff --git a/packages/page-democracy/src/Overview/Proposals.tsx b/packages/page-democracy/src/Overview/Proposals.tsx index 1d71c5cb0e..3707182040 100644 --- a/packages/page-democracy/src/Overview/Proposals.tsx +++ b/packages/page-democracy/src/Overview/Proposals.tsx @@ -15,7 +15,7 @@ interface Props { className?: string; } -export default function Proposals ({ className }: Props): React.ReactElement { +function Proposals ({ className }: Props): React.ReactElement { const { t } = useTranslation(); const { api } = useApi(); const proposals = useCall(api.derive.democracy.proposals, []); @@ -43,3 +43,5 @@ export default function Proposals ({ className }: Props): React.ReactElement ); } + +export default React.memo(Proposals); diff --git a/packages/page-democracy/src/Overview/Propose.tsx b/packages/page-democracy/src/Overview/Propose.tsx index 06285e00a3..292c5ae18f 100644 --- a/packages/page-democracy/src/Overview/Propose.tsx +++ b/packages/page-democracy/src/Overview/Propose.tsx @@ -3,7 +3,7 @@ // of the Apache-2.0 license. See the LICENSE file for details. import BN from 'bn.js'; -import React, { useState } from 'react'; +import React, { useCallback, useState } from 'react'; import { Input, InputAddress, InputBalance, Modal, TxButton } from '@polkadot/react-components'; import { Available } from '@polkadot/react-query'; import { isHex } from '@polkadot/util'; @@ -15,16 +15,16 @@ interface Props { onClose: () => void; } -export default function Propose ({ className, onClose }: Props): React.ReactElement { +function Propose ({ className, onClose }: Props): React.ReactElement { const { t } = useTranslation(); const [accountId, setAccountId] = useState(null); const [balance, setBalance] = useState(); const [{ isHashValid, hash }, setHash] = useState<{ isHashValid: boolean; hash?: string }>({ isHashValid: false, hash: '' }); - const _onChangeHash = (hash?: string): void => setHash({ - isHashValid: isHex(hash, 256), - hash - }); + const _onChangeHash = useCallback( + (hash?: string): void => setHash({ isHashValid: isHex(hash, 256), hash }), + [] + ); return ( ); } + +export default React.memo(Propose); diff --git a/packages/page-democracy/src/Overview/Referendum.tsx b/packages/page-democracy/src/Overview/Referendum.tsx index fa89968a8d..4af120f0b3 100644 --- a/packages/page-democracy/src/Overview/Referendum.tsx +++ b/packages/page-democracy/src/Overview/Referendum.tsx @@ -138,7 +138,7 @@ function Referendum ({ className, idNumber, value }: Props): React.ReactElement< ); } -export default styled(Referendum)` +export default React.memo(styled(Referendum)` .democracy--Referendum-results { margin-bottom: 1em; @@ -146,4 +146,4 @@ export default styled(Referendum)` text-align: center; } } -`; +`); diff --git a/packages/page-democracy/src/Overview/Referendums.tsx b/packages/page-democracy/src/Overview/Referendums.tsx index 63670b62ae..3239a75db0 100644 --- a/packages/page-democracy/src/Overview/Referendums.tsx +++ b/packages/page-democracy/src/Overview/Referendums.tsx @@ -15,7 +15,7 @@ interface Props { className?: string; } -export default function Referendums ({ className }: Props): React.ReactElement { +function Referendums ({ className }: Props): React.ReactElement { const { t } = useTranslation(); const { api } = useApi(); const referendums = useCall(api.derive.democracy.referendums, []); @@ -44,3 +44,5 @@ export default function Referendums ({ className }: Props): React.ReactElement

); } + +export default React.memo(Referendums); diff --git a/packages/page-democracy/src/Overview/Seconding.tsx b/packages/page-democracy/src/Overview/Seconding.tsx index 2dc1d6b8c0..245ef72693 100644 --- a/packages/page-democracy/src/Overview/Seconding.tsx +++ b/packages/page-democracy/src/Overview/Seconding.tsx @@ -18,7 +18,7 @@ interface Props { proposalId: BN | number; } -export default function Seconding ({ depositors, proposal, proposalId }: Props): React.ReactElement | null { +function Seconding ({ depositors, proposal, proposalId }: Props): React.ReactElement | null { const { t } = useTranslation(); const { hasAccounts } = useAccounts(); const [accountId, setAccountId] = useState(null); @@ -73,3 +73,5 @@ export default function Seconding ({ depositors, proposal, proposalId }: Props): ); } + +export default React.memo(Seconding); diff --git a/packages/page-democracy/src/Overview/Summary.tsx b/packages/page-democracy/src/Overview/Summary.tsx index d810110e68..8c508acb1b 100644 --- a/packages/page-democracy/src/Overview/Summary.tsx +++ b/packages/page-democracy/src/Overview/Summary.tsx @@ -2,19 +2,18 @@ // This software may be modified and distributed under the terms // of the Apache-2.0 license. See the LICENSE file for details. -import { I18nProps as Props } from '@polkadot/react-components/types'; - import BN from 'bn.js'; import React from 'react'; import { SummaryBox, CardSummary } from '@polkadot/react-components'; import { useApi, useCall } from '@polkadot/react-hooks'; import { formatNumber } from '@polkadot/util'; -import translate from '../translate'; +import { useTranslation } from '../translate'; const ZERO = new BN(0); -function Summary ({ t }: Props): React.ReactElement { +function Summary (): React.ReactElement<{}> { + const { t } = useTranslation(); const { api } = useApi(); const activeProposals = useCall(api.derive.democracy.proposals, []); const bestNumber = useCall(api.derive.chain.bestNumber, []); @@ -56,4 +55,4 @@ function Summary ({ t }: Props): React.ReactElement { ); } -export default translate(Summary); +export default React.memo(Summary); diff --git a/packages/page-democracy/src/Overview/Voting.tsx b/packages/page-democracy/src/Overview/Voting.tsx index 92d060460e..6c7323ed91 100644 --- a/packages/page-democracy/src/Overview/Voting.tsx +++ b/packages/page-democracy/src/Overview/Voting.tsx @@ -4,7 +4,7 @@ import { PropIndex, Proposal } from '@polkadot/types/interfaces'; -import React, { useMemo, useState } from 'react'; +import React, { useCallback, useMemo, useState } from 'react'; import { Button, Dropdown, Modal, ProposedAction, VoteAccount, VoteActions, VoteToggle } from '@polkadot/react-components'; import { useAccounts, useApi, useToggle } from '@polkadot/react-hooks'; import { isBoolean } from '@polkadot/util'; @@ -18,7 +18,7 @@ interface Props { const CONVICTIONS: [number, number][] = [1, 2, 4, 8, 16, 32].map((lock, index) => [index + 1, lock]); -export default function Voting ({ proposal, referendumId }: Props): React.ReactElement | null { +function Voting ({ proposal, referendumId }: Props): React.ReactElement | null { const { t } = useTranslation(); const { api } = useApi(); const { hasAccounts } = useAccounts(); @@ -43,12 +43,15 @@ export default function Voting ({ proposal, referendumId }: Props): React.ReactE })) ], [t, enact]); + const _onChangeVote = useCallback( + (vote?: boolean): void => setVoteValue(isBoolean(vote) ? vote : true), + [] + ); + if (!hasAccounts) { return null; } - const _onChangeVote = (vote?: boolean): void => setVoteValue(isBoolean(vote) ? vote : true); - return ( <> {isVotingOpen && ( @@ -91,3 +94,5 @@ export default function Voting ({ proposal, referendumId }: Props): React.ReactE ); } + +export default React.memo(Voting); diff --git a/packages/page-democracy/src/Overview/index.tsx b/packages/page-democracy/src/Overview/index.tsx index a53a4e5a11..0293f71dd6 100644 --- a/packages/page-democracy/src/Overview/index.tsx +++ b/packages/page-democracy/src/Overview/index.tsx @@ -2,9 +2,10 @@ // This software may be modified and distributed under the terms // of the Apache-2.0 license. See the LICENSE file for details. -import React, { useState } from 'react'; +import React from 'react'; import styled from 'styled-components'; import { Button } from '@polkadot/react-components'; +import { useToggle } from '@polkadot/react-hooks'; import { useTranslation } from '../translate'; import DispatchQueue from './DispatchQueue'; @@ -21,11 +22,8 @@ interface Props { function Overview ({ className }: Props): React.ReactElement { const { t } = useTranslation(); - const [isPreimageOpen, setIsPreimageOpen] = useState(false); - const [isProposeOpen, setIsProposeOpen] = useState(false); - - const _togglePreimage = (): void => setIsPreimageOpen(!isPreimageOpen); - const _togglePropose = (): void => setIsProposeOpen(!isProposeOpen); + const [isPreimageOpen, togglePreimage] = useToggle(); + const [isProposeOpen, togglePropose] = useToggle(); return (

@@ -35,21 +33,21 @@ function Overview ({ className }: Props): React.ReactElement { icon='add' isPrimary label={t('Submit preimage')} - onClick={_togglePreimage} + onClick={togglePreimage} />
); } + +export default React.memo(BestHash); diff --git a/packages/page-explorer/src/BlockHeader.tsx b/packages/page-explorer/src/BlockHeader.tsx index cbc3e56943..1a71fe6ca2 100644 --- a/packages/page-explorer/src/BlockHeader.tsx +++ b/packages/page-explorer/src/BlockHeader.tsx @@ -82,7 +82,7 @@ function BlockHeader ({ className, isSummary, value, withExplorer, withLink }: P ); } -export default styled(BlockHeader)` +export default React.memo(styled(BlockHeader)` .author { font-size: 1rem; text-align: right; @@ -162,4 +162,4 @@ export default styled(BlockHeader)` } } } -`; +`); diff --git a/packages/page-explorer/src/BlockHeaders.tsx b/packages/page-explorer/src/BlockHeaders.tsx index 44522ee4b2..219f6f15f8 100644 --- a/packages/page-explorer/src/BlockHeaders.tsx +++ b/packages/page-explorer/src/BlockHeaders.tsx @@ -11,7 +11,7 @@ interface Props { headers: HeaderExtended[]; } -export default function BlockHeaders ({ headers }: Props): React.ReactElement { +function BlockHeaders ({ headers }: Props): React.ReactElement { return ( <> {headers.map((header, index): React.ReactNode => ( @@ -25,3 +25,5 @@ export default function BlockHeaders ({ headers }: Props): React.ReactElement ); } + +export default React.memo(BlockHeaders); diff --git a/packages/page-explorer/src/BlockInfo/ByHash.tsx b/packages/page-explorer/src/BlockInfo/ByHash.tsx index 6e98ee843e..8fe556cf92 100644 --- a/packages/page-explorer/src/BlockInfo/ByHash.tsx +++ b/packages/page-explorer/src/BlockInfo/ByHash.tsx @@ -4,7 +4,6 @@ // of the Apache-2.0 license. See the LICENSE file for details. import { EventRecord, SignedBlock } from '@polkadot/types/interfaces'; -import { I18nProps } from '@polkadot/react-components/types'; import React from 'react'; import styled from 'styled-components'; @@ -13,12 +12,12 @@ import { Columar } from '@polkadot/react-components'; import { useApi, useCall } from '@polkadot/react-hooks'; import BlockHeader from '../BlockHeader'; -import translate from '../translate'; import Events from './Events'; import Extrinsics from './Extrinsics'; import Logs from './Logs'; -interface Props extends I18nProps { +interface Props { + className?: string; value: string; } @@ -53,7 +52,7 @@ function BlockByHash ({ className, value }: Props): React.ReactElement | ); } -export default translate( +export default React.memo( styled(BlockByHash)` .exporer--BlockByHash-BlockHeader { border: none; diff --git a/packages/page-explorer/src/BlockInfo/ByNumber.tsx b/packages/page-explorer/src/BlockInfo/ByNumber.tsx index b3ffa81383..4d6054520d 100644 --- a/packages/page-explorer/src/BlockInfo/ByNumber.tsx +++ b/packages/page-explorer/src/BlockInfo/ByNumber.tsx @@ -14,7 +14,7 @@ interface Props { value: string; } -export default function BlockByNumber ({ value }: Props): React.ReactElement | null { +function BlockByNumber ({ value }: Props): React.ReactElement | null { const { api } = useApi(); const getBlockHash = useCall(api.rpc.chain.getBlockHash as any, [value]); @@ -26,3 +26,5 @@ export default function BlockByNumber ({ value }: Props): React.ReactElement ); } + +export default React.memo(BlockByNumber); diff --git a/packages/page-explorer/src/BlockInfo/Events.tsx b/packages/page-explorer/src/BlockInfo/Events.tsx index c1a31e170d..48bde99c55 100644 --- a/packages/page-explorer/src/BlockInfo/Events.tsx +++ b/packages/page-explorer/src/BlockInfo/Events.tsx @@ -3,19 +3,20 @@ // of the Apache-2.0 license. See the LICENSE file for details. import { EventRecord } from '@polkadot/types/interfaces'; -import { I18nProps } from '@polkadot/react-components/types'; import React from 'react'; import { Column } from '@polkadot/react-components'; import EventsDisplay from '../Events'; -import translate from '../translate'; +import { useTranslation } from '../translate'; -interface Props extends I18nProps { +interface Props { value?: EventRecord[]; } -function Events ({ value, t }: Props): React.ReactElement | null { +function Events ({ value }: Props): React.ReactElement | null { + const { t } = useTranslation(); + if (!value || !value.length) { return null; } @@ -34,4 +35,4 @@ function Events ({ value, t }: Props): React.ReactElement | null { ); } -export default translate(Events); +export default React.memo(Events); diff --git a/packages/page-explorer/src/BlockInfo/Extrinsics.tsx b/packages/page-explorer/src/BlockInfo/Extrinsics.tsx index 1456d34414..e233b16d01 100644 --- a/packages/page-explorer/src/BlockInfo/Extrinsics.tsx +++ b/packages/page-explorer/src/BlockInfo/Extrinsics.tsx @@ -3,7 +3,6 @@ // of the Apache-2.0 license. See the LICENSE file for details. import { BlockNumber, Extrinsic } from '@polkadot/types/interfaces'; -import { I18nProps } from '@polkadot/react-components/types'; import React from 'react'; import styled from 'styled-components'; @@ -11,16 +10,17 @@ import { registry } from '@polkadot/react-api'; import { AddressMini, Call, Column, LinkExternal } from '@polkadot/react-components'; import { formatNumber } from '@polkadot/util'; -import translate from '../translate'; +import { useTranslation } from '../translate'; -interface Props extends I18nProps { +interface Props { blockNumber?: BlockNumber; + className?: string; label?: React.ReactNode; value?: Extrinsic[] | null; } -function renderExtrinsic (props: Props, extrinsic: Extrinsic, index: number): React.ReactNode { - const { blockNumber, t } = props; +function renderExtrinsic (props: Props, extrinsic: Extrinsic, index: number, t: (s: string, opt?: any) => string): React.ReactNode { + const { blockNumber } = props; const { meta, method, section } = registry.findMetaCall(extrinsic.callIndex); const isMortal = extrinsic.era.isMortalEra; let eraEnd; @@ -81,7 +81,8 @@ function renderExtrinsic (props: Props, extrinsic: Extrinsic, index: number): Re } function Extrinsics (props: Props): React.ReactElement { - const { className, label, t, value } = props; + const { t } = useTranslation(); + const { className, label, value } = props; return ( { > {value?.map((extrinsic, index): React.ReactNode => { try { - return renderExtrinsic(props, extrinsic, index); + return renderExtrinsic(props, extrinsic, index, t); } catch (error) { console.error(error); - return props.t('Unable to render extrinsic'); + return t('Unable to render extrinsic'); } })} ); } -export default translate(styled(Extrinsics)` +export default React.memo(styled(Extrinsics)` .explorer--BlockByHash-header { position: absolute; top: 0.25rem; diff --git a/packages/page-explorer/src/BlockInfo/Logs.tsx b/packages/page-explorer/src/BlockInfo/Logs.tsx index 3a21f0960e..498f4cb1ae 100644 --- a/packages/page-explorer/src/BlockInfo/Logs.tsx +++ b/packages/page-explorer/src/BlockInfo/Logs.tsx @@ -4,16 +4,15 @@ import { DigestItem } from '@polkadot/types/interfaces'; import { Codec, TypeDef } from '@polkadot/types/types'; -import { I18nProps } from '@polkadot/react-components/types'; import React from 'react'; import { Struct, Tuple, Raw, Vec, getTypeDef } from '@polkadot/types'; import { Column } from '@polkadot/react-components'; import Params from '@polkadot/react-params'; -import translate from '../translate'; +import { useTranslation } from '../translate'; -interface Props extends I18nProps { +interface Props { value?: DigestItem[]; } @@ -86,7 +85,7 @@ function formatVector (vector: Vec): React.ReactNode { ); } -function renderItem ({ t }: Props): (item: DigestItem, index: number) => React.ReactNode { +function renderItem (t: (s: string, opt?: any) => string): (item: DigestItem, index: number) => React.ReactNode { return function LogItem (item: DigestItem, index: number): React.ReactNode { let content: React.ReactNode; @@ -122,7 +121,8 @@ function renderItem ({ t }: Props): (item: DigestItem, index: number) => React.R } function Logs (props: Props): React.ReactElement | null { - const { t, value } = props; + const { value } = props; + const { t } = useTranslation(); if (!value || !value.length) { return null; @@ -130,9 +130,9 @@ function Logs (props: Props): React.ReactElement | null { return ( - {value.map(renderItem(props))} + {value.map(renderItem(t))} ); } -export default translate(Logs); +export default React.memo(Logs); diff --git a/packages/page-explorer/src/BlockInfo/index.tsx b/packages/page-explorer/src/BlockInfo/index.tsx index 6a568936be..d397e702db 100644 --- a/packages/page-explorer/src/BlockInfo/index.tsx +++ b/packages/page-explorer/src/BlockInfo/index.tsx @@ -3,7 +3,6 @@ // of the Apache-2.0 license. See the LICENSE file for details. import { BlockNumber } from '@polkadot/types/interfaces'; -import { BareProps as Props } from '@polkadot/react-components/types'; import React, { useEffect, useState } from 'react'; import { useParams } from 'react-router-dom'; @@ -14,8 +13,7 @@ import Query from '../Query'; import BlockByHash from './ByHash'; import BlockByNumber from './ByNumber'; -// eslint-disable-next-line @typescript-eslint/no-unused-vars -export default function Entry (props: Props): React.ReactElement | null { +function Entry (): React.ReactElement<{}> | null { const { api } = useApi(); const bestNumber = useCall(api.derive.chain.bestNumber, []); const { value } = useParams(); @@ -47,3 +45,5 @@ export default function Entry (props: Props): React.ReactElement | null { ); } + +export default React.memo(Entry); diff --git a/packages/page-explorer/src/Events.tsx b/packages/page-explorer/src/Events.tsx index 6404717948..0e883b23ba 100644 --- a/packages/page-explorer/src/Events.tsx +++ b/packages/page-explorer/src/Events.tsx @@ -2,23 +2,24 @@ // This software may be modified and distributed under the terms // of the Apache-2.0 license. See the LICENSE file for details. -import { I18nProps } from '@polkadot/react-components/types'; import { KeyedEvent } from './types'; import React from 'react'; import { Event as EventDisplay } from '@polkadot/react-components'; import { formatNumber } from '@polkadot/util'; -import translate from './translate'; +import { useTranslation } from './translate'; -interface Props extends I18nProps { +interface Props { emptyLabel?: React.ReactNode; events: KeyedEvent[]; eventClassName?: string; withoutIndex?: boolean; } -function Events ({ emptyLabel, eventClassName, events, withoutIndex, t }: Props): React.ReactElement { +function Events ({ emptyLabel, eventClassName, events, withoutIndex }: Props): React.ReactElement { + const { t } = useTranslation(); + if (!events || events.length === 0) { return (
@@ -72,4 +73,4 @@ function Events ({ emptyLabel, eventClassName, events, withoutIndex, t }: Props) ); } -export default translate(Events); +export default React.memo(Events); diff --git a/packages/page-explorer/src/Forks.tsx b/packages/page-explorer/src/Forks.tsx index 8a035bed70..fa14443062 100644 --- a/packages/page-explorer/src/Forks.tsx +++ b/packages/page-explorer/src/Forks.tsx @@ -4,7 +4,6 @@ // of the Apache-2.0 license. See the LICENSE file for details. import { ApiProps } from '@polkadot/react-api/types'; -import { I18nProps } from '@polkadot/react-components/types'; import { Header } from '@polkadot/types/interfaces'; import React, { useEffect, useRef, useState } from 'react'; @@ -13,7 +12,7 @@ import { CardSummary, IdentityIcon, SummaryBox } from '@polkadot/react-component import { useApi } from '@polkadot/react-hooks'; import { formatNumber } from '@polkadot/util'; -import translate from './translate'; +import { useTranslation } from './translate'; interface LinkHeader { author: string | null; @@ -33,7 +32,7 @@ interface Link { hdr: LinkHeader; } -interface Props extends ApiProps, I18nProps { +interface Props extends ApiProps { className?: string; finHead?: Header; newHead?: Header; @@ -203,7 +202,8 @@ function renderRows (rows: Row[]): React.ReactNode[] { }); } -function Forks ({ className, t }: Props): React.ReactElement | null { +function Forks ({ className }: Props): React.ReactElement | null { + const { t } = useTranslation(); const { api } = useApi(); const [tree, setTree] = useState(null); const childrenRef = useRef>(new Map([['root', []]])); @@ -375,103 +375,101 @@ function Forks ({ className, t }: Props): React.ReactElement | null { ); } -export default translate( - styled(Forks)` - margin-bottom: 1.5rem; +export default React.memo(styled(Forks)` + margin-bottom: 1.5rem; - table { - border-collapse: separate; - border-spacing: 0.25rem; - font-family: monospace; + table { + border-collapse: separate; + border-spacing: 0.25rem; + font-family: monospace; - /* tr { - opacity: 0.05; + /* tr { + opacity: 0.05; - &:nth-child(1) { opacity: 1; } - &:nth-child(2) { opacity: 0.95; } - &:nth-child(3) { opacity: 0.9; } - &:nth-child(4) { opacity: 0.85; } - &:nth-child(5) { opacity: 0.8; } - &:nth-child(6) { opacity: 0.75; } - &:nth-child(7) { opacity: 0.70; } - &:nth-child(8) { opacity: 0.65; } - &:nth-child(9) { opacity: 0.6; } - &:nth-child(10) { opacity: 0.55; } - &:nth-child(11) { opacity: 0.6; } - &:nth-child(12) { opacity: 0.55; } - &:nth-child(13) { opacity: 0.5; } - &:nth-child(14) { opacity: 0.45; } - &:nth-child(15) { opacity: 0.4; } - &:nth-child(16) { opacity: 0.35; } - &:nth-child(17) { opacity: 0.3; } - &:nth-child(18) { opacity: 0.25; } - &:nth-child(19) { opacity: 0.2; } - &:nth-child(20) { opacity: 0.15; } - &:nth-child(21) { opacity: 0.1; } - } */ + &:nth-child(1) { opacity: 1; } + &:nth-child(2) { opacity: 0.95; } + &:nth-child(3) { opacity: 0.9; } + &:nth-child(4) { opacity: 0.85; } + &:nth-child(5) { opacity: 0.8; } + &:nth-child(6) { opacity: 0.75; } + &:nth-child(7) { opacity: 0.70; } + &:nth-child(8) { opacity: 0.65; } + &:nth-child(9) { opacity: 0.6; } + &:nth-child(10) { opacity: 0.55; } + &:nth-child(11) { opacity: 0.6; } + &:nth-child(12) { opacity: 0.55; } + &:nth-child(13) { opacity: 0.5; } + &:nth-child(14) { opacity: 0.45; } + &:nth-child(15) { opacity: 0.4; } + &:nth-child(16) { opacity: 0.35; } + &:nth-child(17) { opacity: 0.3; } + &:nth-child(18) { opacity: 0.25; } + &:nth-child(19) { opacity: 0.2; } + &:nth-child(20) { opacity: 0.15; } + &:nth-child(21) { opacity: 0.1; } + } */ - td { - padding: 0.25rem 0.5rem; - text-align: center; + td { + padding: 0.25rem 0.5rem; + text-align: center; - .author, - .contents { - display: inline-block; - vertical-align: middle; + .author, + .contents { + display: inline-block; + vertical-align: middle; + } + + .author { + margin-right: 0.25rem; + } + + .contents { + .hash, .parent { + margin: 0 auto; + max-width: 6rem; + overflow: hidden; + text-overflow: ellipsis; + white-space: nowrap; } - .author { - margin-right: 0.25rem; + .parent { + font-size: 0.75rem; + line-height: 0.75rem; + max-width: 4.5rem; + } + } + + &.blockNumber { + font-size: 1.25rem; + } + + &.header { + background: #f5f5f5; + border: 1px solid #eee; + border-radius: 0.25rem; + + &.isEmpty { + background: transparent; + border-color: transparent; } - .contents { - .hash, .parent { - margin: 0 auto; - max-width: 6rem; - overflow: hidden; - text-overflow: ellipsis; - white-space: nowrap; - } - - .parent { - font-size: 0.75rem; - line-height: 0.75rem; - max-width: 4.5rem; - } + &.isFinalized { + background: rgba(0, 255, 0, 0.1); + border-color: rgba(0, 255, 0, 0.17); } - &.blockNumber { - font-size: 1.25rem; + &.isLink { + background: transparent; + border-color: transparent; + line-height: 1rem; + padding: 0; } - &.header { - background: #f5f5f5; - border: 1px solid #eee; - border-radius: 0.25rem; - - &.isEmpty { - background: transparent; - border-color: transparent; - } - - &.isFinalized { - background: rgba(0, 255, 0, 0.1); - border-color: rgba(0, 255, 0, 0.17); - } - - &.isLink { - background: transparent; - border-color: transparent; - line-height: 1rem; - padding: 0; - } - - &.isMissing { - background: rgba(255, 0, 0, 0.05); - border-color: rgba(255, 0, 0, 0.06); - } + &.isMissing { + background: rgba(255, 0, 0, 0.05); + border-color: rgba(255, 0, 0, 0.06); } } } - ` -); + } +`); diff --git a/packages/page-explorer/src/Main.tsx b/packages/page-explorer/src/Main.tsx index ab1927c116..5704738942 100644 --- a/packages/page-explorer/src/Main.tsx +++ b/packages/page-explorer/src/Main.tsx @@ -2,7 +2,6 @@ // This software may be modified and distributed under the terms // of the Apache-2.0 license. See the LICENSE file for details. -import { I18nProps } from '@polkadot/react-components/types'; import { KeyedEvent } from './types'; import React from 'react'; @@ -13,14 +12,16 @@ import BlockHeaders from './BlockHeaders'; import Events from './Events'; import Query from './Query'; import Summary from './Summary'; -import translate from './translate'; +import { useTranslation } from './translate'; -interface Props extends I18nProps { +interface Props { events: KeyedEvent[]; headers: HeaderExtended[]; } -function Main ({ events, headers, t }: Props): React.ReactElement { +function Main ({ events, headers }: Props): React.ReactElement { + const { t } = useTranslation(); + return ( <> @@ -37,4 +38,4 @@ function Main ({ events, headers, t }: Props): React.ReactElement { ); } -export default translate(Main); +export default React.memo(Main); diff --git a/packages/page-explorer/src/NodeInfo/Peers.tsx b/packages/page-explorer/src/NodeInfo/Peers.tsx index 5484dbcac1..6214f6383d 100644 --- a/packages/page-explorer/src/NodeInfo/Peers.tsx +++ b/packages/page-explorer/src/NodeInfo/Peers.tsx @@ -3,15 +3,15 @@ // of the Apache-2.0 license. See the LICENSE file for details. import { PeerInfo } from '@polkadot/types/interfaces'; -import { I18nProps } from '@polkadot/react-components/types'; import React from 'react'; import styled from 'styled-components'; import { formatNumber } from '@polkadot/util'; -import translate from './translate'; +import { useTranslation } from '../translate'; -interface Props extends I18nProps { +interface Props { + className?: string; peers?: PeerInfo[] | null; } @@ -28,7 +28,9 @@ const renderPeer = (peer: PeerInfo): React.ReactNode => { ); }; -function Peers ({ className, peers, t }: Props): React.ReactElement { +function Peers ({ className, peers }: Props): React.ReactElement { + const { t } = useTranslation(); + return (

{t('connected peers')}

@@ -63,7 +65,7 @@ function Peers ({ className, peers, t }: Props): React.ReactElement { ); } -export default translate( +export default React.memo( styled(Peers)` table { width: 100%; diff --git a/packages/page-explorer/src/NodeInfo/Summary.tsx b/packages/page-explorer/src/NodeInfo/Summary.tsx index ae06f87112..3e98588cf0 100644 --- a/packages/page-explorer/src/NodeInfo/Summary.tsx +++ b/packages/page-explorer/src/NodeInfo/Summary.tsx @@ -2,7 +2,6 @@ // This software may be modified and distributed under the terms // of the Apache-2.0 license. See the LICENSE file for details. -import { I18nProps } from '@polkadot/react-components/types'; import { Info } from './types'; import BN from 'bn.js'; @@ -11,9 +10,9 @@ import { SummaryBox, CardSummary } from '@polkadot/react-components'; import { formatNumber } from '@polkadot/util'; import { BestNumber, Elapsed } from '@polkadot/react-query'; -import translate from './translate'; +import { useTranslation } from '../translate'; -interface Props extends I18nProps { +interface Props { nextRefresh: number; info: Info; } @@ -21,7 +20,8 @@ interface Props extends I18nProps { const ZERO = new BN(0); const EMPTY_INFO = { extrinsics: null, health: null, peers: null }; -function Summary ({ info: { extrinsics, health, peers } = EMPTY_INFO, nextRefresh, t }: Props): React.ReactElement { +function Summary ({ info: { extrinsics, health, peers } = EMPTY_INFO, nextRefresh }: Props): React.ReactElement { + const { t } = useTranslation(); const [peerBest, setPeerBest] = useState(ZERO); useEffect((): void => { @@ -88,4 +88,4 @@ function Summary ({ info: { extrinsics, health, peers } = EMPTY_INFO, nextRefres ); } -export default translate(Summary); +export default React.memo(Summary); diff --git a/packages/page-explorer/src/NodeInfo/index.tsx b/packages/page-explorer/src/NodeInfo/index.tsx index 11f8a2a988..cb629185c4 100644 --- a/packages/page-explorer/src/NodeInfo/index.tsx +++ b/packages/page-explorer/src/NodeInfo/index.tsx @@ -2,7 +2,6 @@ // This software may be modified and distributed under the terms // of the Apache-2.0 license. See the LICENSE file for details. -import { I18nProps as Props } from '@polkadot/react-components/types'; import { Info } from './types'; import React, { useEffect, useState } from 'react'; @@ -10,9 +9,9 @@ import { ApiPromise } from '@polkadot/api'; import { useApi } from '@polkadot/react-hooks'; import Extrinsics from '../BlockInfo/Extrinsics'; +import { useTranslation } from '../translate'; import Peers from './Peers'; import Summary from './Summary'; -import translate from './translate'; const POLL_TIMEOUT = 9900; @@ -31,7 +30,8 @@ async function retrieveInfo (api: ApiPromise): Promise> { } } -function NodeInfo ({ t }: Props): React.ReactElement { +export default function NodeInfo (): React.ReactElement<{}> { + const { t } = useTranslation(); const { api } = useApi(); const [info, setInfo] = useState>({}); const [nextRefresh, setNextRefresh] = useState(Date.now()); @@ -68,5 +68,3 @@ function NodeInfo ({ t }: Props): React.ReactElement { ); } - -export default translate(NodeInfo); diff --git a/packages/page-explorer/src/NodeInfo/translate.ts b/packages/page-explorer/src/NodeInfo/translate.ts deleted file mode 100644 index 4df53bdb7f..0000000000 --- a/packages/page-explorer/src/NodeInfo/translate.ts +++ /dev/null @@ -1,7 +0,0 @@ -// Copyright 2017-2020 @polkadot/app-nodeinfo authors & contributors -// This software may be modified and distributed under the terms -// of the Apache-2.0 license. See the LICENSE file for details. - -import { withTranslation } from 'react-i18next'; - -export default withTranslation(['app-explorer']); diff --git a/packages/page-explorer/src/Query.tsx b/packages/page-explorer/src/Query.tsx index ed38a924dd..692ef906ce 100644 --- a/packages/page-explorer/src/Query.tsx +++ b/packages/page-explorer/src/Query.tsx @@ -2,16 +2,15 @@ // This software may be modified and distributed under the terms // of the Apache-2.0 license. See the LICENSE file for details. -import { I18nProps } from '@polkadot/react-components/types'; - import React, { useState } from 'react'; import styled from 'styled-components'; import { Button, FilterOverlay, Input } from '@polkadot/react-components'; import { isHex } from '@polkadot/util'; -import translate from './translate'; +import { useTranslation } from './translate'; -interface Props extends I18nProps { +interface Props { + className?: string; value?: string; } @@ -30,7 +29,8 @@ function stateFromValue (value: string): State { }; } -function Query ({ className, t, value: propsValue }: Props): React.ReactElement { +function Query ({ className, value: propsValue }: Props): React.ReactElement { + const { t } = useTranslation(); const [{ value, isValid }, setState] = useState(stateFromValue(propsValue || '')); const _setHash = (value: string): void => setState(stateFromValue(value)); @@ -60,7 +60,7 @@ function Query ({ className, t, value: propsValue }: Props): React.ReactElement< ); } -export default translate(styled(Query)` +export default React.memo(styled(Query)` .explorer--query { width: 20em; } diff --git a/packages/page-explorer/src/Summary.tsx b/packages/page-explorer/src/Summary.tsx index c62d42a153..2cab733e8c 100644 --- a/packages/page-explorer/src/Summary.tsx +++ b/packages/page-explorer/src/Summary.tsx @@ -2,19 +2,19 @@ // This software may be modified and distributed under the terms // of the Apache-2.0 license. See the LICENSE file for details. -import { I18nProps as Props } from '@polkadot/react-components/types'; - import BN from 'bn.js'; import React from 'react'; import { SummaryBox, CardSummary } from '@polkadot/react-components'; import { BestFinalized, BestNumber, BlockToTime, TimeNow, TotalIssuance } from '@polkadot/react-query'; import SummarySession from './SummarySession'; -import translate from './translate'; +import { useTranslation } from './translate'; const ONE_BLOCK = new BN(1); -function Summary ({ t }: Props): React.ReactElement { +function Summary (): React.ReactElement<{}> { + const { t } = useTranslation(); + return (
@@ -49,4 +49,4 @@ function Summary ({ t }: Props): React.ReactElement { ); } -export default translate(Summary); +export default React.memo(Summary); diff --git a/packages/page-explorer/src/SummarySession.tsx b/packages/page-explorer/src/SummarySession.tsx index 91d34580af..b203c97d39 100644 --- a/packages/page-explorer/src/SummarySession.tsx +++ b/packages/page-explorer/src/SummarySession.tsx @@ -16,7 +16,7 @@ interface Props { withSession?: boolean; } -export default function SummarySession ({ withEra = true, withSession = true }: Props): React.ReactElement { +function SummarySession ({ withEra = true, withSession = true }: Props): React.ReactElement { const { t } = useTranslation(); const { api } = useApi(); const sessionInfo = useCall(api.derive.session?.info, []); @@ -74,3 +74,5 @@ export default function SummarySession ({ withEra = true, withSession = true }: ); } + +export default React.memo(SummarySession); diff --git a/packages/page-explorer/src/index.tsx b/packages/page-explorer/src/index.tsx index c634027f61..2fd020783b 100644 --- a/packages/page-explorer/src/index.tsx +++ b/packages/page-explorer/src/index.tsx @@ -78,32 +78,4 @@ function ExplorerApp ({ basePath, className }: Props): React.ReactElement ); } -export default ExplorerApp; - -// export default styled(ExplorerApp)` -// .explorer--Container { -// color: inherit; - -// .header { -// position: relative; -// vertical-align: middle; - -// h3 { -// margin: 0; -// } -// } - -// .description { -// color: rgba(0, 0, 0, 0.6); -// margin: 0rem 0 0.5rem 0; -// overflow: hidden; -// text-overflow: ellipsis; -// vertical-align: middle; -// white-space: nowrap; -// } - -// > .details { -// word-break: break-all; -// } -// } -// `; +export default React.memo(ExplorerApp); diff --git a/packages/page-js/src/Output.tsx b/packages/page-js/src/Output.tsx index d59ec0ae33..809cb2b857 100644 --- a/packages/page-js/src/Output.tsx +++ b/packages/page-js/src/Output.tsx @@ -51,7 +51,7 @@ function Output ({ children, className, logs }: Props): React.ReactElement { ); } -export default styled(Playground)` +export default React.memo(styled(Playground)` display: flex; flex-direction: column; height: 100vh; @@ -334,4 +334,4 @@ export default styled(Playground)` margin: 0; } } -`; +`); diff --git a/packages/page-parachains/src/Overview/Parachain.tsx b/packages/page-parachains/src/Overview/Parachain.tsx index 326dd5c5a6..40855c7f06 100644 --- a/packages/page-parachains/src/Overview/Parachain.tsx +++ b/packages/page-parachains/src/Overview/Parachain.tsx @@ -84,7 +84,7 @@ function Parachain ({ className, parachain: { didUpdate, id, info, pendingSwapId ); } -export default styled(Parachain)` +export default React.memo(styled(Parachain)` & { cursor: pointer !important; } @@ -113,4 +113,4 @@ export default styled(Parachain)` .did-update { margin-bottom: 0; } -`; +`); diff --git a/packages/page-parachains/src/Overview/Parachains.tsx b/packages/page-parachains/src/Overview/Parachains.tsx index 25f43e64cd..dee5944940 100644 --- a/packages/page-parachains/src/Overview/Parachains.tsx +++ b/packages/page-parachains/src/Overview/Parachains.tsx @@ -29,9 +29,10 @@ function Parachains ({ parachains }: Props): React.ReactElement { ); } -export default styled(Parachains)` -tbody { - tr { - cursor: pointer; +export default React.memo(styled(Parachains)` + tbody { + tr { + cursor: pointer; + } } -}`; +`); diff --git a/packages/page-parachains/src/Parachain/Details.tsx b/packages/page-parachains/src/Parachain/Details.tsx index ef986678a9..7d82bad6d7 100644 --- a/packages/page-parachains/src/Parachain/Details.tsx +++ b/packages/page-parachains/src/Parachain/Details.tsx @@ -7,7 +7,6 @@ import { Bytes, Option } from '@polkadot/types'; import FileSaver from 'file-saver'; import React from 'react'; -import styled from 'styled-components'; import { Card, IconLink, Labelled, Output, Static } from '@polkadot/react-components'; import { useApi } from '@polkadot/react-hooks'; @@ -81,5 +80,4 @@ function Details ({ parachain: { heads, info, id } }: Props): React.ReactElement ); } -export default styled(Details)` -`; +export default React.memo(Details); diff --git a/packages/page-parachains/src/Parachain/DispatchQueue.tsx b/packages/page-parachains/src/Parachain/DispatchQueue.tsx index 92a6820ff6..2639c87fcd 100644 --- a/packages/page-parachains/src/Parachain/DispatchQueue.tsx +++ b/packages/page-parachains/src/Parachain/DispatchQueue.tsx @@ -66,8 +66,8 @@ function DispatchQueue ({ className, dispatchQueue = [] }: Props): React.ReactEl ); } -export default styled(DispatchQueue)` +export default React.memo(styled(DispatchQueue)` .queue-message { margin-bottom: 2rem; } -`; +`); diff --git a/packages/page-parachains/src/Parachain/index.tsx b/packages/page-parachains/src/Parachain/index.tsx index a66839b4d0..611e491117 100644 --- a/packages/page-parachains/src/Parachain/index.tsx +++ b/packages/page-parachains/src/Parachain/index.tsx @@ -134,10 +134,10 @@ function Parachain ({ className, basePath, isMine, paraInfoRef, sudoKey }: Props ); } -export default styled(Parachain)` +export default React.memo(styled(Parachain)` & { .menu-button { margin-left: 1.4rem; } } -`; +`); diff --git a/packages/page-parachains/src/ParachainInfo.tsx b/packages/page-parachains/src/ParachainInfo.tsx index e7c82b4da9..b7a7c0bc41 100644 --- a/packages/page-parachains/src/ParachainInfo.tsx +++ b/packages/page-parachains/src/ParachainInfo.tsx @@ -46,7 +46,7 @@ function ParachainInfo ({ children, className, isBig, info }: Props): React.Reac ); } -export default styled(ParachainInfo)` +export default React.memo(styled(ParachainInfo)` & { display: flex; align-items: center; @@ -108,4 +108,4 @@ export default styled(ParachainInfo)` } } } -`; +`); diff --git a/packages/page-settings/src/Developer.tsx b/packages/page-settings/src/Developer.tsx index daf059e235..e807617f7c 100644 --- a/packages/page-settings/src/Developer.tsx +++ b/packages/page-settings/src/Developer.tsx @@ -164,7 +164,7 @@ function Developer ({ className, onStatusChange }: Props): React.ReactElement { - return isCustom && value !== url; - }, true); - const isValid = isValidUrl(url); - return { isCustom, isValid, url }; + return { + isCustom: availableEndpoints.reduce((isCustom: boolean, { value }): boolean => { + return isCustom && value !== url; + }, true), + isValid: isValidUrl(url), + url + }; } function SelectUrl ({ className, onChange }: Props): React.ReactElement { @@ -71,16 +73,22 @@ function SelectUrl ({ className, onChange }: Props): React.ReactElement { onChange && info.isValid && onChange(info.url); }, [info]); - const _onChangeUrl = (url: string): void => setInfo({ ...info, ...makeUrl(url) }); - const _onChangeCustom = (isCustom: boolean): void => - setInfo({ + const _onChangeUrl = useCallback( + (url: string): void => + setInfo((info: State) => ({ ...info, ...makeUrl(url) })), + [] + ); + const _onChangeCustom = useCallback( + (isCustom: boolean): void => setInfo({ ...makeUrl( isCustom ? info.url : (availableEndpoints.find(({ value }) => !!value) || { value: 'ws://127.0.0.1:9944' }).value as string ), isCustom - }); + }), + [] + ); return (
@@ -111,7 +119,7 @@ function SelectUrl ({ className, onChange }: Props): React.ReactElement { ); } -export default styled(SelectUrl)` +export default React.memo(styled(SelectUrl)` position: relative; .settings--customToggle { @@ -119,4 +127,4 @@ export default styled(SelectUrl)` top: .5rem; right: 3.5rem; } -`; +`); diff --git a/packages/page-society/src/Overview/Summary.tsx b/packages/page-society/src/Overview/Summary.tsx index e15f24704a..da853bc951 100644 --- a/packages/page-society/src/Overview/Summary.tsx +++ b/packages/page-society/src/Overview/Summary.tsx @@ -73,7 +73,7 @@ function Summary ({ className, info }: Props): React.ReactElement { ); } -export default styled(Summary)` +export default React.memo(styled(Summary)` .society--header--account { white-space: nowrap; @@ -86,4 +86,4 @@ export default styled(Summary)` margin-right: 0.5rem; } } -`; +`); diff --git a/packages/page-society/src/Overview/index.tsx b/packages/page-society/src/Overview/index.tsx index 3157101773..c6b2240b2f 100644 --- a/packages/page-society/src/Overview/index.tsx +++ b/packages/page-society/src/Overview/index.tsx @@ -44,7 +44,7 @@ function Overview ({ className }: Props): React.ReactElement { ); } -export default styled(Overview)` +export default React.memo(styled(Overview)` .overviewSection { margin-bottom: 1.5rem; @@ -54,4 +54,4 @@ export default styled(Overview)` width: 1rem; } } -`; +`); diff --git a/packages/page-staking/src/Actions/Account/InjectKeys.tsx b/packages/page-staking/src/Actions/Account/InjectKeys.tsx index 016e108415..503e279751 100644 --- a/packages/page-staking/src/Actions/Account/InjectKeys.tsx +++ b/packages/page-staking/src/Actions/Account/InjectKeys.tsx @@ -26,7 +26,7 @@ const CRYPTO_MAP: Record = { const EMPTY_KEY = '0x'; -export default function InjectKeys ({ onClose }: Props): React.ReactElement | null { +function InjectKeys ({ onClose }: Props): React.ReactElement | null { const { t } = useTranslation(); const { queueRpc } = useContext(StatusContext); // this needs to align with what is set as the first value in `type` @@ -120,3 +120,5 @@ export default function InjectKeys ({ onClose }: Props): React.ReactElement ); } + +export default React.memo(InjectKeys); diff --git a/packages/page-staking/src/Actions/Account/InputValidateAmount.tsx b/packages/page-staking/src/Actions/Account/InputValidateAmount.tsx index 71986017ce..693e88b768 100644 --- a/packages/page-staking/src/Actions/Account/InputValidateAmount.tsx +++ b/packages/page-staking/src/Actions/Account/InputValidateAmount.tsx @@ -3,22 +3,22 @@ // of the Apache-2.0 license. See the LICENSE file for details. import { DerivedBalancesAll } from '@polkadot/api-derive/types'; -import { I18nProps } from '@polkadot/react-components/types'; import BN from 'bn.js'; import React, { useEffect, useState } from 'react'; import { Icon } from '@polkadot/react-components'; import { useApi, useCall } from '@polkadot/react-hooks'; -import translate from '../../translate'; +import { useTranslation } from '../../translate'; -interface Props extends I18nProps { +interface Props { accountId: string | null; onError: (error: string | null) => void; value?: BN | null; } -function ValidateAmount ({ accountId, onError, value, t }: Props): React.ReactElement | null { +function ValidateAmount ({ accountId, onError, value }: Props): React.ReactElement | null { + const { t } = useTranslation(); const { api } = useApi(); const allBalances = useCall(api.derive.balances.all as any, [accountId]); const [error, setError] = useState(null); @@ -51,4 +51,4 @@ function ValidateAmount ({ accountId, onError, value, t }: Props): React.ReactEl ); } -export default translate(ValidateAmount); +export default React.memo(ValidateAmount); diff --git a/packages/page-staking/src/Actions/Account/InputValidationController.tsx b/packages/page-staking/src/Actions/Account/InputValidationController.tsx index c06e8b134c..274471c23d 100644 --- a/packages/page-staking/src/Actions/Account/InputValidationController.tsx +++ b/packages/page-staking/src/Actions/Account/InputValidationController.tsx @@ -21,7 +21,7 @@ interface Props { const DISTINCT = 'Distinct stash and controller accounts are recommended to ensure fund security.'; -export default function ValidateController ({ accountId, controllerId, defaultController, isUnsafeChain, onError }: Props): React.ReactElement | null { +function ValidateController ({ accountId, controllerId, defaultController, isUnsafeChain, onError }: Props): React.ReactElement | null { const { t } = useTranslation(); const { api } = useApi(); const bondedId = useCall(api.query.staking.bonded, [controllerId], { @@ -71,3 +71,5 @@ export default function ValidateController ({ accountId, controllerId, defaultCo
); } + +export default React.memo(ValidateController); diff --git a/packages/page-staking/src/Actions/Account/InputValidationSessionKey.tsx b/packages/page-staking/src/Actions/Account/InputValidationSessionKey.tsx index ec808dd56c..1bfbce4dfb 100644 --- a/packages/page-staking/src/Actions/Account/InputValidationSessionKey.tsx +++ b/packages/page-staking/src/Actions/Account/InputValidationSessionKey.tsx @@ -7,7 +7,7 @@ import { I18nProps } from '@polkadot/react-components/types'; import React, { useEffect, useState } from 'react'; import { Icon } from '@polkadot/react-components'; -import translate from '../../translate'; +import { useTranslation } from '../../translate'; interface Props extends I18nProps { controllerId: string; @@ -16,7 +16,8 @@ interface Props extends I18nProps { stashId: string; } -function ValidateSessionEd25519 ({ onError, sessionId, stashId, t }: Props): React.ReactElement | null { +function ValidateSessionEd25519 ({ onError, sessionId, stashId }: Props): React.ReactElement | null { + const { t } = useTranslation(); const [error, setError] = useState(null); useEffect((): void => { @@ -43,4 +44,4 @@ function ValidateSessionEd25519 ({ onError, sessionId, stashId, t }: Props): Rea ); } -export default translate(ValidateSessionEd25519); +export default React.memo(ValidateSessionEd25519); diff --git a/packages/page-staking/src/Actions/Account/InputValidationUnstakeThreshold.tsx b/packages/page-staking/src/Actions/Account/InputValidationUnstakeThreshold.tsx index 7f78f64337..cdfaf75a64 100644 --- a/packages/page-staking/src/Actions/Account/InputValidationUnstakeThreshold.tsx +++ b/packages/page-staking/src/Actions/Account/InputValidationUnstakeThreshold.tsx @@ -13,7 +13,7 @@ interface Props { onError: (error: string | null) => void; } -export default function InputValidationUnstakeThreshold ({ onError, unstakeThreshold }: Props): React.ReactElement | null { +function InputValidationUnstakeThreshold ({ onError, unstakeThreshold }: Props): React.ReactElement | null { const { t } = useTranslation(); const [error, setError] = useState(null); @@ -44,3 +44,5 @@ export default function InputValidationUnstakeThreshold ({ onError, unstakeThres ); } + +export default React.memo(InputValidationUnstakeThreshold); diff --git a/packages/page-staking/src/Actions/Account/Nominate.tsx b/packages/page-staking/src/Actions/Account/Nominate.tsx index 4f6c2045a4..d9d3fd97cd 100644 --- a/packages/page-staking/src/Actions/Account/Nominate.tsx +++ b/packages/page-staking/src/Actions/Account/Nominate.tsx @@ -101,7 +101,7 @@ function Nominate ({ className, controllerId, nominees, onClose, next, stakingOv ); } -export default styled(Nominate)` +export default React.memo(styled(Nominate)` .shortlist { display: flex; flex-wrap: wrap; @@ -148,4 +148,4 @@ export default styled(Nominate)` } } } -`; +`); diff --git a/packages/page-staking/src/Actions/Account/SetSessionKey.tsx b/packages/page-staking/src/Actions/Account/SetSessionKey.tsx index fd4d236fb7..1ea5e10037 100644 --- a/packages/page-staking/src/Actions/Account/SetSessionKey.tsx +++ b/packages/page-staking/src/Actions/Account/SetSessionKey.tsx @@ -14,7 +14,7 @@ interface Props { const EMPTY_PROOF = new Uint8Array(); -export default function SetSessionKey ({ controllerId, onClose }: Props): React.ReactElement | null { +function SetSessionKey ({ controllerId, onClose }: Props): React.ReactElement | null { const { t } = useTranslation(); const [keys, setKeys] = useState(null); @@ -54,3 +54,5 @@ export default function SetSessionKey ({ controllerId, onClose }: Props): React.
); } + +export default React.memo(SetSessionKey); diff --git a/packages/page-staking/src/Actions/index.tsx b/packages/page-staking/src/Actions/index.tsx index aa0c915ff6..162f74d6ff 100644 --- a/packages/page-staking/src/Actions/index.tsx +++ b/packages/page-staking/src/Actions/index.tsx @@ -23,7 +23,7 @@ interface Props { stakingOverview?: DerivedStakingOverview; } -export default function Actions ({ allRewards, allStashes, className, isVisible, next, stakingOverview }: Props): React.ReactElement { +function Actions ({ allRewards, allStashes, className, isVisible, next, stakingOverview }: Props): React.ReactElement { const { t } = useTranslation(); const { api } = useApi(); const activeEra = useCall(api.query.staking?.activeEra, [], { @@ -104,3 +104,5 @@ export default function Actions ({ allRewards, allStashes, className, isVisible, ); } + +export default React.memo(Actions); diff --git a/packages/page-staking/src/Overview/CurrentList.tsx b/packages/page-staking/src/Overview/CurrentList.tsx index 889e86ba5e..89bfcaad62 100644 --- a/packages/page-staking/src/Overview/CurrentList.tsx +++ b/packages/page-staking/src/Overview/CurrentList.tsx @@ -64,7 +64,7 @@ function reduceDetails (state: Record, _details: Address }, { ...state }); } -export default function CurrentList ({ authorsMap, hasQueries, isIntentions, isVisible, lastAuthors, next, recentlyOnline, setNominators, stakingOverview }: Props): React.ReactElement | null { +function CurrentList ({ authorsMap, hasQueries, isIntentions, isVisible, lastAuthors, next, recentlyOnline, setNominators, stakingOverview }: Props): React.ReactElement | null { const { t } = useTranslation(); const { allAccounts } = useAccounts(); const [favorites, toggleFavorite] = useFavorites(STORE_FAVS_BASE); @@ -169,3 +169,5 @@ export default function CurrentList ({ authorsMap, hasQueries, isIntentions, isV ); } + +export default React.memo(CurrentList); diff --git a/packages/page-staking/src/Overview/Summary.tsx b/packages/page-staking/src/Overview/Summary.tsx index 5016552cb6..014c019424 100644 --- a/packages/page-staking/src/Overview/Summary.tsx +++ b/packages/page-staking/src/Overview/Summary.tsx @@ -70,7 +70,7 @@ function Summary ({ className, isVisible, next, nominators, stakingOverview, sty ); } -export default styled(Summary)` +export default React.memo(styled(Summary)` .validator--Account-block-icon { margin-right: 0.75rem; margin-top: -0.25rem; @@ -82,4 +82,4 @@ export default styled(Summary)` margin-left: -1.5rem; } } -`; +`); diff --git a/packages/page-staking/src/Overview/index.tsx b/packages/page-staking/src/Overview/index.tsx index 4934518e2a..52d0a76ef8 100644 --- a/packages/page-staking/src/Overview/index.tsx +++ b/packages/page-staking/src/Overview/index.tsx @@ -20,7 +20,7 @@ interface Props extends BareProps { stakingOverview?: DerivedStakingOverview; } -export default function Overview ({ hasQueries, isVisible, className, recentlyOnline, next, setNominators, stakingOverview }: Props): React.ReactElement { +function Overview ({ hasQueries, isVisible, className, recentlyOnline, next, setNominators, stakingOverview }: Props): React.ReactElement { const { pathname } = useLocation(); const { byAuthor, lastBlockAuthors } = useContext(BlockAuthorsContext); const isIntentions = pathname !== '/staking'; @@ -41,3 +41,5 @@ export default function Overview ({ hasQueries, isVisible, className, recentlyOn ); } + +export default React.memo(Overview); diff --git a/packages/page-staking/src/Query/Validator.tsx b/packages/page-staking/src/Query/Validator.tsx index 138e480fcb..70ecd1f3fe 100644 --- a/packages/page-staking/src/Query/Validator.tsx +++ b/packages/page-staking/src/Query/Validator.tsx @@ -135,7 +135,7 @@ function extractStake (exposures: DeriveStakerExposure[], divisor: BN): ChartInf }; } -export default function Validator ({ className, validatorId }: Props): React.ReactElement { +function Validator ({ className, validatorId }: Props): React.ReactElement { const { t } = useTranslation(); const { api } = useApi(); const [{ chart: pointChart, labels: pointLabels }, setPointChart] = useState({ chart: [], labels: [] }); @@ -218,3 +218,5 @@ export default function Validator ({ className, validatorId }: Props): React.Rea ); } + +export default React.memo(Validator); diff --git a/packages/page-staking/src/Query/index.tsx b/packages/page-staking/src/Query/index.tsx index 18ceb3b66b..7dc85803f4 100644 --- a/packages/page-staking/src/Query/index.tsx +++ b/packages/page-staking/src/Query/index.tsx @@ -13,7 +13,7 @@ interface Props { className?: string; } -export default function Query ({ className }: Props): React.ReactElement { +function Query ({ className }: Props): React.ReactElement { const { t } = useTranslation(); const { value } = useParams(); const [validatorId, setValidatorId] = useState(value || null); @@ -49,3 +49,5 @@ export default function Query ({ className }: Props): React.ReactElement ); } + +export default React.memo(Query); diff --git a/packages/page-staking/src/Targets/Summary.tsx b/packages/page-staking/src/Targets/Summary.tsx index bd85b1c650..68749b2eba 100644 --- a/packages/page-staking/src/Targets/Summary.tsx +++ b/packages/page-staking/src/Targets/Summary.tsx @@ -23,7 +23,7 @@ interface StakeInfo { percentage?: string; } -export default function Summary ({ lastReward, numNominators, numValidators, totalStaked }: Props): React.ReactElement { +function Summary ({ lastReward, numNominators, numValidators, totalStaked }: Props): React.ReactElement { const { t } = useTranslation(); const { api } = useApi(); const totalInsurance = useCall(api.query.balances.totalIssuance, []); @@ -77,3 +77,5 @@ export default function Summary ({ lastReward, numNominators, numValidators, tot ); } + +export default React.memo(Summary); diff --git a/packages/page-staking/src/Targets/index.tsx b/packages/page-staking/src/Targets/index.tsx index 665b7c3cf0..3376415799 100644 --- a/packages/page-staking/src/Targets/index.tsx +++ b/packages/page-staking/src/Targets/index.tsx @@ -263,6 +263,6 @@ function Targets ({ className }: Props): React.ReactElement { ); } -export default styled(Targets)` +export default React.memo(styled(Targets)` text-align: center; -`; +`); diff --git a/packages/page-staking/src/index.tsx b/packages/page-staking/src/index.tsx index 604795f6e1..759fa760a9 100644 --- a/packages/page-staking/src/index.tsx +++ b/packages/page-staking/src/index.tsx @@ -136,7 +136,7 @@ function StakingApp ({ basePath, className }: Props): React.ReactElement ); } -export default styled(StakingApp)` +export default React.memo(styled(StakingApp)` .staking--hidden { display: none; } @@ -152,4 +152,4 @@ export default styled(StakingApp)` .staking--Chart+.staking--Chart { margin-top: 1.5rem; } -`; +`); diff --git a/packages/page-storage/src/Query.tsx b/packages/page-storage/src/Query.tsx index 6ec6e1e868..2eb1470f62 100644 --- a/packages/page-storage/src/Query.tsx +++ b/packages/page-storage/src/Query.tsx @@ -214,7 +214,7 @@ function Query ({ className, onRemove, value }: Props): React.ReactElement { const [queue, setQueue] = useState([]); - const _onAdd = (query: QueryTypes): void => setQueue([query, ...queue]); - const _onRemove = (id: number): void => setQueue(queue.filter((item): boolean => item.id !== id)); + const _onAdd = useCallback( + (query: QueryTypes): void => setQueue((queue: QueryTypes[]) => + [query, ...queue] + ), + [] + ); + const _onRemove = useCallback( + (id: number): void => setQueue((queue: QueryTypes[]) => + queue.filter((item): boolean => item.id !== id) + ), + [] + ); return (
@@ -31,7 +41,7 @@ function StorageApp ({ basePath, className }: Props): React.ReactElement ); } -export default styled(StorageApp)` +export default React.memo(styled(StorageApp)` .storage--actionrow { align-items: center; display: flex; @@ -60,4 +70,4 @@ export default styled(StorageApp)` flex: 0; padding: 0 0.25rem; } -`; +`); diff --git a/packages/page-sudo/src/SetKey.tsx b/packages/page-sudo/src/SetKey.tsx index 5ce2d96587..4cc93955c1 100644 --- a/packages/page-sudo/src/SetKey.tsx +++ b/packages/page-sudo/src/SetKey.tsx @@ -74,7 +74,7 @@ function SetKey ({ allAccounts, className, isMine, sudoKey }: Props): React.Reac ); } -export default styled(SetKey)` +export default React.memo(styled(SetKey)` align-items: flex-end; justify-content: center; @@ -89,4 +89,4 @@ export default styled(SetKey)` .sudoLabelled { align-items: center; } -`; +`); diff --git a/packages/page-toolbox/src/Rpc/Account.tsx b/packages/page-toolbox/src/Rpc/Account.tsx index 5cf9a58bd7..830ed1eab2 100644 --- a/packages/page-toolbox/src/Rpc/Account.tsx +++ b/packages/page-toolbox/src/Rpc/Account.tsx @@ -59,7 +59,7 @@ function Account ({ className, defaultValue, isError, onChange }: Props): React. ); } -export default styled(Account)` +export default React.memo(styled(Account)` box-sizing: border-box; padding-left: 2em; -`; +`); diff --git a/packages/page-toolbox/src/Sign.tsx b/packages/page-toolbox/src/Sign.tsx index f8dbda94e2..fa69a5ddec 100644 --- a/packages/page-toolbox/src/Sign.tsx +++ b/packages/page-toolbox/src/Sign.tsx @@ -205,7 +205,7 @@ function Sign ({ className }: Props): React.ReactElement { ); } -export default styled(Sign)` +export default React.memo(styled(Sign)` .toolbox--Sign-input { position: relative; width: 100%; @@ -237,4 +237,4 @@ export default styled(Sign)` } } } -`; +`); diff --git a/packages/react-components/src/AccountIndex.tsx b/packages/react-components/src/AccountIndex.tsx index a9e436a33b..4d205a8ccc 100644 --- a/packages/react-components/src/AccountIndex.tsx +++ b/packages/react-components/src/AccountIndex.tsx @@ -44,8 +44,8 @@ function AccountIndex ({ children, className, defaultValue, label, style, value ); } -export default styled(AccountIndex)` +export default React.memo(styled(AccountIndex)` .account-index { font-family: monospace; } -`; +`); diff --git a/packages/react-components/src/ActionItem.tsx b/packages/react-components/src/ActionItem.tsx index 893d3fbe66..22d3a38c69 100644 --- a/packages/react-components/src/ActionItem.tsx +++ b/packages/react-components/src/ActionItem.tsx @@ -47,4 +47,4 @@ function ActionItem ({ className, children, accessory, idNumber, proposal, expan ); } -export default styled(ActionItem)`${styles}`; +export default React.memo(styled(ActionItem)`${styles}`); diff --git a/packages/react-components/src/AddressToggle.tsx b/packages/react-components/src/AddressToggle.tsx index 2794338935..e03899f52d 100644 --- a/packages/react-components/src/AddressToggle.tsx +++ b/packages/react-components/src/AddressToggle.tsx @@ -77,7 +77,7 @@ function AddressToggle ({ address, className, filter, isHidden, noToggle, onChan ); } -export default styled(AddressToggle)` +export default React.memo(styled(AddressToggle)` align-items: flex-start; border: 1px solid transparent; /* #eee */ border-radius: 0.25rem; @@ -114,7 +114,6 @@ export default styled(AddressToggle)` filter: none; opacity: 1; } - /* border-color: #ccc; */ } .ui--AddressToggle-address, @@ -127,4 +126,4 @@ export default styled(AddressToggle)` margin-top: 0.1rem; text-align: right; } -`; +`); diff --git a/packages/react-components/src/Bubble.tsx b/packages/react-components/src/Bubble.tsx index 832ae0d461..4c0d2292a3 100644 --- a/packages/react-components/src/Bubble.tsx +++ b/packages/react-components/src/Bubble.tsx @@ -36,7 +36,7 @@ function Bubble ({ color, children, className, icon, label }: Props): React.Reac ); } -export default styled(Bubble)` +export default React.memo(styled(Bubble)` font-weight: normal; margin: 0.25rem; padding: 0; @@ -75,4 +75,4 @@ export default styled(Bubble)` padding: 0 0 0 0.25rem; } } -`; +`); diff --git a/packages/react-components/src/Button/Group.tsx b/packages/react-components/src/Button/Group.tsx index 585e2f55c2..47b844414c 100644 --- a/packages/react-components/src/Button/Group.tsx +++ b/packages/react-components/src/Button/Group.tsx @@ -18,10 +18,9 @@ function ButtonGroup ({ children, className, isBasic = false, isCentered = false style={style} > - { - isBasic - ? null - : + {isBasic + ? null + : } {children} @@ -29,9 +28,7 @@ function ButtonGroup ({ children, className, isBasic = false, isCentered = false ); } -(ButtonGroup as GroupType).Divider = Divider; - -export default styled(ButtonGroup)` +const Memo = React.memo(styled(ButtonGroup)` text-align: right; :not(:first-child) { @@ -42,4 +39,8 @@ export default styled(ButtonGroup)` margin-bottom: 0.5rem; text-align: center; } -` as unknown as GroupType; +`) as unknown as GroupType; + +Memo.Divider = Divider; + +export default Memo; diff --git a/packages/react-components/src/Call.tsx b/packages/react-components/src/Call.tsx index a55bd9f06d..93e7177ddd 100644 --- a/packages/react-components/src/Call.tsx +++ b/packages/react-components/src/Call.tsx @@ -101,7 +101,7 @@ function Call ({ children, className, labelHash, mortality, onError, style, tip, ); } -export default styled(Call)` +export default React.memo(styled(Call)` .hash .ui--Static { overflow: hidden; text-overflow: ellipsis; @@ -120,4 +120,4 @@ export default styled(Call)` } } } -`; +`); diff --git a/packages/react-components/src/Card.tsx b/packages/react-components/src/Card.tsx index 9a1c2b0c0c..8e0604525d 100644 --- a/packages/react-components/src/Card.tsx +++ b/packages/react-components/src/Card.tsx @@ -23,7 +23,7 @@ function Card ({ children, className, isError, isSuccess, withBottomMargin }: Pr ); } -export default styled(Card)` +export default React.memo(styled(Card)` position: relative; flex: 1 1; min-width: 24%; @@ -84,4 +84,4 @@ export default styled(Card)` margin-left: 0.2em; } } -`; +`); diff --git a/packages/react-components/src/CardSummary.tsx b/packages/react-components/src/CardSummary.tsx index 1ab77cb8aa..ad9805aa05 100644 --- a/packages/react-components/src/CardSummary.tsx +++ b/packages/react-components/src/CardSummary.tsx @@ -87,7 +87,7 @@ function CardSummary ({ children, className, help, label, progress }: Props): Re ); } -export default styled(CardSummary)` +export default React.memo(styled(CardSummary)` align-items: center; background: transparent !important; border: none !important; @@ -150,4 +150,4 @@ export default styled(CardSummary)` line-height: 1.4rem; } } -`; +`); diff --git a/packages/react-components/src/ChainImg.tsx b/packages/react-components/src/ChainImg.tsx index d8c4aadf0f..f6505c329b 100644 --- a/packages/react-components/src/ChainImg.tsx +++ b/packages/react-components/src/ChainImg.tsx @@ -33,7 +33,7 @@ function ChainImg ({ className, logo, onClick }: Props): React.ReactElement { ); } -export default styled(Columar)` +export default React.memo(styled(Columar)` display: flex; flex-wrap: wrap; @@ -28,4 +28,4 @@ export default styled(Columar)` min-width: 50%; } } -`; +`); diff --git a/packages/react-components/src/CopyButton.tsx b/packages/react-components/src/CopyButton.tsx index 6943275a6d..00bcf92d68 100644 --- a/packages/react-components/src/CopyButton.tsx +++ b/packages/react-components/src/CopyButton.tsx @@ -55,7 +55,7 @@ function CopyButton ({ children, className, icon = 'copy', isAddress = false, va ); } -export default styled(CopyButton)` +export default React.memo(styled(CopyButton)` cursor: copy; button.ui.mini.icon.primary.button.icon-button { @@ -65,4 +65,4 @@ export default styled(CopyButton)` .copySpan { white-space: nowrap; } -`; +`); diff --git a/packages/react-components/src/Editor.tsx b/packages/react-components/src/Editor.tsx index c99377520c..1462607e40 100644 --- a/packages/react-components/src/Editor.tsx +++ b/packages/react-components/src/Editor.tsx @@ -64,7 +64,7 @@ function Editor ({ className, code, isValid, onEdit }: Props): React.ReactElemen ); } -export default styled(Editor)` +export default React.memo(styled(Editor)` .codeflask { border: 1px solid rgba(34,36,38,.15); background: transparent; @@ -76,4 +76,4 @@ export default styled(Editor)` border-color: #e0b4b4; } } -`; +`); diff --git a/packages/react-components/src/FilterOverlay.tsx b/packages/react-components/src/FilterOverlay.tsx index e35cd019df..38f87edc59 100644 --- a/packages/react-components/src/FilterOverlay.tsx +++ b/packages/react-components/src/FilterOverlay.tsx @@ -21,7 +21,7 @@ function FilterOverlay ({ children, className }: Props): React.ReactElement { ); } -export default styled(HelpOverlay)` +export default React.memo(styled(HelpOverlay)` .help-button { cursor: pointer; font-size: 2rem; @@ -82,4 +82,4 @@ export default styled(HelpOverlay)` right: 0; } } -`; +`); diff --git a/packages/react-components/src/IconLink.tsx b/packages/react-components/src/IconLink.tsx index 21eed7fa0f..4540e4f496 100644 --- a/packages/react-components/src/IconLink.tsx +++ b/packages/react-components/src/IconLink.tsx @@ -27,7 +27,7 @@ function IconLink ({ className, icon, label, onClick }: Props): React.ReactEleme ); } -export default styled(IconLink)` +export default React.memo(styled(IconLink)` font-size: 0.9rem !important; &:hover { @@ -37,4 +37,4 @@ export default styled(IconLink)` text-decoration: none; } } -`; +`); diff --git a/packages/react-components/src/InfoForInput.tsx b/packages/react-components/src/InfoForInput.tsx index 4d99f54fa6..f416dacb5f 100644 --- a/packages/react-components/src/InfoForInput.tsx +++ b/packages/react-components/src/InfoForInput.tsx @@ -22,7 +22,7 @@ function InfoForInput ({ children, className, type = 'info' }: Props): React.Rea ); } -export default styled(InfoForInput)` +export default React.memo(styled(InfoForInput)` background: white; border-radius: 0 0 0.25rem 0.25rem; margin: -0.5rem 0 0.25rem; @@ -41,4 +41,4 @@ export default styled(InfoForInput)` margin: 0; padding: 0; } -`; +`); diff --git a/packages/react-components/src/InputAddress/KeyPair.tsx b/packages/react-components/src/InputAddress/KeyPair.tsx index e7d86527e2..c119048db2 100644 --- a/packages/react-components/src/InputAddress/KeyPair.tsx +++ b/packages/react-components/src/InputAddress/KeyPair.tsx @@ -37,7 +37,7 @@ function KeyPair ({ address, className, style }: Props): React.ReactElement { ); } -export default styled(Messages)` +export default React.memo(styled(Messages)` font-size: 0.9rem; padding: 0; margin: 0; @@ -226,4 +226,4 @@ export default styled(Messages)` color: #555 !important; } } -`; +`); diff --git a/packages/react-components/src/ProposedAction.tsx b/packages/react-components/src/ProposedAction.tsx index 827c68c91a..531c20906e 100644 --- a/packages/react-components/src/ProposedAction.tsx +++ b/packages/react-components/src/ProposedAction.tsx @@ -110,4 +110,4 @@ function ProposedAction ({ className, asInset, idNumber, insetProps, isCollapsib ); } -export default styled(ProposedAction)`${styles}`; +export default React.memo(styled(ProposedAction)`${styles}`); diff --git a/packages/react-components/src/Spinner.tsx b/packages/react-components/src/Spinner.tsx index 366132839d..12cc54528a 100644 --- a/packages/react-components/src/Spinner.tsx +++ b/packages/react-components/src/Spinner.tsx @@ -30,7 +30,7 @@ function Spinner ({ className, variant = 'app' }: Props): React.ReactElement ); } -export default styled(SummaryBox)` +export default React.memo(styled(SummaryBox)` align-items: stretch; border-radius: 4px; display: flex; @@ -66,4 +66,4 @@ export default styled(SummaryBox)` padding-right: 0; padding-top: 0; } -`; +`); diff --git a/packages/react-components/src/Table.tsx b/packages/react-components/src/Table.tsx index 498029df2f..21e537a5da 100644 --- a/packages/react-components/src/Table.tsx +++ b/packages/react-components/src/Table.tsx @@ -50,10 +50,7 @@ function Table ({ children, className }: TableProps): React.ReactElement label { display: inline-block; margin: 0 0.5rem; @@ -56,4 +56,4 @@ export default styled(Toggle)` .ui.checkbox + label { color: rgba(78, 78, 78, 0.75); } -`; +`); diff --git a/packages/react-params/src/Param/Bare.tsx b/packages/react-params/src/Param/Bare.tsx index 121a0e0b97..4bc6942878 100644 --- a/packages/react-params/src/Param/Bare.tsx +++ b/packages/react-params/src/Param/Bare.tsx @@ -23,6 +23,6 @@ function Bare ({ children, className, style }: Props): React.ReactElement ); } -export default styled(Bare)` +export default React.memo(styled(Bare)` position: relative; -`; +`); diff --git a/packages/react-params/src/Param/Option.tsx b/packages/react-params/src/Param/Option.tsx index e36fe4102a..8137dde284 100644 --- a/packages/react-params/src/Param/Option.tsx +++ b/packages/react-params/src/Param/Option.tsx @@ -51,7 +51,7 @@ function Option ({ className, defaultValue, isDisabled, name, onChange, onEnter, ); } -export default styled(Option)` +export default React.memo(styled(Option)` position: relative; .ui--Param-Option-toggle { @@ -59,4 +59,4 @@ export default styled(Option)` right: 3.5rem; top: 0.5rem; } -`; +`); diff --git a/packages/react-query/src/FormatBalance.tsx b/packages/react-query/src/FormatBalance.tsx index f029ab3d59..23684b43b5 100644 --- a/packages/react-query/src/FormatBalance.tsx +++ b/packages/react-query/src/FormatBalance.tsx @@ -64,7 +64,7 @@ function FormatBalance ({ children, className, label, value, withSi }: Props): R ); } -export default styled(FormatBalance)` +export default React.memo(styled(FormatBalance)` display: inline-block; vertical-align: baseline; @@ -84,4 +84,4 @@ export default styled(FormatBalance)` opacity: 0.75; vertical-align: baseline; } -`; +`); diff --git a/packages/react-signer/src/Qr.tsx b/packages/react-signer/src/Qr.tsx index 666900d849..ffddb3f82d 100644 --- a/packages/react-signer/src/Qr.tsx +++ b/packages/react-signer/src/Qr.tsx @@ -34,7 +34,7 @@ function Qr ({ address, className, isScanning, onSignature, payload }: Props): R ); } -export default styled(Qr)` +export default React.memo(styled(Qr)` margin: 0 auto; max-width: 30rem; -`; +`); diff --git a/packages/react-signer/src/Transaction.tsx b/packages/react-signer/src/Transaction.tsx index de6d58f655..99bd5852aa 100644 --- a/packages/react-signer/src/Transaction.tsx +++ b/packages/react-signer/src/Transaction.tsx @@ -95,7 +95,7 @@ function Transaction ({ children, className, hideDetails, isSendable, onError, v ); } -export default styled(Transaction)` +export default React.memo(styled(Transaction)` .tx-details { margin-left: 2rem; @@ -117,4 +117,4 @@ export default styled(Transaction)` opacity: 0.6; } } -`; +`); diff --git a/packages/react-signer/src/Unlock.tsx b/packages/react-signer/src/Unlock.tsx index 9cdd13b0a3..cad91c7e75 100644 --- a/packages/react-signer/src/Unlock.tsx +++ b/packages/react-signer/src/Unlock.tsx @@ -54,9 +54,9 @@ function Unlock ({ autoFocus, className, error, onChange, onEnter, password, tab ); } -export default styled(Unlock)` +export default React.memo(styled(Unlock)` .errorLabel { margin-right: 2rem; color: #9f3a38 !important; } -`; +`); diff --git a/packages/react-signer/src/index.tsx b/packages/react-signer/src/index.tsx index 45fb4af639..c4bd519b78 100644 --- a/packages/react-signer/src/index.tsx +++ b/packages/react-signer/src/index.tsx @@ -31,7 +31,7 @@ function Signer ({ children, className, style }: Props): React.ReactElement