| Command | What it does |
|---|---|---|
| npm run typecheck | tsc --noEmit for all 3 workspaces |
| npm run build | tsup CJS+ESM+dts + copies CSS to dist |
| npm run dev:demo | vite dev server for demo app |
| npm run dev:docs | docusaurus start |
| npm run publish:ui | publishes packages/ui to npm |
| npm run deploy:build | builds UI + docs + demo, copies demo into docs build for deployment |
Order: typecheck before build.
- Monorepo with npm workspaces. Workspaces:
packages/*,apps/*. packages/ui/is the published package@initbase/react-datetime-picker. Entrypoint:src/index.tsx.apps/demo/— Vite + React dev app for manual testing. Uses the local package.apps/docs/— Docusaurus site with MDX docs. Also uses the local package.
- CSS must be imported separately:
import '@initbase/react-datetime-picker/datetime-picker.css'. The.cssfile is copied intodist/manually (cpin build script), NOT bundled by tsup. - Zero dependencies — all date logic uses plain
Date+Intl.DateTimeFormat. No dayjs/date-fns. - Peer deps:
react >= 18,react-dom >= 18. - tsup builds CJS + ESM +
.d.ts+ sourcemaps. Config is CLI flags inbuildscript (notsup.config.ts). - The
exportsfield inpackage.jsonhas two entry points:"."(components) and"./datetime-picker.css"(styles). "types"must come first in the exports conditions array to avoid tsup warning.
types.ts — DateValue, DateRangeValue, PopoverPosition, prop interfaces
utils.ts — pure date helpers (no external deps)
hooks.ts — useControlled, useClickOutside, useMediaQuery
Calendar.tsx — month grid, day cells, range highlighting, prev/next nav
TimeColumn.tsx — scrollable column for hours/minutes/seconds
Popover.tsx — absolutely positioned container, useLayoutEffect for flexible flip
InputTrigger.tsx — read-only trigger button + CalendarIcon (also RangeInputTrigger)
IconButton.tsx — chevron arrow buttons
DatePicker.tsx — single date
TimePicker.tsx — single time (step, 12h/24h, seconds)
DateTimePicker.tsx — date + time
DateRangePicker.tsx — two-click range, pendingStart state
TimeRangePicker.tsx — two time column panels side by side
DateTimeRangePicker.tsx — calendar + time panels
datetime-picker.css — all default styling via --rdp-* custom properties
- All classes prefixed
rdp-(BEM-like). - Theming via CSS custom properties on
.rdp-wrapper(--rdp-primary,--rdp-border-radius, etc.). - Popover has NO min-width — it sizes to content naturally.
- Position classes:
.rdp-popover--bottom,--top,--left,--right. .rdp-wrapperisdisplay: inline-block— it shrinks to content width. Users can override.
- Controlled/uncontrolled via
useControlledhook (similar to<input>pattern). - Every picker destructures
positionand passes it to<Popover>. position="flexible"(default) flips to top when bottom overflows viewport.- Range pickers use
pendingStartstate for two-click selection. RangeInputTriggerextendsInputTriggerwith twoflex:1inputs and a separator.