From ea143fdbc91243375f2abe2b2250d1666aede769 Mon Sep 17 00:00:00 2001 From: Fringg Date: Thu, 19 Mar 2026 08:30:32 +0300 Subject: [PATCH] fix: redesign top bar and filter panel for mobile - Split top bar into two rows on mobile: title + filter icon, then full-width search below - Desktop keeps single-row layout with search and filter inline - Filter button: icon-only on mobile with active indicator dot - Filter panel: full-screen overlay with backdrop on mobile, inline dropdown on desktop - Outside-click closes filter panel - Removed subtitle (only on desktop, saves space) --- src/pages/ReferralNetwork/ReferralNetwork.tsx | 29 ++- .../components/NetworkFilters.tsx | 222 +++++++++++------- 2 files changed, 159 insertions(+), 92 deletions(-) diff --git a/src/pages/ReferralNetwork/ReferralNetwork.tsx b/src/pages/ReferralNetwork/ReferralNetwork.tsx index e5b3b2a..502b3ed 100644 --- a/src/pages/ReferralNetwork/ReferralNetwork.tsx +++ b/src/pages/ReferralNetwork/ReferralNetwork.tsx @@ -34,19 +34,28 @@ export function ReferralNetwork() { className="relative flex h-[calc(100dvh-64px)] flex-col overflow-hidden bg-[#0a0a0f]" > {/* Top bar */} -
- -
-

+
+ {/* Row 1: Back + Title + (desktop: search + filter) + (mobile: filter icon) */} +
+ +

{t('admin.referralNetwork.title')}

-

- {t('admin.referralNetwork.subtitle')} -

+ {/* Desktop: search + filter inline */} +
+ + {networkData && } +
+ {/* Mobile: filter icon only */} + {networkData && ( +
+ +
+ )}
-
- - {networkData && } + {/* Row 2 (mobile only): full-width search */} +
+
diff --git a/src/pages/ReferralNetwork/components/NetworkFilters.tsx b/src/pages/ReferralNetwork/components/NetworkFilters.tsx index 4e2ff6d..d363bbb 100644 --- a/src/pages/ReferralNetwork/components/NetworkFilters.tsx +++ b/src/pages/ReferralNetwork/components/NetworkFilters.tsx @@ -1,3 +1,4 @@ +import { useEffect, useRef } from 'react'; import { useTranslation } from 'react-i18next'; import { useReferralNetworkStore } from '@/store/referralNetwork'; import type { NetworkGraphData } from '@/types/referralNetwork'; @@ -9,6 +10,7 @@ interface NetworkFiltersProps { export function NetworkFilters({ data, className }: NetworkFiltersProps) { const { t } = useTranslation(); + const panelRef = useRef(null); const filters = useReferralNetworkStore((s) => s.filters); const updateFilters = useReferralNetworkStore((s) => s.updateFilters); @@ -16,6 +18,21 @@ export function NetworkFilters({ data, className }: NetworkFiltersProps) { const isOpen = useReferralNetworkStore((s) => s.isFiltersOpen); const setIsOpen = useReferralNetworkStore((s) => s.setIsFiltersOpen); + const hasActiveFilters = + filters.campaigns.length > 0 || filters.partnersOnly || filters.minReferrals > 0; + + // Close on outside click + useEffect(() => { + if (!isOpen) return; + function handleClick(e: MouseEvent) { + if (panelRef.current && !panelRef.current.contains(e.target as Node)) { + setIsOpen(false); + } + } + document.addEventListener('mousedown', handleClick); + return () => document.removeEventListener('mousedown', handleClick); + }, [isOpen, setIsOpen]); + function toggleCampaign(campaignId: number) { const current = filters.campaigns; const next = current.includes(campaignId) @@ -24,12 +41,13 @@ export function NetworkFilters({ data, className }: NetworkFiltersProps) { updateFilters({ campaigns: next }); } + // Trigger button if (!isOpen) { return ( ); } - return ( -
-
-

- {t('admin.referralNetwork.filters.title')} -

- + // Filter panel content (shared between mobile/desktop) + const panelContent = ( +
+ {/* Campaigns */} + {data.campaigns.length > 0 && ( +
+ +
+ {data.campaigns.map((campaign) => ( + + ))} +
+
+ )} + + {/* Partners only */} + + + {/* Min referrals */} +
+ + updateFilters({ minReferrals: Number(e.target.value) })} + className="w-full accent-accent-500" + />
-
- {/* Campaigns */} - {data.campaigns.length > 0 && ( -
- -
- {data.campaigns.map((campaign) => ( - - ))} -
+ {/* Reset */} + +
+ ); + + return ( +
+ {/* Desktop: inline dropdown */} +
+
+
+

+ {t('admin.referralNetwork.filters.title')} +

+
- )} - - {/* Partners only */} - - - {/* Min referrals */} -
- - updateFilters({ minReferrals: Number(e.target.value) })} - className="w-full accent-accent-500" - /> + {panelContent}
+
- {/* Reset */} - + {/* Mobile: full-width overlay below top bar */} +
+ {/* Backdrop */} +
setIsOpen(false)} /> + {/* Panel */} +
+
+

+ {t('admin.referralNetwork.filters.title')} +

+ +
+ {panelContent} +
);