Improve Date, Time, and Date-and-Time field width, clearing, and picker footer in the new Edit Contentlet
@adrianjm-dotCMS is already working on this.
Since Sep 15, 2026.
- Dominant language
- Java
- Stars
- 970
- Forks
- 486
- Avg merge
- 3d 33m
- Merged PRs (30d)
- 170
Description
Description
The Date, Time, and Date and time fields in the new Edit Contentlet need three presentation improvements: they should fill the width of their column, they should be clearable directly from the field, and the picker overlay's footer should show the timezone on the left with a Today button on the right.
1. Field does not fill its column
The date/time control is narrower than its column while every other field type stretches to the full column width.
Cause: calendar-field.component.scss sets display: inline-flex on the p-datepicker wrapper, so the control sizes to its content instead of its container. Sibling fields do stretch — e.g. the Text field puts class="w-full" on its <input>.
// core-web/libs/edit-content/src/lib/fields/dot-edit-content-calendar-field/components/calendar-field/calendar-field.component.scss
:host ::ng-deep p-datepicker {
// Use PrimeNG's default datepicker sizing
display: inline-flex; // <-- keeps the field from filling the column
...
}
2. No clear control on the field
showClear is hardcoded to the content type's expire-date field only, so every other date/time field has no way to empty a value once set:
<!-- calendar-field.component.html -->
[showClear]="$isExpireDateField()"
The mock shows a clear (X) icon between the value and the calendar button on an ordinary Posting Date field.
3. Picker footer
[showButtonBar]="true" renders PrimeNG's default button bar — Today on the left, Clear on the right. The target footer is:
| Slot | Content | Style |
|---|---|---|
| Left | Timezone | Gray, muted text — not a button |
| Right | Today (Now for Time-only) |
Secondary button, outlined |
The Clear button leaves the footer entirely — clearing is now the on-field X from #2.
Interaction with #37464
The timezone currently renders under the input as <small class="p-field-hint">{{ systemTimezone.label }}</small> in dot-edit-content-calendar-field.component.html. This issue moves it into the picker footer and removes the under-input line.
That supersedes part of #37464, which left timezone placement out of scope and specified "when a Date/Time field has both a timezone and a hint, show the hint only". Once the timezone lives in the picker, the timezone-vs-hint collision disappears and the field footer carries hint and required-error text only. Whichever issue lands second should drop the now-moot criterion from the other.
Relevant code
| Concern | Location |
|---|---|
Picker markup, showClear, showButtonBar |
core-web/libs/edit-content/src/lib/fields/dot-edit-content-calendar-field/components/calendar-field/calendar-field.component.html |
inline-flex width, focus-ring styling |
.../components/calendar-field/calendar-field.component.scss |
$isExpireDateField, onCalendarChange, value handling |
.../components/calendar-field/calendar-field.component.ts |
Per-type config (showTime / timeOnly / icon) |
.../components/calendar-field/calendar-field.util.ts — CALENDAR_OPTIONS_PER_TYPE |
| Under-input timezone line (to be removed) | .../dot-edit-content-calendar-field.component.html |
| Server time helper | getCurrentServerTime(...) in calendar-field.util.ts |
| Message bundle | dotCMS/src/main/webapp/WEB-INF/messages/Language.properties |
All three field types route through the same component — DATE, TIME, and DATE_AND_TIME all map to dot-edit-content-calendar-field in dot-edit-content-field.component.html — so one fix covers all three.
Acceptance Criteria
Width
- Date, Time, and Date and time fields fill 100% of the width of the column they are rendered in, matching sibling field types (Text, Select, etc.).
- The input and the calendar/clock trigger button remain visually joined as one control at full width — the trigger stays flush to the right edge.
- The focus ring still encloses input and trigger button as a single unit (the behavior
calendar-field.component.scssdeliberately implements today). - Width is correct in single-column and multi-column form layouts, and at narrow viewport widths.
Clear on the field
- A clear (X) control renders inside the field, between the value and the calendar/clock trigger, for all three field types.
- The X is shown only when the field holds a value, and is not rendered when the field is empty.
- Clicking the X empties the field: the display value clears, the form control is set to
null, and the control is marked touched/dirty so validation reacts. - Clearing a required field leaves it empty and invalid — the X is not suppressed on required fields, and the required error appears per the rules in #37464.
- The X is not rendered when the field is disabled or read-only.
- The expire-date field keeps working: its
Never Expiresplaceholder still shows when cleared, and it does not end up with two clear controls. - The X is keyboard reachable and has an accessible label (e.g.
Clear), not an icon-only unlabelled button.
Picker footer — timezone
- Opening the picker on a Date and time or Time field shows the timezone as gray, muted, non-interactive text in the left of the footer.
- Opening the picker on a Date-only field shows no timezone text — the footer holds the button only.
- The timezone text is the same value shown today (
systemTimezone.label), and renders nothing (no empty footer slot, no layout shift) when the timezone is unavailable. - The under-input
<small class="p-field-hint">timezone line is removed fromdot-edit-content-calendar-field.component.html.
Picker footer — Today / Now button
- The footer's right slot holds a single button, styled as secondary with an outline, using the shared PrimeNG button styling (not bespoke CSS).
- The button reads
Todayon Date and Date and time fields, andNowon Time-only fields. - On a Date and time field, the button sets today's date plus the current server time.
- On a Date-only field, the button sets today's date.
- On a Time-only field,
Nowsets the current server time. - The value the button sets respects the server timezone — it goes through the existing
getCurrentServerTime/convertServerTimeToUtcpath, not the browser's local clock. - After clicking the button the field shows the new value, the form control updates, and the control is marked touched/dirty.
- PrimeNG's default
Clearbutton no longer appears in the footer for any of the three field types. - Button and timezone labels come from
Language.propertieskeys (new keys needed — notoday/nowkey exists under theedit.content.form.field.calendar.*namespace today) and are not hardcoded strings.
Regression
- Existing timezone conversion behavior is unchanged: values still store as UTC timestamps, Date-only as UTC midnight, Time-only against a consistent date base.
-
field.defaultValuehandling (nowand fixed dates) still works. - The picker still does not close on time selection (
hideOnDateTimeSelectisfalse) and still appends tobody. - The error border on the control in the invalid state still renders (
:host.ng-invalid.ng-touched).
Tests
- Unit tests cover: X hidden when empty, X shown when a value is set, X clears the value and marks the control touched.
- Unit tests cover the footer per field type — timezone present for Date and time and Time-only, absent for Date-only.
- Unit tests cover the button label (
TodayvsNow) and the value it sets for each of the three field types. - A test asserts PrimeNG's
Clearbutton is absent from the picker footer. - Existing
dot-edit-content-calendar-field.component.spec.tsassertions on thecalendar-field-timezonetestid are updated for the new placement.
Priority
Medium
Additional Context
Mock 1 — the field. A Posting Date field showing 09/04/2026 09:33, with a clear X and the calendar trigger to its right. A red line extends to the right of the field toward the column edge, marking the width the field should occupy.
Mock 2 — the open picker. Month/year header with prev/next arrows, day grid (the 4th selected), divider, hour/minute spinner (09 : 33), then the footer. Red annotations: "TimeZone: text gray" on the left of the footer and "Today button sec with outline" on the right. The current build's footer — Today left, Clear right — is what the annotations replace.
Resolved during refinement:
| Question | Decision |
|---|---|
| Does the picker footer keep a Clear button? | No — removed; clearing is the on-field X |
| When is the on-field X visible? | Only when the field holds a value |
| Does the under-input timezone line stay? | No — moved into the picker footer |
| Which field types show the timezone in the footer? | Date and time + Time-only; not Date-only |
| What does Today set on a Date and time field? | Today's date + the current time |
| What does the Time-only footer show? | A Now button, same secondary-outline styling and position |
Out of scope: hint and required-error presentation (covered by #37464); moving the timezone to a secondary line under the label; changing the stored value format or the timezone conversion logic; the legacy (non-new) Edit Contentlet screen.
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Assessment
This issue has not been assessed yet.