diff --git a/web/src/pages/Profile.tsx b/web/src/pages/Profile.tsx index eef1ebb..1aba7a0 100644 --- a/web/src/pages/Profile.tsx +++ b/web/src/pages/Profile.tsx @@ -10,7 +10,7 @@ import { Badge } from '../components/ui/badge' import { Button } from '../components/ui/button' import { currency } from '../lib/format' import { useApp } from '../context/AppContext' -import { Calendar, ShoppingBag, User, Clock, Heart, Star, MapPin, CheckCircle2, Bell, Scissors } from 'lucide-react' +import { Calendar, ShoppingBag, User, Clock, Heart, Star, MapPin, CheckCircle2, Scissors, Settings, Camera, Upload } from 'lucide-react' import { supabase } from '../lib/supabase' import { ReviewModal } from '../components/ReviewModal' @@ -29,7 +29,7 @@ const statusLabel: Record = { } export default function Profile() { - const { appointments, orders, shops, favorites, submitReview, notifications, markNotificationRead } = useApp() + const { user, appointments, orders, shops, favorites, submitReview, notifications, markNotificationRead } = useApp() const navigate = useNavigate() const [authEmail, setAuthEmail] = useState('') @@ -40,6 +40,9 @@ export default function Profile() { const [reviewedAppointments, setReviewedAppointments] = useState>(new Set()) const [reviewTarget, setReviewTarget] = useState<{ appointmentId: string; shopId: string; shopName: string } | null>(null) + // Avatar local + const [avatarBase64, setAvatarBase64] = useState(null) + useEffect(() => { let mounted = true ; (async () => { @@ -59,6 +62,9 @@ export default function Profile() { if (reviews) { setReviewedAppointments(new Set(reviews.map((r: any) => r.appointment_id).filter(Boolean))) } + // Load local avatar + const savedAvatar = localStorage.getItem('avatar_' + data.user.id) + if (savedAvatar) setAvatarBase64(savedAvatar) } setLoadingAuth(false) })() @@ -91,7 +97,43 @@ export default function Profile() { setReviewTarget(null) } - const [activeTab, setActiveTab] = useState<'favoritos' | 'agenda' | 'pedidos'>('favoritos') + const [activeTab, setActiveTab] = useState<'favoritos' | 'agenda' | 'pedidos' | 'definicoes'>('favoritos') + const [editName, setEditName] = useState('') + const [isSaving, setIsSaving] = useState(false) + + useEffect(() => { + if (user?.name) { + setEditName(user.name) + } else if (authEmail) { + setEditName(authEmail.split('@')[0]) + } + }, [user, authEmail]) + + const handleSaveProfile = async () => { + if (!authId || !editName.trim()) return + setIsSaving(true) + const { error } = await supabase.from('profiles').update({ name: editName.trim() }).eq('id', authId) + setIsSaving(false) + if (error) { + alert('Erro ao atualizar perfil: ' + error.message) + } else { + alert('Perfil atualizado com sucesso!') + window.location.reload() + } + } + + const handleAvatarChange = (e: React.ChangeEvent) => { + const file = e.target.files?.[0] + if (!file || !authId) return + + const reader = new FileReader() + reader.onload = (event) => { + const base64 = event.target?.result as string + setAvatarBase64(base64) + localStorage.setItem('avatar_' + authId, base64) + } + reader.readAsDataURL(file) + } if (loadingAuth) { return ( @@ -123,7 +165,7 @@ export default function Profile() { ) } - const displayName = authEmail ? authEmail.split('@')[0] : 'Utilizador' + const displayName = user?.name || (authEmail ? authEmail.split('@')[0] : 'Utilizador') return ( <> @@ -147,20 +189,40 @@ export default function Profile() {
-
+