diff --git a/packages/core/src/useDateTimeField/useDateTimeField.ts b/packages/core/src/useDateTimeField/useDateTimeField.ts index 3d2cbbaf..5b35dd45 100644 --- a/packages/core/src/useDateTimeField/useDateTimeField.ts +++ b/packages/core/src/useDateTimeField/useDateTimeField.ts @@ -10,6 +10,7 @@ import { useErrorMessage, useLabel } from '../a11y'; import { fromDateToCalendarZonedDateTime, useTemporalStore } from './useTemporalStore'; import { ZonedDateTime, Calendar } from '@internationalized/date'; import { useInputValidity } from '../validation'; +import { createDisabledContext } from '../helpers/createDisabledContext'; export interface DateTimeFieldProps { /** @@ -96,6 +97,7 @@ export function useDateTimeField(_props: Reactivify toValue(props.timeZone), }); + const isDisabled = createDisabledContext(props.disabled); const formatter = useDateFormatter(locale, props.formatOptions); const controlId = useUniqId(FieldTypePrefixes.DateTimeField); @@ -126,8 +128,10 @@ export function useDateTimeField(_props: Reactivify field.setTouched(true), min: computed(() => fromDateToCalendarZonedDateTime(toValue(props.min), calendar.value, timeZone.value)), @@ -172,6 +176,7 @@ export function useDateTimeField(_props: Reactivify) { const id = useUniqId(FieldTypePrefixes.DateTimeSegment); const segmentEl = shallowRef(); const segmentGroup = inject(DateTimeSegmentGroupKey, null); - const isNonEditable = () => toValue(props.disabled) || !isEditableSegmentType(toValue(props.type)); + const isDisabled = createDisabledContext(props.disabled); + const isNonEditable = () => isDisabled.value || !isEditableSegmentType(toValue(props.type)); if (!segmentGroup) { throw new Error('DateTimeSegmentGroup is not provided'); @@ -80,6 +88,11 @@ export function useDateTimeSegment(_props: Reactivify) { currentInput = ''; }, onBeforeinput(evt: InputEvent) { + if (toValue(props.readonly) || isDisabled.value) { + blockEvent(evt); + return; + } + // No data,like backspace or whatever if (isNullOrUndefined(evt.data)) { return; @@ -129,6 +142,10 @@ export function useDateTimeSegment(_props: Reactivify) { currentInput = ''; }, onKeydown(evt: KeyboardEvent) { + if (toValue(props.readonly) || isDisabled.value) { + return; + } + if (hasKeyCode(evt, 'Enter')) { blockEvent(evt); focusNext(); @@ -165,9 +182,10 @@ export function useDateTimeSegment(_props: Reactivify) { id, tabindex: isNonEditable() ? -1 : 0, contenteditable: isNonEditable() ? undefined : 'plaintext-only', - 'aria-disabled': toValue(props.disabled), + 'aria-disabled': isDisabled.value, 'data-segment-type': toValue(props.type), 'aria-label': isNonEditable() ? undefined : toValue(props.type), + 'aria-readonly': toValue(props.readonly) ? true : undefined, autocorrect: isNonEditable() ? undefined : 'off', spellcheck: isNonEditable() ? undefined : false, enterkeyhint: isNonEditable() ? undefined : isLast() ? 'done' : 'next', @@ -203,7 +221,7 @@ export function useDateTimeSegment(_props: Reactivify) { export const DateTimeSegment = defineComponent({ name: 'DateTimeSegment', - props: ['type', 'value', 'disabled'], + props: ['type', 'value', 'disabled', 'readonly'], setup(props) { const { segmentProps } = useDateTimeSegment(props); diff --git a/packages/core/src/useDateTimeField/useDateTimeSegmentGroup.ts b/packages/core/src/useDateTimeField/useDateTimeSegmentGroup.ts index 80dd8647..313bf94e 100644 --- a/packages/core/src/useDateTimeField/useDateTimeSegmentGroup.ts +++ b/packages/core/src/useDateTimeField/useDateTimeSegmentGroup.ts @@ -46,6 +46,7 @@ export interface DateTimeSegmentGroupProps { temporalValue: MaybeRefOrGetter; direction?: MaybeRefOrGetter; controlEl: Ref; + readonly?: MaybeRefOrGetter; min?: MaybeRefOrGetter>; max?: MaybeRefOrGetter>; onValueChange: (value: ZonedDateTime) => void; @@ -59,6 +60,7 @@ export function useDateTimeSegmentGroup({ direction, locale, controlEl, + readonly, min, max, onValueChange, @@ -78,7 +80,7 @@ export function useDateTimeSegmentGroup({ const segments = computed(() => { const date = toValue(temporalValue); - const parts = formatter.value.formatToParts(date.toDate()) as { + let parts = formatter.value.formatToParts(date.toDate()) as { type: DateTimeSegmentType; value: string; }[]; @@ -95,6 +97,15 @@ export function useDateTimeSegmentGroup({ } } + if (toValue(readonly)) { + parts = parts.map(part => { + return { + ...part, + readonly: true, + }; + }); + } + return parts; });