🌀(component): 重新定义 input-number 尺寸

This commit is contained in:
就眠儀式 2022-07-15 13:34:38 +08:00
parent c6b6f5c0a7
commit 750ad79210
13 changed files with 425 additions and 229 deletions

View File

@ -2,16 +2,39 @@
<div class="layui-laydate"> <div class="layui-laydate">
<div class="layui-laydate-main laydate-main-list-0"> <div class="layui-laydate-main laydate-main-list-0">
<div class="layui-laydate-header"> <div class="layui-laydate-header">
<i class="layui-icon laydate-icon laydate-prev-y" @click="changeYearOrMonth('year', -1)"></i> <i
<i class="layui-icon laydate-icon laydate-prev-m" @click="changeYearOrMonth('month', -1)"></i> class="layui-icon laydate-icon laydate-prev-y"
@click="changeYearOrMonth('year', -1)"
></i
>
<i
class="layui-icon laydate-icon laydate-prev-m"
@click="changeYearOrMonth('month', -1)"
></i
>
<div class="laydate-set-ym"> <div class="laydate-set-ym">
<span @click="datePicker.showPanel.value = 'year'">{{ datePicker.currentYear.value }} </span> <span @click="datePicker.showPanel.value = 'year'"
<span @click="datePicker.showPanel.value = 'month'">{{ datePicker.currentMonth.value + 1 }} </span> >{{ datePicker.currentYear.value }} </span
>
<span @click="datePicker.showPanel.value = 'month'"
>{{ datePicker.currentMonth.value + 1 }} </span
>
</div> </div>
<i class="layui-icon laydate-icon laydate-next-m" @click="changeYearOrMonth('month', 1)"></i> <i
<i class="layui-icon laydate-icon laydate-next-y" @click="changeYearOrMonth('year', 1)"></i> class="layui-icon laydate-icon laydate-next-m"
@click="changeYearOrMonth('month', 1)"
></i
>
<i
class="layui-icon laydate-icon laydate-next-y"
@click="changeYearOrMonth('year', 1)"
></i
>
</div> </div>
<DateContent :date-list="datePicker.dateList" v-model="datePicker.currentDay.value"></DateContent> <DateContent
:date-list="datePicker.dateList"
v-model="datePicker.currentDay.value"
></DateContent>
<PanelFoot></PanelFoot> <PanelFoot></PanelFoot>
</div> </div>
</div> </div>
@ -22,19 +45,22 @@ export default {
}; };
</script> </script>
<script lang="ts" setup> <script lang="ts" setup>
import { computed, inject, ref, watch } from 'vue'; import { computed, inject, ref, watch } from "vue";
import { provideType } from '../interface'; import { provideType } from "../interface";
import { setDateList } from '../day'; import { setDateList } from "../day";
import PanelFoot from './PanelFoot.vue' import PanelFoot from "./PanelFoot.vue";
import DateContent from './components/DateContent.vue' import DateContent from "./components/DateContent.vue";
const datePicker: provideType = inject('datePicker') as provideType; const datePicker: provideType = inject("datePicker") as provideType;
// , // ,
watch( watch(
[datePicker.currentYear, datePicker.currentMonth], [datePicker.currentYear, datePicker.currentMonth],
() => { () => {
datePicker.dateList.value = setDateList(datePicker.currentYear.value, datePicker.currentMonth.value); datePicker.dateList.value = setDateList(
datePicker.currentYear.value,
datePicker.currentMonth.value
);
}, },
{ immediate: true } { immediate: true }
); );
@ -55,6 +81,4 @@ const changeYearOrMonth = (type: "year" | "month", num: number) => {
datePicker.currentMonth.value = month; datePicker.currentMonth.value = month;
} }
}; };
</script> </script>

View File

