Files
pragativeer-v2/src/app/dashboard/ai-coach/strategy/page.tsx

155 lines
8.7 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
"use client"
import { ExamStrategyCard } from "@/components/AI/ExamStrategyCard"
import { StudyTimeOptimizationCard } from "@/components/AI/StudyTimeOptimizationCard"
import { Card, CardContent } from "@/components/ui/card"
import { Zap, Clock, Target, Lightbulb, CheckCircle2, AlertTriangle, TrendingUp } from "lucide-react"
import { useActiveUser, isDemoUser } from "@/hooks/useActiveUser"
const DEMO_NEG_MARKING_DATA = [
{ subject: "Physics", attempts: 30, negMarks: 12, accuracy: 60 },
{ subject: "Chemistry", attempts: 35, negMarks: 7, accuracy: 80 },
{ subject: "Maths / Biology", attempts: 28, negMarks: 10, accuracy: 64 },
]
const ZERO_NEG_MARKING_DATA = [
{ subject: "Physics", attempts: 0, negMarks: 0, accuracy: 0 },
{ subject: "Chemistry", attempts: 0, negMarks: 0, accuracy: 0 },
{ subject: "Maths / Biology", attempts: 0, negMarks: 0, accuracy: 0 },
]
export default function StrategyPage() {
const { userId } = useActiveUser()
const isDemo = isDemoUser(userId)
const negMarkingData = isDemo ? DEMO_NEG_MARKING_DATA : ZERO_NEG_MARKING_DATA
return (
<div className="p-6 md:p-8 space-y-8 max-w-7xl mx-auto animate-in fade-in duration-500 min-h-screen">
{/* Page Header */}
<div className="border-b border-border/50 pb-6">
<div className="flex items-start justify-between gap-4 flex-wrap">
<div>
<h1 className="text-3xl md:text-4xl font-black tracking-tight flex items-center gap-3 mb-2">
<span className="p-2.5 rounded-xl bg-cyan-50 dark:bg-[#00F0FF]/10 border border-cyan-300/60 dark:border-[#00F0FF]/20">
<Zap className="text-cyan-700 dark:text-[#00F0FF]" size={28} />
</span>
Exam Strategy &amp; Time Optimization
</h1>
<p className="text-muted-foreground text-base font-medium max-w-2xl pl-1">
Master time allocation per question, eliminate negative marking traps, and fine-tune your subject sequence for maximum score yield.
</p>
</div>
<span className="text-xs font-bold uppercase tracking-wider text-[#00F0FF] bg-cyan-50 dark:bg-[#00F0FF]/10 border border-cyan-300/60 dark:border-[#00F0FF]/20 px-3 py-1.5 rounded-full flex items-center gap-1.5 shrink-0 self-start">
<Zap size={12} /> AI Powered
</span>
</div>
</div>
{/* KPI Strip */}
<div className="grid grid-cols-2 md:grid-cols-4 gap-4">
{[
{ label: "Time Per Question", value: isDemo ? "45 sec" : "-- sec", note: isDemo ? "Target: 38 sec" : "Not calibrated", icon: <Clock size={18} className="text-red-400" />, color: "border-red-400/20 bg-red-400/5" },
{ label: "Negative Marks Lost", value: isDemo ? "−29" : "0", note: isDemo ? "Last mock test" : "0 negative marks", icon: <AlertTriangle size={18} className="text-amber-400" />, color: "border-amber-400/20 bg-amber-400/5" },
{ label: "Attempted Questions", value: isDemo ? "93 / 120" : "0 / 120", note: isDemo ? "+7 vs last test" : "0 attempted", icon: <Target size={18} className="text-[#00F0FF]" />, color: "border-[#00F0FF]/20 bg-[#00F0FF]/5" },
{ label: "Score Yield", value: isDemo ? "214" : "0", note: isDemo ? "Predicted score" : "Baseline", icon: <TrendingUp size={18} className="text-green-400" />, color: "border-green-400/20 bg-green-400/5" },
].map((kpi) => (
<Card key={kpi.label} className={`rounded-2xl border ${kpi.color} hover:scale-[1.02] transition-transform`}>
<CardContent className="p-5 flex flex-col gap-2">
{kpi.icon}
<div className="text-2xl font-black">{kpi.value}</div>
<div className="text-xs font-semibold text-muted-foreground">{kpi.label}</div>
<div className="text-[11px] font-bold text-muted-foreground/60">{kpi.note}</div>
</CardContent>
</Card>
))}
</div>
{/* Main Cards Row */}
<div className="grid grid-cols-1 lg:grid-cols-2 gap-6">
<div className="space-y-3">
<div className="flex items-center gap-2 text-sm font-black uppercase tracking-wider text-muted-foreground">
<Target size={16} className="text-[#00F0FF]" />
Subject Sequence Strategy
</div>
<ExamStrategyCard />
</div>
<div className="space-y-3">
<div className="flex items-center gap-2 text-sm font-black uppercase tracking-wider text-muted-foreground">
<Clock size={16} className="text-amber-400" />
Daily Peak Hours Analysis
</div>
<StudyTimeOptimizationCard />
</div>
</div>
{/* Negative Marking Analysis */}
<Card className="p-6 bg-secondary/10 border-border/60 rounded-3xl">
<div className="flex items-center gap-2 mb-5">
<AlertTriangle size={20} className="text-amber-400" />
<h3 className="text-lg font-extrabold tracking-tight">Negative Marking Analysis</h3>
<span className="ml-auto text-xs text-muted-foreground font-semibold">
{isDemo ? "Last Mock Test · Aug 1" : "Day 1 Initializing"}
</span>
</div>
<div className="space-y-4">
{negMarkingData.map((row) => (
<div key={row.subject} className="grid grid-cols-4 gap-4 items-center p-3 rounded-xl bg-white/5 border border-border/40">
<div className="font-black text-sm">{row.subject}</div>
<div className="text-center">
<div className="text-sm font-black text-foreground">{row.attempts}</div>
<div className="text-[11px] text-muted-foreground font-semibold">Attempted</div>
</div>
<div className="text-center">
<div className="text-sm font-black text-red-400">{row.negMarks === 0 ? "0" : `−${row.negMarks}`}</div>
<div className="text-[11px] text-muted-foreground font-semibold">Neg. Marks</div>
</div>
<div>
<div className="flex justify-between text-xs font-bold mb-1">
<span className="text-muted-foreground">Accuracy</span>
<span className={row.accuracy >= 75 ? "text-green-400" : row.accuracy >= 60 ? "text-amber-400" : row.accuracy === 0 ? "text-muted-foreground" : "text-red-400"}>
{row.accuracy}%
</span>
</div>
<div className="h-2 w-full bg-secondary rounded-full overflow-hidden">
<div
className={`h-full rounded-full ${row.accuracy >= 75 ? "bg-green-400" : row.accuracy >= 60 ? "bg-amber-400" : isDemo ? "bg-red-400" : "bg-white/10"}`}
style={{ width: `${row.accuracy}%` }}
/>
</div>
</div>
</div>
))}
</div>
<p className="text-xs text-muted-foreground mt-4 font-medium pl-1">
<span className="font-black text-amber-400">Insight:</span> {isDemo ? (
<>You&apos;re losing ~29 marks to wrong answers. Switching to &quot;skip and revisit&quot; for uncertain Physics questions could recover 15–20 marks.</>
) : (
<>Complete your first mock test or timed DPP to calculate your negative marking profile and fine-tune your subject pacing.</>
)}
</p>
</Card>
{/* Strategy Tips */}
<Card className="p-6 bg-gradient-to-br from-[#00F0FF]/5 via-secondary/10 to-background border border-[#00F0FF]/20 rounded-3xl">
<div className="flex items-center gap-2 mb-4">
<Lightbulb size={20} className="text-yellow-400" />
<h3 className="text-base font-black tracking-tight">AI Strategy Recommendations</h3>
</div>
<div className="grid grid-cols-1 md:grid-cols-3 gap-4">
{[
{ tip: "Start with Chemistry (highest accuracy) to build momentum and bank easy marks in the first 40 minutes.", color: "text-green-400", label: "Opening Strategy" },
{ tip: "Attempt Physics only if you are 80%+ confident per question. Otherwise, mark and skip — recover in last 10 min buffer.", color: "text-red-400", label: "Physics Guard" },
{ tip: "Reserve 10–15 minutes at the end to revisit starred questions. Your review accuracy is historically 20% higher than first-attempt.", color: "text-[#00F0FF]", label: "Review Window" },
].map((s) => (
<div key={s.label} className="p-4 rounded-xl bg-white/5 border border-border/30 space-y-2">
<div className={`text-xs font-black uppercase tracking-wider ${s.color}`}>{s.label}</div>
<p className="text-sm text-muted-foreground font-medium leading-relaxed">{s.tip}</p>
</div>
))}
</div>
</Card>
</div>
)
}