Files
hellojewellers/src/components/customer/screens/MyRetailersScreen.tsx
priyanshuvish d58c08ce28 first commit
2025-10-14 12:07:18 +05:30

252 lines
9.5 KiB
TypeScript

import { Store, Plus, MapPin, Phone, Mail, ExternalLink, Share2, Copy, ChevronRight, Sparkles } from "lucide-react";
import { Button } from "../../ui/button";
import { Card } from "../../ui/card";
import { Badge } from "../../ui/badge";
import { Separator } from "../../ui/separator";
import { Dialog, DialogContent, DialogDescription, DialogHeader, DialogTitle } from "../../ui/dialog";
import { Input } from "../../ui/input";
import { Label } from "../../ui/label";
import { useState } from "react";
import { toast } from "sonner@2.0.3";
import { copyWithToast } from "../../utils/clipboard";
interface MyRetailersScreenProps {
onBack: () => void;
onViewStore: (retailerId: string) => void;
}
const connectedRetailers = [
{
id: "1",
name: "Nova Jewels",
location: "Mumbai, Maharashtra",
phone: "+91 98765 43210",
email: "hello@novajewels.com",
associate: "Priya Sharma",
theme: "elegant",
connectedDate: "Jan 2025",
status: "active",
},
{
id: "2",
name: "Sparkle Gems",
location: "Delhi, NCR",
phone: "+91 98111 22333",
email: "contact@sparklegems.com",
associate: "Amit Kumar",
theme: "modern",
connectedDate: "Dec 2024",
status: "active",
},
{
id: "3",
name: "Golden Heritage",
location: "Jaipur, Rajasthan",
phone: "+91 98444 55666",
email: "info@goldenheritage.com",
associate: "Rajesh Verma",
theme: "royal",
connectedDate: "Nov 2024",
status: "active",
},
];
const DEMO_CODE = "NOVA2025";
export function MyRetailersScreen({ onBack, onViewStore }: MyRetailersScreenProps) {
const [showAddDialog, setShowAddDialog] = useState(false);
const [showDemoCodeDialog, setShowDemoCodeDialog] = useState(false);
const [inviteCode, setInviteCode] = useState("");
const handleCopyCode = async () => {
await copyWithToast(DEMO_CODE, "Demo code copied!");
};
const handleAddRetailer = () => {
if (inviteCode.trim()) {
toast.success(`Connecting to retailer with code: ${inviteCode}`);
setShowAddDialog(false);
setInviteCode("");
} else {
toast.error("Please enter an invite code");
}
};
return (
<div className="h-full bg-bg-page flex flex-col">
{/* Header */}
<div className="bg-gradient-to-br from-primary/5 to-secondary/5 border-b border-border px-4 py-4">
<div className="flex items-center justify-between mb-1">
<button onClick={onBack} className="text-[14px] text-primary">
Back
</button>
<Button size="sm" className="bg-secondary text-secondary-foreground hover:bg-secondary/90" onClick={() => setShowDemoCodeDialog(true)}>
<Sparkles className="w-4 h-4 mr-1" />
Demo Code
</Button>
</div>
<h1 className="text-[24px] leading-[32px]">My Retailers</h1>
<p className="text-[13px] text-muted-foreground">
{connectedRetailers.length} store{connectedRetailers.length !== 1 ? 's' : ''} connected
</p>
</div>
{/* Content */}
<div className="flex-1 overflow-y-auto p-4">
<div className="space-y-4">
{/* Add New Retailer Card */}
<button
onClick={() => setShowAddDialog(true)}
className="w-full p-4 rounded-lg border-2 border-dashed border-border hover:border-primary hover:bg-accent/5 transition-all"
>
<div className="flex items-center gap-3">
<div className="w-12 h-12 rounded-full bg-primary/10 flex items-center justify-center">
<Plus className="w-6 h-6 text-primary" />
</div>
<div className="flex-1 text-left">
<p className="text-[14px] font-medium">Connect New Retailer</p>
<p className="text-[12px] text-muted-foreground">Enter invite code to connect</p>
</div>
<ChevronRight className="w-5 h-5 text-muted-foreground" />
</div>
</button>
{/* Connected Retailers */}
{connectedRetailers.map((retailer) => (
<Card key={retailer.id} className="p-4">
<div className="flex items-start gap-3 mb-3">
<div className="w-12 h-12 rounded-lg bg-gradient-to-br from-primary/20 to-secondary/20 flex items-center justify-center flex-shrink-0">
<Store className="w-6 h-6 text-primary" />
</div>
<div className="flex-1 min-w-0">
<div className="flex items-start justify-between gap-2 mb-1">
<h3 className="text-[16px] font-medium">{retailer.name}</h3>
<Badge variant="outline" className="text-[10px] bg-accent-positive/10 text-accent-positive border-accent-positive/20">
Active
</Badge>
</div>
<div className="flex items-center gap-1 text-[12px] text-muted-foreground mb-1">
<MapPin className="w-3 h-3" />
<span>{retailer.location}</span>
</div>
<p className="text-[11px] text-muted-foreground">
Your contact: {retailer.associate}
</p>
</div>
</div>
<Separator className="my-3" />
<div className="space-y-2 text-[12px]">
<div className="flex items-center gap-2 text-muted-foreground">
<Phone className="w-3.5 h-3.5" />
<span>{retailer.phone}</span>
</div>
<div className="flex items-center gap-2 text-muted-foreground">
<Mail className="w-3.5 h-3.5" />
<span>{retailer.email}</span>
</div>
</div>
<Separator className="my-3" />
<div className="flex gap-2">
<Button
size="sm"
className="flex-1"
onClick={() => onViewStore(retailer.id)}
>
<Store className="w-4 h-4 mr-1" />
View Store
</Button>
<Button size="sm" variant="outline" className="flex-1">
<Phone className="w-4 h-4 mr-1" />
Contact
</Button>
</div>
<p className="text-[10px] text-muted-foreground text-center mt-2">
Connected since {retailer.connectedDate}
</p>
</Card>
))}
</div>
</div>
{/* Add Retailer Dialog */}
<Dialog open={showAddDialog} onOpenChange={setShowAddDialog}>
<DialogContent className="max-w-[340px]">
<DialogHeader>
<DialogTitle>Connect to Retailer</DialogTitle>
<DialogDescription>
Enter the invite code provided by your jeweller
</DialogDescription>
</DialogHeader>
<div className="space-y-4">
<div className="space-y-2">
<Label htmlFor="invite-code">Invite Code</Label>
<Input
id="invite-code"
placeholder="e.g., NOVA2025"
value={inviteCode}
onChange={(e) => setInviteCode(e.target.value.toUpperCase())}
className="text-center tracking-wider"
/>
<p className="text-[11px] text-muted-foreground">
💡 Ask your jeweller for their unique invite code
</p>
</div>
<div className="flex gap-3">
<Button variant="outline" onClick={() => setShowAddDialog(false)} className="flex-1">
Cancel
</Button>
<Button onClick={handleAddRetailer} className="flex-1">
Connect
</Button>
</div>
</div>
</DialogContent>
</Dialog>
{/* Demo Code Dialog */}
<Dialog open={showDemoCodeDialog} onOpenChange={setShowDemoCodeDialog}>
<DialogContent className="max-w-[340px]">
<DialogHeader>
<DialogTitle className="flex items-center gap-2">
<Sparkles className="w-5 h-5 text-secondary" />
Demo Retailer Code
</DialogTitle>
<DialogDescription>
Use this code to connect to Nova Jewels demo store
</DialogDescription>
</DialogHeader>
<div className="space-y-4">
<div className="p-5 rounded-lg bg-gradient-to-br from-primary/10 to-secondary/10 border-2 border-primary/20 text-center">
<p className="text-[10px] text-muted-foreground uppercase tracking-wider mb-2">INVITE CODE</p>
<p className="text-[32px] font-mono tracking-widest font-medium text-primary">{DEMO_CODE}</p>
</div>
<Button className="w-full" onClick={handleCopyCode}>
<Copy className="w-4 h-4 mr-2" />
Copy Code
</Button>
<div className="p-4 rounded-lg bg-secondary/5 border border-secondary/20">
<div className="flex items-start gap-2">
<Sparkles className="w-4 h-4 text-secondary mt-0.5 flex-shrink-0" />
<div className="text-[11px] text-muted-foreground">
<p className="font-medium text-foreground mb-1">How to use:</p>
<p>Tap "Connect New Retailer" above and paste this code to instantly connect to our demo store with sample jewellery collections.</p>
</div>
</div>
</div>
</div>
</DialogContent>
</Dialog>
</div>
);
}