UNPKG

element-plus

Version:

A Component Library for Vue3.0

1,281 lines (1,258 loc) 63.8 kB
'use strict'; Object.defineProperty(exports, '__esModule', { value: true }); var vue = require('vue'); var dayjs = require('dayjs'); var customParseFormat = require('dayjs/plugin/customParseFormat'); var directives = require('../directives'); var ElInput = require('../el-input'); var ElPopper = require('../el-popper'); var aria = require('../utils/aria'); var util = require('../utils/util'); var form = require('../el-form'); var validators = require('../utils/validators'); var locale = require('../locale'); var debounce = require('lodash/debounce'); var ElScrollbar = require('../el-scrollbar'); var union = require('lodash/union'); function _interopDefaultLegacy (e) { return e && typeof e === 'object' && 'default' in e ? e : { 'default': e }; } var dayjs__default = /*#__PURE__*/_interopDefaultLegacy(dayjs); var customParseFormat__default = /*#__PURE__*/_interopDefaultLegacy(customParseFormat); var ElInput__default = /*#__PURE__*/_interopDefaultLegacy(ElInput); var ElPopper__default = /*#__PURE__*/_interopDefaultLegacy(ElPopper); var debounce__default = /*#__PURE__*/_interopDefaultLegacy(debounce); var ElScrollbar__default = /*#__PURE__*/_interopDefaultLegacy(ElScrollbar); var union__default = /*#__PURE__*/_interopDefaultLegacy(union); const DEFAULT_FORMATS_TIME = 'HH:mm:ss'; const DEFAULT_FORMATS_DATE = 'YYYY-MM-DD'; const DEFAULT_FORMATS_DATEPICKER = { date: DEFAULT_FORMATS_DATE, week: 'gggg[w]ww', year: 'YYYY', month: 'YYYY-MM', datetime: `${DEFAULT_FORMATS_DATE} ${DEFAULT_FORMATS_TIME}`, monthrange: 'YYYY-MM', daterange: DEFAULT_FORMATS_DATE, datetimerange: `${DEFAULT_FORMATS_DATE} ${DEFAULT_FORMATS_TIME}`, }; const defaultProps = { name: { type: [Array, String], default: '', }, popperClass: { type: String, default: '', }, format: { type: String, }, type: { type: String, default: '', }, clearable: { type: Boolean, default: true, }, clearIcon: { type: String, default: 'el-icon-circle-close', }, editable: { type: Boolean, default: true, }, prefixIcon: { type: String, default: '', }, size: { type: String, validator: validators.isValidComponentSize, }, readonly: { type: Boolean, default: false, }, disabled: { type: Boolean, default: false, }, placeholder: { type: String, default: '', }, modelValue: { type: [Date, Array, String], default: '', }, rangeSeparator: { type: String, default: '-', }, startPlaceholder: String, endPlaceholder: String, defaultValue: { type: [Date, Array], }, defaultTime: { type: [Date, Array], }, isRange: { type: Boolean, default: false, }, disabledHours: { type: Function, }, disabledMinutes: { type: Function, }, disabledSeconds: { type: Function, }, disabledDate: { type: Function, }, cellClassName: { type: Function, }, shortcuts: { type: Array, default: () => ([]), }, arrowControl: { type: Boolean, default: false, }, validateEvent: { type: Boolean, default: true, }, unlinkPanels: Boolean, }; const dateEquals = function (a, b) { const aIsDate = a instanceof Date; const bIsDate = b instanceof Date; if (aIsDate && bIsDate) { return a.getTime() === b.getTime(); } if (!aIsDate && !bIsDate) { return a === b; } return false; }; const valueEquals = function (a, b) { const aIsArray = a instanceof Array; const bIsArray = b instanceof Array; if (aIsArray && bIsArray) { if (a.length !== b.length) { return false; } return a.every((item, index) => dateEquals(item, b[index])); } if (!aIsArray && !bIsArray) { return dateEquals(a, b); } return false; }; var script = vue.defineComponent({ name: 'Picker', components: { ElInput: ElInput__default['default'], ElPopper: ElPopper__default['default'], }, directives: { clickoutside: directives.ClickOutside }, props: defaultProps, emits: ['update:modelValue', 'change', 'focus', 'blur'], setup(props, ctx) { const ELEMENT = util.useGlobalConfig(); const elForm = vue.inject(form.elFormKey, {}); const elFormItem = vue.inject(form.elFormItemKey, {}); const refPopper = vue.ref(null); const pickerVisible = vue.ref(false); const pickerActualVisible = vue.ref(false); const valueOnOpen = vue.ref(null); vue.watch(pickerVisible, val => { var _a; if (!val) { userInput.value = null; ctx.emit('blur'); blurInput(); props.validateEvent && ((_a = elFormItem.formItemMitt) === null || _a === void 0 ? void 0 : _a.emit('el.form.blur')); } else { valueOnOpen.value = props.modelValue; } }); const emitChange = val => { var _a; if (!valueEquals(val, valueOnOpen.value)) { ctx.emit('change', val); props.validateEvent && ((_a = elFormItem.formItemMitt) === null || _a === void 0 ? void 0 : _a.emit('el.form.change', val)); } }; const emitInput = val => { if (!valueEquals(props.modelValue, val)) { ctx.emit('update:modelValue', val); } }; const refInput = vue.computed(() => { if (refPopper.value.triggerRef) { const _r = isRangeInput.value ? refPopper.value.triggerRef : refPopper.value.triggerRef.$el; return [].slice.call(_r.querySelectorAll('input')); } return []; }); const setSelectionRange = (start, end, pos) => { const _inputs = refInput.value; if (!_inputs.length) return; if (!pos || pos === 'min') { _inputs[0].setSelectionRange(start, end); _inputs[0].focus(); } else if (pos === 'max') { _inputs[1].setSelectionRange(start, end); _inputs[1].focus(); } }; const onPick = (date = '', visible = false) => { pickerVisible.value = visible; let result; if (Array.isArray(date)) { result = date.map(_ => _.toDate()); } else { result = date ? date.toDate() : date; } userInput.value = null; emitInput(result); emitChange(result); }; const handleFocus = e => { if (props.readonly || pickerDisabled.value) return; pickerVisible.value = true; ctx.emit('focus', e); }; const pickerDisabled = vue.computed(() => { return props.disabled || elForm.disabled; }); const parsedValue = vue.computed(() => { let result; if (valueIsEmpty.value) { if (pickerOptions.value.getDefaultValue) { result = pickerOptions.value.getDefaultValue(); } } else { if (Array.isArray(props.modelValue)) { result = props.modelValue.map(_ => dayjs__default['default'](_)); } else { result = dayjs__default['default'](props.modelValue); } } if (pickerOptions.value.getRangeAvaliableTime) { result = pickerOptions.value.getRangeAvaliableTime(result); } return result; }); const displayValue = vue.computed(() => { if (!pickerOptions.value.panelReady) return; if (!isTimePicker.value && valueIsEmpty.value) return; if (!pickerVisible.value && valueIsEmpty.value) return; const formattedValue = formatDayjsToString(parsedValue.value); if (Array.isArray(userInput.value)) { return [ userInput.value[0] || (formattedValue && formattedValue[0]) || '', userInput.value[1] || (formattedValue && formattedValue[1]) || '', ]; } else if (userInput.value !== null) { return userInput.value; } if (formattedValue) { return isDatesPicker.value ? formattedValue.join(', ') : formattedValue; } return ''; }); const isTimeLikePicker = vue.computed(() => { return props.type.indexOf('time') !== -1; }); const isTimePicker = vue.computed(() => { return props.type.indexOf('time') === 0; }); const isDatesPicker = vue.computed(() => { return props.type === 'dates'; }); const triggerClass = vue.computed(() => { return props.prefixIcon || (isTimeLikePicker.value ? 'el-icon-time' : 'el-icon-date'); }); const showClose = vue.ref(false); const onClearIconClick = event => { if (props.readonly || pickerDisabled.value) return; if (showClose.value) { event.stopPropagation(); emitInput(null); emitChange(null); showClose.value = false; pickerVisible.value = false; pickerOptions.value.handleClear && pickerOptions.value.handleClear(); } }; const valueIsEmpty = vue.computed(() => { return !props.modelValue || (Array.isArray(props.modelValue) && !props.modelValue.length); }); const onMouseEnter = () => { if (props.readonly || pickerDisabled.value) return; if (!valueIsEmpty.value && props.clearable) { showClose.value = true; } }; const onMouseLeave = () => { showClose.value = false; }; const isRangeInput = vue.computed(() => { return props.type.indexOf('range') > -1; }); const pickerSize = vue.computed(() => { return props.size || elFormItem.size || ELEMENT.size; }); const onClickOutside = () => { if (!pickerVisible.value) return; pickerVisible.value = false; }; const userInput = vue.ref(null); const handleChange = () => { if (userInput.value) { const value = parseUserInputToDayjs(displayValue.value); if (value) { if (isValidValue(value)) { emitInput(value.toDate()); userInput.value = null; } } } if (userInput.value === '') { emitInput(null); emitChange(null); userInput.value = null; } }; const blurInput = () => { refInput.value.forEach(input => input.blur()); }; const parseUserInputToDayjs = value => { if (!value) return null; return pickerOptions.value.parseUserInput(value); }; const formatDayjsToString = value => { if (!value) return null; return pickerOptions.value.formatToString(value); }; const isValidValue = value => { return pickerOptions.value.isValidValue(value); }; const handleKeydown = event => { const code = event.code; if (code === aria.EVENT_CODE.esc) { pickerVisible.value = false; event.stopPropagation(); return; } if (code === aria.EVENT_CODE.tab) { if (!isRangeInput.value) { handleChange(); pickerVisible.value = false; event.stopPropagation(); } else { setTimeout(() => { if (refInput.value.indexOf(document.activeElement) === -1) { pickerVisible.value = false; blurInput(); } }, 0); } return; } if (code === aria.EVENT_CODE.enter) { if (userInput.value === '' || isValidValue(parseUserInputToDayjs(displayValue.value))) { handleChange(); pickerVisible.value = false; } event.stopPropagation(); return; } if (userInput.value) { event.stopPropagation(); return; } if (pickerOptions.value.handleKeydown) { pickerOptions.value.handleKeydown(event); } }; const onUserInput = e => { userInput.value = e; }; const handleStartInput = event => { if (userInput.value) { userInput.value = [event.target.value, userInput.value[1]]; } else { userInput.value = [event.target.value, null]; } }; const handleEndInput = event => { if (userInput.value) { userInput.value = [userInput.value[0], event.target.value]; } else { userInput.value = [null, event.target.value]; } }; const handleStartChange = () => { const value = parseUserInputToDayjs(userInput.value && userInput.value[0]); if (value) { userInput.value = [formatDayjsToString(value), displayValue.value[1]]; const newValue = [value, parsedValue.value && parsedValue.value[1]]; if (isValidValue(newValue)) { emitInput(newValue); userInput.value = null; } } }; const handleEndChange = () => { const value = parseUserInputToDayjs(userInput.value && userInput.value[1]); if (value) { userInput.value = [displayValue.value[0], formatDayjsToString(value)]; const newValue = [parsedValue.value && parsedValue.value[0], value]; if (isValidValue(newValue)) { emitInput(newValue); userInput.value = null; } } }; const pickerOptions = vue.ref({}); const onSetPickerOption = e => { pickerOptions.value[e[0]] = e[1]; pickerOptions.value.panelReady = true; }; vue.provide('EP_PICKER_BASE', { props, }); return { isDatesPicker, handleEndChange, handleStartChange, handleStartInput, handleEndInput, onUserInput, handleChange, handleKeydown, onClickOutside, pickerSize, isRangeInput, onMouseLeave, onMouseEnter, onClearIconClick, showClose, triggerClass, onPick, handleFocus, pickerVisible, pickerActualVisible, displayValue, parsedValue, setSelectionRange, refPopper, pickerDisabled, onSetPickerOption, }; }, }); const _hoisted_1 = { class: "el-range-separator" }; function render(_ctx, _cache, $props, $setup, $data, $options) { const _component_el_input = vue.resolveComponent("el-input"); const _component_el_popper = vue.resolveComponent("el-popper"); const _directive_clickoutside = vue.resolveDirective("clickoutside"); return (vue.openBlock(), vue.createBlock(_component_el_popper, vue.mergeProps({ ref: "refPopper", visible: _ctx.pickerVisible, "onUpdate:visible": _cache[18] || (_cache[18] = $event => (_ctx.pickerVisible = $event)), "manual-mode": "", effect: "light", pure: "", trigger: "click" }, _ctx.$attrs, { "popper-class": `el-picker__popper ${_ctx.popperClass}`, transition: "el-zoom-in-top", "gpu-acceleration": false, "stop-popper-mouse-event": false, "append-to-body": "", onBeforeEnter: _cache[19] || (_cache[19] = $event => (_ctx.pickerActualVisible = true)), onAfterLeave: _cache[20] || (_cache[20] = $event => (_ctx.pickerActualVisible = false)) }), { trigger: vue.withCtx(() => [ (!_ctx.isRangeInput) ? vue.withDirectives((vue.openBlock(), vue.createBlock(_component_el_input, { key: 0, "model-value": _ctx.displayValue, name: _ctx.name, size: _ctx.pickerSize, disabled: _ctx.pickerDisabled, placeholder: _ctx.placeholder, class: ["el-date-editor", 'el-date-editor--' + _ctx.type], readonly: !_ctx.editable || _ctx.readonly || _ctx.isDatesPicker || _ctx.type === 'week', onInput: _ctx.onUserInput, onFocus: _ctx.handleFocus, onKeydown: _ctx.handleKeydown, onChange: _ctx.handleChange, onMouseenter: _ctx.onMouseEnter, onMouseleave: _ctx.onMouseLeave }, { prefix: vue.withCtx(() => [ vue.createVNode("i", { class: ["el-input__icon", _ctx.triggerClass], onClick: _cache[1] || (_cache[1] = (...args) => (_ctx.handleFocus && _ctx.handleFocus(...args))) }, null, 2 /* CLASS */) ]), suffix: vue.withCtx(() => [ vue.createVNode("i", { class: ["el-input__icon", [_ctx.showClose ? '' + _ctx.clearIcon : '']], onClick: _cache[2] || (_cache[2] = (...args) => (_ctx.onClearIconClick && _ctx.onClearIconClick(...args))) }, null, 2 /* CLASS */) ]), _: 1 /* STABLE */ }, 8 /* PROPS */, ["model-value", "name", "size", "disabled", "placeholder", "class", "readonly", "onInput", "onFocus", "onKeydown", "onChange", "onMouseenter", "onMouseleave"])), [ [_directive_clickoutside, _ctx.onClickOutside] ]) : vue.withDirectives((vue.openBlock(), vue.createBlock("div", { key: 1, class: ["el-date-editor el-range-editor el-input__inner", [ 'el-date-editor--' + _ctx.type, _ctx.pickerSize ? `el-range-editor--${ _ctx.pickerSize }` : '', _ctx.pickerDisabled ? 'is-disabled' : '', _ctx.pickerVisible ? 'is-active' : '' ]], onClick: _cache[10] || (_cache[10] = (...args) => (_ctx.handleFocus && _ctx.handleFocus(...args))), onMouseenter: _cache[11] || (_cache[11] = (...args) => (_ctx.onMouseEnter && _ctx.onMouseEnter(...args))), onMouseleave: _cache[12] || (_cache[12] = (...args) => (_ctx.onMouseLeave && _ctx.onMouseLeave(...args))), onKeydown: _cache[13] || (_cache[13] = (...args) => (_ctx.handleKeydown && _ctx.handleKeydown(...args))) }, [ vue.createVNode("i", { class: ['el-input__icon', 'el-range__icon', _ctx.triggerClass] }, null, 2 /* CLASS */), vue.createVNode("input", { autocomplete: "off", name: _ctx.name && _ctx.name[0], placeholder: _ctx.startPlaceholder, value: _ctx.displayValue && _ctx.displayValue[0], disabled: _ctx.pickerDisabled, readonly: !_ctx.editable || _ctx.readonly, class: "el-range-input", onInput: _cache[3] || (_cache[3] = (...args) => (_ctx.handleStartInput && _ctx.handleStartInput(...args))), onChange: _cache[4] || (_cache[4] = (...args) => (_ctx.handleStartChange && _ctx.handleStartChange(...args))), onFocus: _cache[5] || (_cache[5] = (...args) => (_ctx.handleFocus && _ctx.handleFocus(...args))) }, null, 40 /* PROPS, HYDRATE_EVENTS */, ["name", "placeholder", "value", "disabled", "readonly"]), vue.renderSlot(_ctx.$slots, "range-separator", {}, () => [ vue.createVNode("span", _hoisted_1, vue.toDisplayString(_ctx.rangeSeparator), 1 /* TEXT */) ]), vue.createVNode("input", { autocomplete: "off", name: _ctx.name && _ctx.name[1], placeholder: _ctx.endPlaceholder, value: _ctx.displayValue && _ctx.displayValue[1], disabled: _ctx.pickerDisabled, readonly: !_ctx.editable || _ctx.readonly, class: "el-range-input", onFocus: _cache[6] || (_cache[6] = (...args) => (_ctx.handleFocus && _ctx.handleFocus(...args))), onInput: _cache[7] || (_cache[7] = (...args) => (_ctx.handleEndInput && _ctx.handleEndInput(...args))), onChange: _cache[8] || (_cache[8] = (...args) => (_ctx.handleEndChange && _ctx.handleEndChange(...args))) }, null, 40 /* PROPS, HYDRATE_EVENTS */, ["name", "placeholder", "value", "disabled", "readonly"]), vue.createVNode("i", { class: [[_ctx.showClose ? '' + _ctx.clearIcon : ''], "el-input__icon el-range__close-icon"], onClick: _cache[9] || (_cache[9] = (...args) => (_ctx.onClearIconClick && _ctx.onClearIconClick(...args))) }, null, 2 /* CLASS */) ], 34 /* CLASS, HYDRATE_EVENTS */)), [ [_directive_clickoutside, _ctx.onClickOutside] ]) ]), default: vue.withCtx(() => [ vue.renderSlot(_ctx.$slots, "default", { visible: _ctx.pickerVisible, actualVisible: _ctx.pickerActualVisible, parsedValue: _ctx.parsedValue, format: _ctx.format, unlinkPanels: _ctx.unlinkPanels, type: _ctx.type, defaultValue: _ctx.defaultValue, onPick: _cache[14] || (_cache[14] = (...args) => (_ctx.onPick && _ctx.onPick(...args))), onSelectRange: _cache[15] || (_cache[15] = (...args) => (_ctx.setSelectionRange && _ctx.setSelectionRange(...args))), onSetPickerOption: _cache[16] || (_cache[16] = (...args) => (_ctx.onSetPickerOption && _ctx.onSetPickerOption(...args))), onMousedown: _cache[17] || (_cache[17] = vue.withModifiers(() => {}, ["stop"])) }) ]), _: 1 /* STABLE */ }, 16 /* FULL_PROPS */, ["visible", "popper-class"])) } script.render = render; script.__file = "packages/time-picker/src/common/picker.vue"; const makeList = (total, method, methodFunc) => { const arr = []; const disabledArr = method && methodFunc(); for (let i = 0; i < total; i++) { arr[i] = disabledArr ? disabledArr.includes(i) : false; } return arr; }; const makeAvaliableArr = list => { return list.map((_, index) => !_ ? index : _).filter(_ => _ !== true); }; const getTimeLists = (disabledHours, disabledMinutes, disabledSeconds) => { const getHoursList = (role, compare) => { return makeList(24, disabledHours, () => disabledHours(role, compare)); }; const getMinutesList = (hour, role, compare) => { return makeList(60, disabledMinutes, () => disabledMinutes(hour, role, compare)); }; const getSecondsList = (hour, minute, role, compare) => { return makeList(60, disabledSeconds, () => disabledSeconds(hour, minute, role, compare)); }; return { getHoursList, getMinutesList, getSecondsList, }; }; const getAvaliableArrs = (disabledHours, disabledMinutes, disabledSeconds) => { const { getHoursList, getMinutesList, getSecondsList, } = getTimeLists(disabledHours, disabledMinutes, disabledSeconds); const getAvaliableHours = (role, compare) => { return makeAvaliableArr(getHoursList(role, compare)); }; const getAvaliableMinutes = (hour, role, compare) => { return makeAvaliableArr(getMinutesList(hour, role, compare)); }; const getAvaliableSeconds = (hour, minute, role, compare) => { return makeAvaliableArr(getSecondsList(hour, minute, role, compare)); }; return { getAvaliableHours, getAvaliableMinutes, getAvaliableSeconds, }; }; var script$1 = vue.defineComponent({ directives: { repeatClick: directives.RepeatClick, }, components: { ElScrollbar: ElScrollbar__default['default'], }, props: { role: { type: String, required: true, }, spinnerDate: { type: Object, required: true, }, showSeconds: { type: Boolean, default: true, }, arrowControl: Boolean, amPmMode: { type: String, default: '', }, disabledHours: { type: Function, }, disabledMinutes: { type: Function, }, disabledSeconds: { type: Function, }, }, emits: ['change', 'select-range', 'set-option'], setup(props, ctx) { let isScrolling = false; const debouncedResetScroll = debounce__default['default'](type => { isScrolling = false; adjustCurrentSpinner(type); }, 200); const currentScrollbar = vue.ref(null); const listHoursRef = vue.ref(null); const listMinutesRef = vue.ref(null); const listSecondsRef = vue.ref(null); const listRefsMap = { hours: listHoursRef, minutes: listMinutesRef, seconds: listSecondsRef, }; const spinnerItems = vue.computed(() => { const arr = ['hours', 'minutes', 'seconds']; return props.showSeconds ? arr : arr.slice(0, 2); }); const hours = vue.computed(() => { return props.spinnerDate.hour(); }); const minutes = vue.computed(() => { return props.spinnerDate.minute(); }); const seconds = vue.computed(() => { return props.spinnerDate.second(); }); const timePartsMap = vue.computed(() => ({ hours, minutes, seconds, })); const hoursList = vue.computed(() => { return getHoursList(props.role); }); const minutesList = vue.computed(() => { return getMinutesList(hours.value, props.role); }); const secondsList = vue.computed(() => { return getSecondsList(hours.value, minutes.value, props.role); }); const listMap = vue.computed(() => ({ hours: hoursList, minutes: minutesList, seconds: secondsList, })); const arrowHourList = vue.computed(() => { const hour = hours.value; return [ hour > 0 ? hour - 1 : undefined, hour, hour < 23 ? hour + 1 : undefined, ]; }); const arrowMinuteList = vue.computed(() => { const minute = minutes.value; return [ minute > 0 ? minute - 1 : undefined, minute, minute < 59 ? minute + 1 : undefined, ]; }); const arrowSecondList = vue.computed(() => { const second = seconds.value; return [ second > 0 ? second - 1 : undefined, second, second < 59 ? second + 1 : undefined, ]; }); const arrowListMap = vue.computed(() => ({ hours: arrowHourList, minutes: arrowMinuteList, seconds: arrowSecondList, })); const getAmPmFlag = hour => { let shouldShowAmPm = !!props.amPmMode; if (!shouldShowAmPm) return ''; let isCapital = props.amPmMode === 'A'; let content = (hour < 12) ? ' am' : ' pm'; if (isCapital) content = content.toUpperCase(); return content; }; const emitSelectRange = type => { if (type === 'hours') { ctx.emit('select-range', 0, 2); } else if (type === 'minutes') { ctx.emit('select-range', 3, 5); } else if (type === 'seconds') { ctx.emit('select-range', 6, 8); } currentScrollbar.value = type; }; const adjustCurrentSpinner = type => { adjustSpinner(type, timePartsMap.value[type].value); }; const adjustSpinners = () => { adjustCurrentSpinner('hours'); adjustCurrentSpinner('minutes'); adjustCurrentSpinner('seconds'); }; const adjustSpinner = (type, value) => { if (props.arrowControl) return; const el = listRefsMap[type]; if (el.value) { el.value.$el.querySelector('.el-scrollbar__wrap').scrollTop = Math.max(0, value * typeItemHeight(type)); } }; const typeItemHeight = type => { const el = listRefsMap[type]; return el.value.$el.querySelector('li').offsetHeight; }; const onIncreaseClick = () => { scrollDown(1); }; const onDecreaseClick = () => { scrollDown(-1); }; const scrollDown = step => { if (!currentScrollbar.value) { emitSelectRange('hours'); } const label = currentScrollbar.value; let now = timePartsMap.value[label].value; const total = currentScrollbar.value === 'hours' ? 24 : 60; now = (now + step + total) % total; modifyDateField(label, now); adjustSpinner(label, now); vue.nextTick(() => emitSelectRange(currentScrollbar.value)); }; const modifyDateField = (type, value) => { const list = listMap.value[type].value; const isDisabled = list[value]; if (isDisabled) return; switch (type) { case 'hours': ctx.emit('change', props.spinnerDate .hour(value) .minute(minutes.value) .second(seconds.value)); break; case 'minutes': ctx.emit('change', props.spinnerDate .hour(hours.value) .minute(value) .second(seconds.value)); break; case 'seconds': ctx.emit('change', props.spinnerDate .hour(hours.value) .minute(minutes.value) .second(value)); break; } }; const handleClick = (type, { value, disabled }) => { if (!disabled) { modifyDateField(type, value); emitSelectRange(type); adjustSpinner(type, value); } }; const handleScroll = type => { isScrolling = true; debouncedResetScroll(type); const value = Math.min(Math.round((listRefsMap[type].value.$el.querySelector('.el-scrollbar__wrap').scrollTop - (scrollBarHeight(type) * 0.5 - 10) / typeItemHeight(type) + 3) / typeItemHeight(type)), (type === 'hours' ? 23 : 59)); modifyDateField(type, value); }; const scrollBarHeight = type => { return listRefsMap[type].value.$el.offsetHeight; }; const bindScrollEvent = () => { const bindFuntion = type => { if (listRefsMap[type].value) { listRefsMap[type].value.$el.querySelector('.el-scrollbar__wrap').onscroll = () => { handleScroll(type); }; } }; bindFuntion('hours'); bindFuntion('minutes'); bindFuntion('seconds'); }; vue.onMounted(() => { vue.nextTick(() => { !props.arrowControl && bindScrollEvent(); adjustSpinners(); if (props.role === 'start') emitSelectRange('hours'); }); }); const getRefId = item => { return `list${item.charAt(0).toUpperCase() + item.slice(1)}Ref`; }; ctx.emit('set-option', [`${props.role}_scrollDown`, scrollDown]); ctx.emit('set-option', [`${props.role}_emitSelectRange`, emitSelectRange]); const { getHoursList, getMinutesList, getSecondsList, } = getTimeLists(props.disabledHours, props.disabledMinutes, props.disabledSeconds); vue.watch(() => props.spinnerDate, () => { if (isScrolling) return; adjustSpinners(); }); return { getRefId, spinnerItems, currentScrollbar, hours, minutes, seconds, hoursList, minutesList, arrowHourList, arrowMinuteList, arrowSecondList, getAmPmFlag, emitSelectRange, adjustCurrentSpinner, typeItemHeight, listHoursRef, listMinutesRef, listSecondsRef, onIncreaseClick, onDecreaseClick, handleClick, secondsList, timePartsMap, arrowListMap, listMap, }; }, }); const _hoisted_1$1 = { class: "el-time-spinner__arrow el-icon-arrow-up" }; const _hoisted_2 = { class: "el-time-spinner__arrow el-icon-arrow-down" }; const _hoisted_3 = { class: "el-time-spinner__list" }; function render$1(_ctx, _cache, $props, $setup, $data, $options) { const _component_el_scrollbar = vue.resolveComponent("el-scrollbar"); const _directive_repeat_click = vue.resolveDirective("repeat-click"); return (vue.openBlock(), vue.createBlock("div", { class: ["el-time-spinner", { 'has-seconds': _ctx.showSeconds }] }, [ (!_ctx.arrowControl) ? (vue.openBlock(true), vue.createBlock(vue.Fragment, { key: 0 }, vue.renderList(_ctx.spinnerItems, (item) => { return (vue.openBlock(), vue.createBlock(_component_el_scrollbar, { key: item, ref: _ctx.getRefId(item), class: "el-time-spinner__wrapper", "wrap-style": "max-height: inherit;", "view-class": "el-time-spinner__list", noresize: "", tag: "ul", onMouseenter: $event => (_ctx.emitSelectRange(item)), onMousemove: $event => (_ctx.adjustCurrentSpinner(item)) }, { default: vue.withCtx(() => [ (vue.openBlock(true), vue.createBlock(vue.Fragment, null, vue.renderList(_ctx.listMap[item].value, (disabled, key) => { return (vue.openBlock(), vue.createBlock("li", { key: key, class: ["el-time-spinner__item", { 'active': key === _ctx.timePartsMap[item].value, disabled }], onClick: $event => (_ctx.handleClick(item, { value: key, disabled })) }, [ (item === 'hours') ? (vue.openBlock(), vue.createBlock(vue.Fragment, { key: 0 }, [ vue.createTextVNode(vue.toDisplayString(('0' + (_ctx.amPmMode ? (key % 12 || 12) : key )).slice(-2)) + vue.toDisplayString(_ctx.getAmPmFlag(key)), 1 /* TEXT */) ], 64 /* STABLE_FRAGMENT */)) : (vue.openBlock(), vue.createBlock(vue.Fragment, { key: 1 }, [ vue.createTextVNode(vue.toDisplayString(('0' + key).slice(-2)), 1 /* TEXT */) ], 64 /* STABLE_FRAGMENT */)) ], 10 /* CLASS, PROPS */, ["onClick"])) }), 128 /* KEYED_FRAGMENT */)) ]), _: 2 /* DYNAMIC */ }, 1032 /* PROPS, DYNAMIC_SLOTS */, ["onMouseenter", "onMousemove"])) }), 128 /* KEYED_FRAGMENT */)) : vue.createCommentVNode("v-if", true), (_ctx.arrowControl) ? (vue.openBlock(true), vue.createBlock(vue.Fragment, { key: 1 }, vue.renderList(_ctx.spinnerItems, (item) => { return (vue.openBlock(), vue.createBlock("div", { key: item, class: "el-time-spinner__wrapper is-arrow", onMouseenter: $event => (_ctx.emitSelectRange(item)) }, [ vue.withDirectives(vue.createVNode("i", _hoisted_1$1, null, 512 /* NEED_PATCH */), [ [_directive_repeat_click, _ctx.onDecreaseClick] ]), vue.withDirectives(vue.createVNode("i", _hoisted_2, null, 512 /* NEED_PATCH */), [ [_directive_repeat_click, _ctx.onIncreaseClick] ]), vue.createVNode("ul", _hoisted_3, [ (vue.openBlock(true), vue.createBlock(vue.Fragment, null, vue.renderList(_ctx.arrowListMap[item].value, (time, key) => { return (vue.openBlock(), vue.createBlock("li", { key: key, class: ["el-time-spinner__item", { 'active': time === _ctx.timePartsMap[item].value, 'disabled': _ctx.listMap[item].value[time] }] }, vue.toDisplayString(time === undefined ? '' : ('0' + (_ctx.amPmMode ? (time % 12 || 12) : time )).slice(-2) + _ctx.getAmPmFlag(time)), 3 /* TEXT, CLASS */)) }), 128 /* KEYED_FRAGMENT */)) ]) ], 40 /* PROPS, HYDRATE_EVENTS */, ["onMouseenter"])) }), 128 /* KEYED_FRAGMENT */)) : vue.createCommentVNode("v-if", true) ], 2 /* CLASS */)) } script$1.render = render$1; script$1.__file = "packages/time-picker/src/time-picker-com/basic-time-spinner.vue"; var script$2 = vue.defineComponent({ components: { TimeSpinner: script$1, }, props: { visible: Boolean, actualVisible: { type: Boolean, default: undefined, }, datetimeRole: { type: String, }, parsedValue: { type: [Object, String], }, format: { type: String, default: '', }, }, emits: ['pick', 'select-range', 'set-picker-option'], setup(props, ctx) { const selectionRange = vue.ref([0, 2]); const oldValue = vue.ref(props.parsedValue); const transitionName = vue.computed(() => { return props.actualVisible === undefined ? 'el-zoom-in-top' : ''; }); const showSeconds = vue.computed(() => { return props.format.includes('ss'); }); const amPmMode = vue.computed(() => { if (props.format.includes('A')) return 'A'; if (props.format.includes('a')) return 'a'; return ''; }); const isValidValue = _date => { const parsedDate = dayjs__default['default'](_date); const result = getRangeAvaliableTime(parsedDate); return parsedDate.isSame(result); }; const handleCancel = () => { ctx.emit('pick', oldValue.value, false); }; const handleConfirm = (visible = false, first) => { if (first) return; ctx.emit('pick', props.parsedValue, visible); }; const handleChange = (_date) => { if (!props.visible) { return; } const result = getRangeAvaliableTime(_date).millisecond(0); ctx.emit('pick', result, true); }; const setSelectionRange = (start, end) => { ctx.emit('select-range', start, end); selectionRange.value = [start, end]; }; const changeSelectionRange = step => { const list = [0, 3].concat(showSeconds.value ? [6] : []); const mapping = ['hours', 'minutes'].concat(showSeconds.value ? ['seconds'] : []); const index = list.indexOf(selectionRange.value[0]); const next = (index + step + list.length) % list.length; timePickeOptions['start_emitSelectRange'](mapping[next]); }; const handleKeydown = event => { const code = event.code; if (code === aria.EVENT_CODE.left || code === aria.EVENT_CODE.right) { const step = (code === aria.EVENT_CODE.left) ? -1 : 1; changeSelectionRange(step); event.preventDefault(); return; } if (code === aria.EVENT_CODE.up || code === aria.EVENT_CODE.down) { const step = (code === aria.EVENT_CODE.up) ? -1 : 1; timePickeOptions['start_scrollDown'](step); event.preventDefault(); return; } }; const getRangeAvaliableTime = (date) => { const avaliableMap = { hour: getAvaliableHours, minute: getAvaliableMinutes, second: getAvaliableSeconds, }; let result = date; ['hour', 'minute', 'second'].forEach(_ => { if (avaliableMap[_]) { let avaliableArr; const method = avaliableMap[_]; if (_ === 'minute') { avaliableArr = method(result.hour(), props.datetimeRole); } else if (_ === 'second') { avaliableArr = method(result.hour(), result.minute(), props.datetimeRole); } else { avaliableArr = method(props.datetimeRole); } if (avaliableArr && avaliableArr.length && !avaliableArr.includes(result[_]())) { result = result[_](avaliableArr[0]); } } }); return result; }; const parseUserInput = value => { if (!value) return null; return dayjs__default['default'](value, props.format); }; const formatToString = value => { if (!value) return null; return value.format(props.format); }; const getDefaultValue = () => { return dayjs__default['default'](defaultValue); }; ctx.emit('set-picker-option', ['isValidValue', isValidValue]); ctx.emit('set-picker-option', ['formatToString', formatToString]); ctx.emit('set-picker-option', ['parseUserInput', parseUserInput]); ctx.emit('set-picker-option', ['handleKeydown', handleKeydown]); ctx.emit('set-picker-option', ['getRangeAvaliableTime', getRangeAvaliableTime]); ctx.emit('set-picker-option', ['getDefaultValue', getDefaultValue]); const timePickeOptions = {}; const onSetOption = e => { timePickeOptions[e[0]] = e[1]; }; const pickerBase = vue.inject('EP_PICKER_BASE'); const { arrowControl, disabledHours, disabledMinutes, disabledSeconds, defaultValue } = pickerBase.props; const { getAvaliableHours, getAvaliableMinutes, getAvaliableSeconds, } = getAvaliableArrs(disabledHours, disabledMinutes, disabledSeconds); return { transitionName, arrowControl, onSetOption, t: locale.t, handleConfirm, handleChange, setSelectionRange, amPmMode, showSeconds, handleCancel, disabledHours, disabledMinutes, disabledSeconds, }; }, }); const _hoisted_1$2 = { key: 0, class: "el-time-panel" }; const _hoisted_2$1 = { class: "el-time-panel__footer" }; function render$2(_ctx, _cache, $props, $setup, $data, $options) { const _component_time_spinner = vue.resolveComponent("time-spinner"); return (vue.openBlock(), vue.createBlock(vue.Transition, { name: _ctx.transitionName }, { default: vue.withCtx(() => [ (_ctx.actualVisible || _ctx.visible) ? (vue.openBlock(), vue.createBlock("div", _hoisted_1$2, [ vue.createVNode("div", { class: ["el-time-panel__content", { 'has-seconds': _ctx.showSeconds }] }, [ vue.createVNode(_component_time_spinner, { ref: "spinner", role: _ctx.datetimeRole || 'start', "arrow-control": _ctx.arrowControl, "show-seconds": _ctx.showSeconds, "am-pm-mode": _ctx.amPmMode, "spinner-date": _ctx.parsedValue, "disabled-hours": _ctx.disabledHours, "disabled-minutes": _ctx.disabledMinutes, "disabled-seconds": _ctx.disabledSeconds, onChange: _ctx.handleChange, onSetOption: _ctx.onSetOption, onSelectRange: _ctx.setSelectionRange }, null, 8 /* PROPS */, ["role", "arrow-control", "show-seconds", "am-pm-mode", "spinner-date", "disabled-hours", "disabled-minutes", "disabled-seconds", "onChange", "onSetOption", "onSelectRange"]) ], 2 /* CLASS */), vue.createVNode("div", _hoisted_2$1, [ vue.createVNode("button", { type: "button", class: "el-time-panel__btn cancel", onClick: _cache[1] || (_cache[1] = (...args) => (_ctx.handleCancel && _ctx.handleCancel(...args))) }, vue.toDisplayString(_ctx.t('el.datepicker.cancel')), 1 /* TEXT */), vue.createVNode("button", { type: "button", class: "el-time-panel__btn confirm", onClick: _cache[2] || (_cache[2] = $event => (_ctx.handleConfirm())) }, vue.toDisplayString(_ctx.t('el.datepicker.confirm')), 1 /* TEXT */) ]) ])) : vue.createCommentVNode("v-if", true) ]), _: 1 /* STABLE */ }, 8 /* PROPS */, ["name"])) } script$2.render = render$2; script$2.__file = "packages/time-picker/src/time-picker-com/panel-time-pick.vue"; const makeSelectRange = (start, end) => { const result = []; for (let i = start; i <= end; i++) { result.push(i); } return result; }; var script$3 = vue.defineComponent({ components: { TimeSpinner: script$1 }, props: { visible: Boolean, actualVisible: Boolean, parsedValue: { type: [Array, String], }, format: { type: String, default: '', }, }, emits: ['pick', 'select-range', 'set-picker-option'], setup(props, ctx) { const minDate = vue.computed(() => props.parsedValue[0]); const maxDate = vue.computed(() => props.parsedValue[1]); const oldValue = vue.ref(props.parsedValue); const handleCancel = () => { ctx.emit('pick', oldValue.value, null); }; const showSeconds = vue.computed(() => { return props.format.includes('ss'); }); const amPmMode = vue.computed(() => { if (props.format.includes('A')) return 'A'; if (props.format.includes('a')) return 'a'; return ''; }); const minSelectableRange = vue.ref([]); const maxSelectableRange = vue.ref([]); const handleConfirm = (visible = false) => { ctx.emit('pick', [minDate.value, maxDate.value], visible); }; const handleMinChange = date => { handleChange(date.millisecond(0), maxDate.value); }; const handleMaxChange = date => { handleChange(minDate.value, date.millisecond(0)); }; const isValidValue = _date => { const parsedDate = _date.map(_ => dayjs__default['default'](_)); const result = getRangeAvaliableTime(parsedDate); return parsedDate[0].isSame(result[0]) && parsedDate[1].isSame(result[1]); }; const handleChange = (_minDate, _maxDate) => { ctx.emit('pick', [_minDate, _maxDate], true); }; const btnConfirmDisabled = vue.computed(() =