@ -2,19 +2,34 @@
<div class="layui-laydate"> <div class="layui-laydate">
<div class="layui-laydate-main laydate-main-list-0 laydate-ym-show"> <div class="layui-laydate-main laydate-main-list-0 laydate-ym-show">
<div class="layui-laydate-header"> <div class="layui-laydate-header">
<i class="layui-icon laydate-icon laydate-prev-y" @click="changeYearOrMonth('year', -1)"></i> <i
class="layui-icon laydate-icon laydate-prev-y"
@click="changeYearOrMonth('year', -1)"
></i
>
<div class="laydate-set-ym"> <div class="laydate-set-ym">
<span @click="datePicker.showPanel.value = 'month'">{{ datePicker.currentMonth.value + 1 }} </span> <span @click="datePicker.showPanel.value = 'month'"
>{{ datePicker.currentMonth.value + 1 }} </span
>
</div> </div>
<i class="layui-icon laydate-icon laydate-next-y" @click="changeYearOrMonth('year', 1)"></i> <i
class="layui-icon laydate-icon laydate-next-y"
@click="changeYearOrMonth('year', 1)"
></i
>
</div> </div>
</div> </div>
<div class="layui-laydate-content" style="height: 220px"> <div class="layui-laydate-content" style="height: 220px">
<ul class="layui-laydate-list laydate-month-list"> <ul class="layui-laydate-list laydate-month-list">
<li v-for="item of MONTH_NAME" :key="item" <li
:class="{ 'layui-this': MONTH_NAME.indexOf(item) === datePicker.currentMonth.value }" v-for="item of MONTH_NAME"
@click="handleMonthClick(item)"> :key="item"
:class="{
'layui-this':
MONTH_NAME.indexOf(item) === datePicker.currentMonth.value,
}"
@click="handleMonthClick(item)"
>
{{ item.slice(0, 3) }} {{ item.slice(0, 3) }}
</li> </li>
</ul> </ul>
@ -28,12 +43,11 @@ export default {
}; };
</script> </script>
<script lang="ts" setup> <script lang="ts" setup>
import dayjs from 'dayjs'; import dayjs from "dayjs";
import { inject } from 'vue'; import { inject } from "vue";
import { provideType } from '../interface'; import { provideType } from "../interface";
import PanelFoot from './PanelFoot.vue' import PanelFoot from "./PanelFoot.vue";
const datePicker: provideType = inject('datePicker') as provideType; const datePicker: provideType = inject("datePicker") as provideType;
const MONTH_NAME = [ const MONTH_NAME = [
"1月", "1月",

View File

@ -1,36 +1,91 @@
<template> <template>
<div class="layui-laydate-footer"> <div class="layui-laydate-footer">
<span v-if="datePicker.type === 'datetime' && datePicker.showPanel.value === 'datetime'" @click="chooseTime" <span
class="laydate-btns-time">选择时间</span> v-if="
datePicker.type === 'datetime' &&
datePicker.showPanel.value === 'datetime'
"
@click="chooseTime"
class="laydate-btns-time"
>选择时间</span
>
<span v-else-if="datePicker.type === 'datetime' && datePicker.showPanel.value === 'time'" <span
@click="datePicker.showPanel.value = 'datetime'" class="laydate-btns-time">选择日期</span> v-else-if="
datePicker.type === 'datetime' && datePicker.showPanel.value === 'time'
"
@click="datePicker.showPanel.value = 'datetime'"
class="laydate-btns-time"
>选择日期</span
>
<span v-else-if="datePicker.type === 'yearmonth' && datePicker.showPanel.value === 'year'" <span
@click="datePicker.showPanel.value = 'month'" class="laydate-btns-time">选择月份</span> v-else-if="
<span v-else-if="datePicker.type === 'yearmonth' && datePicker.showPanel.value === 'month'" datePicker.type === 'yearmonth' && datePicker.showPanel.value === 'year'
@click="datePicker.showPanel.value = 'year'" class="laydate-btns-time">选择年份</span> "
@click="datePicker.showPanel.value = 'month'"
class="laydate-btns-time"
>选择月份</span
>
<span
v-else-if="
datePicker.type === 'yearmonth' &&
datePicker.showPanel.value === 'month'
"
@click="datePicker.showPanel.value = 'year'"
class="laydate-btns-time"
>选择年份</span
>
<span v-else-if="!datePicker.range" class="layui-laydate-preview" title="当前选中的结果"> <span
<template v-if="datePicker.type === 'month' && datePicker.currentMonth.value != -1"> v-else-if="!datePicker.range"
class="layui-laydate-preview"
title="当前选中的结果"
>
<template
v-if="
datePicker.type === 'month' && datePicker.currentMonth.value != -1
"
>
{{ datePicker.currentMonth.value + 1 }} {{ datePicker.currentMonth.value + 1 }}
</template> </template>
<template v-else-if="datePicker.type === 'year' && datePicker.currentYear.value != -1"> <template
v-else-if="
datePicker.type === 'year' && datePicker.currentYear.value != -1
"
>
{{ datePicker.currentYear.value }} {{ datePicker.currentYear.value }}
</template> </template>
<template v-else-if="datePicker.type === 'time'"> <template v-else-if="datePicker.type === 'time'">
{{ {{
(datePicker.hms.value.hh < 10 ? '0' : '') + datePicker.hms.value.hh +':'+ (datePicker.hms.value.hh < 10 ? "0" : "") +
(datePicker.hms.value.mm < 10 ? '0' : '') + datePicker.hms.value.mm +':'+ datePicker.hms.value.hh +
(datePicker.hms.value.ss < 10 ? '0' : '') + datePicker.hms.value.ss ":" +
(datePicker.hms.value.mm < 10 ? "0" : "") +
datePicker.hms.value.mm +
":" +
(datePicker.hms.value.ss < 10 ? "0" : "") +
datePicker.hms.value.ss
}} }}
</template> </template>
</span> </span>
<div class="laydate-footer-btns"> <div class="laydate-footer-btns">
<span lay-type="clear" class="laydate-btns-clear" @click="datePicker.clear()">清空</span> <span
<span lay-type="now" class="laydate-btns-now" @click="datePicker.now()">现在</span> lay-type="clear"
<span lay-type="confirm" class="laydate-btns-confirm" @click="datePicker.ok()">确定</span> class="laydate-btns-clear"
@click="datePicker.clear()"
>清空</span
>
<span lay-type="now" class="laydate-btns-now" @click="datePicker.now()"
>现在</span
>
<span
lay-type="confirm"
class="laydate-btns-confirm"
@click="datePicker.ok()"
>确定</span
>
</div> </div>
</div> </div>
</template> </template>
@ -40,16 +95,20 @@ export default {
}; };
</script> </script>
<script lang="ts" setup> <script lang="ts" setup>
import { inject } from 'vue'; import { inject } from "vue";
import { provideType } from '../interface'; import { provideType } from "../interface";
const datePicker: provideType = inject("datePicker") as provideType;
const datePicker: provideType = inject('datePicker') as provideType; const emits = defineEmits([
const emits = defineEmits(['showYearPanel', 'update:showPanel', 'scrollToCurrentTime', 'ok']); "showYearPanel",
"update:showPanel",
"scrollToCurrentTime",
"ok",
]);
// //
const chooseTime = () => { const chooseTime = () => {
datePicker.showPanel.value = 'time' datePicker.showPanel.value = "time";
//scrollToCurrentTime() //scrollToCurrentTime()
} };
</script> </script>

View File

@ -8,15 +8,27 @@
</div> </div>
<div class="layui-laydate-content" style="height: 210px"> <div class="layui-laydate-content" style="height: 210px">
<ul class="layui-laydate-list laydate-time-list" ref="timePanelRef"> <ul class="layui-laydate-list laydate-time-list" ref="timePanelRef">
<li class="num-list" v-for="item in els" :key="item.type" :data-type="item.type"> <li
class="num-list"
v-for="item in els"
:key="item.type"
:data-type="item.type"
>
<ol class="scroll" @click="choseTime"> <ol class="scroll" @click="choseTime">
<li v-for="(it, index) in item.count" :id="item.type + index.toString()" <li
:data-value="index.toString().padStart(2, '0')" :data-type="item.type" :key="it" :class="[ v-for="(it, index) in item.count"
:id="item.type + index.toString()"
:data-value="index.toString().padStart(2, '0')"
:data-type="item.type"
:key="it"
:class="[
'num', 'num',
index.toString().padStart(2, '0') == datePicker.hms.value[item.type] index.toString().padStart(2, '0') ==
datePicker.hms.value[item.type]
? 'layui-this' ? 'layui-this'
: '', : '',
]"> ]"
>
{{ index.toString().padStart(2, "0") }} {{ index.toString().padStart(2, "0") }}
</li> </li>
</ol> </ol>
@ -33,10 +45,10 @@ export default {
}; };
</script> </script>
<script lang="ts" setup> <script lang="ts" setup>
import { inject, onMounted, ref, nextTick, watch } from 'vue'; import { inject, onMounted, ref, nextTick, watch } from "vue";
import { provideType } from '../interface'; import { provideType } from "../interface";
import PanelFoot from './PanelFoot.vue' import PanelFoot from "./PanelFoot.vue";
const datePicker: provideType = inject('datePicker') as provideType; const datePicker: provideType = inject("datePicker") as provideType;
const els = [ const els = [
{ count: 24, type: "hh" }, { count: 24, type: "hh" },
{ count: 60, type: "mm" }, { count: 60, type: "mm" },
@ -54,15 +66,18 @@ const choseTime = (e: any) => {
unWatch.value = false; unWatch.value = false;
}, 0); }, 0);
}; };
const unWatch = ref(false) const unWatch = ref(false);
const timePanelRef = ref() const timePanelRef = ref();
onMounted(() => { onMounted(() => {
scrollTo(); scrollTo();
}) });
watch([datePicker.hms], () => { watch(
if (!unWatch.value) [datePicker.hms],
scrollTo(); () => {
}, { deep: true }) if (!unWatch.value) scrollTo();
},
{ deep: true }
);
const scrollTo = () => { const scrollTo = () => {
nextTick(() => { nextTick(() => {
timePanelRef.value.childNodes.forEach((element: HTMLElement) => { timePanelRef.value.childNodes.forEach((element: HTMLElement) => {
@ -76,13 +91,15 @@ const scrollTo = () => {
continue; continue;
} }
if (child.classList && child.classList.contains("layui-this")) { if (child.classList && child.classList.contains("layui-this")) {
scrollTop = child.offsetTop - (parentDom.offsetHeight - child.offsetHeight) / 2; scrollTop =
child.offsetTop -
(parentDom.offsetHeight - child.offsetHeight) / 2;
parentDom.scrollTo(0, scrollTop); parentDom.scrollTo(0, scrollTop);
break; break;
} }
} }
} }
}); });
}) });
} };
</script> </script>

