File size: 4,290 Bytes
eb22aa0
ce2d6ca
 
 
 
 
 
 
 
 
 
 
 
 
5dca218
ce2d6ca
 
 
 
eb22aa0
 
 
 
 
 
 
 
 
 
 
 
ce2d6ca
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
eb22aa0
 
 
 
 
 
 
 
 
 
db82489
eb22aa0
 
 
 
 
 
 
 
 
 
 
 
 
 
 
ce2d6ca
 
 
 
 
 
 
 
 
 
0505270
ce2d6ca
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
import { ReactNode, useState, useRef, useEffect } from 'react';
import { useAuthStore } from '../../store/authStore';
import { useNavigate, useLocation } from 'react-router-dom';
import {
  LayoutDashboard, FolderOpen, LogOut, User, Settings,
  Menu, X, ChevronRight, Save, Cloud, Code2, Blocks, FileType
} from 'lucide-react';

interface AppLayoutProps {
  children: ReactNode;
  sidebarContent?: ReactNode;
  showSidebar?: boolean;
}

export default function AppLayout({ children, sidebarContent, showSidebar }: AppLayoutProps) {
  const { user, logout } = useAuthStore();
  const navigate = useNavigate();
  const location = useLocation();
  const isEditor = location.pathname.startsWith('/project/');
  const [showProfileMenu, setShowProfileMenu] = useState(false);
  const profileRef = useRef<HTMLDivElement>(null);

  useEffect(() => {
    const handleClickOutside = (e: MouseEvent) => {
      if (profileRef.current && !profileRef.current.contains(e.target as Node)) {
        setShowProfileMenu(false);
      }
    };
    document.addEventListener('mousedown', handleClickOutside);
    return () => document.removeEventListener('mousedown', handleClickOutside);
  }, []);

  return (
    <div className="min-h-screen bg-surface-950 flex flex-col">
      {/* Top Navigation */}
      <header className="h-14 glass border-b border-surface-700 flex items-center justify-between px-4 z-50">
        <div className="flex items-center gap-3">
          <button
            onClick={() => navigate('/dashboard')}
            className="flex items-center gap-2 text-white font-bold text-lg hover:text-primary-400 transition-colors"
          >
            <Blocks className="w-6 h-6 text-primary-500" />
            RealBlocks
          </button>
          {isEditor && (
            <>
              <ChevronRight className="w-4 h-4 text-surface-400" />
              <span className="text-surface-200 text-sm font-medium">
                {useAuthStore.getState().token ? 'Project Editor' : ''}
              </span>
            </>
          )}
        </div>

        <div className="flex items-center gap-2">
          {user && (
            <>
              <span className="text-surface-300 text-sm hidden md:block">
                {user.username}
              </span>
              <div className="relative" ref={profileRef}>
                <button
                  onClick={() => setShowProfileMenu(!showProfileMenu)}
                  className="w-8 h-8 rounded-full bg-primary-600 flex items-center justify-center text-white text-sm font-medium hover:bg-primary-500 transition-colors"
                >
                  {user.username.charAt(0).toUpperCase()}
                </button>
                {showProfileMenu && (
                  <div className="absolute right-0 top-full mt-2 w-48 bg-surface-800 border border-surface-700 rounded-lg shadow-xl py-1 z-50">
                    <button
                      onClick={() => { setShowProfileMenu(false); navigate('/settings'); }}
                      className="w-full flex items-center gap-2 px-4 py-2 text-sm text-surface-200 hover:bg-surface-700 transition-colors"
                    >
                      <Settings className="w-4 h-4" />
                      Settings
                    </button>
                    <div className="border-t border-surface-700 my-1" />
                    <button
                      onClick={() => { logout(); navigate('/login'); }}
                      className="w-full flex items-center gap-2 px-4 py-2 text-sm text-red-400 hover:bg-surface-700 transition-colors"
                    >
                      <LogOut className="w-4 h-4" />
                      Logout
                    </button>
                  </div>
                )}
              </div>
            </>
          )}
        </div>
      </header>

      {/* Main Content Area */}
      <div className="flex-1 flex overflow-hidden">
        {/* Sidebar (for editor) */}
        {showSidebar && sidebarContent && (
          <aside className="w-64 panel flex-shrink-0 overflow-y-auto">
            {sidebarContent}
          </aside>
        )}

        {/* Main Content */}
        <main className="flex-1 overflow-auto">
          {children}
        </main>
      </div>
    </div>
  );
}