MogensR commited on
Commit
e81fbd9
·
1 Parent(s): 9a2a4eb

Create web/src/app/page.tsx

Browse files
Files changed (1) hide show
  1. web/src/app/page.tsx +211 -0
web/src/app/page.tsx ADDED
@@ -0,0 +1,211 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ 'use client'
2
+
3
+ import { useState } from 'react'
4
+ import Link from 'next/link'
5
+ import { motion } from 'framer-motion'
6
+ import {
7
+ Plus, Upload, Grid, List, Search, Filter,
8
+ Download, Trash2, Share2, Clock, Image,
9
+ Video, FileText, Settings, CreditCard
10
+ } from 'lucide-react'
11
+ import { Button } from '@/components/ui/button'
12
+ import { Input } from '@/components/ui/input'
13
+ import { Tabs, TabsContent, TabsList, TabsTrigger } from '@/components/ui/tabs'
14
+ import { ProjectCard } from '@/components/dashboard/project-card'
15
+ import { StatsCard } from '@/components/dashboard/stats-card'
16
+ import { UsageChart } from '@/components/dashboard/usage-chart'
17
+ import { QuickActions } from '@/components/dashboard/quick-actions'
18
+ import { useProjects } from '@/lib/hooks/use-projects'
19
+ import { formatDate } from '@/lib/utils'
20
+
21
+ export default function DashboardPage() {
22
+ const [viewMode, setViewMode] = useState<'grid' | 'list'>('grid')
23
+ const [searchQuery, setSearchQuery] = useState('')
24
+ const { projects, isLoading } = useProjects()
25
+
26
+ const stats = [
27
+ {
28
+ title: 'Images Processed',
29
+ value: '1,234',
30
+ change: '+12%',
31
+ icon: <Image className="w-5 h-5" />,
32
+ },
33
+ {
34
+ title: 'Videos Processed',
35
+ value: '56',
36
+ change: '+8%',
37
+ icon: <Video className="w-5 h-5" />,
38
+ },
39
+ {
40
+ title: 'Storage Used',
41
+ value: '2.4 GB',
42
+ change: '+5%',
43
+ icon: <FileText className="w-5 h-5" />,
44
+ },
45
+ {
46
+ title: 'API Calls',
47
+ value: '8,901',
48
+ change: '+23%',
49
+ icon: <Clock className="w-5 h-5" />,
50
+ },
51
+ ]
52
+
53
+ return (
54
+ <div className="min-h-screen bg-gray-900">
55
+ {/* Header */}
56
+ <header className="border-b border-gray-800 bg-gray-900/95 backdrop-blur sticky top-0 z-10">
57
+ <div className="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8">
58
+ <div className="flex items-center justify-between h-16">
59
+ <div className="flex items-center gap-8">
60
+ <Link href="/" className="text-xl font-semibold text-white">
61
+ BackgroundFX Pro
62
+ </Link>
63
+ <nav className="hidden md:flex items-center gap-6">
64
+ <Link href="/dashboard" className="text-white">
65
+ Dashboard
66
+ </Link>
67
+ <Link href="/editor" className="text-gray-400 hover:text-white">
68
+ Editor
69
+ </Link>
70
+ <Link href="/dashboard/projects" className="text-gray-400 hover:text-white">
71
+ Projects
72
+ </Link>
73
+ </nav>
74
+ </div>
75
+
76
+ <div className="flex items-center gap-4">
77
+ <Button variant="ghost" size="sm">
78
+ <Settings className="w-4 h-4" />
79
+ </Button>
80
+ <Button variant="ghost" size="sm">
81
+ <CreditCard className="w-4 h-4" />
82
+ </Button>
83
+ <div className="w-8 h-8 rounded-full bg-gradient-to-r from-purple-400 to-pink-600" />
84
+ </div>
85
+ </div>
86
+ </div>
87
+ </header>
88
+
89
+ {/* Main Content */}
90
+ <main className="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8 py-8">
91
+ {/* Welcome Section */}
92
+ <div className="mb-8">
93
+ <h1 className="text-3xl font-bold text-white mb-2">
94
+ Welcome back, John!
95
+ </h1>
96
+ <p className="text-gray-400">
97
+ Here's what's happening with your projects today.
98
+ </p>
99
+ </div>
100
+
101
+ {/* Quick Actions */}
102
+ <QuickActions />
103
+
104
+ {/* Stats Grid */}
105
+ <div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-4 gap-6 mb-8">
106
+ {stats.map((stat) => (
107
+ <StatsCard key={stat.title} {...stat} />
108
+ ))}
109
+ </div>
110
+
111
+ {/* Usage Chart */}
112
+ <div className="bg-gray-800 rounded-xl p-6 mb-8">
113
+ <h2 className="text-lg font-semibold text-white mb-4">
114
+ Usage Overview
115
+ </h2>
116
+ <UsageChart />
117
+ </div>
118
+
119
+ {/* Projects Section */}
120
+ <div className="bg-gray-800 rounded-xl p-6">
121
+ <div className="flex items-center justify-between mb-6">
122
+ <h2 className="text-lg font-semibold text-white">
123
+ Recent Projects
124
+ </h2>
125
+
126
+ <div className="flex items-center gap-3">
127
+ <div className="relative">
128
+ <Search className="absolute left-3 top-1/2 -translate-y-1/2 w-4 h-4 text-gray-400" />
129
+ <Input
130
+ type="search"
131
+ placeholder="Search projects..."
132
+ value={searchQuery}
133
+ onChange={(e) => setSearchQuery(e.target.value)}
134
+ className="pl-9 w-64"
135
+ />
136
+ </div>
137
+
138
+ <Button variant="outline" size="sm">
139
+ <Filter className="w-4 h-4 mr-2" />
140
+ Filter
141
+ </Button>
142
+
143
+ <div className="flex items-center border border-gray-700 rounded-lg">
144
+ <Button
145
+ variant={viewMode === 'grid' ? 'default' : 'ghost'}
146
+ size="sm"
147
+ onClick={() => setViewMode('grid')}
148
+ className="rounded-r-none"
149
+ >
150
+ <Grid className="w-4 h-4" />
151
+ </Button>
152
+ <Button
153
+ variant={viewMode === 'list' ? 'default' : 'ghost'}
154
+ size="sm"
155
+ onClick={() => setViewMode('list')}
156
+ className="rounded-l-none"
157
+ >
158
+ <List className="w-4 h-4" />
159
+ </Button>
160
+ </div>
161
+ </div>
162
+ </div>
163
+
164
+ <Tabs defaultValue="all" className="w-full">
165
+ <TabsList>
166
+ <TabsTrigger value="all">All</TabsTrigger>
167
+ <TabsTrigger value="images">Images</TabsTrigger>
168
+ <TabsTrigger value="videos">Videos</TabsTrigger>
169
+ <TabsTrigger value="batch">Batch</TabsTrigger>
170
+ </TabsList>
171
+
172
+ <TabsContent value="all" className="mt-6">
173
+ {isLoading ? (
174
+ <div className="text-center py-12">
175
+ <div className="inline-block animate-spin rounded-full h-8 w-8 border-b-2 border-white"></div>
176
+ </div>
177
+ ) : (
178
+ <div className={
179
+ viewMode === 'grid'
180
+ ? 'grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6'
181
+ : 'space-y-4'
182
+ }>
183
+ {projects?.map((project) => (
184
+ <ProjectCard
185
+ key={project.id}
186
+ project={project}
187
+ viewMode={viewMode}
188
+ />
189
+ ))}
190
+ </div>
191
+ )}
192
+
193
+ {!isLoading && projects?.length === 0 && (
194
+ <div className="text-center py-12">
195
+ <Image className="w-16 h-16 text-gray-600 mx-auto mb-4" />
196
+ <p className="text-gray-400 mb-4">No projects yet</p>
197
+ <Link href="/editor">
198
+ <Button>
199
+ <Plus className="w-4 h-4 mr-2" />
200
+ Create First Project
201
+ </Button>
202
+ </Link>
203
+ </div>
204
+ )}
205
+ </TabsContent>
206
+ </Tabs>
207
+ </div>
208
+ </main>
209
+ </div>
210
+ )
211
+ }