UNPKG

song-ui-u

Version:

vue3 + js的PC前端组件库

425 lines (422 loc) 15.7 kB
import { defineComponent, ref, computed, onMounted, onUnmounted, createVNode, createTextVNode, resolveComponent } from 'vue'; import '../../button/index.mjs'; import '../../buttonGroup/index.mjs'; import { XIcon } from '../../icon/index.mjs'; import { XInput } from '../../input/index.mjs'; import '../../textarea/index.mjs'; import '../../row/index.mjs'; import '../../col/index.mjs'; import '../../container/index.mjs'; import '../../checkbox/index.mjs'; import '../../switch/index.mjs'; import '../../form/index.mjs'; import '../../message/index.mjs'; import '../../mask/src/mask.mjs'; import '../../modal/index.mjs'; import '../../messageBox/index.mjs'; import '../../drawer/index.mjs'; import '../../badge/index.mjs'; import '../../space/index.mjs'; import '../../image/index.mjs'; import '../../radio/index.mjs'; import '../../divider/index.mjs'; import '../../chat/index.mjs'; import '../../progress/index.mjs'; import '../../upload/index.mjs'; import '../../vTree/index.mjs'; import '../../table/index.mjs'; import '../../tabs/index.mjs'; import '../../menu/index.mjs'; import '../../steps/index.mjs'; import '../../header/index.mjs'; import '../../breadcrumble/index.mjs'; import '../../datePicker/index.mjs'; import '../../tooltip/index.mjs'; import '../../popover/index.mjs'; import '../index.mjs'; import '../../select/index.mjs'; import '../../collapse/index.mjs'; import '../../card/index.mjs'; import '../../timeline/index.mjs'; import '../../tag/index.mjs'; import '../../result/index.mjs'; import '../../sender/index.mjs'; import { format, setHours, setMinutes, setSeconds, addHours, subHours } from 'date-fns'; import { Clock } from 'song-ui-pro-icon'; import { useNamespace } from '../../../hook/use-namespace/index.mjs'; import '../../../hook/use-zindex/index.mjs'; var DateTime = /* @__PURE__ */ defineComponent({ name: "x-time-picker", props: { modelValue: { type: [String, Array], default: "" }, placeholder: { type: String, default: "\u8BF7\u9009\u62E9\u65F6\u95F4" }, format: { type: String, default: "HH:mm:ss" }, disabled: { type: Boolean, default: false }, readonly: { type: Boolean, default: false }, clearable: { type: Boolean, default: true }, range: { type: Boolean, default: false }, startPlaceholder: { type: String, default: "\u5F00\u59CB\u65F6\u95F4" }, endPlaceholder: { type: String, default: "\u7ED3\u675F\u65F6\u95F4" } }, setup(props, { emit }) { const ns = useNamespace("time-picker"); const visible = ref(false); const displayValue = ref(""); const currentTime = ref(props.modelValue ? new Date(props.modelValue) : /* @__PURE__ */ new Date()); const rangeState = ref({ startTime: null, endTime: null }); if (props.range && Array.isArray(props.modelValue) && props.modelValue.length === 2) { rangeState.value.startTime = new Date(props.modelValue[0]); rangeState.value.endTime = new Date(props.modelValue[1]); displayValue.value = `${formatTime(rangeState.value.startTime)} \u81F3 ${formatTime(rangeState.value.endTime)}`; } const hours = computed(() => { const hours2 = []; for (let i = 0; i < 24; i++) { hours2.push({ value: i, label: i.toString().padStart(2, "0"), isSelected: (position) => isSelectedHour(i, position) }); } return hours2; }); const minutes = computed(() => { const minutes2 = []; for (let i = 0; i < 60; i++) { minutes2.push({ value: i, label: i.toString().padStart(2, "0"), isSelected: (position) => isSelectedMinute(i, position) }); } return minutes2; }); const seconds = computed(() => { const seconds2 = []; for (let i = 0; i < 60; i++) { seconds2.push({ value: i, label: i.toString().padStart(2, "0"), isSelected: (position) => isSelectedSecond(i, position) }); } return seconds2; }); const isSelectedHour = (hour, position) => { if (props.range) { if (position === "left") { return hour === (rangeState.value.startTime ? rangeState.value.startTime.getHours() : null); } else if (position === "right") { return hour === (rangeState.value.endTime ? rangeState.value.endTime.getHours() : null); } } return hour === currentTime.value.getHours(); }; const isSelectedMinute = (minute, position) => { if (props.range) { if (position === "left") { return minute === (rangeState.value.startTime ? rangeState.value.startTime.getMinutes() : null); } else if (position === "right") { return minute === (rangeState.value.endTime ? rangeState.value.endTime.getMinutes() : null); } } return minute === currentTime.value.getMinutes(); }; const isSelectedSecond = (second, position) => { if (props.range) { if (position === "left") { return second === (rangeState.value.startTime ? rangeState.value.startTime.getSeconds() : null); } else if (position === "right") { return second === (rangeState.value.endTime ? rangeState.value.endTime.getSeconds() : null); } } return second === currentTime.value.getSeconds(); }; const formatTime = (time) => { return format(time, props.format); }; const showPanel = () => { if (props.disabled || props.readonly) return; visible.value = true; }; const handleClear = () => { emit("update:modelValue", props.range ? [] : ""); emit("change", props.range ? [] : ""); displayValue.value = ""; if (props.range) { rangeState.value.startTime = null; rangeState.value.endTime = null; rangeState.value.selecting = false; } }; const selectTime = (type, value, position) => { let newTime; if (props.range) { const baseTime = position === "left" ? rangeState.value.startTime || /* @__PURE__ */ new Date() : rangeState.value.endTime || /* @__PURE__ */ new Date(); if (type === "hour") { newTime = setHours(baseTime, value); } else if (type === "minute") { newTime = setMinutes(baseTime, value); } else if (type === "second") { newTime = setSeconds(baseTime, value); } if (position === "left") { rangeState.value.startTime = newTime; if (!rangeState.value.endTime) { rangeState.value.endTime = addHours(newTime, 1); } } else if (position === "right") { rangeState.value.endTime = newTime; if (!rangeState.value.startTime) { rangeState.value.startTime = subHours(newTime, 1); } } } else { newTime = currentTime.value; if (type === "hour") { newTime = setHours(newTime, value); } else if (type === "minute") { newTime = setMinutes(newTime, value); } else if (type === "second") { newTime = setSeconds(newTime, value); } currentTime.value = newTime; const formattedTime = formatTime(newTime); console.log("formattedTime", formattedTime); displayValue.value = formattedTime; } }; const generateUniqueId = () => { return `time-picker-${Math.random().toString(36).substr(2, 9)}`; }; const uniqueId = ref(generateUniqueId()); const handleClickOutside = (e) => { const root = e.currentTarget; const panel = root.querySelector(".x-time-picker__panel"); const input = root.querySelector(".x-time-picker__input"); if (panel && !panel.contains(e.target) && !input.contains(e.target)) { visible.value = false; } }; onMounted(() => { const root = document.querySelector(`[data-id="${uniqueId.value}"]`); if (root) { root.addEventListener("click", handleClickOutside); } }); onUnmounted(() => { const root = document.querySelector(`[data-id="${uniqueId.value}"]`); if (root) { root.removeEventListener("click", handleClickOutside); } }); const handleConfirm = () => { if (props.range) { if (rangeState.value.startTime && rangeState.value.endTime) { const startFormatted = formatTime(rangeState.value.startTime); const endFormatted = formatTime(rangeState.value.endTime); emit("update:modelValue", [startFormatted, endFormatted]); emit("change", [startFormatted, endFormatted]); displayValue.value = `${startFormatted} \u81F3 ${endFormatted}`; } } else { const formattedTime = formatTime(currentTime.value); emit("update:modelValue", formattedTime); emit("change", formattedTime); displayValue.value = formattedTime; } visible.value = false; }; const hanleCondel = () => { visible.value = false; if (props.range) { rangeState.value.startTime = null; rangeState.value.endTime = null; rangeState.value.selecting = false; } emit("update:modelValue", props.range ? [] : ""); emit("change", props.range ? [] : ""); displayValue.value = ""; }; return () => createVNode("div", { "data-id": uniqueId.value, "class": ns.b() }, [createVNode("div", { "class": [ns.e("input"), ns.is("range", props.range)], "onClick": showPanel }, [createVNode(XInput, { "modelValue": displayValue.value, "placeholder": props.range ? `${props.startPlaceholder} \u81F3 ${props.endPlaceholder}` : props.placeholder, "disabled": props.disabled, "readonly": props.readonly, "clearance": props.clearable, "onClear": handleClear }, { prepend: () => createVNode(XIcon, null, { default: () => [createVNode(Clock, null, null)] }) })]), visible.value && createVNode("div", { "class": [ns.e("panel"), props.range ? ns.m("panel", "range") : ""] }, [props.range && createVNode("div", { "class": ns.e("panel-left") }, [createVNode("div", { "class": ns.e("time-columns") }, [createVNode("div", { "class": ns.e("column") }, [createVNode("div", { "class": ns.e("column-header") }, [createTextVNode("\u65F6")]), createVNode("div", { "class": ns.e("column-content") }, [hours.value.map((hour) => createVNode("span", { "key": hour.value, "class": [ns.e("cell"), ns.is("selected", hour.isSelected("left"))], "onClick": () => selectTime("hour", hour.value, "left") }, [hour.label]))])]), createVNode("div", { "class": ns.e("column") }, [createVNode("div", { "class": ns.e("column-header") }, [createTextVNode("\u5206")]), createVNode("div", { "class": ns.e("column-content") }, [minutes.value.map((minute) => createVNode("span", { "key": minute.value, "class": [ns.e("cell"), ns.is("selected", minute.isSelected("left"))], "onClick": () => selectTime("minute", minute.value, "left") }, [minute.label]))])]), createVNode("div", { "class": ns.e("column") }, [createVNode("div", { "class": ns.e("column-header") }, [createTextVNode("\u79D2")]), createVNode("div", { "class": ns.e("column-content") }, [seconds.value.map((second) => createVNode("span", { "key": second.value, "class": [ns.e("cell"), ns.is("selected", second.isSelected("left"))], "onClick": () => selectTime("second", second.value, "left") }, [second.label]))])])])]), props.range && createVNode("div", { "class": ns.e("panel-right") }, [createVNode("div", { "class": ns.e("time-columns") }, [createVNode("div", { "class": ns.e("column") }, [createVNode("div", { "class": ns.e("column-header") }, [createTextVNode("\u65F6")]), createVNode("div", { "class": ns.e("column-content") }, [hours.value.map((hour) => createVNode("span", { "key": hour.value, "class": [ns.e("cell"), ns.is("selected", hour.isSelected("right"))], "onClick": () => selectTime("hour", hour.value, "right") }, [hour.label]))])]), createVNode("div", { "class": ns.e("column") }, [createVNode("div", { "class": ns.e("column-header") }, [createTextVNode("\u5206")]), createVNode("div", { "class": ns.e("column-content") }, [minutes.value.map((minute) => createVNode("span", { "key": minute.value, "class": [ns.e("cell"), ns.is("selected", minute.isSelected("right"))], "onClick": () => selectTime("minute", minute.value, "right") }, [minute.label]))])]), createVNode("div", { "class": ns.e("column") }, [createVNode("div", { "class": ns.e("column-header") }, [createTextVNode("\u79D2")]), createVNode("div", { "class": ns.e("column-content") }, [seconds.value.map((second) => createVNode("span", { "key": second.value, "class": [ns.e("cell"), ns.is("selected", second.isSelected("right"))], "onClick": () => selectTime("second", second.value, "right") }, [second.label]))])])]), createVNode("div", { "class": ns.e("bottom") }, [createVNode(resolveComponent("x-button"), { "size": "small", "type": "primary", "onClick": handleConfirm }, { default: () => [createTextVNode("\u786E\u5B9A")] }), createVNode(resolveComponent("x-button"), { "size": "small", "onClick": hanleCondel }, { default: () => [createTextVNode("\u53D6\u6D88")] })])]), !props.range && createVNode("div", { "class": ns.e("time-columns") }, [createVNode("div", { "class": ns.e("column") }, [createVNode("div", { "class": ns.e("column-header") }, [createTextVNode("\u65F6")]), createVNode("div", { "class": ns.e("column-content") }, [hours.value.map((hour) => createVNode("span", { "key": hour.value, "class": [ns.e("cell"), ns.is("selected", hour.isSelected())], "onClick": () => selectTime("hour", hour.value) }, [hour.label]))])]), createVNode("div", { "class": ns.e("column") }, [createVNode("div", { "class": ns.e("column-header") }, [createTextVNode("\u5206")]), createVNode("div", { "class": ns.e("column-content") }, [minutes.value.map((minute) => createVNode("span", { "key": minute.value, "class": [ns.e("cell"), ns.is("selected", minute.isSelected())], "onClick": () => selectTime("minute", minute.value) }, [minute.label]))])]), createVNode("div", { "class": ns.e("column") }, [createVNode("div", { "class": ns.e("column-header") }, [createTextVNode("\u79D2")]), createVNode("div", { "class": ns.e("column-content") }, [seconds.value.map((second) => createVNode("span", { "key": second.value, "class": [ns.e("cell"), ns.is("selected", second.isSelected())], "onClick": () => selectTime("second", second.value) }, [second.label]))])])]), !props.range && createVNode("div", { "class": ns.e("bottom") }, [createVNode(resolveComponent("x-button"), { "size": "small", "type": "primary", "onClick": handleConfirm }, { default: () => [createTextVNode("\u786E\u5B9A")] }), createVNode(resolveComponent("x-button"), { "size": "small", "onClick": hanleCondel }, { default: () => [createTextVNode("\u53D6\u6D88")] })])])]); } }); export { DateTime as default }; //# sourceMappingURL=index.mjs.map