|
|
2 months ago | |
|---|---|---|
| .. | ||
| README.md | 5 months ago | |
| context.svelte.ts | 5 months ago | |
| index.ts | 3 months ago | |
| time-range-picker-clock.svelte | 3 months ago | |
| time-range-picker-content.svelte | 4 months ago | |
| time-range-picker-day-period-toggle.svelte | 3 months ago | |
| time-range-picker-hour-slider.svelte | 3 months ago | |
| time-range-picker-input.svelte | 3 months ago | |
| time-range-picker-minute-slider.svelte | 3 months ago | |
| time-range-picker-second-slider.svelte | 3 months ago | |
| time-range-picker-trigger.svelte | 3 months ago | |
| time-range-picker.css | 3 months ago | |
| time-range-picker.svelte | 3 months ago | |
| types.ts | 2 months ago | |
README.md
Eidos TimeRangePicker
Composite popover combining a segmented TimeRangeField input pair (start + end)
and a Clock view with per-endpoint sliders (Hour / Minute / Second + AM/PM
toggle). Soma owns range state coordination ({ start, end } + open +
helpers commit / cancel / clear); Eidos adds visual treatment, the popover
content shell, the side-by-side endpoint layout and the canonical Footer
parts.
Baseline
Air no tenía un TimeRangePicker propio en la rama anterior. La referencia
real es la composición Soma time-range-picker + time-range-field +
popover + slider que ya implementa la edición segmentada de ambos
extremos y la selección por sliders independientes (type="start" | "end"). La receta Eidos sólo envuelve esa superficie con tamaños, variante
visual y paleta de intents. Referencias externas: React Aria
DateRangePicker (pares), Ark UI Time Picker (single), Chakra Time Picker.
Superficie
<TimeRangePicker bind:value bind:open mode="inline">
<TimeRangePicker.Input type="start">
{#snippet children({ segments })}
{#each segments as { part, value }, i (`${part}-${i}`)}
<TimeRangePicker.Segment {part}>{value}</TimeRangePicker.Segment>
{/each}
{/snippet}
</TimeRangePicker.Input>
<TimeRangePicker.Input type="end">
{#snippet children({ segments })}
{#each segments as { part, value }, i (`${part}-${i}`)}
<TimeRangePicker.Segment {part}>{value}</TimeRangePicker.Segment>
{/each}
<TimeRangePicker.Trigger />
{/snippet}
</TimeRangePicker.Input>
<TimeRangePicker.Portal>
<TimeRangePicker.Content>
<TimeRangePicker.Clock>
<div class="time-range-picker-endpoint">
<span class="time-range-picker-endpoint-label">Start</span>
<TimeRangePicker.HourSlider type="start" />
<TimeRangePicker.MinuteSlider type="start" />
<TimeRangePicker.DayPeriodToggle type="start" />
</div>
<div class="time-range-picker-endpoint">
<span class="time-range-picker-endpoint-label">End</span>
<TimeRangePicker.HourSlider type="end" />
<TimeRangePicker.MinuteSlider type="end" />
<TimeRangePicker.DayPeriodToggle type="end" />
</div>
<TimeRangePicker.Footer>
<TimeRangePicker.Clear />
<TimeRangePicker.Cancel />
<TimeRangePicker.Close />
</TimeRangePicker.Footer>
</TimeRangePicker.Clock>
</TimeRangePicker.Content>
</TimeRangePicker.Portal>
</TimeRangePicker>
Partes públicas: Trigger, Content, Clock, Label, Input,
Segment, HourSlider, MinuteSlider, SecondSlider,
DayPeriodToggle, Footer, Clear, Cancel, Close. Cada slider /
toggle acepta type: 'start' | 'end'.
Comparativa
| Característica | React Aria | Ark | Chakra | UIX |
|---|---|---|---|---|
| Inputs segmentados (par) | sí | no | no | sí |
| Sliders por endpoint | no | no | no | sí |
| Modo inline / modal | no | no | no | sí |
| Footer (composición) | no | no | no | sí |
| commit / cancel / clear shell | manual | no | no | sí |
| Range state-machine swap | sí | n/a | n/a | sí |
Decisiones
- State machine empty → pending → complete vive en el provider Soma —
el eidos no decide cuándo se cierra.
closeOnRangeCompletees opcional. mode='inline'|'modal'propaga al popover (modal: mode === 'modal').- Footer = composición — sin
*Buttonprops, igual que TimePicker. - N-8 — los sliders comparten
SliderProvider(no se reimplementa drag / teclado). - Layout 2 columnas — Start y End ocupan columnas independientes en el popover. Por debajo de 40rem caen apiladas.
Gaps
| Gap | Disposición | Detalle |
|---|---|---|
| Vista "preset list" (Hoy, Última hora, Last 5 min…) | diferir | Se puede componer fuera con un Picker.Header + botones que llamen setRange(a, b). Si emerge demanda recurrente, promover a parte canónica. |
Swap automático visible cuando end < start |
diferir | Hoy la validación vive en el validate opt y el data-invalid resultante. Auto-swap silencioso oculta intención del usuario — preferimos que el formulario muestre el error. |
Estilado visual de [data-readonly] y [data-invalid] en el recipe |
implementar | Audit R-1.3 / R-1.4: las attrs se emiten desde el morfo pero el recipe no las consume. Pendiente añadir reglas en time-range-picker.css. |