Now.js Framework Documentation
Date Elements
Date Elements
Documentation for DateElementFactory - custom date/time picker with calendar UI, locale support, and flexible formatting.
📋 Table of Contents
- Overview
- Basic Usage
- HTML Attributes
- Date Formats
- Time Picker
- Min/Max Dates
- Locale Support
- JavaScript API
- Events
- Styling
- Best Practices
Overview
DateElementFactory creates a custom date picker with full calendar UI, replacing the native HTML5 date input for consistent cross-browser experience.
Key Features
- ✅ Custom Calendar UI: Full month calendar with navigation
- ✅ Time Picker: Optional time selection with hour/minute inputs
- ✅ Flexible Formats: Customizable date format patterns
- ✅ Thai/Buddhist Year: Support for Buddhist Era (BE) year display
- ✅ Min/Max Dates: Restrict selectable date range
- ✅ Locale Support: Thai and English month/day names
- ✅ Keyboard Navigation: Arrow keys to navigate calendar
- ✅ DropdownPanel Integration: Consistent dropdown behavior
Basic Usage
<!-- Simple date picker -->
<input type="text"
data-element="date"
name="birthdate"
placeholder="Select date">
<!-- Date with format -->
<input type="text"
data-element="date"
data-format="d/m/Y"
name="start_date">
<!-- Date with time -->
<input type="text"
data-element="date"
data-format="d/m/Y H:i"
data-time="true"
name="appointment">Rendered UI
The date picker renders:
- Input wrapper with calendar icon button
- Dropdown calendar with:
- Month/Year header with navigation
- Day grid (Sunday-Saturday)
- Optional time inputs
- Hidden input for form submission (ISO format)
HTML Attributes
| Attribute | Type | Default | Description |
|---|---|---|---|
data-element |
string | - | Set to date |
data-format |
string | 'd/m/Y' |
Display format pattern |
data-time |
boolean | false |
Enable time picker |
data-locale |
string | 'th' |
Locale for month/day names |
data-min |
string | - | Minimum date (ISO or formatted) |
data-max |
string | - | Maximum date (ISO or formatted) |
value |
string | - | Initial value |
Date Formats
Format Patterns
| Pattern | Description | Example |
|---|---|---|
Y |
Full year (CE) | 2025 |
y |
Full year (BE) | 2568 |
M |
Full month name | มกราคม / January |
m |
Month (2 digits) | 01-12 |
D |
Full day name | จันทร์ / Monday |
d |
Day (2 digits) | 01-31 |
H |
Hour (2 digits, 24h) | 00-23 |
i |
Minute (2 digits) | 00-59 |
Common Format Examples
<!-- Thai format: 31/12/2568 -->
<input data-element="date" data-format="d/m/y">
<!-- ISO format: 2025-12-31 -->
<input data-element="date" data-format="Y-m-d">
<!-- Long format: 31 มกราคม 2568 -->
<input data-element="date" data-format="d M y">
<!-- With time: 31/12/2025 14:30 -->
<input data-element="date" data-format="d/m/Y H:i" data-time="true">Buddhist Era (BE) Year
Use lowercase y for Buddhist Era year (CE + 543):
<!-- Shows: 10/12/2568 (BE year) -->
<input data-element="date"
data-format="d/m/y"
data-locale="th"
name="date_th">Time Picker
Enable time picker with data-time="true":
<input type="text"
data-element="date"
data-format="d/m/Y H:i"
data-time="true"
name="appointment">Time Picker UI
When enabled, the dropdown shows:
- Hour input (00-23)
- Minute input (00-59)
- Colon separator
Time-only Input
For time-only selection without date:
<input type="text"
data-element="time"
name="meeting_time">Min/Max Dates
Restrict selectable date range:
<!-- Dates from today onwards -->
<input type="text"
data-element="date"
data-min="today"
name="future_date">
<!-- Dates in specific range -->
<input type="text"
data-element="date"
data-min="2025-01-01"
data-max="2025-12-31"
name="date_2025">
<!-- Past dates only (up to today) -->
<input type="text"
data-element="date"
data-max="today"
name="past_date">Disabled Date Styling
Dates outside the valid range are:
- Visually dimmed
- Not clickable
- Keyboard navigation skips them
Locale Support
Thai Locale (Default)
<input data-element="date" data-locale="th">Month Names: มกราคม, กุมภาพันธ์, มีนาคม, ...
Day Names: อา, จ, อ, พ, พฤ, ศ, ส
English Locale
<input data-element="date" data-locale="en">Month Names: January, February, March, ...
Day Names: Sun, Mon, Tue, Wed, Thu, Fri, Sat
Dynamic Locale Change
The date picker responds to locale:changed events from I18nManager:
I18nManager.setLocale('en');
// All date pickers update their month/day namesJavaScript API
Get Instance
const dateInput = document.querySelector('[name="appointment"]');
const instance = ElementManager.getInstance(dateInput);
// Access the internal EmbeddedDateTime component
const picker = instance.picker;Methods
// Get current value (ISO format)
const value = instance.getValue(); // '2025-12-31' or '2025-12-31T14:30'
// Get Date object
const date = instance.getDate(); // Date object
// Set value
instance.setValue('2025-12-31');
instance.setValue('2025-12-31T14:30');
// Open calendar
instance.open();
// Close calendar
instance.close();
// Toggle calendar
instance.toggle();
// Navigate months
instance.previousMonth();
instance.nextMonth();
// Destroy and cleanup
instance.destroy();Direct Picker Access
const picker = instance.picker;
// Get element wrapper
const wrapper = picker.getElement();
// Select a specific date
picker.selectDate(new Date(2025, 11, 31));Events
| Event | When Emitted | Detail |
|---|---|---|
change |
Date selected | Native event with formatted value |
input |
Value changed | Native event |
open |
Calendar opened | - |
close |
Calendar closed | - |
Usage
dateInput.addEventListener('change', (e) => {
const instance = ElementManager.getInstance(e.target);
console.log('Display value:', e.target.value); // '31/12/2025'
console.log('ISO value:', instance.getValue()); // '2025-12-31'
console.log('Date object:', instance.getDate()); // Date object
});Styling
CSS Variables
:root {
--date-picker-bg: #ffffff;
--date-picker-border: #e0e0e0;
--date-picker-text: #333333;
--date-picker-selected: #007bff;
--date-picker-today: #28a745;
--date-picker-disabled: #cccccc;
}Key CSS Classes
/* Wrapper */
.datetime-wrapper {
position: relative;
display: inline-flex;
}
/* Calendar button */
.datetime-button {
padding: 8px;
cursor: pointer;
}
/* Calendar dropdown */
.datetime-calendar {
background: var(--date-picker-bg);
border: 1px solid var(--date-picker-border);
border-radius: 4px;
box-shadow: 0 4px 12px rgba(0,0,0,0.15);
}
/* Calendar header */
.calendar-header {
display: flex;
justify-content: space-between;
padding: 8px;
}
/* Day cells */
.calendar-day {
width: 36px;
height: 36px;
text-align: center;
cursor: pointer;
}
.calendar-day.today {
border: 2px solid var(--date-picker-today);
}
.calendar-day.selected {
background: var(--date-picker-selected);
color: white;
}
.calendar-day.disabled {
opacity: 0.4;
cursor: not-allowed;
}
/* Time picker */
.datetime-time {
display: flex;
align-items: center;
gap: 4px;
padding: 8px;
border-top: 1px solid var(--date-picker-border);
}
.datetime-time input {
width: 40px;
text-align: center;
}Best Practices
1. ✅ Use Appropriate Format for Locale
<!-- ✅ Good: Thai format with BE year -->
<input data-element="date"
data-format="d/m/y"
data-locale="th">
<!-- ✅ Good: ISO format for international -->
<input data-element="date"
data-format="Y-m-d"
data-locale="en">2. ✅ Set Reasonable Min/Max Dates
<!-- ✅ Good: Future dates for appointments -->
<input data-element="date"
data-min="today"
name="appointment">
<!-- ✅ Good: Birth dates must be in the past -->
<input data-element="date"
data-max="today"
name="birthdate">3. ✅ Include Placeholder
<!-- ✅ Good: Clear instruction -->
<input data-element="date"
placeholder="dd/mm/yyyy"
name="date">4. ✅ Use Time for Appointments
<!-- ✅ Good: Date + time for scheduling -->
<input data-element="date"
data-format="d/m/Y H:i"
data-time="true"
name="meeting_time">5. ✅ Handle Form Submission
The hidden input contains ISO format for reliable server parsing:
<!-- User sees: 31/12/2568 -->
<!-- Form submits: 2025-12-31 (ISO format) -->
<input data-element="date" data-format="d/m/y">Related Documentation
- Form Elements Overview
- ElementFactory - Base class
- Number Elements - Number inputs
- Special Elements - Other specialized inputs