@burdenoff/microfe-atheletebridge 2026.705.2 → 2026.706.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/atheletebridge/AthleteBridgeRoot.js +55 -39
- package/dist/atheletebridge/AthleteBridgeRoot.js.map +1 -1
- package/dist/atheletebridge/AthleteBridgeRoutes.js +18 -6
- package/dist/atheletebridge/AthleteBridgeRoutes.js.map +1 -1
- package/dist/atheletebridge/components/Crest.js +70 -0
- package/dist/atheletebridge/components/Crest.js.map +1 -0
- package/dist/atheletebridge/components/FixtureCard.js +8 -72
- package/dist/atheletebridge/components/FixtureCard.js.map +1 -1
- package/dist/atheletebridge/components/MatchupRow.js +74 -0
- package/dist/atheletebridge/components/MatchupRow.js.map +1 -0
- package/dist/atheletebridge/components/MetricsCard.js +61 -21
- package/dist/atheletebridge/components/MetricsCard.js.map +1 -1
- package/dist/atheletebridge/components/ProgramCard.js +75 -43
- package/dist/atheletebridge/components/ProgramCard.js.map +1 -1
- package/dist/atheletebridge/components/Scoreboard.js +163 -0
- package/dist/atheletebridge/components/Scoreboard.js.map +1 -0
- package/dist/atheletebridge/components/SessionCard.js +64 -41
- package/dist/atheletebridge/components/SessionCard.js.map +1 -1
- package/dist/atheletebridge/components/SessionStatusTimeline.js +80 -0
- package/dist/atheletebridge/components/SessionStatusTimeline.js.map +1 -0
- package/dist/atheletebridge/components/StatusBadge.js +5 -5
- package/dist/atheletebridge/components/StatusBadge.js.map +1 -1
- package/dist/atheletebridge/components/TeamCard.js +65 -35
- package/dist/atheletebridge/components/TeamCard.js.map +1 -1
- package/dist/atheletebridge/components/UserAvatar.js +33 -0
- package/dist/atheletebridge/components/UserAvatar.js.map +1 -0
- package/dist/atheletebridge/components/domain.js +5 -2
- package/dist/atheletebridge/components/domain.js.map +1 -1
- package/dist/atheletebridge/components/viz/AvatarStack.js +2 -0
- package/dist/atheletebridge/components/viz/BarChart.js +83 -0
- package/dist/atheletebridge/components/viz/BarChart.js.map +1 -0
- package/dist/atheletebridge/components/viz/DonutChart.js +109 -0
- package/dist/atheletebridge/components/viz/DonutChart.js.map +1 -0
- package/dist/atheletebridge/components/viz/LineChart.js +123 -0
- package/dist/atheletebridge/components/viz/LineChart.js.map +1 -0
- package/dist/atheletebridge/components/viz/ProgressRing.js +6 -0
- package/dist/atheletebridge/components/viz/ProgressRing.js.map +1 -0
- package/dist/atheletebridge/components/viz/RatingStars.js +92 -0
- package/dist/atheletebridge/components/viz/RatingStars.js.map +1 -0
- package/dist/atheletebridge/components/viz/Sparkline.js +74 -0
- package/dist/atheletebridge/components/viz/Sparkline.js.map +1 -0
- package/dist/atheletebridge/components/viz/StatCard.js +60 -0
- package/dist/atheletebridge/components/viz/StatCard.js.map +1 -0
- package/dist/atheletebridge/components/viz/StepProgress.js +3 -0
- package/dist/atheletebridge/components/viz/Timeline.js +66 -0
- package/dist/atheletebridge/components/viz/Timeline.js.map +1 -0
- package/dist/atheletebridge/components/viz/index.js +13 -0
- package/dist/atheletebridge/components/viz/lib/Avatar.js +1 -0
- package/dist/atheletebridge/components/viz/lib/CartesianFrame.js +119 -0
- package/dist/atheletebridge/components/viz/lib/CartesianFrame.js.map +1 -0
- package/dist/atheletebridge/components/viz/lib/ResponsiveSvg.js +35 -0
- package/dist/atheletebridge/components/viz/lib/ResponsiveSvg.js.map +1 -0
- package/dist/atheletebridge/components/viz/lib/format.js +17 -0
- package/dist/atheletebridge/components/viz/lib/format.js.map +1 -0
- package/dist/atheletebridge/components/viz/lib/geometry.js +61 -0
- package/dist/atheletebridge/components/viz/lib/geometry.js.map +1 -0
- package/dist/atheletebridge/components/viz/lib/hooks.js +39 -0
- package/dist/atheletebridge/components/viz/lib/hooks.js.map +1 -0
- package/dist/atheletebridge/components/viz/lib/palette.js +27 -0
- package/dist/atheletebridge/components/viz/lib/palette.js.map +1 -0
- package/dist/atheletebridge/hooks/useAthleteBridgeApi.js +369 -163
- package/dist/atheletebridge/hooks/useAthleteBridgeApi.js.map +1 -1
- package/dist/atheletebridge/pages/DashboardPage.js +182 -117
- package/dist/atheletebridge/pages/DashboardPage.js.map +1 -1
- package/dist/atheletebridge/pages/StandingsPage.js +119 -95
- package/dist/atheletebridge/pages/StandingsPage.js.map +1 -1
- package/dist/atheletebridge/pages/analytics/CoachAnalyticsPage.js +372 -0
- package/dist/atheletebridge/pages/analytics/CoachAnalyticsPage.js.map +1 -0
- package/dist/atheletebridge/pages/athletes/AthleteProfilePage.js +511 -0
- package/dist/atheletebridge/pages/athletes/AthleteProfilePage.js.map +1 -0
- package/dist/atheletebridge/pages/fixtures/FixtureDetailPage.js +120 -131
- package/dist/atheletebridge/pages/fixtures/FixtureDetailPage.js.map +1 -1
- package/dist/atheletebridge/pages/fixtures/FixtureFormPage.js +264 -176
- package/dist/atheletebridge/pages/fixtures/FixtureFormPage.js.map +1 -1
- package/dist/atheletebridge/pages/fixtures/FixturesListPage.js +84 -47
- package/dist/atheletebridge/pages/fixtures/FixturesListPage.js.map +1 -1
- package/dist/atheletebridge/pages/performance/PerformancePage.js +432 -281
- package/dist/atheletebridge/pages/performance/PerformancePage.js.map +1 -1
- package/dist/atheletebridge/pages/programs/ProgramDetailPage.js +187 -123
- package/dist/atheletebridge/pages/programs/ProgramDetailPage.js.map +1 -1
- package/dist/atheletebridge/pages/programs/ProgramsListPage.js +56 -39
- package/dist/atheletebridge/pages/programs/ProgramsListPage.js.map +1 -1
- package/dist/atheletebridge/pages/sessions/SessionDetailPage.js +267 -139
- package/dist/atheletebridge/pages/sessions/SessionDetailPage.js.map +1 -1
- package/dist/atheletebridge/pages/sessions/SessionFormPage.js +253 -162
- package/dist/atheletebridge/pages/sessions/SessionFormPage.js.map +1 -1
- package/dist/atheletebridge/pages/sessions/SessionsListPage.js +38 -36
- package/dist/atheletebridge/pages/sessions/SessionsListPage.js.map +1 -1
- package/dist/atheletebridge/pages/teams/TeamDetailPage.js +437 -189
- package/dist/atheletebridge/pages/teams/TeamDetailPage.js.map +1 -1
- package/dist/atheletebridge/pages/teams/TeamFormPage.js +368 -177
- package/dist/atheletebridge/pages/teams/TeamFormPage.js.map +1 -1
- package/dist/atheletebridge/pages/teams/TeamsListPage.js +3 -0
- package/dist/atheletebridge/pages/teams/TeamsListPage.js.map +1 -1
- package/dist/atheletebridge/pages/tournaments/TournamentBracketPage.js +298 -0
- package/dist/atheletebridge/pages/tournaments/TournamentBracketPage.js.map +1 -0
- package/dist/atheletebridge/utils/identity.js +31 -0
- package/dist/atheletebridge/utils/identity.js.map +1 -0
- package/dist/atheletebridge/utils/timeAgo.js +20 -0
- package/dist/atheletebridge/utils/timeAgo.js.map +1 -0
- package/package.json +1 -1
|
@@ -1,17 +1,17 @@
|
|
|
1
1
|
import { useAthleteBridge as e } from "../../context/AthleteBridgeContext.js";
|
|
2
2
|
import { PageLayout as t } from "../../components/PageLayout.js";
|
|
3
3
|
import { StatusBadge as n } from "../../components/StatusBadge.js";
|
|
4
|
-
import { PROGRAM_LEVEL_LABELS as r,
|
|
5
|
-
import { EmptyState as
|
|
6
|
-
import { ErrorState as
|
|
7
|
-
import { useAddDrill as
|
|
4
|
+
import { PROGRAM_LEVEL_LABELS as r, SPORT_ICONS as i, SPORT_LABELS as a } from "../../components/domain.js";
|
|
5
|
+
import { EmptyState as o } from "../../components/EmptyState.js";
|
|
6
|
+
import { ErrorState as s, LoadingState as c } from "../../components/LoadingState.js";
|
|
7
|
+
import { useAddDrill as l, useArchiveProgram as ee, useProgram as te, useRemoveDrill as ne, useTransitionProgram as re, useUploadFile as ie } from "../../hooks/useAthleteBridgeApi.js";
|
|
8
8
|
import { FormField as u, fieldInputClass as d } from "../../components/form.js";
|
|
9
9
|
import { DrillVideoLink as f } from "../../components/DrillVideoLink.js";
|
|
10
10
|
import { useMemo as p, useState as m } from "react";
|
|
11
|
-
import { Archive as h, ArrowLeft as g, Copy as _, Edit as v, FileVideo as y, Loader2 as b, Plus as x, Send as
|
|
12
|
-
import { useParams as
|
|
13
|
-
import { Fragment as
|
|
14
|
-
import {
|
|
11
|
+
import { Archive as h, ArrowLeft as g, Copy as _, Edit as v, FileVideo as y, Loader2 as b, Plus as x, Send as ae, Trash2 as oe, Undo2 as se } from "lucide-react";
|
|
12
|
+
import { useParams as ce } from "react-router-dom";
|
|
13
|
+
import { Fragment as le, jsx as S, jsxs as C } from "react/jsx-runtime";
|
|
14
|
+
import { Accordion as ue, AccordionContent as de, AccordionItem as fe, AccordionTrigger as pe, Badge as w, GlassCard as T, ResponsiveDialog as E, ResponsiveDialogContent as D, ResponsiveDialogFooter as O, ResponsiveDialogHeader as k, ResponsiveDialogTitle as A } from "@burdenoff/fe-libs/ui";
|
|
15
15
|
//#region src/atheletebridge/pages/programs/ProgramDetailPage.tsx
|
|
16
16
|
var j = {
|
|
17
17
|
name: "",
|
|
@@ -21,15 +21,18 @@ var j = {
|
|
|
21
21
|
reps: "",
|
|
22
22
|
durationSec: "",
|
|
23
23
|
restSec: ""
|
|
24
|
-
}, M = (e) => {
|
|
24
|
+
}, M = ({ children: e }) => /* @__PURE__ */ S("span", {
|
|
25
|
+
className: "inline-flex items-center rounded-md border border-border-seam bg-bg-sunken px-2 py-0.5 text-xs font-medium tabular-nums text-text-secondary",
|
|
26
|
+
children: e
|
|
27
|
+
}), N = (e) => {
|
|
25
28
|
let t = e.trim();
|
|
26
29
|
if (!t) return;
|
|
27
30
|
let n = Number.parseInt(t, 10);
|
|
28
31
|
return Number.isNaN(n) ? void 0 : n;
|
|
29
32
|
};
|
|
30
|
-
function
|
|
31
|
-
let { id:
|
|
32
|
-
let e =
|
|
33
|
+
function P() {
|
|
34
|
+
let { id: P } = ce(), { navigateTo: F } = e(), I = te(P), L = re(), R = ee(), z = l(), B = ne(P), me = ie(), [he, V] = m(!1), [H, U] = m(j), [W, G] = m(null), [K, q] = m(!1), [J, Y] = m(null), X = p(() => {
|
|
35
|
+
let e = I.data?.drills ?? [], t = /* @__PURE__ */ new Map();
|
|
33
36
|
for (let n of e) {
|
|
34
37
|
let e = t.get(n.weekNumber) ?? [];
|
|
35
38
|
e.push(n), t.set(n.weekNumber, e);
|
|
@@ -38,52 +41,53 @@ function N() {
|
|
|
38
41
|
week: e,
|
|
39
42
|
drills: [...t].sort((e, t) => e.orderIndex - t.orderIndex)
|
|
40
43
|
}));
|
|
41
|
-
}, [
|
|
42
|
-
if (
|
|
44
|
+
}, [I.data]);
|
|
45
|
+
if (I.isLoading) return /* @__PURE__ */ S(t, {
|
|
43
46
|
title: "Program",
|
|
44
|
-
children: /* @__PURE__ */ S(
|
|
47
|
+
children: /* @__PURE__ */ S(c, { label: "Loading program…" })
|
|
45
48
|
});
|
|
46
|
-
if (
|
|
49
|
+
if (I.isError || !I.data) return /* @__PURE__ */ S(t, {
|
|
47
50
|
title: "Program",
|
|
48
|
-
children: /* @__PURE__ */ S(
|
|
51
|
+
children: /* @__PURE__ */ S(s, {
|
|
49
52
|
title: "Program not found",
|
|
50
53
|
message: "This program does not exist or you do not have access to it.",
|
|
51
|
-
onRetry: () =>
|
|
54
|
+
onRetry: () => F("/programs")
|
|
52
55
|
})
|
|
53
56
|
});
|
|
54
|
-
let Z =
|
|
55
|
-
|
|
56
|
-
id:
|
|
57
|
+
let Z = I.data, Q = Z.drills?.length ?? 0, ge = i[Z.sport], _e = X.map(({ week: e }) => `week-${e}`), $ = (e) => {
|
|
58
|
+
P && L.mutate({
|
|
59
|
+
id: P,
|
|
57
60
|
status: e
|
|
58
61
|
});
|
|
59
62
|
};
|
|
60
63
|
return /* @__PURE__ */ C(t, {
|
|
61
64
|
title: Z.name,
|
|
62
|
-
|
|
65
|
+
gradientTitle: !0,
|
|
66
|
+
description: `${a[Z.sport]} · ${r[Z.level]} · ${Z.weeks} ${Z.weeks === 1 ? "week" : "weeks"}`,
|
|
63
67
|
actions: /* @__PURE__ */ C("div", {
|
|
64
68
|
className: "flex flex-wrap items-center gap-2",
|
|
65
69
|
children: [
|
|
66
70
|
/* @__PURE__ */ C("button", {
|
|
67
71
|
type: "button",
|
|
68
|
-
onClick: () =>
|
|
72
|
+
onClick: () => F("/programs"),
|
|
69
73
|
className: "inline-flex items-center gap-1.5 rounded-lg border border-border-seam px-3 py-2 text-sm font-medium text-text-primary transition-colors hover:bg-bg-sunken",
|
|
70
74
|
children: [/* @__PURE__ */ S(g, { className: "h-4 w-4" }), " Back"]
|
|
71
75
|
}),
|
|
72
76
|
/* @__PURE__ */ C("button", {
|
|
73
77
|
type: "button",
|
|
74
|
-
onClick: () =>
|
|
78
|
+
onClick: () => F(`/programs/${Z.id}/edit`),
|
|
75
79
|
className: "inline-flex items-center gap-1.5 rounded-lg border border-border-seam px-3 py-2 text-sm font-medium text-text-primary transition-colors hover:bg-bg-sunken",
|
|
76
80
|
children: [/* @__PURE__ */ S(v, { className: "h-4 w-4" }), " Edit"]
|
|
77
81
|
}),
|
|
78
82
|
Z.status !== "ARCHIVED" && /* @__PURE__ */ C("button", {
|
|
79
83
|
type: "button",
|
|
80
84
|
onClick: async () => {
|
|
81
|
-
|
|
85
|
+
P && (await R.mutateAsync(P), F("/programs"));
|
|
82
86
|
},
|
|
83
|
-
disabled:
|
|
87
|
+
disabled: R.isPending,
|
|
84
88
|
className: "inline-flex items-center gap-1.5 rounded-lg border border-border-seam px-3 py-2 text-sm font-medium text-status-error-text transition-colors hover:bg-status-error-bg-subtle disabled:opacity-60",
|
|
85
89
|
children: [
|
|
86
|
-
|
|
90
|
+
R.isPending ? /* @__PURE__ */ S(b, { className: "h-4 w-4 animate-spin" }) : /* @__PURE__ */ S(h, { className: "h-4 w-4" }),
|
|
87
91
|
" ",
|
|
88
92
|
"Archive"
|
|
89
93
|
]
|
|
@@ -96,10 +100,44 @@ function N() {
|
|
|
96
100
|
className: "mb-8 p-6",
|
|
97
101
|
children: [
|
|
98
102
|
/* @__PURE__ */ C("div", {
|
|
99
|
-
className: "flex
|
|
100
|
-
children: [/* @__PURE__ */ S(
|
|
101
|
-
className: "
|
|
102
|
-
children:
|
|
103
|
+
className: "flex items-start gap-4",
|
|
104
|
+
children: [/* @__PURE__ */ S("div", {
|
|
105
|
+
className: "flex h-14 w-14 shrink-0 items-center justify-center rounded-2xl bg-[var(--color-accent-soft)] text-text-primary",
|
|
106
|
+
children: /* @__PURE__ */ S(ge, {
|
|
107
|
+
className: "h-7 w-7",
|
|
108
|
+
"aria-hidden": "true"
|
|
109
|
+
})
|
|
110
|
+
}), /* @__PURE__ */ C("div", {
|
|
111
|
+
className: "min-w-0 flex-1",
|
|
112
|
+
children: [/* @__PURE__ */ C("div", {
|
|
113
|
+
className: "flex flex-wrap items-center gap-2",
|
|
114
|
+
children: [
|
|
115
|
+
/* @__PURE__ */ S(w, {
|
|
116
|
+
variant: "secondary",
|
|
117
|
+
children: a[Z.sport]
|
|
118
|
+
}),
|
|
119
|
+
/* @__PURE__ */ S(w, {
|
|
120
|
+
variant: "secondary",
|
|
121
|
+
children: r[Z.level]
|
|
122
|
+
}),
|
|
123
|
+
/* @__PURE__ */ S(n, { status: Z.status }),
|
|
124
|
+
Z.isTemplate && /* @__PURE__ */ C("span", {
|
|
125
|
+
className: "inline-flex items-center gap-1 text-xs text-text-secondary",
|
|
126
|
+
children: [/* @__PURE__ */ S(_, { className: "h-3.5 w-3.5" }), " Template"]
|
|
127
|
+
})
|
|
128
|
+
]
|
|
129
|
+
}), /* @__PURE__ */ C("p", {
|
|
130
|
+
className: "mt-2 text-sm text-text-secondary",
|
|
131
|
+
children: [
|
|
132
|
+
Z.weeks,
|
|
133
|
+
" ",
|
|
134
|
+
Z.weeks === 1 ? "week" : "weeks",
|
|
135
|
+
" · ",
|
|
136
|
+
Q,
|
|
137
|
+
" ",
|
|
138
|
+
Q === 1 ? "drill" : "drills"
|
|
139
|
+
]
|
|
140
|
+
})]
|
|
103
141
|
})]
|
|
104
142
|
}),
|
|
105
143
|
Z.summary && /* @__PURE__ */ S("p", {
|
|
@@ -123,20 +161,20 @@ function N() {
|
|
|
123
161
|
Z.status === "DRAFT" && /* @__PURE__ */ C("button", {
|
|
124
162
|
type: "button",
|
|
125
163
|
onClick: () => $("PUBLISHED"),
|
|
126
|
-
disabled:
|
|
164
|
+
disabled: L.isPending,
|
|
127
165
|
className: "inline-flex items-center gap-1.5 rounded-lg bg-action-primary-bg px-3 py-1.5 text-sm font-medium text-action-primary-text transition-colors hover:bg-action-primary-bg/90 disabled:opacity-60",
|
|
128
|
-
children: [/* @__PURE__ */ S(
|
|
166
|
+
children: [/* @__PURE__ */ S(ae, { className: "h-4 w-4" }), " Publish"]
|
|
129
167
|
}),
|
|
130
|
-
Z.status === "PUBLISHED" && /* @__PURE__ */ C(
|
|
168
|
+
Z.status === "PUBLISHED" && /* @__PURE__ */ C(le, { children: [/* @__PURE__ */ C("button", {
|
|
131
169
|
type: "button",
|
|
132
170
|
onClick: () => $("DRAFT"),
|
|
133
|
-
disabled:
|
|
171
|
+
disabled: L.isPending,
|
|
134
172
|
className: "inline-flex items-center gap-1.5 rounded-lg border border-border-seam px-3 py-1.5 text-sm font-medium text-text-primary transition-colors hover:bg-bg-sunken disabled:opacity-60",
|
|
135
|
-
children: [/* @__PURE__ */ S(
|
|
173
|
+
children: [/* @__PURE__ */ S(se, { className: "h-4 w-4" }), " Pull back to draft"]
|
|
136
174
|
}), /* @__PURE__ */ C("button", {
|
|
137
175
|
type: "button",
|
|
138
176
|
onClick: () => $("ARCHIVED"),
|
|
139
|
-
disabled:
|
|
177
|
+
disabled: L.isPending,
|
|
140
178
|
className: "inline-flex items-center gap-1.5 rounded-lg border border-border-seam px-3 py-1.5 text-sm font-medium text-text-primary transition-colors hover:bg-bg-sunken disabled:opacity-60",
|
|
141
179
|
children: [/* @__PURE__ */ S(h, { className: "h-4 w-4" }), " Archive"]
|
|
142
180
|
})] }),
|
|
@@ -144,7 +182,7 @@ function N() {
|
|
|
144
182
|
className: "text-sm text-text-secondary",
|
|
145
183
|
children: "This program is archived."
|
|
146
184
|
}),
|
|
147
|
-
|
|
185
|
+
L.isPending && /* @__PURE__ */ S(b, { className: "h-4 w-4 animate-spin text-text-secondary" })
|
|
148
186
|
]
|
|
149
187
|
})
|
|
150
188
|
]
|
|
@@ -161,94 +199,120 @@ function N() {
|
|
|
161
199
|
}), /* @__PURE__ */ C("button", {
|
|
162
200
|
type: "button",
|
|
163
201
|
onClick: () => {
|
|
164
|
-
|
|
202
|
+
Y(null), V(!0);
|
|
165
203
|
},
|
|
166
204
|
className: "inline-flex items-center gap-1.5 rounded-lg bg-action-primary-bg px-3 py-1.5 text-sm font-medium text-action-primary-text transition-colors hover:bg-action-primary-bg/90",
|
|
167
205
|
children: [/* @__PURE__ */ S(x, { className: "h-4 w-4" }), " Add drill"]
|
|
168
206
|
})]
|
|
169
|
-
}), Q === 0 ? /* @__PURE__ */ S(
|
|
207
|
+
}), Q === 0 ? /* @__PURE__ */ S(o, {
|
|
170
208
|
illustration: "empty-data",
|
|
171
209
|
icon: /* @__PURE__ */ S(x, { className: "h-10 w-10" }),
|
|
172
210
|
title: "No drills yet",
|
|
173
211
|
description: "Add drills with sets, reps and durations, organized by week."
|
|
174
|
-
}) : /* @__PURE__ */ S(
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
className: "
|
|
181
|
-
children:
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
}),
|
|
194
|
-
/* @__PURE__ */ C("div", {
|
|
195
|
-
className: "mt-1.5 flex flex-wrap gap-x-3 gap-y-1 text-xs text-text-secondary",
|
|
212
|
+
}) : /* @__PURE__ */ S(ue, {
|
|
213
|
+
type: "multiple",
|
|
214
|
+
defaultValue: _e,
|
|
215
|
+
className: "flex flex-col gap-3",
|
|
216
|
+
children: X.map(({ week: e, drills: t }) => /* @__PURE__ */ S(T, {
|
|
217
|
+
treatment: "insight",
|
|
218
|
+
className: "overflow-hidden px-4 py-0",
|
|
219
|
+
children: /* @__PURE__ */ C(fe, {
|
|
220
|
+
value: `week-${e}`,
|
|
221
|
+
className: "border-b-0",
|
|
222
|
+
children: [/* @__PURE__ */ S(pe, {
|
|
223
|
+
className: "py-4",
|
|
224
|
+
children: /* @__PURE__ */ C("span", {
|
|
225
|
+
className: "flex items-center gap-2.5",
|
|
226
|
+
children: [/* @__PURE__ */ C("span", {
|
|
227
|
+
className: "text-sm font-semibold text-text-primary",
|
|
228
|
+
children: ["Week ", e]
|
|
229
|
+
}), /* @__PURE__ */ C(w, {
|
|
230
|
+
variant: "secondary",
|
|
196
231
|
children: [
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
e.restSec !== null && /* @__PURE__ */ C("span", { children: [e.restSec, "s rest"] })
|
|
232
|
+
t.length,
|
|
233
|
+
" ",
|
|
234
|
+
t.length === 1 ? "drill" : "drills"
|
|
201
235
|
]
|
|
202
|
-
})
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
236
|
+
})]
|
|
237
|
+
})
|
|
238
|
+
}), /* @__PURE__ */ S(de, {
|
|
239
|
+
className: "pb-2",
|
|
240
|
+
children: /* @__PURE__ */ S("div", {
|
|
241
|
+
className: "divide-y divide-border-seam",
|
|
242
|
+
children: t.map((e) => /* @__PURE__ */ C("div", {
|
|
243
|
+
className: "flex items-start gap-4 py-3",
|
|
244
|
+
children: [/* @__PURE__ */ C("div", {
|
|
245
|
+
className: "min-w-0 flex-1",
|
|
246
|
+
children: [
|
|
247
|
+
/* @__PURE__ */ S("p", {
|
|
248
|
+
className: "text-sm font-medium text-text-primary",
|
|
249
|
+
children: e.name
|
|
250
|
+
}),
|
|
251
|
+
e.description && /* @__PURE__ */ S("p", {
|
|
252
|
+
className: "mt-0.5 text-xs text-text-secondary",
|
|
253
|
+
children: e.description
|
|
254
|
+
}),
|
|
255
|
+
/* @__PURE__ */ C("div", {
|
|
256
|
+
className: "mt-2 flex flex-wrap gap-1.5",
|
|
257
|
+
children: [
|
|
258
|
+
e.sets !== null && /* @__PURE__ */ C(M, { children: [e.sets, " sets"] }),
|
|
259
|
+
e.reps !== null && /* @__PURE__ */ C(M, { children: [e.reps, " reps"] }),
|
|
260
|
+
e.durationSec !== null && /* @__PURE__ */ C(M, { children: [e.durationSec, "s work"] }),
|
|
261
|
+
e.restSec !== null && /* @__PURE__ */ C(M, { children: [e.restSec, "s rest"] })
|
|
262
|
+
]
|
|
263
|
+
}),
|
|
264
|
+
e.video?.id && /* @__PURE__ */ S("div", { children: /* @__PURE__ */ S(f, { fileId: e.video.id }) })
|
|
265
|
+
]
|
|
266
|
+
}), /* @__PURE__ */ S("button", {
|
|
267
|
+
type: "button",
|
|
268
|
+
onClick: () => void B.mutate(e.id),
|
|
269
|
+
disabled: B.isPending,
|
|
270
|
+
"aria-label": `Remove ${e.name}`,
|
|
271
|
+
className: "rounded-lg p-2 text-text-secondary transition-colors hover:bg-status-error-bg-subtle hover:text-status-error-text disabled:opacity-60",
|
|
272
|
+
children: /* @__PURE__ */ S(oe, { className: "h-4 w-4" })
|
|
273
|
+
})]
|
|
274
|
+
}, e.id))
|
|
275
|
+
})
|
|
212
276
|
})]
|
|
213
|
-
}
|
|
214
|
-
}
|
|
277
|
+
})
|
|
278
|
+
}, e))
|
|
215
279
|
})] }),
|
|
216
280
|
/* @__PURE__ */ S(E, {
|
|
217
|
-
open:
|
|
218
|
-
onOpenChange:
|
|
281
|
+
open: he,
|
|
282
|
+
onOpenChange: V,
|
|
219
283
|
children: /* @__PURE__ */ C(D, { children: [/* @__PURE__ */ S(k, { children: /* @__PURE__ */ S(A, { children: "Add drill" }) }), /* @__PURE__ */ C("form", {
|
|
220
284
|
onSubmit: async (e) => {
|
|
221
|
-
if (e.preventDefault(),
|
|
222
|
-
if (!
|
|
223
|
-
|
|
285
|
+
if (e.preventDefault(), Y(null), !P) return;
|
|
286
|
+
if (!H.name.trim()) {
|
|
287
|
+
Y("Drill name is required.");
|
|
224
288
|
return;
|
|
225
289
|
}
|
|
226
|
-
let t =
|
|
227
|
-
if (
|
|
228
|
-
|
|
290
|
+
let t = N(H.weekNumber) ?? 1, n;
|
|
291
|
+
if (W) {
|
|
292
|
+
q(!0);
|
|
229
293
|
try {
|
|
230
|
-
n = await
|
|
294
|
+
n = await me(W);
|
|
231
295
|
} catch (e) {
|
|
232
|
-
|
|
296
|
+
Y(e instanceof Error ? e.message : "Failed to upload the demo video."), q(!1);
|
|
233
297
|
return;
|
|
234
298
|
}
|
|
235
|
-
|
|
299
|
+
q(!1);
|
|
236
300
|
}
|
|
237
301
|
try {
|
|
238
|
-
await
|
|
239
|
-
programId:
|
|
240
|
-
name:
|
|
241
|
-
description:
|
|
302
|
+
await z.mutateAsync({
|
|
303
|
+
programId: P,
|
|
304
|
+
name: H.name.trim(),
|
|
305
|
+
description: H.description.trim() || void 0,
|
|
242
306
|
weekNumber: t,
|
|
243
|
-
orderIndex:
|
|
244
|
-
sets:
|
|
245
|
-
reps:
|
|
246
|
-
durationSec:
|
|
247
|
-
restSec:
|
|
307
|
+
orderIndex: I.data?.drills?.filter((e) => e.weekNumber === t).length ?? 0,
|
|
308
|
+
sets: N(H.sets),
|
|
309
|
+
reps: N(H.reps),
|
|
310
|
+
durationSec: N(H.durationSec),
|
|
311
|
+
restSec: N(H.restSec),
|
|
248
312
|
videoFileId: n
|
|
249
|
-
}),
|
|
313
|
+
}), U(j), G(null), V(!1);
|
|
250
314
|
} catch (e) {
|
|
251
|
-
|
|
315
|
+
Y(e instanceof Error ? e.message : "Failed to add drill.");
|
|
252
316
|
}
|
|
253
317
|
},
|
|
254
318
|
className: "space-y-4 px-1",
|
|
@@ -260,8 +324,8 @@ function N() {
|
|
|
260
324
|
children: /* @__PURE__ */ S("input", {
|
|
261
325
|
id: "drillName",
|
|
262
326
|
className: d,
|
|
263
|
-
value:
|
|
264
|
-
onChange: (e) =>
|
|
327
|
+
value: H.name,
|
|
328
|
+
onChange: (e) => U((t) => ({
|
|
265
329
|
...t,
|
|
266
330
|
name: e.target.value
|
|
267
331
|
})),
|
|
@@ -275,8 +339,8 @@ function N() {
|
|
|
275
339
|
id: "drillDesc",
|
|
276
340
|
className: d,
|
|
277
341
|
rows: 2,
|
|
278
|
-
value:
|
|
279
|
-
onChange: (e) =>
|
|
342
|
+
value: H.description,
|
|
343
|
+
onChange: (e) => U((t) => ({
|
|
280
344
|
...t,
|
|
281
345
|
description: e.target.value
|
|
282
346
|
})),
|
|
@@ -293,8 +357,8 @@ function N() {
|
|
|
293
357
|
id: "drillWeek",
|
|
294
358
|
inputMode: "numeric",
|
|
295
359
|
className: d,
|
|
296
|
-
value:
|
|
297
|
-
onChange: (e) =>
|
|
360
|
+
value: H.weekNumber,
|
|
361
|
+
onChange: (e) => U((t) => ({
|
|
298
362
|
...t,
|
|
299
363
|
weekNumber: e.target.value
|
|
300
364
|
}))
|
|
@@ -307,8 +371,8 @@ function N() {
|
|
|
307
371
|
id: "drillSets",
|
|
308
372
|
inputMode: "numeric",
|
|
309
373
|
className: d,
|
|
310
|
-
value:
|
|
311
|
-
onChange: (e) =>
|
|
374
|
+
value: H.sets,
|
|
375
|
+
onChange: (e) => U((t) => ({
|
|
312
376
|
...t,
|
|
313
377
|
sets: e.target.value
|
|
314
378
|
}))
|
|
@@ -321,8 +385,8 @@ function N() {
|
|
|
321
385
|
id: "drillReps",
|
|
322
386
|
inputMode: "numeric",
|
|
323
387
|
className: d,
|
|
324
|
-
value:
|
|
325
|
-
onChange: (e) =>
|
|
388
|
+
value: H.reps,
|
|
389
|
+
onChange: (e) => U((t) => ({
|
|
326
390
|
...t,
|
|
327
391
|
reps: e.target.value
|
|
328
392
|
}))
|
|
@@ -339,8 +403,8 @@ function N() {
|
|
|
339
403
|
id: "drillDuration",
|
|
340
404
|
inputMode: "numeric",
|
|
341
405
|
className: d,
|
|
342
|
-
value:
|
|
343
|
-
onChange: (e) =>
|
|
406
|
+
value: H.durationSec,
|
|
407
|
+
onChange: (e) => U((t) => ({
|
|
344
408
|
...t,
|
|
345
409
|
durationSec: e.target.value
|
|
346
410
|
}))
|
|
@@ -352,8 +416,8 @@ function N() {
|
|
|
352
416
|
id: "drillRest",
|
|
353
417
|
inputMode: "numeric",
|
|
354
418
|
className: d,
|
|
355
|
-
value:
|
|
356
|
-
onChange: (e) =>
|
|
419
|
+
value: H.restSec,
|
|
420
|
+
onChange: (e) => U((t) => ({
|
|
357
421
|
...t,
|
|
358
422
|
restSec: e.target.value
|
|
359
423
|
}))
|
|
@@ -369,32 +433,32 @@ function N() {
|
|
|
369
433
|
type: "file",
|
|
370
434
|
accept: "video/*",
|
|
371
435
|
className: d,
|
|
372
|
-
onChange: (e) =>
|
|
373
|
-
}),
|
|
436
|
+
onChange: (e) => G(e.target.files?.[0] ?? null)
|
|
437
|
+
}), W && /* @__PURE__ */ C("p", {
|
|
374
438
|
className: "mt-1 inline-flex items-center gap-1 text-xs text-text-secondary",
|
|
375
439
|
children: [
|
|
376
440
|
/* @__PURE__ */ S(y, { className: "h-3.5 w-3.5" }),
|
|
377
441
|
" ",
|
|
378
|
-
|
|
442
|
+
W.name
|
|
379
443
|
]
|
|
380
444
|
})]
|
|
381
445
|
}),
|
|
382
|
-
|
|
446
|
+
J && /* @__PURE__ */ S("p", {
|
|
383
447
|
className: "text-sm text-status-error-text",
|
|
384
|
-
children:
|
|
448
|
+
children: J
|
|
385
449
|
}),
|
|
386
450
|
/* @__PURE__ */ C(O, { children: [/* @__PURE__ */ S("button", {
|
|
387
451
|
type: "button",
|
|
388
452
|
onClick: () => {
|
|
389
|
-
|
|
453
|
+
V(!1), G(null);
|
|
390
454
|
},
|
|
391
455
|
className: "rounded-lg border border-border-seam px-4 py-2 text-sm font-medium text-text-primary transition-colors hover:bg-bg-sunken",
|
|
392
456
|
children: "Cancel"
|
|
393
457
|
}), /* @__PURE__ */ C("button", {
|
|
394
458
|
type: "submit",
|
|
395
|
-
disabled:
|
|
459
|
+
disabled: z.isPending || K,
|
|
396
460
|
className: "inline-flex items-center gap-1.5 rounded-lg bg-action-primary-bg px-4 py-2 text-sm font-medium text-action-primary-text transition-colors hover:bg-action-primary-bg/90 disabled:opacity-60",
|
|
397
|
-
children: [(
|
|
461
|
+
children: [(z.isPending || K) && /* @__PURE__ */ S(b, { className: "h-4 w-4 animate-spin" }), K ? "Uploading video…" : "Add drill"]
|
|
398
462
|
})] })
|
|
399
463
|
]
|
|
400
464
|
})] })
|
|
@@ -403,6 +467,6 @@ function N() {
|
|
|
403
467
|
});
|
|
404
468
|
}
|
|
405
469
|
//#endregion
|
|
406
|
-
export {
|
|
470
|
+
export { P as ProgramDetailPage };
|
|
407
471
|
|
|
408
472
|
//# sourceMappingURL=ProgramDetailPage.js.map
|