@eifi1/ui-kit 0.15.3 → 0.15.5
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/README.md +11 -10
- package/dist/chart.d.ts +50 -1
- package/dist/components/alert-banner.js +1 -1
- package/dist/components/alert-banner.js.map +1 -1
- package/dist/components/amount-input.d.ts +5 -3
- package/dist/components/amount-input.js +6 -11
- package/dist/components/amount-input.js.map +1 -1
- package/dist/components/button-group.d.ts +2 -3
- package/dist/components/calculator.d.ts +2 -3
- package/dist/components/chart.d.ts +16 -1
- package/dist/components/chart.js +65 -37
- package/dist/components/chart.js.map +1 -1
- package/dist/components/checkbox.js +1 -1
- package/dist/components/checkbox.js.map +1 -1
- package/dist/components/chip.d.ts +8 -2
- package/dist/components/chip.js +12 -3
- package/dist/components/chip.js.map +1 -1
- package/dist/components/choice-card.js +1 -1
- package/dist/components/choice-card.js.map +1 -1
- package/dist/components/copy-button.d.ts +2 -3
- package/dist/components/error-boundary.js +1 -1
- package/dist/components/error-boundary.js.map +1 -1
- package/dist/components/facing-pair.d.ts +50 -0
- package/dist/components/file-button.d.ts +2 -3
- package/dist/components/file-dropzone.d.ts +2 -3
- package/dist/components/file-dropzone.js +1 -1
- package/dist/components/file-dropzone.js.map +1 -1
- package/dist/components/form-actions.d.ts +2 -3
- package/dist/components/form-actions.js +9 -1
- package/dist/components/form-actions.js.map +1 -1
- package/dist/components/money-field.d.ts +2 -3
- package/dist/components/number-field.d.ts +2 -3
- package/dist/components/number-input.d.ts +2 -3
- package/dist/components/number-input.js +17 -3
- package/dist/components/number-input.js.map +1 -1
- package/dist/components/numpad-sheet.d.ts +2 -3
- package/dist/components/series-chart.d.ts +78 -1
- package/dist/components/series-chart.js +74 -13
- package/dist/components/series-chart.js.map +1 -1
- package/dist/components/settings-fields.d.ts +2 -3
- package/dist/components/text-link.d.ts +2 -3
- package/dist/components/time-input.d.ts +2 -3
- package/dist/components/ui.d.ts +2 -3
- package/dist/components/ui.js +7 -7
- package/dist/components/ui.js.map +1 -1
- package/dist/feedback/feedback-attachment.d.ts +2 -82
- package/dist/feedback/feedback-attachment.js +271 -54
- package/dist/feedback/feedback-attachment.js.map +1 -1
- package/dist/feedback/feedback-dialog.d.ts +2 -105
- package/dist/feedback/feedback-dialog.js +56 -25
- package/dist/feedback/feedback-dialog.js.map +1 -1
- package/dist/feedback/feedback-inbox.d.ts +1 -1
- package/dist/feedback/feedback-thread.d.ts +2 -2
- package/dist/feedback-attachment-BYAHJMOr.d.ts +289 -0
- package/dist/feedback.d.ts +1 -2
- package/dist/hooks/use-file-drop.d.ts +2 -3
- package/dist/i18n/defaults.d.ts +2 -3
- package/dist/i18n/kit-labels.d.ts +2 -3
- package/dist/i18n/kit-labels.js +8 -2
- package/dist/i18n/kit-labels.js.map +1 -1
- package/dist/i18n/locales/de-CH-informal.d.ts +2 -3
- package/dist/i18n/locales/de-CH.d.ts +2 -3
- package/dist/i18n/locales/de-informal.d.ts +2 -3
- package/dist/i18n/locales/de.d.ts +2 -3
- package/dist/i18n/locales/de.js +5 -1
- package/dist/i18n/locales/de.js.map +1 -1
- package/dist/i18n/locales/es.d.ts +2 -3
- package/dist/i18n/locales/es.js +5 -1
- package/dist/i18n/locales/es.js.map +1 -1
- package/dist/i18n/locales/fr.d.ts +2 -3
- package/dist/i18n/locales/fr.js +5 -1
- package/dist/i18n/locales/fr.js.map +1 -1
- package/dist/i18n/locales/hu.d.ts +2 -3
- package/dist/i18n/locales/hu.js +5 -1
- package/dist/i18n/locales/hu.js.map +1 -1
- package/dist/i18n/locales/it.d.ts +2 -3
- package/dist/i18n/locales/it.js +5 -1
- package/dist/i18n/locales/it.js.map +1 -1
- package/dist/i18n/locales/zh.d.ts +2 -3
- package/dist/i18n/locales/zh.js +5 -1
- package/dist/i18n/locales/zh.js.map +1 -1
- package/dist/index.d.ts +4 -5
- package/dist/{kit-labels-BHfRBbHs.d.ts → kit-labels-BD2F7sOz.d.ts} +15 -5
- package/dist/lib/format.d.ts +15 -1
- package/dist/lib/format.js +16 -0
- package/dist/lib/format.js.map +1 -1
- package/dist/rhf/fields.d.ts +2 -3
- package/dist/rhf/form.d.ts +2 -3
- package/dist/rhf.d.ts +2 -3
- package/dist/shell/app-shell.d.ts +2 -3
- package/dist/shell/top-bar-brand.d.ts +2 -3
- package/dist/shell.d.ts +2 -3
- package/dist/theme/palette-derive.d.ts +3 -0
- package/dist/theme/palette-derive.js +7 -0
- package/dist/theme/palette-derive.js.map +1 -1
- package/dist/wizard/stepper-nav.d.ts +2 -3
- package/dist/wizard.d.ts +2 -3
- package/package.json +4 -2
- package/src/components/alert-banner.tsx +1 -1
- package/src/components/amount-input.tsx +16 -14
- package/src/components/chart.tsx +102 -41
- package/src/components/checkbox.tsx +1 -1
- package/src/components/chip.tsx +29 -4
- package/src/components/choice-card.tsx +1 -1
- package/src/components/error-boundary.tsx +1 -1
- package/src/components/file-dropzone.tsx +1 -1
- package/src/components/form-actions.tsx +9 -1
- package/src/components/number-input.tsx +22 -2
- package/src/components/series-chart.tsx +122 -20
- package/src/components/ui.tsx +7 -7
- package/src/feedback/feedback-attachment.tsx +441 -96
- package/src/feedback/feedback-dialog.tsx +147 -50
- package/src/i18n/kit-labels.tsx +19 -1
- package/src/i18n/locales/de.ts +4 -0
- package/src/i18n/locales/es.ts +4 -0
- package/src/i18n/locales/fr.ts +4 -0
- package/src/i18n/locales/hu.ts +4 -0
- package/src/i18n/locales/it.ts +4 -0
- package/src/i18n/locales/zh.ts +4 -0
- package/src/lib/format.ts +30 -0
- package/src/theme/palette-derive.ts +10 -0
- package/tokens.css +9 -1
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { useId, useRef, useState } from "react";
|
|
1
|
+
import { useId, useLayoutEffect, useRef, useState } from "react";
|
|
2
2
|
import type { KeyboardEvent, ReactNode } from "react";
|
|
3
3
|
import { CalculatorButton, type CalculatorButtonLabels } from "./calculator";
|
|
4
4
|
import { NumberPadSheet, type NumberPadSheetLabels } from "./numpad-sheet";
|
|
@@ -191,6 +191,21 @@ export function NumberInput({
|
|
|
191
191
|
const asDisplay = isMobile && variant === "display";
|
|
192
192
|
const showCalc = calculator && !disabled && !isMobile;
|
|
193
193
|
const [focused, setFocused] = useState(false);
|
|
194
|
+
// The unit and the calculator's measured width, reserved as the field's end padding.
|
|
195
|
+
const endRef = useRef<HTMLDivElement>(null);
|
|
196
|
+
const [endWidth, setEndWidth] = useState<number | null>(null);
|
|
197
|
+
const hasEnd = showCalc || suffix !== undefined;
|
|
198
|
+
useLayoutEffect(() => {
|
|
199
|
+
const el = endRef.current;
|
|
200
|
+
if (!hasEnd || !el || typeof ResizeObserver === "undefined") return;
|
|
201
|
+
// The first callback fires on `observe`; no layout (jsdom) keeps the class fallback.
|
|
202
|
+
const observer = new ResizeObserver(() => {
|
|
203
|
+
const width = el.getBoundingClientRect().width;
|
|
204
|
+
setEndWidth(width > 0 ? Math.ceil(width) : null);
|
|
205
|
+
});
|
|
206
|
+
observer.observe(el);
|
|
207
|
+
return () => observer.disconnect();
|
|
208
|
+
}, [hasEnd]);
|
|
194
209
|
// On mobile, focusing opens the numpad bottom sheet instead of the native
|
|
195
210
|
// keyboard (#334); the ref lets its "Done" blur → commit + close.
|
|
196
211
|
const showNumpad = isMobile && !disabled && focused;
|
|
@@ -272,12 +287,17 @@ export function NumberInput({
|
|
|
272
287
|
showCalc && suffix !== undefined ? "pe-16" : showCalc ? "pe-9" : suffix !== undefined ? "pe-8" : undefined,
|
|
273
288
|
invalid && FIELD_INVALID,
|
|
274
289
|
)}
|
|
290
|
+
// The classes above are the fallback; once the end controls are measured the
|
|
291
|
+
// field reserves exactly their width (+4px). A fixed pe-8 for any unit left a
|
|
292
|
+
// "%" in a ~78px table cell 32px of padding and the digits ~32px of room
|
|
293
|
+
// (keksdose live #367); a long unit ("km/h") got too little.
|
|
294
|
+
style={hasEnd && endWidth != null ? { paddingInlineEnd: endWidth + 4 } : undefined}
|
|
275
295
|
/>
|
|
276
296
|
{(showCalc || suffix !== undefined) && (
|
|
277
297
|
// One flex track for both, so the unit and the calculator sit side by side
|
|
278
298
|
// instead of stacking on the same corner — AmountInput's arrangement, which
|
|
279
299
|
// has carried a chip and a calculator together since #430.
|
|
280
|
-
<div className="absolute inset-y-0 end-0 flex items-center">
|
|
300
|
+
<div ref={endRef} className="absolute inset-y-0 end-0 flex items-center">
|
|
281
301
|
{showCalc && (
|
|
282
302
|
<CalculatorButton
|
|
283
303
|
value={value}
|
|
@@ -68,7 +68,13 @@ import { autoAxisBudget, axisUnit, budgetedAxes, type SeriesChartAxisBudget } fr
|
|
|
68
68
|
// The rule stays internal, like the ticks; the one type a public prop names is re-exported.
|
|
69
69
|
export type { SeriesChartAxisBudget } from "./series-chart-budget";
|
|
70
70
|
import { paletteFor } from "../theme/chart-palette";
|
|
71
|
-
import {
|
|
71
|
+
import {
|
|
72
|
+
useKitChartTooltipPlacement,
|
|
73
|
+
useKitLabels,
|
|
74
|
+
useKitLocale,
|
|
75
|
+
type ChartTooltipPlacement,
|
|
76
|
+
} from "../i18n/kit-labels";
|
|
77
|
+
import { useMediaQuery } from "../hooks/use-media-query";
|
|
72
78
|
import { cn } from "../lib/cn";
|
|
73
79
|
|
|
74
80
|
export interface SeriesChartSeries {
|
|
@@ -356,8 +362,49 @@ export interface SeriesChartX {
|
|
|
356
362
|
integerTicks?: boolean;
|
|
357
363
|
}
|
|
358
364
|
|
|
365
|
+
/** Where the tooltip goes — see {@link SeriesChartTooltip.placement}. */
|
|
366
|
+
export type SeriesChartTooltipPlacement = ChartTooltipPlacement;
|
|
367
|
+
|
|
368
|
+
/** Below Tailwind's `sm` — where `"auto"` takes the tooltip off the plot. Narrower than
|
|
369
|
+
* the kit's `PHONE_QUERY` (767 px) on purpose: a tablet's plot is wide enough that the
|
|
370
|
+
* box beside the finger leaves the data in view; a phone's is not. */
|
|
371
|
+
const TOOLTIP_READOUT_QUERY = "(max-width: 639px)";
|
|
372
|
+
|
|
373
|
+
/**
|
|
374
|
+
* The placement a chart actually uses: its own, else the provider's, else `"cursor"`;
|
|
375
|
+
* `"auto"` is `"above"` on a phone (`phone`: below `sm`) and `"cursor"` from `sm` up.
|
|
376
|
+
*/
|
|
377
|
+
export function resolveTooltipPlacement(
|
|
378
|
+
own: SeriesChartTooltipPlacement | undefined,
|
|
379
|
+
fromProvider: SeriesChartTooltipPlacement | undefined,
|
|
380
|
+
phone: boolean,
|
|
381
|
+
): "cursor" | "above" | "below" {
|
|
382
|
+
const wanted = own ?? fromProvider ?? "cursor";
|
|
383
|
+
return wanted === "auto" ? (phone ? "above" : "cursor") : wanted;
|
|
384
|
+
}
|
|
385
|
+
|
|
359
386
|
/** Room for the tooltip beyond the chart — see {@link SeriesChartProps.tooltip}. */
|
|
360
387
|
export interface SeriesChartTooltip {
|
|
388
|
+
/**
|
|
389
|
+
* Where the values under the pointer are shown (keksdose #359: on a phone the box
|
|
390
|
+
* sat under the finger, on the very data it was reporting).
|
|
391
|
+
* - `"cursor"` (the default): the floating box that follows the pointer.
|
|
392
|
+
* - `"above"` / `"below"`: a READOUT row — the same heading and values, flat — in
|
|
393
|
+
* room reserved over or under the plot from the first render, so nothing jumps on
|
|
394
|
+
* the first tap. It follows hover, a tap and the keyboard's stops; the cursor line
|
|
395
|
+
* and the active dot stay on the plot, and no box floats. Idle, it lists the series
|
|
396
|
+
* with "—" under the x axis' title. The row is taken out of the chart's `height`
|
|
397
|
+
* (the plot gets shorter, the page around it does not move).
|
|
398
|
+
* - `"auto"`: `"above"` below Tailwind's `sm` (640 px), `"cursor"` from there up.
|
|
399
|
+
*
|
|
400
|
+
* Default: the provider's `chartTooltipPlacement`, else `"cursor"`.
|
|
401
|
+
*
|
|
402
|
+
* The row is deliberately NOT an `aria-live` region: scrubbing a line announces a
|
|
403
|
+
* value per pixel of travel. A keyboard reader already hears each stop's name
|
|
404
|
+
* ("period — series: value") from the stop itself, and the row stays in the
|
|
405
|
+
* document for a screen reader to read on its way past.
|
|
406
|
+
*/
|
|
407
|
+
placement?: SeriesChartTooltipPlacement;
|
|
361
408
|
/** Let the tooltip run past the chart's own box on that axis instead of recharts
|
|
362
409
|
* clamping it inside. Default: `{ x: true }` when `boundary` is set, else neither. */
|
|
363
410
|
allowEscapeViewBox?: { x?: boolean; y?: boolean };
|
|
@@ -1173,6 +1220,10 @@ function SeriesPlot({
|
|
|
1173
1220
|
// Up here, above the empty state's early return, like every hook.
|
|
1174
1221
|
const [keyStop, setKeyStop] = useState(0);
|
|
1175
1222
|
const [keyFocus, setKeyFocus] = useState<number | undefined>(undefined);
|
|
1223
|
+
// Where the tooltip goes, and — off the plot — the row it is portalled into.
|
|
1224
|
+
const phone = useMediaQuery(TOOLTIP_READOUT_QUERY, false);
|
|
1225
|
+
const placement = resolveTooltipPlacement(tooltip?.placement, useKitChartTooltipPlacement(), phone);
|
|
1226
|
+
const [readout, setReadout] = useState<HTMLDivElement | null>(null);
|
|
1176
1227
|
|
|
1177
1228
|
// The chart's own width, for the automatic axis budget. Its box, not the plot's: the
|
|
1178
1229
|
// box does not change when an axis is hidden, so the rule cannot oscillate. Nothing
|
|
@@ -1495,13 +1546,21 @@ function SeriesPlot({
|
|
|
1495
1546
|
animationEasing: "ease-out" as const,
|
|
1496
1547
|
};
|
|
1497
1548
|
|
|
1498
|
-
|
|
1549
|
+
const inRow = placement !== "cursor";
|
|
1550
|
+
const chart = (
|
|
1499
1551
|
<ChartContainer
|
|
1500
1552
|
ref={setBox}
|
|
1501
1553
|
data-axis-budget={budgeted.length ? budgetKey.replace(/\n/g, " ") : undefined}
|
|
1502
1554
|
config={config}
|
|
1503
|
-
className={cn(
|
|
1504
|
-
|
|
1555
|
+
className={cn(
|
|
1556
|
+
"w-full",
|
|
1557
|
+
// With a readout the chart's height is the whole block's, and the plot takes
|
|
1558
|
+
// what the row leaves.
|
|
1559
|
+
inRow ? "min-h-0 flex-1" : heightClass,
|
|
1560
|
+
className,
|
|
1561
|
+
onPointClick && "cursor-pointer",
|
|
1562
|
+
)}
|
|
1563
|
+
style={inRow ? undefined : heightStyle}
|
|
1505
1564
|
>
|
|
1506
1565
|
<ComposedChart
|
|
1507
1566
|
data={plotted as Record<string, unknown>[]}
|
|
@@ -1607,23 +1666,45 @@ function SeriesPlot({
|
|
|
1607
1666
|
</YAxis>
|
|
1608
1667
|
);
|
|
1609
1668
|
})}
|
|
1610
|
-
|
|
1611
|
-
|
|
1612
|
-
|
|
1613
|
-
|
|
1614
|
-
|
|
1615
|
-
|
|
1616
|
-
|
|
1617
|
-
|
|
1618
|
-
|
|
1619
|
-
|
|
1620
|
-
|
|
1621
|
-
|
|
1622
|
-
|
|
1623
|
-
|
|
1669
|
+
{inRow ? (
|
|
1670
|
+
// Not before the row exists: without its own portal recharts would float this
|
|
1671
|
+
// content over the plot for the first frame.
|
|
1672
|
+
readout && (
|
|
1673
|
+
<ChartTooltip
|
|
1674
|
+
portal={readout}
|
|
1675
|
+
// recharts hides an inactive tooltip; the row shows its idle state instead.
|
|
1676
|
+
wrapperStyle={{ visibility: "visible" }}
|
|
1677
|
+
defaultIndex={focusedStop?.index}
|
|
1678
|
+
content={
|
|
1679
|
+
<ChartTooltipContent
|
|
1680
|
+
variant="readout"
|
|
1681
|
+
idleKeys={series.map((entry) => entry.key)}
|
|
1682
|
+
idleLabel={x.title || undefined}
|
|
1683
|
+
labelFormatter={(value) => xLabel(Number(value))}
|
|
1684
|
+
valueFormatter={valueFormat ?? number}
|
|
1685
|
+
/>
|
|
1686
|
+
}
|
|
1624
1687
|
/>
|
|
1625
|
-
|
|
1626
|
-
|
|
1688
|
+
)
|
|
1689
|
+
) : (
|
|
1690
|
+
<ChartTooltip
|
|
1691
|
+
{...(tooltip?.allowEscapeViewBox || tooltip?.boundary
|
|
1692
|
+
? { allowEscapeViewBox: tooltip.allowEscapeViewBox ?? { x: true } }
|
|
1693
|
+
: {})}
|
|
1694
|
+
// The content shifts itself 12 px off the cursor (or flips) against the
|
|
1695
|
+
// boundary; recharts' own offset on top would double it.
|
|
1696
|
+
{...(tooltip?.boundary ? { offset: 0 } : {})}
|
|
1697
|
+
// The keyboard's stop shows its tooltip as the pointer's would.
|
|
1698
|
+
defaultIndex={focusedStop?.index}
|
|
1699
|
+
content={
|
|
1700
|
+
<ChartTooltipContent
|
|
1701
|
+
labelFormatter={(value) => xLabel(Number(value))}
|
|
1702
|
+
valueFormatter={valueFormat ?? number}
|
|
1703
|
+
boundaryRef={tooltip?.boundary}
|
|
1704
|
+
/>
|
|
1705
|
+
}
|
|
1706
|
+
/>
|
|
1707
|
+
)}
|
|
1627
1708
|
{series.map((entry) => {
|
|
1628
1709
|
const type = entry.type ?? "line";
|
|
1629
1710
|
const yAxisId = entry.axis ?? DEFAULT_Y_AXIS;
|
|
@@ -1787,6 +1868,27 @@ function SeriesPlot({
|
|
|
1787
1868
|
</ComposedChart>
|
|
1788
1869
|
</ChartContainer>
|
|
1789
1870
|
);
|
|
1871
|
+
if (!inRow) return chart;
|
|
1872
|
+
// The row's own box, reserved from the first render: its idle state has the cells the
|
|
1873
|
+
// active one will, so the first tap fills it in rather than pushing the plot down.
|
|
1874
|
+
const row = (
|
|
1875
|
+
<div
|
|
1876
|
+
ref={setReadout}
|
|
1877
|
+
data-tooltip-readout={placement}
|
|
1878
|
+
className={cn(
|
|
1879
|
+
"shrink-0",
|
|
1880
|
+
// Above, the heading line shares the top corner with the zoom's reset button.
|
|
1881
|
+
placement === "above" ? "pb-2 [&_[data-readout-heading]]:pe-32" : "pt-2",
|
|
1882
|
+
)}
|
|
1883
|
+
/>
|
|
1884
|
+
);
|
|
1885
|
+
return (
|
|
1886
|
+
<div className={cn("flex w-full flex-col", heightClass)} style={heightStyle}>
|
|
1887
|
+
{placement === "above" && row}
|
|
1888
|
+
{chart}
|
|
1889
|
+
{placement === "below" && row}
|
|
1890
|
+
</div>
|
|
1891
|
+
);
|
|
1790
1892
|
}
|
|
1791
1893
|
|
|
1792
1894
|
const ZoomablePlot = withChartZoom(SeriesPlot);
|
package/src/components/ui.tsx
CHANGED
|
@@ -46,7 +46,7 @@ const buttonVariantClasses: Record<ButtonVariant, string> = {
|
|
|
46
46
|
ghost:
|
|
47
47
|
"bg-transparent text-[var(--text-primary)] hover:bg-[var(--bg-surface-2)] focus:ring-[var(--brand)]",
|
|
48
48
|
danger:
|
|
49
|
-
"bg-[var(--danger)] text-[var(--danger-contrast)] hover:bg-[var(--danger-hover)] focus:ring-[var(--danger-border)]",
|
|
49
|
+
"bg-[var(--danger)] text-[var(--danger-contrast)] hover:bg-[var(--danger-hover)] focus:ring-[var(--danger-border-strong)]",
|
|
50
50
|
brand:
|
|
51
51
|
"bg-[var(--brand)] text-[var(--brand-contrast)] hover:bg-[var(--brand-hover)] focus:ring-[var(--brand)]",
|
|
52
52
|
// A text link that is still a `<button>` — keksdose's six hand-rolled
|
|
@@ -92,7 +92,7 @@ const BUTTON_TONES: Record<Exclude<ButtonTone, "default">, string> = {
|
|
|
92
92
|
muted:
|
|
93
93
|
"text-[var(--text-secondary)] hover:text-[var(--text-primary)] disabled:hover:text-[var(--text-secondary)]",
|
|
94
94
|
danger:
|
|
95
|
-
"text-[var(--text-secondary)] hover:text-[var(--danger)] focus:ring-[var(--danger-border)] disabled:hover:text-[var(--text-secondary)]",
|
|
95
|
+
"text-[var(--text-secondary)] hover:text-[var(--danger)] focus:ring-[var(--danger-border-strong)] disabled:hover:text-[var(--text-secondary)]",
|
|
96
96
|
};
|
|
97
97
|
|
|
98
98
|
/** Only the two transparent variants take every tone; see {@link ButtonTone}. */
|
|
@@ -103,9 +103,9 @@ const TONED_VARIANTS = new Set<ButtonVariant>(["link", "ghost"]);
|
|
|
103
103
|
// the neutral ones survives the merge.
|
|
104
104
|
const BUTTON_BOXED_DANGER: Partial<Record<ButtonVariant, string>> = {
|
|
105
105
|
secondary:
|
|
106
|
-
"border-[var(--danger-border)] bg-transparent text-[var(--danger)] hover:bg-[var(--danger-bg)] focus:ring-[var(--danger-border)]",
|
|
106
|
+
"border-[var(--danger-border)] bg-transparent text-[var(--danger)] hover:bg-[var(--danger-bg)] focus:ring-[var(--danger-border-strong)]",
|
|
107
107
|
primary:
|
|
108
|
-
"border-[var(--danger-border)] bg-[var(--danger-bg)] text-[var(--danger)] hover:border-[var(--danger)] hover:bg-[var(--danger)] hover:text-[var(--danger-contrast)] focus:ring-[var(--danger-border)] disabled:hover:border-[var(--danger-border)] disabled:hover:bg-[var(--danger-bg)] disabled:hover:text-[var(--danger)]",
|
|
108
|
+
"border-[var(--danger-border)] bg-[var(--danger-bg)] text-[var(--danger)] hover:border-[var(--danger)] hover:bg-[var(--danger)] hover:text-[var(--danger-contrast)] focus:ring-[var(--danger-border-strong)] disabled:hover:border-[var(--danger-border)] disabled:hover:bg-[var(--danger-bg)] disabled:hover:text-[var(--danger)]",
|
|
109
109
|
};
|
|
110
110
|
|
|
111
111
|
// `pressed` on a `link`: the brand colour and a heavier weight, which is exactly what
|
|
@@ -543,8 +543,8 @@ type ColouredTone = "danger" | "warning" | "info" | "success" | "custom";
|
|
|
543
543
|
const ICON_BUTTON_TONES: Record<ColouredTone, { quiet: string; toned: string }> = {
|
|
544
544
|
danger: {
|
|
545
545
|
quiet:
|
|
546
|
-
"text-[var(--text-placeholder)] hover:bg-[var(--danger-bg)] hover:text-[var(--danger)] focus:ring-[var(--danger-border)]",
|
|
547
|
-
toned: "text-[var(--danger)] hover:bg-[var(--danger-bg)] focus:ring-[var(--danger-border)]",
|
|
546
|
+
"text-[var(--text-placeholder)] hover:bg-[var(--danger-bg)] hover:text-[var(--danger)] focus:ring-[var(--danger-border-strong)]",
|
|
547
|
+
toned: "text-[var(--danger)] hover:bg-[var(--danger-bg)] focus:ring-[var(--danger-border-strong)]",
|
|
548
548
|
},
|
|
549
549
|
warning: {
|
|
550
550
|
quiet:
|
|
@@ -1250,7 +1250,7 @@ export const FIELD_FLOATING_PAD = "pt-4 pb-1";
|
|
|
1250
1250
|
// stays exactly the size of a valid one and nothing beside it moves when the value
|
|
1251
1251
|
// arrives.
|
|
1252
1252
|
export const FIELD_INVALID =
|
|
1253
|
-
"border-[var(--danger-border)] ring-1 ring-[var(--danger-border)] focus:border-[var(--danger)] focus:ring-[var(--danger)]";
|
|
1253
|
+
"border-[var(--danger-border-strong)] ring-1 ring-[var(--danger-border-strong)] focus:border-[var(--danger)] focus:ring-[var(--danger)]";
|
|
1254
1254
|
|
|
1255
1255
|
export const FLOATING_INPUT_CLASS = cn(FIELD_BASE, FIELD_FLOATING_PAD, "peer placeholder:text-transparent");
|
|
1256
1256
|
|