diff --git a/components/Auth.tsx b/components/Auth.tsx new file mode 100644 index 00000000..a1b526b1 --- /dev/null +++ b/components/Auth.tsx @@ -0,0 +1,325 @@ +import React, { useState } from 'react'; +import { Mail, Lock, User, ArrowRight, Loader2, Eye, EyeOff, ArrowLeft } from 'lucide-react'; + +type AuthView = 'login' | 'register' | 'forgot-password' | 'reset-sent'; + +const Auth: React.FC = () => { + const [authView, setAuthView] = useState('login'); + const [isLoading, setIsLoading] = useState(false); + const [showPassword, setShowPassword] = useState(false); + const [formData, setFormData] = useState({ + name: '', + email: '', + password: '', + confirmPassword: '' + }); + + const handleSubmit = async (e: React.FormEvent) => { + e.preventDefault(); + setIsLoading(true); + setTimeout(() => { + setIsLoading(false); + if (authView === 'forgot-password') { + setAuthView('reset-sent'); + } + }, 1500); + }; + + const renderLogin = () => ( +
+
+

Welcome Back

+

Sign in to continue to StellarMail

+
+ +
+
+
+ +
+
+ +
+ setFormData({ ...formData, email: e.target.value })} + className="w-full pl-10 pr-4 py-3 bg-gray-950 border border-gray-800 rounded-lg text-white placeholder-gray-500 focus:outline-none focus:border-primary-500 focus:ring-1 focus:ring-primary-500 transition-colors" + placeholder="alex@stellar.io" + required + /> +
+
+ +
+ +
+
+ +
+ setFormData({ ...formData, password: e.target.value })} + className="w-full pl-10 pr-12 py-3 bg-gray-950 border border-gray-800 rounded-lg text-white placeholder-gray-500 focus:outline-none focus:border-primary-500 focus:ring-1 focus:ring-primary-500 transition-colors" + placeholder="••••••••" + required + /> + +
+
+ +
+ + +
+ + +
+ +
+ Don't have an account?{' '} + +
+
+
+ ); + + const renderRegister = () => ( +
+
+

Create Account

+

Start your email marketing journey

+
+ +
+
+
+ +
+
+ +
+ setFormData({ ...formData, name: e.target.value })} + className="w-full pl-10 pr-4 py-3 bg-gray-950 border border-gray-800 rounded-lg text-white placeholder-gray-500 focus:outline-none focus:border-primary-500 focus:ring-1 focus:ring-primary-500 transition-colors" + placeholder="Alex Morgan" + required + /> +
+
+ +
+ +
+
+ +
+ setFormData({ ...formData, email: e.target.value })} + className="w-full pl-10 pr-4 py-3 bg-gray-950 border border-gray-800 rounded-lg text-white placeholder-gray-500 focus:outline-none focus:border-primary-500 focus:ring-1 focus:ring-primary-500 transition-colors" + placeholder="alex@stellar.io" + required + /> +
+
+ +
+ +
+
+ +
+ setFormData({ ...formData, password: e.target.value })} + className="w-full pl-10 pr-12 py-3 bg-gray-950 border border-gray-800 rounded-lg text-white placeholder-gray-500 focus:outline-none focus:border-primary-500 focus:ring-1 focus:ring-primary-500 transition-colors" + placeholder="••••••••" + required + /> + +
+

Must be at least 8 characters

