@sensiblestats/widget-react 0.15.0 → 0.17.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 +128 -34
- 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 +133 -39
- package/dist/index.js.map +1 -1
- package/dist/styles.css +36 -10
- package/package.json +2 -2
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,27 @@
|
|
|
1
1
|
# @sensiblestats/widget-react
|
|
2
2
|
|
|
3
|
+
## 0.17.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- 5fd5471: Redesign the betting insight card: crest-led three-row layout with competition logo, kickoff time and a bar-chart reasoning strip.
|
|
8
|
+
|
|
9
|
+
### Patch Changes
|
|
10
|
+
|
|
11
|
+
- Updated dependencies [5fd5471]
|
|
12
|
+
- @sensiblestats/widget-sdk@0.15.0
|
|
13
|
+
|
|
14
|
+
## 0.16.0
|
|
15
|
+
|
|
16
|
+
### Minor Changes
|
|
17
|
+
|
|
18
|
+
- 399d6bf: Label market-floor betting insight cards with a distinct "Market price · not a value pick" pill, so a screenshot of one can never read as a recommendation. Older servers that never send `isMarketFloor` render cards exactly as before.
|
|
19
|
+
|
|
20
|
+
### Patch Changes
|
|
21
|
+
|
|
22
|
+
- Updated dependencies [399d6bf]
|
|
23
|
+
- @sensiblestats/widget-sdk@0.14.0
|
|
24
|
+
|
|
3
25
|
## 0.15.0
|
|
4
26
|
|
|
5
27
|
### Minor Changes
|
package/dist/index.cjs
CHANGED
|
@@ -39,6 +39,18 @@ module.exports = __toCommonJS(index_exports);
|
|
|
39
39
|
var import_react12 = require("react");
|
|
40
40
|
var import_widget_sdk5 = require("@sensiblestats/widget-sdk");
|
|
41
41
|
|
|
42
|
+
// src/kickoff.ts
|
|
43
|
+
function formatBettingKickoff(kickoffUtc, ui, locale, now = /* @__PURE__ */ new Date()) {
|
|
44
|
+
const at = new Date(kickoffUtc);
|
|
45
|
+
const intlLocale = locale === "tr" ? "tr-TR" : "en-GB";
|
|
46
|
+
const time = new Intl.DateTimeFormat(intlLocale, { hour: "2-digit", minute: "2-digit" }).format(at);
|
|
47
|
+
const atLocalDate = new Date(at.getFullYear(), at.getMonth(), at.getDate());
|
|
48
|
+
const nowLocalDate = new Date(now.getFullYear(), now.getMonth(), now.getDate());
|
|
49
|
+
const dayDiff = Math.round((atLocalDate.getTime() - nowLocalDate.getTime()) / 864e5);
|
|
50
|
+
const dayLabel = dayDiff === 0 ? ui.today : dayDiff === 1 ? ui.tomorrow : new Intl.DateTimeFormat(intlLocale, { weekday: "short", day: "numeric", month: "short" }).format(at);
|
|
51
|
+
return { dayLabel, time };
|
|
52
|
+
}
|
|
53
|
+
|
|
42
54
|
// src/i18n.ts
|
|
43
55
|
var STRINGS = {
|
|
44
56
|
en: {
|
|
@@ -57,6 +69,7 @@ var STRINGS = {
|
|
|
57
69
|
hideStats: "Hide stats",
|
|
58
70
|
oddsLabel: "Odds",
|
|
59
71
|
liveLabel: "Live",
|
|
72
|
+
marketFloorLabel: "Market price \xB7 not a value pick",
|
|
60
73
|
addToSlip: "Add to slip",
|
|
61
74
|
marketPrices: "Market prices",
|
|
62
75
|
moreLines: "More lines",
|
|
@@ -92,7 +105,10 @@ var STRINGS = {
|
|
|
92
105
|
slipPriceNotAccepted: (from, to) => `Price moved to ${to} (was ${from}). Tap to add.`,
|
|
93
106
|
slipLoginRequired: "Sign in to add to your slip",
|
|
94
107
|
slipSuspended: "Market suspended",
|
|
95
|
-
slipFailed: "Couldn't add to slip. Try again."
|
|
108
|
+
slipFailed: "Couldn't add to slip. Try again.",
|
|
109
|
+
today: "Today",
|
|
110
|
+
tomorrow: "Tomorrow",
|
|
111
|
+
bettingKickoff: (kickoffUtc, now) => formatBettingKickoff(kickoffUtc, STRINGS.en, "en", now)
|
|
96
112
|
},
|
|
97
113
|
tr: {
|
|
98
114
|
launcherLabel: "SensibleStats ile sohbet et",
|
|
@@ -110,6 +126,7 @@ var STRINGS = {
|
|
|
110
126
|
hideStats: "\u0130statistikleri gizle",
|
|
111
127
|
oddsLabel: "Oran",
|
|
112
128
|
liveLabel: "Canl\u0131",
|
|
129
|
+
marketFloorLabel: "Piyasa oran\u0131 \xB7 de\u011Fer bahsi de\u011Fil",
|
|
113
130
|
addToSlip: "Kupona ekle",
|
|
114
131
|
marketPrices: "Piyasa fiyatlar\u0131",
|
|
115
132
|
moreLines: "Di\u011Fer \xE7izgiler",
|
|
@@ -145,7 +162,10 @@ var STRINGS = {
|
|
|
145
162
|
slipPriceNotAccepted: (from, to) => `Oran ${to} oldu (\xF6nceki ${from}). Eklemek i\xE7in dokunun.`,
|
|
146
163
|
slipLoginRequired: "Kupona eklemek i\xE7in giri\u015F yap\u0131n",
|
|
147
164
|
slipSuspended: "Bu market ask\u0131ya al\u0131nd\u0131",
|
|
148
|
-
slipFailed: "Kupona eklenemedi. Tekrar deneyin."
|
|
165
|
+
slipFailed: "Kupona eklenemedi. Tekrar deneyin.",
|
|
166
|
+
today: "Bug\xFCn",
|
|
167
|
+
tomorrow: "Yar\u0131n",
|
|
168
|
+
bettingKickoff: (kickoffUtc, now) => formatBettingKickoff(kickoffUtc, STRINGS.tr, "tr", now)
|
|
149
169
|
}
|
|
150
170
|
};
|
|
151
171
|
function resolveLocaleStrings(locale) {
|
|
@@ -180,6 +200,7 @@ function normalizeUi(cfg) {
|
|
|
180
200
|
hideStats: strings.hideStats,
|
|
181
201
|
oddsLabel: strings.oddsLabel,
|
|
182
202
|
liveLabel: strings.liveLabel,
|
|
203
|
+
marketFloorLabel: strings.marketFloorLabel,
|
|
183
204
|
marketPrices: strings.marketPrices,
|
|
184
205
|
moreLines: strings.moreLines,
|
|
185
206
|
hideLines: strings.hideLines,
|
|
@@ -211,7 +232,10 @@ function normalizeUi(cfg) {
|
|
|
211
232
|
slipPriceNotAccepted: strings.slipPriceNotAccepted,
|
|
212
233
|
slipLoginRequired: strings.slipLoginRequired,
|
|
213
234
|
slipSuspended: strings.slipSuspended,
|
|
214
|
-
slipFailed: strings.slipFailed
|
|
235
|
+
slipFailed: strings.slipFailed,
|
|
236
|
+
today: strings.today,
|
|
237
|
+
tomorrow: strings.tomorrow,
|
|
238
|
+
bettingKickoff: strings.bettingKickoff
|
|
215
239
|
};
|
|
216
240
|
}
|
|
217
241
|
function toClientOptions(cfg) {
|
|
@@ -396,10 +420,17 @@ function toInsightVM(insight) {
|
|
|
396
420
|
matchId: typeof insight.matchId === "number" ? insight.matchId : 0,
|
|
397
421
|
matchOddsId,
|
|
398
422
|
addToSlipEnabled: insight.addToSlipEnabled === true,
|
|
423
|
+
isMarketFloor: insight.isMarketFloor === true,
|
|
399
424
|
oddsDecimal: typeof oddsValue === "number" && Number.isFinite(oddsValue) ? oddsValue : void 0,
|
|
400
425
|
quotedAtUtc: str(insight.odds?.quotedAtUtc),
|
|
401
426
|
previousOdds: previous !== void 0 && direction !== void 0 ? previous.toFixed(2) : void 0,
|
|
402
|
-
movementDirection: previous !== void 0 && direction !== void 0 ? direction : void 0
|
|
427
|
+
movementDirection: previous !== void 0 && direction !== void 0 ? direction : void 0,
|
|
428
|
+
homeTeamName: home,
|
|
429
|
+
awayTeamName: away,
|
|
430
|
+
homeCrest: str(insight.homeTeamImagePath),
|
|
431
|
+
awayCrest: str(insight.awayTeamImagePath),
|
|
432
|
+
competitionCrest: str(insight.competitionImagePath),
|
|
433
|
+
kickoffUtc: str(insight.kickoffUtc)
|
|
403
434
|
};
|
|
404
435
|
}
|
|
405
436
|
function toSlipSelection(vm, conversationId) {
|
|
@@ -989,10 +1020,21 @@ function ScopedStats({ scopes }) {
|
|
|
989
1020
|
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)(StatRows2, { stats: current.stats }, current.key)
|
|
990
1021
|
] });
|
|
991
1022
|
}
|
|
1023
|
+
function hasStatsContent(it) {
|
|
1024
|
+
return !!it.scopes && it.scopes.length >= 2 || it.stats.length > 0;
|
|
1025
|
+
}
|
|
1026
|
+
function initials2(name) {
|
|
1027
|
+
return (name ?? "").trim().slice(0, 1).toUpperCase() || "?";
|
|
1028
|
+
}
|
|
1029
|
+
function Crest2({ url, name, kind }) {
|
|
1030
|
+
const cls = kind === "comp" ? "ss-w-bi-comp-logo" : "ss-w-bi-crest";
|
|
1031
|
+
if (url) return /* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: cls, style: { backgroundImage: `url(${url})` }, "aria-hidden": "true" });
|
|
1032
|
+
return /* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: `${cls} ss-w-bi-crest-mono`, "aria-hidden": "true", children: initials2(name) });
|
|
1033
|
+
}
|
|
992
1034
|
function StatsDisclosure({ it, ui }) {
|
|
993
1035
|
const [open, setOpen] = (0, import_react5.useState)(false);
|
|
994
1036
|
const hasScopes = !!it.scopes && it.scopes.length >= 2;
|
|
995
|
-
const hasStats =
|
|
1037
|
+
const hasStats = hasStatsContent(it);
|
|
996
1038
|
if (!hasStats) return null;
|
|
997
1039
|
return /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("div", { className: "ss-w-bi-stats", children: [
|
|
998
1040
|
/* @__PURE__ */ (0, import_jsx_runtime10.jsxs)(
|
|
@@ -1013,21 +1055,42 @@ function StatsDisclosure({ it, ui }) {
|
|
|
1013
1055
|
}
|
|
1014
1056
|
function InsightCard({ it, ui, slip }) {
|
|
1015
1057
|
const live = it.isLive || it.phase === "live";
|
|
1058
|
+
const kickoff = it.kickoffUtc && ui?.bettingKickoff ? ui.bettingKickoff(it.kickoffUtc) : void 0;
|
|
1059
|
+
const hasNamedTeams = !!it.homeTeamName && !!it.awayTeamName;
|
|
1060
|
+
const showHeader = !!it.competition || live || !!kickoff;
|
|
1061
|
+
const showReason = !!it.text || hasStatsContent(it);
|
|
1016
1062
|
return /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("div", { className: "ss-w-binsight", children: [
|
|
1017
|
-
|
|
1018
|
-
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-
|
|
1019
|
-
|
|
1020
|
-
|
|
1021
|
-
|
|
1022
|
-
/* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("span", { className: "ss-w-bi-
|
|
1023
|
-
/* @__PURE__ */ (0, import_jsx_runtime10.
|
|
1024
|
-
|
|
1025
|
-
|
|
1026
|
-
|
|
1027
|
-
|
|
1063
|
+
showHeader ? /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("div", { className: "ss-w-bi-header", children: [
|
|
1064
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-header-left", children: it.competition ? /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)(import_jsx_runtime10.Fragment, { children: [
|
|
1065
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)(Crest2, { kind: "comp", url: it.competitionCrest, name: it.competition }),
|
|
1066
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-comp", children: it.competition })
|
|
1067
|
+
] }) : null }),
|
|
1068
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("span", { className: "ss-w-bi-header-right", children: [
|
|
1069
|
+
live ? /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("span", { className: "ss-w-bi-live", children: [
|
|
1070
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-live-dot", "aria-hidden": "true" }),
|
|
1071
|
+
ui?.liveLabel ?? "Live"
|
|
1072
|
+
] }) : null,
|
|
1073
|
+
kickoff ? /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("span", { className: "ss-w-bi-kick", children: [
|
|
1074
|
+
kickoff.dayLabel,
|
|
1075
|
+
" ",
|
|
1076
|
+
kickoff.time
|
|
1028
1077
|
] }) : null
|
|
1029
|
-
] })
|
|
1078
|
+
] })
|
|
1079
|
+
] }) : null,
|
|
1080
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("div", { className: "ss-w-bi-body", children: [
|
|
1081
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("div", { className: "ss-w-bi-fixture", children: hasNamedTeams ? /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)(import_jsx_runtime10.Fragment, { children: [
|
|
1082
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)(Crest2, { kind: "team", url: it.homeCrest, name: it.homeTeamName }),
|
|
1083
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-team", children: it.homeTeamName }),
|
|
1084
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-vs", "aria-hidden": "true", children: "vs" }),
|
|
1085
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-team", children: it.awayTeamName }),
|
|
1086
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)(Crest2, { kind: "team", url: it.awayCrest, name: it.awayTeamName })
|
|
1087
|
+
] }) : it.fixture ? /* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-fixture-txt", children: it.fixture }) : null }),
|
|
1030
1088
|
/* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("div", { className: "ss-w-bi-action", children: [
|
|
1089
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("span", { className: "ss-w-bi-mkt", children: [
|
|
1090
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-market", children: it.market }),
|
|
1091
|
+
it.selection ? /* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-sel", children: it.selection }) : null
|
|
1092
|
+
] }),
|
|
1093
|
+
it.isMarketFloor ? /* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-floor", children: ui?.marketFloorLabel ?? "Market price \xB7 not a value pick" }) : null,
|
|
1031
1094
|
it.odds ? /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("span", { className: "ss-w-bi-odds", children: [
|
|
1032
1095
|
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-odds-cap", children: ui?.oddsLabel ?? "Odds" }),
|
|
1033
1096
|
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("b", { children: it.odds }),
|
|
@@ -1037,8 +1100,13 @@ function InsightCard({ it, ui, slip }) {
|
|
|
1037
1100
|
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)(AddToSlipButton, { it, slip, ui })
|
|
1038
1101
|
] })
|
|
1039
1102
|
] }),
|
|
1040
|
-
|
|
1041
|
-
|
|
1103
|
+
showReason ? /* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("div", { className: "ss-w-bi-reason", children: [
|
|
1104
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)("span", { className: "ss-w-bi-chart", "aria-hidden": "true" }),
|
|
1105
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsxs)("div", { className: "ss-w-bi-reason-body", children: [
|
|
1106
|
+
it.text ? /* @__PURE__ */ (0, import_jsx_runtime10.jsx)("p", { className: "ss-w-bi-text", children: it.text }) : null,
|
|
1107
|
+
/* @__PURE__ */ (0, import_jsx_runtime10.jsx)(StatsDisclosure, { it, ui })
|
|
1108
|
+
] })
|
|
1109
|
+
] }) : null,
|
|
1042
1110
|
it.disclaimer ? /* @__PURE__ */ (0, import_jsx_runtime10.jsx)("p", { className: "ss-w-bi-disc", children: it.disclaimer }) : null
|
|
1043
1111
|
] });
|
|
1044
1112
|
}
|
|
@@ -1226,13 +1294,13 @@ function GreetingHeaderBlock({ block }) {
|
|
|
1226
1294
|
// src/components/club-dashboard/FixtureHeroBlock.tsx
|
|
1227
1295
|
var import_react7 = require("react");
|
|
1228
1296
|
var import_jsx_runtime17 = require("react/jsx-runtime");
|
|
1229
|
-
function
|
|
1297
|
+
function initials3(name) {
|
|
1230
1298
|
return name.split(/\s+/).filter(Boolean).slice(0, 2).map((w) => w[0].toUpperCase()).join("");
|
|
1231
1299
|
}
|
|
1232
|
-
function
|
|
1300
|
+
function Crest3({ url, name }) {
|
|
1233
1301
|
const [broken, setBroken] = (0, import_react7.useState)(false);
|
|
1234
1302
|
if (!url || broken) {
|
|
1235
|
-
return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("span", { className: "ss-w-cdash-crest ss-w-cdash-crest--fallback", "aria-hidden": "true", children:
|
|
1303
|
+
return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("span", { className: "ss-w-cdash-crest ss-w-cdash-crest--fallback", "aria-hidden": "true", children: initials3(name) });
|
|
1236
1304
|
}
|
|
1237
1305
|
return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("img", { className: "ss-w-cdash-crest", src: url, alt: "", "aria-hidden": "true", onError: () => setBroken(true) });
|
|
1238
1306
|
}
|
|
@@ -1243,11 +1311,11 @@ function FixtureHeroBlock({
|
|
|
1243
1311
|
}) {
|
|
1244
1312
|
return /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("div", { className: "ss-w-cdash-fixture", children: [
|
|
1245
1313
|
/* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("div", { className: "ss-w-cdash-tie", children: [
|
|
1246
|
-
/* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
|
|
1314
|
+
/* @__PURE__ */ (0, import_jsx_runtime17.jsx)(Crest3, { url: block.homeCrestUrl, name: block.homeName }),
|
|
1247
1315
|
/* @__PURE__ */ (0, import_jsx_runtime17.jsx)("span", { className: "ss-w-cdash-team", children: block.homeName }),
|
|
1248
1316
|
/* @__PURE__ */ (0, import_jsx_runtime17.jsx)("span", { className: "ss-w-cdash-vs", children: "v" }),
|
|
1249
1317
|
/* @__PURE__ */ (0, import_jsx_runtime17.jsx)("span", { className: "ss-w-cdash-team", children: block.awayName }),
|
|
1250
|
-
/* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
|
|
1318
|
+
/* @__PURE__ */ (0, import_jsx_runtime17.jsx)(Crest3, { url: block.awayCrestUrl, name: block.awayName })
|
|
1251
1319
|
] }),
|
|
1252
1320
|
/* @__PURE__ */ (0, import_jsx_runtime17.jsxs)("div", { className: "ss-w-cdash-fixture-meta", children: [
|
|
1253
1321
|
/* @__PURE__ */ (0, import_jsx_runtime17.jsx)("span", { className: "ss-w-cdash-kickoff", children: ui.clubKickoff(block.kickoffUnix * 1e3) }),
|
|
@@ -1641,25 +1709,51 @@ var WIDGET_CSS = `.ss-w-root { all: revert; }
|
|
|
1641
1709
|
|
|
1642
1710
|
/* betting insights */
|
|
1643
1711
|
.ss-w-binsights { display: flex; flex-direction: column; gap: 7px; }
|
|
1644
|
-
.ss-w-binsight { background: var(--ss-w-panel); border: 1px solid var(--ss-w-line); border-radius: 12px; border-left: 3px solid var(--ss-w-accent); padding: 9px 11px; display: flex; flex-direction: column; gap:
|
|
1645
|
-
|
|
1646
|
-
|
|
1647
|
-
.ss-w-bi-
|
|
1712
|
+
.ss-w-binsight { background: var(--ss-w-panel); border: 1px solid var(--ss-w-line); border-radius: 12px; border-left: 3px solid var(--ss-w-accent); padding: 9px 11px; display: flex; flex-direction: column; gap: 8px; }
|
|
1713
|
+
|
|
1714
|
+
/* row 1: competition logo + name on the left, live badge + kickoff on the right */
|
|
1715
|
+
.ss-w-bi-header { display: flex; align-items: center; justify-content: space-between; gap: 8px; min-width: 0; padding-bottom: 7px; border-bottom: 1px solid var(--ss-w-line); }
|
|
1716
|
+
.ss-w-bi-header-left { display: inline-flex; align-items: center; gap: 6px; min-width: 0; }
|
|
1717
|
+
.ss-w-bi-header-right { display: inline-flex; align-items: center; gap: 8px; flex: none; }
|
|
1718
|
+
.ss-w-bi-comp { font-size: 10.5px; color: var(--ss-w-faint); font-weight: 600; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
|
|
1719
|
+
.ss-w-bi-kick { font-size: 10.5px; font-weight: 600; color: var(--ss-w-faint); white-space: nowrap; flex: none; }
|
|
1648
1720
|
.ss-w-bi-live { font-size: 8.5px; font-weight: 700; letter-spacing: .04em; text-transform: uppercase; color: #fff; background: #c0392b; border-radius: 4px; padding: 1px 5px; display: inline-flex; align-items: center; gap: 4px; flex: none; }
|
|
1649
1721
|
.ss-w-bi-live-dot { width: 5px; height: 5px; border-radius: 50%; background: #fff; }
|
|
1650
|
-
.ss-w-bi-
|
|
1651
|
-
|
|
1652
|
-
|
|
1653
|
-
.ss-w-bi-
|
|
1654
|
-
.ss-w-bi-
|
|
1655
|
-
.ss-w-bi-
|
|
1722
|
+
.ss-w-bi-floor { font-size: 8.5px; font-weight: 700; letter-spacing: .04em; text-transform: uppercase; color: var(--ss-w-faint); background: var(--ss-w-bubble); border: 1px solid var(--ss-w-line); border-radius: 4px; padding: 1px 5px; display: inline-flex; align-items: center; align-self: flex-start; flex: none; }
|
|
1723
|
+
|
|
1724
|
+
/* crests -- CSS background-image on a span, never <img> (matches .ss-w-ecard-crest precedent) */
|
|
1725
|
+
.ss-w-bi-comp-logo { width: 15px; height: 15px; flex: none; display: block; border-radius: 50%; background-size: contain; background-repeat: no-repeat; background-position: center; }
|
|
1726
|
+
.ss-w-bi-crest { width: 22px; height: 22px; flex: none; display: block; border-radius: 50%; background-size: contain; background-repeat: no-repeat; background-position: center; background-color: var(--ss-w-bubble); border: 1px solid var(--ss-w-line); }
|
|
1727
|
+
.ss-w-bi-crest-mono { display: grid; place-items: center; font-size: 9px; font-weight: 700; color: var(--ss-w-accent); background: color-mix(in srgb, var(--ss-w-accent) 16%, var(--ss-w-panel)); }
|
|
1728
|
+
|
|
1729
|
+
/* row 2: crest-flanked fixture on the left, boxed action panel on the right */
|
|
1730
|
+
.ss-w-bi-body { display: flex; align-items: center; gap: 10px; }
|
|
1731
|
+
.ss-w-bi-fixture { display: flex; align-items: center; gap: 6px; min-width: 0; flex: 1; font-size: 12px; font-weight: 650; color: var(--ss-w-ink); }
|
|
1732
|
+
.ss-w-bi-team { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
|
|
1733
|
+
.ss-w-bi-vs { font-size: 10px; font-weight: 600; color: var(--ss-w-faint); flex: none; }
|
|
1734
|
+
.ss-w-bi-fixture-txt { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
|
|
1735
|
+
.ss-w-bi-action { margin-left: auto; flex: none; display: flex; flex-direction: column; align-items: stretch; gap: 6px; background: var(--ss-w-bubble); border: 1px solid var(--ss-w-line); border-radius: 12px; padding: 8px 10px; }
|
|
1656
1736
|
.ss-w-bi-action .ss-w-slip > button { flex: 1; text-align: center; }
|
|
1657
1737
|
/* The action column is narrow; let its toast size to its own text and anchor to the card's right edge instead of being clipped to the button width. */
|
|
1658
1738
|
.ss-w-bi-action .ss-w-toast { left: auto; right: 0; width: max-content; max-width: 210px; white-space: normal; }
|
|
1739
|
+
.ss-w-bi-mkt { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
|
|
1740
|
+
.ss-w-bi-market { font-size: 13.5px; font-weight: 700; line-height: 1.25; color: var(--ss-w-ink); }
|
|
1741
|
+
.ss-w-bi-sel { font-size: 11.5px; line-height: 1.3; color: var(--ss-w-faint); }
|
|
1659
1742
|
.ss-w-bi-odds { flex: none; display: flex; flex-direction: column; align-items: center; justify-content: center; text-align: center; gap: 1px; background: color-mix(in srgb, var(--ss-w-accent) 12%, var(--ss-w-panel)); border: 1px solid color-mix(in srgb, var(--ss-w-accent) 30%, var(--ss-w-line)); border-radius: 10px; padding: 4px 11px; min-width: 62px; }
|
|
1660
1743
|
.ss-w-bi-odds-cap { font-size: 9px; font-weight: 700; letter-spacing: .09em; text-transform: uppercase; color: var(--ss-w-faint); }
|
|
1661
1744
|
.ss-w-bi-odds b { font-size: 19px; font-family: ui-monospace, monospace; font-weight: 700; font-variant-numeric: tabular-nums; color: var(--ss-w-accent); line-height: 1.1; }
|
|
1662
1745
|
.ss-w-bi-book { font-size: 9.5px; color: var(--ss-w-faint); }
|
|
1746
|
+
|
|
1747
|
+
/* row 3: bar-chart glyph + reasoning prose + stats-expander chevron, in a subtle strip */
|
|
1748
|
+
.ss-w-bi-reason { display: flex; align-items: flex-start; gap: 8px; background: var(--ss-w-bubble); border-radius: 10px; padding: 8px 10px; }
|
|
1749
|
+
.ss-w-bi-chart { flex: none; width: 13px; height: 12px; margin-top: 2px; opacity: .55;
|
|
1750
|
+
background:
|
|
1751
|
+
linear-gradient(var(--ss-w-accent), var(--ss-w-accent)) left / 3px 55% no-repeat,
|
|
1752
|
+
linear-gradient(var(--ss-w-accent), var(--ss-w-accent)) center / 3px 100% no-repeat,
|
|
1753
|
+
linear-gradient(var(--ss-w-accent), var(--ss-w-accent)) right / 3px 75% no-repeat;
|
|
1754
|
+
background-position: left bottom, center bottom, right bottom;
|
|
1755
|
+
}
|
|
1756
|
+
.ss-w-bi-reason-body { display: flex; flex-direction: column; gap: 8px; min-width: 0; flex: 1; }
|
|
1663
1757
|
.ss-w-bi-text { font-size: 12px; line-height: 1.45; color: var(--ss-w-ink); }
|
|
1664
1758
|
.ss-w-bi-stats { display: flex; flex-direction: column; gap: 8px; }
|
|
1665
1759
|
.ss-w-bi-toggle { align-self: flex-start; display: inline-flex; align-items: center; gap: 5px; background: none; border: none; color: var(--ss-w-accent); font: inherit; font-size: 11.5px; font-weight: 600; padding: 2px 0; cursor: pointer; }
|