// running/src/dashboard.jsx — slice 6 of the module split.
//
// The Dashboard view: weekly volume bars, recent-activity list, health
// snapshot tiles. Extracted verbatim from running/index.html. Activity
// classification (isRun/isXT/actDisplay) and HR-zone helpers live in
// the main block and are reached through the render-time
// window.__appHelpers bridge; HR-zone fns come from the lib
// (window.HRZones).

const { C, Card, Stat, Badge, EmptyState, fmt, ChartTooltip } = window.SharedUI;
const useData = () => (window.__appUseData ? window.__appUseData() : null);
const { getHRZones, classifyHRZone } = window.HRZones;
const { isRun, isXT, actDisplay, effectiveType } = window.ActivityTypes;
const { useState, useMemo } = React;
const {
  Bar, ComposedChart, XAxis, YAxis, CartesianGrid, Tooltip, Legend,
  ResponsiveContainer,
} = Recharts;

    function Dashboard({ activities, profile, userId, isOwner, hrZoneConfig }) {
      const { healthToday, healthYesterday } = useData();
      const [weeklyData, setWeeklyData] = useState([]);

      const recentRuns = useMemo(() => {
        return activities
          .filter(a => isRun(a))
          .sort((a,b) => b.start_date?.seconds - a.start_date?.seconds)
          .slice(0, 5);
      }, [activities]);

      const recentXT = useMemo(() => {
        return activities
          .filter(a => isXT(a))
          .sort((a,b) => b.start_date?.seconds - a.start_date?.seconds)
          .slice(0, 5);
      }, [activities]);

      const lastRun = recentRuns[0];

      // Weekly mileage for last 8 weeks
      useMemo(() => {
        const now = new Date();
        const weeks = [];
        for (let i = 7; i >= 0; i--) {
          const weekStart = new Date(now);
          weekStart.setDate(now.getDate() - (i * 7) - ((now.getDay() + 6) % 7));
          weekStart.setHours(0,0,0,0);
          const weekEnd = new Date(weekStart);
          weekEnd.setDate(weekStart.getDate() + 7);

          const weekRuns = activities.filter(a => {
            const d = a.start_date?.toDate ? a.start_date.toDate() : new Date(a.start_date);
            return d >= weekStart && d < weekEnd && isRun(a);
          });
          const weekXT = activities.filter(a => {
            const d = a.start_date?.toDate ? a.start_date.toDate() : new Date(a.start_date);
            return d >= weekStart && d < weekEnd && isXT(a);
          });

          const miles = weekRuns.reduce((sum, a) => sum + (a.distance / 1609.34), 0);
          const xtHours = weekXT.reduce((sum, a) => sum + ((a.moving_time || 0) / 3600), 0);
          weeks.push({
            week: `W${8-i}`,
            miles: parseFloat(miles.toFixed(1)),
            runs: weekRuns.length,
            xtHours: parseFloat(xtHours.toFixed(1)),
            xtCount: weekXT.length,
          });
        }
        setWeeklyData(weeks);
      }, [activities]);

      const thisWeekMiles = weeklyData[weeklyData.length - 1]?.miles || 0;
      const lastWeekMiles = weeklyData[weeklyData.length - 2]?.miles || 0;
      const milesDelta = thisWeekMiles - lastWeekMiles;

      const monthMiles = useMemo(() => {
        const now = new Date();
        const monthStart = new Date(now.getFullYear(), now.getMonth(), 1);
        return activities
          .filter(a => {
            const d = a.start_date?.toDate ? a.start_date.toDate() : new Date(a.start_date);
            return d >= monthStart && isRun(a);
          })
          .reduce((sum, a) => sum + (a.distance / 1609.34), 0);
      }, [activities]);

      const weekXTHours = weeklyData[weeklyData.length - 1]?.xtHours || 0;

      const avgPace = useMemo(() => {
        const runs = recentRuns.filter(r => r.moving_time && r.distance);
        if (!runs.length) return null;
        return runs.reduce((sum, r) => sum + (r.moving_time / (r.distance / 1609.34)), 0) / runs.length;
      }, [recentRuns]);

      const today = new Date().toLocaleDateString("en-US", { weekday:"long", month:"long", day:"numeric" });

      return (
        <div style={{ display:"flex", flexDirection:"column", gap: 20 }}>
          {/* Header row */}
          <div style={{ display:"flex", justifyContent:"space-between", alignItems:"flex-start", flexWrap:"wrap", gap: 12 }}>
            <div>
              <div style={{ fontFamily:"'Space Grotesk', sans-serif", fontSize: 26, fontWeight: 800, color: C.text }}>
                Dashboard
              </div>
              <div style={{ color: C.textMuted, fontSize: 13, marginTop: 2 }}>{today}</div>
            </div>
            {lastRun && (
              <Badge label={`Last run: ${fmt.dateShort(lastRun.start_date)}`} color={C.green} />
            )}
          </div>

          {/* Key stats */}
          <div style={{ display:"grid", gridTemplateColumns:"repeat(auto-fit, minmax(150px, 1fr))", gap: 16 }}>
            <Card>
              <Stat label="This Week" value={thisWeekMiles.toFixed(1)} unit="mi" color={C.cyan} />
              <div style={{ marginTop: 8, fontSize: 11, color: milesDelta >= 0 ? C.green : C.red }}>
                {milesDelta >= 0 ? "▲" : "▼"} {Math.abs(milesDelta).toFixed(1)} mi vs last week
              </div>
            </Card>
            <Card>
              <Stat label="Cross-Training" value={weekXTHours.toFixed(1)} unit="hrs" color={C.green} />
              <div style={{ marginTop: 8, fontSize: 11, color: C.textMuted }}>
                {weeklyData[weeklyData.length - 1]?.xtCount || 0} sessions this week
              </div>
            </Card>
            <Card>
              <Stat label="This Month" value={monthMiles.toFixed(1)} unit="mi" color={C.purple} />
              <div style={{ marginTop: 8, fontSize: 11, color: C.textMuted }}>{activities.filter(a => {
                const d = a.start_date?.toDate ? a.start_date.toDate() : new Date(a.start_date);
                const s = new Date(); s.setDate(1);
                return d >= s && isRun(a);
              }).length} runs</div>
            </Card>
            <Card>
              <Stat label="Avg Pace" value={avgPace ? fmt.pace(avgPace).split(" ")[0] : "--"} unit="/mi" color={C.amber} />
              <div style={{ marginTop: 8, fontSize: 11, color: C.textMuted }}>last 5 runs</div>
            </Card>
            <Card>
              <Stat label="All Activities" value={activities.length} unit="" color={C.green} />
              <div style={{ marginTop: 8, fontSize: 11, color: C.textMuted }}>
                {activities.filter(a=>isRun(a)).length} runs · {activities.filter(a=>isXT(a)).length} cross-training
              </div>
            </Card>
          </div>

          {/* Weekly mileage chart */}
          <Card>
            <div style={{ fontSize: 13, fontWeight: 600, color: C.textDim, marginBottom: 16 }}>Weekly Training — Last 8 Weeks</div>
            <ResponsiveContainer width="100%" height={200}>
              <ComposedChart data={weeklyData} barSize={22}>
                <CartesianGrid strokeDasharray="3 3" stroke={C.border} vertical={false} />
                <XAxis dataKey="week" tick={{ fill: C.textMuted, fontSize: 11 }} axisLine={false} tickLine={false} />
                <YAxis yAxisId="mi" tick={{ fill: C.textMuted, fontSize: 11 }} axisLine={false} tickLine={false} />
                <YAxis yAxisId="xt" orientation="right" tick={{ fill: C.textMuted, fontSize: 11 }} axisLine={false} tickLine={false} />
                <Tooltip content={<ChartTooltip formatter={(v,n) => n === "xtHours" ? `${v} hrs` : `${v} mi`} />} />
                <Legend wrapperStyle={{ fontSize: 11 }} />
                <Bar yAxisId="mi" dataKey="miles" fill={C.cyan} radius={[4,4,0,0]} fillOpacity={0.85} name="Running (mi)" />
                <Bar yAxisId="xt" dataKey="xtHours" fill={C.green} radius={[4,4,0,0]} fillOpacity={0.7} name="Cross-Training (hrs)" />
              </ComposedChart>
            </ResponsiveContainer>
          </Card>

          {/* Garmin Health Snapshot */}
          {healthToday && (
            <Card style={{ borderColor: C.green + "40" }}>
              <div style={{ display: "flex", justifyContent: "space-between", alignItems: "center", marginBottom: 16 }}>
                <div style={{ fontSize: 13, fontWeight: 600, color: C.textDim }}>Health Snapshot</div>
                <Badge label="Garmin" color={C.green} />
              </div>
              <div style={{ display: "grid", gridTemplateColumns: "repeat(auto-fit, minmax(100px, 1fr))", gap: 12 }}>
                {(healthToday.hrv ?? healthYesterday?.hrv) != null && <Stat label="HRV" value={healthToday.hrv ?? healthYesterday?.hrv} unit="ms" color={C.cyan} size={22} />}
                {/* RHR is computed from last night's sleep — yesterday's finalized value is more accurate */}
                {(healthYesterday?.restingHR ?? healthToday.restingHR) != null && <Stat label="Resting HR" value={healthYesterday?.restingHR ?? healthToday.restingHR} unit="bpm" color={C.pink} size={22} />}
                {(healthToday.bodyBattery ?? healthYesterday?.bodyBattery) != null && <Stat label="Body Battery" value={healthToday.bodyBattery ?? healthYesterday?.bodyBattery} unit="%" color={C.green} size={22} />}
                {(healthYesterday?.sleepScore ?? healthToday.sleepScore) != null && <Stat label="Sleep" value={healthYesterday?.sleepScore ?? healthToday.sleepScore} unit="/100" color={C.purple} size={22} />}
                {healthToday.stress != null && <Stat label="Stress" value={healthToday.stress} unit="" color={C.amber} size={22} />}
                {(healthToday.trainingReadiness ?? healthYesterday?.trainingReadiness) != null && <Stat label="Readiness" value={healthToday.trainingReadiness ?? healthYesterday?.trainingReadiness} unit="" color={C.green} size={22} />}
                {healthToday.steps != null && <Stat label="Steps" value={healthToday.steps.toLocaleString()} unit="" color={C.amber} size={22} />}
              </div>
            </Card>
          )}

          {/* Recent runs */}
          <Card>
            <div style={{ fontSize: 13, fontWeight: 600, color: C.textDim, marginBottom: 16 }}>Recent Runs</div>
            {recentRuns.length === 0 ? (
              <EmptyState icon="🏃" title="No runs yet" sub="Connect Strava to sync your activities" />
            ) : (
              <div style={{ display:"flex", flexDirection:"column", gap: 0 }}>
                {recentRuns.map((run, i) => {
                  const wKg = 88;
                  const { zones: dZones, maxHR: dMaxHR } = getHRZones(hrZoneConfig);
                  const dFuelParams = [
                    { carbPct: 25, kcF: 0.13 }, { carbPct: 40, kcF: 0.15 },
                    { carbPct: 60, kcF: 0.17 }, { carbPct: 80, kcF: 0.19 }, { carbPct: 95, kcF: 0.22 },
                  ];
                  const mins = (run.moving_time || 0) / 60;
                  const dZi = run.average_heartrate ? classifyHRZone(run.average_heartrate, hrZoneConfig) : 1;
                  const dP = dFuelParams[dZi] || dFuelParams[1];
                  const cPct = dP.carbPct;
                  const kcPerMin = wKg * dP.kcF;
                  const tCal = Math.round(kcPerMin * mins);
                  const cG = Math.round(tCal * cPct / 100 / 4);
                  const fG = Math.round(tCal * (100 - cPct) / 100 / 9);
                  return (
                  <div key={run.id} style={{
                    display:"grid", gridTemplateColumns:"1fr auto auto auto auto auto",
                    gap: 14, alignItems:"center", padding:"12px 0",
                    borderBottom: i < recentRuns.length-1 ? `1px solid ${C.border}` : "none",
                  }}>
                    <div>
                      {(() => {
                        // Strides marker: name keyword, or the Z1-avg-with-Z4-spikes
                        // signature scoring.js uses to mark easy_with_strides runs.
                        const nm = (run.name || "").toLowerCase();
                        const nameStride = /stride|strides|neuromuscular/.test(nm);
                        const avg = run.average_heartrate || 0;
                        const max = run.max_heartrate || 0;
                        const hrStride = avg > 0 && max > 0 && avg < 144 && max >= 163 && (max - avg) >= 22;
                        const strides = nameStride || hrStride;
                        return (
                          <div style={{ display:"flex", alignItems:"center", gap:6 }}>
                            <div style={{ fontSize: 13, fontWeight: 600, color: C.text }}>{run.name || "Run"}</div>
                            {strides && <span style={{ fontSize:9, color:C.purple, padding:"1px 5px", background:C.purple+"18", border:`1px solid ${C.purple}40`, borderRadius:3, whiteSpace:"nowrap", fontWeight:700, letterSpacing:0.3 }}>⚡ STRIDES</span>}
                          </div>
                        );
                      })()}
                      <div style={{ fontSize: 11, color: C.textMuted, marginTop: 2 }}>{fmt.date(run.start_date)}</div>
                    </div>
                    <div style={{ textAlign:"right" }}>
                      <div style={{ fontSize: 14, fontWeight: 700, color: C.cyan }}>{fmt.distShort(run.distance)}</div>
                      <div style={{ fontSize: 10, color: C.textMuted }}>mi</div>
                    </div>
                    <div style={{ textAlign:"right" }}>
                      <div style={{ fontSize: 14, fontWeight: 700, color: C.text }}>{fmt.duration(run.moving_time)}</div>
                      <div style={{ fontSize: 10, color: C.textMuted }}>time</div>
                    </div>
                    <div style={{ textAlign:"right" }}>
                      <div style={{ fontSize: 13, color: C.amber }}>{fmt.pace(run.moving_time / (run.distance / 1609.34)).split(" ")[0]}</div>
                      <div style={{ fontSize: 10, color: C.textMuted }}>/mi</div>
                    </div>
                    <div style={{ textAlign:"right" }}>
                      <div style={{ fontSize: 13, color: C.pink }}>{run.average_heartrate ? Math.round(run.average_heartrate) : "--"}</div>
                      <div style={{ fontSize: 10, color: C.textMuted }}>bpm</div>
                    </div>
                    <div style={{ textAlign:"right", minWidth:52 }}>
                      <div style={{ fontSize:10, color:C.amber, fontWeight:600 }}>{cG}g C</div>
                      <div style={{ fontSize:10, color:C.cyan, fontWeight:600 }}>{fG}g F</div>
                    </div>
                  </div>
                  );
                })}
              </div>
            )}
          </Card>

          {/* Recent Cross-Training */}
          {recentXT.length > 0 && (
            <Card style={{ borderColor: C.green + "40" }}>
              <div style={{ display: "flex", justifyContent: "space-between", alignItems: "center", marginBottom: 16 }}>
                <div style={{ fontSize: 13, fontWeight: 600, color: C.textDim }}>Recent Cross-Training</div>
                <Badge label={`${recentXT.length} activities`} color={C.green} />
              </div>
              <div style={{ display:"flex", flexDirection:"column", gap: 0 }}>
                {recentXT.map((act, i) => {
                  const disp = actDisplay(effectiveType(act));
                  return (
                    <div key={act.id} style={{
                      display:"grid", gridTemplateColumns:"auto 1fr auto auto auto",
                      gap: 14, alignItems:"center", padding:"10px 0",
                      borderBottom: i < recentXT.length-1 ? `1px solid ${C.border}` : "none",
                    }}>
                      <span style={{ fontSize: 20 }}>{disp.emoji}</span>
                      <div>
                        <div style={{ fontSize: 13, fontWeight: 600, color: C.text }}>{act.name || disp.label}</div>
                        <div style={{ display:"flex", gap: 8, marginTop: 2 }}>
                          <span style={{ fontSize: 10, color: disp.color, background: disp.color + "18",
                            border: `1px solid ${disp.color}40`, borderRadius: 4, padding: "1px 6px" }}>{disp.label}</span>
                          <span style={{ fontSize: 11, color: C.textMuted }}>{fmt.date(act.start_date)}</span>
                        </div>
                      </div>
                      <div style={{ textAlign:"right" }}>
                        <div style={{ fontSize: 13, fontWeight: 700, color: disp.color }}>
                          {act.distance > 0 ? fmt.distShort(act.distance) + " mi" : fmt.duration(act.moving_time)}
                        </div>
                      </div>
                      <div style={{ textAlign:"right" }}>
                        <div style={{ fontSize: 13, color: C.text }}>{act.distance > 0 ? fmt.duration(act.moving_time) : ""}</div>
                      </div>
                      <div style={{ textAlign:"right" }}>
                        <div style={{ fontSize: 13, color: C.pink }}>{act.average_heartrate ? Math.round(act.average_heartrate) : "--"}</div>
                        <div style={{ fontSize: 10, color: C.textMuted }}>bpm</div>
                      </div>
                    </div>
                  );
                })}
              </div>
            </Card>
          )}
        </div>
      );
    }

window.AppViews = Object.assign(window.AppViews || {}, { Dashboard });
