@sensiblestats/widget-react 0.84.0 → 0.86.0
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/CHANGELOG.md +22 -0
- package/dist/index.cjs +1273 -392
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1236 -355
- package/dist/index.js.map +1 -1
- package/dist/styles.css +106 -4
- package/package.json +2 -2
package/dist/index.cjs
CHANGED
|
@@ -37,7 +37,7 @@ __export(index_exports, {
|
|
|
37
37
|
module.exports = __toCommonJS(index_exports);
|
|
38
38
|
|
|
39
39
|
// src/StatsWidget.tsx
|
|
40
|
-
var
|
|
40
|
+
var import_react69 = require("react");
|
|
41
41
|
var import_widget_sdk6 = require("@sensiblestats/widget-sdk");
|
|
42
42
|
|
|
43
43
|
// src/kickoff.ts
|
|
@@ -53,8 +53,13 @@ function formatBettingKickoff(kickoffUtc, ui, locale, now = /* @__PURE__ */ new
|
|
|
53
53
|
}
|
|
54
54
|
|
|
55
55
|
// src/i18n.ts
|
|
56
|
+
var GROUP_NOUN_EN = { G: "goalkeepers", D: "defenders", M: "midfielders", F: "forwards" };
|
|
57
|
+
var GROUP_NOUN_TR = { G: "kalecileri", D: "defans oyuncular\u0131", M: "orta saha oyuncular\u0131", F: "forvetleri" };
|
|
56
58
|
var formatPtsEn = (n) => new Intl.NumberFormat("en-GB").format(n);
|
|
57
59
|
var formatPtsTr = (n) => new Intl.NumberFormat("tr-TR").format(n);
|
|
60
|
+
var nbsp = (s) => s.replace(/\s/g, "\xA0");
|
|
61
|
+
var pdDateEn = (ms, opts) => nbsp(new Intl.DateTimeFormat("en-GB", opts).format(new Date(ms)).replace("Sept", "Sep"));
|
|
62
|
+
var pdDateTr = (ms, opts) => nbsp(new Intl.DateTimeFormat("tr-TR", opts).format(new Date(ms)));
|
|
58
63
|
var STRINGS = {
|
|
59
64
|
en: {
|
|
60
65
|
launcherLabel: "Chat with SensibleStats",
|
|
@@ -157,7 +162,93 @@ var STRINGS = {
|
|
|
157
162
|
clubFixturesEmpty: "No fixtures yet.",
|
|
158
163
|
clubStandingsEmpty: "Standings are not available yet.",
|
|
159
164
|
clubSquadEmpty: "Squad is not available yet.",
|
|
165
|
+
footRight: "Right",
|
|
166
|
+
footLeft: "Left",
|
|
167
|
+
footBoth: "Both",
|
|
168
|
+
positionGoalkeeper: "Goalkeeper",
|
|
169
|
+
positionDefender: "Defender",
|
|
170
|
+
positionMidfielder: "Midfielder",
|
|
171
|
+
positionAttacker: "Attacker",
|
|
172
|
+
tabRecords: "Records",
|
|
173
|
+
clubSquadStatsEmpty: "Squad stats are not available yet.",
|
|
174
|
+
clubPlayerDetailEmpty: "Player details are not available.",
|
|
175
|
+
clubRecordsEmpty: "Club records are not available yet.",
|
|
176
|
+
squadViewRoster: "Roster",
|
|
177
|
+
squadViewStats: "Stats",
|
|
178
|
+
statColApps: "Apps",
|
|
179
|
+
statColGoals: "Goals",
|
|
180
|
+
statColAssists: "Assists",
|
|
181
|
+
statColRating: "Rating",
|
|
182
|
+
statColMinutes: "Minutes",
|
|
183
|
+
statColYellow: "Yellow cards",
|
|
184
|
+
statColRed: "Red cards",
|
|
185
|
+
statColXg: "xG",
|
|
186
|
+
statColShots: "Shots",
|
|
187
|
+
detailNationality: "Nationality",
|
|
188
|
+
detailAge: "Age",
|
|
189
|
+
detailHeight: "Height",
|
|
190
|
+
detailFoot: "Foot",
|
|
191
|
+
detailSeason: "Season {season}",
|
|
192
|
+
clubPlayerBack: "Back",
|
|
193
|
+
recordsTopScorers: "Top scorers",
|
|
194
|
+
recordsMostAppearances: "Most appearances",
|
|
195
|
+
recordsMostAssists: "Most assists",
|
|
196
|
+
recordsSince: "Since {season}",
|
|
160
197
|
standingsColClub: "Club",
|
|
198
|
+
statHeadPos: "Pos",
|
|
199
|
+
statHeadMins: "Mins",
|
|
200
|
+
statHeadGoals: "G",
|
|
201
|
+
statHeadAssists: "A",
|
|
202
|
+
statHeadYellow: "Y",
|
|
203
|
+
statHeadRed: "R",
|
|
204
|
+
statHeadRating: "Rtg",
|
|
205
|
+
squadStatsEyebrow: (season, competition, n) => `${season} ${competition} \xB7 after ${n} game${n === 1 ? "" : "s"}`,
|
|
206
|
+
squadTopScorer: (name, n) => `Top scorer: ${name} (${n})`,
|
|
207
|
+
squadTopAssists: (name, n) => `Most assists: ${name} (${n})`,
|
|
208
|
+
detailStarted: "Started",
|
|
209
|
+
detailMatches: "Matches",
|
|
210
|
+
detailNatShort: "Nat.",
|
|
211
|
+
detailYellows: "Yellows",
|
|
212
|
+
detailReds: "Reds",
|
|
213
|
+
availabilityNext: (opponent, isHome, kickoffMs) => `Next: ${isHome ? "vs" : "at"} ${opponent} (${isHome ? "H" : "A"})` + (kickoffMs !== null && kickoffMs > 0 ? ` \xB7 ${pdDateEn(kickoffMs, { weekday: "short", day: "numeric", month: "short" })}` : ""),
|
|
214
|
+
availabilityAvailable: "Available",
|
|
215
|
+
availabilityInjured: "Injured",
|
|
216
|
+
availabilitySuspended: "Suspended",
|
|
217
|
+
availabilityUnavailable: "Unavailable",
|
|
218
|
+
availabilityNoConcerns: "No fitness concerns reported",
|
|
219
|
+
availabilityBack: (ms) => `Expected back ${pdDateEn(ms, { day: "numeric", month: "short" })}`,
|
|
220
|
+
perfTitle: "Season performance",
|
|
221
|
+
perfTotal: "Total",
|
|
222
|
+
perfPer90: "Per 90",
|
|
223
|
+
perfRankedAgainst: (competition, group) => `Ranked against ${competition} ${GROUP_NOUN_EN[group] ?? group}`,
|
|
224
|
+
perfUnranked: "Not enough minutes to rank",
|
|
225
|
+
perfUnrankedCohort: "Not enough players in this position to rank",
|
|
226
|
+
perfUnrankedNoLeague: "Not ranked \u2014 no league data",
|
|
227
|
+
perfGroupShooting: "Shooting",
|
|
228
|
+
perfGroupPassing: "Passing",
|
|
229
|
+
perfGroupPossession: "Possession",
|
|
230
|
+
perfGroupDefending: "Defending",
|
|
231
|
+
perfMetric: {
|
|
232
|
+
goals: "Goals",
|
|
233
|
+
xg: "Expected goals (xG)",
|
|
234
|
+
shots: "Shots",
|
|
235
|
+
shotsOnTarget: "Shots on target",
|
|
236
|
+
assists: "Assists",
|
|
237
|
+
successfulPasses: "Successful passes",
|
|
238
|
+
passAccuracy: "Pass accuracy",
|
|
239
|
+
chancesCreated: "Chances created",
|
|
240
|
+
successfulDribbles: "Successful dribbles",
|
|
241
|
+
dribbleSuccess: "Dribble success",
|
|
242
|
+
touches: "Touches",
|
|
243
|
+
tacklesWon: "Tackles won",
|
|
244
|
+
interceptions: "Interceptions",
|
|
245
|
+
duelsWon: "Duels won"
|
|
246
|
+
},
|
|
247
|
+
perfGroupNoun: GROUP_NOUN_EN,
|
|
248
|
+
matchLogTitle: "Match log",
|
|
249
|
+
matchLogOpponent: (name, isHome) => isHome ? `vs ${name}` : `at ${name}`,
|
|
250
|
+
resultLetter: { W: "W", D: "D", L: "L" },
|
|
251
|
+
logShortDate: (ms) => pdDateEn(ms, { day: "numeric", month: "short" }),
|
|
161
252
|
standingsColPlayed: "P",
|
|
162
253
|
standingsColWon: "W",
|
|
163
254
|
standingsColDrawn: "D",
|
|
@@ -538,7 +629,93 @@ var STRINGS = {
|
|
|
538
629
|
clubFixturesEmpty: "Hen\xFCz fikst\xFCr yok.",
|
|
539
630
|
clubStandingsEmpty: "Puan durumu hen\xFCz mevcut de\u011Fil.",
|
|
540
631
|
clubSquadEmpty: "Kadro hen\xFCz mevcut de\u011Fil.",
|
|
632
|
+
footRight: "Sa\u011F",
|
|
633
|
+
footLeft: "Sol",
|
|
634
|
+
footBoth: "\u0130ki ayak",
|
|
635
|
+
positionGoalkeeper: "Kaleci",
|
|
636
|
+
positionDefender: "Defans",
|
|
637
|
+
positionMidfielder: "Orta saha",
|
|
638
|
+
positionAttacker: "Forvet",
|
|
639
|
+
tabRecords: "Rekorlar",
|
|
640
|
+
clubSquadStatsEmpty: "Kadro istatistikleri hen\xFCz mevcut de\u011Fil.",
|
|
641
|
+
clubPlayerDetailEmpty: "Oyuncu bilgileri mevcut de\u011Fil.",
|
|
642
|
+
clubRecordsEmpty: "Kul\xFCp rekorlar\u0131 hen\xFCz mevcut de\u011Fil.",
|
|
643
|
+
squadViewRoster: "Kadro",
|
|
644
|
+
squadViewStats: "\u0130statistik",
|
|
645
|
+
statColApps: "Ma\xE7",
|
|
646
|
+
statColGoals: "Gol",
|
|
647
|
+
statColAssists: "Asist",
|
|
648
|
+
statColRating: "Puan",
|
|
649
|
+
statColMinutes: "Dakika",
|
|
650
|
+
statColYellow: "Sar\u0131 kart",
|
|
651
|
+
statColRed: "K\u0131rm\u0131z\u0131 kart",
|
|
652
|
+
statColXg: "xG",
|
|
653
|
+
statColShots: "\u015Eut",
|
|
654
|
+
detailNationality: "Uyruk",
|
|
655
|
+
detailAge: "Ya\u015F",
|
|
656
|
+
detailHeight: "Boy",
|
|
657
|
+
detailFoot: "Ayak",
|
|
658
|
+
detailSeason: "{season} sezonu",
|
|
659
|
+
clubPlayerBack: "Geri",
|
|
660
|
+
recordsTopScorers: "En \xE7ok gol atanlar",
|
|
661
|
+
recordsMostAppearances: "En \xE7ok ma\xE7 yapanlar",
|
|
662
|
+
recordsMostAssists: "En \xE7ok asist yapanlar",
|
|
663
|
+
recordsSince: "{season} sezonundan beri",
|
|
541
664
|
standingsColClub: "Tak\u0131m",
|
|
665
|
+
statHeadPos: "Mvk",
|
|
666
|
+
statHeadMins: "Dk",
|
|
667
|
+
statHeadGoals: "G",
|
|
668
|
+
statHeadAssists: "A",
|
|
669
|
+
statHeadYellow: "S",
|
|
670
|
+
statHeadRed: "K",
|
|
671
|
+
statHeadRating: "Puan",
|
|
672
|
+
squadStatsEyebrow: (season, competition, n) => `${season} ${competition} \xB7 ${n} ma\xE7 sonra`,
|
|
673
|
+
squadTopScorer: (name, n) => `Gol kral\u0131: ${name} (${n})`,
|
|
674
|
+
squadTopAssists: (name, n) => `Asist lideri: ${name} (${n})`,
|
|
675
|
+
detailStarted: "\u0130lk 11",
|
|
676
|
+
detailMatches: "Ma\xE7",
|
|
677
|
+
detailNatShort: "Uyruk",
|
|
678
|
+
detailYellows: "Sar\u0131",
|
|
679
|
+
detailReds: "K\u0131rm\u0131z\u0131",
|
|
680
|
+
availabilityNext: (opponent, isHome, kickoffMs) => `Sonraki: ${opponent} (${isHome ? "\u0130\xE7\xA0saha" : "Deplasman"})` + (kickoffMs !== null && kickoffMs > 0 ? ` \xB7 ${pdDateTr(kickoffMs, { day: "numeric", month: "short", weekday: "short" })}` : ""),
|
|
681
|
+
availabilityAvailable: "Haz\u0131r",
|
|
682
|
+
availabilityInjured: "Sakat",
|
|
683
|
+
availabilitySuspended: "Cezal\u0131",
|
|
684
|
+
availabilityUnavailable: "Haz\u0131r de\u011Fil",
|
|
685
|
+
availabilityNoConcerns: "Sakatl\u0131k bildirimi yok",
|
|
686
|
+
availabilityBack: (ms) => `D\xF6n\xFC\u015F: ${pdDateTr(ms, { day: "numeric", month: "short" })}`,
|
|
687
|
+
perfTitle: "Sezon performans\u0131",
|
|
688
|
+
perfTotal: "Toplam",
|
|
689
|
+
perfPer90: "90 dk",
|
|
690
|
+
perfRankedAgainst: (competition, group) => `${competition} ${GROUP_NOUN_TR[group] ?? group} aras\u0131nda`,
|
|
691
|
+
perfUnranked: "S\u0131ralama i\xE7in yeterli s\xFCre yok",
|
|
692
|
+
perfUnrankedCohort: "Bu mevkide s\u0131ralama i\xE7in yeterli oyuncu yok",
|
|
693
|
+
perfUnrankedNoLeague: "S\u0131ralanmad\u0131 \u2014 lig verisi yok",
|
|
694
|
+
perfGroupShooting: "\u015Eut",
|
|
695
|
+
perfGroupPassing: "Pas",
|
|
696
|
+
perfGroupPossession: "Top hakimiyeti",
|
|
697
|
+
perfGroupDefending: "Savunma",
|
|
698
|
+
perfMetric: {
|
|
699
|
+
goals: "Gol",
|
|
700
|
+
xg: "Gol beklentisi (xG)",
|
|
701
|
+
shots: "\u015Eut",
|
|
702
|
+
shotsOnTarget: "\u0130sabetli \u015Fut",
|
|
703
|
+
assists: "Asist",
|
|
704
|
+
successfulPasses: "Ba\u015Far\u0131l\u0131 pas",
|
|
705
|
+
passAccuracy: "Pas isabeti",
|
|
706
|
+
chancesCreated: "Yarat\u0131lan f\u0131rsat",
|
|
707
|
+
successfulDribbles: "Ba\u015Far\u0131l\u0131 \xE7al\u0131m",
|
|
708
|
+
dribbleSuccess: "\xC7al\u0131m ba\u015Far\u0131s\u0131",
|
|
709
|
+
touches: "Topla bulu\u015Fma",
|
|
710
|
+
tacklesWon: "Kazan\u0131lan m\xFCdahale",
|
|
711
|
+
interceptions: "Top kapma",
|
|
712
|
+
duelsWon: "Kazan\u0131lan ikili m\xFCcadele"
|
|
713
|
+
},
|
|
714
|
+
perfGroupNoun: GROUP_NOUN_TR,
|
|
715
|
+
matchLogTitle: "Ma\xE7 ge\xE7mi\u015Fi",
|
|
716
|
+
matchLogOpponent: (name, isHome) => isHome ? `${name} (\u0130)` : `${name} (D)`,
|
|
717
|
+
resultLetter: { W: "G", D: "B", L: "M" },
|
|
718
|
+
logShortDate: (ms) => pdDateTr(ms, { day: "numeric", month: "short" }),
|
|
542
719
|
standingsColPlayed: "O",
|
|
543
720
|
standingsColWon: "G",
|
|
544
721
|
standingsColDrawn: "B",
|
|
@@ -916,7 +1093,78 @@ function normalizeUi(cfg) {
|
|
|
916
1093
|
clubFixturesEmpty: strings.clubFixturesEmpty,
|
|
917
1094
|
clubStandingsEmpty: strings.clubStandingsEmpty,
|
|
918
1095
|
clubSquadEmpty: strings.clubSquadEmpty,
|
|
1096
|
+
footRight: strings.footRight,
|
|
1097
|
+
footLeft: strings.footLeft,
|
|
1098
|
+
footBoth: strings.footBoth,
|
|
1099
|
+
positionGoalkeeper: strings.positionGoalkeeper,
|
|
1100
|
+
positionDefender: strings.positionDefender,
|
|
1101
|
+
positionMidfielder: strings.positionMidfielder,
|
|
1102
|
+
positionAttacker: strings.positionAttacker,
|
|
1103
|
+
tabRecords: strings.tabRecords,
|
|
1104
|
+
clubSquadStatsEmpty: strings.clubSquadStatsEmpty,
|
|
1105
|
+
clubPlayerDetailEmpty: strings.clubPlayerDetailEmpty,
|
|
1106
|
+
clubRecordsEmpty: strings.clubRecordsEmpty,
|
|
1107
|
+
squadViewRoster: strings.squadViewRoster,
|
|
1108
|
+
squadViewStats: strings.squadViewStats,
|
|
1109
|
+
statColApps: strings.statColApps,
|
|
1110
|
+
statColGoals: strings.statColGoals,
|
|
1111
|
+
statColAssists: strings.statColAssists,
|
|
1112
|
+
statColRating: strings.statColRating,
|
|
1113
|
+
statColMinutes: strings.statColMinutes,
|
|
1114
|
+
statColYellow: strings.statColYellow,
|
|
1115
|
+
statColRed: strings.statColRed,
|
|
1116
|
+
statColXg: strings.statColXg,
|
|
1117
|
+
statColShots: strings.statColShots,
|
|
1118
|
+
detailNationality: strings.detailNationality,
|
|
1119
|
+
detailAge: strings.detailAge,
|
|
1120
|
+
detailHeight: strings.detailHeight,
|
|
1121
|
+
detailFoot: strings.detailFoot,
|
|
1122
|
+
detailSeason: strings.detailSeason,
|
|
1123
|
+
clubPlayerBack: strings.clubPlayerBack,
|
|
1124
|
+
recordsTopScorers: strings.recordsTopScorers,
|
|
1125
|
+
recordsMostAppearances: strings.recordsMostAppearances,
|
|
1126
|
+
recordsMostAssists: strings.recordsMostAssists,
|
|
1127
|
+
recordsSince: strings.recordsSince,
|
|
919
1128
|
standingsColClub: strings.standingsColClub,
|
|
1129
|
+
statHeadPos: strings.statHeadPos,
|
|
1130
|
+
statHeadMins: strings.statHeadMins,
|
|
1131
|
+
statHeadGoals: strings.statHeadGoals,
|
|
1132
|
+
statHeadAssists: strings.statHeadAssists,
|
|
1133
|
+
statHeadYellow: strings.statHeadYellow,
|
|
1134
|
+
statHeadRed: strings.statHeadRed,
|
|
1135
|
+
statHeadRating: strings.statHeadRating,
|
|
1136
|
+
squadStatsEyebrow: strings.squadStatsEyebrow,
|
|
1137
|
+
squadTopScorer: strings.squadTopScorer,
|
|
1138
|
+
squadTopAssists: strings.squadTopAssists,
|
|
1139
|
+
detailStarted: strings.detailStarted,
|
|
1140
|
+
detailMatches: strings.detailMatches,
|
|
1141
|
+
detailNatShort: strings.detailNatShort,
|
|
1142
|
+
detailYellows: strings.detailYellows,
|
|
1143
|
+
detailReds: strings.detailReds,
|
|
1144
|
+
availabilityNext: strings.availabilityNext,
|
|
1145
|
+
availabilityAvailable: strings.availabilityAvailable,
|
|
1146
|
+
availabilityInjured: strings.availabilityInjured,
|
|
1147
|
+
availabilitySuspended: strings.availabilitySuspended,
|
|
1148
|
+
availabilityUnavailable: strings.availabilityUnavailable,
|
|
1149
|
+
availabilityNoConcerns: strings.availabilityNoConcerns,
|
|
1150
|
+
availabilityBack: strings.availabilityBack,
|
|
1151
|
+
perfTitle: strings.perfTitle,
|
|
1152
|
+
perfTotal: strings.perfTotal,
|
|
1153
|
+
perfPer90: strings.perfPer90,
|
|
1154
|
+
perfRankedAgainst: strings.perfRankedAgainst,
|
|
1155
|
+
perfUnranked: strings.perfUnranked,
|
|
1156
|
+
perfUnrankedCohort: strings.perfUnrankedCohort,
|
|
1157
|
+
perfUnrankedNoLeague: strings.perfUnrankedNoLeague,
|
|
1158
|
+
perfGroupShooting: strings.perfGroupShooting,
|
|
1159
|
+
perfGroupPassing: strings.perfGroupPassing,
|
|
1160
|
+
perfGroupPossession: strings.perfGroupPossession,
|
|
1161
|
+
perfGroupDefending: strings.perfGroupDefending,
|
|
1162
|
+
perfMetric: strings.perfMetric,
|
|
1163
|
+
perfGroupNoun: strings.perfGroupNoun,
|
|
1164
|
+
matchLogTitle: strings.matchLogTitle,
|
|
1165
|
+
matchLogOpponent: strings.matchLogOpponent,
|
|
1166
|
+
resultLetter: strings.resultLetter,
|
|
1167
|
+
logShortDate: strings.logShortDate,
|
|
920
1168
|
standingsColPlayed: strings.standingsColPlayed,
|
|
921
1169
|
standingsColWon: strings.standingsColWon,
|
|
922
1170
|
standingsColDrawn: strings.standingsColDrawn,
|
|
@@ -3281,8 +3529,87 @@ function useClubSquad(conversation, { activeTab, enabled }) {
|
|
|
3281
3529
|
return { data, loading: effectiveLoading, refresh };
|
|
3282
3530
|
}
|
|
3283
3531
|
|
|
3284
|
-
// src/
|
|
3532
|
+
// src/useClubSquadStats.ts
|
|
3285
3533
|
var import_react12 = require("react");
|
|
3534
|
+
function useClubSquadStats(conversation, { activeTab, enabled }) {
|
|
3535
|
+
const [data, setData] = (0, import_react12.useState)(null);
|
|
3536
|
+
const [seasonName, setSeasonName] = (0, import_react12.useState)(null);
|
|
3537
|
+
const [competitionName, setCompetitionName] = (0, import_react12.useState)(null);
|
|
3538
|
+
const [matchesPlayed, setMatchesPlayed] = (0, import_react12.useState)(null);
|
|
3539
|
+
const [loading, setLoading] = (0, import_react12.useState)(false);
|
|
3540
|
+
const [refreshCount, setRefreshCount] = (0, import_react12.useState)(0);
|
|
3541
|
+
const inFlightRef = (0, import_react12.useRef)(false);
|
|
3542
|
+
const conversationRef = (0, import_react12.useRef)(conversation);
|
|
3543
|
+
conversationRef.current = conversation;
|
|
3544
|
+
(0, import_react12.useEffect)(() => {
|
|
3545
|
+
if (activeTab !== "squad" || !enabled) return;
|
|
3546
|
+
let active = true;
|
|
3547
|
+
const doFetch = async () => {
|
|
3548
|
+
const conv = conversationRef.current;
|
|
3549
|
+
if (!conv || inFlightRef.current) return;
|
|
3550
|
+
inFlightRef.current = true;
|
|
3551
|
+
setLoading(true);
|
|
3552
|
+
try {
|
|
3553
|
+
const result = await conv.getClubSquadStats();
|
|
3554
|
+
if (active) {
|
|
3555
|
+
setData(result?.players ?? null);
|
|
3556
|
+
setSeasonName(result?.seasonName ?? null);
|
|
3557
|
+
setCompetitionName(result?.competitionName ?? null);
|
|
3558
|
+
setMatchesPlayed(result?.clubMatchesPlayed ?? null);
|
|
3559
|
+
}
|
|
3560
|
+
} catch {
|
|
3561
|
+
} finally {
|
|
3562
|
+
inFlightRef.current = false;
|
|
3563
|
+
if (active) setLoading(false);
|
|
3564
|
+
}
|
|
3565
|
+
};
|
|
3566
|
+
void doFetch();
|
|
3567
|
+
return () => {
|
|
3568
|
+
active = false;
|
|
3569
|
+
inFlightRef.current = false;
|
|
3570
|
+
};
|
|
3571
|
+
}, [activeTab, enabled, refreshCount]);
|
|
3572
|
+
const refresh = (0, import_react12.useCallback)(() => {
|
|
3573
|
+
setRefreshCount((c) => c + 1);
|
|
3574
|
+
}, []);
|
|
3575
|
+
const effectiveLoading = loading || activeTab === "squad" && enabled && data === null;
|
|
3576
|
+
return { data, seasonName, competitionName, matchesPlayed, loading: effectiveLoading, refresh };
|
|
3577
|
+
}
|
|
3578
|
+
|
|
3579
|
+
// src/useClubPlayerDetail.ts
|
|
3580
|
+
var import_react13 = require("react");
|
|
3581
|
+
function useClubPlayerDetail(conversation) {
|
|
3582
|
+
const [data, setData] = (0, import_react13.useState)(null);
|
|
3583
|
+
const [loading, setLoading] = (0, import_react13.useState)(false);
|
|
3584
|
+
const requestSeqRef = (0, import_react13.useRef)(0);
|
|
3585
|
+
const conversationRef = (0, import_react13.useRef)(conversation);
|
|
3586
|
+
conversationRef.current = conversation;
|
|
3587
|
+
const fetch = (0, import_react13.useCallback)((playerId) => {
|
|
3588
|
+
const conv = conversationRef.current;
|
|
3589
|
+
if (!conv) return;
|
|
3590
|
+
const seq = ++requestSeqRef.current;
|
|
3591
|
+
setData(null);
|
|
3592
|
+
setLoading(true);
|
|
3593
|
+
void (async () => {
|
|
3594
|
+
try {
|
|
3595
|
+
const result = await conv.getClubPlayerDetail(playerId);
|
|
3596
|
+
if (seq === requestSeqRef.current) setData(result);
|
|
3597
|
+
} catch {
|
|
3598
|
+
} finally {
|
|
3599
|
+
if (seq === requestSeqRef.current) setLoading(false);
|
|
3600
|
+
}
|
|
3601
|
+
})();
|
|
3602
|
+
}, []);
|
|
3603
|
+
const clear = (0, import_react13.useCallback)(() => {
|
|
3604
|
+
requestSeqRef.current++;
|
|
3605
|
+
setData(null);
|
|
3606
|
+
setLoading(false);
|
|
3607
|
+
}, []);
|
|
3608
|
+
return { data, loading, fetch, clear };
|
|
3609
|
+
}
|
|
3610
|
+
|
|
3611
|
+
// src/usePresetGrid.ts
|
|
3612
|
+
var import_react14 = require("react");
|
|
3286
3613
|
|
|
3287
3614
|
// src/presetGrid.ts
|
|
3288
3615
|
var DEFAULT_SINGLES_LIMITS = [1.3, 1.5, 1.7, 2];
|
|
@@ -3425,22 +3752,22 @@ function marketDisplay(cell, s) {
|
|
|
3425
3752
|
// src/usePresetGrid.ts
|
|
3426
3753
|
var GRID_MAX_AGE_MS = 6e5;
|
|
3427
3754
|
function usePresetGrid({ getPricePresets, isOpen, locale, now = Date.now }) {
|
|
3428
|
-
const [grid, setGrid] = (0,
|
|
3429
|
-
const keptRef = (0,
|
|
3430
|
-
const localeRef = (0,
|
|
3431
|
-
const inFlightRef = (0,
|
|
3432
|
-
const mountedRef = (0,
|
|
3433
|
-
const getRef = (0,
|
|
3755
|
+
const [grid, setGrid] = (0, import_react14.useState)(null);
|
|
3756
|
+
const keptRef = (0, import_react14.useRef)(null);
|
|
3757
|
+
const localeRef = (0, import_react14.useRef)(locale);
|
|
3758
|
+
const inFlightRef = (0, import_react14.useRef)(false);
|
|
3759
|
+
const mountedRef = (0, import_react14.useRef)(true);
|
|
3760
|
+
const getRef = (0, import_react14.useRef)(getPricePresets);
|
|
3434
3761
|
getRef.current = getPricePresets;
|
|
3435
|
-
const nowRef = (0,
|
|
3762
|
+
const nowRef = (0, import_react14.useRef)(now);
|
|
3436
3763
|
nowRef.current = now;
|
|
3437
|
-
(0,
|
|
3764
|
+
(0, import_react14.useEffect)(() => {
|
|
3438
3765
|
mountedRef.current = true;
|
|
3439
3766
|
return () => {
|
|
3440
3767
|
mountedRef.current = false;
|
|
3441
3768
|
};
|
|
3442
3769
|
}, []);
|
|
3443
|
-
(0,
|
|
3770
|
+
(0, import_react14.useEffect)(() => {
|
|
3444
3771
|
if (localeRef.current !== locale) {
|
|
3445
3772
|
localeRef.current = locale;
|
|
3446
3773
|
keptRef.current = null;
|
|
@@ -3483,18 +3810,18 @@ function visibleGroupsOf(groups, states) {
|
|
|
3483
3810
|
}
|
|
3484
3811
|
|
|
3485
3812
|
// src/eventLogContext.ts
|
|
3486
|
-
var
|
|
3487
|
-
var EventLogContext = (0,
|
|
3813
|
+
var import_react15 = require("react");
|
|
3814
|
+
var EventLogContext = (0, import_react15.createContext)(null);
|
|
3488
3815
|
function useEventLog() {
|
|
3489
|
-
return (0,
|
|
3816
|
+
return (0, import_react15.useContext)(EventLogContext);
|
|
3490
3817
|
}
|
|
3491
3818
|
|
|
3492
3819
|
// src/popupTelemetry.ts
|
|
3493
|
-
var
|
|
3820
|
+
var import_react16 = require("react");
|
|
3494
3821
|
function usePopupTelemetry(log, isOpen, popupText, dismissPopup) {
|
|
3495
|
-
const shownRef = (0,
|
|
3496
|
-
const closedTextRef = (0,
|
|
3497
|
-
(0,
|
|
3822
|
+
const shownRef = (0, import_react16.useRef)(/* @__PURE__ */ new Set());
|
|
3823
|
+
const closedTextRef = (0, import_react16.useRef)(null);
|
|
3824
|
+
(0, import_react16.useEffect)(() => {
|
|
3498
3825
|
if (isOpen) {
|
|
3499
3826
|
if (closedTextRef.current) log?.log({ name: "popup_opened" });
|
|
3500
3827
|
closedTextRef.current = null;
|
|
@@ -3506,17 +3833,17 @@ function usePopupTelemetry(log, isOpen, popupText, dismissPopup) {
|
|
|
3506
3833
|
log?.log({ name: "popup_shown" });
|
|
3507
3834
|
}
|
|
3508
3835
|
}, [log, isOpen, popupText]);
|
|
3509
|
-
return (0,
|
|
3836
|
+
return (0, import_react16.useCallback)(() => {
|
|
3510
3837
|
log?.log({ name: "popup_dismissed" });
|
|
3511
3838
|
dismissPopup();
|
|
3512
3839
|
}, [log, dismissPopup]);
|
|
3513
3840
|
}
|
|
3514
3841
|
|
|
3515
3842
|
// src/openTelemetry.ts
|
|
3516
|
-
var
|
|
3843
|
+
var import_react17 = require("react");
|
|
3517
3844
|
function useOpenTelemetry(log, isOpen) {
|
|
3518
|
-
const openLoggedRef = (0,
|
|
3519
|
-
(0,
|
|
3845
|
+
const openLoggedRef = (0, import_react17.useRef)(false);
|
|
3846
|
+
(0, import_react17.useEffect)(() => {
|
|
3520
3847
|
if (!isOpen) {
|
|
3521
3848
|
openLoggedRef.current = false;
|
|
3522
3849
|
return;
|
|
@@ -3528,10 +3855,10 @@ function useOpenTelemetry(log, isOpen) {
|
|
|
3528
3855
|
}
|
|
3529
3856
|
|
|
3530
3857
|
// src/components/ChatFab.tsx
|
|
3531
|
-
var
|
|
3858
|
+
var import_react19 = require("react");
|
|
3532
3859
|
|
|
3533
3860
|
// src/components/BrandMark.tsx
|
|
3534
|
-
var
|
|
3861
|
+
var import_react18 = require("react");
|
|
3535
3862
|
|
|
3536
3863
|
// src/assets/logo.ts
|
|
3537
3864
|
var SS_LOGO_DATA_URI = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAjoAAAI6CAYAAAAuSOLAAAAAAXNSR0IArs4c6QAAAJplWElmTU0AKgAAAAgAAwESAAMAAAABAAEAAAExAAIAAAA9AAAAModpAAQAAAABAAAAcAAAAABBZG9iZSBQaG90b3Nob3AgMjYuMTAgKDIwMjUwNzMwLm0uMzE2NiAwN2IxMjM0KSAgKE1hY2ludG9zaCkAAAADoAEAAwAAAAEAAQAAoAIABAAAAAEAAAI6oAMABAAAAAEAAAI6AAAAACwGtVwAAAQwaVRYdFhNTDpjb20uYWRvYmUueG1wAAAAAAA8eDp4bXBtZXRhIHhtbG5zOng9ImFkb2JlOm5zOm1ldGEvIiB4OnhtcHRrPSJYTVAgQ29yZSA2LjAuMCI+CiAgIDxyZGY6UkRGIHhtbG5zOnJkZj0iaHR0cDovL3d3dy53My5vcmcvMTk5OS8wMi8yMi1yZGYtc3ludGF4LW5zIyI+CiAgICAgIDxyZGY6RGVzY3JpcHRpb24gcmRmOmFib3V0PSIiCiAgICAgICAgICAgIHhtbG5zOnhtcE1NPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvbW0vIgogICAgICAgICAgICB4bWxuczpzdFJlZj0iaHR0cDovL25zLmFkb2JlLmNvbS94YXAvMS4wL3NUeXBlL1Jlc291cmNlUmVmIyIKICAgICAgICAgICAgeG1sbnM6eG1wPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvIgogICAgICAgICAgICB4bWxuczp0aWZmPSJodHRwOi8vbnMuYWRvYmUuY29tL3RpZmYvMS4wLyI+CiAgICAgICAgIDx4bXBNTTpEb2N1bWVudElEPnhtcC5kaWQ6QzBGRTM5NjM5NEJEMTFGMEJGNjZEMjUyN0U0MzU5RUM8L3htcE1NOkRvY3VtZW50SUQ+CiAgICAgICAgIDx4bXBNTTpJbnN0YW5jZUlEPnhtcC5paWQ6QzBGRTM5NjI5NEJEMTFGMEJGNjZEMjUyN0U0MzU5RUM8L3htcE1NOkluc3RhbmNlSUQ+CiAgICAgICAgIDx4bXBNTTpEZXJpdmVkRnJvbSByZGY6cGFyc2VUeXBlPSJSZXNvdXJjZSI+CiAgICAgICAgICAgIDxzdFJlZjppbnN0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";
|
|
@@ -3594,7 +3921,7 @@ function DashboardIcon({ name }) {
|
|
|
3594
3921
|
// src/components/BrandMark.tsx
|
|
3595
3922
|
var import_jsx_runtime2 = require("react/jsx-runtime");
|
|
3596
3923
|
function BrandMark({ logoUrl, className }) {
|
|
3597
|
-
const [failed, setFailed] = (0,
|
|
3924
|
+
const [failed, setFailed] = (0, import_react18.useState)(false);
|
|
3598
3925
|
if (!logoUrl || failed) return /* @__PURE__ */ (0, import_jsx_runtime2.jsx)(SsMark, { className });
|
|
3599
3926
|
return /* @__PURE__ */ (0, import_jsx_runtime2.jsx)("img", { className, src: logoUrl, alt: "", "aria-hidden": "true", onError: () => setFailed(true) });
|
|
3600
3927
|
}
|
|
@@ -3630,9 +3957,9 @@ function GreetingBubble({ text, onOpen, onDismiss, dismissLabel = "Dismiss", ask
|
|
|
3630
3957
|
var import_jsx_runtime4 = require("react/jsx-runtime");
|
|
3631
3958
|
function ChatFab({ label, greeting, popupText, logoUrl, onOpen, onDismissPopup, dismissLabel = "Dismiss", introAllowed = false, onIntroStart, asks }) {
|
|
3632
3959
|
const bubble = popupText ?? greeting;
|
|
3633
|
-
const [intro, setIntro] = (0,
|
|
3634
|
-
const armedRef = (0,
|
|
3635
|
-
(0,
|
|
3960
|
+
const [intro, setIntro] = (0, import_react19.useState)(false);
|
|
3961
|
+
const armedRef = (0, import_react19.useRef)(introAllowed);
|
|
3962
|
+
(0, import_react19.useEffect)(() => {
|
|
3636
3963
|
if (armedRef.current && bubble) {
|
|
3637
3964
|
armedRef.current = false;
|
|
3638
3965
|
setIntro(true);
|
|
@@ -3646,10 +3973,10 @@ function ChatFab({ label, greeting, popupText, logoUrl, onOpen, onDismissPopup,
|
|
|
3646
3973
|
}
|
|
3647
3974
|
|
|
3648
3975
|
// src/components/ChatPanel.tsx
|
|
3649
|
-
var
|
|
3976
|
+
var import_react68 = require("react");
|
|
3650
3977
|
|
|
3651
3978
|
// src/components/ChatHeader.tsx
|
|
3652
|
-
var
|
|
3979
|
+
var import_react20 = require("react");
|
|
3653
3980
|
var import_jsx_runtime5 = require("react/jsx-runtime");
|
|
3654
3981
|
function ChatHeader({
|
|
3655
3982
|
onClose,
|
|
@@ -3661,15 +3988,15 @@ function ChatHeader({
|
|
|
3661
3988
|
newConversationLabel = "New conversation",
|
|
3662
3989
|
moreOptionsLabel = "More options"
|
|
3663
3990
|
}) {
|
|
3664
|
-
const [menuOpen, setMenuOpen] = (0,
|
|
3665
|
-
const wrapRef = (0,
|
|
3666
|
-
const kebabRef = (0,
|
|
3667
|
-
const firstItemRef = (0,
|
|
3991
|
+
const [menuOpen, setMenuOpen] = (0, import_react20.useState)(false);
|
|
3992
|
+
const wrapRef = (0, import_react20.useRef)(null);
|
|
3993
|
+
const kebabRef = (0, import_react20.useRef)(null);
|
|
3994
|
+
const firstItemRef = (0, import_react20.useRef)(null);
|
|
3668
3995
|
const hasMenu = !!(canReset && onNewConversation);
|
|
3669
|
-
(0,
|
|
3996
|
+
(0, import_react20.useEffect)(() => {
|
|
3670
3997
|
if (menuOpen) firstItemRef.current?.focus();
|
|
3671
3998
|
}, [menuOpen]);
|
|
3672
|
-
(0,
|
|
3999
|
+
(0, import_react20.useEffect)(() => {
|
|
3673
4000
|
if (!menuOpen) return;
|
|
3674
4001
|
const onPointer = (e) => {
|
|
3675
4002
|
if (!wrapRef.current?.contains(e.target)) setMenuOpen(false);
|
|
@@ -3725,7 +4052,7 @@ function ChatHeader({
|
|
|
3725
4052
|
}
|
|
3726
4053
|
|
|
3727
4054
|
// src/components/MessageList.tsx
|
|
3728
|
-
var
|
|
4055
|
+
var import_react40 = require("react");
|
|
3729
4056
|
|
|
3730
4057
|
// src/components/Markdown.tsx
|
|
3731
4058
|
var import_react_markdown = __toESM(require("react-markdown"), 1);
|
|
@@ -3743,7 +4070,7 @@ function Markdown({ text }) {
|
|
|
3743
4070
|
}
|
|
3744
4071
|
|
|
3745
4072
|
// src/components/EntityCardList.tsx
|
|
3746
|
-
var
|
|
4073
|
+
var import_react21 = require("react");
|
|
3747
4074
|
var import_jsx_runtime7 = require("react/jsx-runtime");
|
|
3748
4075
|
var MAX_VISIBLE = 3;
|
|
3749
4076
|
var RECORD_RE = /^(\d+)-(\d+)-(\d+)$/;
|
|
@@ -3827,7 +4154,7 @@ function ScopeTabs({ scopes, active, onSelect }) {
|
|
|
3827
4154
|
)) });
|
|
3828
4155
|
}
|
|
3829
4156
|
function EntityCardItem({ c }) {
|
|
3830
|
-
const [active, setActive] = (0,
|
|
4157
|
+
const [active, setActive] = (0, import_react21.useState)(0);
|
|
3831
4158
|
const hasBody = c.scopes.length > 0;
|
|
3832
4159
|
if (!hasBody) {
|
|
3833
4160
|
return /* @__PURE__ */ (0, import_jsx_runtime7.jsx)("div", { className: "ss-w-ecard ss-w-ecard-bare", "data-kind": c.kind, children: /* @__PURE__ */ (0, import_jsx_runtime7.jsx)(CardHeader, { c, showScopeCrest: false }) });
|
|
@@ -3841,7 +4168,7 @@ function EntityCardItem({ c }) {
|
|
|
3841
4168
|
] });
|
|
3842
4169
|
}
|
|
3843
4170
|
function EntityCardList({ cards, disabled, showLessLabel = "Show less", showMoreLabel = (n) => `Show ${n} more` }) {
|
|
3844
|
-
const [expanded, setExpanded] = (0,
|
|
4171
|
+
const [expanded, setExpanded] = (0, import_react21.useState)(false);
|
|
3845
4172
|
if (cards.length === 0) return null;
|
|
3846
4173
|
const visible = expanded ? cards : cards.slice(0, MAX_VISIBLE);
|
|
3847
4174
|
const overflow = cards.length - MAX_VISIBLE;
|
|
@@ -3852,17 +4179,17 @@ function EntityCardList({ cards, disabled, showLessLabel = "Show less", showMore
|
|
|
3852
4179
|
}
|
|
3853
4180
|
|
|
3854
4181
|
// src/components/AddToSlipButton.tsx
|
|
3855
|
-
var
|
|
4182
|
+
var import_react25 = require("react");
|
|
3856
4183
|
|
|
3857
4184
|
// src/slipAdd.ts
|
|
3858
|
-
var
|
|
4185
|
+
var import_react23 = require("react");
|
|
3859
4186
|
var import_widget_sdk5 = require("@sensiblestats/widget-sdk");
|
|
3860
4187
|
|
|
3861
4188
|
// src/slipStateContext.ts
|
|
3862
|
-
var
|
|
3863
|
-
var SlipStateContext = (0,
|
|
4189
|
+
var import_react22 = require("react");
|
|
4190
|
+
var SlipStateContext = (0, import_react22.createContext)(null);
|
|
3864
4191
|
function useSlipState() {
|
|
3865
|
-
return (0,
|
|
4192
|
+
return (0, import_react22.useContext)(SlipStateContext);
|
|
3866
4193
|
}
|
|
3867
4194
|
|
|
3868
4195
|
// src/slipAdd.ts
|
|
@@ -3877,7 +4204,7 @@ function useSlipAdd(slip, ui) {
|
|
|
3877
4204
|
const slipState = useSlipState();
|
|
3878
4205
|
const handler = slip.onAddToSlip;
|
|
3879
4206
|
const rawLabels = !!ui?.rawBettingLabels;
|
|
3880
|
-
return (0,
|
|
4207
|
+
return (0, import_react23.useCallback)(async (selection, { marketDeveloperName, selectionLabel, line }) => {
|
|
3881
4208
|
if (!handler) return { kind: "failed" };
|
|
3882
4209
|
const pick = slipPickFields(selection, rawLabels ? selectionLabel : void 0, line);
|
|
3883
4210
|
if (marketDeveloperName !== void 0) {
|
|
@@ -3914,11 +4241,11 @@ function useSlipAdd(slip, ui) {
|
|
|
3914
4241
|
}
|
|
3915
4242
|
|
|
3916
4243
|
// src/components/Toast.tsx
|
|
3917
|
-
var
|
|
4244
|
+
var import_react24 = require("react");
|
|
3918
4245
|
var import_jsx_runtime8 = require("react/jsx-runtime");
|
|
3919
4246
|
var DISMISS_MS = 4e3;
|
|
3920
4247
|
function Toast({ toast, onDismiss }) {
|
|
3921
|
-
(0,
|
|
4248
|
+
(0, import_react24.useEffect)(() => {
|
|
3922
4249
|
if (!toast) return;
|
|
3923
4250
|
const timer = setTimeout(onDismiss, DISMISS_MS);
|
|
3924
4251
|
return () => clearTimeout(timer);
|
|
@@ -3930,10 +4257,10 @@ function Toast({ toast, onDismiss }) {
|
|
|
3930
4257
|
// src/components/AddToSlipButton.tsx
|
|
3931
4258
|
var import_jsx_runtime9 = require("react/jsx-runtime");
|
|
3932
4259
|
function SlipButton({ selection, shownOdds, marketDeveloperName, selectionLabel, line, slip, ui, price, ariaLabel }) {
|
|
3933
|
-
const [pending, setPending] = (0,
|
|
3934
|
-
const [settledLocal, setSettledLocal] = (0,
|
|
3935
|
-
const [toast, setToast] = (0,
|
|
3936
|
-
const dismiss = (0,
|
|
4260
|
+
const [pending, setPending] = (0, import_react25.useState)(false);
|
|
4261
|
+
const [settledLocal, setSettledLocal] = (0, import_react25.useState)(false);
|
|
4262
|
+
const [toast, setToast] = (0, import_react25.useState)(null);
|
|
4263
|
+
const dismiss = (0, import_react25.useCallback)(() => setToast(null), []);
|
|
3937
4264
|
const add = useSlipAdd(slip, ui);
|
|
3938
4265
|
const slipState = useSlipState();
|
|
3939
4266
|
const handler = slip.onAddToSlip;
|
|
@@ -4021,14 +4348,14 @@ function OddsMovementBadge({
|
|
|
4021
4348
|
}
|
|
4022
4349
|
|
|
4023
4350
|
// src/components/Crest.tsx
|
|
4024
|
-
var
|
|
4351
|
+
var import_react26 = require("react");
|
|
4025
4352
|
var import_jsx_runtime11 = require("react/jsx-runtime");
|
|
4026
4353
|
function initials2(name) {
|
|
4027
4354
|
return (name ?? "").trim().slice(0, 1).toUpperCase() || "?";
|
|
4028
4355
|
}
|
|
4029
4356
|
function Crest2({ url, name, kind }) {
|
|
4030
4357
|
const cls = kind === "comp" ? "ss-w-bi-comp-logo" : "ss-w-bi-crest";
|
|
4031
|
-
const [failed, setFailed] = (0,
|
|
4358
|
+
const [failed, setFailed] = (0, import_react26.useState)(false);
|
|
4032
4359
|
if (url && !failed) {
|
|
4033
4360
|
return /* @__PURE__ */ (0, import_jsx_runtime11.jsx)("img", { className: cls, src: url, alt: "", "aria-hidden": "true", onError: () => setFailed(true) });
|
|
4034
4361
|
}
|
|
@@ -4036,7 +4363,7 @@ function Crest2({ url, name, kind }) {
|
|
|
4036
4363
|
}
|
|
4037
4364
|
|
|
4038
4365
|
// src/components/PinToggle.tsx
|
|
4039
|
-
var
|
|
4366
|
+
var import_react27 = require("react");
|
|
4040
4367
|
var import_jsx_runtime12 = require("react/jsx-runtime");
|
|
4041
4368
|
var PIN_GLYPHS = {
|
|
4042
4369
|
pin: { viewBox: "0 0 24 24", strokeWidth: 1.4, transform: "scale(1.5)", d: "M9.5 1.5 14.5 6.5 13 8l-.5-.5-3 3 .3 2.2-1.4 1.4L5.6 11.3l-3.3 3.3-1-1 3.3-3.3L1.9 7.5l1.4-1.4 2.2.3 3-3L8 2.9z" },
|
|
@@ -4044,8 +4371,8 @@ var PIN_GLYPHS = {
|
|
|
4044
4371
|
bookmark: { viewBox: "0 0 24 24", strokeWidth: 2, d: "M7 3h10a1.5 1.5 0 0 1 1.5 1.5V21l-6.5-3.6L5.5 21V4.5A1.5 1.5 0 0 1 7 3z" }
|
|
4045
4372
|
};
|
|
4046
4373
|
function PinToggle({ pin, monitor, ui, market }) {
|
|
4047
|
-
const [toast, setToast] = (0,
|
|
4048
|
-
const dismiss = (0,
|
|
4374
|
+
const [toast, setToast] = (0, import_react27.useState)(null);
|
|
4375
|
+
const dismiss = (0, import_react27.useCallback)(() => setToast(null), []);
|
|
4049
4376
|
const log = useEventLog();
|
|
4050
4377
|
if (!monitor || !monitor.enabled) return null;
|
|
4051
4378
|
const key = pinKey(pin);
|
|
@@ -4102,11 +4429,11 @@ function PinToggle({ pin, monitor, ui, market }) {
|
|
|
4102
4429
|
}
|
|
4103
4430
|
|
|
4104
4431
|
// src/components/PriceHistoryButton.tsx
|
|
4105
|
-
var
|
|
4432
|
+
var import_react28 = require("react");
|
|
4106
4433
|
var import_jsx_runtime13 = require("react/jsx-runtime");
|
|
4107
4434
|
function PriceHistoryButton({ selection, monitor, ui }) {
|
|
4108
|
-
const [toast, setToast] = (0,
|
|
4109
|
-
const dismiss = (0,
|
|
4435
|
+
const [toast, setToast] = (0, import_react28.useState)(null);
|
|
4436
|
+
const dismiss = (0, import_react28.useCallback)(() => setToast(null), []);
|
|
4110
4437
|
const log = useEventLog();
|
|
4111
4438
|
if (!monitor || !monitor.enabled) return null;
|
|
4112
4439
|
const name = joinSelection(selection.selectionLabel ?? void 0, selection.line ?? void 0);
|
|
@@ -4221,15 +4548,15 @@ function BettingInsightList({ insights, ui, slip, monitor }) {
|
|
|
4221
4548
|
}
|
|
4222
4549
|
|
|
4223
4550
|
// src/components/AddAllToSlipButton.tsx
|
|
4224
|
-
var
|
|
4551
|
+
var import_react29 = require("react");
|
|
4225
4552
|
var import_jsx_runtime15 = require("react/jsx-runtime");
|
|
4226
4553
|
function AddAllToSlipButton({ legs, slip, ui }) {
|
|
4227
4554
|
const add = useSlipAdd(slip, ui);
|
|
4228
4555
|
const slipState = useSlipState();
|
|
4229
|
-
const [pending, setPending] = (0,
|
|
4230
|
-
const [settledLocal, setSettledLocal] = (0,
|
|
4231
|
-
const [toast, setToast] = (0,
|
|
4232
|
-
const dismiss = (0,
|
|
4556
|
+
const [pending, setPending] = (0, import_react29.useState)(false);
|
|
4557
|
+
const [settledLocal, setSettledLocal] = (0, import_react29.useState)({});
|
|
4558
|
+
const [toast, setToast] = (0, import_react29.useState)(null);
|
|
4559
|
+
const dismiss = (0, import_react29.useCallback)(() => setToast(null), []);
|
|
4233
4560
|
if (!ui || !slip.onAddToSlip || legs.length < 2) return null;
|
|
4234
4561
|
const settled = slipState ? slipState.settled : settledLocal;
|
|
4235
4562
|
const open = legs.filter((leg) => !settled[leg.matchOddsId]);
|
|
@@ -4271,10 +4598,10 @@ function AddAllToSlipButton({ legs, slip, ui }) {
|
|
|
4271
4598
|
}
|
|
4272
4599
|
|
|
4273
4600
|
// src/presetToolsContext.ts
|
|
4274
|
-
var
|
|
4275
|
-
var PresetToolsContext = (0,
|
|
4601
|
+
var import_react30 = require("react");
|
|
4602
|
+
var PresetToolsContext = (0, import_react30.createContext)(null);
|
|
4276
4603
|
function usePresetTools() {
|
|
4277
|
-
return (0,
|
|
4604
|
+
return (0, import_react30.useContext)(PresetToolsContext);
|
|
4278
4605
|
}
|
|
4279
4606
|
|
|
4280
4607
|
// src/components/ComboCardList.tsx
|
|
@@ -4339,7 +4666,7 @@ function ComboCardList({ cards, ui, slip, monitor }) {
|
|
|
4339
4666
|
}
|
|
4340
4667
|
|
|
4341
4668
|
// src/components/MarketOddsCardList.tsx
|
|
4342
|
-
var
|
|
4669
|
+
var import_react31 = require("react");
|
|
4343
4670
|
|
|
4344
4671
|
// src/components/AllMarketsButton.tsx
|
|
4345
4672
|
var import_jsx_runtime17 = require("react/jsx-runtime");
|
|
@@ -4402,7 +4729,7 @@ function fmtHhMm(iso, locale) {
|
|
|
4402
4729
|
return new Date(iso).toLocaleTimeString(locale, { hour: "2-digit", minute: "2-digit", hour12: false });
|
|
4403
4730
|
}
|
|
4404
4731
|
function MarketOddsCard({ vm, ui, slip, monitor, inSlipIds, hideHeader, pinRef }) {
|
|
4405
|
-
const [open, setOpen] = (0,
|
|
4732
|
+
const [open, setOpen] = (0, import_react31.useState)(false);
|
|
4406
4733
|
const kickoffFallback = vm.kickoffUtc && ui?.bettingKickoff ? ui.bettingKickoff(vm.kickoffUtc) : void 0;
|
|
4407
4734
|
const kickoff = vm.kickoffLabel ?? (kickoffFallback ? `${kickoffFallback.dayLabel} ${kickoffFallback.time}` : void 0);
|
|
4408
4735
|
const hasNamedTeams = !!vm.homeTeamName && !!vm.awayTeamName;
|
|
@@ -4412,9 +4739,9 @@ function MarketOddsCard({ vm, ui, slip, monitor, inSlipIds, hideHeader, pinRef }
|
|
|
4412
4739
|
const asOfMs = live ? new Date(live.asOfUtc).getTime() : NaN;
|
|
4413
4740
|
const isStale = live != null && !isClosed && (vm.awaitingLiveUpdate === true || Date.now() - asOfMs > STALE_AFTER_MS);
|
|
4414
4741
|
const staleTime = isStale && live ? fmtHhMm(live.asOfUtc, ui?.locale ?? "en") : null;
|
|
4415
|
-
const [, setStaleTick] = (0,
|
|
4742
|
+
const [, setStaleTick] = (0, import_react31.useState)(0);
|
|
4416
4743
|
const watchStale = live != null && !isClosed && !isStale;
|
|
4417
|
-
(0,
|
|
4744
|
+
(0, import_react31.useEffect)(() => {
|
|
4418
4745
|
if (!watchStale) return;
|
|
4419
4746
|
const id = window.setTimeout(() => setStaleTick((n) => n + 1), Math.max(0, asOfMs + STALE_AFTER_MS - Date.now()) + 1);
|
|
4420
4747
|
return () => window.clearTimeout(id);
|
|
@@ -4493,7 +4820,7 @@ function MarketOddsCardList({ cards, ui, slip, monitor, inSlipIds, hideHeader, p
|
|
|
4493
4820
|
}
|
|
4494
4821
|
|
|
4495
4822
|
// src/components/CompactOddsList.tsx
|
|
4496
|
-
var
|
|
4823
|
+
var import_react32 = require("react");
|
|
4497
4824
|
|
|
4498
4825
|
// src/compactList.ts
|
|
4499
4826
|
var COMPACT_MIN_CARDS = 3;
|
|
@@ -4607,11 +4934,11 @@ function Row({ row, columns, ui, slip, monitor, rowRef }) {
|
|
|
4607
4934
|
] });
|
|
4608
4935
|
}
|
|
4609
4936
|
function CompactOddsList({ list, ui, slip, monitor }) {
|
|
4610
|
-
const [shown, setShown] = (0,
|
|
4937
|
+
const [shown, setShown] = (0, import_react32.useState)(COMPACT_PAGE);
|
|
4611
4938
|
const hidden = list.rowCount - shown;
|
|
4612
|
-
const [focusIndex, setFocusIndex] = (0,
|
|
4613
|
-
const focusRef = (0,
|
|
4614
|
-
(0,
|
|
4939
|
+
const [focusIndex, setFocusIndex] = (0, import_react32.useState)(null);
|
|
4940
|
+
const focusRef = (0, import_react32.useRef)(null);
|
|
4941
|
+
(0, import_react32.useEffect)(() => {
|
|
4615
4942
|
if (focusIndex !== null) focusRef.current?.focus();
|
|
4616
4943
|
}, [focusIndex]);
|
|
4617
4944
|
let left = shown;
|
|
@@ -4916,7 +5243,7 @@ function FixtureCard({ card }) {
|
|
|
4916
5243
|
}
|
|
4917
5244
|
|
|
4918
5245
|
// src/components/dashboard/CountdownCard.tsx
|
|
4919
|
-
var
|
|
5246
|
+
var import_react33 = require("react");
|
|
4920
5247
|
var import_jsx_runtime25 = require("react/jsx-runtime");
|
|
4921
5248
|
var DAY_MS = 864e5;
|
|
4922
5249
|
function remainingSegments(kickoffUnix, nowMs, withSeconds) {
|
|
@@ -4935,12 +5262,12 @@ function remainingSegments(kickoffUnix, nowMs, withSeconds) {
|
|
|
4935
5262
|
function CountdownCard({ card }) {
|
|
4936
5263
|
const { data } = card;
|
|
4937
5264
|
const unitLabel = { d: data.daysUnit, h: data.hoursUnit, m: data.minutesUnit, s: data.secondsUnit };
|
|
4938
|
-
const [nowMs, setNowMs] = (0,
|
|
4939
|
-
const [reduced] = (0,
|
|
5265
|
+
const [nowMs, setNowMs] = (0, import_react33.useState)(() => Date.now());
|
|
5266
|
+
const [reduced] = (0, import_react33.useState)(
|
|
4940
5267
|
() => typeof window !== "undefined" && window.matchMedia("(prefers-reduced-motion: reduce)").matches
|
|
4941
5268
|
);
|
|
4942
5269
|
const withinDay = data.kickoffUnix * 1e3 - nowMs < DAY_MS;
|
|
4943
|
-
(0,
|
|
5270
|
+
(0, import_react33.useEffect)(() => {
|
|
4944
5271
|
if (reduced) return;
|
|
4945
5272
|
const id = window.setInterval(() => setNowMs(Date.now()), withinDay ? 1e3 : 6e4);
|
|
4946
5273
|
return () => window.clearInterval(id);
|
|
@@ -4948,7 +5275,7 @@ function CountdownCard({ card }) {
|
|
|
4948
5275
|
const segments = remainingSegments(data.kickoffUnix, nowMs, withinDay && !reduced);
|
|
4949
5276
|
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "ss-w-fandash-card ss-w-fandash-countdown", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: "ss-w-fandash-countdown-top", children: [
|
|
4950
5277
|
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "ss-w-fandash-eyebrow", children: card.title ?? "Kick-off in" }),
|
|
4951
|
-
segments ? /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "ss-w-fandash-countdown-clock", children: segments.map((s, i) => /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(
|
|
5278
|
+
segments ? /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "ss-w-fandash-countdown-clock", children: segments.map((s, i) => /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(import_react33.Fragment, { children: [
|
|
4952
5279
|
i > 0 ? /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "ss-w-fandash-countdown-colon", children: ":" }) : null,
|
|
4953
5280
|
/* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("span", { className: "ss-w-fandash-countdown-seg", children: [
|
|
4954
5281
|
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "ss-w-fandash-countdown-value", children: s.value }),
|
|
@@ -4959,7 +5286,7 @@ function CountdownCard({ card }) {
|
|
|
4959
5286
|
}
|
|
4960
5287
|
|
|
4961
5288
|
// src/components/dashboard/InjuriesCard.tsx
|
|
4962
|
-
var
|
|
5289
|
+
var import_react34 = require("react");
|
|
4963
5290
|
var import_jsx_runtime26 = require("react/jsx-runtime");
|
|
4964
5291
|
var SHOWN = 3;
|
|
4965
5292
|
function ColHead({ name, crestUrl }) {
|
|
@@ -4982,7 +5309,7 @@ function InjuryList({ rows, emptyLabel, limit }) {
|
|
|
4982
5309
|
}
|
|
4983
5310
|
function InjuriesCard({ card, ui }) {
|
|
4984
5311
|
const { data } = card;
|
|
4985
|
-
const [expanded, setExpanded] = (0,
|
|
5312
|
+
const [expanded, setExpanded] = (0, import_react34.useState)(false);
|
|
4986
5313
|
const hidden = Math.max(0, data.ours.length - SHOWN) + Math.max(0, data.theirs.length - SHOWN);
|
|
4987
5314
|
const limit = expanded ? void 0 : SHOWN;
|
|
4988
5315
|
const showMore = ui?.showMore ?? ((n) => `Show ${n} more`);
|
|
@@ -5088,7 +5415,7 @@ function LinksCard({ card }) {
|
|
|
5088
5415
|
}
|
|
5089
5416
|
|
|
5090
5417
|
// src/components/dashboard/PostMatchResultCard.tsx
|
|
5091
|
-
var
|
|
5418
|
+
var import_react35 = require("react");
|
|
5092
5419
|
var import_jsx_runtime32 = require("react/jsx-runtime");
|
|
5093
5420
|
function initials3(name) {
|
|
5094
5421
|
return name.trim().slice(0, 3).toUpperCase();
|
|
@@ -5098,7 +5425,7 @@ function PostMatchCrest({
|
|
|
5098
5425
|
name,
|
|
5099
5426
|
side
|
|
5100
5427
|
}) {
|
|
5101
|
-
const [failed, setFailed] = (0,
|
|
5428
|
+
const [failed, setFailed] = (0, import_react35.useState)(false);
|
|
5102
5429
|
const cls = `ss-w-fandash-postmatch-crest ss-w-fandash-postmatch-crest--${side}`;
|
|
5103
5430
|
if (url && !failed) {
|
|
5104
5431
|
return /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("img", { className: cls, src: url, alt: "", "aria-hidden": "true", onError: () => setFailed(true) });
|
|
@@ -5297,10 +5624,10 @@ function RestingFormCard({ card }) {
|
|
|
5297
5624
|
}
|
|
5298
5625
|
|
|
5299
5626
|
// src/components/dashboard/LiveScoreCard.tsx
|
|
5300
|
-
var
|
|
5627
|
+
var import_react37 = require("react");
|
|
5301
5628
|
|
|
5302
5629
|
// src/useLiveClock.ts
|
|
5303
|
-
var
|
|
5630
|
+
var import_react36 = require("react");
|
|
5304
5631
|
var TICK_MS = 6e4;
|
|
5305
5632
|
var MAX_LIVE_TICK_MINUTES = 15;
|
|
5306
5633
|
function computeDisplayMinute(minute, clockRunning, receivedAtMs) {
|
|
@@ -5309,10 +5636,10 @@ function computeDisplayMinute(minute, clockRunning, receivedAtMs) {
|
|
|
5309
5636
|
return minute + Math.min(Math.max(0, elapsedMinutes), MAX_LIVE_TICK_MINUTES);
|
|
5310
5637
|
}
|
|
5311
5638
|
function useLiveClock(minute, clockRunning, receivedAtMs) {
|
|
5312
|
-
const [displayMinute, setDisplayMinute] = (0,
|
|
5639
|
+
const [displayMinute, setDisplayMinute] = (0, import_react36.useState)(
|
|
5313
5640
|
() => computeDisplayMinute(minute, clockRunning, receivedAtMs)
|
|
5314
5641
|
);
|
|
5315
|
-
(0,
|
|
5642
|
+
(0, import_react36.useEffect)(() => {
|
|
5316
5643
|
setDisplayMinute(computeDisplayMinute(minute, clockRunning, receivedAtMs));
|
|
5317
5644
|
if (!clockRunning) return;
|
|
5318
5645
|
const id = window.setInterval(() => {
|
|
@@ -5329,7 +5656,7 @@ function initials5(name) {
|
|
|
5329
5656
|
return name.trim().slice(0, 3).toUpperCase();
|
|
5330
5657
|
}
|
|
5331
5658
|
function LiveCrest({ url, name, side }) {
|
|
5332
|
-
const [failed, setFailed] = (0,
|
|
5659
|
+
const [failed, setFailed] = (0, import_react37.useState)(false);
|
|
5333
5660
|
const cls = `ss-w-fandash-live-crest ss-w-fandash-live-crest--${side}`;
|
|
5334
5661
|
if (url && !failed) {
|
|
5335
5662
|
return /* @__PURE__ */ (0, import_jsx_runtime41.jsx)("img", { className: cls, src: url, alt: "", "aria-hidden": "true", onError: () => setFailed(true) });
|
|
@@ -5348,7 +5675,7 @@ function LiveScoreCard({
|
|
|
5348
5675
|
}) {
|
|
5349
5676
|
const { data } = card;
|
|
5350
5677
|
const seedKey = `${data.minute}:${data.homeScore}:${data.awayScore}`;
|
|
5351
|
-
const seedRef = (0,
|
|
5678
|
+
const seedRef = (0, import_react37.useRef)(null);
|
|
5352
5679
|
if (!seedRef.current || seedRef.current.key !== seedKey) {
|
|
5353
5680
|
seedRef.current = { key: seedKey, receivedAtMs: Date.now() };
|
|
5354
5681
|
}
|
|
@@ -5388,7 +5715,7 @@ function LiveScoreCard({
|
|
|
5388
5715
|
}
|
|
5389
5716
|
|
|
5390
5717
|
// src/components/dashboard/LiveTimelineCard.tsx
|
|
5391
|
-
var
|
|
5718
|
+
var import_react38 = require("react");
|
|
5392
5719
|
var import_jsx_runtime42 = require("react/jsx-runtime");
|
|
5393
5720
|
var SHOWN2 = 3;
|
|
5394
5721
|
function EventIcon({ type }) {
|
|
@@ -5430,7 +5757,7 @@ function EventRow({ e }) {
|
|
|
5430
5757
|
] });
|
|
5431
5758
|
}
|
|
5432
5759
|
function LiveTimelineCard({ card, ui }) {
|
|
5433
|
-
const [expanded, setExpanded] = (0,
|
|
5760
|
+
const [expanded, setExpanded] = (0, import_react38.useState)(false);
|
|
5434
5761
|
const events = card.data.events;
|
|
5435
5762
|
if (!events || events.length === 0) return null;
|
|
5436
5763
|
const sorted = [...events].sort((a, b) => b.minute - a.minute);
|
|
@@ -5455,7 +5782,7 @@ function LiveTimelineCard({ card, ui }) {
|
|
|
5455
5782
|
}
|
|
5456
5783
|
|
|
5457
5784
|
// src/components/dashboard/MomentumWave.tsx
|
|
5458
|
-
var
|
|
5785
|
+
var import_react39 = require("react");
|
|
5459
5786
|
var import_jsx_runtime43 = require("react/jsx-runtime");
|
|
5460
5787
|
var WIDTH = 270;
|
|
5461
5788
|
var HEIGHT = 56;
|
|
@@ -5479,7 +5806,7 @@ function MomentumWave({
|
|
|
5479
5806
|
}) {
|
|
5480
5807
|
if (points.length === 0) return null;
|
|
5481
5808
|
const { area, line, lastLeftPct, lastTopPx } = buildPaths(points);
|
|
5482
|
-
const clipId = (0,
|
|
5809
|
+
const clipId = (0, import_react39.useId)();
|
|
5483
5810
|
const topClipId = `${clipId}-top`;
|
|
5484
5811
|
const bottomClipId = `${clipId}-bottom`;
|
|
5485
5812
|
const topClass = clubIsHome ? "ss-w-fandash-live-mom-home" : "ss-w-fandash-live-mom-away";
|
|
@@ -5672,11 +5999,11 @@ function turnAnchor(messages) {
|
|
|
5672
5999
|
}
|
|
5673
6000
|
function MessageList({ controller, ui, slip, onDashboardTap, monitor }) {
|
|
5674
6001
|
const { state, send } = controller;
|
|
5675
|
-
const listRef = (0,
|
|
5676
|
-
const endRef = (0,
|
|
5677
|
-
const pinnedRef = (0,
|
|
5678
|
-
const anchoredTurnRef = (0,
|
|
5679
|
-
(0,
|
|
6002
|
+
const listRef = (0, import_react40.useRef)(null);
|
|
6003
|
+
const endRef = (0, import_react40.useRef)(null);
|
|
6004
|
+
const pinnedRef = (0, import_react40.useRef)(true);
|
|
6005
|
+
const anchoredTurnRef = (0, import_react40.useRef)(null);
|
|
6006
|
+
(0, import_react40.useEffect)(() => {
|
|
5680
6007
|
const anchor = turnAnchor(state.messages);
|
|
5681
6008
|
const list = listRef.current;
|
|
5682
6009
|
if (anchor && anchor.turnId !== anchoredTurnRef.current) {
|
|
@@ -5733,13 +6060,13 @@ function MessageList({ controller, ui, slip, onDashboardTap, monitor }) {
|
|
|
5733
6060
|
}
|
|
5734
6061
|
|
|
5735
6062
|
// src/components/ChatInput.tsx
|
|
5736
|
-
var
|
|
6063
|
+
var import_react41 = require("react");
|
|
5737
6064
|
var import_jsx_runtime49 = require("react/jsx-runtime");
|
|
5738
|
-
var ChatInput = (0,
|
|
5739
|
-
const [value, setValue] = (0,
|
|
5740
|
-
const textareaRef = (0,
|
|
5741
|
-
const stopRef = (0,
|
|
5742
|
-
const textBoxWantsFocusRef = (0,
|
|
6065
|
+
var ChatInput = (0, import_react41.forwardRef)(function ChatInput2({ placeholder, streaming, onSend, onStop, stopLabel = "Stop response", sendLabel = "Send message", disabled = false, onType }, ref) {
|
|
6066
|
+
const [value, setValue] = (0, import_react41.useState)("");
|
|
6067
|
+
const textareaRef = (0, import_react41.useRef)(null);
|
|
6068
|
+
const stopRef = (0, import_react41.useRef)(null);
|
|
6069
|
+
const textBoxWantsFocusRef = (0, import_react41.useRef)(false);
|
|
5743
6070
|
const submit = () => {
|
|
5744
6071
|
if (disabled) return;
|
|
5745
6072
|
const t = value.trim();
|
|
@@ -5753,7 +6080,7 @@ var ChatInput = (0, import_react39.forwardRef)(function ChatInput2({ placeholder
|
|
|
5753
6080
|
submit();
|
|
5754
6081
|
}
|
|
5755
6082
|
};
|
|
5756
|
-
(0,
|
|
6083
|
+
(0, import_react41.useImperativeHandle)(ref, () => ({
|
|
5757
6084
|
focus() {
|
|
5758
6085
|
const box = textareaRef.current;
|
|
5759
6086
|
if (box && !box.disabled) {
|
|
@@ -5765,7 +6092,7 @@ var ChatInput = (0, import_react39.forwardRef)(function ChatInput2({ placeholder
|
|
|
5765
6092
|
stopRef.current?.focus();
|
|
5766
6093
|
}
|
|
5767
6094
|
}), []);
|
|
5768
|
-
(0,
|
|
6095
|
+
(0, import_react41.useEffect)(() => {
|
|
5769
6096
|
if (streaming || disabled || !textBoxWantsFocusRef.current) return;
|
|
5770
6097
|
textBoxWantsFocusRef.current = false;
|
|
5771
6098
|
const box = textareaRef.current;
|
|
@@ -5797,6 +6124,7 @@ var ChatInput = (0, import_react39.forwardRef)(function ChatInput2({ placeholder
|
|
|
5797
6124
|
});
|
|
5798
6125
|
|
|
5799
6126
|
// src/components/TabBar.tsx
|
|
6127
|
+
var import_react42 = require("react");
|
|
5800
6128
|
var import_jsx_runtime50 = require("react/jsx-runtime");
|
|
5801
6129
|
function TabBar({ monitor, ui, matchCount, oddsCount, todayCount, hasToday, gamesEnabled, clubEnabled }) {
|
|
5802
6130
|
const tabs = [
|
|
@@ -5812,8 +6140,16 @@ function TabBar({ monitor, ui, matchCount, oddsCount, todayCount, hasToday, game
|
|
|
5812
6140
|
],
|
|
5813
6141
|
...gamesEnabled ? [{ tab: "games", label: ui.tabGames, count: 0, dot: false }] : []
|
|
5814
6142
|
];
|
|
6143
|
+
const listRef = (0, import_react42.useRef)(null);
|
|
6144
|
+
const activeTab = monitor.activeTab;
|
|
6145
|
+
(0, import_react42.useEffect)(() => {
|
|
6146
|
+
const el = listRef.current?.querySelector("[data-on]");
|
|
6147
|
+
if (!el || typeof el.scrollIntoView !== "function") return;
|
|
6148
|
+
const reduce = typeof window.matchMedia === "function" && window.matchMedia("(prefers-reduced-motion: reduce)").matches;
|
|
6149
|
+
el.scrollIntoView({ block: "nearest", inline: "nearest", behavior: reduce ? "auto" : "smooth" });
|
|
6150
|
+
}, [activeTab]);
|
|
5815
6151
|
if (tabs.length < 2) return null;
|
|
5816
|
-
return /* @__PURE__ */ (0, import_jsx_runtime50.jsx)("div", { className: "ss-w-tabs", role: "tablist", children: tabs.map(({ tab, label, count, dot }) => {
|
|
6152
|
+
return /* @__PURE__ */ (0, import_jsx_runtime50.jsx)("div", { className: "ss-w-tabs", role: "tablist", ref: listRef, children: tabs.map(({ tab, label, count, dot }) => {
|
|
5817
6153
|
const active = monitor.activeTab === tab;
|
|
5818
6154
|
return /* @__PURE__ */ (0, import_jsx_runtime50.jsxs)(
|
|
5819
6155
|
"button",
|
|
@@ -5890,10 +6226,10 @@ function MarketAccordion({ match, monitor, ui, slip }) {
|
|
|
5890
6226
|
}
|
|
5891
6227
|
|
|
5892
6228
|
// src/components/LiveFactBlock.tsx
|
|
5893
|
-
var
|
|
6229
|
+
var import_react43 = require("react");
|
|
5894
6230
|
var import_jsx_runtime52 = require("react/jsx-runtime");
|
|
5895
6231
|
function LiveFactBlock({ facts, matchId, ui, slip, onAsk }) {
|
|
5896
|
-
const [expanded, setExpanded] = (0,
|
|
6232
|
+
const [expanded, setExpanded] = (0, import_react43.useState)(false);
|
|
5897
6233
|
const [current, ...earlier] = facts;
|
|
5898
6234
|
if (!current) return null;
|
|
5899
6235
|
const m = current.market;
|
|
@@ -6159,7 +6495,7 @@ function OddsPanel({ monitor, ui, slip }) {
|
|
|
6159
6495
|
}
|
|
6160
6496
|
|
|
6161
6497
|
// src/components/TodayPanel.tsx
|
|
6162
|
-
var
|
|
6498
|
+
var import_react47 = require("react");
|
|
6163
6499
|
|
|
6164
6500
|
// src/placement.ts
|
|
6165
6501
|
function placeLeagues(visible, pinnedMatchIds) {
|
|
@@ -6222,11 +6558,11 @@ function matchingFixtures(group, query) {
|
|
|
6222
6558
|
}
|
|
6223
6559
|
|
|
6224
6560
|
// src/useStarTap.ts
|
|
6225
|
-
var
|
|
6561
|
+
var import_react44 = require("react");
|
|
6226
6562
|
function useStarTap(starLeague) {
|
|
6227
|
-
const [pendingId, setPendingId] = (0,
|
|
6228
|
-
const pendingRef = (0,
|
|
6229
|
-
const tap = (0,
|
|
6563
|
+
const [pendingId, setPendingId] = (0, import_react44.useState)(null);
|
|
6564
|
+
const pendingRef = (0, import_react44.useRef)(null);
|
|
6565
|
+
const tap = (0, import_react44.useCallback)(async (competitionId, next) => {
|
|
6230
6566
|
if (pendingRef.current !== null) return false;
|
|
6231
6567
|
pendingRef.current = competitionId;
|
|
6232
6568
|
setPendingId(competitionId);
|
|
@@ -6285,7 +6621,7 @@ function LeagueTile({ group, starClickable: starClickable2, disambiguate, onOpen
|
|
|
6285
6621
|
}
|
|
6286
6622
|
|
|
6287
6623
|
// src/components/LeagueDetail.tsx
|
|
6288
|
-
var
|
|
6624
|
+
var import_react45 = require("react");
|
|
6289
6625
|
|
|
6290
6626
|
// src/components/FixtureRow.tsx
|
|
6291
6627
|
var import_jsx_runtime56 = require("react/jsx-runtime");
|
|
@@ -6320,11 +6656,11 @@ function FixtureRow({ match, state, stale, ui, monitor }) {
|
|
|
6320
6656
|
var import_jsx_runtime57 = require("react/jsx-runtime");
|
|
6321
6657
|
var STAR_PATH2 = "M12 2.5l2.9 5.9 6.5.95-4.7 4.58 1.1 6.47L12 17.35 6.1 20.4l1.1-6.47L2.5 9.35l6.5-.95z";
|
|
6322
6658
|
function LeagueDetail({ group, position, states, stale, ui, monitor, starTap, onBack, onPrev, onNext }) {
|
|
6323
|
-
const [toast, setToast] = (0,
|
|
6324
|
-
(0,
|
|
6659
|
+
const [toast, setToast] = (0, import_react45.useState)(null);
|
|
6660
|
+
(0, import_react45.useEffect)(() => {
|
|
6325
6661
|
setToast(null);
|
|
6326
6662
|
}, [group.competitionId]);
|
|
6327
|
-
(0,
|
|
6663
|
+
(0, import_react45.useEffect)(() => {
|
|
6328
6664
|
if (toast === null) return;
|
|
6329
6665
|
const id = setTimeout(() => setToast(null), 4e3);
|
|
6330
6666
|
return () => clearTimeout(id);
|
|
@@ -6456,7 +6792,7 @@ function LeagueRowGroup({ group, states, stale, cap, starClickable: starClickabl
|
|
|
6456
6792
|
}
|
|
6457
6793
|
|
|
6458
6794
|
// src/components/games/ui/SearchField.tsx
|
|
6459
|
-
var
|
|
6795
|
+
var import_react46 = require("react");
|
|
6460
6796
|
|
|
6461
6797
|
// src/components/games/ui/icons.tsx
|
|
6462
6798
|
var import_jsx_runtime59 = require("react/jsx-runtime");
|
|
@@ -6495,8 +6831,8 @@ var IconFlame = ({ size = 16 }) => svg(size, /* @__PURE__ */ (0, import_jsx_runt
|
|
|
6495
6831
|
// src/components/games/ui/SearchField.tsx
|
|
6496
6832
|
var import_jsx_runtime60 = require("react/jsx-runtime");
|
|
6497
6833
|
function SearchField({ id, label, labelHidden = false, placeholder, value, onChange, disabled, inputRef, onKeyDown, clearLabel }) {
|
|
6498
|
-
const localRef = (0,
|
|
6499
|
-
const setInputRef = (0,
|
|
6834
|
+
const localRef = (0, import_react46.useRef)(null);
|
|
6835
|
+
const setInputRef = (0, import_react46.useCallback)((node) => {
|
|
6500
6836
|
localRef.current = node;
|
|
6501
6837
|
if (typeof inputRef === "function") inputRef(node);
|
|
6502
6838
|
else if (inputRef) inputRef.current = node;
|
|
@@ -6540,23 +6876,23 @@ function SearchField({ id, label, labelHidden = false, placeholder, value, onCha
|
|
|
6540
6876
|
var import_jsx_runtime61 = require("react/jsx-runtime");
|
|
6541
6877
|
function TodayPanel({ discovery, ui, monitor }) {
|
|
6542
6878
|
const { groups, states, stale, starLeague } = discovery;
|
|
6543
|
-
const searchId = (0,
|
|
6544
|
-
const [query, setQuery] = (0,
|
|
6545
|
-
const [selectedCompetitionId, setSelectedCompetitionId] = (0,
|
|
6546
|
-
const [toast, setToast] = (0,
|
|
6547
|
-
(0,
|
|
6879
|
+
const searchId = (0, import_react47.useId)();
|
|
6880
|
+
const [query, setQuery] = (0, import_react47.useState)("");
|
|
6881
|
+
const [selectedCompetitionId, setSelectedCompetitionId] = (0, import_react47.useState)(null);
|
|
6882
|
+
const [toast, setToast] = (0, import_react47.useState)(null);
|
|
6883
|
+
(0, import_react47.useEffect)(() => {
|
|
6548
6884
|
if (toast === null) return;
|
|
6549
6885
|
const id = setTimeout(() => setToast(null), 4e3);
|
|
6550
6886
|
return () => clearTimeout(id);
|
|
6551
6887
|
}, [toast]);
|
|
6552
6888
|
const visibleGroups = visibleGroupsOf(groups, states);
|
|
6553
|
-
const pinnedMatchIds = (0,
|
|
6889
|
+
const pinnedMatchIds = (0, import_react47.useMemo)(
|
|
6554
6890
|
() => monitor.pins.filter((p) => p.kind === "match").map((p) => p.matchId),
|
|
6555
6891
|
[monitor.pins]
|
|
6556
6892
|
);
|
|
6557
|
-
const placement = (0,
|
|
6893
|
+
const placement = (0, import_react47.useMemo)(() => placeLeagues(visibleGroups, pinnedMatchIds), [visibleGroups, pinnedMatchIds]);
|
|
6558
6894
|
const starTap = useStarTap(starLeague);
|
|
6559
|
-
const gridStarTap = (0,
|
|
6895
|
+
const gridStarTap = (0, import_react47.useMemo)(() => ({
|
|
6560
6896
|
pendingId: starTap.pendingId,
|
|
6561
6897
|
tap: async (competitionId, next) => {
|
|
6562
6898
|
const ok = await starTap.tap(competitionId, next);
|
|
@@ -6590,7 +6926,7 @@ function TodayPanel({ discovery, ui, monitor }) {
|
|
|
6590
6926
|
}
|
|
6591
6927
|
const openIndex = selectedCompetitionId === null ? -1 : placement.order.findIndex((g) => g.competitionId === selectedCompetitionId);
|
|
6592
6928
|
const openGroup = openIndex === -1 ? void 0 : placement.order[openIndex];
|
|
6593
|
-
(0,
|
|
6929
|
+
(0, import_react47.useEffect)(() => {
|
|
6594
6930
|
if (selectedCompetitionId !== null && openGroup === void 0) setSelectedCompetitionId(null);
|
|
6595
6931
|
}, [selectedCompetitionId, openGroup]);
|
|
6596
6932
|
const liveRows = stale ? [] : visibleGroups.flatMap((group) => group.matches.filter((m) => isTreatedLive(states[m.matchId], stale)).map((match) => ({ match, rank: group.rank }))).sort((a, b) => a.rank - b.rank);
|
|
@@ -6737,7 +7073,7 @@ function TodayPanel({ discovery, ui, monitor }) {
|
|
|
6737
7073
|
}
|
|
6738
7074
|
|
|
6739
7075
|
// src/components/GamesPanel.tsx
|
|
6740
|
-
var
|
|
7076
|
+
var import_react62 = require("react");
|
|
6741
7077
|
|
|
6742
7078
|
// src/components/GamesLoginWall.tsx
|
|
6743
7079
|
var import_jsx_runtime62 = require("react/jsx-runtime");
|
|
@@ -6746,7 +7082,7 @@ function GamesLoginWall({ ui }) {
|
|
|
6746
7082
|
}
|
|
6747
7083
|
|
|
6748
7084
|
// src/components/GamesHub.tsx
|
|
6749
|
-
var
|
|
7085
|
+
var import_react48 = require("react");
|
|
6750
7086
|
|
|
6751
7087
|
// src/components/games/ui/gameMeta.ts
|
|
6752
7088
|
function prettifyGameId(gameId) {
|
|
@@ -6897,8 +7233,8 @@ function pickHeroGame(games) {
|
|
|
6897
7233
|
}
|
|
6898
7234
|
var tileKey = (g) => `${g.gameId}-${g.gameDay}-${g.fixtureId}`;
|
|
6899
7235
|
function GamesHub({ games, myWeeklyRow, weeklyPrize, onOpen, ui }) {
|
|
6900
|
-
const [, setTick] = (0,
|
|
6901
|
-
(0,
|
|
7236
|
+
const [, setTick] = (0, import_react48.useState)(0);
|
|
7237
|
+
(0, import_react48.useEffect)(() => {
|
|
6902
7238
|
const id = setInterval(() => setTick((t) => t + 1), 6e4);
|
|
6903
7239
|
return () => clearInterval(id);
|
|
6904
7240
|
}, []);
|
|
@@ -6958,10 +7294,10 @@ function GamesHub({ games, myWeeklyRow, weeklyPrize, onOpen, ui }) {
|
|
|
6958
7294
|
}
|
|
6959
7295
|
|
|
6960
7296
|
// src/components/GameScreenHost.tsx
|
|
6961
|
-
var
|
|
7297
|
+
var import_react60 = require("react");
|
|
6962
7298
|
|
|
6963
7299
|
// src/useGamePlay.ts
|
|
6964
|
-
var
|
|
7300
|
+
var import_react49 = require("react");
|
|
6965
7301
|
function toSubmitResult(payload) {
|
|
6966
7302
|
return {
|
|
6967
7303
|
// 'pending' means the play is recorded but awaiting resolution (fixture games)
|
|
@@ -6973,17 +7309,17 @@ function toSubmitResult(payload) {
|
|
|
6973
7309
|
};
|
|
6974
7310
|
}
|
|
6975
7311
|
function useGamePlay(conversation, { gameId, gameDay, fixtureId, locale, refresh }) {
|
|
6976
|
-
const [result, setResult] = (0,
|
|
6977
|
-
const [submitting, setSubmitting] = (0,
|
|
6978
|
-
const [rawStatus, setRawStatus] = (0,
|
|
6979
|
-
const inFlightRef = (0,
|
|
6980
|
-
const convRef = (0,
|
|
7312
|
+
const [result, setResult] = (0, import_react49.useState)(null);
|
|
7313
|
+
const [submitting, setSubmitting] = (0, import_react49.useState)(false);
|
|
7314
|
+
const [rawStatus, setRawStatus] = (0, import_react49.useState)(null);
|
|
7315
|
+
const inFlightRef = (0, import_react49.useRef)(false);
|
|
7316
|
+
const convRef = (0, import_react49.useRef)(conversation);
|
|
6981
7317
|
convRef.current = conversation;
|
|
6982
|
-
const optsRef = (0,
|
|
7318
|
+
const optsRef = (0, import_react49.useRef)({ gameId, gameDay, fixtureId, locale, refresh });
|
|
6983
7319
|
optsRef.current = { gameId, gameDay, fixtureId, locale, refresh };
|
|
6984
|
-
const resultRef = (0,
|
|
7320
|
+
const resultRef = (0, import_react49.useRef)(null);
|
|
6985
7321
|
resultRef.current = result;
|
|
6986
|
-
const refetch = (0,
|
|
7322
|
+
const refetch = (0, import_react49.useCallback)(async () => {
|
|
6987
7323
|
const conv = convRef.current;
|
|
6988
7324
|
if (!conv) return;
|
|
6989
7325
|
const opts = optsRef.current;
|
|
@@ -6999,7 +7335,7 @@ function useGamePlay(conversation, { gameId, gameDay, fixtureId, locale, refresh
|
|
|
6999
7335
|
} catch {
|
|
7000
7336
|
}
|
|
7001
7337
|
}, []);
|
|
7002
|
-
const submit = (0,
|
|
7338
|
+
const submit = (0, import_react49.useCallback)(async (answerJson) => {
|
|
7003
7339
|
const conv = convRef.current;
|
|
7004
7340
|
if (!conv || inFlightRef.current) return;
|
|
7005
7341
|
inFlightRef.current = true;
|
|
@@ -7026,14 +7362,14 @@ function useGamePlay(conversation, { gameId, gameDay, fixtureId, locale, refresh
|
|
|
7026
7362
|
setSubmitting(false);
|
|
7027
7363
|
}
|
|
7028
7364
|
}, [refetch]);
|
|
7029
|
-
const hydrate = (0,
|
|
7365
|
+
const hydrate = (0, import_react49.useCallback)(() => {
|
|
7030
7366
|
void refetch();
|
|
7031
7367
|
}, [refetch]);
|
|
7032
7368
|
return { result, submitting, submit, hydrate, rawStatus };
|
|
7033
7369
|
}
|
|
7034
7370
|
|
|
7035
7371
|
// src/components/games/MysteryTigerGame.tsx
|
|
7036
|
-
var
|
|
7372
|
+
var import_react51 = require("react");
|
|
7037
7373
|
|
|
7038
7374
|
// src/components/games/nationFlags.ts
|
|
7039
7375
|
var FLAGS = {
|
|
@@ -7244,7 +7580,7 @@ function isNationCode(flag) {
|
|
|
7244
7580
|
}
|
|
7245
7581
|
|
|
7246
7582
|
// src/components/games/PlayerAvatar.tsx
|
|
7247
|
-
var
|
|
7583
|
+
var import_react50 = require("react");
|
|
7248
7584
|
var import_jsx_runtime67 = require("react/jsx-runtime");
|
|
7249
7585
|
function initialsOf(name) {
|
|
7250
7586
|
const parts = name.trim().split(/\s+/).filter(Boolean);
|
|
@@ -7262,7 +7598,7 @@ function PlayerAvatar({
|
|
|
7262
7598
|
imagePath,
|
|
7263
7599
|
className
|
|
7264
7600
|
}) {
|
|
7265
|
-
const [failed, setFailed] = (0,
|
|
7601
|
+
const [failed, setFailed] = (0, import_react50.useState)(false);
|
|
7266
7602
|
const showImage = Boolean(imagePath) && !isPlaceholderImage(imagePath) && !failed;
|
|
7267
7603
|
return /* @__PURE__ */ (0, import_jsx_runtime67.jsx)("div", { className, "aria-hidden": "true", children: showImage ? /* @__PURE__ */ (0, import_jsx_runtime67.jsx)("img", { src: imagePath, alt: "", loading: "lazy", onError: () => setFailed(true) }) : /* @__PURE__ */ (0, import_jsx_runtime67.jsx)("span", { className: "ss-w-av-initials", children: initialsOf(name) }) });
|
|
7268
7604
|
}
|
|
@@ -7503,8 +7839,8 @@ function MysteryTigerGame({
|
|
|
7503
7839
|
onBack
|
|
7504
7840
|
}) {
|
|
7505
7841
|
const t = ui.games.mysteryTiger;
|
|
7506
|
-
const [query, setQuery] = (0,
|
|
7507
|
-
const inputId = (0,
|
|
7842
|
+
const [query, setQuery] = (0, import_react51.useState)("");
|
|
7843
|
+
const inputId = (0, import_react51.useId)();
|
|
7508
7844
|
const clientState = parseClientState(result?.clientStateJson);
|
|
7509
7845
|
const guessResults = clientState?.guessResults ?? [];
|
|
7510
7846
|
const alreadyGuessedIds = new Set(guessResults.map((g) => g.playerId));
|
|
@@ -7765,13 +8101,13 @@ function HigherOrLowerGame({
|
|
|
7765
8101
|
}
|
|
7766
8102
|
|
|
7767
8103
|
// src/components/games/CareerPathGame.tsx
|
|
7768
|
-
var
|
|
8104
|
+
var import_react53 = require("react");
|
|
7769
8105
|
|
|
7770
8106
|
// src/components/games/ui/CrestShield.tsx
|
|
7771
|
-
var
|
|
8107
|
+
var import_react52 = require("react");
|
|
7772
8108
|
var import_jsx_runtime78 = require("react/jsx-runtime");
|
|
7773
8109
|
function CrestShield({ src, name, size = 28 }) {
|
|
7774
|
-
const [failed, setFailed] = (0,
|
|
8110
|
+
const [failed, setFailed] = (0, import_react52.useState)(false);
|
|
7775
8111
|
if (src && !isPlaceholderImage(src) && !failed) {
|
|
7776
8112
|
return /* @__PURE__ */ (0, import_jsx_runtime78.jsx)("img", { className: "ss-g-crest", src, alt: name, width: size, height: size, loading: "lazy", onError: () => setFailed(true) });
|
|
7777
8113
|
}
|
|
@@ -7803,8 +8139,8 @@ function CareerPathGame({
|
|
|
7803
8139
|
}) {
|
|
7804
8140
|
const s = ui.games.careerPath;
|
|
7805
8141
|
const title = gameTitle({ gameId: "career-path" }, ui.games.titles);
|
|
7806
|
-
const [query, setQuery] = (0,
|
|
7807
|
-
const inputId = (0,
|
|
8142
|
+
const [query, setQuery] = (0, import_react53.useState)("");
|
|
8143
|
+
const inputId = (0, import_react53.useId)();
|
|
7808
8144
|
const clientState = parseClientState3(result?.clientStateJson);
|
|
7809
8145
|
const alreadyGuessedIds = new Set(clientState?.guessResults.map((g) => g.playerId) ?? []);
|
|
7810
8146
|
const isOver = result?.alreadyPlayed === true || clientState?.solved === true || clientState?.failed === true;
|
|
@@ -7910,7 +8246,7 @@ function CareerPathGame({
|
|
|
7910
8246
|
}
|
|
7911
8247
|
|
|
7912
8248
|
// src/components/games/BeatTheGridGame.tsx
|
|
7913
|
-
var
|
|
8249
|
+
var import_react54 = __toESM(require("react"), 1);
|
|
7914
8250
|
|
|
7915
8251
|
// src/components/games/ui/OptionList.tsx
|
|
7916
8252
|
var import_jsx_runtime80 = require("react/jsx-runtime");
|
|
@@ -7999,10 +8335,10 @@ function SearchSheet({
|
|
|
7999
8335
|
ui
|
|
8000
8336
|
}) {
|
|
8001
8337
|
const s = ui.games.beatTheGrid;
|
|
8002
|
-
const [query, setQuery] = (0,
|
|
8003
|
-
const inputId = (0,
|
|
8004
|
-
const inputRef = (0,
|
|
8005
|
-
(0,
|
|
8338
|
+
const [query, setQuery] = (0, import_react54.useState)("");
|
|
8339
|
+
const inputId = (0, import_react54.useId)();
|
|
8340
|
+
const inputRef = (0, import_react54.useRef)(null);
|
|
8341
|
+
(0, import_react54.useEffect)(() => {
|
|
8006
8342
|
inputRef.current?.focus();
|
|
8007
8343
|
}, [row, col]);
|
|
8008
8344
|
const filtered = playerPool.filter(
|
|
@@ -8067,7 +8403,7 @@ function BeatTheGridGame({
|
|
|
8067
8403
|
}) {
|
|
8068
8404
|
const s = ui.games.beatTheGrid;
|
|
8069
8405
|
const title = gameTitle({ gameId: "beat-the-grid" }, ui.games.titles);
|
|
8070
|
-
const [activeCell, setActiveCell] = (0,
|
|
8406
|
+
const [activeCell, setActiveCell] = (0, import_react54.useState)(null);
|
|
8071
8407
|
const clientState = parseClientState4(result?.clientStateJson);
|
|
8072
8408
|
const filledCells = clientState?.cells ?? [];
|
|
8073
8409
|
const isLocked2 = result?.alreadyPlayed === true || clientState?.isComplete === true;
|
|
@@ -8141,7 +8477,7 @@ function BeatTheGridGame({
|
|
|
8141
8477
|
/* @__PURE__ */ (0, import_jsx_runtime81.jsx)("span", { "aria-hidden": "true", children: abbr }),
|
|
8142
8478
|
/* @__PURE__ */ (0, import_jsx_runtime81.jsx)("span", { className: "ss-g-sr", children: rowLabel })
|
|
8143
8479
|
] });
|
|
8144
|
-
return /* @__PURE__ */ (0, import_jsx_runtime81.jsxs)(
|
|
8480
|
+
return /* @__PURE__ */ (0, import_jsx_runtime81.jsxs)(import_react54.default.Fragment, { children: [
|
|
8145
8481
|
/* @__PURE__ */ (0, import_jsx_runtime81.jsx)("div", { className: "ss-g-btg-rowhdr", "data-meta": rowMeta ? "true" : void 0, children: rowHeaderContent }),
|
|
8146
8482
|
cols.map((colLabel, colIdx) => {
|
|
8147
8483
|
const filled = findCellResult(filledCells, rowIdx, colIdx);
|
|
@@ -8222,7 +8558,7 @@ function BeatTheGridGame({
|
|
|
8222
8558
|
}
|
|
8223
8559
|
|
|
8224
8560
|
// src/components/games/GuessTheXiGame.tsx
|
|
8225
|
-
var
|
|
8561
|
+
var import_react55 = require("react");
|
|
8226
8562
|
|
|
8227
8563
|
// src/components/games/ui/PitchSvg.tsx
|
|
8228
8564
|
var import_jsx_runtime82 = require("react/jsx-runtime");
|
|
@@ -8311,8 +8647,8 @@ function GuessTheXiGame({
|
|
|
8311
8647
|
onBack
|
|
8312
8648
|
}) {
|
|
8313
8649
|
const t = ui.games.guessTheXi;
|
|
8314
|
-
const [query, setQuery] = (0,
|
|
8315
|
-
const inputId = (0,
|
|
8650
|
+
const [query, setQuery] = (0, import_react55.useState)("");
|
|
8651
|
+
const inputId = (0, import_react55.useId)();
|
|
8316
8652
|
const clientState = parseClientState5(result?.clientStateJson);
|
|
8317
8653
|
const isOver = result?.alreadyPlayed === true || clientState?.status === "solved" || clientState?.status === "failed";
|
|
8318
8654
|
const solved = clientState?.status === "solved";
|
|
@@ -8454,7 +8790,7 @@ function GuessTheXiGame({
|
|
|
8454
8790
|
}
|
|
8455
8791
|
|
|
8456
8792
|
// src/components/games/DailyQuizGame.tsx
|
|
8457
|
-
var
|
|
8793
|
+
var import_react56 = require("react");
|
|
8458
8794
|
var import_jsx_runtime84 = require("react/jsx-runtime");
|
|
8459
8795
|
function parseClientState6(json) {
|
|
8460
8796
|
if (!json) return null;
|
|
@@ -8495,8 +8831,8 @@ function DailyQuizGame({
|
|
|
8495
8831
|
}) {
|
|
8496
8832
|
const s = ui.games.dailyQuiz;
|
|
8497
8833
|
const title = gameTitle({ gameId: "daily-quiz" }, ui.games.titles);
|
|
8498
|
-
const [selections, setSelections] = (0,
|
|
8499
|
-
const [page, setPage] = (0,
|
|
8834
|
+
const [selections, setSelections] = (0, import_react56.useState)(/* @__PURE__ */ new Map());
|
|
8835
|
+
const [page, setPage] = (0, import_react56.useState)(0);
|
|
8500
8836
|
const clientState = parseClientState6(result?.clientStateJson);
|
|
8501
8837
|
const results = clientState?.results ?? [];
|
|
8502
8838
|
const isRevealed = results.length > 0 || result?.alreadyPlayed === true;
|
|
@@ -8606,7 +8942,7 @@ function DailyQuizGame({
|
|
|
8606
8942
|
}
|
|
8607
8943
|
|
|
8608
8944
|
// src/components/games/MatchdayPredictorGame.tsx
|
|
8609
|
-
var
|
|
8945
|
+
var import_react57 = require("react");
|
|
8610
8946
|
var import_jsx_runtime85 = require("react/jsx-runtime");
|
|
8611
8947
|
var SCORER_SEARCH_THRESHOLD = 9;
|
|
8612
8948
|
function parseClientState7(json) {
|
|
@@ -8702,12 +9038,12 @@ function MatchdayPredictorGame({
|
|
|
8702
9038
|
onBack
|
|
8703
9039
|
}) {
|
|
8704
9040
|
const t = ui.games.predictor;
|
|
8705
|
-
const [homeScore, setHomeScore] = (0,
|
|
8706
|
-
const [awayScore, setAwayScore] = (0,
|
|
8707
|
-
const [firstScorerPlayerId, setFirstScorerPlayerId] = (0,
|
|
8708
|
-
const [lastEdited, setLastEdited] = (0,
|
|
8709
|
-
const [query, setQuery] = (0,
|
|
8710
|
-
const searchId = (0,
|
|
9041
|
+
const [homeScore, setHomeScore] = (0, import_react57.useState)(0);
|
|
9042
|
+
const [awayScore, setAwayScore] = (0, import_react57.useState)(0);
|
|
9043
|
+
const [firstScorerPlayerId, setFirstScorerPlayerId] = (0, import_react57.useState)(null);
|
|
9044
|
+
const [lastEdited, setLastEdited] = (0, import_react57.useState)("home");
|
|
9045
|
+
const [query, setQuery] = (0, import_react57.useState)("");
|
|
9046
|
+
const searchId = (0, import_react57.useId)();
|
|
8711
9047
|
const clientState = parseClientState7(result?.clientStateJson);
|
|
8712
9048
|
const alreadyPlayed = result?.alreadyPlayed === true;
|
|
8713
9049
|
const header = /* @__PURE__ */ (0, import_jsx_runtime85.jsx)(
|
|
@@ -8874,7 +9210,7 @@ function MatchdayPredictorGame({
|
|
|
8874
9210
|
}
|
|
8875
9211
|
|
|
8876
9212
|
// src/components/games/StartingXiGame.tsx
|
|
8877
|
-
var
|
|
9213
|
+
var import_react58 = require("react");
|
|
8878
9214
|
var import_jsx_runtime86 = require("react/jsx-runtime");
|
|
8879
9215
|
var POINTS_PER_STARTER = 8;
|
|
8880
9216
|
var XI_SIZE = 11;
|
|
@@ -8918,10 +9254,10 @@ function StartingXiGame({
|
|
|
8918
9254
|
lockAtUtc
|
|
8919
9255
|
}) {
|
|
8920
9256
|
const t = ui.games.startingXi;
|
|
8921
|
-
const [slotPlayers, setSlotPlayers] = (0,
|
|
8922
|
-
const [active, setActive] = (0,
|
|
8923
|
-
const [query, setQuery] = (0,
|
|
8924
|
-
const searchId = (0,
|
|
9257
|
+
const [slotPlayers, setSlotPlayers] = (0, import_react58.useState)(() => Array(XI_SIZE).fill(null));
|
|
9258
|
+
const [active, setActive] = (0, import_react58.useState)(0);
|
|
9259
|
+
const [query, setQuery] = (0, import_react58.useState)("");
|
|
9260
|
+
const searchId = (0, import_react58.useId)();
|
|
8925
9261
|
const clientState = parseClientState8(result?.clientStateJson);
|
|
8926
9262
|
const alreadyPlayed = result?.alreadyPlayed === true;
|
|
8927
9263
|
const header = /* @__PURE__ */ (0, import_jsx_runtime86.jsx)(
|
|
@@ -9060,7 +9396,7 @@ function StartingXiGame({
|
|
|
9060
9396
|
}
|
|
9061
9397
|
|
|
9062
9398
|
// src/components/games/StatLadderGame.tsx
|
|
9063
|
-
var
|
|
9399
|
+
var import_react59 = require("react");
|
|
9064
9400
|
var import_jsx_runtime87 = require("react/jsx-runtime");
|
|
9065
9401
|
function ladderClue(ladder) {
|
|
9066
9402
|
const mystery = ladder.find((r) => r.rank === 2);
|
|
@@ -9097,9 +9433,9 @@ function StatLadderGame({
|
|
|
9097
9433
|
onBack
|
|
9098
9434
|
}) {
|
|
9099
9435
|
const t = ui.games.statLadder;
|
|
9100
|
-
const [query, setQuery] = (0,
|
|
9101
|
-
const [selectedId, setSelectedId] = (0,
|
|
9102
|
-
const searchId = (0,
|
|
9436
|
+
const [query, setQuery] = (0, import_react59.useState)("");
|
|
9437
|
+
const [selectedId, setSelectedId] = (0, import_react59.useState)(null);
|
|
9438
|
+
const searchId = (0, import_react59.useId)();
|
|
9103
9439
|
const clientState = parseClientState9(result?.clientStateJson);
|
|
9104
9440
|
const revealed = clientState != null;
|
|
9105
9441
|
const header = /* @__PURE__ */ (0, import_jsx_runtime87.jsx)(GameHeader, { title: gameTitle({ gameId: "stat-ladder" }, ui.games.titles), eyebrow: t.eyebrow, onBack, backLabel: ui.back });
|
|
@@ -9305,8 +9641,8 @@ function GameScreenHost({
|
|
|
9305
9641
|
ui
|
|
9306
9642
|
}) {
|
|
9307
9643
|
const { gameId, fixtureId, gameDay = "", lockAtUtc = null } = selected;
|
|
9308
|
-
const [configJson, setConfigJson] = (0,
|
|
9309
|
-
(0,
|
|
9644
|
+
const [configJson, setConfigJson] = (0, import_react60.useState)(null);
|
|
9645
|
+
(0, import_react60.useEffect)(() => {
|
|
9310
9646
|
setConfigJson(null);
|
|
9311
9647
|
if (!conversation) return;
|
|
9312
9648
|
let cancelled = false;
|
|
@@ -9329,12 +9665,12 @@ function GameScreenHost({
|
|
|
9329
9665
|
fixtureId: fixtureId || void 0,
|
|
9330
9666
|
locale: ui.games.lang
|
|
9331
9667
|
});
|
|
9332
|
-
(0,
|
|
9668
|
+
(0, import_react60.useEffect)(() => {
|
|
9333
9669
|
if (conversation) hydrate();
|
|
9334
9670
|
}, [conversation, gameId]);
|
|
9335
|
-
const hydrateRef = (0,
|
|
9671
|
+
const hydrateRef = (0, import_react60.useRef)(hydrate);
|
|
9336
9672
|
hydrateRef.current = hydrate;
|
|
9337
|
-
(0,
|
|
9673
|
+
(0, import_react60.useEffect)(() => {
|
|
9338
9674
|
if (!FIXTURE_GAME_IDS.has(gameId)) return;
|
|
9339
9675
|
if (rawStatus !== "pending") return;
|
|
9340
9676
|
const timerId = setInterval(() => {
|
|
@@ -9447,7 +9783,7 @@ function GameScreenHost({
|
|
|
9447
9783
|
}
|
|
9448
9784
|
|
|
9449
9785
|
// src/components/Leaderboard.tsx
|
|
9450
|
-
var
|
|
9786
|
+
var import_react61 = require("react");
|
|
9451
9787
|
|
|
9452
9788
|
// src/components/LeaderboardRow.tsx
|
|
9453
9789
|
var import_jsx_runtime90 = require("react/jsx-runtime");
|
|
@@ -9532,7 +9868,7 @@ function Leaderboard({
|
|
|
9532
9868
|
ui,
|
|
9533
9869
|
onPlay
|
|
9534
9870
|
}) {
|
|
9535
|
-
const [segment, setSegment] = (0,
|
|
9871
|
+
const [segment, setSegment] = (0, import_react61.useState)("weekly");
|
|
9536
9872
|
const myRow = segment === "weekly" ? data.myWeeklyRow : data.myAllTimeRow;
|
|
9537
9873
|
const offBoard = myRow !== null && myRow !== void 0 && myRow.rank === -1;
|
|
9538
9874
|
const isEmpty = segment === "weekly" ? data.weeklyTop.length === 0 : data.allTimeTop.length === 0;
|
|
@@ -9635,9 +9971,9 @@ function GamesPanel({
|
|
|
9635
9971
|
leaderboardLoading,
|
|
9636
9972
|
refreshHub
|
|
9637
9973
|
}) {
|
|
9638
|
-
const [selected, setSelected] = (0,
|
|
9639
|
-
const [segment, setSegment] = (0,
|
|
9640
|
-
(0,
|
|
9974
|
+
const [selected, setSelected] = (0, import_react62.useState)(null);
|
|
9975
|
+
const [segment, setSegment] = (0, import_react62.useState)("play");
|
|
9976
|
+
(0, import_react62.useEffect)(() => {
|
|
9641
9977
|
ensureGamesFonts();
|
|
9642
9978
|
}, []);
|
|
9643
9979
|
if (!loggedIn) return /* @__PURE__ */ (0, import_jsx_runtime94.jsx)(GamesLoginWall, { ui });
|
|
@@ -9785,8 +10121,7 @@ function Standings({ standings, loading, ui }) {
|
|
|
9785
10121
|
] }, `${gi}-${group.table ?? "none"}`)) });
|
|
9786
10122
|
}
|
|
9787
10123
|
|
|
9788
|
-
// src/components/
|
|
9789
|
-
var import_jsx_runtime97 = require("react/jsx-runtime");
|
|
10124
|
+
// src/components/groupByPosition.ts
|
|
9790
10125
|
function groupByPosition(players) {
|
|
9791
10126
|
const groups = [];
|
|
9792
10127
|
for (const p of players) {
|
|
@@ -9796,26 +10131,412 @@ function groupByPosition(players) {
|
|
|
9796
10131
|
}
|
|
9797
10132
|
return groups;
|
|
9798
10133
|
}
|
|
9799
|
-
|
|
9800
|
-
|
|
9801
|
-
|
|
9802
|
-
|
|
9803
|
-
|
|
9804
|
-
|
|
9805
|
-
|
|
9806
|
-
|
|
9807
|
-
|
|
9808
|
-
|
|
10134
|
+
|
|
10135
|
+
// src/components/labels.ts
|
|
10136
|
+
function positionLabel(ui, name) {
|
|
10137
|
+
switch (name) {
|
|
10138
|
+
case "Goalkeeper":
|
|
10139
|
+
return ui.positionGoalkeeper;
|
|
10140
|
+
case "Defender":
|
|
10141
|
+
return ui.positionDefender;
|
|
10142
|
+
case "Midfielder":
|
|
10143
|
+
return ui.positionMidfielder;
|
|
10144
|
+
case "Attacker":
|
|
10145
|
+
return ui.positionAttacker;
|
|
10146
|
+
default:
|
|
10147
|
+
return name;
|
|
10148
|
+
}
|
|
10149
|
+
}
|
|
10150
|
+
function footLabel(ui, foot) {
|
|
10151
|
+
const v = foot?.trim() ?? "";
|
|
10152
|
+
if (v === "" || v.toUpperCase() === "N/A") return null;
|
|
10153
|
+
switch (v.toLowerCase()) {
|
|
10154
|
+
case "right":
|
|
10155
|
+
return ui.footRight;
|
|
10156
|
+
case "left":
|
|
10157
|
+
return ui.footLeft;
|
|
10158
|
+
case "both":
|
|
10159
|
+
return ui.footBoth;
|
|
10160
|
+
default:
|
|
10161
|
+
return v;
|
|
10162
|
+
}
|
|
10163
|
+
}
|
|
10164
|
+
var GROUP_CODE = { Goalkeeper: "GK", Defender: "DF", Midfielder: "MF", Attacker: "FW" };
|
|
10165
|
+
function positionShort(code, positionName) {
|
|
10166
|
+
const c = code?.trim().toUpperCase() ?? "";
|
|
10167
|
+
if (c !== "") return c === "CF" || c === "SS" ? "ST" : c;
|
|
10168
|
+
return positionName !== null && GROUP_CODE[positionName] || "\u2013";
|
|
10169
|
+
}
|
|
10170
|
+
function statsEyebrow(ui, season, competition, matches) {
|
|
10171
|
+
if (season === null || competition === null || matches === null || matches <= 0) return null;
|
|
10172
|
+
return ui.squadStatsEyebrow(season, competition, matches);
|
|
9809
10173
|
}
|
|
9810
10174
|
|
|
9811
|
-
// src/components/
|
|
9812
|
-
var
|
|
10175
|
+
// src/components/SquadStats.tsx
|
|
10176
|
+
var import_jsx_runtime97 = require("react/jsx-runtime");
|
|
10177
|
+
function leader(stats, pick) {
|
|
10178
|
+
let best = null;
|
|
10179
|
+
for (const p of stats) {
|
|
10180
|
+
if (pick(p) <= 0) continue;
|
|
10181
|
+
if (best === null || pick(p) > pick(best) || pick(p) === pick(best) && p.minutesPlayed < best.minutesPlayed) best = p;
|
|
10182
|
+
}
|
|
10183
|
+
return best;
|
|
10184
|
+
}
|
|
10185
|
+
function ratingClass(rating) {
|
|
10186
|
+
if (rating === null) return "ss-w-sq-c36 ss-w-sq-rtg-none";
|
|
10187
|
+
return Number(rating.toFixed(1)) >= 7 ? "ss-w-sq-c36 ss-w-sq-rtg ss-w-pos-ink" : "ss-w-sq-c36 ss-w-sq-rtg";
|
|
10188
|
+
}
|
|
10189
|
+
function SquadStats({ stats, loading, ui, onSelectPlayer }) {
|
|
10190
|
+
if (stats === null && loading) return /* @__PURE__ */ (0, import_jsx_runtime97.jsx)("div", { className: "ss-w-mon-list" });
|
|
10191
|
+
if (stats === null || stats.length === 0) return /* @__PURE__ */ (0, import_jsx_runtime97.jsx)("div", { className: "ss-w-mon-empty", children: ui.clubSquadStatsEmpty });
|
|
10192
|
+
const scorer = leader(stats, (p) => p.goals);
|
|
10193
|
+
const assister = leader(stats, (p) => p.assists);
|
|
10194
|
+
const footer = [
|
|
10195
|
+
scorer && ui.squadTopScorer(scorer.playerName, scorer.goals),
|
|
10196
|
+
assister && ui.squadTopAssists(assister.playerName, assister.assists)
|
|
10197
|
+
].filter((part) => !!part).join(" \xB7 ");
|
|
10198
|
+
return /* @__PURE__ */ (0, import_jsx_runtime97.jsxs)("div", { className: "ss-w-mon-list ss-w-sq-stats", children: [
|
|
10199
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsxs)("div", { className: "ss-w-sq-card", children: [
|
|
10200
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsxs)("div", { className: "ss-w-sq-row ss-w-sq-head", "aria-hidden": "true", children: [
|
|
10201
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-name" }),
|
|
10202
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-pos", children: ui.statHeadPos }),
|
|
10203
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c30", children: ui.statColApps }),
|
|
10204
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c36", children: ui.statHeadMins }),
|
|
10205
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c20", children: ui.statHeadGoals }),
|
|
10206
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c20", children: ui.statHeadAssists }),
|
|
10207
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c20 ss-w-sq-yr", children: ui.statHeadYellow }),
|
|
10208
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c20 ss-w-sq-yr", children: ui.statHeadRed }),
|
|
10209
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c36", children: ui.statHeadRating })
|
|
10210
|
+
] }),
|
|
10211
|
+
stats.map((p) => /* @__PURE__ */ (0, import_jsx_runtime97.jsxs)("button", { type: "button", className: "ss-w-sq-row ss-w-sq-tap", onClick: () => onSelectPlayer(p.playerId), children: [
|
|
10212
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsxs)("span", { className: "ss-w-sq-player", children: [
|
|
10213
|
+
p.jerseyNumber !== null && /* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-badge", children: p.jerseyNumber }),
|
|
10214
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-name ss-w-sq-name-1", children: p.playerName })
|
|
10215
|
+
] }),
|
|
10216
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-pos", children: positionShort(p.positionCode, p.positionName) }),
|
|
10217
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c30", children: p.appearances }),
|
|
10218
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c36", children: p.minutesPlayed }),
|
|
10219
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c20", children: p.goals }),
|
|
10220
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c20", children: p.assists }),
|
|
10221
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c20 ss-w-sq-yr", children: p.yellowCards }),
|
|
10222
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: "ss-w-sq-c20 ss-w-sq-yr", children: p.redCards }),
|
|
10223
|
+
/* @__PURE__ */ (0, import_jsx_runtime97.jsx)("span", { className: ratingClass(p.averageRating), children: p.averageRating === null ? "\u2013" : p.averageRating.toFixed(1) })
|
|
10224
|
+
] }, p.playerId))
|
|
10225
|
+
] }),
|
|
10226
|
+
footer !== "" && /* @__PURE__ */ (0, import_jsx_runtime97.jsx)("div", { className: "ss-w-sq-foot", children: footer })
|
|
10227
|
+
] });
|
|
10228
|
+
}
|
|
10229
|
+
|
|
10230
|
+
// src/components/Squad.tsx
|
|
9813
10231
|
var import_jsx_runtime98 = require("react/jsx-runtime");
|
|
10232
|
+
function Squad({ squad, loading, ui, view, onToggleView, stats, statsLoading, seasonName = null, competitionName = null, matchesPlayed = null, onSelectPlayer }) {
|
|
10233
|
+
const eyebrow = view === "stats" ? statsEyebrow(ui, seasonName, competitionName, matchesPlayed) : null;
|
|
10234
|
+
const toggle = /* @__PURE__ */ (0, import_jsx_runtime98.jsxs)("div", { className: "ss-w-sq-bar", children: [
|
|
10235
|
+
eyebrow !== null && /* @__PURE__ */ (0, import_jsx_runtime98.jsx)("div", { className: "ss-w-sq-eyebrow", children: eyebrow }),
|
|
10236
|
+
/* @__PURE__ */ (0, import_jsx_runtime98.jsx)("div", { className: "ss-w-sq-seg", role: "group", children: ["roster", "stats"].map((v) => /* @__PURE__ */ (0, import_jsx_runtime98.jsx)(
|
|
10237
|
+
"button",
|
|
10238
|
+
{
|
|
10239
|
+
type: "button",
|
|
10240
|
+
className: "ss-w-sq-seg-btn",
|
|
10241
|
+
"aria-pressed": view === v,
|
|
10242
|
+
onClick: () => {
|
|
10243
|
+
if (view !== v) onToggleView();
|
|
10244
|
+
},
|
|
10245
|
+
children: v === "roster" ? ui.squadViewRoster : ui.squadViewStats
|
|
10246
|
+
},
|
|
10247
|
+
v
|
|
10248
|
+
)) })
|
|
10249
|
+
] });
|
|
10250
|
+
if (view === "stats") {
|
|
10251
|
+
return /* @__PURE__ */ (0, import_jsx_runtime98.jsxs)(import_jsx_runtime98.Fragment, { children: [
|
|
10252
|
+
toggle,
|
|
10253
|
+
/* @__PURE__ */ (0, import_jsx_runtime98.jsx)(SquadStats, { stats, loading: statsLoading, ui, onSelectPlayer })
|
|
10254
|
+
] });
|
|
10255
|
+
}
|
|
10256
|
+
if (squad === null && loading) return /* @__PURE__ */ (0, import_jsx_runtime98.jsxs)(import_jsx_runtime98.Fragment, { children: [
|
|
10257
|
+
toggle,
|
|
10258
|
+
/* @__PURE__ */ (0, import_jsx_runtime98.jsx)("div", { className: "ss-w-mon-list" })
|
|
10259
|
+
] });
|
|
10260
|
+
if (squad === null || squad.length === 0) return /* @__PURE__ */ (0, import_jsx_runtime98.jsxs)(import_jsx_runtime98.Fragment, { children: [
|
|
10261
|
+
toggle,
|
|
10262
|
+
/* @__PURE__ */ (0, import_jsx_runtime98.jsx)("div", { className: "ss-w-mon-empty", children: ui.clubSquadEmpty })
|
|
10263
|
+
] });
|
|
10264
|
+
return /* @__PURE__ */ (0, import_jsx_runtime98.jsxs)(import_jsx_runtime98.Fragment, { children: [
|
|
10265
|
+
toggle,
|
|
10266
|
+
/* @__PURE__ */ (0, import_jsx_runtime98.jsx)("div", { className: "ss-w-mon-list", children: groupByPosition(squad).map((group, gi) => /* @__PURE__ */ (0, import_jsx_runtime98.jsxs)("div", { children: [
|
|
10267
|
+
group.positionName && /* @__PURE__ */ (0, import_jsx_runtime98.jsx)("div", { className: "ss-w-club-eyebrow", children: positionLabel(ui, group.positionName) }),
|
|
10268
|
+
group.items.map((p) => /* @__PURE__ */ (0, import_jsx_runtime98.jsxs)("button", { type: "button", className: "ss-w-sq-row ss-w-sq-tap", onClick: () => onSelectPlayer(p.playerId), children: [
|
|
10269
|
+
/* @__PURE__ */ (0, import_jsx_runtime98.jsx)("span", { className: "ss-w-sq-num", children: p.jerseyNumber ?? "" }),
|
|
10270
|
+
/* @__PURE__ */ (0, import_jsx_runtime98.jsx)("span", { className: "ss-w-sq-name", children: p.playerName })
|
|
10271
|
+
] }, p.playerId))
|
|
10272
|
+
] }, `${gi}-${group.positionName ?? "none"}`)) })
|
|
10273
|
+
] });
|
|
10274
|
+
}
|
|
10275
|
+
|
|
10276
|
+
// src/components/PlayerPhoto.tsx
|
|
10277
|
+
var import_react63 = require("react");
|
|
10278
|
+
var import_jsx_runtime99 = require("react/jsx-runtime");
|
|
10279
|
+
function PlayerPhoto({ photoUrl, jerseyNumber, size }) {
|
|
10280
|
+
const [failed, setFailed] = (0, import_react63.useState)(false);
|
|
10281
|
+
const box = { width: size, height: size };
|
|
10282
|
+
if (photoUrl && !failed) {
|
|
10283
|
+
return /* @__PURE__ */ (0, import_jsx_runtime99.jsx)("img", { className: "ss-w-pd-photo", style: box, src: photoUrl, alt: "", "aria-hidden": "true", onError: () => setFailed(true) });
|
|
10284
|
+
}
|
|
10285
|
+
return /* @__PURE__ */ (0, import_jsx_runtime99.jsx)("span", { className: "ss-w-pd-photo ss-w-pd-avatar", style: { ...box, fontSize: Math.round(size * 0.35) }, "aria-hidden": "true", children: jerseyNumber ?? "" });
|
|
10286
|
+
}
|
|
10287
|
+
|
|
10288
|
+
// src/components/MiniPitch.tsx
|
|
10289
|
+
var import_jsx_runtime100 = require("react/jsx-runtime");
|
|
10290
|
+
var SPOT = {
|
|
10291
|
+
GK: [50, 90],
|
|
10292
|
+
CB: [50, 75],
|
|
10293
|
+
LB: [18, 70],
|
|
10294
|
+
RB: [82, 70],
|
|
10295
|
+
LWB: [15, 58],
|
|
10296
|
+
RWB: [85, 58],
|
|
10297
|
+
DM: [50, 60],
|
|
10298
|
+
CM: [50, 48],
|
|
10299
|
+
LM: [18, 45],
|
|
10300
|
+
RM: [82, 45],
|
|
10301
|
+
AM: [50, 32],
|
|
10302
|
+
LW: [20, 25],
|
|
10303
|
+
RW: [80, 25],
|
|
10304
|
+
CF: [50, 14],
|
|
10305
|
+
SS: [50, 14],
|
|
10306
|
+
ST: [50, 14]
|
|
10307
|
+
};
|
|
10308
|
+
function MiniPitch({ positionCode }) {
|
|
10309
|
+
const spot = SPOT[positionCode?.trim().toUpperCase() ?? ""];
|
|
10310
|
+
if (spot === void 0) return null;
|
|
10311
|
+
return /* @__PURE__ */ (0, import_jsx_runtime100.jsx)("div", { className: "ss-w-pd-pitch", "aria-hidden": "true", children: /* @__PURE__ */ (0, import_jsx_runtime100.jsx)("div", { className: "ss-w-pd-pitch-dot", style: { left: `${spot[0]}%`, top: `${spot[1]}%` } }) });
|
|
10312
|
+
}
|
|
10313
|
+
|
|
10314
|
+
// src/components/PerformanceBars.tsx
|
|
10315
|
+
var import_react64 = require("react");
|
|
10316
|
+
var import_jsx_runtime101 = require("react/jsx-runtime");
|
|
10317
|
+
var GROUPS = ["shooting", "passing", "possession", "defending"];
|
|
10318
|
+
function finite3(v) {
|
|
10319
|
+
return typeof v === "number" && Number.isFinite(v) ? v : null;
|
|
10320
|
+
}
|
|
10321
|
+
function valueOf(m, mode) {
|
|
10322
|
+
return finite3(mode === "total" ? m.total : m.per90);
|
|
10323
|
+
}
|
|
10324
|
+
function rankOf(m, mode) {
|
|
10325
|
+
const r = finite3(mode === "total" ? m.totalRank : m.per90Rank);
|
|
10326
|
+
return r === null ? null : Math.min(100, Math.max(0, Math.round(r)));
|
|
10327
|
+
}
|
|
10328
|
+
function format(m, v, mode) {
|
|
10329
|
+
if (m.isPercent) return `${v.toFixed(1)}%`;
|
|
10330
|
+
if (mode === "per90" || m.key === "xg") return v.toFixed(2);
|
|
10331
|
+
return String(Math.round(v));
|
|
10332
|
+
}
|
|
10333
|
+
function band(rank) {
|
|
10334
|
+
if (rank >= 67) return "pos";
|
|
10335
|
+
if (rank >= 34) return "warn";
|
|
10336
|
+
return "neg";
|
|
10337
|
+
}
|
|
10338
|
+
function groupTitle(ui, g) {
|
|
10339
|
+
switch (g) {
|
|
10340
|
+
case "shooting":
|
|
10341
|
+
return ui.perfGroupShooting;
|
|
10342
|
+
case "passing":
|
|
10343
|
+
return ui.perfGroupPassing;
|
|
10344
|
+
case "possession":
|
|
10345
|
+
return ui.perfGroupPossession;
|
|
10346
|
+
case "defending":
|
|
10347
|
+
return ui.perfGroupDefending;
|
|
10348
|
+
}
|
|
10349
|
+
}
|
|
10350
|
+
function unrankedLine(ui, reason) {
|
|
10351
|
+
switch (reason) {
|
|
10352
|
+
case "cohort":
|
|
10353
|
+
return ui.perfUnrankedCohort;
|
|
10354
|
+
case "noLeague":
|
|
10355
|
+
return ui.perfUnrankedNoLeague;
|
|
10356
|
+
default:
|
|
10357
|
+
return ui.perfUnranked;
|
|
10358
|
+
}
|
|
10359
|
+
}
|
|
10360
|
+
function PerformanceBars({ performance, competitionName, strings }) {
|
|
10361
|
+
const [mode, setMode] = (0, import_react64.useState)("total");
|
|
10362
|
+
const labelled = performance.metrics.filter((m) => Object.prototype.hasOwnProperty.call(strings.perfMetric, m.key));
|
|
10363
|
+
if (!labelled.some((m) => valueOf(m, "total") !== null || valueOf(m, "per90") !== null)) return null;
|
|
10364
|
+
const subtitle = !performance.ranked ? unrankedLine(strings, performance.unrankedReason) : competitionName ? strings.perfRankedAgainst(competitionName, performance.positionGroup) : null;
|
|
10365
|
+
const cards = GROUPS.map((g) => {
|
|
10366
|
+
const rows = labelled.filter((m) => m.group === g && valueOf(m, mode) !== null);
|
|
10367
|
+
if (rows.length === 0) return null;
|
|
10368
|
+
return /* @__PURE__ */ (0, import_jsx_runtime101.jsxs)("div", { className: "ss-w-pd-card ss-w-pd-perf-card", children: [
|
|
10369
|
+
/* @__PURE__ */ (0, import_jsx_runtime101.jsx)("div", { className: "ss-w-pd-perf-group", children: groupTitle(strings, g) }),
|
|
10370
|
+
rows.map((m) => {
|
|
10371
|
+
const v = valueOf(m, mode);
|
|
10372
|
+
const rank = performance.ranked ? rankOf(m, mode) : null;
|
|
10373
|
+
return /* @__PURE__ */ (0, import_jsx_runtime101.jsxs)("div", { className: "ss-w-pd-bar-row", children: [
|
|
10374
|
+
/* @__PURE__ */ (0, import_jsx_runtime101.jsxs)("div", { className: "ss-w-pd-bar-top", children: [
|
|
10375
|
+
/* @__PURE__ */ (0, import_jsx_runtime101.jsx)("span", { className: "ss-w-pd-bar-label", children: strings.perfMetric[m.key] }),
|
|
10376
|
+
/* @__PURE__ */ (0, import_jsx_runtime101.jsx)("span", { className: "ss-w-pd-bar-value", children: format(m, v, mode) })
|
|
10377
|
+
] }),
|
|
10378
|
+
rank !== null && /* @__PURE__ */ (0, import_jsx_runtime101.jsx)("div", { className: "ss-w-pd-track", children: /* @__PURE__ */ (0, import_jsx_runtime101.jsx)("div", { className: `ss-w-pd-fill ss-w-pd-fill--${band(rank)}`, style: { width: `${rank}%` } }) })
|
|
10379
|
+
] }, m.key);
|
|
10380
|
+
})
|
|
10381
|
+
] }, g);
|
|
10382
|
+
});
|
|
10383
|
+
return /* @__PURE__ */ (0, import_jsx_runtime101.jsxs)("div", { children: [
|
|
10384
|
+
/* @__PURE__ */ (0, import_jsx_runtime101.jsxs)("div", { className: "ss-w-pd-perf-head", children: [
|
|
10385
|
+
/* @__PURE__ */ (0, import_jsx_runtime101.jsx)("div", { className: "ss-w-pd-eyebrow", children: strings.perfTitle }),
|
|
10386
|
+
/* @__PURE__ */ (0, import_jsx_runtime101.jsx)("div", { className: "ss-w-pd-seg", role: "group", children: ["total", "per90"].map((m) => /* @__PURE__ */ (0, import_jsx_runtime101.jsx)("button", { type: "button", className: "ss-w-pd-seg-btn", "aria-pressed": mode === m, onClick: () => setMode(m), children: m === "total" ? strings.perfTotal : strings.perfPer90 }, m)) })
|
|
10387
|
+
] }),
|
|
10388
|
+
subtitle !== null && /* @__PURE__ */ (0, import_jsx_runtime101.jsx)("div", { className: "ss-w-pd-perf-sub", children: subtitle }),
|
|
10389
|
+
/* @__PURE__ */ (0, import_jsx_runtime101.jsx)("div", { className: "ss-w-pd-perf-cards", children: cards })
|
|
10390
|
+
] });
|
|
10391
|
+
}
|
|
10392
|
+
|
|
10393
|
+
// src/components/PlayerDetail.tsx
|
|
10394
|
+
var import_jsx_runtime102 = require("react/jsx-runtime");
|
|
10395
|
+
var DASH = "\u2014";
|
|
10396
|
+
function ageFrom(dobMs) {
|
|
10397
|
+
if (dobMs === null) return DASH;
|
|
10398
|
+
const dob = new Date(dobMs);
|
|
10399
|
+
const now = /* @__PURE__ */ new Date();
|
|
10400
|
+
let age = now.getUTCFullYear() - dob.getUTCFullYear();
|
|
10401
|
+
const beforeBirthday = now.getUTCMonth() < dob.getUTCMonth() || now.getUTCMonth() === dob.getUTCMonth() && now.getUTCDate() < dob.getUTCDate();
|
|
10402
|
+
if (beforeBirthday) age--;
|
|
10403
|
+
return String(age);
|
|
10404
|
+
}
|
|
10405
|
+
function validMs(ms) {
|
|
10406
|
+
return typeof ms === "number" && Number.isFinite(ms) && ms > 0 ? ms : null;
|
|
10407
|
+
}
|
|
10408
|
+
function ratingTone(rounded) {
|
|
10409
|
+
if (rounded >= 7) return "pos";
|
|
10410
|
+
if (rounded >= 6) return "warn";
|
|
10411
|
+
return "neg";
|
|
10412
|
+
}
|
|
10413
|
+
function Bio({ label, value }) {
|
|
10414
|
+
return /* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { className: "ss-w-pd-bio-item", children: [
|
|
10415
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("span", { className: "ss-w-pd-faint", children: label }),
|
|
10416
|
+
" ",
|
|
10417
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("span", { children: value })
|
|
10418
|
+
] });
|
|
10419
|
+
}
|
|
10420
|
+
function Tile({ label, value, pos }) {
|
|
10421
|
+
return /* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { className: "ss-w-pd-tile", children: [
|
|
10422
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-tile-label", children: label }),
|
|
10423
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: pos ? "ss-w-pd-tile-value ss-w-pd-pos-ink" : "ss-w-pd-tile-value", children: value })
|
|
10424
|
+
] });
|
|
10425
|
+
}
|
|
10426
|
+
function AvailabilityCard({ ui, next, availability }) {
|
|
10427
|
+
let note = null;
|
|
10428
|
+
let pill = null;
|
|
10429
|
+
if (availability !== null) {
|
|
10430
|
+
if (availability.status === "available") {
|
|
10431
|
+
note = ui.availabilityNoConcerns;
|
|
10432
|
+
pill = { text: ui.availabilityAvailable, tone: "pos" };
|
|
10433
|
+
} else {
|
|
10434
|
+
const back = validMs(availability.expectedReturnUnixMs);
|
|
10435
|
+
note = [availability.detail?.trim() || null, back === null ? null : ui.availabilityBack(back)].filter(Boolean).join(" \xB7 ") || null;
|
|
10436
|
+
pill = availability.status === "injured" ? { text: ui.availabilityInjured, tone: "neg" } : availability.status === "suspended" ? { text: ui.availabilitySuspended, tone: "warn" } : { text: ui.availabilityUnavailable, tone: "warn" };
|
|
10437
|
+
}
|
|
10438
|
+
}
|
|
10439
|
+
return /* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { className: "ss-w-pd-card ss-w-pd-avail", children: [
|
|
10440
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { className: "ss-w-pd-avail-text", children: [
|
|
10441
|
+
next !== null && /* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-avail-next", children: ui.availabilityNext(next.opponentName, next.isHome, validMs(next.kickoffUnixMs)) }),
|
|
10442
|
+
note !== null && /* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-avail-note", children: note })
|
|
10443
|
+
] }),
|
|
10444
|
+
pill !== null && /* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: `ss-w-pd-pill ss-w-pd-pill--${pill.tone}`, children: pill.text })
|
|
10445
|
+
] });
|
|
10446
|
+
}
|
|
10447
|
+
function MatchRow({ ui, row }) {
|
|
10448
|
+
const date = validMs(row.kickoffUnixMs);
|
|
10449
|
+
const extras = [
|
|
10450
|
+
row.goals > 0 ? `${row.goals}${ui.statHeadGoals}` : null,
|
|
10451
|
+
row.assists > 0 ? `${row.assists}${ui.statHeadAssists}` : null,
|
|
10452
|
+
row.yellowCards > 0 ? `${row.yellowCards}${ui.statHeadYellow}` : null,
|
|
10453
|
+
row.sentOff ? ui.statHeadRed : null
|
|
10454
|
+
].filter((x) => x !== null);
|
|
10455
|
+
const sub = [`${ui.resultLetter[row.result]} ${row.goalsFor}\u2013${row.goalsAgainst}`, `${row.minutes}\u2032`, ...extras].join(" \xB7 ");
|
|
10456
|
+
const rating = typeof row.rating === "number" && Number.isFinite(row.rating) ? Math.round(row.rating * 10) / 10 : null;
|
|
10457
|
+
const pillTone = row.result === "W" ? "pos" : row.result === "L" ? "neg" : "draw";
|
|
10458
|
+
return /* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { className: "ss-w-pd-match", children: [
|
|
10459
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-match-date", children: date === null ? "" : ui.logShortDate(date) }),
|
|
10460
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { className: "ss-w-pd-match-main", children: [
|
|
10461
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-match-opp", children: ui.matchLogOpponent(row.opponentName, row.isHome) }),
|
|
10462
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-match-sub", children: sub })
|
|
10463
|
+
] }),
|
|
10464
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: `ss-w-pd-pill ss-w-pd-pill--${pillTone}`, children: ui.resultLetter[row.result] }),
|
|
10465
|
+
rating === null ? /* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-chip-empty" }) : /* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: `ss-w-pd-chip ss-w-pd-chip--${ratingTone(rating)}`, children: rating.toFixed(1) })
|
|
10466
|
+
] });
|
|
10467
|
+
}
|
|
10468
|
+
function PlayerDetail({ detail, loading, ui, seasonName, onClose }) {
|
|
10469
|
+
const back = /* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("button", { type: "button", className: "ss-w-pd-back", onClick: onClose, children: [
|
|
10470
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("svg", { width: "16", height: "16", viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round", "aria-hidden": "true", children: /* @__PURE__ */ (0, import_jsx_runtime102.jsx)("path", { d: "M15 18l-6-6 6-6" }) }),
|
|
10471
|
+
ui.clubPlayerBack
|
|
10472
|
+
] });
|
|
10473
|
+
if (detail === null) {
|
|
10474
|
+
return loading ? /* @__PURE__ */ (0, import_jsx_runtime102.jsxs)(import_jsx_runtime102.Fragment, { children: [
|
|
10475
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-bar", children: back }),
|
|
10476
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-mon-list" })
|
|
10477
|
+
] }) : /* @__PURE__ */ (0, import_jsx_runtime102.jsxs)(import_jsx_runtime102.Fragment, { children: [
|
|
10478
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-bar", children: back }),
|
|
10479
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-mon-empty", children: ui.clubPlayerDetailEmpty })
|
|
10480
|
+
] });
|
|
10481
|
+
}
|
|
10482
|
+
const s = detail.seasonStats;
|
|
10483
|
+
const foot = footLabel(ui, detail.foot);
|
|
10484
|
+
const position = positionLabel(ui, detail.positionName);
|
|
10485
|
+
const subLine = [detail.teamName?.trim() || null, position].filter(Boolean).join(" \xB7 ");
|
|
10486
|
+
const competition = detail.competitionName?.trim() || null;
|
|
10487
|
+
const eyebrow = seasonName === null ? null : competition === null ? ui.detailSeason.replace("{season}", seasonName) : `${seasonName} ${competition}`;
|
|
10488
|
+
const rating = typeof s.averageRating === "number" && Number.isFinite(s.averageRating) ? s.averageRating : null;
|
|
10489
|
+
const next = detail.nextFixture ?? null;
|
|
10490
|
+
const availability = detail.availability ?? null;
|
|
10491
|
+
const log = detail.matchLog ?? [];
|
|
10492
|
+
return /* @__PURE__ */ (0, import_jsx_runtime102.jsxs)(import_jsx_runtime102.Fragment, { children: [
|
|
10493
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-bar", children: back }),
|
|
10494
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { className: "ss-w-mon-list ss-w-pd-list", children: [
|
|
10495
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { className: "ss-w-pd-card ss-w-pd-profile", children: [
|
|
10496
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)(PlayerPhoto, { photoUrl: detail.photoUrl, jerseyNumber: detail.jerseyNumber, size: 52 }, detail.photoUrl ?? ""),
|
|
10497
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { className: "ss-w-pd-profile-main", children: [
|
|
10498
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-name", children: detail.playerName }),
|
|
10499
|
+
subLine !== "" && /* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-sub", children: subLine }),
|
|
10500
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { className: "ss-w-pd-bio", children: [
|
|
10501
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)(Bio, { label: ui.detailAge, value: ageFrom(detail.dateOfBirthUnixMs) }),
|
|
10502
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)(Bio, { label: ui.detailHeight, value: detail.heightCm === null ? DASH : `${detail.heightCm} cm` }),
|
|
10503
|
+
foot !== null && /* @__PURE__ */ (0, import_jsx_runtime102.jsx)(Bio, { label: ui.detailFoot, value: foot }),
|
|
10504
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)(Bio, { label: ui.detailNatShort, value: detail.nationality ?? DASH })
|
|
10505
|
+
] })
|
|
10506
|
+
] }),
|
|
10507
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)(MiniPitch, { positionCode: detail.positionCode })
|
|
10508
|
+
] }),
|
|
10509
|
+
(next !== null || availability !== null) && /* @__PURE__ */ (0, import_jsx_runtime102.jsx)(AvailabilityCard, { ui, next, availability }),
|
|
10510
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { children: [
|
|
10511
|
+
eyebrow !== null && /* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-eyebrow ss-w-pd-eyebrow--block", children: eyebrow }),
|
|
10512
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { className: "ss-w-pd-tiles", children: [
|
|
10513
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)(Tile, { label: ui.statColGoals, value: String(s.goals) }),
|
|
10514
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)(Tile, { label: ui.statColAssists, value: String(s.assists) }),
|
|
10515
|
+
typeof s.starts === "number" && /* @__PURE__ */ (0, import_jsx_runtime102.jsx)(Tile, { label: ui.detailStarted, value: String(s.starts) }),
|
|
10516
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)(Tile, { label: ui.detailMatches, value: String(s.appearances) }),
|
|
10517
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)(Tile, { label: ui.statColMinutes, value: String(s.minutesPlayed) }),
|
|
10518
|
+
rating !== null && /* @__PURE__ */ (0, import_jsx_runtime102.jsx)(Tile, { label: ui.statColRating, value: rating.toFixed(2), pos: Math.round(rating * 100) / 100 >= 7 }),
|
|
10519
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)(Tile, { label: ui.detailYellows, value: String(s.yellowCards) }),
|
|
10520
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)(Tile, { label: ui.detailReds, value: String(s.redCards) })
|
|
10521
|
+
] })
|
|
10522
|
+
] }),
|
|
10523
|
+
detail.performance != null && /* @__PURE__ */ (0, import_jsx_runtime102.jsx)(PerformanceBars, { performance: detail.performance, competitionName: competition, strings: ui }),
|
|
10524
|
+
log.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime102.jsxs)("div", { children: [
|
|
10525
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-eyebrow ss-w-pd-eyebrow--block", children: ui.matchLogTitle }),
|
|
10526
|
+
/* @__PURE__ */ (0, import_jsx_runtime102.jsx)("div", { className: "ss-w-pd-card ss-w-pd-log", children: log.map((row) => /* @__PURE__ */ (0, import_jsx_runtime102.jsx)(MatchRow, { ui, row }, row.matchId)) })
|
|
10527
|
+
] })
|
|
10528
|
+
] })
|
|
10529
|
+
] });
|
|
10530
|
+
}
|
|
10531
|
+
|
|
10532
|
+
// src/components/PresetSpeedDial.tsx
|
|
10533
|
+
var import_react65 = require("react");
|
|
10534
|
+
var import_jsx_runtime103 = require("react/jsx-runtime");
|
|
9814
10535
|
function PresetSpeedDial({ expanded, showDot, strings, onToggle, onOpen, rootRef, buttonRef }) {
|
|
9815
|
-
const pillsId = (0,
|
|
10536
|
+
const pillsId = (0, import_react65.useId)();
|
|
9816
10537
|
const tabIndex = expanded ? 0 : -1;
|
|
9817
|
-
return /* @__PURE__ */ (0,
|
|
9818
|
-
/* @__PURE__ */ (0,
|
|
10538
|
+
return /* @__PURE__ */ (0, import_jsx_runtime103.jsxs)("div", { ref: rootRef, className: "ss-w-dial", children: [
|
|
10539
|
+
/* @__PURE__ */ (0, import_jsx_runtime103.jsxs)(
|
|
9819
10540
|
"button",
|
|
9820
10541
|
{
|
|
9821
10542
|
ref: buttonRef,
|
|
@@ -9826,36 +10547,36 @@ function PresetSpeedDial({ expanded, showDot, strings, onToggle, onOpen, rootRef
|
|
|
9826
10547
|
"aria-label": strings.dialName,
|
|
9827
10548
|
onClick: onToggle,
|
|
9828
10549
|
children: [
|
|
9829
|
-
/* @__PURE__ */ (0,
|
|
9830
|
-
/* @__PURE__ */ (0,
|
|
9831
|
-
showDot && !expanded ? /* @__PURE__ */ (0,
|
|
10550
|
+
/* @__PURE__ */ (0, import_jsx_runtime103.jsx)("span", { className: "ss-w-dial-icon ss-w-dial-icon--open", children: /* @__PURE__ */ (0, import_jsx_runtime103.jsx)(SlidersIcon, {}) }),
|
|
10551
|
+
/* @__PURE__ */ (0, import_jsx_runtime103.jsx)("span", { className: "ss-w-dial-icon ss-w-dial-icon--close", children: /* @__PURE__ */ (0, import_jsx_runtime103.jsx)(CloseIcon, {}) }),
|
|
10552
|
+
showDot && !expanded ? /* @__PURE__ */ (0, import_jsx_runtime103.jsx)("span", { className: "ss-w-dial-dot", "aria-hidden": "true" }) : null
|
|
9832
10553
|
]
|
|
9833
10554
|
}
|
|
9834
10555
|
),
|
|
9835
|
-
/* @__PURE__ */ (0,
|
|
9836
|
-
/* @__PURE__ */ (0,
|
|
9837
|
-
/* @__PURE__ */ (0,
|
|
9838
|
-
/* @__PURE__ */ (0,
|
|
10556
|
+
/* @__PURE__ */ (0, import_jsx_runtime103.jsxs)("div", { id: pillsId, className: "ss-w-dial-pills", "data-open": expanded ? "" : void 0, children: [
|
|
10557
|
+
/* @__PURE__ */ (0, import_jsx_runtime103.jsxs)("button", { type: "button", className: "ss-w-dial-pill", tabIndex, onClick: () => onOpen("numbers"), children: [
|
|
10558
|
+
/* @__PURE__ */ (0, import_jsx_runtime103.jsx)(SlidersIcon, {}),
|
|
10559
|
+
/* @__PURE__ */ (0, import_jsx_runtime103.jsx)("span", { className: "ss-w-dial-pill-label", children: strings.setNumbers })
|
|
9839
10560
|
] }),
|
|
9840
|
-
/* @__PURE__ */ (0,
|
|
9841
|
-
/* @__PURE__ */ (0,
|
|
9842
|
-
/* @__PURE__ */ (0,
|
|
10561
|
+
/* @__PURE__ */ (0, import_jsx_runtime103.jsxs)("button", { type: "button", className: "ss-w-dial-pill", tabIndex, onClick: () => onOpen("combo"), children: [
|
|
10562
|
+
/* @__PURE__ */ (0, import_jsx_runtime103.jsx)(ComboIcon, {}),
|
|
10563
|
+
/* @__PURE__ */ (0, import_jsx_runtime103.jsx)("span", { className: "ss-w-dial-pill-label", children: strings.buildCombo })
|
|
9843
10564
|
] })
|
|
9844
10565
|
] })
|
|
9845
10566
|
] });
|
|
9846
10567
|
}
|
|
9847
10568
|
|
|
9848
10569
|
// src/components/PresetTools.tsx
|
|
9849
|
-
var
|
|
9850
|
-
var
|
|
10570
|
+
var import_react66 = require("react");
|
|
10571
|
+
var import_jsx_runtime104 = require("react/jsx-runtime");
|
|
9851
10572
|
var FOCUSABLE = 'button:not([disabled]), [href], input:not([disabled]), textarea:not([disabled]), [tabindex]:not([tabindex="-1"])';
|
|
9852
10573
|
function PresetToolModal({ title, closeLabel, onClose, children, footer }) {
|
|
9853
|
-
const dialogRef = (0,
|
|
9854
|
-
const titleId = (0,
|
|
9855
|
-
(0,
|
|
10574
|
+
const dialogRef = (0, import_react66.useRef)(null);
|
|
10575
|
+
const titleId = (0, import_react66.useId)();
|
|
10576
|
+
(0, import_react66.useEffect)(() => {
|
|
9856
10577
|
dialogRef.current?.focus();
|
|
9857
10578
|
}, []);
|
|
9858
|
-
(0,
|
|
10579
|
+
(0, import_react66.useEffect)(() => {
|
|
9859
10580
|
const onKey = (e) => {
|
|
9860
10581
|
if (e.key !== "Escape") return;
|
|
9861
10582
|
e.stopPropagation();
|
|
@@ -9885,79 +10606,79 @@ function PresetToolModal({ title, closeLabel, onClose, children, footer }) {
|
|
|
9885
10606
|
first.focus();
|
|
9886
10607
|
}
|
|
9887
10608
|
};
|
|
9888
|
-
return /* @__PURE__ */ (0,
|
|
9889
|
-
/* @__PURE__ */ (0,
|
|
9890
|
-
/* @__PURE__ */ (0,
|
|
9891
|
-
/* @__PURE__ */ (0,
|
|
10609
|
+
return /* @__PURE__ */ (0, import_jsx_runtime104.jsx)("div", { className: "ss-w-tool-backdrop", children: /* @__PURE__ */ (0, import_jsx_runtime104.jsxs)("div", { ref: dialogRef, className: "ss-w-tool", role: "dialog", "aria-modal": "true", "aria-labelledby": titleId, tabIndex: -1, onKeyDown: trapTab, children: [
|
|
10610
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsxs)("div", { className: "ss-w-tool-head", children: [
|
|
10611
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("h2", { id: titleId, className: "ss-w-tool-title", children: title }),
|
|
10612
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("button", { type: "button", className: "ss-w-tool-close", "aria-label": closeLabel, onClick: onClose, children: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(CloseIcon, {}) })
|
|
9892
10613
|
] }),
|
|
9893
|
-
/* @__PURE__ */ (0,
|
|
9894
|
-
footer ? /* @__PURE__ */ (0,
|
|
10614
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("div", { className: "ss-w-tool-body", children }),
|
|
10615
|
+
footer ? /* @__PURE__ */ (0, import_jsx_runtime104.jsx)("div", { className: "ss-w-tool-foot", children: footer }) : null
|
|
9895
10616
|
] }) });
|
|
9896
10617
|
}
|
|
9897
10618
|
function fillTemplate(template, slots) {
|
|
9898
10619
|
return template.split(/(\{[a-z]+\})/).filter((part) => part !== "").map((part, i) => {
|
|
9899
10620
|
const key = /^\{([a-z]+)\}$/.exec(part)?.[1];
|
|
9900
|
-
return /* @__PURE__ */ (0,
|
|
10621
|
+
return /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(import_react66.Fragment, { children: key !== void 0 && key in slots ? slots[key] : part }, i);
|
|
9901
10622
|
});
|
|
9902
10623
|
}
|
|
9903
10624
|
function NumberSelect({ current, choices: choices2, label, notToday, lockEmpty = true, onChoose }) {
|
|
9904
10625
|
const selected = Math.max(0, choices2.findIndex((c) => c.text === current));
|
|
9905
|
-
return /* @__PURE__ */ (0,
|
|
9906
|
-
/* @__PURE__ */ (0,
|
|
9907
|
-
/* @__PURE__ */ (0,
|
|
10626
|
+
return /* @__PURE__ */ (0, import_jsx_runtime104.jsxs)("span", { className: "ss-w-tool-num", children: [
|
|
10627
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("span", { className: "ss-w-tool-num-size", "aria-hidden": "true", children: current }),
|
|
10628
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("select", { className: "ss-w-tool-num-select", "aria-label": label, value: String(selected), onChange: (e) => {
|
|
9908
10629
|
const c = choices2[Number(e.target.value)];
|
|
9909
10630
|
if (c) onChoose(c.value);
|
|
9910
|
-
}, children: choices2.map((c, i) => /* @__PURE__ */ (0,
|
|
10631
|
+
}, children: choices2.map((c, i) => /* @__PURE__ */ (0, import_jsx_runtime104.jsx)("option", { value: String(i), disabled: lockEmpty && !c.available && i !== selected, children: c.available ? c.text : `${c.text}${notToday}` }, i)) })
|
|
9911
10632
|
] });
|
|
9912
10633
|
}
|
|
9913
10634
|
function ChoiceSelect({ currentIdx, sizeLabels, optionLabels, label, onChoose }) {
|
|
9914
10635
|
const sizeText = sizeLabels[currentIdx] ?? "";
|
|
9915
|
-
return /* @__PURE__ */ (0,
|
|
9916
|
-
/* @__PURE__ */ (0,
|
|
9917
|
-
/* @__PURE__ */ (0,
|
|
10636
|
+
return /* @__PURE__ */ (0, import_jsx_runtime104.jsxs)("span", { className: "ss-w-tool-num", children: [
|
|
10637
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("span", { className: "ss-w-tool-num-size", "aria-hidden": "true", children: sizeText }),
|
|
10638
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("select", { className: "ss-w-tool-num-select", "aria-label": label, value: String(currentIdx), onChange: (e) => onChoose(Number(e.target.value)), children: optionLabels.map((opt, i) => /* @__PURE__ */ (0, import_jsx_runtime104.jsx)("option", { value: String(i), children: opt }, i)) })
|
|
9918
10639
|
] });
|
|
9919
10640
|
}
|
|
9920
10641
|
function SendButton({ label, display, disabled, onClick }) {
|
|
9921
|
-
return /* @__PURE__ */ (0,
|
|
10642
|
+
return /* @__PURE__ */ (0, import_jsx_runtime104.jsx)("button", { type: "button", className: "ss-w-tool-send", "aria-label": `${label}: ${display}`, disabled, onClick, children: label });
|
|
9922
10643
|
}
|
|
9923
10644
|
function PickList({ picks, formatKickoff }) {
|
|
9924
|
-
return /* @__PURE__ */ (0,
|
|
9925
|
-
/* @__PURE__ */ (0,
|
|
10645
|
+
return /* @__PURE__ */ (0, import_jsx_runtime104.jsx)("ul", { className: "ss-w-tool-picks", role: "list", children: picks.map((p) => /* @__PURE__ */ (0, import_jsx_runtime104.jsxs)("li", { className: "ss-w-tool-pick", children: [
|
|
10646
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsxs)("span", { className: "ss-w-tool-pick-match", children: [
|
|
9926
10647
|
p.homeTeamName,
|
|
9927
10648
|
" \u2013 ",
|
|
9928
10649
|
p.awayTeamName
|
|
9929
10650
|
] }),
|
|
9930
|
-
/* @__PURE__ */ (0,
|
|
10651
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsxs)("span", { className: "ss-w-tool-pick-sel", children: [
|
|
9931
10652
|
p.marketLabel,
|
|
9932
10653
|
": ",
|
|
9933
10654
|
p.selectionLabel,
|
|
9934
10655
|
p.line ? ` ${p.line}` : ""
|
|
9935
10656
|
] }),
|
|
9936
|
-
/* @__PURE__ */ (0,
|
|
9937
|
-
/* @__PURE__ */ (0,
|
|
10657
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("span", { className: "ss-w-tool-pick-kick", children: formatKickoff(p.kickoffUtc) }),
|
|
10658
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("span", { className: "ss-w-tool-pick-price", children: p.price.toFixed(2) })
|
|
9938
10659
|
] }, p.matchOddsId)) });
|
|
9939
10660
|
}
|
|
9940
10661
|
function ComboPreview({ cell, formatKickoff }) {
|
|
9941
|
-
return /* @__PURE__ */ (0,
|
|
9942
|
-
/* @__PURE__ */ (0,
|
|
9943
|
-
/* @__PURE__ */ (0,
|
|
10662
|
+
return /* @__PURE__ */ (0, import_jsx_runtime104.jsxs)(import_jsx_runtime104.Fragment, { children: [
|
|
10663
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)(PickList, { picks: cell.combo.legs, formatKickoff }),
|
|
10664
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("div", { className: "ss-w-tool-math", children: cell.combo.multiplication })
|
|
9944
10665
|
] });
|
|
9945
10666
|
}
|
|
9946
10667
|
function Unavailable({ text }) {
|
|
9947
|
-
return /* @__PURE__ */ (0,
|
|
10668
|
+
return /* @__PURE__ */ (0, import_jsx_runtime104.jsx)("p", { className: "ss-w-tool-unavailable", children: text });
|
|
9948
10669
|
}
|
|
9949
10670
|
function AskRow({ icon, ask, ready, send }) {
|
|
9950
|
-
return /* @__PURE__ */ (0,
|
|
9951
|
-
/* @__PURE__ */ (0,
|
|
9952
|
-
/* @__PURE__ */ (0,
|
|
9953
|
-
/* @__PURE__ */ (0,
|
|
9954
|
-
ready ? /* @__PURE__ */ (0,
|
|
10671
|
+
return /* @__PURE__ */ (0, import_jsx_runtime104.jsxs)("section", { className: "ss-w-tool-row ss-w-tool-row--ask", children: [
|
|
10672
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("span", { className: "ss-w-tool-icon", "aria-hidden": "true", children: icon }),
|
|
10673
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsxs)("div", { className: "ss-w-tool-main", children: [
|
|
10674
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("p", { className: "ss-w-tool-ask", children: ask }),
|
|
10675
|
+
ready ? /* @__PURE__ */ (0, import_jsx_runtime104.jsx)("span", { className: "ss-w-tool-ready", children: ready }) : null
|
|
9955
10676
|
] }),
|
|
9956
10677
|
send
|
|
9957
10678
|
] });
|
|
9958
10679
|
}
|
|
9959
10680
|
function RoundSend({ label, display, disabled, onClick }) {
|
|
9960
|
-
return /* @__PURE__ */ (0,
|
|
10681
|
+
return /* @__PURE__ */ (0, import_jsx_runtime104.jsx)("button", { type: "button", className: "ss-w-tool-go", "aria-label": `${label}: ${display}`, disabled, onClick, children: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(SendIcon, {}) });
|
|
9961
10682
|
}
|
|
9962
10683
|
var BIG_COMBO = { total: 50, legs: 6 };
|
|
9963
10684
|
function SetNumbersTool({ grid, strings, streaming, onSend, onClose }) {
|
|
@@ -9966,15 +10687,15 @@ function SetNumbersTool({ grid, strings, streaming, onSend, onClose }) {
|
|
|
9966
10687
|
const totals = comboTotals(grid);
|
|
9967
10688
|
const legChoices = comboLegChoices(grid);
|
|
9968
10689
|
const count = FIXED_SINGLES_COUNT;
|
|
9969
|
-
const [maxPrice, setMaxPrice] = (0,
|
|
9970
|
-
const [minPrice, setMinPrice] = (0,
|
|
9971
|
-
const [start] = (0,
|
|
9972
|
-
const [total, setTotal] = (0,
|
|
9973
|
-
const [legs, setLegs] = (0,
|
|
9974
|
-
const [bigStart] = (0,
|
|
9975
|
-
const [bigTotal, setBigTotal] = (0,
|
|
9976
|
-
const [bigLegs, setBigLegs] = (0,
|
|
9977
|
-
const [announcement, setAnnouncement] = (0,
|
|
10690
|
+
const [maxPrice, setMaxPrice] = (0, import_react66.useState)(() => startSingles(grid.singles, limits, START.maxPrice, count));
|
|
10691
|
+
const [minPrice, setMinPrice] = (0, import_react66.useState)(() => startSingles(grid.singlesFrom, floors, START.minPrice, count));
|
|
10692
|
+
const [start] = (0, import_react66.useState)(() => startCombo(grid, totals, legChoices, START.comboTotal, START.comboLegs));
|
|
10693
|
+
const [total, setTotal] = (0, import_react66.useState)(start.total);
|
|
10694
|
+
const [legs, setLegs] = (0, import_react66.useState)(start.legs);
|
|
10695
|
+
const [bigStart] = (0, import_react66.useState)(() => startCombo(grid, totals, legChoices, BIG_COMBO.total, BIG_COMBO.legs));
|
|
10696
|
+
const [bigTotal, setBigTotal] = (0, import_react66.useState)(bigStart.total);
|
|
10697
|
+
const [bigLegs, setBigLegs] = (0, import_react66.useState)(bigStart.legs);
|
|
10698
|
+
const [announcement, setAnnouncement] = (0, import_react66.useState)("");
|
|
9978
10699
|
const maxCell = findSingles(grid.singles, maxPrice, count);
|
|
9979
10700
|
const minCell = findSingles(grid.singlesFrom, minPrice, count);
|
|
9980
10701
|
const comboCell = findCombo(grid, total, legs);
|
|
@@ -10018,95 +10739,95 @@ function SetNumbersTool({ grid, strings, streaming, onSend, onClose }) {
|
|
|
10018
10739
|
const totalChoices = totals.map((v) => ({ value: v, text: v.toFixed(1), available: legChoices.some((n) => !!findCombo(grid, v, n)) }));
|
|
10019
10740
|
const legChoicesFor = (t) => legChoices.map((n) => ({ value: n, text: String(n), available: !!findCombo(grid, t, n) }));
|
|
10020
10741
|
const markets = grid.markets ?? [];
|
|
10021
|
-
const [marketIdx, setMarketIdx] = (0,
|
|
10742
|
+
const [marketIdx, setMarketIdx] = (0, import_react66.useState)(0);
|
|
10022
10743
|
const marketCell = markets[marketIdx] ?? null;
|
|
10023
10744
|
const marketLabels = markets.map((c) => strings.marketShort(c.marketDeveloperName, c.marketLabel, c.selectionLabel ?? null));
|
|
10024
10745
|
const singlesReady = (cell) => cell ? strings.readyCount(cell.picks.length) : strings.unavailable;
|
|
10025
10746
|
const comboReady = (cell) => cell ? strings.readyAt(cell.combo.total) : strings.unavailable;
|
|
10026
|
-
return /* @__PURE__ */ (0,
|
|
10027
|
-
/* @__PURE__ */ (0,
|
|
10747
|
+
return /* @__PURE__ */ (0, import_jsx_runtime104.jsxs)(PresetToolModal, { title: strings.setNumbers, closeLabel: strings.close, onClose, children: [
|
|
10748
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)(
|
|
10028
10749
|
AskRow,
|
|
10029
10750
|
{
|
|
10030
10751
|
icon: "\u{1F3AF}",
|
|
10031
10752
|
ask: fillTemplate(strings.maxPriceRow, {
|
|
10032
10753
|
count: String(count),
|
|
10033
|
-
price: /* @__PURE__ */ (0,
|
|
10754
|
+
price: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(NumberSelect, { current: maxPrice.toFixed(2), choices: maxChoices, label: strings.maxPriceName, notToday: strings.notToday, onChoose: chooseMax })
|
|
10034
10755
|
}),
|
|
10035
10756
|
ready: singlesReady(maxCell),
|
|
10036
|
-
send: /* @__PURE__ */ (0,
|
|
10757
|
+
send: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(RoundSend, { label: strings.send, display: strings.maxPriceDisplay(count, maxPrice), disabled: !maxCell || streaming, onClick: () => {
|
|
10037
10758
|
if (maxCell) onSend(maxPriceAsk(maxCell, strings));
|
|
10038
10759
|
} })
|
|
10039
10760
|
}
|
|
10040
10761
|
),
|
|
10041
|
-
/* @__PURE__ */ (0,
|
|
10762
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)(
|
|
10042
10763
|
AskRow,
|
|
10043
10764
|
{
|
|
10044
10765
|
icon: "\u{1F4C8}",
|
|
10045
10766
|
ask: fillTemplate(strings.minPriceRow, {
|
|
10046
10767
|
count: String(count),
|
|
10047
|
-
price: /* @__PURE__ */ (0,
|
|
10768
|
+
price: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(NumberSelect, { current: minPrice.toFixed(2), choices: minChoices, label: strings.minPriceName, notToday: strings.notToday, onChoose: chooseMin })
|
|
10048
10769
|
}),
|
|
10049
10770
|
ready: singlesReady(minCell),
|
|
10050
|
-
send: /* @__PURE__ */ (0,
|
|
10771
|
+
send: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(RoundSend, { label: strings.send, display: strings.minPriceDisplay(count, minPrice), disabled: !minCell || streaming, onClick: () => {
|
|
10051
10772
|
if (minCell) onSend(minPriceAsk(minCell, strings));
|
|
10052
10773
|
} })
|
|
10053
10774
|
}
|
|
10054
10775
|
),
|
|
10055
|
-
/* @__PURE__ */ (0,
|
|
10776
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)(
|
|
10056
10777
|
AskRow,
|
|
10057
10778
|
{
|
|
10058
10779
|
icon: "\u2728",
|
|
10059
10780
|
ask: fillTemplate(strings.comboRow, {
|
|
10060
|
-
legs: /* @__PURE__ */ (0,
|
|
10061
|
-
total: /* @__PURE__ */ (0,
|
|
10781
|
+
legs: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(NumberSelect, { current: String(legs), choices: legChoicesFor(total), label: strings.matchesLabel, notToday: strings.notToday, lockEmpty: false, onChoose: chooseLegs }),
|
|
10782
|
+
total: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(NumberSelect, { current: total.toFixed(1), choices: totalChoices, label: strings.totalLabel, notToday: strings.notToday, onChoose: chooseTotal })
|
|
10062
10783
|
}),
|
|
10063
10784
|
ready: comboReady(comboCell),
|
|
10064
|
-
send: /* @__PURE__ */ (0,
|
|
10785
|
+
send: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(RoundSend, { label: strings.send, display: strings.comboDisplay(legs, total), disabled: !comboCell || streaming, onClick: () => {
|
|
10065
10786
|
if (comboCell) onSend(comboAsk(comboCell, strings));
|
|
10066
10787
|
} })
|
|
10067
10788
|
}
|
|
10068
10789
|
),
|
|
10069
|
-
/* @__PURE__ */ (0,
|
|
10790
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)(
|
|
10070
10791
|
AskRow,
|
|
10071
10792
|
{
|
|
10072
10793
|
icon: "\u{1F3C6}",
|
|
10073
10794
|
ask: fillTemplate(strings.bigComboRow, {
|
|
10074
|
-
legs: /* @__PURE__ */ (0,
|
|
10075
|
-
total: /* @__PURE__ */ (0,
|
|
10795
|
+
legs: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(NumberSelect, { current: String(bigLegs), choices: legChoicesFor(bigTotal), label: strings.matchesLabel, notToday: strings.notToday, lockEmpty: false, onChoose: chooseBigLegs }),
|
|
10796
|
+
total: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(NumberSelect, { current: bigTotal.toFixed(1), choices: totalChoices, label: strings.totalLabel, notToday: strings.notToday, onChoose: chooseBigTotal })
|
|
10076
10797
|
}),
|
|
10077
10798
|
ready: comboReady(bigCell),
|
|
10078
|
-
send: /* @__PURE__ */ (0,
|
|
10799
|
+
send: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(RoundSend, { label: strings.send, display: strings.comboDisplay(bigLegs, bigTotal), disabled: !bigCell || streaming, onClick: () => {
|
|
10079
10800
|
if (bigCell) onSend(comboAsk(bigCell, strings));
|
|
10080
10801
|
} })
|
|
10081
10802
|
}
|
|
10082
10803
|
),
|
|
10083
|
-
markets.length > 0 && /* @__PURE__ */ (0,
|
|
10804
|
+
markets.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(
|
|
10084
10805
|
AskRow,
|
|
10085
10806
|
{
|
|
10086
10807
|
icon: "\u26BD",
|
|
10087
10808
|
ask: fillTemplate(strings.marketRow, {
|
|
10088
|
-
market: /* @__PURE__ */ (0,
|
|
10809
|
+
market: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(ChoiceSelect, { currentIdx: marketIdx, sizeLabels: marketLabels, optionLabels: marketLabels, label: strings.marketName, onChoose: chooseMarket })
|
|
10089
10810
|
}),
|
|
10090
10811
|
ready: marketCell ? strings.readyCount(marketCell.count) : null,
|
|
10091
|
-
send: /* @__PURE__ */ (0,
|
|
10812
|
+
send: /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(RoundSend, { label: strings.send, display: marketCell ? marketDisplay(marketCell, strings) : "", disabled: !marketCell || streaming, onClick: () => {
|
|
10092
10813
|
if (marketCell) onSend(marketAsk(marketCell, strings));
|
|
10093
10814
|
} })
|
|
10094
10815
|
}
|
|
10095
10816
|
),
|
|
10096
|
-
/* @__PURE__ */ (0,
|
|
10817
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("p", { className: "ss-w-vh", "aria-live": "polite", children: announcement })
|
|
10097
10818
|
] });
|
|
10098
10819
|
}
|
|
10099
10820
|
function BuildComboTool({ grid, strings, streaming, formatKickoff, initialTotal, initialLegs, onSend, onClose }) {
|
|
10100
10821
|
const totals = comboTotals(grid);
|
|
10101
10822
|
const legChoices = comboLegChoices(grid);
|
|
10102
|
-
const [start] = (0,
|
|
10103
|
-
const [total, setTotal] = (0,
|
|
10104
|
-
const [legs, setLegs] = (0,
|
|
10823
|
+
const [start] = (0, import_react66.useState)(() => initialTotal === void 0 ? startCombo(grid, totals, legChoices, START.comboTotal, START.comboLegs) : null);
|
|
10824
|
+
const [total, setTotal] = (0, import_react66.useState)(() => initialTotal !== void 0 ? nearest(totals, initialTotal) : start.total);
|
|
10825
|
+
const [legs, setLegs] = (0, import_react66.useState)(() => {
|
|
10105
10826
|
if (initialTotal === void 0) return initialLegs !== void 0 ? clampLegs(legChoices, initialLegs) : start.legs;
|
|
10106
10827
|
const from = initialLegs !== void 0 ? clampLegs(legChoices, initialLegs) : startValue(legChoices, START.comboLegs);
|
|
10107
10828
|
return legsForTotal(grid, nearest(totals, initialTotal), from);
|
|
10108
10829
|
});
|
|
10109
|
-
const [announcement, setAnnouncement] = (0,
|
|
10830
|
+
const [announcement, setAnnouncement] = (0, import_react66.useState)("");
|
|
10110
10831
|
const cell = findCombo(grid, total, legs);
|
|
10111
10832
|
const minLegs = legChoices[0] ?? legs;
|
|
10112
10833
|
const maxLegs = legChoices[legChoices.length - 1] ?? legs;
|
|
@@ -10117,29 +10838,29 @@ function BuildComboTool({ grid, strings, streaming, formatKickoff, initialTotal,
|
|
|
10117
10838
|
const d = strings.comboDisplay(nextLegs, nextTotal);
|
|
10118
10839
|
setAnnouncement(findCombo(grid, nextTotal, nextLegs) ? d : `${d}. ${strings.unavailable}`);
|
|
10119
10840
|
};
|
|
10120
|
-
const footer = /* @__PURE__ */ (0,
|
|
10841
|
+
const footer = /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(SendButton, { label: strings.send, display, disabled: !cell || streaming, onClick: () => {
|
|
10121
10842
|
if (cell) onSend(comboAsk(cell, strings));
|
|
10122
10843
|
} });
|
|
10123
|
-
return /* @__PURE__ */ (0,
|
|
10124
|
-
/* @__PURE__ */ (0,
|
|
10125
|
-
/* @__PURE__ */ (0,
|
|
10126
|
-
/* @__PURE__ */ (0,
|
|
10844
|
+
return /* @__PURE__ */ (0, import_jsx_runtime104.jsxs)(PresetToolModal, { title: strings.buildCombo, closeLabel: strings.close, onClose, footer, children: [
|
|
10845
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsxs)("div", { className: "ss-w-tool-section", role: "group", "aria-label": strings.totalLabel, children: [
|
|
10846
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("span", { className: "ss-w-tool-label", "aria-hidden": "true", children: strings.totalLabel }),
|
|
10847
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("div", { className: "ss-w-tool-chips", children: totals.map((t) => /* @__PURE__ */ (0, import_jsx_runtime104.jsx)("button", { type: "button", className: "ss-w-tool-chip", "aria-pressed": samePrice(t, total), onClick: () => choose(t, samePrice(t, total) ? legs : legsForTotal(grid, t, legs)), children: t.toFixed(1) }, t)) })
|
|
10127
10848
|
] }),
|
|
10128
|
-
/* @__PURE__ */ (0,
|
|
10129
|
-
/* @__PURE__ */ (0,
|
|
10130
|
-
/* @__PURE__ */ (0,
|
|
10131
|
-
/* @__PURE__ */ (0,
|
|
10132
|
-
/* @__PURE__ */ (0,
|
|
10133
|
-
/* @__PURE__ */ (0,
|
|
10849
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsxs)("div", { className: "ss-w-tool-section", role: "group", "aria-label": strings.matchesLabel, children: [
|
|
10850
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("span", { className: "ss-w-tool-label", "aria-hidden": "true", children: strings.matchesLabel }),
|
|
10851
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsxs)("div", { className: "ss-w-tool-stepper", children: [
|
|
10852
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("button", { type: "button", className: "ss-w-tool-step", "aria-label": strings.fewerMatches, disabled: legs <= minLegs, onClick: () => choose(total, legs - 1), children: "\u2212" }),
|
|
10853
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("span", { className: "ss-w-tool-count", children: legs }),
|
|
10854
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("button", { type: "button", className: "ss-w-tool-step", "aria-label": strings.moreMatches, disabled: legs >= maxLegs, onClick: () => choose(total, legs + 1), children: "+" })
|
|
10134
10855
|
] })
|
|
10135
10856
|
] }),
|
|
10136
|
-
cell ? /* @__PURE__ */ (0,
|
|
10137
|
-
/* @__PURE__ */ (0,
|
|
10857
|
+
cell ? /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(ComboPreview, { cell, formatKickoff }) : /* @__PURE__ */ (0, import_jsx_runtime104.jsx)(Unavailable, { text: strings.unavailable }),
|
|
10858
|
+
/* @__PURE__ */ (0, import_jsx_runtime104.jsx)("p", { className: "ss-w-vh", "aria-live": "polite", children: announcement })
|
|
10138
10859
|
] });
|
|
10139
10860
|
}
|
|
10140
10861
|
|
|
10141
10862
|
// src/usePresetDial.ts
|
|
10142
|
-
var
|
|
10863
|
+
var import_react67 = require("react");
|
|
10143
10864
|
function sendInFlight(messages, isStreaming) {
|
|
10144
10865
|
const last = messages[messages.length - 1];
|
|
10145
10866
|
return isStreaming && !!last && last.role === "assistant" && !last.done && !last.isGreeting;
|
|
@@ -10153,25 +10874,25 @@ function lastUserId(messages) {
|
|
|
10153
10874
|
}
|
|
10154
10875
|
var SCROLL_KEYS = /* @__PURE__ */ new Set(["ArrowUp", "ArrowDown", "PageUp", "PageDown", "Home", "End", " "]);
|
|
10155
10876
|
function usePresetDial({ layerRef, dialRef, dialButtonRef, messages, isStreaming, activeTab }) {
|
|
10156
|
-
const [expanded, setExpanded] = (0,
|
|
10157
|
-
const fold = (0,
|
|
10158
|
-
const toggle = (0,
|
|
10877
|
+
const [expanded, setExpanded] = (0, import_react67.useState)(() => !sendInFlight(messages, isStreaming));
|
|
10878
|
+
const fold = (0, import_react67.useCallback)(() => setExpanded(false), []);
|
|
10879
|
+
const toggle = (0, import_react67.useCallback)(() => setExpanded((e) => !e), []);
|
|
10159
10880
|
const currentUserId = lastUserId(messages);
|
|
10160
|
-
const userIdRef = (0,
|
|
10161
|
-
(0,
|
|
10881
|
+
const userIdRef = (0, import_react67.useRef)(currentUserId);
|
|
10882
|
+
(0, import_react67.useEffect)(() => {
|
|
10162
10883
|
if (currentUserId === userIdRef.current) return;
|
|
10163
10884
|
userIdRef.current = currentUserId;
|
|
10164
10885
|
setExpanded(false);
|
|
10165
10886
|
}, [currentUserId]);
|
|
10166
|
-
const tabRef = (0,
|
|
10167
|
-
(0,
|
|
10887
|
+
const tabRef = (0, import_react67.useRef)(activeTab);
|
|
10888
|
+
(0, import_react67.useEffect)(() => {
|
|
10168
10889
|
if (activeTab === tabRef.current) return;
|
|
10169
10890
|
tabRef.current = activeTab;
|
|
10170
10891
|
setExpanded(false);
|
|
10171
10892
|
}, [activeTab]);
|
|
10172
|
-
const expandedRef = (0,
|
|
10893
|
+
const expandedRef = (0, import_react67.useRef)(expanded);
|
|
10173
10894
|
expandedRef.current = expanded;
|
|
10174
|
-
(0,
|
|
10895
|
+
(0, import_react67.useEffect)(() => {
|
|
10175
10896
|
const onEscape = (e) => {
|
|
10176
10897
|
const dial = dialRef.current;
|
|
10177
10898
|
if (e.key !== "Escape" || !dial || !e.composedPath().includes(dial)) return;
|
|
@@ -10184,7 +10905,7 @@ function usePresetDial({ layerRef, dialRef, dialButtonRef, messages, isStreaming
|
|
|
10184
10905
|
window.addEventListener("keydown", onEscape, true);
|
|
10185
10906
|
return () => window.removeEventListener("keydown", onEscape, true);
|
|
10186
10907
|
}, [dialRef, dialButtonRef]);
|
|
10187
|
-
(0,
|
|
10908
|
+
(0, import_react67.useEffect)(() => {
|
|
10188
10909
|
if (!expanded) return;
|
|
10189
10910
|
const layer = layerRef.current;
|
|
10190
10911
|
const inDial = (e) => {
|
|
@@ -10236,11 +10957,11 @@ function markToolSeen() {
|
|
|
10236
10957
|
}
|
|
10237
10958
|
|
|
10238
10959
|
// src/components/ChatPanel.tsx
|
|
10239
|
-
var
|
|
10960
|
+
var import_jsx_runtime105 = require("react/jsx-runtime");
|
|
10240
10961
|
var FULLSCREEN_QUERY = "(max-width: 639px)";
|
|
10241
10962
|
function useIsModal() {
|
|
10242
|
-
const [modal, setModal] = (0,
|
|
10243
|
-
(0,
|
|
10963
|
+
const [modal, setModal] = (0, import_react68.useState)(false);
|
|
10964
|
+
(0, import_react68.useEffect)(() => {
|
|
10244
10965
|
if (typeof window === "undefined" || typeof window.matchMedia !== "function") return;
|
|
10245
10966
|
const mql = window.matchMedia(FULLSCREEN_QUERY);
|
|
10246
10967
|
const sync = () => setModal(mql.matches);
|
|
@@ -10251,10 +10972,38 @@ function useIsModal() {
|
|
|
10251
10972
|
return modal;
|
|
10252
10973
|
}
|
|
10253
10974
|
var HIDDEN_LAYER_STYLE = { position: "absolute", inset: 0, visibility: "hidden", display: "flex", flexDirection: "column" };
|
|
10254
|
-
|
|
10975
|
+
var SQUAD_LAYER_STYLE = { display: "flex", flexDirection: "column", flex: 1, minHeight: 0 };
|
|
10976
|
+
function ChatPanel({ controller, ui, slip, onDashboardTap, monitor, discovery, gamesResult, leaderboardResult, clubFixturesResult, clubStandingsResult, clubSquadResult, clubSquadStatsResult, clubPlayerDetailResult, loggedIn, conversation, presetGrid }) {
|
|
10255
10977
|
const { state, close, stop, send, reset } = controller;
|
|
10978
|
+
const [squadView, setSquadView] = (0, import_react68.useState)("roster");
|
|
10979
|
+
const [selectedPlayerId, setSelectedPlayerId] = (0, import_react68.useState)(null);
|
|
10980
|
+
const clearPlayerDetail = clubPlayerDetailResult?.clear;
|
|
10981
|
+
const fetchPlayerDetail = clubPlayerDetailResult?.fetch;
|
|
10982
|
+
const squadLayerRef = (0, import_react68.useRef)(null);
|
|
10983
|
+
const squadScrollRef = (0, import_react68.useRef)(null);
|
|
10984
|
+
const selectPlayer = (playerId) => {
|
|
10985
|
+
squadScrollRef.current = squadLayerRef.current?.querySelector(".ss-w-mon-list")?.scrollTop ?? null;
|
|
10986
|
+
setSelectedPlayerId(playerId);
|
|
10987
|
+
fetchPlayerDetail?.(playerId);
|
|
10988
|
+
};
|
|
10989
|
+
const closePlayer = () => {
|
|
10990
|
+
setSelectedPlayerId(null);
|
|
10991
|
+
clearPlayerDetail?.();
|
|
10992
|
+
};
|
|
10993
|
+
(0, import_react68.useLayoutEffect)(() => {
|
|
10994
|
+
if (selectedPlayerId !== null || squadScrollRef.current === null) return;
|
|
10995
|
+
const list = squadLayerRef.current?.querySelector(".ss-w-mon-list");
|
|
10996
|
+
if (list) list.scrollTop = squadScrollRef.current;
|
|
10997
|
+
squadScrollRef.current = null;
|
|
10998
|
+
}, [selectedPlayerId]);
|
|
10999
|
+
const activeTab = monitor?.activeTab;
|
|
11000
|
+
(0, import_react68.useEffect)(() => {
|
|
11001
|
+
if (activeTab === "squad" || selectedPlayerId === null) return;
|
|
11002
|
+
setSelectedPlayerId(null);
|
|
11003
|
+
clearPlayerDetail?.();
|
|
11004
|
+
}, [activeTab, selectedPlayerId, clearPlayerDetail]);
|
|
10256
11005
|
const isModal = useIsModal();
|
|
10257
|
-
(0,
|
|
11006
|
+
(0, import_react68.useEffect)(() => {
|
|
10258
11007
|
const onKey = (e) => {
|
|
10259
11008
|
if (e.key === "Escape") close();
|
|
10260
11009
|
};
|
|
@@ -10270,19 +11019,19 @@ function ChatPanel({ controller, ui, slip, onDashboardTap, monitor, discovery, g
|
|
|
10270
11019
|
monitor?.setActiveTab("chat");
|
|
10271
11020
|
send(text, { grounding });
|
|
10272
11021
|
};
|
|
10273
|
-
(0,
|
|
11022
|
+
(0, import_react68.useEffect)(() => {
|
|
10274
11023
|
if (monitor && monitor.activeTab !== "chat" && state.isStreaming) monitor.markChatActivity();
|
|
10275
11024
|
}, [monitor, state.isStreaming, state.messages.length]);
|
|
10276
11025
|
const onChatTab = !monitor || monitor.activeTab === "chat";
|
|
10277
|
-
const layerRef = (0,
|
|
10278
|
-
const dialRef = (0,
|
|
10279
|
-
const dialButtonRef = (0,
|
|
10280
|
-
const inputRef = (0,
|
|
10281
|
-
const limitRef = (0,
|
|
10282
|
-
const typedSendRef = (0,
|
|
10283
|
-
const focusAfterCloseRef = (0,
|
|
10284
|
-
const [tool, setTool] = (0,
|
|
10285
|
-
const [toolSeen, setToolSeen] = (0,
|
|
11026
|
+
const layerRef = (0, import_react68.useRef)(null);
|
|
11027
|
+
const dialRef = (0, import_react68.useRef)(null);
|
|
11028
|
+
const dialButtonRef = (0, import_react68.useRef)(null);
|
|
11029
|
+
const inputRef = (0, import_react68.useRef)(null);
|
|
11030
|
+
const limitRef = (0, import_react68.useRef)(null);
|
|
11031
|
+
const typedSendRef = (0, import_react68.useRef)(false);
|
|
11032
|
+
const focusAfterCloseRef = (0, import_react68.useRef)(null);
|
|
11033
|
+
const [tool, setTool] = (0, import_react68.useState)(null);
|
|
11034
|
+
const [toolSeen, setToolSeen] = (0, import_react68.useState)(readToolSeen);
|
|
10286
11035
|
const dial = usePresetDial({
|
|
10287
11036
|
layerRef,
|
|
10288
11037
|
dialRef,
|
|
@@ -10294,53 +11043,53 @@ function ChatPanel({ controller, ui, slip, onDashboardTap, monitor, discovery, g
|
|
|
10294
11043
|
const { fold } = dial;
|
|
10295
11044
|
const paused = isPaused(state.limit);
|
|
10296
11045
|
const showDial = !!presetGrid && onChatTab && !tool && !paused;
|
|
10297
|
-
(0,
|
|
11046
|
+
(0, import_react68.useEffect)(() => {
|
|
10298
11047
|
if (paused) setTool(null);
|
|
10299
11048
|
}, [paused]);
|
|
10300
|
-
(0,
|
|
11049
|
+
(0, import_react68.useEffect)(() => {
|
|
10301
11050
|
if (!paused) return;
|
|
10302
11051
|
if (typedSendRef.current) limitRef.current?.focus();
|
|
10303
11052
|
typedSendRef.current = false;
|
|
10304
11053
|
}, [paused]);
|
|
10305
|
-
const openTool = (0,
|
|
11054
|
+
const openTool = (0, import_react68.useCallback)((next) => {
|
|
10306
11055
|
fold();
|
|
10307
11056
|
markToolSeen();
|
|
10308
11057
|
setToolSeen(true);
|
|
10309
11058
|
setTool(next);
|
|
10310
11059
|
}, [fold]);
|
|
10311
|
-
const onPill = (0,
|
|
10312
|
-
const toolsValue = (0,
|
|
11060
|
+
const onPill = (0, import_react68.useCallback)((kind) => openTool(kind === "numbers" ? { kind: "numbers" } : { kind: "combo" }), [openTool]);
|
|
11061
|
+
const toolsValue = (0, import_react68.useMemo)(
|
|
10313
11062
|
() => presetGrid && !paused ? { openBuilder: (total, legs) => openTool({ kind: "combo", total, legs }), changeLabel: ui.presets.changeCombo } : null,
|
|
10314
11063
|
[presetGrid, paused, openTool, ui.presets.changeCombo]
|
|
10315
11064
|
);
|
|
10316
|
-
const closeTool = (0,
|
|
11065
|
+
const closeTool = (0, import_react68.useCallback)(() => {
|
|
10317
11066
|
focusAfterCloseRef.current = "dial";
|
|
10318
11067
|
setTool(null);
|
|
10319
11068
|
}, []);
|
|
10320
|
-
const sendAsk = (0,
|
|
11069
|
+
const sendAsk = (0, import_react68.useCallback)((ask) => {
|
|
10321
11070
|
focusAfterCloseRef.current = "composer";
|
|
10322
11071
|
setTool(null);
|
|
10323
11072
|
monitor?.setActiveTab("chat");
|
|
10324
11073
|
send(ask.message, { displayText: ask.displayText, preset: ask.preset });
|
|
10325
11074
|
}, [monitor, send]);
|
|
10326
|
-
const formatKickoff = (0,
|
|
11075
|
+
const formatKickoff = (0, import_react68.useCallback)((kickoffUtc) => {
|
|
10327
11076
|
const k = ui.bettingKickoff(kickoffUtc);
|
|
10328
11077
|
return `${k.dayLabel} ${k.time}`;
|
|
10329
11078
|
}, [ui]);
|
|
10330
|
-
(0,
|
|
11079
|
+
(0, import_react68.useEffect)(() => {
|
|
10331
11080
|
if (tool) return;
|
|
10332
11081
|
const target = focusAfterCloseRef.current;
|
|
10333
11082
|
focusAfterCloseRef.current = null;
|
|
10334
11083
|
if (target === "dial") dialButtonRef.current?.focus();
|
|
10335
11084
|
else if (target === "composer") inputRef.current?.focus();
|
|
10336
11085
|
}, [tool]);
|
|
10337
|
-
(0,
|
|
11086
|
+
(0, import_react68.useEffect)(() => {
|
|
10338
11087
|
if (!tool || onChatTab && presetGrid) return;
|
|
10339
11088
|
focusAfterCloseRef.current = "composer";
|
|
10340
11089
|
setTool(null);
|
|
10341
11090
|
}, [tool, onChatTab, presetGrid]);
|
|
10342
|
-
return /* @__PURE__ */ (0,
|
|
10343
|
-
/* @__PURE__ */ (0,
|
|
11091
|
+
return /* @__PURE__ */ (0, import_jsx_runtime105.jsxs)("div", { className: "ss-w-panel", role: "dialog", "aria-modal": isModal, "aria-label": ui.chatDialogLabel, children: [
|
|
11092
|
+
/* @__PURE__ */ (0, import_jsx_runtime105.jsx)(
|
|
10344
11093
|
ChatHeader,
|
|
10345
11094
|
{
|
|
10346
11095
|
onClose: close,
|
|
@@ -10353,7 +11102,7 @@ function ChatPanel({ controller, ui, slip, onDashboardTap, monitor, discovery, g
|
|
|
10353
11102
|
moreOptionsLabel: ui.moreOptions
|
|
10354
11103
|
}
|
|
10355
11104
|
),
|
|
10356
|
-
monitor && /* @__PURE__ */ (0,
|
|
11105
|
+
monitor && /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(
|
|
10357
11106
|
TabBar,
|
|
10358
11107
|
{
|
|
10359
11108
|
monitor,
|
|
@@ -10366,9 +11115,9 @@ function ChatPanel({ controller, ui, slip, onDashboardTap, monitor, discovery, g
|
|
|
10366
11115
|
clubEnabled: clubFixturesResult?.enabled ?? false
|
|
10367
11116
|
}
|
|
10368
11117
|
),
|
|
10369
|
-
/* @__PURE__ */ (0,
|
|
10370
|
-
/* @__PURE__ */ (0,
|
|
10371
|
-
showDial ? /* @__PURE__ */ (0,
|
|
11118
|
+
/* @__PURE__ */ (0, import_jsx_runtime105.jsxs)("div", { ref: layerRef, className: "ss-w-chat-layer", "data-dial": presetGrid ? "" : void 0, style: onChatTab ? void 0 : HIDDEN_LAYER_STYLE, children: [
|
|
11119
|
+
/* @__PURE__ */ (0, import_jsx_runtime105.jsx)(PresetToolsContext.Provider, { value: toolsValue, children: /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(MessageList, { controller, ui, slip, onDashboardTap, monitor }) }),
|
|
11120
|
+
showDial ? /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(
|
|
10372
11121
|
PresetSpeedDial,
|
|
10373
11122
|
{
|
|
10374
11123
|
expanded: dial.expanded,
|
|
@@ -10380,15 +11129,41 @@ function ChatPanel({ controller, ui, slip, onDashboardTap, monitor, discovery, g
|
|
|
10380
11129
|
buttonRef: dialButtonRef
|
|
10381
11130
|
}
|
|
10382
11131
|
) : null,
|
|
10383
|
-
tool && presetGrid && onChatTab && !paused ? tool.kind === "numbers" ? /* @__PURE__ */ (0,
|
|
11132
|
+
tool && presetGrid && onChatTab && !paused ? tool.kind === "numbers" ? /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(SetNumbersTool, { grid: presetGrid, strings: ui.presets, streaming: state.isStreaming, onSend: sendAsk, onClose: closeTool }) : /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(BuildComboTool, { grid: presetGrid, strings: ui.presets, streaming: state.isStreaming, formatKickoff, initialTotal: tool.total, initialLegs: tool.legs, onSend: sendAsk, onClose: closeTool }) : null
|
|
10384
11133
|
] }),
|
|
10385
|
-
monitor && discovery && monitor.activeTab === "today" && /* @__PURE__ */ (0,
|
|
10386
|
-
monitor && monitor.activeTab === "following" && /* @__PURE__ */ (0,
|
|
10387
|
-
monitor && monitor.activeTab === "odds" && /* @__PURE__ */ (0,
|
|
10388
|
-
monitor && monitor.activeTab === "fixtures" && /* @__PURE__ */ (0,
|
|
10389
|
-
monitor && monitor.activeTab === "standings" && /* @__PURE__ */ (0,
|
|
10390
|
-
monitor && monitor.activeTab === "squad" && /* @__PURE__ */ (0,
|
|
10391
|
-
|
|
11134
|
+
monitor && discovery && monitor.activeTab === "today" && /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(TodayPanel, { discovery, ui, monitor }),
|
|
11135
|
+
monitor && monitor.activeTab === "following" && /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(MatchesPanel, { monitor, ui, slip, onAsk: paused ? void 0 : handleAsk }),
|
|
11136
|
+
monitor && monitor.activeTab === "odds" && /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(OddsPanel, { monitor, ui, slip }),
|
|
11137
|
+
monitor && monitor.activeTab === "fixtures" && /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(Fixtures, { fixtures: clubFixturesResult?.fixtures ?? [], loading: clubFixturesResult?.loading ?? false, ui }),
|
|
11138
|
+
monitor && monitor.activeTab === "standings" && /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(Standings, { standings: clubStandingsResult?.data ?? null, loading: clubStandingsResult?.loading ?? false, ui }),
|
|
11139
|
+
monitor && monitor.activeTab === "squad" && /* @__PURE__ */ (0, import_jsx_runtime105.jsxs)(import_jsx_runtime105.Fragment, { children: [
|
|
11140
|
+
/* @__PURE__ */ (0, import_jsx_runtime105.jsx)(
|
|
11141
|
+
"div",
|
|
11142
|
+
{
|
|
11143
|
+
ref: squadLayerRef,
|
|
11144
|
+
style: selectedPlayerId === null ? SQUAD_LAYER_STYLE : HIDDEN_LAYER_STYLE,
|
|
11145
|
+
"aria-hidden": selectedPlayerId !== null ? true : void 0,
|
|
11146
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(
|
|
11147
|
+
Squad,
|
|
11148
|
+
{
|
|
11149
|
+
squad: clubSquadResult?.data ?? null,
|
|
11150
|
+
loading: clubSquadResult?.loading ?? false,
|
|
11151
|
+
ui,
|
|
11152
|
+
view: squadView,
|
|
11153
|
+
onToggleView: () => setSquadView((v) => v === "roster" ? "stats" : "roster"),
|
|
11154
|
+
stats: clubSquadStatsResult?.data ?? null,
|
|
11155
|
+
statsLoading: clubSquadStatsResult?.loading ?? false,
|
|
11156
|
+
seasonName: clubSquadStatsResult?.seasonName ?? null,
|
|
11157
|
+
competitionName: clubSquadStatsResult?.competitionName ?? null,
|
|
11158
|
+
matchesPlayed: clubSquadStatsResult?.matchesPlayed ?? null,
|
|
11159
|
+
onSelectPlayer: selectPlayer
|
|
11160
|
+
}
|
|
11161
|
+
)
|
|
11162
|
+
}
|
|
11163
|
+
),
|
|
11164
|
+
selectedPlayerId !== null && /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(PlayerDetail, { detail: clubPlayerDetailResult?.data ?? null, loading: clubPlayerDetailResult?.loading ?? false, ui, seasonName: clubSquadStatsResult?.seasonName ?? null, onClose: closePlayer })
|
|
11165
|
+
] }),
|
|
11166
|
+
monitor && monitor.activeTab === "games" && gamesResult && /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(
|
|
10392
11167
|
GamesPanel,
|
|
10393
11168
|
{
|
|
10394
11169
|
loggedIn: !!loggedIn,
|
|
@@ -10403,9 +11178,9 @@ function ChatPanel({ controller, ui, slip, onDashboardTap, monitor, discovery, g
|
|
|
10403
11178
|
}
|
|
10404
11179
|
}
|
|
10405
11180
|
),
|
|
10406
|
-
(!monitor || monitor.activeTab !== "games") && /* @__PURE__ */ (0,
|
|
10407
|
-
/* @__PURE__ */ (0,
|
|
10408
|
-
paused ? null : /* @__PURE__ */ (0,
|
|
11181
|
+
(!monitor || monitor.activeTab !== "games") && /* @__PURE__ */ (0, import_jsx_runtime105.jsxs)(import_jsx_runtime105.Fragment, { children: [
|
|
11182
|
+
/* @__PURE__ */ (0, import_jsx_runtime105.jsx)("div", { ref: limitRef, className: "ss-w-limit", role: "status", tabIndex: -1, children: state.limit ? limitText(state.limit, ui) : null }),
|
|
11183
|
+
paused ? null : /* @__PURE__ */ (0, import_jsx_runtime105.jsx)(
|
|
10409
11184
|
ChatInput,
|
|
10410
11185
|
{
|
|
10411
11186
|
ref: inputRef,
|
|
@@ -10424,9 +11199,9 @@ function ChatPanel({ controller, ui, slip, onDashboardTap, monitor, discovery, g
|
|
|
10424
11199
|
}
|
|
10425
11200
|
|
|
10426
11201
|
// src/components/HostEventsProvider.tsx
|
|
10427
|
-
var
|
|
11202
|
+
var import_jsx_runtime106 = require("react/jsx-runtime");
|
|
10428
11203
|
function HostEventsProvider({ value, children }) {
|
|
10429
|
-
return /* @__PURE__ */ (0,
|
|
11204
|
+
return /* @__PURE__ */ (0, import_jsx_runtime106.jsx)(SlipStateContext.Provider, { value: value.slipState, children });
|
|
10430
11205
|
}
|
|
10431
11206
|
|
|
10432
11207
|
// src/styles/css.generated.ts
|
|
@@ -10437,7 +11212,7 @@ var WIDGET_CSS = `.ss-w-root { all: revert; }
|
|
|
10437
11212
|
--ss-w-cta: #f5a623; --ss-w-cta-ink: #1b1300;
|
|
10438
11213
|
--ss-w-ink: #14181d; --ss-w-faint: #6b7580; --ss-w-line: #e4e8ec;
|
|
10439
11214
|
--ss-w-panel: #ffffff; --ss-w-bubble: #f3f5f7; --ss-w-nav: #0e1622;
|
|
10440
|
-
--ss-w-pos: #1aa563; --ss-w-neg: #e0524b;
|
|
11215
|
+
--ss-w-pos: #1aa563; --ss-w-neg: #e0524b; --ss-w-warn: #c07a00;
|
|
10441
11216
|
--ss-w-home: #3a63a8; --ss-w-away: #c8102e; --ss-w-track: #e9edf1;
|
|
10442
11217
|
--ss-w-correct: #1f9d55; --ss-w-wrong: #b9bbc2;
|
|
10443
11218
|
--ss-w-radius: 16px; --ss-w-offset-x: 20px; --ss-w-offset-y: 20px;
|
|
@@ -10449,7 +11224,7 @@ var WIDGET_CSS = `.ss-w-root { all: revert; }
|
|
|
10449
11224
|
--ss-w-accent: #37c891; --ss-w-cta: #ffb638; --ss-w-cta-ink: #1b1300;
|
|
10450
11225
|
--ss-w-ink: #e8edf2; --ss-w-faint: #8b95a1;
|
|
10451
11226
|
--ss-w-line: #2a3441; --ss-w-panel: #141b24; --ss-w-bubble: #1e2732; --ss-w-nav: #0a0f16;
|
|
10452
|
-
--ss-w-pos: #37c891; --ss-w-neg: #f0655d;
|
|
11227
|
+
--ss-w-pos: #37c891; --ss-w-neg: #f0655d; --ss-w-warn: #e0a030;
|
|
10453
11228
|
--ss-w-home: #5b83c8; --ss-w-away: #e8384f; --ss-w-track: #232d3a;
|
|
10454
11229
|
--ss-w-correct: #37c86b; --ss-w-wrong: #3a3a41;
|
|
10455
11230
|
}
|
|
@@ -10458,7 +11233,7 @@ var WIDGET_CSS = `.ss-w-root { all: revert; }
|
|
|
10458
11233
|
--ss-w-accent: #37c891; --ss-w-cta: #ffb638; --ss-w-cta-ink: #1b1300;
|
|
10459
11234
|
--ss-w-ink: #e8edf2; --ss-w-faint: #8b95a1;
|
|
10460
11235
|
--ss-w-line: #2a3441; --ss-w-panel: #141b24; --ss-w-bubble: #1e2732; --ss-w-nav: #0a0f16;
|
|
10461
|
-
--ss-w-pos: #37c891; --ss-w-neg: #f0655d;
|
|
11236
|
+
--ss-w-pos: #37c891; --ss-w-neg: #f0655d; --ss-w-warn: #e0a030;
|
|
10462
11237
|
--ss-w-home: #5b83c8; --ss-w-away: #e8384f; --ss-w-track: #232d3a;
|
|
10463
11238
|
--ss-w-correct: #37c86b; --ss-w-wrong: #3a3a41;
|
|
10464
11239
|
}
|
|
@@ -11505,7 +12280,7 @@ var WIDGET_CSS = `.ss-w-root { all: revert; }
|
|
|
11505
12280
|
/* live monitor tab bar: underline pattern mirrors .ss-w-ecard-scope; the unread dot uses --ss-w-neg */
|
|
11506
12281
|
.ss-w-tabs { display: flex; align-items: stretch; gap: 2px; border-bottom: 1px solid var(--ss-w-line); overflow-x: auto; scrollbar-width: none; }
|
|
11507
12282
|
.ss-w-tabs::-webkit-scrollbar { display: none; }
|
|
11508
|
-
.ss-w-tab { display: inline-flex; align-items: center; gap: 6px; font-size: 12.5px; font-weight: 620; color: var(--ss-w-faint); background: none; border: none; cursor: pointer; padding: 9px
|
|
12283
|
+
.ss-w-tab { display: inline-flex; align-items: center; gap: 6px; font-size: 12.5px; font-weight: 620; color: var(--ss-w-faint); background: none; border: none; cursor: pointer; padding: 9px 8px; margin-bottom: -1px; border-bottom: 2px solid transparent; flex: none; white-space: nowrap; }
|
|
11509
12284
|
.ss-w-tab[data-on] { color: var(--ss-w-ink); border-bottom-color: var(--ss-w-accent); }
|
|
11510
12285
|
.ss-w-tab-count { font-size: 10.5px; font-weight: 700; color: var(--ss-w-faint); background: var(--ss-w-bubble); border-radius: 999px; padding: 1px 6px; }
|
|
11511
12286
|
.ss-w-tab[data-on] .ss-w-tab-count { color: var(--ss-w-accent); }
|
|
@@ -11587,6 +12362,108 @@ var WIDGET_CSS = `.ss-w-root { all: revert; }
|
|
|
11587
12362
|
.ss-w-sq-row { display: flex; align-items: center; gap: 10px; padding: 7px 2px; border-bottom: 1px solid var(--ss-w-line); }
|
|
11588
12363
|
.ss-w-sq-num { flex: none; width: 20px; text-align: right; font-size: 12px; font-weight: 700; font-variant-numeric: tabular-nums; color: var(--ss-w-faint); }
|
|
11589
12364
|
.ss-w-sq-name { font-size: 13px; font-weight: 600; color: var(--ss-w-ink); }
|
|
12365
|
+
.ss-w-sq-name { flex: 1; min-width: 0; }
|
|
12366
|
+
.ss-w-sq-name-1 { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
|
|
12367
|
+
.ss-w-sq-seg { display: flex; gap: 2px; padding: 2px; border-radius: var(--ss-w-radius); background: var(--ss-w-track); }
|
|
12368
|
+
.ss-w-sq-seg-btn { flex: 1; padding: 5px 8px; border: 0; border-radius: calc(var(--ss-w-radius) - 2px); background: transparent; font: inherit; font-size: 12px; font-weight: 600; color: var(--ss-w-faint); cursor: pointer; }
|
|
12369
|
+
.ss-w-sq-seg-btn[aria-pressed="true"] { background: var(--ss-w-panel); color: var(--ss-w-ink); }
|
|
12370
|
+
.ss-w-sq-seg-btn:focus-visible, .ss-w-sq-tap:focus-visible, .ss-w-pd-back:focus-visible { outline: 2px solid var(--ss-w-accent); outline-offset: 1px; }
|
|
12371
|
+
.ss-w-sq-tap { width: 100%; border: 0; border-bottom: 1px solid var(--ss-w-line); background: transparent; font: inherit; text-align: left; cursor: pointer; }
|
|
12372
|
+
.ss-w-sq-col { flex: none; width: 40px; text-align: center; font-size: 12px; font-weight: 600; font-variant-numeric: tabular-nums; color: var(--ss-w-ink); }
|
|
12373
|
+
.ss-w-sq-head { border-bottom: 0; padding-bottom: 0; }
|
|
12374
|
+
.ss-w-sq-head .ss-w-sq-col { font-size: 10px; font-weight: 700; color: var(--ss-w-faint); }
|
|
12375
|
+
.ss-w-sq-stats { padding-top: 10px; gap: 10px; }
|
|
12376
|
+
.ss-w-sq-card { background: var(--ss-w-panel); border: 1px solid var(--ss-w-line); border-radius: 12px; overflow: hidden; }
|
|
12377
|
+
.ss-w-sq-stats .ss-w-sq-row { display: grid; grid-template-columns: 1fr 26px 30px 36px 20px 20px 20px 20px 36px; gap: 0; padding: 7px 10px; font-size: 11px; }
|
|
12378
|
+
.ss-w-sq-card > :last-child { border-bottom: 0; }
|
|
12379
|
+
.ss-w-sq-pos, .ss-w-sq-c20, .ss-w-sq-c30, .ss-w-sq-c36 { text-align: right; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; font-size: 11px; font-weight: 400; font-variant-numeric: tabular-nums; color: var(--ss-w-ink); }
|
|
12380
|
+
.ss-w-sq-stats .ss-w-sq-head { padding-bottom: 7px; border-bottom: 1px solid var(--ss-w-line); font-size: 9px; font-weight: 700; text-transform: uppercase; letter-spacing: .02em; color: var(--ss-w-faint); }
|
|
12381
|
+
.ss-w-sq-stats .ss-w-sq-head > span { font-size: 9px; font-weight: 700; color: var(--ss-w-faint); }
|
|
12382
|
+
.ss-w-sq-player { display: flex; align-items: center; gap: 6px; min-width: 0; }
|
|
12383
|
+
.ss-w-sq-badge { flex: none; width: 18px; height: 18px; border-radius: 6px; background: var(--ss-w-track); color: var(--ss-w-faint); font-size: 9px; font-weight: 700; display: flex; align-items: center; justify-content: center; }
|
|
12384
|
+
.ss-w-sq-stats .ss-w-sq-name { font-size: 11px; }
|
|
12385
|
+
.ss-w-sq-rtg { font-weight: 700; }
|
|
12386
|
+
.ss-w-sq-rtg-none { color: var(--ss-w-faint); font-weight: 400; }
|
|
12387
|
+
.ss-w-sq-stats .ss-w-pos-ink { color: var(--ss-w-pos); font-weight: 700; }
|
|
12388
|
+
.ss-w-sq-foot { padding: 0 2px; font-size: 10.5px; color: var(--ss-w-faint); }
|
|
12389
|
+
.ss-w-sq-bar { flex: none; display: flex; align-items: center; justify-content: space-between; gap: 8px; margin: 10px 14px 0; }
|
|
12390
|
+
.ss-w-sq-bar .ss-w-sq-seg { margin: 0; }
|
|
12391
|
+
.ss-w-sq-bar .ss-w-sq-seg:only-child { flex: 1; }
|
|
12392
|
+
.ss-w-sq-bar .ss-w-sq-seg:not(:only-child) { flex: none; }
|
|
12393
|
+
.ss-w-sq-eyebrow { flex: 1; min-width: 0; font-size: 10.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--ss-w-faint); }
|
|
12394
|
+
@media (max-width: 429px) { .ss-w-sq-badge { display: none; } }
|
|
12395
|
+
@media (max-width: 359px) {
|
|
12396
|
+
.ss-w-sq-yr { display: none; }
|
|
12397
|
+
.ss-w-sq-stats .ss-w-sq-row { grid-template-columns: 1fr 26px 30px 36px 20px 20px 36px; }
|
|
12398
|
+
}
|
|
12399
|
+
.ss-w-pd-bar { flex: none; display: flex; align-items: center; padding: 12px 16px; border-bottom: 1px solid var(--ss-w-line); line-height: normal; }
|
|
12400
|
+
.ss-w-pd-back { display: flex; align-items: center; gap: 2px; min-height: 32px; padding: 8px 8px 8px 0; margin: -8px 0; border: 0; background: transparent; font: inherit; font-size: 12.5px; font-weight: 600; color: var(--ss-w-faint); cursor: pointer; }
|
|
12401
|
+
.ss-w-pd-back:hover { color: var(--ss-w-ink); }
|
|
12402
|
+
.ss-w-mon-list.ss-w-pd-list { padding: 16px; gap: 14px; line-height: normal; }
|
|
12403
|
+
.ss-w-pd-card { background: var(--ss-w-panel); border: 1px solid var(--ss-w-line); border-radius: 12px; }
|
|
12404
|
+
.ss-w-pd-faint { color: var(--ss-w-faint); }
|
|
12405
|
+
.ss-w-pd-profile { display: flex; gap: 12px; padding: 14px; }
|
|
12406
|
+
.ss-w-pd-photo { flex: none; border-radius: 50%; border: 1px solid var(--ss-w-line); background: var(--ss-w-bubble); object-fit: cover; }
|
|
12407
|
+
.ss-w-pd-avatar { display: flex; align-items: center; justify-content: center; font-weight: 700; color: var(--ss-w-ink); }
|
|
12408
|
+
.ss-w-pd-profile-main { flex: 1; min-width: 0; }
|
|
12409
|
+
.ss-w-pd-name { font-size: 16px; font-weight: 800; color: var(--ss-w-ink); overflow-wrap: break-word; }
|
|
12410
|
+
.ss-w-pd-sub { margin-top: 1px; font-size: 12px; color: var(--ss-w-faint); }
|
|
12411
|
+
/* Two columns as on the board, collapsing to one when a column would drop under 80px (narrow phones). */
|
|
12412
|
+
.ss-w-pd-bio { display: grid; grid-template-columns: repeat(auto-fill, minmax(max(80px, calc((100% - 10px) / 2)), 1fr)); gap: 4px 10px; margin-top: 10px; font-size: 11.5px; }
|
|
12413
|
+
.ss-w-pd-bio-item { min-width: 0; overflow-wrap: break-word; }
|
|
12414
|
+
.ss-w-pd-pitch { position: relative; flex: none; width: 56px; height: 76px; border: 1px solid var(--ss-w-line); border-radius: 6px; background: var(--ss-w-track); }
|
|
12415
|
+
.ss-w-pd-pitch-dot { position: absolute; width: 11px; height: 11px; border-radius: 50%; background: var(--ss-w-accent); border: 2px solid var(--ss-w-nav); transform: translate(-50%, -50%); }
|
|
12416
|
+
.ss-w-pd-avail { display: flex; align-items: center; justify-content: space-between; gap: 10px; padding: 10px 14px; }
|
|
12417
|
+
.ss-w-pd-avail-text { min-width: 0; }
|
|
12418
|
+
.ss-w-pd-avail-next { font-size: 12.5px; font-weight: 700; }
|
|
12419
|
+
.ss-w-pd-avail-note { margin-top: 1px; font-size: 11px; color: var(--ss-w-faint); }
|
|
12420
|
+
.ss-w-pd-pill { flex: none; padding: 4px 10px; border-radius: 999px; font-size: 11px; font-weight: 700; white-space: nowrap; }
|
|
12421
|
+
.ss-w-pd-pill--pos, .ss-w-pd-chip--pos { background: color-mix(in srgb, var(--ss-w-pos) 14%, transparent); color: var(--ss-w-pos); }
|
|
12422
|
+
.ss-w-pd-pill--warn, .ss-w-pd-chip--warn { background: color-mix(in srgb, var(--ss-w-warn) 14%, transparent); color: var(--ss-w-warn); }
|
|
12423
|
+
.ss-w-pd-pill--neg, .ss-w-pd-chip--neg { background: color-mix(in srgb, var(--ss-w-neg) 14%, transparent); color: var(--ss-w-neg); }
|
|
12424
|
+
.ss-w-pd-pill--draw { background: var(--ss-w-track); color: var(--ss-w-faint); }
|
|
12425
|
+
.ss-w-pd-eyebrow { font-size: 10.5px; font-weight: 700; letter-spacing: .06em; text-transform: uppercase; color: var(--ss-w-faint); padding: 0 2px; }
|
|
12426
|
+
.ss-w-pd-eyebrow--block { margin-bottom: 8px; }
|
|
12427
|
+
.ss-w-pd-tiles { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 8px; }
|
|
12428
|
+
.ss-w-pd-tile { min-width: 0; padding: 10px; background: var(--ss-w-panel); border: 1px solid var(--ss-w-line); border-radius: 12px; }
|
|
12429
|
+
.ss-w-pd-tile-label { font-size: 10.5px; color: var(--ss-w-faint); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
|
|
12430
|
+
.ss-w-pd-tile-value { margin-top: 2px; font-size: 18px; font-weight: 800; font-variant-numeric: tabular-nums; }
|
|
12431
|
+
.ss-w-pd-pos-ink { color: var(--ss-w-pos); }
|
|
12432
|
+
/* Below 360px the board's 10px tile padding clips "Matches"/"Minutes" (43px) in a ~34px label box. */
|
|
12433
|
+
@media (max-width: 359px) {
|
|
12434
|
+
.ss-w-pd-tiles { gap: 6px; }
|
|
12435
|
+
.ss-w-pd-tile { padding: 10px 6px; }
|
|
12436
|
+
}
|
|
12437
|
+
.ss-w-pd-perf-head { display: flex; align-items: center; justify-content: space-between; gap: 8px; margin-bottom: 2px; }
|
|
12438
|
+
.ss-w-pd-perf-head .ss-w-pd-eyebrow { flex: 1; min-width: 0; }
|
|
12439
|
+
.ss-w-pd-seg { flex: none; display: flex; gap: 2px; padding: 3px; border-radius: 999px; background: var(--ss-w-track); }
|
|
12440
|
+
.ss-w-pd-seg-btn { padding: 5px 12px; border: 0; border-radius: 999px; background: transparent; font: inherit; font-size: 11.5px; font-weight: 700; line-height: normal; white-space: nowrap; color: var(--ss-w-faint); cursor: pointer; }
|
|
12441
|
+
.ss-w-pd-seg-btn[aria-pressed="true"] { background: var(--ss-w-nav); color: #fff; }
|
|
12442
|
+
.ss-w-pd-seg-btn:focus-visible { outline: 2px solid var(--ss-w-accent); outline-offset: 1px; }
|
|
12443
|
+
.ss-w-pd-perf-sub { margin-bottom: 10px; font-size: 11px; color: var(--ss-w-faint); }
|
|
12444
|
+
.ss-w-pd-perf-head + .ss-w-pd-perf-cards { margin-top: 10px; }
|
|
12445
|
+
.ss-w-pd-perf-cards { display: flex; flex-direction: column; gap: 8px; }
|
|
12446
|
+
.ss-w-pd-perf-card { padding: 14px; }
|
|
12447
|
+
.ss-w-pd-perf-group { margin-bottom: 10px; font-size: 12.5px; font-weight: 700; }
|
|
12448
|
+
.ss-w-pd-bar-row + .ss-w-pd-bar-row { margin-top: 12px; }
|
|
12449
|
+
.ss-w-pd-bar-top { display: flex; align-items: baseline; justify-content: space-between; gap: 8px; margin-bottom: 5px; font-size: 12.5px; }
|
|
12450
|
+
.ss-w-pd-bar-label { min-width: 0; overflow-wrap: break-word; }
|
|
12451
|
+
.ss-w-pd-bar-value { flex: none; font-weight: 700; font-variant-numeric: tabular-nums; }
|
|
12452
|
+
.ss-w-pd-track { height: 6px; border-radius: 999px; background: var(--ss-w-track); overflow: hidden; }
|
|
12453
|
+
.ss-w-pd-fill { height: 100%; border-radius: 999px; }
|
|
12454
|
+
.ss-w-pd-fill--pos { background: var(--ss-w-pos); }
|
|
12455
|
+
.ss-w-pd-fill--warn { background: var(--ss-w-warn); }
|
|
12456
|
+
.ss-w-pd-fill--neg { background: var(--ss-w-neg); }
|
|
12457
|
+
.ss-w-pd-match { display: grid; grid-template-columns: 44px minmax(0, 1fr) auto auto; align-items: center; gap: 10px; padding: 9px 12px; border-bottom: 1px solid var(--ss-w-line); }
|
|
12458
|
+
.ss-w-pd-match:last-child { border-bottom: none; }
|
|
12459
|
+
.ss-w-pd-match-date { font-size: 10.5px; color: var(--ss-w-faint); }
|
|
12460
|
+
.ss-w-pd-match-opp { font-size: 12.5px; font-weight: 600; overflow-wrap: break-word; }
|
|
12461
|
+
.ss-w-pd-match-sub { margin-top: 1px; font-size: 10.5px; color: var(--ss-w-faint); }
|
|
12462
|
+
.ss-w-pd-chip-empty { min-width: 30px; }
|
|
12463
|
+
.ss-w-pd-chip { min-width: 30px; padding: 3px 0; border-radius: 6px; text-align: center; font-size: 11.5px; font-weight: 800; font-variant-numeric: tabular-nums; }
|
|
12464
|
+
.ss-w-rec-list { margin: 0; padding: 0; list-style: none; }
|
|
12465
|
+
.ss-w-rec-value { flex: none; font-size: 13px; font-weight: 700; font-variant-numeric: tabular-nums; color: var(--ss-w-ink); }
|
|
12466
|
+
.ss-w-rec-since { font-size: 12px; color: var(--ss-w-faint); }
|
|
11590
12467
|
/* Per-pin unavailable state: the pin's context line still rendered above (score, name, unpin), but
|
|
11591
12468
|
the pin has neither a card nor history (compose-time rescue failed) -- a small inline note beats
|
|
11592
12469
|
a bare context line with nothing under it. */
|
|
@@ -12190,7 +13067,7 @@ var WIDGET_CSS = `.ss-w-root { all: revert; }
|
|
|
12190
13067
|
`;
|
|
12191
13068
|
|
|
12192
13069
|
// src/StatsWidget.tsx
|
|
12193
|
-
var
|
|
13070
|
+
var import_jsx_runtime107 = require("react/jsx-runtime");
|
|
12194
13071
|
function buildClient(props) {
|
|
12195
13072
|
try {
|
|
12196
13073
|
if ("client" in props && props.client) {
|
|
@@ -12215,24 +13092,24 @@ function injectStyles(root) {
|
|
|
12215
13092
|
function StatsWidget(props) {
|
|
12216
13093
|
const injectedClient = "client" in props ? props.client : void 0;
|
|
12217
13094
|
const cfg = props.config;
|
|
12218
|
-
const built = (0,
|
|
12219
|
-
const logger = (0,
|
|
13095
|
+
const built = (0, import_react69.useMemo)(() => buildClient(props), [injectedClient, cfg?.operatorId, cfg?.publicKey, cfg?.baseUrl]);
|
|
13096
|
+
const logger = (0, import_react69.useMemo)(
|
|
12220
13097
|
() => built ? built.client.createEventLogger({
|
|
12221
13098
|
operatorUserId: cfg?.userContext?.operatorUserId,
|
|
12222
13099
|
anonymousUserId: cfg?.userContext?.anonymousUserId
|
|
12223
13100
|
}) : null,
|
|
12224
13101
|
[built?.client]
|
|
12225
13102
|
);
|
|
12226
|
-
const ui = (0,
|
|
12227
|
-
const rootRef = (0,
|
|
12228
|
-
const introDoneRef = (0,
|
|
12229
|
-
const markIntroDone = (0,
|
|
13103
|
+
const ui = (0, import_react69.useMemo)(() => normalizeUi(props.config ?? { operatorId: "", publicKey: "" }), [props.config]);
|
|
13104
|
+
const rootRef = (0, import_react69.useRef)(null);
|
|
13105
|
+
const introDoneRef = (0, import_react69.useRef)(false);
|
|
13106
|
+
const markIntroDone = (0, import_react69.useCallback)(() => {
|
|
12230
13107
|
introDoneRef.current = true;
|
|
12231
13108
|
}, []);
|
|
12232
13109
|
const convStorageKey = `ss-w-conv:${cfg?.operatorId ?? ""}:${cfg?.userContext?.operatorUserId ?? "anon"}`;
|
|
12233
13110
|
const controller = useChatStream(built?.conversation ?? emptyConversation(), ui.starters, built ? ui.greetingMessage : void 0, convStorageKey);
|
|
12234
|
-
const [hasToday, setHasToday] = (0,
|
|
12235
|
-
const liveCardWatches = (0,
|
|
13111
|
+
const [hasToday, setHasToday] = (0, import_react69.useState)(false);
|
|
13112
|
+
const liveCardWatches = (0, import_react69.useMemo)(() => {
|
|
12236
13113
|
const seen = /* @__PURE__ */ new Set();
|
|
12237
13114
|
const out = [];
|
|
12238
13115
|
for (const msg of controller.state.messages) {
|
|
@@ -12258,19 +13135,19 @@ function StatsWidget(props) {
|
|
|
12258
13135
|
});
|
|
12259
13136
|
const operatorUserId = cfg?.userContext?.operatorUserId;
|
|
12260
13137
|
const anonymousUserId = cfg?.userContext?.anonymousUserId;
|
|
12261
|
-
const getSchedule = (0,
|
|
13138
|
+
const getSchedule = (0, import_react69.useCallback)(
|
|
12262
13139
|
(localDate, utcOffsetMinutes) => built ? built.conversation.getSchedule(localDate, utcOffsetMinutes, operatorUserId, anonymousUserId) : Promise.resolve(null),
|
|
12263
13140
|
[built, operatorUserId, anonymousUserId]
|
|
12264
13141
|
);
|
|
12265
|
-
const postLeagueStar = (0,
|
|
13142
|
+
const postLeagueStar = (0, import_react69.useCallback)(
|
|
12266
13143
|
(competitionId, starred) => built ? built.conversation.starLeague(competitionId, starred, operatorUserId, anonymousUserId) : Promise.resolve(null),
|
|
12267
13144
|
[built, operatorUserId, anonymousUserId]
|
|
12268
13145
|
);
|
|
12269
|
-
const getStates = (0,
|
|
13146
|
+
const getStates = (0, import_react69.useCallback)(
|
|
12270
13147
|
(matchIds) => built ? built.conversation.getStates(matchIds) : Promise.resolve(null),
|
|
12271
13148
|
[built]
|
|
12272
13149
|
);
|
|
12273
|
-
const pinnedMatchIds = (0,
|
|
13150
|
+
const pinnedMatchIds = (0, import_react69.useMemo)(
|
|
12274
13151
|
() => monitor.pins.filter((p) => p.kind === "match").map((p) => p.matchId),
|
|
12275
13152
|
[monitor.pins]
|
|
12276
13153
|
);
|
|
@@ -12285,11 +13162,11 @@ function StatsWidget(props) {
|
|
|
12285
13162
|
pinnedMatchIds
|
|
12286
13163
|
});
|
|
12287
13164
|
const todayHasContent = visibleGroupsOf(discovery.groups, discovery.states).length > 0;
|
|
12288
|
-
(0,
|
|
13165
|
+
(0, import_react69.useEffect)(() => {
|
|
12289
13166
|
setHasToday(todayHasContent);
|
|
12290
13167
|
}, [todayHasContent]);
|
|
12291
|
-
const prevLiveSnapshotRef = (0,
|
|
12292
|
-
(0,
|
|
13168
|
+
const prevLiveSnapshotRef = (0, import_react69.useRef)(monitor.snapshot);
|
|
13169
|
+
(0, import_react69.useEffect)(() => {
|
|
12293
13170
|
const snap = monitor.snapshot;
|
|
12294
13171
|
if (!snap || snap === prevLiveSnapshotRef.current) return;
|
|
12295
13172
|
prevLiveSnapshotRef.current = snap;
|
|
@@ -12327,14 +13204,16 @@ function StatsWidget(props) {
|
|
|
12327
13204
|
const leaderboardResult = useLeaderboard(built?.conversation ?? null, { activeTab: monitor.activeTab });
|
|
12328
13205
|
const clubStandingsResult = useClubStandings(built?.conversation ?? null, { activeTab: monitor.activeTab, enabled: clubFixturesResult.enabled });
|
|
12329
13206
|
const clubSquadResult = useClubSquad(built?.conversation ?? null, { activeTab: monitor.activeTab, enabled: clubFixturesResult.enabled });
|
|
12330
|
-
const
|
|
13207
|
+
const clubSquadStatsResult = useClubSquadStats(built?.conversation ?? null, { activeTab: monitor.activeTab, enabled: clubFixturesResult.enabled });
|
|
13208
|
+
const clubPlayerDetailResult = useClubPlayerDetail(built?.conversation ?? null);
|
|
13209
|
+
const getPricePresets = (0, import_react69.useCallback)(
|
|
12331
13210
|
(locale2) => built ? built.conversation.getPricePresets(locale2, { pool: "open" }) : Promise.resolve(null),
|
|
12332
13211
|
[built]
|
|
12333
13212
|
);
|
|
12334
13213
|
const presetGrid = usePresetGrid({ getPricePresets, isOpen: controller.state.isOpen, locale: ui.presets.lang });
|
|
12335
13214
|
const markTodayActivity = monitor.markTodayActivity;
|
|
12336
|
-
const prevLiveCountRef = (0,
|
|
12337
|
-
(0,
|
|
13215
|
+
const prevLiveCountRef = (0, import_react69.useRef)(0);
|
|
13216
|
+
(0, import_react69.useEffect)(() => {
|
|
12338
13217
|
const rose = prevLiveCountRef.current === 0 && discovery.liveCount > 0;
|
|
12339
13218
|
prevLiveCountRef.current = discovery.liveCount;
|
|
12340
13219
|
if (rose) markTodayActivity();
|
|
@@ -12348,7 +13227,7 @@ function StatsWidget(props) {
|
|
|
12348
13227
|
closePanel: controller.close
|
|
12349
13228
|
});
|
|
12350
13229
|
const markAdded = hostEvents.markAdded;
|
|
12351
|
-
const slip = (0,
|
|
13230
|
+
const slip = (0, import_react69.useMemo)(
|
|
12352
13231
|
() => {
|
|
12353
13232
|
const handler = props.config?.onAddToSlip;
|
|
12354
13233
|
return {
|
|
@@ -12367,7 +13246,7 @@ function StatsWidget(props) {
|
|
|
12367
13246
|
},
|
|
12368
13247
|
[props.config?.onAddToSlip, controller.state.conversationId, markAdded]
|
|
12369
13248
|
);
|
|
12370
|
-
const onDashboardTap = (0,
|
|
13249
|
+
const onDashboardTap = (0, import_react69.useMemo)(
|
|
12371
13250
|
() => built ? createDashboardTapSignal((input) => built.conversation.sendSignal(input), logger) : void 0,
|
|
12372
13251
|
[built, logger]
|
|
12373
13252
|
);
|
|
@@ -12384,11 +13263,11 @@ function StatsWidget(props) {
|
|
|
12384
13263
|
})
|
|
12385
13264
|
}));
|
|
12386
13265
|
const conversationId = controller.state.conversationId ?? void 0;
|
|
12387
|
-
(0,
|
|
13266
|
+
(0, import_react69.useEffect)(() => {
|
|
12388
13267
|
if (!logger) return;
|
|
12389
13268
|
logger.setIdentity({ operatorUserId, anonymousUserId, conversationId });
|
|
12390
13269
|
}, [logger, operatorUserId, anonymousUserId, conversationId]);
|
|
12391
|
-
(0,
|
|
13270
|
+
(0, import_react69.useEffect)(() => {
|
|
12392
13271
|
if (!logger) return;
|
|
12393
13272
|
logger.resume();
|
|
12394
13273
|
const onHide = () => {
|
|
@@ -12406,14 +13285,14 @@ function StatsWidget(props) {
|
|
|
12406
13285
|
logger.dispose();
|
|
12407
13286
|
};
|
|
12408
13287
|
}, [logger]);
|
|
12409
|
-
(0,
|
|
13288
|
+
(0, import_react69.useEffect)(() => {
|
|
12410
13289
|
if (!built || !ui.injectStyles) return;
|
|
12411
13290
|
const node = rootRef.current?.getRootNode();
|
|
12412
13291
|
if (node) injectStyles(node);
|
|
12413
13292
|
}, [built, ui.injectStyles]);
|
|
12414
13293
|
if (!built) return null;
|
|
12415
13294
|
const attrs = themeAttrs(ui);
|
|
12416
|
-
return /* @__PURE__ */ (0,
|
|
13295
|
+
return /* @__PURE__ */ (0, import_jsx_runtime107.jsx)(EventLogContext.Provider, { value: logger, children: /* @__PURE__ */ (0, import_jsx_runtime107.jsx)(HostEventsProvider, { value: hostEvents, children: /* @__PURE__ */ (0, import_jsx_runtime107.jsx)("div", { ref: rootRef, className: "ss-w-root", "data-ss-w-theme": attrs["data-ss-w-theme"], "data-ss-w-pos": attrs["data-ss-w-pos"], style: attrs.style, children: controller.state.isOpen ? /* @__PURE__ */ (0, import_jsx_runtime107.jsx)(
|
|
12417
13296
|
ChatPanel,
|
|
12418
13297
|
{
|
|
12419
13298
|
controller,
|
|
@@ -12427,11 +13306,13 @@ function StatsWidget(props) {
|
|
|
12427
13306
|
clubFixturesResult,
|
|
12428
13307
|
clubStandingsResult,
|
|
12429
13308
|
clubSquadResult,
|
|
13309
|
+
clubSquadStatsResult,
|
|
13310
|
+
clubPlayerDetailResult,
|
|
12430
13311
|
loggedIn: !!operatorUserId,
|
|
12431
13312
|
conversation: built?.conversation ?? null,
|
|
12432
13313
|
presetGrid
|
|
12433
13314
|
}
|
|
12434
|
-
) : /* @__PURE__ */ (0,
|
|
13315
|
+
) : /* @__PURE__ */ (0, import_jsx_runtime107.jsx)(
|
|
12435
13316
|
ChatFab,
|
|
12436
13317
|
{
|
|
12437
13318
|
label: ui.launcherLabel,
|