SuperDate

Lightweight TypeScript enhancer for native date, time, and datetime-local inputs.

✦ Zero dependencies ✦ 3 input types ✦ Fully keyboard-accessible

SuperDate replaces the native browser date/time picker chrome with a fully custom, format-aware overlay — while still delegating the actual popup calendar or clock to the OS. You never re-implement a calendar widget.

The underlying input.value always stays in standard ISO format, so it drops in alongside any existing form logic without changes.

Install & Build

Copy the dist/ folder into your project, or build from source:

npm install
npm run build
FileFormatUse when
super-date.umd.jsUMDPlain <script> tag, exposes global SuperDate
super-date.min.jsUMD minifiedProduction <script> tag
super-date.esm.jsES Moduleimport in bundler or modern browser
super-date.esm.min.jsESM minifiedProduction ESM

CDN (jsDelivr)

No installation needed — load SuperDate directly via jsDelivr. Use the @latest tag to always receive the newest version automatically:

Always use the latest version ✦ recommended

<!-- CSS -->
<link rel="stylesheet"
      href="https://cdn.jsdelivr.net/npm/@maihcx/super-date@latest/dist/super-date.min.css" />

<!-- JS (UMD — exposes global SuperDate) -->
<script src="https://cdn.jsdelivr.net/npm/@maihcx/super-date@latest/dist/super-date.min.js"></script>

Pin a specific version

If you need stricter stability guarantees for production, replace @latest with an exact version number:

<link rel="stylesheet"
      href="https://cdn.jsdelivr.net/npm/@maihcx/super-date@1.0.0/dist/super-date.min.css" />
<script src="https://cdn.jsdelivr.net/npm/@maihcx/super-date@1.0.0/dist/super-date.min.js"></script>

ESM via jsDelivr

<script type="module">
  import SuperDate from 'https://cdn.jsdelivr.net/npm/@maihcx/super-date@latest/dist/super-date.esm.min.js';
  SuperDate.bind('.sd', { format: 'dd/MM/yyyy' });
</script>

Usage

Via <script> tag

<link rel="stylesheet" href="dist/super-date.min.css" />
<script src="dist/super-date.umd.js"></script>
<script>
  SuperDate.bind('.sd', { format: 'dd/MM/yyyy' });
</script>

ES Module

import SuperDate from './dist/super-date.esm.js';
SuperDate.bind('.sd', { format: 'dd/MM/yyyy' });

TypeScript / bundler

import SuperDate from 'superdate';
SuperDate.bind('.sd');

SuperDate.bind()

Enhances all current and future matching inputs. Uses a MutationObserver to catch inputs added to the DOM after the call.

SuperDate.bind(selector: string, options?: SuperDateOptions): this

Supports input[type="date"], input[type="time"], and input[type="datetime-local"] within the same selector. Returns this for chaining.

// all three types under one selector
SuperDate.bind('.sd', {
  format:            'dd/MM/yyyy',
  timeFormat:        'HH:mm',
  dateTimeDelimiter: ' ',
});

// chaining
SuperDate
  .bind('.date-field', { format: 'yyyy/MM/dd' })
  .bind('.time-field', { timeFormat: 'HH:mm:ss' });

SuperDate.init()

Manually enhance a single element. Returns the SuperDateInstance. Safe to call on an already-enhanced element — returns the existing instance.

SuperDate.init(el: HTMLInputElement, options?: SuperDateOptions): SuperDateInstance
const el = document.querySelector('#my-dt') as HTMLInputElement;
SuperDate.init(el, {
  format:            'dd/MM/yyyy',
  timeFormat:        'HH:mm:ss',
  dateTimeDelimiter: ' | ',
});

SuperDate.destroy()

Removes the overlay, detaches all listeners, and restores the original native input. The element is marked so the MutationObserver won't re-bind it automatically. Call bind() or init() again to re-enable.

SuperDate.destroy(el: HTMLInputElement): void

Options

OptionTypeDefaultDescription
formatstring'dd/MM/yyyy'Display format for date inputs, and the date part of datetime-local
timeFormatstring'HH:mm'Display format for time inputs, and the time part of datetime-local
dateTimeDelimiterstring' 'String inserted between date and time parts in datetime-local overlays
localestringnavigator.languageLocale — reserved for future i18n features

Format tokens

Date tokens

TokenDescriptionExample
yyyy4-digit year2025
yy2-digit year25
MMMonth, zero-padded03
MMonth, no padding3
ddDay, zero-padded07
dDay, no padding7

Time tokens

TokenDescriptionRangeExample
HHHours, 24h, zero-padded00–2309, 23
HHours, 24h, no padding0–239, 23
hhHours, 12h, zero-padded01–1209, 12
hHours, 12h, no padding1–129, 12
mmMinutes, zero-padded00–5905
ssSeconds, zero-padded00–5930
MM vs mmMM (uppercase) = months, mm (lowercase) = minutes. The token regex is case-sensitive.

Data attributes

Per-element attributes always override the global bind() options.

AttributeApplies toExample value
data-date-formatdate, datetime-local"yyyy/MM/dd"
data-time-formattime, datetime-local"HH:mm:ss"
data-date-time-delimiterdatetime-local" | "
<input type="date"           data-date-format="yyyy/MM/dd" />
<input type="time"           data-time-format="HH:mm:ss" />
<input type="datetime-local"
       data-date-format="dd/MM/yyyy"
       data-time-format="HH:mm:ss"
       data-date-time-delimiter=" | " />

CSS variables

Scope overrides to .superdate-overlay on a wrapper or globally:

VariableDefaultControls
--superdate-active-bg#2563ebActive segment background
--superdate-active-color#fffActive segment text
--superdate-placeholder-color#9ca3afEmpty segment placeholder text
--superdate-sep-colorinheritSeparator / literal character color
/* Override globally */
.superdate-overlay {
  --superdate-active-bg:         #0ea5e9;
  --superdate-active-color:      #fff;
  --superdate-placeholder-color: #475569;
  --superdate-sep-color:         #64748b;
}

/* Or scope to one wrapper */
#my-form .superdate-overlay {
  --superdate-active-bg: #7c3aed;
}

Keyboard shortcuts

KeyAction
0–9Type digit into active segment; auto-advances when segment is full
↑ / ↓Increment / decrement the active segment value (wraps around)
← / →Move to previous / next token segment
Tab / Shift+TabMove to next / previous segment; Tab out when at last/first
BackspaceErase last digit in the typing buffer
DeleteSame as Backspace; on a selection — clears all selected tokens
EscapeClear selection, or deactivate overlay
Ctrl+ASelect all segments
Ctrl+CCopy selected segments as formatted string
Click & dragMulti-segment selection
Double-clickSelect all segments

Input value

SuperDate only changes the visual overlay. The underlying input.value always stays in standard ISO format:

Input typeinput.value formatExample
dateyyyy-MM-dd2025-03-07
timeHH:mm:ss09:30:00
datetime-localyyyy-MM-ddTHH:mm:ss2025-03-07T09:30:00
Because input.value is unchanged, SuperDate is fully compatible with any existing form serialisation, validation library, or framework two-way binding.

Live demo — date

dd/MM/yyyy (default)
yyyy/MM/dd — data-date-format
MM-dd-yyyy

Live demo — time

HH:mm (default)
HH:mm:ss — data-time-format

Live demo — datetime-local

dd/MM/yyyy HH:mm (space delimiter)
yyyy-MM-dd | HH:mm:ss — custom delimiter