Components · Data Entry
TimePicker
Pick a time of day from scrolling hour/minute/second columns — schedules, reminders, durations — rendered through the shared TimePicker.
Examples
<!-- Paste-and-run: save as .html and open in a browser. No build step, no bundler.
TimePicker is a COMPOSITE (antd, no framework-free element), so its HTML form is a CDN-React
page — React + antd load from a CDN (esm.sh) and mount on open. It consumes the SAME shared
`timePickerTheme` the React/Vue wrappers use, so it renders the DS V3 look (32px field, radius
8, #E3E3E3 border, brand-selected cell). Times use Day.js.
No JSX here (JSX needs a compiler) — we use React.createElement via the `h` alias. -->
<div id="root"></div>
<script type="module">
import React from 'https://esm.sh/react@18';
import { createRoot } from 'https://esm.sh/react-dom@18/client';
import { ConfigProvider, TimePicker } from 'https://esm.sh/antd@6?deps=react@18,react-dom@18';
import dayjs from 'https://esm.sh/dayjs@1';
import { timePickerTheme } from 'https://cdn.jsdelivr.net/gh/ahaslides-product/ahaslides-design@master/lib/time-picker-theme.js';
const h = React.createElement;
const { RangePicker } = TimePicker;
const seed = dayjs('09:30', 'HH:mm');
createRoot(document.getElementById('root')).render(
h(ConfigProvider, { theme: timePickerTheme },
h('div', { style: { display: 'flex', flexWrap: 'wrap', gap: 12 } },
// Default · 24-hour
h(TimePicker, { defaultValue: seed, format: 'HH:mm', allowClear: true, style: { width: 200 } }),
// Sizes — small 24 · large 40
h(TimePicker, { size: 'small', format: 'HH:mm', style: { width: 200 } }),
h(TimePicker, { size: 'large', format: 'HH:mm', style: { width: 200 } }),
// Status — error / warning border
h(TimePicker, { status: 'error', format: 'HH:mm', style: { width: 200 } }),
h(TimePicker, { status: 'warning', format: 'HH:mm', style: { width: 200 } }),
// 12-hour · seconds · disabled
h(TimePicker, { use12Hours: true, format: 'h:mm a', minuteStep: 15, style: { width: 240 } }),
h(TimePicker, { format: 'HH:mm:ss', style: { width: 240 } }),
h(TimePicker, { disabled: true, format: 'HH:mm', style: { width: 200 } }),
// Range — start → end
h(RangePicker, { format: 'HH:mm', style: { width: 320 } })
)
)
);
</script>
import { ConfigProvider, TimePicker } from 'antd'; // antd v6
import dayjs from 'dayjs';
import { timePickerTheme } from '@ahaslides-product/design/time-picker-theme';
const { RangePicker } = TimePicker;
<ConfigProvider theme={timePickerTheme}>
{/* Default — 24-hour, minute granularity */}
<TimePicker
defaultValue={dayjs('09:30', 'HH:mm')}
format="HH:mm"
minuteStep={15}
allowClear
onChange={setTime}
style={{ width: 200 }}
/>
{/* Sizes — small 24 · default 32 · large 40 */}
<TimePicker size="small" format="HH:mm" style={{ width: 200 }} />
<TimePicker size="large" format="HH:mm" style={{ width: 200 }} />
{/* Status — tints the border */}
<TimePicker status="error" format="HH:mm" style={{ width: 200 }} />
<TimePicker status="warning" format="HH:mm" style={{ width: 200 }} />
{/* 12-hour + seconds + disabled */}
<TimePicker use12Hours format="h:mm a" style={{ width: 240 }} />
<TimePicker format="HH:mm:ss" style={{ width: 240 }} />
<TimePicker disabled format="HH:mm" style={{ width: 200 }} />
{/* Range — start → end */}
<RangePicker format="HH:mm" style={{ width: 320 }} />
</ConfigProvider>
// One shared timePickerTheme → the DS V3 look; match format to the precision you need. Times use Day.js.
<script setup>
import { ref } from 'vue';
import { ConfigProvider, TimePicker } from 'ant-design-vue'; // ant-design-vue v4
import dayjs from 'dayjs';
import { timePickerTheme } from '@ahaslides-product/design/time-picker-theme';
const time = ref(dayjs('09:30', 'HH:mm'));
const range = ref([dayjs('09:30', 'HH:mm'), dayjs('10:30', 'HH:mm')]);
</script>
<template>
<a-config-provider :theme="timePickerTheme">
<!-- Default — 24-hour, 15-min step -->
<a-time-picker v-model:value="time" format="HH:mm" :minute-step="15" allow-clear style="width: 200px" />
<!-- Sizes — small 24 · default 32 · large 40 -->
<a-time-picker size="small" format="HH:mm" style="width: 200px" />
<a-time-picker size="large" format="HH:mm" style="width: 200px" />
<!-- Status · 12-hour · seconds · disabled -->
<a-time-picker status="error" format="HH:mm" style="width: 200px" />
<a-time-picker status="warning" format="HH:mm" style="width: 200px" />
<a-time-picker use12-hours format="h:mm a" style="width: 240px" />
<a-time-picker format="HH:mm:ss" style="width: 240px" />
<a-time-picker disabled format="HH:mm" style="width: 200px" />
<!-- Range — start → end -->
<a-time-picker-range-picker v-model:value="range" format="HH:mm" style="width: 320px" />
</a-config-provider>
</template>
<!-- The SAME timePickerTheme as React → one DS V3 look across both vendor libraries. -->
// @ahaslides-product/design/time-picker-theme — declared ONCE, consumed by both tiers.
import { timePickerTheme } from '@ahaslides-product/design/time-picker-theme';
export const timePickerTheme = {
token: {
colorPrimary: '#6A1EBB',
borderRadius: 8,
controlHeight: 32,
colorBorder: '#E3E3E3',
colorTextPlaceholder: '#8A8A8A',
fontFamily: 'var(--aha-font-product, "Plus Jakarta Sans", sans-serif)',
},
components: {
// TimePicker is built on Ant's DatePicker internals — theme it through the DatePicker token.
DatePicker: {
borderRadius: 8,
controlHeight: 32,
cellHoverBg: '#F7F7F7', // hovered time cell (gray-20)
cellActiveWithRangeBg: '#F9F5FF',
},
},
};
API
| Prop | Type | Default | Notes |
|---|---|---|---|
value | Dayjs | — | Selected time |
size | 'small' | 'middle' | 'large' | 'middle' | Field height: 24 / 32 / 40 |
status | 'error' | 'warning' | — | Validation state — tints the border |
disabled | boolean | false | Non-interactive, greyed field |
format | string | HH:mm:ss | Display/parse format (HH:mm · HH:mm:ss · h:mm a) |
use12Hours | boolean | false | 12-hour clock with AM/PM |
allowClear | boolean | true | Show the clear (×) affordance |
minuteStep | number | 1 | Granularity of the minute column |
onChange | (time) => void | — | Fires with the new time |
Install
# .npmrc — once: point the @ahaslides-product scope at GitHub Packages
@ahaslides-product:registry=https://npm.pkg.github.com
//npm.pkg.github.com/:_authToken=${GITHUB_TOKEN} # a GitHub token with read:packages
npm i @ahaslides-product/design
import '@ahaslides-product/design/tokens.css'; // once, at the app root
import '@ahaslides-product/design/time-picker-theme'; // registers <time-picker>
Agent feed for this component (absolute, fetchable anywhere): time-picker.agent.json · time-picker.md · time-picker.llms.txt
When to use
When to use
- TimePicker — a time of day on its own — a reminder, a daily schedule slot
- DatePicker showTime — a date AND a time together — a precise timestamp
- Select — a small fixed set of times (e.g. 15-min slots) — a list beats scrolling
Match format to the precision you need — HH:mm hides seconds. Use minuteStep to snap to sensible increments rather than every minute. Times use Day.js.
Surfaces
editor dashboard settings
Spec
Field height 32 · radius 8 · 1px #E3E3E3 border · Sizes small 24 · default 32 · large 40 (via size) · Status error/warning tints the border (#FF5A7A error) · Selected cell brand #6A1EBB · Hover cell #F7F7F7 (gray-20) · Format HH:mm · HH:mm:ss · h:mm a (use12Hours) · Range TimePicker.RangePicker — start → end · Placeholder #8A8A8A