Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Subtract hidden assets from wallet balance #6205

Merged
merged 27 commits into from
Nov 2, 2024
Merged
Show file tree
Hide file tree
Changes from 20 commits
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
c107a75
stash
walmat Oct 15, 2024
28e17a3
fix up hiding and unhiding assets
walmat Oct 16, 2024
e5029ef
change back to 16 pro
walmat Oct 16, 2024
616b37a
rm commented out line
walmat Oct 16, 2024
0135c4b
revert podlock
walmat Oct 16, 2024
ca1856e
Merge branch 'develop' into @matthew/migrate-hidden-coins-to-zustand
walmat Oct 16, 2024
c720f43
add in balance calculation
walmat Oct 16, 2024
e012db7
chore: merge
walmat Oct 16, 2024
d856900
revert a few changes
walmat Oct 16, 2024
ce35df6
fix userAssetsStore subscription
benisgold Oct 16, 2024
3d6eb2c
clean up
walmat Oct 16, 2024
b1e51d9
remove old storage once we migrate
walmat Oct 16, 2024
e13f1a1
fix lint
walmat Oct 16, 2024
9258a0f
subscribe to query cache once and use address from arg
walmat Oct 16, 2024
4ec8a5f
add array of hidden assets to user assets store
walmat Oct 16, 2024
f63b7f2
add dapp browser control panel and consolidate conversion to happen o…
walmat Oct 16, 2024
2c13ca6
Merge branch 'develop' into @matthew/migrate-hidden-coins-to-zustand
walmat Oct 22, 2024
327238e
Merge branch 'develop' into @matthew/migrate-hidden-coins-to-zustand
walmat Oct 22, 2024
d77bfb0
Merge branch 'develop' into @matthew/migrate-hidden-coins-to-zustand
walmat Oct 24, 2024
0ce4b16
Merge branch 'develop' into @matthew/migrate-hidden-coins-to-zustand
walmat Oct 25, 2024
5a3a023
remove duplicate equality check
walmat Oct 31, 2024
2626ba0
chore: merge
walmat Oct 31, 2024
4d825c6
Merge branch 'develop' into @matthew/migrate-hidden-coins-to-zustand
walmat Nov 1, 2024
3b0f1bb
Update src/hooks/useWalletsHiddenBalances.ts
walmat Nov 1, 2024
c495478
fix lint
walmat Nov 1, 2024
c712c83
Merge branch 'develop' into @matthew/migrate-hidden-coins-to-zustand
walmat Nov 1, 2024
548bbec
formatter fix
walmat Nov 1, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion src/components/DappBrowser/control-panel/ControlPanel.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -144,7 +144,9 @@ export const ControlPanel = () => {
(wallet.addresses || [])
.filter(account => account.visible)
.forEach(account => {
const balanceText = account.balances ? account.balances.totalBalanceDisplay : i18n.t(i18n.l.wallet.change_wallet.loading_balance);
const balanceText = account.balancesMinusHiddenBalances
? account.balancesMinusHiddenBalances
: i18n.t(i18n.l.wallet.change_wallet.loading_balance);

const item: ControlPanelMenuItemProps = {
IconComponent: account.image ? (
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -144,7 +144,7 @@ const MemoizedBalanceCoinRow = React.memo(
MemoizedBalanceCoinRow.displayName = 'MemoizedBalanceCoinRow';

export default React.memo(function BalanceCoinRow({ uniqueId, extendedState }: { uniqueId: string; extendedState: ExtendedState }) {
const { theme, nativeCurrencySymbol, navigate, nativeCurrency, hiddenCoins, pinnedCoins, toggleSelectedCoin, isCoinListEdited } =
const { theme, nativeCurrencySymbol, navigate, nativeCurrency, hiddenAssets, pinnedCoins, toggleSelectedCoin, isCoinListEdited } =
extendedState;

const onPress = useCallback(() => {
Expand All @@ -156,7 +156,7 @@ export default React.memo(function BalanceCoinRow({ uniqueId, extendedState }: {
const maybeCallback = useRef<null | (() => void)>(null);
maybeCallback.current = isCoinListEdited ? onPress : null;

const isHidden = hiddenCoins[uniqueId];
const isHidden = hiddenAssets.has(uniqueId);
const isPinned = pinnedCoins[uniqueId];

return (
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@ import { useRoute } from '@react-navigation/native';
import Routes from '@/navigation/routesNames';
import { useRemoteConfig } from '@/model/remoteConfig';
import { useExperimentalConfig } from '@/config/experimentalHooks';
import { useUserAssetsStore } from '@/state/assets/userAssets';
import { UniqueId } from '@/__swaps__/types/assets';

const dataProvider = new DataProvider((r1, r2) => {
return r1.uid !== r2.uid;
Expand All @@ -34,7 +36,7 @@ export type ExtendedState = {
nativeCurrency: NativeCurrencyKey;
navigate: any;
isCoinListEdited: boolean;
hiddenCoins: BooleanMap;
hiddenAssets: Set<UniqueId>;
pinnedCoins: BooleanMap;
toggleSelectedCoin: (id: string) => void;
setIsCoinListEdited: SetterOrUpdater<boolean>;
Expand All @@ -61,6 +63,7 @@ const RawMemoRecyclerAssetList = React.memo(function RawRecyclerAssetList({
const currentDataProvider = useMemoOne(() => dataProvider.cloneWithRows(briefSectionsData), [briefSectionsData]);
const { isCoinListEdited, setIsCoinListEdited } = useCoinListEdited();
const y = useRecyclerAssetListPosition()!;
const hiddenAssets = useUserAssetsStore(state => state.hiddenAssets);

const { name } = useRoute();
const getCardIdsForScreen = remoteCardsStore(state => state.getCardIdsForScreen);
Expand Down Expand Up @@ -129,34 +132,34 @@ const RawMemoRecyclerAssetList = React.memo(function RawRecyclerAssetList({

const theme = useTheme();
const { nativeCurrencySymbol, nativeCurrency } = useAccountSettings();
const { hiddenCoinsObj: hiddenCoins, pinnedCoinsObj: pinnedCoins, toggleSelectedCoin } = useCoinListEditOptions();
const { pinnedCoinsObj: pinnedCoins, toggleSelectedCoin } = useCoinListEditOptions();

const { navigate } = useNavigation();

const mergedExtendedState = useMemo<ExtendedState>(() => {
return {
...extendedState,
hiddenCoins,
isCoinListEdited,
nativeCurrency,
nativeCurrencySymbol,
navigate,
hiddenAssets,
pinnedCoins,
setIsCoinListEdited,
theme,
toggleSelectedCoin,
};
}, [
extendedState,
theme,
navigate,
nativeCurrencySymbol,
isCoinListEdited,
nativeCurrency,
nativeCurrencySymbol,
navigate,
hiddenAssets,
pinnedCoins,
hiddenCoins,
toggleSelectedCoin,
isCoinListEdited,
setIsCoinListEdited,
theme,
toggleSelectedCoin,
]);

return (
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,10 @@ import { useMemo } from 'react';
import { useDeepCompareMemo } from 'use-deep-compare';
import { AssetListType } from '..';
import { CellType, CoinExtraData, NFTFamilyExtraData } from './ViewTypes';
import {
useCoinListEdited,
useCoinListEditOptions,
useExternalWalletSectionsData,
useOpenFamilies,
useOpenSmallBalances,
useWalletSectionsData,
} from '@/hooks';
import { useCoinListEdited, useExternalWalletSectionsData, useOpenFamilies, useOpenSmallBalances, useWalletSectionsData } from '@/hooks';
import useOpenPositionCards from '@/hooks/useOpenPositionCards';
import * as ls from '@/storage';
import useOpenClaimables from '@/hooks/useOpenClaimables';
import { useUserAssetsStore } from '@/state/assets/userAssets';

const FILTER_TYPES = {
'ens-profile': [CellType.NFT_SPACE_AFTER, CellType.NFT, CellType.FAMILY_HEADER],
Expand Down Expand Up @@ -50,7 +43,7 @@ export default function useMemoBriefSectionData({
const { isPositionCardsOpen } = useOpenPositionCards();
const { isClaimablesOpen } = useOpenClaimables();
const { isCoinListEdited } = useCoinListEdited();
const { hiddenCoinsObj } = useCoinListEditOptions();
const hiddenAssets = useUserAssetsStore(state => state.hiddenAssets);
const { openFamilies } = useOpenFamilies();

const result = useMemo(() => {
Expand Down Expand Up @@ -81,7 +74,7 @@ export default function useMemoBriefSectionData({
if (data.type === CellType.COIN && !isSmallBalancesOpen && !isCoinListEdited && afterDivider) {
return false;
}
if (data.type === CellType.COIN && hiddenCoinsObj[(data as CoinExtraData).uniqueId] && !isCoinListEdited) {
if (data.type === CellType.COIN && hiddenAssets.has((data as CoinExtraData).uniqueId) && !isCoinListEdited) {
return false;
}

Expand Down Expand Up @@ -120,7 +113,7 @@ export default function useMemoBriefSectionData({
return { type: cellType, uid };
});
return briefSectionsDataFiltered;
}, [sectionsDataToUse, type, isCoinListEdited, isSmallBalancesOpen, hiddenCoinsObj, isPositionCardsOpen, isClaimablesOpen, openFamilies]);
}, [sectionsDataToUse, type, isCoinListEdited, isSmallBalancesOpen, hiddenAssets, isPositionCardsOpen, isClaimablesOpen, openFamilies]);
const memoizedResult = useDeepCompareMemo(() => result, [result]);
const additionalData = useDeepCompareMemo(
() =>
Expand Down
8 changes: 7 additions & 1 deletion src/components/change-wallet/AddressRow.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,13 @@ export default function AddressRow({ contextMenuActions, data, editMode, onPress

const labelQuaternary = useForegroundColor('labelQuaternary');

const balanceText = balances ? balances.totalBalanceDisplay : lang.t('wallet.change_wallet.loading_balance');
const balanceText = useMemo(() => {
if (!balances) {
return lang.t('wallet.change_wallet.loading_balance');
}

return balances.balancesMinusHiddenBalances;
}, [balances]);

const cleanedUpLabel = useMemo(() => removeFirstEmojiFromString(label), [label]);

Expand Down
9 changes: 6 additions & 3 deletions src/components/expanded-state/chart/ChartContextButton.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,13 +5,16 @@ import { ContextCircleButton } from '../../context-menu';
import EditAction from '@/helpers/EditAction';
import { useCoinListEditOptions, useCoinListFinishEditingOptions } from '@/hooks';
import { ethereumUtils } from '@/utils';
import { useUserAssetsStore } from '@/state/assets/userAssets';
import { getUniqueId } from '@/utils/ethereumUtils';

const emojiSpacing = ios ? '' : ' ';

export default function ChartContextButton({ asset, color }) {
const { clearSelectedCoins, pushSelectedCoin } = useCoinListEditOptions();
const setHiddenAssets = useUserAssetsStore(state => state.setHiddenAssets);

const { currentAction, setHiddenCoins, setPinnedCoins } = useCoinListFinishEditingOptions();
const { currentAction, setPinnedCoins } = useCoinListFinishEditingOptions();

useEffect(() => {
// Ensure this expanded state's asset is always actively inside
Expand All @@ -29,13 +32,13 @@ export default function ChartContextButton({ asset, color }) {
setPinnedCoins();
} else if (buttonIndex === 1) {
// 🙈️ Hide
setHiddenCoins();
setHiddenAssets([getUniqueId(asset.address, asset.chainId)]);
} else if (buttonIndex === 2 && !asset?.isNativeAsset) {
// 🔍 View on Etherscan
ethereumUtils.openTokenEtherscanURL({ address: asset?.address, chainId: asset?.chainId });
}
},
[asset?.address, asset?.isNativeAsset, asset?.chainId, setHiddenCoins, setPinnedCoins]
[asset?.address, asset?.isNativeAsset, asset?.chainId, setHiddenAssets, setPinnedCoins]
);

const options = useMemo(
Expand Down
25 changes: 17 additions & 8 deletions src/helpers/assets.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import { getUniqueTokenFormat, getUniqueTokenType } from '@/utils';
import * as i18n from '@/languages';
import { UniqueAsset } from '@/entities';
import { NftCollectionSortCriterion } from '@/graphql/__generated__/arc';
import { UniqueId } from '@/__swaps__/types/assets';

const COINS_TO_SHOW = 5;

Expand All @@ -25,7 +26,13 @@ const getTotal = (assets: any) =>
return add(acc, balance);
}, 0);

export const buildCoinsList = (sortedAssets: any, nativeCurrency: any, isCoinListEdited: any, pinnedCoins: any, hiddenCoins: any) => {
export const buildCoinsList = (
sortedAssets: any,
nativeCurrency: any,
isCoinListEdited: any,
pinnedCoins: any,
hiddenCoins: Set<UniqueId>
) => {
if (!sortedAssets.length) {
return {
assets: [],
Expand All @@ -41,7 +48,7 @@ export const buildCoinsList = (sortedAssets: any, nativeCurrency: any, isCoinLis

// separate into standard, pinned, small balances, hidden assets
sortedAssets?.forEach((asset: any) => {
if (!!hiddenCoins && hiddenCoins[asset.uniqueId]) {
if (hiddenCoins.has(asset.uniqueId)) {
hiddenAssets.push({
isCoin: true,
isHidden: true,
Expand Down Expand Up @@ -117,13 +124,19 @@ export const buildCoinsList = (sortedAssets: any, nativeCurrency: any, isCoinLis
};

// TODO make it better
export const buildBriefCoinsList = (sortedAssets: any, nativeCurrency: any, isCoinListEdited: any, pinnedCoins: any, hiddenCoins: any) => {
export const buildBriefCoinsList = (
sortedAssets: any,
nativeCurrency: any,
isCoinListEdited: any,
pinnedCoins: any,
hiddenAssets: Set<UniqueId>
) => {
const { assets, smallBalancesValue, totalBalancesValue } = buildCoinsList(
sortedAssets,
nativeCurrency,
isCoinListEdited,
pinnedCoins,
hiddenCoins
hiddenAssets
);
const briefAssets = [];
if (assets) {
Expand Down Expand Up @@ -156,10 +169,6 @@ export const buildBriefCoinsList = (sortedAssets: any, nativeCurrency: any, isCo
return { briefAssets, totalBalancesValue };
};

interface Dictionary<T> {
[index: string]: T;
}

export const buildUniqueTokenList = (uniqueTokens: any, selectedShowcaseTokens: any[] = []) => {
let rows: any = [];
const showcaseTokens = [];
Expand Down
9 changes: 5 additions & 4 deletions src/helpers/buildWalletSections.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import { Claimable } from '@/resources/addys/claimables/types';
import { add, convertAmountToNativeDisplay } from './utilities';
import { RainbowConfig } from '@/model/remoteConfig';
import { IS_TEST } from '@/env';
import { UniqueId } from '@/__swaps__/types/assets';

const CONTENT_PLACEHOLDER = [
{ type: 'LOADING_ASSETS', uid: 'loadings-asset-1' },
Expand Down Expand Up @@ -41,7 +42,7 @@ const ONLY_NFTS_CONTENT = [{ type: 'ETH_CARD', uid: 'eth-card' }];

const sortedAssetsSelector = (state: any) => state.sortedAssets;
const accountBalanceDisplaySelector = (state: any) => state.accountBalanceDisplay;
const hiddenCoinsSelector = (state: any) => state.hiddenCoins;
const hiddenAssetsSelector = (state: any) => state.hiddenAssets;
const isCoinListEditedSelector = (state: any) => state.isCoinListEdited;
const isLoadingUserAssetsSelector = (state: any) => state.isLoadingUserAssets;
const isLoadingBalanceSelector = (state: any) => state.isLoadingBalance;
Expand Down Expand Up @@ -162,10 +163,10 @@ const withBriefBalanceSection = (
nativeCurrency: NativeCurrencyKey,
isCoinListEdited: boolean,
pinnedCoins: any,
hiddenCoins: any,
hiddenAssets: Set<UniqueId>,
collectibles: any
) => {
const { briefAssets } = buildBriefCoinsList(sortedAssets, nativeCurrency, isCoinListEdited, pinnedCoins, hiddenCoins);
const { briefAssets } = buildBriefCoinsList(sortedAssets, nativeCurrency, isCoinListEdited, pinnedCoins, hiddenAssets);

const hasTokens = briefAssets?.length;
const hasNFTs = collectibles?.length;
Expand Down Expand Up @@ -275,7 +276,7 @@ const briefBalanceSectionSelector = createSelector(
nativeCurrencySelector,
isCoinListEditedSelector,
pinnedCoinsSelector,
hiddenCoinsSelector,
hiddenAssetsSelector,
uniqueTokensSelector,
],
withBriefBalanceSection
Expand Down
37 changes: 14 additions & 23 deletions src/hooks/useCoinListEditOptions.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,10 @@
import { difference } from 'lodash';
import { useCallback, useMemo, useRef } from 'react';
import { useMMKVObject } from 'react-native-mmkv';
import { useDispatch } from 'react-redux';
import { atom, useRecoilState, useSetRecoilState } from 'recoil';
import useAccountSettings from './useAccountSettings';
import EditAction from '@/helpers/EditAction';
import { setHiddenCoins as reduxSetHiddenCoins } from '@/redux/editOptions';
import { useUserAssetsStore } from '@/state/assets/userAssets';

const selectedItemsAtom = atom<string[]>({
default: [],
Expand All @@ -20,7 +19,6 @@ export default function useCoinListEditOptions() {
const { accountAddress } = useAccountSettings();

const setSelectedItems = useSetRecoilState(selectedItemsAtom);
const [hiddenCoins = {}] = useMMKVObject<BooleanMap>('hidden-coins-obj-' + accountAddress);

const [pinnedCoins = {}] = useMMKVObject<BooleanMap>('pinned-coins-obj-' + accountAddress);
const pushSelectedCoin = useCallback(
Expand Down Expand Up @@ -49,7 +47,6 @@ export default function useCoinListEditOptions() {

return {
clearSelectedCoins,
hiddenCoinsObj: hiddenCoins,
pinnedCoinsObj: pinnedCoins,
pushSelectedCoin,
removeSelectedCoin,
Expand All @@ -59,13 +56,13 @@ export default function useCoinListEditOptions() {

export function useCoinListFinishEditingOptions() {
const { accountAddress } = useAccountSettings();
const hiddenAssets = useUserAssetsStore(state => state.getHiddenAssetsIds());
const setHiddenAssets = useUserAssetsStore(state => state.setHiddenAssets);

const [selectedItems, setSelectedItems] = useRecoilState(selectedItemsAtom);
const selectedItemsNonReactive = useRef<string[]>();
selectedItemsNonReactive.current = selectedItems;

const [hiddenCoins = {}, setHiddenCoinsObject] = useMMKVObject<BooleanMap>('hidden-coins-obj-' + accountAddress);

const [pinnedCoins = {}, setPinnedCoinsObject] = useMMKVObject<BooleanMap>('pinned-coins-obj-' + accountAddress);

const currentAction = useMemo(() => {
Expand All @@ -75,7 +72,7 @@ export function useCoinListFinishEditingOptions() {
return EditAction.none;
} else if (
newSelectedCoinsLength > 0 &&
difference(Object.keys(hiddenCoins), selectedItems).length === Object.keys(hiddenCoins).length - newSelectedCoinsLength
difference(hiddenAssets, selectedItems).length === hiddenAssets.length - newSelectedCoinsLength
) {
return EditAction.unhide;
} else if (
Expand All @@ -86,7 +83,7 @@ export function useCoinListFinishEditingOptions() {
} else {
return EditAction.standard;
}
}, [hiddenCoins, pinnedCoins, selectedItems]);
}, [hiddenAssets, pinnedCoins, selectedItems]);

const currentActionNonReactive = useRef<keyof typeof EditAction>();
currentActionNonReactive.current = currentAction;
Expand Down Expand Up @@ -114,24 +111,18 @@ export function useCoinListFinishEditingOptions() {
setSelectedItems([]);
}, [setSelectedItems, setPinnedCoinsObject]);

const dispatch = useDispatch();

const setHiddenCoins = useCallback(() => {
setHiddenCoinsObject((hiddenCoins: BooleanMap | undefined) => {
const safeHiddenCoins = hiddenCoins ?? {};
const newList = [
...Object.keys(safeHiddenCoins).filter(i => !selectedItemsNonReactive.current?.includes(i)),
...(currentActionNonReactive.current === EditAction.standard ? selectedItemsNonReactive.current || [] : []),
].reduce((acc, curr) => {
acc[curr] = true;
return acc;
}, {} as BooleanMap);
dispatch(reduxSetHiddenCoins(newList));
return newList;
});
if (
!currentActionNonReactive.current ||
currentActionNonReactive.current === EditAction.none ||
currentActionNonReactive.current === EditAction.unpin
)
return;

setHiddenAssets([...(selectedItemsNonReactive.current || [])]);

setSelectedItems([]);
}, [dispatch, setSelectedItems, setHiddenCoinsObject]);
}, [setHiddenAssets, setSelectedItems]);

return {
currentAction,
Expand Down
Loading
Loading