diff --git a/src/components/ha-date-input.ts b/src/components/ha-date-input.ts index d3b5a0607eb3..d4d9922639d9 100644 --- a/src/components/ha-date-input.ts +++ b/src/components/ha-date-input.ts @@ -18,7 +18,8 @@ export interface datePickerDialogParams { max?: string; locale?: string; firstWeekday?: number; - onChange: (value: string) => void; + canClear?: boolean; + onChange: (value: string | undefined) => void; } const showDatePickerDialog = ( @@ -49,6 +50,8 @@ export class HaDateInput extends LitElement { @property() public helper?: string; + @property({ type: Boolean }) public canClear?: boolean; + render() { return html` this._valueChanged(value), locale: this.locale.language, firstWeekday: firstWeekdayIndex(this.locale), }); } - private _valueChanged(value: string) { + private _keyDown(ev: KeyboardEvent) { + if (!this.canClear) { + return; + } + if (["Backspace", "Delete"].includes(ev.key)) { + this._valueChanged(undefined); + } + } + + private _valueChanged(value: string | undefined) { if (this.value !== value) { this.value = value; fireEvent(this, "change"); diff --git a/src/components/ha-dialog-date-picker.ts b/src/components/ha-dialog-date-picker.ts index 2422754cfb15..b71e063ae410 100644 --- a/src/components/ha-dialog-date-picker.ts +++ b/src/components/ha-dialog-date-picker.ts @@ -50,6 +50,15 @@ export class HaDialogDatePicker extends LitElement { @datepicker-value-updated=${this._valueChanged} .firstDayOfWeek=${this._params.firstWeekday} > + ${this._params.canClear + ? html` + ${this.hass.localize("ui.dialogs.date-picker.clear")} + ` + : nothing} ${this.hass.localize("ui.dialogs.date-picker.today")} @@ -66,6 +75,11 @@ export class HaDialogDatePicker extends LitElement { this._value = ev.detail.value; } + private _clear() { + this._params?.onChange(undefined); + this.closeDialog(); + } + private _setToday() { const today = new Date(); this._value = format(today, "yyyy-MM-dd"); diff --git a/src/data/todo.ts b/src/data/todo.ts index e4f99090776b..9af8ef0f4cc6 100644 --- a/src/data/todo.ts +++ b/src/data/todo.ts @@ -18,8 +18,8 @@ export interface TodoItem { uid: string; summary: string; status: TodoItemStatus; - description?: string; - due?: string; + description?: string | null; + due?: string | null; } export const enum TodoListEntityFeature { @@ -83,9 +83,9 @@ export const updateItem = ( item: item.uid, rename: item.summary, status: item.status, - description: item.description || undefined, + description: item.description || null, due_datetime: item.due?.includes("T") ? item.due : undefined, - due_date: item.due?.includes("T") ? undefined : item.due || undefined, + due_date: item.due?.includes("T") ? undefined : item.due || null, }, { entity_id } ); diff --git a/src/panels/todo/dialog-todo-item-editor.ts b/src/panels/todo/dialog-todo-item-editor.ts index 5206bfe8a877..c81b9e4dbec3 100644 --- a/src/panels/todo/dialog-todo-item-editor.ts +++ b/src/panels/todo/dialog-todo-item-editor.ts @@ -161,7 +161,8 @@ class DialogTodoItemEditor extends LitElement { .value=${dueDate} .locale=${this.hass.locale} .disabled=${!canUpdate} - @value-changed=${this._endDateChanged} + @value-changed=${this._dueDateChanged} + canClear > ${this._todoListSupportsFeature( TodoListEntityFeature.SET_DUE_DATETIME_ON_ITEM @@ -170,7 +171,7 @@ class DialogTodoItemEditor extends LitElement { .value=${dueTime} .locale=${this.hass.locale} .disabled=${!canUpdate} - @value-changed=${this._endTimeChanged} + @value-changed=${this._dueTimeChanged} >` : nothing} @@ -259,12 +260,16 @@ class DialogTodoItemEditor extends LitElement { this._description = ev.target.value; } - private _endDateChanged(ev: CustomEvent) { + private _dueDateChanged(ev: CustomEvent) { + if (!ev.detail.value) { + this._due = undefined; + return; + } const time = this._due ? this._formatTime(this._due) : undefined; this._due = this._parseDate(`${ev.detail.value}${time ? `T${time}` : ""}`); } - private _endTimeChanged(ev: CustomEvent) { + private _dueTimeChanged(ev: CustomEvent) { this._hasTime = true; this._due = this._parseDate( `${this._formatDate(this._due || new Date())}T${ev.detail.value}` @@ -320,13 +325,13 @@ class DialogTodoItemEditor extends LitElement { TodoListEntityFeature.SET_DESCRIPTION_ON_ITEM ) ? // backend should accept null to clear the field, but it doesn't now - " " + null : undefined), due: this._due ? this._hasTime ? this._due.toISOString() : this._formatDate(this._due) - : undefined, + : null, status: this._checked ? TodoItemStatus.Completed : TodoItemStatus.NeedsAction, diff --git a/src/translations/en.json b/src/translations/en.json index b78aebb34507..b74543649f46 100644 --- a/src/translations/en.json +++ b/src/translations/en.json @@ -1009,7 +1009,8 @@ "crop_image": "Picture to crop" }, "date-picker": { - "today": "Today" + "today": "Today", + "clear": "Clear" }, "more_info_control": { "dismiss": "Dismiss dialog",