TimeField#
A time input field with a searchable dropdown list of time intervals. The user can type a custom time or select from the dropdown.
Usage#
Basic usage#
bs.TimeField(label="Select a time")
Display formats#
The value_format= parameter controls how times are displayed in the field.
Any ICU time format pattern or named preset is accepted.
now = datetime.time(14, 30)
bs.TimeField(value=now, value_format="shortTime") # 2:30 PM
bs.TimeField(value=now, value_format="HH:mm") # 14:30
bs.TimeField(value=now, value_format="HH:mm:ss") # 14:30:00
bs.TimeField(value=now, value_format="h:mm a") # 2:30 PM
Dropdown interval#
The interval= parameter sets the spacing between entries in the dropdown.
bs.TimeField(interval=15) # every 15 minutes
bs.TimeField(interval=30) # every 30 minutes (default)
bs.TimeField(interval=60) # hourly
Time range constraints#
Use min_time= and max_time= to limit which times appear in the dropdown.
import datetime
bs.TimeField(
label="Appointment time",
message="Available 9 AM – 5 PM.",
min_time=datetime.time(9, 0),
max_time=datetime.time(17, 0),
interval=30,
)
Reactive binding#
Pass a Signal[str] via textsignal= to keep the field text in sync with
application state.
time_sig = bs.Signal("")
bs.TimeField(label="Pick a time", textsignal=time_sig)
bs.Label(textsignal=time_sig, accent="secondary")
Handling changes#
on_change() fires whenever the time value changes — whether by typing,
dropdown selection, or value= assignment.
tf = bs.TimeField(label="Start time")
tf.on_change(lambda e: print("Selected:", tf.value))
States#
bs.TimeField(value=now, label="Normal")
bs.TimeField(value=now, label="Read only", read_only=True)
bs.TimeField(value=now, label="Disabled", disabled=True)
Widget sizing#
All widgets accept self-placement kwargs via **kwargs. The parent
container determines which options apply — stack-based parents use stack
kwargs, grid-based parents use grid kwargs. Unrecognised keys are
silently ignored.
Stack#
Used inside VStack, HStack, App, and other stack containers.
|
Fill direction: |
|
Grow to consume extra space in the parent. |
|
Alignment when the widget does not fill the available slot:
|
|
External spacing in pixels. Accepts an integer (equal on all
sides), a 2-tuple |
|
Horizontal external spacing (left and right). Accepts an integer
or a 2-tuple |
|
Vertical external spacing (top and bottom). Accepts an integer
or a 2-tuple |
Grid#
Used inside a Grid container.
|
Zero-based row and column indices. |
|
Number of rows or columns to span. |
|
Alignment and fill within the grid cell. Any combination of
|
|
External spacing in pixels. Accepts an integer, a 2-tuple
|
|
Horizontal external spacing. Accepts an integer or |
|
Vertical external spacing. Accepts an integer or |
See also#
DateField — date input with calendar picker
API#
The complete reference for TimeField lives on the
Widgets API page. At a glance:
A time-input field with a searchable dropdown of time intervals. |
Full Example#
1
2with bs.App(title="TimeField Demo", padding=20, gap=16) as app:
3
4 # Basic usage
5 bs.Label("Basic", font="heading-sm")
6 bs.TimeField(label="Select a time")
7
8 # Time format presets
9 bs.Label("Display Formats", font="heading-sm")
10 now = datetime.time(14, 30)
11 bs.TimeField(value=now, label="Short time (default)", value_format="shortTime")
12 bs.TimeField(value=now, label="24-hour", value_format="HH:mm")
13 bs.TimeField(value=now, label="24-hour with seconds", value_format="HH:mm:ss")
14
15 # Dropdown interval
16 bs.Label("Dropdown Interval", font="heading-sm")
17 bs.TimeField(value=now, label="15-minute intervals", interval=15)
18 bs.TimeField(value=now, label="60-minute intervals", interval=60)
19
20 # Time range constraints
21 bs.Label("Business Hours", font="heading-sm")
22 bs.TimeField(
23 value=datetime.time(9, 0),
24 label="Appointment time",
25 message="Available Monday – Friday, 9 AM – 5 PM.",
26 min_time=datetime.time(9, 0),
27 max_time=datetime.time(17, 0),
28 interval=30,
29 )
30
31 # Reactive binding
32 bs.Label("Reactive Binding", font="heading-sm")
33 time_sig = bs.Signal("")
34 bs.TimeField(label="Pick a time", textsignal=time_sig)
35 bs.Label(textsignal=time_sig, accent="secondary")
36
37 # States
38 bs.Label("States", font="heading-sm")
39 bs.TimeField(value=now, label="Normal")
40 bs.TimeField(value=now, label="Read only", read_only=True)
41 bs.TimeField(value=now, label="Disabled", disabled=True)
42
43 # Handling changes
44 bs.Label("Handling Changes", font="heading-sm")
45 last = bs.Signal("(none)")
46 tf = bs.TimeField(label="Choose a time")
47 tf.on_change(lambda e: last.set(str(tf.value)))
48 bs.Label(textsignal=last, accent="secondary")
49
50 # Validation
51 bs.Label("Validation", font="heading-sm")
52 validated = bs.TimeField(label="Required time", required=True)
53 with bs.HStack(gap=8):
54 bs.Button("Validate", on_click=lambda: validated.validate())
55
56app.run()