Skip to content

Commit

Permalink
Merge pull request #220 from TosiDrop/feat/ui
Browse files Browse the repository at this point in the history
fix/client: fix dancing token box
  • Loading branch information
aryelciu001 authored Aug 7, 2022
2 parents dd05fb8 + 1e638cc commit 31b3ba4
Show file tree
Hide file tree
Showing 7 changed files with 102 additions and 98 deletions.
8 changes: 4 additions & 4 deletions client/src/components/CatalystPopUp/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import useComponentVisible from "src/hooks/useComponentVisible";

const CatalystPopUp = () => {
const CATALYST_LINK = "https://linktr.ee/tosidrop.catalystf9";
const {visible, setVisible, ref} = useComponentVisible(false)
const { visible, setVisible, ref } = useComponentVisible(false);

useEffect(() => {
setTimeout(() => {
Expand All @@ -15,7 +15,7 @@ const CatalystPopUp = () => {

return (
<div
className={`w-full max-w-md px-5 pb-5 absolute text bottom-0 left-0 duration-200 ${
className={`z-50 w-full max-w-md px-5 pb-5 absolute text bottom-0 left-0 duration-200 ${
visible ? "translate-x-0" : "-translate-x-full"
}`}
ref={ref}
Expand All @@ -34,8 +34,8 @@ const CatalystPopUp = () => {
<p className="mt-5">
TosiDrop is building cross-chain infrastructure for Ergo and
Cardano. Check out our catalyst proposals on Project
Catalyst F9 and vote for us! Let’s
build a better future together.
Catalyst F9 and vote for us! Let’s build a better future
together.
</p>
<div className="flex w-full mt-5">
<a
Expand Down
19 changes: 10 additions & 9 deletions client/src/entities/vm.entities.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,4 @@
export interface GetRewards {
total_rewards?: number;
consolidated_promises?: Assets;
consolidated_rewards?: Assets;
nfts?: any[];
assets?: Assets;
min_balance?: number;
vending_address?: string;
withdrawal_fee?: string;
export interface GetRewardsDto {
claimable_tokens: ClaimableToken[];
pool_info: {
delegated_pool_name: string;
Expand All @@ -15,6 +7,14 @@ export interface GetRewards {
delegated_pool_ticker: string;
delegated_pool_logo: string;
};
total_rewards?: number;
consolidated_promises?: Assets;
consolidated_rewards?: Assets;
nfts?: any[];
assets?: Assets;
min_balance?: number;
vending_address?: string;
withdrawal_fee?: string;
project_locked_rewards?: {
consolidated_promises: Assets;
consolidated_rewards: Assets;
Expand Down Expand Up @@ -45,6 +45,7 @@ export interface ClaimableToken {
decimals: number;
amount: number;
premium: boolean;
selected?: boolean;
}

export interface GetTokens {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,9 @@ const ClaimableTokenBox = ({
}: Props) => {
return (
<div
className="mt-5 background rounded-2xl p-5 flex flex-col items-center w-full sm:w-64 sm:mr-5"
className="cursor-pointer mt-5 background rounded-2xl p-5 flex flex-col items-center w-full sm:w-64 sm:mr-5"
key={index}
onClick={() => handleOnChange(index)}
>
<div className="w-full flex flex-row items-center">
<label className="flex flex-row items-center mr-auto">
Expand All @@ -38,8 +39,8 @@ const ClaimableTokenBox = ({
name={ticker}
value={ticker}
checked={checked}
onChange={() => handleOnChange(index)}
className="mr-1"
onChange={() => {}}
/>
{amount / Math.pow(10, decimals)} available
</label>
Expand Down
6 changes: 3 additions & 3 deletions client/src/pages/Rewards/components/DepositInfo/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -44,10 +44,10 @@ const DepositInfo = ({
</b>{" "}
using one of the following options:
<ul>
<li>manual transfer to the address below,</li>
<li>transfer by scanning the QR code, or</li>
<li>manual transfer to the address below,</li>
<li>transfer by scanning the QR code, or</li>
<li>
<b>Send ADA</b> button (if your wallet is
<b>Send ADA</b> button (if your wallet is
connected).
</li>
</ul>
Expand Down
154 changes: 78 additions & 76 deletions client/src/pages/Rewards/index.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { faXmark, faStar } from "@fortawesome/free-solid-svg-icons";
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
import { useEffect, useState, KeyboardEvent } from "react";
import { GetRewards } from "../../entities/vm.entities";
import { useEffect, useState, KeyboardEvent, useCallback } from "react";
import { ClaimableToken } from "../../entities/vm.entities";
import {
getCustomRewards,
getRewards,
Expand All @@ -27,34 +27,26 @@ function Rewards() {
);
const [hideCheck, setHideCheck] = useState(false);
const [hideStakingInfo, setHideStakingInfo] = useState(true);
const [rewards, setRewards] = useState<GetRewards | undefined>();

const [claimableTokens, setClaimableTokens] = useState<ClaimableToken[]>(
[]
);
const [poolInfo, setPoolInfo] = useState<any>(null);
const [numberOfSelectedTokens, setNumberOfSelectedTokens] = useState(0);

const [searchAddress, setSearchAddress] = useState<string>("");
const [rewardsLoader, setRewardsLoader] = useState(false);
const [checkedState, setCheckedState] = useState(new Array<boolean>());
const [checkedCount, setCheckedCount] = useState(0);
const [allIsSelected, setAllIsSelected] = useState<boolean>(false);
const [stakeAddress, setStakeAddress] = useState<string>("");
const [claimMyRewardLoading, setClaimMyRewardLoading] =
useState<boolean>(false);

/**
* check if every token is selected
*/
useEffect(() => {
setAllIsSelected(checkedState.every((i) => i));
}, [checkedState]);

useEffect(() => {
if (rewards?.claimable_tokens.length) {
setCheckedState(
new Array(rewards.claimable_tokens.length).fill(false)
);
if (claimableTokens.length) {
setHideStakingInfo(false);
} else {
setCheckedState([]);
setHideStakingInfo(true);
}
}, [rewards?.claimable_tokens]);
}, [claimableTokens]);

useEffect(() => {
async function init() {
Expand All @@ -68,37 +60,38 @@ function Rewards() {
init();
}, [connectedWallet?.wallet?.api, connectedWallet, isWrongNetwork]);

const getNumberOfSelectedTokens = useCallback(() => {
return claimableTokens.reduce((prev, token) => {
if (token.selected) {
prev += 1;
}
return prev;
}, 0);
}, [claimableTokens]);

/**
* select/unselect all tokens
*/
const selectAll = () => {
let updatedCheckedState;
if (allIsSelected) {
updatedCheckedState = checkedState.map(() => false);
const updatedClaimableTokens = [...claimableTokens];
if (numberOfSelectedTokens < claimableTokens.length) {
updatedClaimableTokens.forEach((token) => (token.selected = true));
} else {
updatedCheckedState = checkedState.map(() => true);
updatedClaimableTokens.forEach((token) => (token.selected = false));
}

setCheckedState(updatedCheckedState);
const updatedCheckedCount = updatedCheckedState.filter(
(check) => check
).length;
setCheckedCount(updatedCheckedCount);
setClaimableTokens(updatedClaimableTokens);
setNumberOfSelectedTokens(getNumberOfSelectedTokens());
};

/**
* handle token select
*/
const handleTokenSelect = (position: number) => {
const updatedCheckedState = checkedState.map((item, index) =>
index === position ? !item : item
);

setCheckedState(updatedCheckedState);
const updatedCheckedCount = updatedCheckedState.filter(
(check) => check
).length;
setCheckedCount(updatedCheckedCount);
const updatedClaimableTokens = [...claimableTokens];
updatedClaimableTokens[position].selected =
!updatedClaimableTokens[position].selected;
setClaimableTokens(updatedClaimableTokens);
setNumberOfSelectedTokens(getNumberOfSelectedTokens());
};

const checkRewards = async () => {
Expand All @@ -115,10 +108,16 @@ function Rewards() {
address = address.staking_address;

setStakeAddress(address);
const rewards = await getRewards(address);

if (rewards && Object.keys(rewards.claimable_tokens).length) {
setRewards(rewards);
const getRewardsDto = await getRewards(address);
if (getRewardsDto == null) throw new Error();
if (getRewardsDto.claimable_tokens.length !== 0) {
setClaimableTokens(
getRewardsDto.claimable_tokens.map((token) => {
token.selected = false;
return token;
})
);
setPoolInfo(getRewardsDto.pool_info);
setRewardsLoader(false);
} else {
dispatch(
Expand Down Expand Up @@ -152,28 +151,21 @@ function Rewards() {
};

const claimMyRewards = async () => {
let selectedPremiumToken = false;

if (checkedCount === 0) return;
if (rewards == null) return;

/**
* get tx info for custom withdrawal
*/
if (rewards == null) return;
if (numberOfSelectedTokens === 0) return;

setClaimMyRewardLoading(true);
let selectedPremiumToken = false;

const selectedTokenId = [];
const availableRewards = rewards.claimable_tokens;
for (let i = 0; i < checkedState.length; i++) {
if (checkedState[i]) {
if (availableRewards[i].premium) {
const selectedTokenId: string[] = [];
claimableTokens.forEach((token) => {
if (token.selected) {
if (token.premium) {
selectedPremiumToken = true;
}
selectedTokenId.push(availableRewards[i].assetId);
selectedTokenId.push(token.assetId);
}
}
});

try {
const res = await getCustomRewards(
stakeAddress,
Expand All @@ -183,7 +175,7 @@ function Rewards() {
);
if (res == null) throw new Error();

let depositInfoUrl = `/claim/?stakeAddress=${stakeAddress}&withdrawAddress=${res.withdrawal_address}&requestId=${res.request_id}&selectedTokens=${checkedCount}&unlock=${selectedPremiumToken}`;
let depositInfoUrl = `/claim/?stakeAddress=${stakeAddress}&withdrawAddress=${res.withdrawal_address}&requestId=${res.request_id}&selectedTokens=${numberOfSelectedTokens}&unlock=${selectedPremiumToken}`;
navigate(depositInfoUrl, { replace: true });
} catch (e) {
dispatch(
Expand All @@ -201,18 +193,17 @@ function Rewards() {
};

const cancelClaim = async () => {
setRewards(undefined);
setSearchAddress("");
setClaimableTokens([]);
};

const renderStakeInfo = () => {
if (rewards?.pool_info) {
if (poolInfo != null) {
return (
<>
{rewards?.pool_info?.delegated_pool_logo ? (
{poolInfo.delegated_pool_logo ? (
<img
className="h-5 mr-2.5"
src={rewards?.pool_info?.delegated_pool_logo}
src={poolInfo.delegated_pool_logo}
alt=""
/>
) : (
Expand All @@ -221,17 +212,15 @@ function Rewards() {
<div className="pool-info">
<div className="staking-info">
Currently staking&nbsp;
<strong>
{rewards?.pool_info?.total_balance} ADA
</strong>
<strong>{poolInfo.total_balance} ADA</strong>
&nbsp;with&nbsp;
<strong className="no-break">
[{rewards?.pool_info?.delegated_pool_name}
[{poolInfo.delegated_pool_name}
]&nbsp;
{rewards?.pool_info?.delegated_pool_description}
{poolInfo.delegated_pool_description}
</strong>
<strong className="no-break-mobile">
[{rewards?.pool_info?.delegated_pool_name}]
[{poolInfo.delegated_pool_name}]
</strong>
</div>
</div>
Expand Down Expand Up @@ -318,15 +307,25 @@ function Rewards() {
Premium tokens incur a premium token fee when claiming
</div>
<div className={"flex flex-row flex-wrap"}>
{rewards?.claimable_tokens
?.sort((a, b) => (a.premium ? -1 : 1))
{claimableTokens
.sort((a, b) => {
if (a.premium && b.premium) {
if (a.ticker < b.ticker) {
return -1;
} else {
return 1;
}
} else {
return a.premium ? -1 : 1;
}
})
.map((token, index) => {
return (
<ClaimableTokenBox
key={index}
index={index}
ticker={token.ticker}
checked={checkedState[index]}
checked={token.selected || false}
handleOnChange={handleTokenSelect}
amount={token.amount}
decimals={token.decimals}
Expand All @@ -343,17 +342,20 @@ function Rewards() {
"background flex flex-row items-center p-5 mt-5 rounded-2xl"
}
>
<div>Selected {checkedCount} token</div>
<div>Selected {numberOfSelectedTokens} token</div>
<div className="ml-auto flex flex-row w-fit">
<button
className="tosi-button py-2.5 px-5 rounded-lg"
onClick={selectAll}
>
{allIsSelected ? "Unselect All" : "Select All"}
{numberOfSelectedTokens ===
claimableTokens.length
? "Unselect All"
: "Select All"}
</button>
<button
className="tosi-button ml-5 py-2.5 px-5 rounded-lg flex flex-row items-center"
disabled={checkedCount === 0}
disabled={numberOfSelectedTokens === 0}
onClick={claimMyRewards}
>
Claim my rewards
Expand Down
4 changes: 2 additions & 2 deletions client/src/services/claim.services.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
import { NetworkId } from "src/entities/common.entities";
import { EpochParams, TransactionStatus } from "src/entities/koios.entities";
import { GetRewards, GetCustomRewards } from "../entities/vm.entities";
import { GetRewardsDto, GetCustomRewards } from "../entities/vm.entities";
import axios from "axios";

export async function getRewards(
address: string
): Promise<GetRewards | undefined> {
): Promise<GetRewardsDto | undefined> {
const response = await axios.get(`/getrewards?address=${address}`);
if (response && response.data) {
return response.data;
Expand Down
Loading

0 comments on commit 31b3ba4

Please sign in to comment.