diff --git a/src/app/auth/forgot-password/page.tsx b/src/app/auth/forgot-password/page.tsx new file mode 100644 index 0000000..54bfca1 --- /dev/null +++ b/src/app/auth/forgot-password/page.tsx @@ -0,0 +1,180 @@ +"use client" + +import { ThemeProvider } from "@/providers/themeProvider/ThemeProvider"; +import NavbarStyleApple from '@/components/navbar/NavbarStyleApple/NavbarStyleApple'; +import FooterSimple from '@/components/sections/footer/FooterSimple'; +import { useState } from 'react'; +import { Mail, Heart, ArrowLeft } from 'lucide-react'; +import Link from 'next/link'; + +export default function ForgotPasswordPage() { + const [email, setEmail] = useState(''); + const [errors, setErrors] = useState>({}); + const [isLoading, setIsLoading] = useState(false); + const [submitted, setSubmitted] = useState(false); + + const validateEmail = () => { + const newErrors: Record = {}; + + if (!email.trim()) newErrors.email = 'Email is required'; + else if (!/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(email)) newErrors.email = 'Invalid email address'; + + setErrors(newErrors); + return Object.keys(newErrors).length === 0; + }; + + const handleSubmit = async (e: React.FormEvent) => { + e.preventDefault(); + + if (!validateEmail()) return; + + setIsLoading(true); + try { + // Simulate API call + await new Promise(resolve => setTimeout(resolve, 1500)); + // In real app, would make API request here to send reset email + console.log('Password reset email sent to:', email); + setSubmitted(true); + } catch (error) { + setErrors({ submit: 'Failed to send reset email. Please try again.' }); + } finally { + setIsLoading(false); + } + }; + + return ( + + + +
+
+
+ +

Reset your password

+

+ We'll send you a link to reset your password +

+
+ + {submitted ? ( +
+
+

Check your email

+

+ We've sent a password reset link to {email} +

+

+ The link will expire in 24 hours. If you don't see the email, check your spam folder. +

+
+ + + Back to sign in + +
+ ) : ( +
+ {errors.submit && ( +
+ {errors.submit} +
+ )} + +
+ +
+ + { + setEmail(e.target.value); + if (errors.email) setErrors(prev => ({ ...prev, email: '' })); + }} + className="pl-10 w-full px-4 py-2 border border-input rounded-lg focus:outline-none focus:ring-2 focus:ring-primary focus:border-transparent" + placeholder="you@example.com" + /> +
+ {errors.email &&

{errors.email}

} +
+ + + +
+ + + Back to sign in + +
+
+ )} +
+
+ + +
+ ); +} \ No newline at end of file diff --git a/src/app/auth/login/page.tsx b/src/app/auth/login/page.tsx new file mode 100644 index 0000000..f734958 --- /dev/null +++ b/src/app/auth/login/page.tsx @@ -0,0 +1,224 @@ +"use client" + +import { ThemeProvider } from "@/providers/themeProvider/ThemeProvider"; +import NavbarStyleApple from '@/components/navbar/NavbarStyleApple/NavbarStyleApple'; +import FooterSimple from '@/components/sections/footer/FooterSimple'; +import { useState } from 'react'; +import { Mail, Lock, Heart, Eye, EyeOff } from 'lucide-react'; +import Link from 'next/link'; + +export default function LoginPage() { + const [formData, setFormData] = useState({ + email: '', + password: '' + }); + const [showPassword, setShowPassword] = useState(false); + const [errors, setErrors] = useState>({}); + const [isLoading, setIsLoading] = useState(false); + const [rememberMe, setRememberMe] = useState(false); + + const validateForm = () => { + const newErrors: Record = {}; + + if (!formData.email.trim()) newErrors.email = 'Email is required'; + else if (!/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(formData.email)) newErrors.email = 'Invalid email address'; + if (!formData.password) newErrors.password = 'Password is required'; + + setErrors(newErrors); + return Object.keys(newErrors).length === 0; + }; + + const handleSubmit = async (e: React.FormEvent) => { + e.preventDefault(); + + if (!validateForm()) return; + + setIsLoading(true); + try { + // Simulate API call + await new Promise(resolve => setTimeout(resolve, 1500)); + // In real app, would make API request here + console.log('Login attempt:', { ...formData, rememberMe }); + // Redirect to dashboard + } catch (error) { + setErrors({ submit: 'Failed to sign in. Please check your credentials.' }); + } finally { + setIsLoading(false); + } + }; + + const handleChange = (e: React.ChangeEvent) => { + const { name, value } = e.target; + setFormData(prev => ({ ...prev, [name]: value })); + if (errors[name]) { + setErrors(prev => ({ ...prev, [name]: '' })); + } + }; + + return ( + + + +
+
+
+ +

Welcome back

+

+ Sign in to continue your relationship journey +

+
+ +
+ {errors.submit && ( +
+ {errors.submit} +
+ )} + +
+ {/* Email Field */} +
+ +
+ + +
+ {errors.email &&

{errors.email}

} +
+ + {/* Password Field */} +
+
+ + + Forgot password? + +
+
+ + + +
+ {errors.password &&

{errors.password}

} +
+
+ + {/* Remember Me Checkbox */} +
+ setRememberMe(e.target.checked)} + className="h-4 w-4 text-primary focus:ring-primary border-input rounded" + /> + +
+ + {/* Submit Button */} + +
+ + {/* Sign Up Link */} +

+ Don't have an account?{' '} + + Create one + +

+
+
+ + +
+ ); +} \ No newline at end of file diff --git a/src/app/auth/signup/page.tsx b/src/app/auth/signup/page.tsx new file mode 100644 index 0000000..b6abaeb --- /dev/null +++ b/src/app/auth/signup/page.tsx @@ -0,0 +1,256 @@ +"use client" + +import { ThemeProvider } from "@/providers/themeProvider/ThemeProvider"; +import NavbarStyleApple from '@/components/navbar/NavbarStyleApple/NavbarStyleApple'; +import FooterSimple from '@/components/sections/footer/FooterSimple'; +import { useState } from 'react'; +import { Mail, Lock, User, Heart, Eye, EyeOff } from 'lucide-react'; +import Link from 'next/link'; + +export default function SignupPage() { + const [formData, setFormData] = useState({ + name: '', + email: '', + password: '', + confirmPassword: '' + }); + const [showPassword, setShowPassword] = useState(false); + const [showConfirmPassword, setShowConfirmPassword] = useState(false); + const [errors, setErrors] = useState>({}); + const [isLoading, setIsLoading] = useState(false); + + const validateForm = () => { + const newErrors: Record = {}; + + if (!formData.name.trim()) newErrors.name = 'Name is required'; + if (!formData.email.trim()) newErrors.email = 'Email is required'; + else if (!/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(formData.email)) newErrors.email = 'Invalid email address'; + if (!formData.password) newErrors.password = 'Password is required'; + else if (formData.password.length < 8) newErrors.password = 'Password must be at least 8 characters'; + if (formData.password !== formData.confirmPassword) newErrors.confirmPassword = 'Passwords do not match'; + + setErrors(newErrors); + return Object.keys(newErrors).length === 0; + }; + + const handleSubmit = async (e: React.FormEvent) => { + e.preventDefault(); + + if (!validateForm()) return; + + setIsLoading(true); + try { + // Simulate API call + await new Promise(resolve => setTimeout(resolve, 1500)); + // In real app, would make API request here + console.log('Account created:', formData); + // Redirect to dashboard or login + } catch (error) { + setErrors({ submit: 'Failed to create account. Please try again.' }); + } finally { + setIsLoading(false); + } + }; + + const handleChange = (e: React.ChangeEvent) => { + const { name, value } = e.target; + setFormData(prev => ({ ...prev, [name]: value })); + if (errors[name]) { + setErrors(prev => ({ ...prev, [name]: '' })); + } + }; + + return ( + + + +
+
+
+ +

Create your account

+

+ Join little hearts and strengthen your relationship +

+
+ +
+ {errors.submit && ( +
+ {errors.submit} +
+ )} + +
+ {/* Name Field */} +
+ +
+ + +
+ {errors.name &&

{errors.name}

} +
+ + {/* Email Field */} +
+ +
+ + +
+ {errors.email &&

{errors.email}

} +
+ + {/* Password Field */} +
+ +
+ + + +
+ {errors.password &&

{errors.password}

} +
+ + {/* Confirm Password Field */} +
+ +
+ + + +
+ {errors.confirmPassword &&

{errors.confirmPassword}

} +
+
+ + {/* Submit Button */} + +
+ + {/* Sign In Link */} +

+ Already have an account?{' '} + + Sign in + +

+
+
+ + +
+ ); +} \ No newline at end of file diff --git a/src/app/page.tsx b/src/app/page.tsx index f0181d9..7dc68de 100644 --- a/src/app/page.tsx +++ b/src/app/page.tsx @@ -9,7 +9,7 @@ import TestimonialCardTwelve from '@/components/sections/testimonial/Testimonial import FaqSplitText from '@/components/sections/faq/FaqSplitText'; import ContactFaq from '@/components/sections/contact/ContactFaq'; import FooterSimple from '@/components/sections/footer/FooterSimple'; -import { Heart, TrendingUp, Sparkles, Shield } from 'lucide-react'; +import { Heart, TrendingUp, Sparkles, Shield, Lock, KeyRound, Eye, Database } from 'lucide-react'; export default function LandingPage() { return ( @@ -32,6 +32,7 @@ export default function LandingPage() { { name: "Features", id: "features" }, { name: "How It Works", id: "about" }, { name: "Stories", id: "testimonials" }, + { name: "Security", id: "security" }, { name: "FAQ", id: "faq" }, { name: "Contact", id: "contact" } ]} @@ -120,6 +121,36 @@ export default function LandingPage() { /> +
+ +
+
+ + +
+ +
+ +
+ +
+ + + + ); +}