View File

@ -7,10 +7,19 @@
</div> </div>
</div> </div>
</div> </div>
<div class="layui-laydate-content" style="height: 220px; overflow-y: auto" ref="ScrollRef"> <div
class="layui-laydate-content"
style="height: 220px; overflow-y: auto"
ref="ScrollRef"
>
<ul class="layui-laydate-list laydate-year-list"> <ul class="layui-laydate-list laydate-year-list">
<li v-for="item of datePicker.yearList.value" :key="item" <li
:class="{ 'layui-this': datePicker.currentYear.value === item }" @click="handleYearClick(item)">{{ item }} v-for="item of datePicker.yearList.value"
:key="item"
:class="{ 'layui-this': datePicker.currentYear.value === item }"
@click="handleYearClick(item)"
>
{{ item }}
</li> </li>
</ul> </ul>
</div> </div>
@ -23,12 +32,12 @@ export default {
}; };
</script> </script>
<script lang="ts" setup> <script lang="ts" setup>
import dayjs from 'dayjs'; import dayjs from "dayjs";
import { inject, nextTick, onMounted, ref, watch } from 'vue'; import { inject, nextTick, onMounted, ref, watch } from "vue";
import { provideType } from '../interface'; import { provideType } from "../interface";
import PanelFoot from './PanelFoot.vue' import PanelFoot from "./PanelFoot.vue";
const datePicker: provideType = inject('datePicker') as provideType; const datePicker: provideType = inject("datePicker") as provideType;
const unWatch = ref(false) const unWatch = ref(false);
// //
const handleYearClick = (item: any) => { const handleYearClick = (item: any) => {
unWatch.value = true; unWatch.value = true;
@ -49,21 +58,22 @@ const handleYearClick = (item: any) => {
const ScrollRef = ref(); const ScrollRef = ref();
onMounted(() => { onMounted(() => {
scrollTo(); scrollTo();
}) });
watch([datePicker.currentYear], () => { watch([datePicker.currentYear], () => {
if (!unWatch.value) if (!unWatch.value) scrollTo();
scrollTo(); });
})
const scrollTo = () => { const scrollTo = () => {
nextTick(() => { nextTick(() => {
let scrollTop = 0; let scrollTop = 0;
for (const child of ScrollRef.value.firstElementChild.childNodes) { for (const child of ScrollRef.value.firstElementChild.childNodes) {
if (child.classList && child.classList.contains('layui-this')) { if (child.classList && child.classList.contains("layui-this")) {
scrollTop = child.offsetTop - (ScrollRef.value.offsetHeight - child.offsetHeight) / 2; scrollTop =
child.offsetTop -
(ScrollRef.value.offsetHeight - child.offsetHeight) / 2;
break; break;
} }
} }
ScrollRef.value.scrollTo(0, scrollTop) ScrollRef.value.scrollTo(0, scrollTop);
}) });
} };
</script> </script>

View File

@ -7,18 +7,31 @@
</tr> </tr>
</thead> </thead>
<tbody> <tbody>
<template v-for="(o, i) of dateList.value.length % 7 == 0 <template
v-for="(o, i) of dateList.value.length % 7 == 0
? dateList.value.length / 7 ? dateList.value.length / 7
: Math.floor(dateList.value.length / 7) + 1" :key="i"> : Math.floor(dateList.value.length / 7) + 1"
:key="i"
>
<tr> <tr>
<td v-for="(item, index) of dateList.value.slice( <td
i * 7, v-for="(item, index) of dateList.value.slice(i * 7, i * 7 + 7)"
i * 7 + 7 :key="index"
)" :key="index" :data-unix="item.value" :class="{ :data-unix="item.value"
:class="{
'laydate-day-prev': item.type !== 'current', 'laydate-day-prev': item.type !== 'current',
'layui-this': item.value === modelValue || (datePicker.range && (item.value == parseInt(datePicker.rangeValue.value.first) || item.value == parseInt(datePicker.rangeValue.value.last))), 'layui-this':
item.value === modelValue ||
(datePicker.range &&
(item.value ==
parseInt(datePicker.rangeValue.value.first) ||
item.value ==
parseInt(datePicker.rangeValue.value.last))),
'laydate-range-hover': ifHasRangeHoverClass(item), 'laydate-range-hover': ifHasRangeHoverClass(item),
}" @click="handleDayClick(item)" @mouseenter="dayItemMouseEnter($event, item)"> }"
@click="handleDayClick(item)"
@mouseenter="dayItemMouseEnter($event, item)"
>
{{ item.day }} {{ item.day }}
</td> </td>
</tr> </tr>
@ -32,21 +45,22 @@ export default {
name: "DateContent", name: "DateContent",
}; };
</script> </script>
<script lang="ts" setup>import { computed, inject, ref, Ref } from 'vue'; <script lang="ts" setup>
import { provideType } from '../../interface'; import { computed, inject, ref, Ref } from "vue";
import { provideType } from "../../interface";
export interface LayDatePickerProps { export interface LayDatePickerProps {
dateList: any, dateList: any;
modelValue: number modelValue: number;
} }
const props = withDefaults(defineProps<LayDatePickerProps>(), { const props = withDefaults(defineProps<LayDatePickerProps>(), {
dateList: [], dateList: [],
modelValue:-1, modelValue: -1,
}); });
const WEEK_NAME = ["日", "一", "二", "三", "四", "五", "六"]; const WEEK_NAME = ["日", "一", "二", "三", "四", "五", "六"];
const datePicker: provideType = inject('datePicker') as provideType; const datePicker: provideType = inject("datePicker") as provideType;
const emits = defineEmits(['update:modelValue']); const emits = defineEmits(["update:modelValue"]);
// //
const handleDayClick = (item: any) => { const handleDayClick = (item: any) => {
@ -55,19 +69,31 @@ const handleDayClick = (item: any) => {
return; return;
} }
} }
emits('update:modelValue',item.value); emits("update:modelValue", item.value);
if (item.type !== "current") { if (item.type !== "current") {
datePicker.currentMonth.value = item.type === "prev" ? datePicker.currentMonth.value - 1 : datePicker.currentMonth.value + 1; datePicker.currentMonth.value =
item.type === "prev"
? datePicker.currentMonth.value - 1
: datePicker.currentMonth.value + 1;
} }
if (datePicker.range) { if (datePicker.range) {
if (datePicker.rangeValue.value.first === '' && datePicker.rangeValue.value.last === '') { if (
datePicker.rangeValue.value.first === "" &&
datePicker.rangeValue.value.last === ""
) {
//props.rangeValue.first = item.value //props.rangeValue.first = item.value
} else if (datePicker.rangeValue.value.first !== '' && datePicker.rangeValue.value.last !== '') { } else if (
datePicker.rangeValue.value.first !== "" &&
datePicker.rangeValue.value.last !== ""
) {
// rangeValue.first = item.value // rangeValue.first = item.value
// rangeValue.last = '' // rangeValue.last = ''
} else if (datePicker.rangeValue.value.first !== '' && datePicker.rangeValue.value.last === '') { } else if (
datePicker.rangeValue.value.first !== "" &&
datePicker.rangeValue.value.last === ""
) {
//rangeValue.last = item.value //rangeValue.last = item.value
} }
} }
@ -80,32 +106,43 @@ const dayItemMouseEnter = (event: MouseEvent, item: any) => {
if (!datePicker.rangeValue.value.first) { if (!datePicker.rangeValue.value.first) {
return; return;
} }
if (item.type !== 'current') { if (item.type !== "current") {
return; return;
} }
//rpropsangeValue.hover = (event.target as HTMLElement).dataset.unix as string //rpropsangeValue.hover = (event.target as HTMLElement).dataset.unix as string
} };
const ifHasRangeHoverClass = computed(() => { const ifHasRangeHoverClass = computed(() => {
return function (item: any) { return function (item: any) {
if (!datePicker.range) { if (!datePicker.range) {
return false return false;
} }
if (!datePicker.rangeValue.value.first) { if (!datePicker.rangeValue.value.first) {
return false return false;
} }
if (item.type !== 'current') { if (item.type !== "current") {
return false return false;
} }
if (item.value == parseInt(datePicker.rangeValue.value.first) || item.value == parseInt(datePicker.rangeValue.value.last)) { if (
item.value == parseInt(datePicker.rangeValue.value.first) ||
item.value == parseInt(datePicker.rangeValue.value.last)
) {
return true; return true;
} }
let hover = datePicker.rangeValue.value.last ? datePicker.rangeValue.value.last : datePicker.rangeValue.value.hover; let hover = datePicker.rangeValue.value.last
let max = datePicker.rangeValue.value.first > hover ? datePicker.rangeValue.value.first : hover; ? datePicker.rangeValue.value.last
let min = datePicker.rangeValue.value.first < hover ? datePicker.rangeValue.value.first : hover : datePicker.rangeValue.value.hover;
let max =
datePicker.rangeValue.value.first > hover
? datePicker.rangeValue.value.first
: hover;
let min =
datePicker.rangeValue.value.first < hover
? datePicker.rangeValue.value.first
: hover;
if (item.value >= parseInt(min) && item.value <= parseInt(max)) { if (item.value >= parseInt(min) && item.value <= parseInt(max)) {
return true return true;
} }
return false return false;
} };
}) });
</script> </script>

