Skip to content

Commit

Permalink
feat(chain-selector): filter options + loading (#159)
Browse files Browse the repository at this point in the history
  • Loading branch information
jagnani73 committed Apr 19, 2024
1 parent f32898a commit 03ef6f7
Show file tree
Hide file tree
Showing 3 changed files with 63 additions and 36 deletions.
17 changes: 8 additions & 9 deletions src/components/Molecules/ChainSelector/ChainSelector.stories.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -6,18 +6,17 @@ type Story = StoryObj<typeof ChainSelectorComponent>;
const meta: Meta<typeof ChainSelectorComponent> = {
title: "Molecules/Chain Selector",
component: ChainSelectorComponent,
argTypes: {
onChangeChain: {
control: false,
table: {
disable: true,
},
},
},
};

export default meta;

export const ChainSelector: Story = {
args: {},
args: {
chain_options: [
"eth-mainnet",
"matic-mainnet",
"arbitrum-mainnet",
"solana-mainnet",
],
},
};
81 changes: 54 additions & 27 deletions src/components/Molecules/ChainSelector/ChainSelector.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,16 +11,33 @@ import {
PopoverContent,
PopoverTrigger,
} from "@/components/ui/popover";
import { useState } from "react";
import { useMemo, useState } from "react";
import { CheckIcon, DoubleArrowDownIcon } from "@radix-ui/react-icons";
import { Button } from "@/components/ui/button";
import { type ChainSelectorProps } from "@/utils/types/molecules.types";
import { type ChainItem, type Chain } from "@covalenthq/client-sdk";
import { CommandLoading } from "cmdk";
import { Skeleton } from "@/components/ui/skeleton";
import { GRK_SIZES } from "@/utils/constants/shared.constants";

export const ChainSelector: React.FC<ChainSelectorProps> = ({
chain_options = [],
onChangeChain,
}) => {
const { chains, selectedChain, setSelectedChain } = useGoldRush();
const [open, setOpen] = useState<boolean>(false);
const [open, setOpen] = useState<boolean>(!false);

const dropdownChains = useMemo<ChainItem[] | null>(() => {
if (!chains) {
return null;
}
const chainOptionsSet = new Set(chain_options);
if (chainOptionsSet.size === 0) {
return chains;
}

return chains.filter(({ name }) => chainOptionsSet.has(name as Chain));
}, [chains, chain_options]);

return (
<Popover open={open} onOpenChange={setOpen}>
Expand All @@ -40,31 +57,41 @@ export const ChainSelector: React.FC<ChainSelectorProps> = ({
<Command className="w-72">
<CommandInput placeholder="Search chain..." />
<CommandEmpty>No chain found.</CommandEmpty>
<CommandGroup>
{chains?.map((chain) => (
<CommandItem
key={chain.name}
value={chain.name}
className="cursor-pointer bg-background-light dark:bg-background-dark"
onSelect={() => {
setSelectedChain(chain);
setOpen(false);
if (onChangeChain) {
onChangeChain(chain);
}
}}
>
{chain.label}
<CheckIcon
className={`w-4" ml-auto h-4 ${
chain.name === selectedChain?.name
? "opacity-100"
: "opacity-0"
}`}
/>
</CommandItem>
))}
</CommandGroup>
{!dropdownChains ? (
<CommandLoading>
<div className="flex flex-col gap-2 px-4 pt-2">
<Skeleton size={GRK_SIZES.LARGE} />
<Skeleton size={GRK_SIZES.LARGE} />
<Skeleton size={GRK_SIZES.LARGE} />
</div>
</CommandLoading>
) : (
<CommandGroup>
{dropdownChains.map((chain) => (
<CommandItem
key={chain.name}
value={chain.name}
className="cursor-pointer bg-background-light dark:bg-background-dark"
onSelect={() => {
setSelectedChain(chain);
setOpen(false);
if (onChangeChain) {
onChangeChain(chain);
}
}}
>
{chain.label}
<CheckIcon
className={`w-4" ml-auto h-4 ${
chain.name === selectedChain?.name
? "opacity-100"
: "opacity-0"
}`}
/>
</CommandItem>
))}
</CommandGroup>
)}
</Command>
</PopoverContent>
</Popover>
Expand Down
1 change: 1 addition & 0 deletions src/utils/types/molecules.types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ export interface AddressDetailsProps {
}

export interface ChainSelectorProps {
chain_options?: Chain[];
onChangeChain?: (chain: ChainItem) => unknown;
}

Expand Down

0 comments on commit 03ef6f7

Please sign in to comment.