仿element时间选择器 选择周范围
最近需求出现 周维度选择范围,常用的element不支持周类型 下面是写了一个dome供大家参考
组件库用到moment 处理时间 element【popover】 语言vue2
组件库用到moment 处理时间 element【popover】 语言vue2
<el-popover placement="bottom" width="650" @show="popoverShow" @hide="hide" ref="popoverRef" trigger="click"> <div class="picker-box"> <div class="picker-top"><div @click="minusYear"><i class="el-icon-arrow-left"></i> </div> <div>{{ year }}</div><div @click="addYear"><i class="el-icon-arrow-right"></i></div></div> <div class="picker-content"> <!-- oneState? 选中的第一个: highlight ? 选中的中间高亮 : 无--> <div @click="selectWeeks(item)" @mouseenter="handleMouseEnter(item)" v-for="(item, index) in weeksData" :class="item.oneState || item.twoState ? 'one-state-box' : item.highlight ? 'highlight-box' :''" :key="index" class="weeks-block"> <!-- item.isCurrent ? 当前周高亮 : 其他周 --> <span :class=" item.isCurrent ? 'current-week' : ''">第{{ item.weekNumber }}周 <br> {{ item.start }}~{{ item.end }} </span> </div> </div> </div> <div slot="reference" class="popover-slot-box"> <i class="el-icon-date" style="line-height: 34px;"></i> <div style="width: 130px; text-align: center;">{{ value1[0] ? $moment(value1[0].startState).format('YYYY-MM-DD') + '第' + value1[0].weekNumber + '周' : '开始日期' }}</div><span style="color: 303133;">至</span><div style="width: 130px; text-align: center;">{{ value1[1] ? $moment(value1[1].endState).format('YYYY-MM-DD') + '第' + value1[1].weekNumber + '周' : '结束日期' }}</div> </div> </el-popover>
<script> export default { data () { return { year: moment().format("YYYY"), // 当前年份 value1: [], // 存储选中的日期 weeksData: [], // 存储页面展示 周 } }, created() { // 根据年份 获取到所有的周 this.getAllWeeksOfYear(this.year) }, methods: { // 减一年 minusYear() { // 对年份进行减1 this.year = moment(this.year).add(-1, 'y').format("YYYY") // 获取减去年 所有的周 this.getAllWeeksOfYear(this.year) // 公共方法 处理高亮问题 选择跨年数据 需要用到 this.HighlightFunc() }, // 加一年 addYear() { // 对年份进行减 加1 this.year = moment(this.year).add(1, 'y').format("YYYY") // 获取增加年 所有的周 this.getAllWeeksOfYear(this.year) // 公共方法 处理高亮问题 选择跨年数据 需要用到 this.HighlightFunc() }, // 获取全年周 getAllWeeksOfYear(year) { const currentMoment = moment(); // 获取的年份 const weeks = []; const totalWeeks = moment().year(year).isoWeeksInYear(); // 全年周数 for (let week = 1; week <= totalWeeks; week++) { const start = moment().year(year).isoWeek(week).startOf('isoWeek'); const end = moment().year(year).isoWeek(week).endOf('isoWeek'); // 判断当前周(精确到日期范围) const isCurrent = currentMoment.isBetween(start, end, null, '[]'); weeks.push({ weekNumber: week, start: start.format('MM-DD'), end: end.format('MM-DD'), startState: start.format('YYYY-MM-DD'), endState: end.format('YYYY-MM-DD'), oneState: false, // 首次点击 twoState: false, // 二次点击 highlight: false, // 是否高亮 isCurrent: isCurrent // 是否是当前周 }); } this.weeksData = weeks }, // 选择数据 selectWeeks(item) { // 已经满足了 日期选择 再次选择做重置 处理 if (this.value1.length == 2) { this.value1 = [] this.weeksData.forEach((item) => { item.oneState = false item.twoState = false item.highlight = false }) } // 默认push 数据 this.value1.push(item) // 根据长度进行判断 1 还是 2 if (this.value1.length == 1) { item.oneState = true } if (this.value1.length == 2) { item.twoState = true } // 长度等于2 等于已经选择完成 if (this.value1.length == 2) { return this.$refs.popoverRef.doClose() } }, // 找到 开始高亮结尾高亮 HighlightFunc() { this.weeksData.forEach((item) => { if (this.value1[0].startState == item.startState) { item.oneState = true } if (this.value1[1].startState == item.startState) { item.twoState = true } }) if (this.value1.length == 2) { // 高亮 中间块 进行高亮 this.handleMouseEnter(this.value1[1], true) } }, // 鼠标移入 handleMouseEnter(row, state = false) { if (this.value1.length == 1 || state) { let startState = this.value1[0].startState this.weeksData.forEach((item) => { // 进项判断 大于 小于 根据我的启示日期 进行判断 if (startState <= row.startState) { if ((startState <= item.startState) && item.startState <= row.startState) { item.highlight = true } else { item.highlight = false } } // 进项判断 大于 小于 根据我的启示日期 进行判断 if (startState >= row.startState) { if ((startState >= item.startState) && item.startState >= row.startState) { item.highlight = true } else { item.highlight = false } } }) } // console.log('鼠标移入',e , item); }, // 检测关闭是否选择完整 hide() { if (this.value1.length != 2) { this.value1 = [] // 赋值自己的默认值 } }, // 周数据框 展开 popoverShow() { if (this.value1.length == 2) { // 处理默认高亮 this.HighlightFunc() } }, } } </script>
.popover-slot-box { border: 1px solid #dcdfe6; color: #c0c4cc; display: flex; width: 350px; height: 36px; line-height: 36px; padding: 0 10px; box-sizing: border-box; font-size: 13px; } .picker-box { color: #606266; .picker-top { display: flex; justify-content: space-between; } .picker-content { display: flex; flex-wrap: wrap; .current-week { color: #409eff; font-weight: 700; } .one-state-box { background: #409eff; color: #fff !important; } .highlight-box { background: #f2f6fc; } .weeks-block { font-size: 12px; width: 81px; height: 40px; text-align: center; cursor: pointer; padding-top: 5px; box-sizing: border-box; } .weeks-block:hover { color: #409eff; } } }
本文来自博客园,作者:樱桃树下的约定,转载请注明原文链接:https://www.cnblogs.com/tcyweb/p/18727322

浙公网安备 33010602011771号