28 KiB
time-range-picker — alcance de tema: análisis y propuesta
Generado por
node --import tsx/esm scripts/theming-census.ts --report. Lo medido y la propuesta se regeneran; el Veredicto (§5) se conserva. Vista de conjunto: README · método y protocolo:PLAN-theming.md§1, §2, §7.
- Medido: 2026-08-22 · Alcance: 20% — 17 de 84 knobs por token público
- Knobs de apariencia: 88 — público 17 · privado 19 · global 33 · literal 15 · sistema 4 · excepción 0 (los dos últimos, fuera del ratio)
- Contrato hoy (
lib/recipes/base.ts): 22 pública(s) —accent-border,accent-track,accent-text,clock-column-gap,clock-width,clock-fg,clock-font-family,clock-font-size,clock-line-height,clock-hand-hour,clock-hand-minute,clock-hand-second,day-period-toggle-gap,day-period-toggle-radius,day-period-toggle-bg,day-period-toggle-border,day-period-item-min-width,day-period-item-padding-inline,day-period-item-padding-block,day-period-item-font-size,day-period-item-font-weight,day-period-item-fg - Eje
size: sí · ficheros:time-range-picker.css
1. Knobs fuera de alcance
1.1 Directo a primitivo global (33)
| # | fichero:línea | selector | propiedad | valor |
|---|---|---|---|---|
| 1 | time-range-picker.css:23 |
[data-time-range-picker] |
color |
var(--field-control-fg) ⤴ prestado de field |
| 2 | time-range-picker.css:24 |
[data-time-range-picker] |
font-family |
var(--field-font-family) ⤴ prestado de field |
| 3 | time-range-picker.css:26 |
[data-time-range-picker] |
line-height |
var(--field-control-line-height) ⤴ prestado de field |
| 4 | time-range-picker.css:107 |
[data-time-range-picker-trigger] |
border |
var(--field-control-border-width) solid var(--field-control-border) ⤴ prestado de field |
| 5 | time-range-picker.css:108 |
[data-time-range-picker-trigger] |
border-radius |
var(--field-control-radius) ⤴ prestado de field |
| 6 | time-range-picker.css:109 |
[data-time-range-picker-trigger] |
background |
var(--field-control-bg) ⤴ prestado de field |
| 7 | time-range-picker.css:135 |
[data-time-range-picker-trigger][data-disabled], [data-time-range-picker-trigger]:disabled |
opacity |
var(--field-disabled-opacity) ⤴ prestado de field |
| 8 | time-range-picker.css:153 |
[data-time-range-field-input] [data-time-range-picker-trigger] |
border-radius |
var(--radius-sm) |
| 9 | time-range-picker.css:155 |
[data-time-range-field-input] [data-time-range-picker-trigger] |
color |
var(--field-control-fg) ⤴ prestado de field |
| 10 | time-range-picker.css:169 |
[data-time-range-field-input] [data-time-range-picker-trigger]:focus-visible |
background |
var(--field-segment-active-bg) ⤴ prestado de field |
| 11 | time-range-picker.css:170 |
[data-time-range-field-input] [data-time-range-picker-trigger]:focus-visible |
color |
var(--field-segment-active-text) ⤴ prestado de field |
| 12 | time-range-picker.css:191 |
[data-time-range-picker-clock] |
padding |
var(--space-2-5) |
| 13 | time-range-picker.css:262 |
[data-time-range-picker-clock] [data-time-range-picker-day-period-toggle] [data-toggle-group-item][data-state='on']:hover |
background |
var(--toggle-palette-solid) ⤴ prestado de toggle |
| 14 | time-range-picker.css:263 |
[data-time-range-picker-clock] [data-time-range-picker-day-period-toggle] [data-toggle-group-item][data-state='on']:hover |
border-color |
var(--toggle-palette-solid) ⤴ prestado de toggle |
| 15 | time-range-picker.css:272 |
.time-range-picker-endpoint |
gap |
var(--space-2) |
| 16 | time-range-picker.css:285 |
.time-range-picker-endpoint:first-child::after |
inline-size |
var(--border-width) |
| 17 | time-range-picker.css:289 |
.time-range-picker-endpoint:first-child::after |
background |
var(--color-border-strong) |
| 18 | time-range-picker.css:296 |
.time-range-picker-endpoint-label |
font-weight |
var(--font-weight-semibold) |
| 19 | time-range-picker.css:298 |
.time-range-picker-endpoint-label |
letter-spacing |
var(--tracking-wider) |
| 20 | time-range-picker.css:299 |
.time-range-picker-endpoint-label |
color |
var(--color-content-secondary) |
| 21 | time-range-picker.css:308 |
.time-range-picker-slider-label |
color |
var(--color-content-muted) |
| 22 | time-range-picker.css:309 |
.time-range-picker-slider-label |
font-family |
var(--style-label-font-family) |
| 23 | time-range-picker.css:312 |
.time-range-picker-slider-label |
font-weight |
var(--font-weight-medium) |
| 24 | time-range-picker.css:313 |
.time-range-picker-slider-label |
letter-spacing |
var(--tracking-caps) |
| 25 | time-range-picker.css:330 |
.time-range-picker-scale |
padding-inline |
calc(var(--_slider-thumb-size, 1rem) / 2) |
| 26 | time-range-picker.css:342 |
.time-range-picker-scale-tick |
color |
var(--color-content-muted) |
| 27 | time-range-picker.css:343 |
.time-range-picker-scale-tick |
font-family |
var(--font-family-mono, var(--style-label-font-family)) |
| 28 | time-range-picker.css:345 |
.time-range-picker-scale-tick |
font-size |
var(--font-size-xxs) |
| 29 | time-range-picker.css:354 |
.time-range-picker-scale-mark |
background |
var(--color-border-default) |
| 30 | time-range-picker.css:389 |
[data-time-range-picker-clock] [data-slider-thumb] |
box-shadow |
var(--slider-thumb-shadow), 0 0 0 2px var(--color-surface-default) ⤴ prestado de slider |
| 31 | time-range-picker.css:395 |
[data-time-range-picker-clock] [data-slider-thumb]:focus-visible |
box-shadow |
var(--slider-thumb-shadow), 0 0 0 2px var(--color-surface-default) ⤴ prestado de slider |
| 32 | time-range-picker.css:468 |
[data-time-range-picker][data-invalid] [data-time-range-picker-trigger] |
border-color |
var(--color-threat-border) |
| 33 | time-range-picker.css:475 |
[data-time-range-picker][data-invalid] [data-time-range-picker-trigger]:hover |
border-color |
var(--color-threat-border) |
1.2 A través de un privado (19)
| # | fichero:línea | selector | propiedad | valor |
|---|---|---|---|---|
| 1 | time-range-picker.css:20 |
[data-time-range-picker] |
gap |
var(--space-1-5) var(--_time-range-picker-gap) |
| 2 | time-range-picker.css:25 |
[data-time-range-picker] |
font-size |
var(--_time-range-picker-font-size) |
| 3 | time-range-picker.css:104 |
[data-time-range-picker-trigger] |
inline-size |
var(--_time-range-picker-height) |
| 4 | time-range-picker.css:105 |
[data-time-range-picker-trigger] |
block-size |
var(--_time-range-picker-height) |
| 5 | time-range-picker.css:120 |
[data-time-range-picker-trigger]:hover |
border-color |
var(--_time-range-picker-accent-border) |
| 6 | time-range-picker.css:121 |
[data-time-range-picker-trigger]:hover |
background |
var(--_time-range-picker-accent-track) |
| 7 | time-range-picker.css:122 |
[data-time-range-picker-trigger]:hover |
color |
var(--_time-range-picker-accent-text) |
| 8 | time-range-picker.css:126 |
[data-time-range-picker-trigger]:focus-visible |
border-color |
var(--_time-range-picker-accent-border) |
| 9 | time-range-picker.css:148 |
[data-time-range-field-input] [data-time-range-picker-trigger] |
inline-size |
calc(var(--_time-range-picker-height) - var(--space-2)) |
| 10 | time-range-picker.css:149 |
[data-time-range-field-input] [data-time-range-picker-trigger] |
block-size |
calc(var(--_time-range-picker-height) - var(--space-2)) |
| 11 | time-range-picker.css:162 |
[data-time-range-field-input] [data-time-range-picker-trigger]:hover |
background |
var(--_time-range-picker-accent-track) |
| 12 | time-range-picker.css:163 |
[data-time-range-field-input] [data-time-range-picker-trigger]:hover |
color |
var(--_time-range-picker-accent-text) |
| 13 | time-range-picker.css:295 |
.time-range-picker-endpoint-label |
font-size |
var(--_time-range-picker-label-font, var(--font-size-sm)) |
| 14 | time-range-picker.css:311 |
.time-range-picker-slider-label |
font-size |
var(--_time-range-picker-channel-font, var(--font-size-xxs)) |
| 15 | time-range-picker.css:388 |
[data-time-range-picker-clock] [data-slider-thumb] |
border-color |
var(--_time-range-picker-slider-accent, var(--_time-range-picker-accent-border)) |
| 16 | time-range-picker.css:403 |
[data-time-range-picker-clock] [data-slider-range] |
background |
var(--_time-range-picker-slider-accent, var(--_time-range-picker-accent-border)) |
| 17 | time-range-picker.css:408 |
[data-time-range-picker-clock] [data-endpoint='end'] [data-slider-range] |
background |
color-mix( in oklch, var(--_time-range-picker-slider-accent, var(--_time-range-picker-accent-border)) 70%, var(--color-content-muted) ) |
| 18 | time-range-picker.css:441 |
[data-time-range-picker-day-period-item][data-checked] |
background |
var(--_time-range-picker-accent-track) |
| 19 | time-range-picker.css:442 |
[data-time-range-picker-day-period-item][data-checked] |
color |
var(--_time-range-picker-accent-text) |
1.3 Literales (15)
| # | fichero:línea | selector | propiedad | valor |
|---|---|---|---|---|
| 1 | time-range-picker.css:21 |
[data-time-range-picker] |
inline-size |
100% |
| 2 | time-range-picker.css:226 |
[data-time-range-picker-clock] |
min-inline-size |
14rem |
| 3 | time-range-picker.css:239 |
[data-time-range-picker-clock] [data-slider] |
inline-size |
100% |
| 4 | time-range-picker.css:314 |
.time-range-picker-slider-label |
line-height |
1 |
| 5 | time-range-picker.css:321 |
.time-range-picker-slider |
gap |
2px |
| 6 | time-range-picker.css:323 |
.time-range-picker-slider |
inline-size |
100% |
| 7 | time-range-picker.css:328 |
.time-range-picker-scale |
block-size |
0.875rem |
| 8 | time-range-picker.css:329 |
.time-range-picker-scale |
inline-size |
100% |
| 9 | time-range-picker.css:341 |
.time-range-picker-scale-tick |
gap |
1px |
| 10 | time-range-picker.css:346 |
.time-range-picker-scale-tick |
line-height |
1 |
| 11 | time-range-picker.css:352 |
.time-range-picker-scale-mark |
inline-size |
1px |
| 12 | time-range-picker.css:353 |
.time-range-picker-scale-mark |
block-size |
4px |
| 13 | time-range-picker.css:420 |
[data-time-range-picker-day-period-toggle] |
padding |
2px |
| 14 | time-range-picker.css:447 |
[data-time-range-picker-day-period-item] input[type='radio'] |
inline-size |
1px |
| 15 | time-range-picker.css:448 |
[data-time-range-picker-day-period-item] input[type='radio'] |
block-size |
1px |
1.4 Excepciones firmadas (0) — fuera del ratio
Literales que llevan su anotación /* literal: <razón> */ en la propia
declaración: la válvula de recipe-contract §3, la misma que honra
component-audit. Una desviación firmada no es deuda — se listan para que la
razón se lea, no para acuñarlas.
Ninguno.
2. Sistema transversal (4) — informativo, fuera del ratio
Un tema los alcanza a nivel de sistema, por diseño (recipe-contract §2).
| # | fichero:línea | selector | propiedad | valor |
|---|---|---|---|---|
| 1 | time-range-picker.css:128 |
[data-time-range-picker-trigger]:focus-visible |
outline |
var(--focus-ring-width) solid var(--focus-ring-color) |
| 2 | time-range-picker.css:398 |
[data-time-range-picker-clock] [data-slider-thumb]:focus-visible |
outline |
var(--focus-ring-width) solid var(--focus-ring-color) |
| 3 | time-range-picker.css:463 |
[data-time-range-picker][data-readonly] [data-time-range-picker-trigger], [data-time-range-picker][data-readonly] [data-time-range-picker-clear] |
opacity |
var(--opacity-muted) |
| 4 | time-range-picker.css:469 |
[data-time-range-picker][data-invalid] [data-time-range-picker-trigger] |
box-shadow |
0 0 0 var(--focus-ring-offset) var(--color-surface-default), 0 0 0 calc(var(--focus-ring-offset) + var(--focus-ring-width)) var(--color-threat-border) |
3. Privados de la receta — ¿de dónde sale su valor?
| privado | declaraciones | valor(es) | origen | ¿deriva de un público? |
|---|---|---|---|---|
--_time-range-picker-height |
4 | var(--field-control-height-md), var(--field-control-height-xs), var(--field-control-height-sm), var(--field-control-height-lg) |
global | no |
--_time-range-picker-gap |
4 | var(--space-1), var(--space-0-5), var(--space-1-5) |
global | no |
--_time-range-picker-font-size |
4 | var(--field-control-font-size-md), var(--field-control-font-size-xs), var(--field-control-font-size-sm), var(--field-control-font-size-lg) |
global | no |
--_time-range-picker-accent-border |
8 | var(--time-range-picker-accent-border), var(--color-secondary-border), var(--color-neutral-border), var(--color-affirm-border), var(--color-fulfill-border), var(--color-risk-border) …(+2) |
global, public | no |
--_time-range-picker-accent-track |
8 | var(--time-range-picker-accent-track), var(--color-secondary-track), var(--color-neutral-track), var(--color-affirm-track), var(--color-fulfill-track), var(--color-risk-track) …(+2) |
global, public | no |
--_time-range-picker-accent-text |
8 | var(--time-range-picker-accent-text), var(--color-secondary-text), var(--color-neutral-text), var(--color-affirm-text), var(--color-fulfill-text), var(--color-risk-text) …(+2) |
global, public | no |
--_time-range-picker-column-gap |
1 | var(--time-range-picker-clock-column-gap) |
public | sí |
--_time-range-picker-label-font |
4 | var(--font-size-sm), var(--font-size-xxs), var(--font-size-xs), var(--font-size-md) |
global | no |
--_time-range-picker-channel-font |
4 | var(--font-size-xxs), var(--font-size-xs) |
global | no |
--_time-range-picker-slider-accent |
3 | var(--time-range-picker-clock-hand-hour), var(--time-range-picker-clock-hand-minute), var(--time-range-picker-clock-hand-second) |
public | sí |
4. Propuesta de corrección
- Consume la capa compartida
picker-shell. Un eje que la capa posee se consume comovar(--_x, var(--x)); el consumidor no acuña--time-range-picker-{eje}para él — sería un vocabulario paralelo (README deeidos/components, «Capas compartidas» regla 2). - Consume tokens públicos de
field,slider,toggle. Un token prestado importa la semántica de su dueño: la corrección no es duplicarlo con prefijo propio, sino la decisión de familia que la auditoría de fase 1 dejó registrada (theming-audit.md§B, familia calendar). - Tiene eje
size: los tokens dimensionales van por talla ({part}-{eje}-{k}) apuntando al bundle--size-{k}-*, nunca al primitivo crudo (theming §5; el guardrecipe-css-contractprohíbe el primitivo).
4.1 Tokens a declarar en lib/recipes/base.ts (45)
Valor verbatim del CSS de hoy: el default no se mueve, sólo cambia quién
puede moverlo. Nombres derivados de recipe-contract §1 (ejes lógicos, talla
al final) y theming §6.7 (slots de color, modificador delante). Un token con
DOS valores distintos es una colisión de nombre: son dos knobs, o el nombre
no distingue lo que debería — se marca ⚠.
token (--time-range-picker-…) |
scope TSC | valor propuesto | usos |
|---|---|---|---|
hover-trigger-bg |
root |
⚠ var(--time-range-picker-accent-track) / var(--color-secondary-track) / var(--color-neutral-track) / var(--color-affirm-track) / var(--color-fulfill-track) / var(--color-risk-track) / var(--color-threat-track) / var(--color-loss-track) |
16 |
hover-trigger-fg |
root |
⚠ var(--time-range-picker-accent-text) / var(--color-secondary-text) / var(--color-neutral-text) / var(--color-affirm-text) / var(--color-fulfill-text) / var(--color-risk-text) / var(--color-threat-text) / var(--color-loss-text) |
16 |
hover-trigger-border |
root |
⚠ var(--time-range-picker-accent-border) / var(--color-secondary-border) / var(--color-neutral-border) / var(--color-affirm-border) / var(--color-fulfill-border) / var(--color-risk-border) / var(--color-threat-border) / var(--color-loss-border) |
8 |
trigger-border |
root |
⚠ var(--time-range-picker-accent-border) / var(--color-secondary-border) / var(--color-neutral-border) / var(--color-affirm-border) / var(--color-fulfill-border) / var(--color-risk-border) / var(--color-threat-border) / var(--color-loss-border) |
8 |
on-day-period-item-bg |
root |
⚠ var(--time-range-picker-accent-track) / var(--color-secondary-track) / var(--color-neutral-track) / var(--color-affirm-track) / var(--color-fulfill-track) / var(--color-risk-track) / var(--color-threat-track) / var(--color-loss-track) |
8 |
on-day-period-item-fg |
root |
⚠ var(--time-range-picker-accent-text) / var(--color-secondary-text) / var(--color-neutral-text) / var(--color-affirm-text) / var(--color-fulfill-text) / var(--color-risk-text) / var(--color-threat-text) / var(--color-loss-text) |
8 |
fg |
root |
⚠ var(--field-control-fg) / var(--color-content-secondary) / var(--color-content-muted) |
4 |
font-family |
root |
⚠ var(--field-font-family) / var(--style-label-font-family) / var(--font-family-mono, var(--style-label-font-family)) |
3 |
font-size-md |
size:md |
⚠ var(--field-control-font-size-md) / var(--font-size-sm) / var(--font-size-xxs) |
3 |
font-size-xs |
size:xs |
⚠ var(--field-control-font-size-xs) / var(--font-size-xxs) |
3 |
font-size-sm |
size:sm |
⚠ var(--field-control-font-size-sm) / var(--font-size-xs) / var(--font-size-xxs) |
3 |
font-size-lg |
size:lg |
⚠ var(--field-control-font-size-lg) / var(--font-size-md) / var(--font-size-xs) |
3 |
gap |
root |
⚠ var(--space-2) / 2px / 1px |
3 |
trigger-width-md |
size:md |
var(--field-control-height-md) |
2 |
trigger-width-xs |
size:xs |
var(--field-control-height-xs) |
2 |
trigger-width-sm |
size:sm |
var(--field-control-height-sm) |
2 |
trigger-width-lg |
size:lg |
var(--field-control-height-lg) |
2 |
trigger-height-md |
size:md |
var(--field-control-height-md) |
2 |
trigger-height-xs |
size:xs |
var(--field-control-height-xs) |
2 |
trigger-height-sm |
size:sm |
var(--field-control-height-sm) |
2 |
trigger-height-lg |
size:lg |
var(--field-control-height-lg) |
2 |
trigger-radius |
root |
⚠ var(--field-control-radius) / var(--radius-sm) |
2 |
trigger-bg |
root |
⚠ var(--field-control-bg) / var(--field-segment-active-bg) |
2 |
trigger-fg |
root |
⚠ var(--field-control-fg) / var(--field-segment-active-text) |
2 |
width |
root |
⚠ var(--border-width) / 1px |
2 |
bg |
root |
⚠ var(--color-border-strong) / var(--color-border-default) |
2 |
font-weight |
root |
⚠ var(--font-weight-semibold) / var(--font-weight-medium) |
2 |
letter-spacing |
root |
⚠ var(--tracking-wider) / var(--tracking-caps) |
2 |
height |
root |
⚠ 0.875rem / 4px |
2 |
clock-shadow |
root |
var(--slider-thumb-shadow), 0 0 0 2px var(--color-surface-default) |
2 |
gap-md |
size:md |
var(--space-1) |
1 |
gap-xs |
size:xs |
var(--space-0-5) |
1 |
gap-sm |
size:sm |
var(--space-0-5) |
1 |
gap-lg |
size:lg |
var(--space-1-5) |
1 |
line-height |
root |
var(--field-control-line-height) |
1 |
disabled-trigger-opacity |
root |
var(--field-disabled-opacity) |
1 |
clock-width (ya existe) |
root |
14rem |
1 |
hover-clock-bg |
host |
var(--toggle-palette-solid) |
1 |
hover-clock-border |
host |
var(--toggle-palette-solid) |
1 |
padding-inline |
root |
calc(var(--_slider-thumb-size, 1rem) / 2) |
1 |
font-size |
root |
var(--font-size-xxs) |
1 |
day-period-item-width |
root |
1px |
1 |
day-period-item-height |
root |
1px |
1 |
invalid-trigger-border |
root |
var(--color-threat-border) |
1 |
hover-invalid-trigger-border |
root |
var(--color-threat-border) |
1 |
4.2 Sin nombre mecánico (12)
- ⚠ decisión:
100%es un valor identidad o geometría de layout, no un knob de tema — el perímetro de «knob» es D-TH.2, sin firmar — 4:inline-size. - ⚠ decisión:
borderes shorthand o eje físico — hay que partirlo en ejes lógicos antes de nombrarlo (recipe-contract §1, R-4.4) — 1:border. - ⚠ decisión:
paddinges shorthand o eje físico — hay que partirlo en ejes lógicos antes de nombrarlo (recipe-contract §1, R-4.4) — 2:padding. - ⚠ decisión:
1es un valor identidad o geometría de layout, no un knob de tema — el perímetro de «knob» es D-TH.2, sin firmar — 2:line-height. - ya alcanzable: el privado
--_time-range-picker-slider-accentderiva de un público (var(--time-range-picker-clock-hand-hour),var(--time-range-picker-clock-hand-minute),var(--time-range-picker-clock-hand-second)) — sin acción; el censo lo cuenta como no alcanzable por el límite del regex — 3:border-color,background.
4.3 Avisos sobre los tokens propuestos (9)
- el privado
--_time-range-picker-gapdebe pasar a leer este público (o desaparecer) —--time-range-picker-gap-md,--time-range-picker-gap-xs,--time-range-picker-gap-sm,--time-range-picker-gap-lg - el privado
--_time-range-picker-font-sizedebe pasar a leer este público (o desaparecer) —--time-range-picker-font-size-md,--time-range-picker-font-size-xs,--time-range-picker-font-size-sm,--time-range-picker-font-size-lg - el privado
--_time-range-picker-heightdebe pasar a leer este público (o desaparecer) —--time-range-picker-trigger-width-md,--time-range-picker-trigger-width-xs,--time-range-picker-trigger-width-sm,--time-range-picker-trigger-width-lg,--time-range-picker-trigger-height-md,--time-range-picker-trigger-height-xs,--time-range-picker-trigger-height-sm,--time-range-picker-trigger-height-lg - el privado
--_time-range-picker-accent-borderdebe pasar a leer este público (o desaparecer) —--time-range-picker-hover-trigger-border,--time-range-picker-trigger-border - el privado
--_time-range-picker-accent-trackdebe pasar a leer este público (o desaparecer) —--time-range-picker-hover-trigger-bg,--time-range-picker-on-day-period-item-bg - el privado
--_time-range-picker-accent-textdebe pasar a leer este público (o desaparecer) —--time-range-picker-hover-trigger-fg,--time-range-picker-on-day-period-item-fg - el privado
--_time-range-picker-label-fontdebe pasar a leer este público (o desaparecer) —--time-range-picker-font-size-md,--time-range-picker-font-size-xs,--time-range-picker-font-size-sm,--time-range-picker-font-size-lg - el privado
--_time-range-picker-channel-fontdebe pasar a leer este público (o desaparecer) —--time-range-picker-font-size-md,--time-range-picker-font-size-xs,--time-range-picker-font-size-sm,--time-range-picker-font-size-lg - ⚠ decisión: el valor es una expresión — el token puede llevar la expresión entera o sólo su término variable —
--time-range-picker-padding-inline
4.4 Lo que hay que comprobar a mano (PLAN-theming §1.3 · §7.4)
- Privado que no deriva de un público — §3 lo marca; el privado debe leer el público o desaparecer.
- Velo o acento en el nodo equivocado (
archetype: 'item'en un envoltorio, unbackgrounden shorthand que mata la capa de estado) — se mide desde el píxel hacia arriba. - Doble animación al mover un sello a una superficie con animación propia — registro de
animationstart/animationend. - Diff de computed = 0 en reposo · hover · abierto · disabled · foco, por talla, antes y después.
- Centinela por token nuevo: valor imposible en el root → el nodo lo sigue. Si no, el token miente.
5. Veredicto
Revisión 2026-08-20 — verificación previa a implementación (Opus).
Análisis (§1–§3): CORRECTO en cifras (88 · 0 · 6 · 61 · 17 · 4), con un
hallazgo que el censo no podía ver: los «privados ajenos» --_time-field-*
NO vienen de time-field — los declara este mismo CSS con el prefijo
equivocado (time-range-picker.css:10-15: --_time-field-height,
--_time-field-gap, --_time-field-font-size, --_time-field-accent-*).
Mal prefijo = el censo los clasifica global, y si un time-field real
convive cerca, los nombres se cruzan. Primer paso obligado: renombrarlos a
--_time-range-picker-* (mecánico, computed idéntico) — con git ls-files
por si algo más los toca.
Propuesta (§4.1): NO APTA tal cual. Tres causas verificadas:
- Colisiones por estado no parseado:
clock-bgmezcla los colores de las DOS manecillas y los ticks (primary/secondary/neutral border) porque la derivación no lee los attrs de manecilla;width/height/bg/gapcolapsan separadores y pistas. Las partes SÍ existen y están limpias (clock,trigger,day-period-toggle/-item,hour/minute/second-slider,clear) — el nombre correcto sale de parte+estado a mano. - Es un COMPUESTO (Field + Slider + Toggle + capa
picker-shell): los knobs que leen--field-*,--slider-*públicos se teman en las fichas de SUS dueños, no aquí;padding-inline: calc(var(--_slider-thumb-size,…)/2)consume un privado DE SLIDER (geometría acoplada al thumb) — o slider publica ese eje o la expresión se ancla de otro modo: decisión del dueño, no un token de este componente. Es el mandato «Field composition» detheming-audit.md§5.3-3. hover-clock-bg/border = var(--toggle-palette-solid)con scopehostes inválido: referencia la paleta de OTRO componente; si procede, es un bloquecomposition:(tsc.md §cross-recipe), nunca un token propio.
Lo genuinamente acuñable aquí (válido de §4.1, con el patrón Sidebar):
la franja day-period (day-period-toggle-*, day-period-item-* — separando
el estado on-), la cara del reloj (clock-gap/fg/font-*/shadow/width —
partiendo las dos anchuras 22rem/14rem en clock-width y
clock-rail-width o análogo tras mirar el selector), y los acentos
accent-border/track/text promovidos a públicos que los privados
renombrados pasen a leer. Los font-size-{k} por talla: el root estampa
data-size ✓ pero hay DOS escalas mezcladas (la del campo y la del HUD
xxs) — separar por parte antes de nombrar. Los 17 literales: anotar o
tokenizar uno a uno (varios son geometría de manecilla: candidatos a
excepción con razón).
Bloqueos de firma: mandato field-composition (§B, sin ejecutar) ·
publicación del eje del thumb en slider · D-TH.4 (orden: familia tiempo va
en B7).
EJECUTADO 2026-08-20 (parcial, como su gemelo). Alcance 0 % → 19 % · contrato 0 → 21 claves públicas.
Hecho: renombradas las 56 referencias con prefijo ajeno (--_time-field-*
declarado dentro de este CSS, y una mención en el wrapper) a
--_time-range-picker-*; acento a público; y a contrato el reloj de dos
columnas (clock-column-gap, clock-width, clock-fg, clock-font-*), las
tres manecillas y la franja AM/PM completa (day-period-toggle-*,
day-period-item-*).
Confirmado al ejecutar lo que la revisión anotó: el hover-clock-bg/border que
la propuesta quería acuñar lee --toggle-palette-solid — paleta de OTRO
componente —, así que NO se acuña: si procede, es un bloque composition:
(tsc.md), y eso es decisión. Igual el padding-inline que consume
--_slider-thumb-size: el eje lo publica su dueño o no se publica.
Verificación: diff de computed = 0 sobre 725 valores en 8 estados ·
component:audit PASS · suite eidos sin rojos nuevos · rtl:check 0 ·
docs:check 0.
El 81 % restante es préstamo con dueño (Field, Slider, Toggle, picker-shell) y
espera el mandato de composición de Field, no este eje.