98 lines
5.4 KiB
TypeScript
98 lines
5.4 KiB
TypeScript
"use client";
|
|
|
|
import { motion } from 'framer-motion';
|
|
import { Plus, Search, GripVertical, Settings2, Trash2, Target } from 'lucide-react';
|
|
|
|
const mockTargets = [
|
|
{ id: 1, term: 'ThinkPad T14 Gen 3', maxPrice: 600, weight: 1.5, status: 'active' },
|
|
{ id: 2, term: 'RTX 3080', maxPrice: 350, weight: 2.0, status: 'active' },
|
|
{ id: 3, term: 'iPhone 12 Pro Unlocked', maxPrice: 200, weight: 1.0, status: 'paused' },
|
|
];
|
|
|
|
export default function KeywordsPage() {
|
|
return (
|
|
<div className="container mx-auto px-6 py-12">
|
|
<div className="flex flex-col md:flex-row justify-between items-start md:items-center mb-10 gap-4">
|
|
<div>
|
|
<h1 className="text-4xl font-extrabold tracking-tight mb-2 flex items-center gap-3">
|
|
Target Vectors <span className="text-primary"><Target className="w-8 h-8" /></span>
|
|
</h1>
|
|
<p className="text-muted-foreground text-lg">Define the precise assets your AI agents should hunt for.</p>
|
|
</div>
|
|
<button className="flex items-center gap-3 px-6 py-3 bg-primary hover:bg-primary/90 text-primary-foreground rounded-full font-bold shadow-lg hover:shadow-primary/30 transition-all hover:scale-105 active:scale-95">
|
|
<Plus className="w-5 h-5" /> New Target
|
|
</button>
|
|
</div>
|
|
|
|
<div className="bg-card border-2 border-border/50 rounded-3xl overflow-hidden shadow-sm">
|
|
<div className="grid grid-cols-12 gap-4 p-6 border-b-2 border-border/50 bg-secondary/30 text-sm font-bold text-muted-foreground uppercase tracking-wider">
|
|
<div className="col-span-1">Sort</div>
|
|
<div className="col-span-5">Search Query</div>
|
|
<div className="col-span-2">Max Price</div>
|
|
<div className="col-span-2">Priority</div>
|
|
<div className="col-span-2 text-right">Actions</div>
|
|
</div>
|
|
|
|
<div className="divide-y divide-border/30">
|
|
{mockTargets.map((target, i) => (
|
|
<motion.div
|
|
key={target.id}
|
|
initial={{ opacity: 0, x: -20 }}
|
|
animate={{ opacity: 1, x: 0 }}
|
|
transition={{ delay: i * 0.1, type: "spring" }}
|
|
className={`grid grid-cols-12 gap-4 p-6 items-center hover:bg-secondary/10 transition-colors group ${target.status === 'paused' ? 'opacity-50' : ''}`}
|
|
>
|
|
<div className="col-span-1 text-muted-foreground/50 group-hover:text-primary transition-colors">
|
|
<GripVertical className="w-6 h-6 cursor-grab" />
|
|
</div>
|
|
<div className="col-span-5 text-lg font-bold flex items-center gap-3">
|
|
<div className={`p-2 rounded-xl ${target.status === 'active' ? 'bg-primary/10 text-primary' : 'bg-muted text-muted-foreground'}`}>
|
|
<Search className="w-5 h-5" />
|
|
</div>
|
|
{target.term}
|
|
</div>
|
|
<div className="col-span-2 text-xl font-black text-foreground">
|
|
${target.maxPrice}
|
|
</div>
|
|
<div className="col-span-2">
|
|
<div className="flex items-center gap-3">
|
|
<div className="w-24 h-2.5 bg-secondary rounded-full overflow-hidden">
|
|
<div className="h-full bg-accent rounded-full transition-all" style={{width: `${(target.weight / 2) * 100}%`}}></div>
|
|
</div>
|
|
<span className="font-bold text-sm bg-accent/10 text-accent px-2 py-1 rounded-md">{target.weight}x</span>
|
|
</div>
|
|
</div>
|
|
<div className="col-span-2 flex justify-end gap-3 opacity-0 group-hover:opacity-100 transition-opacity">
|
|
<button className="p-2.5 bg-secondary hover:bg-primary/10 text-muted-foreground hover:text-primary rounded-xl transition-all shadow-sm hover:shadow-primary/20">
|
|
<Settings2 className="w-5 h-5" />
|
|
</button>
|
|
<button className="p-2.5 bg-secondary hover:bg-destructive/10 text-muted-foreground hover:text-destructive rounded-xl transition-all shadow-sm hover:shadow-destructive/20">
|
|
<Trash2 className="w-5 h-5" />
|
|
</button>
|
|
</div>
|
|
</motion.div>
|
|
))}
|
|
</div>
|
|
</div>
|
|
|
|
<motion.div
|
|
initial={{ opacity: 0, y: 20 }}
|
|
animate={{ opacity: 1, y: 0 }}
|
|
transition={{ delay: 0.4 }}
|
|
className="mt-10 p-8 border-2 border-primary/20 bg-primary/5 rounded-3xl"
|
|
>
|
|
<div className="flex items-center gap-3 mb-4">
|
|
<div className="p-3 bg-primary/20 rounded-2xl">
|
|
<Settings2 className="w-6 h-6 text-primary" />
|
|
</div>
|
|
<h3 className="text-2xl font-bold">Global AI Filtering Template</h3>
|
|
</div>
|
|
<p className="text-lg text-muted-foreground mb-6 font-medium">Define a natural language description for the LLM to verify against globally. For example: <span className="text-foreground bg-secondary px-2 py-0.5 rounded-md">"Item must not be broken. Must include power cable. Ignore 'box only' listings."</span></p>
|
|
<textarea
|
|
className="w-full h-32 bg-background/50 border-2 border-border/50 focus:border-primary rounded-2xl p-5 text-lg text-foreground font-medium outline-none resize-none transition-all shadow-inner placeholder:text-muted-foreground/50"
|
|
placeholder="Enter custom instructions for the Analyst Agent here..."
|
|
/>
|
|
</motion.div>
|
|
</div>
|
|
);
|
|
} |