View File

@ -52,7 +52,6 @@ const getDayLength = (year: number, month: number): number => {
return new Date(year, month + 1, 0).getDate(); return new Date(year, month + 1, 0).getDate();
}; };
// 设置日期列表 // 设置日期列表
const setDateList = (year: number, month: number) => { const setDateList = (year: number, month: number) => {
const curDays = getDayLength(year, month); // 当月天数 const curDays = getDayLength(year, month); // 当月天数
@ -95,4 +94,12 @@ const setDateList = (year: number, month: number) => {
return list; return list;
}; };
export { getDayLength, getYears, getDate, getMonth, getYear,getDay,setDateList }; export {
getDayLength,
getYears,
getDate,
getMonth,
getYear,
getDay,
setDateList,
};

View File

@ -1,16 +1,26 @@
<template> <template>
<div> <div>
<lay-dropdown ref="dropdownRef" :disabled="disabled"> <lay-dropdown ref="dropdownRef" :disabled="disabled">
<lay-input readonly :name="name" :model-value="dateValue" :placeholder="placeholder" prefix-icon="layui-icon-date" <lay-input
:disabled="disabled"> readonly
:name="name"
:model-value="dateValue"
:placeholder="placeholder"
prefix-icon="layui-icon-date"
:disabled="disabled"
>
</lay-input> </lay-input>
<template #content> <template #content>
<!-- 日期选择 --> <!-- 日期选择 -->
<DatePanel v-if="!range && (showPanel === 'date' || showPanel === 'datetime')"></DatePanel> <DatePanel
v-if="!range && (showPanel === 'date' || showPanel === 'datetime')"
></DatePanel>
<!-- 时间选择 --> <!-- 时间选择 -->
<TimePanel v-if="!range && showPanel === 'time'"></TimePanel> <TimePanel v-if="!range && showPanel === 'time'"></TimePanel>
<!-- 年份选择器 --> <!-- 年份选择器 -->
<YearPanel v-if="!range && (showPanel === 'year' || showPanel === 'yearmonth')"></YearPanel> <YearPanel
v-if="!range && (showPanel === 'year' || showPanel === 'yearmonth')"
></YearPanel>
<!-- 月份选择器 --> <!-- 月份选择器 -->
<MonthPanel v-if="!range && showPanel === 'month'"></MonthPanel> <MonthPanel v-if="!range && showPanel === 'month'"></MonthPanel>
</template> </template>
@ -31,11 +41,21 @@ import { LayIcon } from "@layui/icons-vue";
import LayInput from "../input/index.vue"; import LayInput from "../input/index.vue";
import LayDropdown from "../dropdown/index.vue"; import LayDropdown from "../dropdown/index.vue";
import { getDayLength, getYears, getMonth, getYear, getDay } from "./day"; import { getDayLength, getYears, getMonth, getYear, getDay } from "./day";
import { ref, watch, computed, defineProps, defineEmits, onMounted, nextTick, reactive, provide } from "vue"; import {
import DatePanel from './components/DatePanel.vue'; ref,
import TimePanel from './components/TimePanel.vue'; watch,
import YearPanel from './components/YearPanel.vue'; computed,
import MonthPanel from './components/MonthPanel.vue'; defineProps,
defineEmits,
onMounted,
nextTick,
reactive,
provide,
} from "vue";
import DatePanel from "./components/DatePanel.vue";
import TimePanel from "./components/TimePanel.vue";
import YearPanel from "./components/YearPanel.vue";
import MonthPanel from "./components/MonthPanel.vue";
export interface LayDatePickerProps { export interface LayDatePickerProps {
type?: "date" | "datetime" | "year" | "time" | "month" | "yearmonth"; type?: "date" | "datetime" | "year" | "time" | "month" | "yearmonth";
@ -46,7 +66,7 @@ export interface LayDatePickerProps {
name?: string; name?: string;
max?: string; max?: string;
min?: string; min?: string;
range?: boolean range?: boolean;
} }
const props = withDefaults(defineProps<LayDatePickerProps>(), { const props = withDefaults(defineProps<LayDatePickerProps>(), {
@ -54,7 +74,7 @@ const props = withDefaults(defineProps<LayDatePickerProps>(), {
type: "date", type: "date",
disabled: false, disabled: false,
simple: false, simple: false,
range: false range: false,
}); });
const dropdownRef = ref(null); const dropdownRef = ref(null);
@ -75,15 +95,17 @@ const dateListNext = ref<any[]>([]);
const showPanel = ref("date"); const showPanel = ref("date");
// //
const rangeValue = reactive({ const rangeValue = reactive({
first: '', last: '', hover: '' first: "",
}) last: "",
hover: "",
});
watch( watch(
() => props.type, () => props.type,
() => { () => {
showPanel.value = props.type; showPanel.value = props.type;
if (props.type === 'yearmonth') { if (props.type === "yearmonth") {
showPanel.value = 'year'; showPanel.value = "year";
} }
}, },
{ immediate: true } { immediate: true }
@ -98,17 +120,18 @@ onMounted(() => {
}, 0); }, 0);
} }
let modelValue = props.modelValue; let modelValue = props.modelValue;
if (modelValue.length === 8) { //dayjs if (modelValue.length === 8) {
modelValue = '1970-01-01 ' + modelValue; //dayjs
modelValue = "1970-01-01 " + modelValue;
} }
hms.value.hh = dayjs(modelValue).hour(); hms.value.hh = dayjs(modelValue).hour();
hms.value.mm = dayjs(modelValue).minute(); hms.value.mm = dayjs(modelValue).minute();
hms.value.ss = dayjs(modelValue).second(); hms.value.ss = dayjs(modelValue).second();
getDateValue() getDateValue();
}); });
// //
const dateValue = ref('') const dateValue = ref("");
const getDateValue = (checkCurrentDay = true) => { const getDateValue = (checkCurrentDay = true) => {
if (checkCurrentDay) { if (checkCurrentDay) {
if (currentDay.value === -1) { if (currentDay.value === -1) {
@ -157,18 +180,18 @@ const getDateValue = (checkCurrentDay = true) => {
// //
const ok = () => { const ok = () => {
if (props.type === 'time') { if (props.type === "time") {
getDateValue(false) getDateValue(false);
} else { } else {
getDateValue() getDateValue();
} }
if (dropdownRef.value) if (dropdownRef.value)
// @ts-ignore // @ts-ignore
dropdownRef.value.hide(); dropdownRef.value.hide();
if (props.type === 'yearmonth') { if (props.type === "yearmonth") {
showPanel.value = 'year'; showPanel.value = "year";
} else if (props.type === 'datetime') { } else if (props.type === "datetime") {
showPanel.value = 'datetime'; showPanel.value = "datetime";
} }
}; };
@ -180,23 +203,20 @@ const now = () => {
hms.value.hh = dayjs().hour(); hms.value.hh = dayjs().hour();
hms.value.mm = dayjs().minute(); hms.value.mm = dayjs().minute();
hms.value.ss = dayjs().second(); hms.value.ss = dayjs().second();
if (props.simple) if (props.simple) getDateValue(true);
getDateValue(true)
}; };
// //
const clear = () => { const clear = () => {
currentDay.value = -1; currentDay.value = -1;
if (showPanel.value === 'year') if (showPanel.value === "year") currentYear.value = -1;
currentYear.value = -1; if (showPanel.value === "month") currentMonth.value = -1;
if (showPanel.value === 'month') if (showPanel.value === "time") {
currentMonth.value = -1; hms.value.hh = 0;
if (showPanel.value === 'time') { hms.value.mm = 0;
hms.value.hh = 0 hms.value.ss = 0;
hms.value.mm = 0
hms.value.ss = 0
} }
getDateValue(true) getDateValue(true);
}; };
//simple //simple
@ -205,21 +225,21 @@ watch(currentDay, () => {
getDateValue(); getDateValue();
ok(); ok();
} }
}) });
watch(currentMonth, () => { watch(currentMonth, () => {
if (props.simple && props.type !== 'date') { if (props.simple && props.type !== "date") {
getDateValue(); getDateValue();
ok(); ok();
} }
}) });
watch(currentYear, () => { watch(currentYear, () => {
if (props.simple && props.type !== 'date') { if (props.simple && props.type !== "date") {
getDateValue(); getDateValue();
ok(); ok();
} }
}) });
provide('datePicker', { provide("datePicker", {
currentYear: currentYear, currentYear: currentYear,
currentMonth: currentMonth, currentMonth: currentMonth,
currentDay: currentDay, currentDay: currentDay,
@ -234,6 +254,6 @@ provide('datePicker', {
ok: () => ok(), ok: () => ok(),
getDateValue: () => getDateValue, getDateValue: () => getDateValue,
range: props.range, range: props.range,
rangeValue: rangeValue rangeValue: rangeValue,
}); });
</script> </script>

View File

@ -2,19 +2,19 @@ import { Ref } from "vue";
export type DatePickerType = "date" | "datetime" | "year" | "time" | "month"; export type DatePickerType = "date" | "datetime" | "year" | "time" | "month";
export type provideType={ export type provideType = {
currentYear:Ref, currentYear: Ref;
currentMonth:Ref, currentMonth: Ref;
currentDay:Ref, currentDay: Ref;
dateValue:Ref, dateValue: Ref;
dateList:Ref, dateList: Ref;
yearList:Ref, yearList: Ref;
hms:Ref, hms: Ref;
type:string, type: string;
showPanel:Ref, showPanel: Ref;
clear:Function, clear: Function;
now:Function, now: Function;
ok:Function, ok: Function;
range:boolean, range: boolean;
rangeValue:Ref rangeValue: Ref;
} };

View File

@ -15,7 +15,7 @@ export interface LayInputProps {
type?: string; type?: string;
prefixIcon?: string; prefixIcon?: string;
suffixIcon?: string; suffixIcon?: string;
modelValue?: string; modelValue?: string | number;
allowClear?: boolean; allowClear?: boolean;
autocomplete?: string; autocomplete?: string;
placeholder?: string; placeholder?: string;
@ -96,9 +96,7 @@ const classes = computed(() => {
</script> </script>
<template> <template>
<div <div class="layui-input">
class="layui-input"
>
<div class="layui-input-prepend" v-if="slots.prepend"> <div class="layui-input-prepend" v-if="slots.prepend">
<slot name="prepend"></slot> <slot name="prepend"></slot>
</div> </div>

View File

@ -3,41 +3,46 @@
@border-color: #eee; @border-color: #eee;
@hover-border-color: var(--global-primary-color); @hover-border-color: var(--global-primary-color);
@lg: 40px; @lg: 44px;
@lg-wdith: 200px; @lg-wdith: 200px;
@lg-right: 20px; @lg-right: 22px;
@md: 32px; @md: 38px;
@md-wdith: 160px; @md-wdith: 160px;
@md-right: 16px; @md-right: 19px;
@sm: 28px; @sm: 32px;
@sm-wdith: 140px; @sm-wdith: 140px;
@sm-right: 14px; @sm-right: 16px;
@xs: 24px; @xs: 26px;
@xs-wdith: 120px; @xs-wdith: 120px;
@xs-right: 12px; @xs-right: 13px;
.set-size(@width, @size, @right-size) { .set-size(@width, @size, @right-size) {
& { & {
height: @size; height: @size;
width: @width; width: @width;
.layui-input { .layui-input {
height: @size; height: @size;
line-height: @size; line-height: @size;
padding: 0 @size; padding: 0 @size;
} }
.layui-control-btn { .layui-control-btn {
width: @size; width: @size;
height: @size; height: @size;
line-height: @size; line-height: @size;
} }
&[position="right"] { &[position="right"] {
.layui-input { .layui-input {
padding: 0 @size 0 0; padding: 0 @size 0 0;
} }
.layui-control-btn { .layui-control-btn {
height: @right-size; height: @right-size;
line-height: @right-size; line-height: @right-size;
} }
.layui-subtraction-btn { .layui-subtraction-btn {
top: @right-size - 1; top: @right-size - 1;
} }
@ -45,6 +50,10 @@
} }
} }
.layui-input-number + .layui-input-number {
margin-left: 10px;
}
.layui-input-number { .layui-input-number {
position: relative; position: relative;
display: inline-block; display: inline-block;
@ -53,14 +62,15 @@
border-color: @border-color; border-color: @border-color;
border-radius: var(--global-border-radius); border-radius: var(--global-border-radius);
overflow: hidden; overflow: hidden;
.set-size(@lg-wdith, @lg, @lg-right);
margin-left: 5px;
.layui-input-wrapper {
border: 0;
.layui-input { .layui-input {
border: 0;
input {
text-align: center; text-align: center;
} }
} }
.layui-control-btn { .layui-control-btn {
position: absolute; position: absolute;
box-sizing: border-box; box-sizing: border-box;
@ -71,28 +81,31 @@
padding: 0; padding: 0;
text-align: center; text-align: center;
top: 0; top: 0;
&:hover { &:hover {
color: @hover-border-color; color: @hover-border-color;
} }
&.layui-subtraction-btn { &.layui-subtraction-btn {
border-right-width: 1px; border-right-width: 1px;
} }
&.layui-addition-btn { &.layui-addition-btn {
border-left-width: 1px; border-left-width: 1px;
right: 0; right: 0;
} }
.layui-icon { .layui-icon {
padding: 0px; padding: 0px;
} }
} }
/* google */
input.layui-input::-webkit-outer-spin-button, .layui-input input::-webkit-outer-spin-button,
input.layui-input::-webkit-inner-spin-button { .layui-input input::-webkit-inner-spin-button {
-webkit-appearance: none; -webkit-appearance: none;
} }
/* firefox */ .layui-input input[type="number"] {
input.layui-input[type="number"] {
-moz-appearance: textfield; -moz-appearance: textfield;
} }
@ -102,19 +115,21 @@
border-right-width: 0px; border-right-width: 0px;
border-left-width: 1px; border-left-width: 1px;
} }
.layui-addition-btn { .layui-addition-btn {
border-bottom-width: 1px; border-bottom-width: 1px;
} }
} }
&[size="md"] { &[size="lg"] {
.set-size(@md-wdith,@md, @md-right); .set-size(@lg-wdith, @lg, @lg-right);
}
&[size="md"] {
.set-size(@md-wdith, @md, @md-right);
} }
&[size="sm"] { &[size="sm"] {
.set-size(@sm-wdith, @sm, @sm-right); .set-size(@sm-wdith, @sm, @sm-right);
} }
&[size="xs"] { &[size="xs"] {
.set-size(@xs-wdith, @xs, @xs-right); .set-size(@xs-wdith, @xs, @xs-right);
} }

View File

@ -20,7 +20,7 @@ export interface LayInputNumberProps {
position?: "right"; position?: "right";
min?: number; min?: number;
max?: number; max?: number;
size?: "md" | "sm" | "xs"; size?: "lg" | "md" | "sm" | "xs";
} }
const props = withDefaults(defineProps<LayInputNumberProps>(), { const props = withDefaults(defineProps<LayInputNumberProps>(), {
@ -30,6 +30,7 @@ const props = withDefaults(defineProps<LayInputNumberProps>(), {
step: 1, step: 1,
min: -Infinity, min: -Infinity,
max: Infinity, max: Infinity,
size: "md",
}); });
const emit = defineEmits(["update:modelValue", "change"]); const emit = defineEmits(["update:modelValue", "change"]);

View File

@ -41,17 +41,11 @@
<template> <template>
<div> <div>
<div> <div>
<lay-input-number></lay-input-number> <lay-input-number size="lg"></lay-input-number>
<lay-input-number size="md"></lay-input-number> <lay-input-number size="md"></lay-input-number>
<lay-input-number size="sm"></lay-input-number> <lay-input-number size="sm"></lay-input-number>
<lay-input-number size="xs"></lay-input-number> <lay-input-number size="xs"></lay-input-number>
</div> </div>
<div>
<lay-input-number position="right"></lay-input-number>
<lay-input-number position="right" size="md"></lay-input-number>
<lay-input-number position="right" size="sm"></lay-input-number>
<lay-input-number position="right" size="xs"></lay-input-number>
</div>
</div> </div>
</template> </template>