mobile: Optimizations for Maps Drawer, Legend, and Customer Profile Tabs
This commit is contained in:
+62
-10
@@ -1,14 +1,15 @@
|
||||
import React, { useRef, useState } from 'react';
|
||||
import { Outlet, NavLink, useNavigate, useLocation } from 'react-router-dom';
|
||||
import { useAuth } from '../context/AuthContext';
|
||||
import { LayoutDashboard, Map, Calendar, LogOut, User, Home, MessageSquare, ChevronLeft, ChevronRight } from 'lucide-react';
|
||||
import { useTheme } from '../context/ThemeContext';
|
||||
import { LayoutDashboard, Map, Calendar, LogOut, User, Home, MessageSquare, ChevronLeft, ChevronRight, Sun, Moon } from 'lucide-react';
|
||||
|
||||
import PageTransition from './PageTransition';
|
||||
import Chatbot from './Chatbot';
|
||||
import Logo from '../assets/images/LynkedUp_Pro_F_logo_Y.png';
|
||||
|
||||
// Rainbow Sidebar Item Component
|
||||
const SidebarItem = ({ to, icon: Icon, label, isCollapsed }) => {
|
||||
const SidebarItem = ({ to, icon: Icon, label, isCollapsed, onClick }) => {
|
||||
const divRef = useRef(null);
|
||||
const [position, setPosition] = useState({ x: 0, y: 0 });
|
||||
const [opacity, setOpacity] = useState(0);
|
||||
@@ -29,6 +30,7 @@ const SidebarItem = ({ to, icon: Icon, label, isCollapsed }) => {
|
||||
<NavLink
|
||||
to={to}
|
||||
ref={divRef}
|
||||
onClick={onClick}
|
||||
onMouseMove={handleMouseMove}
|
||||
onFocus={handleFocus}
|
||||
onBlur={handleBlur}
|
||||
@@ -76,10 +78,12 @@ const SidebarItem = ({ to, icon: Icon, label, isCollapsed }) => {
|
||||
|
||||
const Layout = () => {
|
||||
const { user, logout } = useAuth();
|
||||
const { theme, toggleTheme } = useTheme();
|
||||
const navigate = useNavigate();
|
||||
const location = useLocation();
|
||||
|
||||
const [isCollapsed, setIsCollapsed] = useState(false);
|
||||
const [isMobileMenuOpen, setIsMobileMenuOpen] = useState(false);
|
||||
|
||||
const handleLogout = () => {
|
||||
logout();
|
||||
@@ -99,14 +103,45 @@ const Layout = () => {
|
||||
|
||||
return (
|
||||
<div className="flex h-screen bg-zinc-50 dark:bg-[#050505] text-zinc-900 dark:text-white overflow-hidden font-sans selection:bg-blue-500/20 dark:selection:bg-white/20 transition-colors duration-300">
|
||||
|
||||
{/* Mobile Header */}
|
||||
<div className="md:hidden fixed top-0 left-0 right-0 h-16 bg-white/80 dark:bg-zinc-900/80 backdrop-blur-md border-b border-zinc-200 dark:border-white/5 flex items-center justify-between px-4 z-40">
|
||||
<div className="flex items-center gap-2">
|
||||
<img src={Logo} alt="Logo" className="w-8 h-8" />
|
||||
<span className="font-bold text-lg">LynkedUp</span>
|
||||
</div>
|
||||
<button
|
||||
onClick={() => setIsMobileMenuOpen(!isMobileMenuOpen)}
|
||||
className="p-2 rounded-lg hover:bg-zinc-100 dark:hover:bg-zinc-800 transition-colors"
|
||||
>
|
||||
{isMobileMenuOpen ? <ChevronRight size={24} className="rotate-180 transition-transform" /> : <LayoutDashboard size={24} />}
|
||||
</button>
|
||||
</div>
|
||||
|
||||
{/* Mobile Backdrop */}
|
||||
{isMobileMenuOpen && (
|
||||
<div
|
||||
className="fixed inset-0 bg-black/50 backdrop-blur-sm z-40 md:hidden"
|
||||
onClick={() => setIsMobileMenuOpen(false)}
|
||||
/>
|
||||
)}
|
||||
|
||||
{/* Sidebar */}
|
||||
{/* Enhanced glassmorphism with light/dark support */}
|
||||
<aside className={`${isCollapsed ? 'w-20' : 'w-72'} bg-white/60 dark:bg-zinc-900/60 backdrop-blur-2xl border-r border-zinc-200 dark:border-white/5 flex flex-col shrink-0 z-30 shadow-[4px_0_24px_rgba(0,0,0,0.05)] dark:shadow-[4px_0_24px_rgba(0,0,0,0.4)] relative transition-all duration-300 ease-in-out`}>
|
||||
<aside className={`
|
||||
fixed md:static inset-y-0 left-0 z-50
|
||||
${isMobileMenuOpen ? 'translate-x-0' : '-translate-x-full md:translate-x-0'}
|
||||
${isCollapsed ? 'w-20' : 'w-72'}
|
||||
bg-white/95 md:bg-white/60 dark:bg-zinc-900/95 md:dark:bg-zinc-900/60
|
||||
backdrop-blur-2xl border-r border-zinc-200 dark:border-white/5
|
||||
flex flex-col shrink-0 shadow-[4px_0_24px_rgba(0,0,0,0.05)] dark:shadow-[4px_0_24px_rgba(0,0,0,0.4)]
|
||||
transition-all duration-300 ease-in-out
|
||||
`}>
|
||||
|
||||
{/* Collapse Toggle Button */}
|
||||
{/* Collapse Toggle Button (Desktop Only) */}
|
||||
<button
|
||||
onClick={() => setIsCollapsed(!isCollapsed)}
|
||||
className="absolute -right-3 top-9 w-6 h-6 bg-white dark:bg-zinc-800 border border-zinc-200 dark:border-white/10 rounded-full flex items-center justify-center text-zinc-500 hover:text-zinc-900 dark:hover:text-white shadow-sm z-50 transition-colors"
|
||||
className="hidden md:flex absolute -right-3 top-9 w-6 h-6 bg-white dark:bg-zinc-800 border border-zinc-200 dark:border-white/10 rounded-full items-center justify-center text-zinc-500 hover:text-zinc-900 dark:hover:text-white shadow-sm z-50 transition-colors"
|
||||
>
|
||||
{isCollapsed ? <ChevronRight size={14} /> : <ChevronLeft size={14} />}
|
||||
</button>
|
||||
@@ -128,24 +163,41 @@ const Layout = () => {
|
||||
|
||||
{user?.role === 'FIELD_AGENT' || user?.role === 'ADMIN' ? (
|
||||
<>
|
||||
<SidebarItem to="/emp/fa/dashboard" icon={LayoutDashboard} label="Dashboard" isCollapsed={isCollapsed} />
|
||||
<SidebarItem to="/emp/fa/maps" icon={Map} label="Territory Map" isCollapsed={isCollapsed} />
|
||||
<SidebarItem to="/emp/fa/dashboard" icon={LayoutDashboard} label="Dashboard" isCollapsed={isCollapsed} onClick={() => setIsMobileMenuOpen(false)} />
|
||||
<SidebarItem to="/emp/fa/maps" icon={Map} label="Territory Map" isCollapsed={isCollapsed} onClick={() => setIsMobileMenuOpen(false)} />
|
||||
</>
|
||||
) : null}
|
||||
|
||||
{user?.role === 'ADMIN' && (
|
||||
<SidebarItem to="/admin/schedule" icon={Calendar} label="Team Schedule" isCollapsed={isCollapsed} />
|
||||
<SidebarItem to="/admin/schedule" icon={Calendar} label="Team Schedule" isCollapsed={isCollapsed} onClick={() => setIsMobileMenuOpen(false)} />
|
||||
)}
|
||||
|
||||
{/* Common Links */}
|
||||
<div className={`pt-6 mt-6 border-t border-zinc-200 dark:border-white/5 transition-all duration-300 ${isCollapsed ? 'flex justify-center' : ''}`}>
|
||||
<div className={`text-[10px] font-bold text-zinc-400 dark:text-zinc-500 uppercase tracking-widest mb-4 pl-4 whitespace-nowrap overflow-hidden transition-all duration-300 ${isCollapsed ? 'opacity-0 h-0 scale-y-0' : 'opacity-100 h-auto scale-y-100'}`}>System</div>
|
||||
<SidebarItem to="/" icon={MessageSquare} label="Public Site" isCollapsed={isCollapsed} />
|
||||
<SidebarItem to="/" icon={MessageSquare} label="Public Site" isCollapsed={isCollapsed} onClick={() => setIsMobileMenuOpen(false)} />
|
||||
{user?.role === 'CUSTOMER' && (
|
||||
<SidebarItem to="/portal/profile" icon={User} label="My Profile" isCollapsed={isCollapsed} onClick={() => setIsMobileMenuOpen(false)} />
|
||||
)}
|
||||
</div>
|
||||
</nav>
|
||||
</div>
|
||||
|
||||
<div className="mt-auto p-4 border-t border-zinc-200 dark:border-white/5 bg-zinc-50/50 dark:bg-black/20 relative z-10">
|
||||
{/* Theme Toggle */}
|
||||
<button
|
||||
onClick={toggleTheme}
|
||||
className={`flex items-center ${isCollapsed ? 'justify-center' : 'space-x-3'} w-full mb-3 p-3 rounded-xl bg-white/40 dark:bg-white/5 border border-zinc-200 dark:border-white/5 backdrop-blur-md transition-all duration-300 hover:bg-white/60 dark:hover:bg-white/10 group text-zinc-600 dark:text-zinc-400`}
|
||||
title={isCollapsed ? "Toggle Theme" : ""}
|
||||
>
|
||||
<div className="shrink-0">
|
||||
{theme === 'dark' ? <Sun size={18} /> : <Moon size={18} />}
|
||||
</div>
|
||||
<span className={`font-medium text-sm whitespace-nowrap overflow-hidden transition-all duration-300 ${isCollapsed ? 'w-0 opacity-0' : 'w-auto opacity-100'}`}>
|
||||
{theme === 'dark' ? 'Light Mode' : 'Dark Mode'}
|
||||
</span>
|
||||
</button>
|
||||
|
||||
<div className={`flex items-center ${isCollapsed ? 'justify-center' : 'space-x-3'} p-3 mb-3 rounded-xl bg-white/40 dark:bg-white/5 border border-zinc-200 dark:border-white/5 backdrop-blur-md transition-all duration-300 hover:bg-white/60 dark:hover:bg-white/10 group cursor-default`}>
|
||||
<div className="w-10 h-10 rounded-full bg-zinc-200 dark:bg-zinc-800 flex items-center justify-center text-zinc-600 dark:text-zinc-400 border border-zinc-300 dark:border-white/5 group-hover:border-zinc-400 dark:group-hover:border-white/20 transition-colors shrink-0">
|
||||
<User size={18} />
|
||||
@@ -168,7 +220,7 @@ const Layout = () => {
|
||||
</aside>
|
||||
|
||||
{/* Main Content */}
|
||||
<main className="flex-1 overflow-auto relative bg-zinc-50 dark:bg-[#09090b] scroll-smooth transition-colors duration-300">
|
||||
<main className="flex-1 overflow-auto relative bg-zinc-50 dark:bg-[#09090b] scroll-smooth transition-colors duration-300 pt-16 md:pt-0">
|
||||
<PageTransition>
|
||||
<Outlet />
|
||||
</PageTransition>
|
||||
|
||||
Reference in New Issue
Block a user