fix(components): [date-picker] config format manual change value invalid (#20223)

* fix(components): [date-picker] config format manual change value invalid

* fix: update
This commit is contained in:
btea
2025-03-25 10:09:47 +08:00
committed by GitHub
parent f9890d1df4
commit 2e58b8259d
7 changed files with 67 additions and 12 deletions

View File

@@ -478,6 +478,29 @@ describe('DatePicker', () => {
expect(dayjs(wrapper.vm.value).format('YYYY-MM-DD')).toBe('2023-10-01')
})
it('validate manual change value with format', async () => {
const wrapper = _mount(
`<el-date-picker
v-model="value"
format="DD.MM.YYYY"
/>`,
() => ({
value: '',
})
)
const input = wrapper.find('input')
input.element.value = '01.10.2023'
await input.trigger('input')
await input.trigger('blur')
expect(dayjs(wrapper.vm.value).format('YYYY-MM-DD')).toBe('2023-10-01')
input.element.value = '02.10.2023'
await input.trigger('input')
await input.trigger('blur')
expect(dayjs(wrapper.vm.value).format('YYYY-MM-DD')).toBe('2023-10-02')
})
it('ref focus', async () => {
_mount(
`<el-date-picker

View File

@@ -257,6 +257,7 @@ const slots = useSlots()
const { t, lang } = useLocale()
const pickerBase = inject('EP_PICKER_BASE') as any
const isDefaultFormat = inject('ElIsDefaultFormat') as any
const popper = inject(TOOLTIP_INJECTION_KEY)
const { shortcuts, disabledDate, cellClassName, defaultTime } = pickerBase.props
const defaultValue = toRef(pickerBase.props, 'defaultValue')
@@ -623,7 +624,8 @@ const handleVisibleDateChange = (value: string) => {
const newDate = correctlyParseUserInput(
value,
dateFormat.value,
lang.value
lang.value,
isDefaultFormat
) as Dayjs
if (newDate.isValid()) {
if (disabledDate && disabledDate(newDate.toDate())) {
@@ -651,7 +653,12 @@ const formatToString = (value: Dayjs | Dayjs[]) => {
}
const parseUserInput = (value: Dayjs) => {
return correctlyParseUserInput(value, props.format, lang.value)
return correctlyParseUserInput(
value,
props.format,
lang.value,
isDefaultFormat
)
}
const getDefaultValue = () => {

View File

@@ -313,6 +313,7 @@ const emit = defineEmits([
const unit = 'month'
// FIXME: fix the type for ep picker
const pickerBase = inject('EP_PICKER_BASE') as any
const isDefaultFormat = inject('ElIsDefaultFormat') as any
const { disabledDate, cellClassName, defaultTime, clearable } = pickerBase.props
const format = toRef(pickerBase.props, 'format')
const shortcuts = toRef(pickerBase.props, 'shortcuts')
@@ -722,7 +723,12 @@ const formatToString = (value: Dayjs | Dayjs[]) => {
}
const parseUserInput = (value: Dayjs | Dayjs[]) => {
return correctlyParseUserInput(value, format.value, lang.value)
return correctlyParseUserInput(
value,
format.value,
lang.value,
isDefaultFormat
)
}
function onParsedValueChanged(

View File

@@ -138,6 +138,7 @@ const unit = 'year'
const { lang } = useLocale()
const pickerBase = inject('EP_PICKER_BASE') as any
const isDefaultFormat = inject('ElIsDefaultFormat') as any
const { shortcuts, disabledDate } = pickerBase.props
const format = toRef(pickerBase.props, 'format')
const defaultValue = toRef(pickerBase.props, 'defaultValue')
@@ -224,7 +225,12 @@ const formatToString = (value: Dayjs | Dayjs[]) => {
}
const parseUserInput = (value: Dayjs | Dayjs[]) => {
return correctlyParseUserInput(value, format.value, lang.value)
return correctlyParseUserInput(
value,
format.value,
lang.value,
isDefaultFormat
)
}
function onParsedValueChanged(

View File

@@ -123,6 +123,7 @@ const leftDate = ref(dayjs().locale(lang.value))
const rightDate = ref(leftDate.value.add(10, 'year'))
const { pickerNs: ppNs } = inject(ROOT_PICKER_INJECTION_KEY)!
const drpNs = useNamespace('date-range-picker')
const isDefaultFormat = inject('isDefaultFormat') as any
const hasShortcuts = computed(() => !!shortcuts.length)
@@ -287,7 +288,12 @@ watch(
)
const parseUserInput = (value: Dayjs | Dayjs[]) => {
return correctlyParseUserInput(value, format.value, lang.value)
return correctlyParseUserInput(
value,
format.value,
lang.value,
isDefaultFormat
)
}
const formatToString = (value: Dayjs[] | Dayjs) => {

View File

@@ -1,4 +1,4 @@
import { defineComponent, provide, reactive, ref, toRef } from 'vue'
import { computed, defineComponent, provide, reactive, ref, toRef } from 'vue'
import dayjs from 'dayjs'
import customParseFormat from 'dayjs/plugin/customParseFormat.js'
import advancedFormat from 'dayjs/plugin/advancedFormat.js'
@@ -39,7 +39,10 @@ export default defineComponent({
emits: [UPDATE_MODEL_EVENT],
setup(props, { expose, emit, slots }) {
const ns = useNamespace('picker-panel')
const isDefaultFormat = computed(() => {
return !props.format
})
provide('ElIsDefaultFormat', isDefaultFormat)
provide('ElPopperOptions', reactive(toRef(props, 'popperOptions')))
provide(ROOT_PICKER_INJECTION_KEY, {
slots,

View File

@@ -1,7 +1,8 @@
import dayjs from 'dayjs'
import { isArray } from '@element-plus/utils'
import { isArray, isString } from '@element-plus/utils'
import { rangeArr } from '@element-plus/components/time-picker'
import type { ComputedRef } from 'vue'
import type { Dayjs } from 'dayjs'
import type { DateCell } from './date-picker.type'
import type { DisabledDateType } from './props/shared'
@@ -185,13 +186,16 @@ export const getValidDateOfYear = (
export const correctlyParseUserInput = (
value: string | Dayjs | Dayjs[],
format: string,
lang: string
lang: string,
defaultFormat: ComputedRef<boolean>
): Dayjs | Dayjs[] => {
if (isArray(value)) {
return value.map((v) => correctlyParseUserInput(v, format, lang) as Dayjs)
return value.map(
(v) => correctlyParseUserInput(v, format, lang, defaultFormat) as Dayjs
)
}
if (typeof value === 'string') {
const dayjsValue = dayjs(value)
if (isString(value)) {
const dayjsValue = defaultFormat.value ? dayjs(value) : dayjs(value, format)
if (!dayjsValue.isValid()) {
// return directly if not valid
return dayjsValue