DatePicker — basic
import { html, atom, renderApp } from 'mates';
import { DatePicker, Text } from 'mates-ui';
const App = () => {
const today = new Date();
const val = atom(null);
const vy = atom(today.getFullYear());
const vm = atom(today.getMonth());
return () => html`
<x-col gap="var(--md-space-3)" style="max-width:17.5rem;width:100%;">
${DatePicker({ value: val(), label: "Select a date", viewYear: vy(), viewMonth: vm(), onChange: (ts) => val.set(ts), onViewChange: (y, m) => { vy.set(y); vm.set(m); } })}
${val() ? Text("Selected: " + new Date(val()).toLocaleDateString("default", { dateStyle: "full" }), { type: "body-sm", color: "muted" }) : html``}
</x-col>
`;
};
renderApp(App, document.getElementById('app'));
DatePicker — pre-filled value
import { html, atom, renderApp } from 'mates';
import { DatePicker, Text } from 'mates-ui';
const App = () => {
const today = new Date();
const todayTs = new Date(today.getFullYear(), today.getMonth(), today.getDate()).getTime();
const val = atom(todayTs);
const vy = atom(today.getFullYear());
const vm = atom(today.getMonth());
return () => html`
<x-col gap="var(--md-space-3)" style="max-width:17.5rem;width:100%;">
${DatePicker({ value: val(), label: "Date of birth", viewYear: vy(), viewMonth: vm(), onChange: (ts) => val.set(ts), onViewChange: (y, m) => { vy.set(y); vm.set(m); } })}
${val() ? Text("Selected: " + new Date(val()).toLocaleDateString(), { type: "body-sm", color: "muted" }) : html``}
</x-col>
`;
};
renderApp(App, document.getElementById('app'));
DatePicker — disabled ranges
import { html, atom, renderApp } from 'mates';
import { DatePicker, Text } from 'mates-ui';
const App = () => {
const today = new Date();
const y = today.getFullYear(); const m = today.getMonth();
const minTs = new Date(y, m - 1, 1).getTime();
const maxTs = new Date(y, m + 2, 0).getTime();
const val = atom(null);
const vy = atom(y);
const vm = atom(m);
return () => html`
<x-col gap="var(--md-space-3)" style="max-width:17.5rem;width:100%;">
${Text("Only current ±2 months selectable.", { type: "body-sm", color: "muted" })}
${DatePicker({ value: val(), label: "Booking date", min: minTs, max: maxTs, viewYear: vy(), viewMonth: vm(), onChange: (ts) => val.set(ts), onViewChange: (yy, mm) => { vy.set(yy); vm.set(mm); } })}
${val() ? Text("Selected: " + new Date(val()).toLocaleDateString(), { type: "body-sm", color: "muted" }) : html``}
</x-col>
`;
};
renderApp(App, document.getElementById('app'));
DatePicker — locale
import { html, atom, renderApp } from 'mates';
import { DatePicker } from 'mates-ui';
const App = () => {
const today = new Date();
const valDe = atom(null); const vyDe = atom(today.getFullYear()); const vmDe = atom(today.getMonth());
const valMon = atom(null); const vyMon = atom(today.getFullYear()); const vmMon = atom(today.getMonth());
return () => html`
<x-row gap="var(--md-space-5)" wrap align="flex-start">
<div style="max-width:17.5rem;">
${DatePicker({ value: valDe(), label: "Datum wählen", locale: "de", strings: { clear: "Zurücksetzen", today: "Heute", previousMonth: "Vorheriger Monat", nextMonth: "Nächster Monat", monthSelect: "Monat", yearInput: "Jahr", calendarDialog: "Kalender" }, viewYear: vyDe(), viewMonth: vmDe(), onChange: (ts) => valDe.set(ts), onViewChange: (y, m) => { vyDe.set(y); vmDe.set(m); } })}
</div>
<div style="max-width:17.5rem;">
${DatePicker({ value: valMon(), label: "Event date (Mon start)", weekStart: 1, viewYear: vyMon(), viewMonth: vmMon(), onChange: (ts) => valMon.set(ts), onViewChange: (y, m) => { vyMon.set(y); vmMon.set(m); } })}
</div>
</x-row>
`;
};
renderApp(App, document.getElementById('app'));
DatePicker — per-label props
import { html, atom, renderApp } from 'mates';
import { DatePicker } from 'mates-ui';
const App = () => {
const today = new Date();
const val = atom(null);
const vy = atom(today.getFullYear());
const vm = atom(today.getMonth());
return () => html`
<x-col gap="var(--md-space-3)" style="max-width:17.5rem;width:100%;">
${DatePicker({ value: val(), label: "Event date", previousMonthLabel: "Zurück", monthSelectLabel: "Monat", yearLabel: "Jahr", nextMonthLabel: "Weiter", calendarLabel: "Kalender", clearLabel: "Zurücksetzen", todayLabel: "Heute", viewYear: vy(), viewMonth: vm(), onChange: (ts) => val.set(ts), onViewChange: (y, m) => { vy.set(y); vm.set(m); } })}
</x-col>
`;
};
renderApp(App, document.getElementById('app'));
DateRangePicker
import { html, atom, renderApp } from 'mates';
import { DateRangePicker, Text } from 'mates-ui';
const App = () => {
const today = new Date();
const range = atom({ start: null, end: null });
const vy = atom(today.getFullYear()); const vm = atom(today.getMonth());
return () => html`
<x-col gap="var(--md-space-3)" style="max-width:17.5rem;width:100%;">
${DateRangePicker({ value: range(), label: "Booking window", viewYear: vy(), viewMonth: vm(), onChange: (r) => range.set(r), onViewChange: (y, m) => { vy.set(y); vm.set(m); } })}
${range().start && range().end
? Text(new Date(Math.min(range().start, range().end)).toLocaleDateString() + " → " + new Date(Math.max(range().start, range().end)).toLocaleDateString(), { type: "body-sm", color: "muted" })
: range().start ? Text("End date pending…", { type: "body-sm", color: "muted" }) : html``}
</x-col>
`;
};
renderApp(App, document.getElementById('app'));
DatePicker — multiple selection
import { html, atom, renderApp } from 'mates';
import { DatePicker, Text } from 'mates-ui';
const App = () => {
const today = new Date();
const values = atom([]);
const vy = atom(today.getFullYear()); const vm = atom(today.getMonth());
return () => html`
<x-col gap="var(--md-space-3)" style="max-width:20rem;width:100%;">
${DatePicker({ multiple: true, values: values(), label: "Unavailable dates", viewYear: vy(), viewMonth: vm(), onChangeMultiple: (ts) => values.set(ts), onViewChange: (y, m) => { vy.set(y); vm.set(m); } })}
${values().length > 0 ? Text(values().length + " date(s) selected", { type: "body-sm", color: "muted" }) : html``}
</x-col>
`;
};
renderApp(App, document.getElementById('app'));
DateRangePicker — multiple ranges (no overlap)
import { html, atom, renderApp } from 'mates';
import { DateRangePicker, Text } from 'mates-ui';
const App = () => {
const today = new Date();
const ranges = atom([]);
const inProgress = atom({ start: null, end: null });
const vy = atom(today.getFullYear()); const vm = atom(today.getMonth());
return () => html`
<x-col gap="var(--md-space-3)" style="max-width:20rem;width:100%;">
${Text("Overlapping ranges are blocked.", { type: "body-sm", color: "muted" })}
${DateRangePicker({ multiple: true, allowOverlappingRanges: false, values: ranges(), value: inProgress(), label: "Blocked periods", viewYear: vy(), viewMonth: vm(), onChangeMultiple: (r) => ranges.set(r), onChange: (r) => inProgress.set(r), onViewChange: (y, m) => { vy.set(y); vm.set(m); } })}
${ranges().length > 0 ? Text(ranges().length + " range(s) — no overlaps", { type: "body-sm", color: "muted" }) : html``}
</x-col>
`;
};
renderApp(App, document.getElementById('app'));
DateRangePicker — multiple ranges (overlapping allowed)
import { html, atom, renderApp } from 'mates';
import { DateRangePicker, Text } from 'mates-ui';
const App = () => {
const today = new Date();
const ranges = atom([]);
const inProgress = atom({ start: null, end: null });
const vy = atom(today.getFullYear()); const vm = atom(today.getMonth());
return () => html`
<x-col gap="var(--md-space-3)" style="max-width:20rem;width:100%;">
${Text("Overlapping ranges are permitted.", { type: "body-sm", color: "muted" })}
${DateRangePicker({ multiple: true, allowOverlappingRanges: true, values: ranges(), value: inProgress(), label: "Availability windows", viewYear: vy(), viewMonth: vm(), onChangeMultiple: (r) => ranges.set(r), onChange: (r) => inProgress.set(r), onViewChange: (y, m) => { vy.set(y); vm.set(m); } })}
${ranges().length > 0 ? Text(ranges().length + " range(s) — overlaps OK", { type: "body-sm", color: "muted" }) : html``}
</x-col>
`;
};
renderApp(App, document.getElementById('app'));
TimePicker
import { html, atom, renderApp } from 'mates';
import { TimePicker, Text } from 'mates-ui';
const App = () => {
const time = atom(null);
return () => html`
<x-col gap="var(--md-space-3)" style="max-width:17.5rem;width:100%;">
${TimePicker({ value: time(), label: "Start time", onChange: (v) => time.set(v) })}
${time() ? Text("Value (24 h): " + time().hour + ":" + String(time().minute).padStart(2, "0"), { type: "body-sm", color: "muted" }) : html``}
</x-col>
`;
};
renderApp(App, document.getElementById('app'));
DateTimePicker
import { html, atom, renderApp } from 'mates';
import { DateTimePicker, Text } from 'mates-ui';
const App = () => {
const today = new Date();
const val = atom(null);
const vy = atom(today.getFullYear()); const vm = atom(today.getMonth());
return () => html`
<x-col gap="var(--md-space-3)" style="max-width:20rem;width:100%;">
${DateTimePicker({ value: val(), label: "Appointment", minuteStep: 5, viewYear: vy(), viewMonth: vm(), onChange: (ts) => val.set(ts), onViewChange: (y, m) => { vy.set(y); vm.set(m); } })}
${val() ? Text("ISO: " + new Date(val()).toISOString(), { type: "body-sm", color: "muted" }) : html``}
</x-col>
`;
};
renderApp(App, document.getElementById('app'));