+
+ +
+ +
+
+ +
+ setFormData({ ...formData, confirmPassword: e.target.value })} + className="w-full pl-10 pr-4 py-3 bg-gray-950 border border-gray-800 rounded-lg text-white placeholder-gray-500 focus:outline-none focus:border-primary-500 focus:ring-1 focus:ring-primary-500 transition-colors" + placeholder="••••••••" + required + /> +
+
+ + +
+ +
+ Already have an account?{' '} + +
+
+
+ ); + + const renderForgotPassword = () => ( +
+ + +
+

Forgot Password?

+

We'll send you a reset link

+
+ +
+
+
+ +
+
+ +
+ setFormData({ ...formData, email: e.target.value })} + className="w-full pl-10 pr-4 py-3 bg-gray-950 border border-gray-800 rounded-lg text-white placeholder-gray-500 focus:outline-none focus:border-primary-500 focus:ring-1 focus:ring-primary-500 transition-colors" + placeholder="alex@stellar.io" + required + /> +
+
+ + +
+
+
+ ); + + const renderResetSent = () => ( +
+
+ +
+

Check Your Email

+

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

+ +
+ ); + + return ( +
+ {authView === 'login' && renderLogin()} + {authView === 'register' && renderRegister()} + {authView === 'forgot-password' && renderForgotPassword()} + {authView === 'reset-sent' && renderResetSent()} +
+ ); +}; + +export default Auth; \ No newline at end of file diff --git a/components/Chat.tsx b/components/Chat.tsx new file mode 100644 index 00000000..fde4f02a --- /dev/null +++ b/components/Chat.tsx @@ -0,0 +1,325 @@ +import React, { useState } from 'react'; +import { Search, Send, Phone, Video, MoreVertical, Paperclip, Smile, Check, CheckCheck } from 'lucide-react'; + +interface Message { + id: string; + text: string; + sender: 'user' | 'contact'; + timestamp: string; + read: boolean; +} + +interface Conversation { + id: string; + name: string; + avatar: string; + lastMessage: string; + timestamp: string; + unreadCount: number; + online: boolean; +} + +const Chat: React.FC = () => { + const [selectedConversation, setSelectedConversation] = useState('1'); + const [messageInput, setMessageInput] = useState(''); + const [searchQuery, setSearchQuery] = useState(''); + + const conversations: Conversation[] = [ + { + id: '1', + name: 'Alice Johnson', + avatar: 'AJ', + lastMessage: 'Hey, how are you doing?', + timestamp: '2m ago', + unreadCount: 2, + online: true, + }, + { + id: '2', + name: 'Bob Smith', + avatar: 'BS', + lastMessage: 'Did you see the latest update?', + timestamp: '15m ago', + unreadCount: 0, + online: true, + }, + { + id: '3', + name: 'Carol Williams', + avatar: 'CW', + lastMessage: 'Thanks for your help!', + timestamp: '1h ago', + unreadCount: 5, + online: false, + }, + { + id: '4', + name: 'David Brown', + avatar: 'DB', + lastMessage: 'Let\'s schedule a meeting', + timestamp: '3h ago', + unreadCount: 0, + online: false, + }, + { + id: '5', + name: 'Emma Davis', + avatar: 'ED', + lastMessage: 'Great work on the project!', + timestamp: '1d ago', + unreadCount: 1, + online: true, + }, + ]; + + const messages: Message[] = [ + { + id: '1', + text: 'Hey! How\'s the project going?', + sender: 'contact', + timestamp: '10:30 AM', + read: true, + }, + { + id: '2', + text: 'It\'s going really well! Just finished the main features.', + sender: 'user', + timestamp: '10:32 AM', + read: true, + }, + { + id: '3', + text: 'That\'s awesome! Can you show me a demo?', + sender: 'contact', + timestamp: '10:33 AM', + read: true, + }, + { + id: '4', + text: 'Sure! I\'ll prepare something for tomorrow.', + sender: 'user', + timestamp: '10:35 AM', + read: true, + }, + { + id: '5', + text: 'Perfect! Looking forward to it.', + sender: 'contact', + timestamp: '10:36 AM', + read: true, + }, + { + id: '6', + text: 'Hey, how are you doing?', + sender: 'contact', + timestamp: '2m ago', + read: false, + }, + ]; + + const handleSendMessage = () => { + if (messageInput.trim()) { + // Handle sending message + console.log('Sending message:', messageInput); + setMessageInput(''); + } + }; + + const handleKeyPress = (e: React.KeyboardEvent) => { + if (e.key === 'Enter' && !e.shiftKey) { + e.preventDefault(); + handleSendMessage(); + } + }; + + const filteredConversations = conversations.filter((conv) => + conv.name.toLowerCase().includes(searchQuery.toLowerCase()) + ); + + const selectedConv = conversations.find((c) => c.id === selectedConversation); + + return ( +
+ {/* Sidebar - Conversations List */} +
+ {/* Header */} +
+

Messages

+ + {/* Search Bar */} +
+ + setSearchQuery(e.target.value)} + className="w-full bg-gray-800 text-white pl-10 pr-4 py-2 rounded-lg focus:outline-none focus:ring-2 focus:ring-[#2dd4bf]" + /> +
+
+ + {/* Conversations List */} +
+ {filteredConversations.map((conversation) => ( +
setSelectedConversation(conversation.id)} + className={`p-4 cursor-pointer hover:bg-gray-800 transition-colors ${ + selectedConversation === conversation.id ? 'bg-gray-800' : '' + }`} + > +
+ {/* Avatar with Online Indicator */} +
+
+ {conversation.avatar} +
+ {conversation.online && ( +
+ )} +
+ + {/* Conversation Info */} +
+
+

{conversation.name}

+ {conversation.timestamp} +
+
+

{conversation.lastMessage}

+ {conversation.unreadCount > 0 && ( + + {conversation.unreadCount} + + )} +
+
+
+
+ ))} +
+
+ + {/* Main Chat Area */} +
+ {selectedConv ? ( + <> + {/* Chat Header */} +
+
+
+
+ {selectedConv.avatar} +
+ {selectedConv.online && ( +
+ )} +
+
+

{selectedConv.name}

+

+ {selectedConv.online ? 'Online' : 'Offline'} +

+
+
+ + {/* Action Buttons */} +
+ + + +
+
+ + {/* Messages Area */} +
+ {messages.map((message) => ( +
+
+

{message.text}

+
+ + {message.timestamp} + + {message.sender === 'user' && ( + <> + {message.read ? ( + + ) : ( + + )} + + )} +
+
+
+ ))} +
+ + {/* Message Input */} +
+
+ + +
+