uniapp、小程序自定义选择日、周、月、季、年的时间选择器组件

小程序 0

目录

代码分享

utils文件

uniapp使用插件使用

zdp-date-picker使用说明


本组件用到了uni-ui的uni-popup弹窗组件

废话不多说直接上代码

代码分享

<template>	<view class="content-pop">		<uni-popup ref="popup" type="bottom">		<view class="zdp-pop">			<view class="top-cont">				<view class="close-cont" @click="close(1)">					取消				</view>				<!-- 可以自定义显示 -->				<slot name="text" :scope="{range,zdpdate}">					<view class="text-info">						请选择时间						<view>							{{selInfo}}						</view>					</view>				</slot>				<view class="save-cont" @click="close(2)">					确认				</view>			</view>			<view class="tabs-cont">				<view class="tab-list" v-for="item in tabs" :class="item.value==activeIdx?'active':''"					@click="handleTabs(item.value)">					{{item.label}}				</view>			</view>			<view class="date-cont">				<picker-view :value="value" @change="handleChange" class="picker-view">					<picker-view-column v-for="obj in SelArr">						<view class="item" v-for="(item,index) in obj.child" :key="index">{{item}}{{obj.value}}						</view>					</picker-view-column>				</picker-view>			</view>		</view>		</uni-popup>	</view></template><script>	import {		whichWeek	} from '../../utils/getWeek.js'	import {		getMonthStartEnd	} from '../../utils/getMonth.js'	import {		getQuarterDates	} from '../../utils/getQuarter.js'	export default {		props: {			type: {				type: String,				default: '日',				validator(value, props) {					return ['日', '月', '周', '年', '季'].includes(value)				}			},			time: {				type: String, //'2024-1-1' '2024-2' '2024-2' '2024-2' '2024			}		},		data() {			return {				tabs: [{						label: '日',						value: '日'					},					{						label: '周',						value: '周',					},					{						label: '月',						value: '月',					},					{						label: '季',						value: '季',					},					{						label: '年',						value: '年',					}				],				activeIdx: '日',				value: [], //选择的值,要设置默认值				dateArr: [],				day: 18,				week: 1,				month: 1, //				quarter: 2,				years: 24,				SelArr: [],				range: '',				zdpdate: ''			}		},		computed: {			selInfo() {				let str = ''				let {					activeIdx,					years,					day,					month,					week,					quarter				} = this				if (activeIdx == '日') {					str = `20${years}年 ${month<10?'0'+month:month}月 ${day}日`				} else if (activeIdx == '周') {					str = `20${years}年 第${week}周`				} else if (activeIdx == '月') {					str = `20${years}年 ${month<10?'0'+month:month}月`				} else if (activeIdx == '季') {					str = `20${years}年 ${quarter}季`				} else if (activeIdx == '年') {					str = `20${years}年`				}				return str			}		},		created() {		},		methods: {			// 			handleProps() {				let arr = []				arr = this.time.split('-')				if (this.type == '日') {					this.month = arr[1] - 0					this.day = arr[2] - 0				} else if (this.type == '周') {					this.week = arr[1] - 0				} else if (this.type == '季') {					this.quarter = arr[1] - 0				} else if (this.type == '月') {					this.month = arr[1] - 0					this.quarter = this.handleQuarter(this.month)				}				for (let i = 0; i < arr.length; i++) {					if (i == 0) {						arr[0] = arr[0].slice(2)						arr[0] -= 0						this.years = arr[0]					} else {						arr[i]--					}				}				this.value = arr			},			// 初始化			newDate() {				// this.activeIdx=this.type				const date = new Date()				this.day = date.getDate()				this.years = date.getFullYear()				this.week = this.getYearWeek(date)				this.quarter = this.handleQuarter(this.month)				this.month = date.getMonth() + 1				this.handleTabs(this.type)				if (this.time) {					this.handleProps()				}				this.initArr()			},			initArr() {				const date = new Date()				let arr = []				let {					activeIdx,				} = this				let day = []				let week = []				let month = []				let quarter = []				let years = []				for (let i = 2000; i <= date.getFullYear(); i++) {					years.push(i)				}				for (let i = 1; i <= 12; i++) {					month.push(i)				}				let weekArr = whichWeek(`20${this.years}`)				for (let i = 1; i <= weekArr.length; i++) {					week.push(i)				}				for (let i = 1; i <= 4; i++) {					quarter.push(i)				}				if (activeIdx == '日') {					let num = this.getMonthDays(this.years, this.month)					for (let i = 1; i <= num; i++) {						day.push(i)					}					arr = [{						value: "年",						child: years					}, {						value: "月",						child: month					}, {						value: "日",						child: day					}]					this.zdpdate = `20${this.years}-${this.month<10?'0'+this.month:this.month}-${this.day}`					this.range = `20${this.years}-${this.month<10?'0'+this.month:this.month}-${this.day}`				} else if (activeIdx == '月') {					arr = [{						value: "年",						child: years					}, {						value: "月",						child: month					}]					// console.log(this.years,'年22');					this.zdpdate = `20${this.years}-${this.month<10?'0'+this.month:this.month}`					this.range = getMonthStartEnd(this.zdpdate)				} else if (activeIdx == '年') {					arr = [{						value: "年",						child: years					}]					this.zdpdate = `20${this.years}`					this.range = `20${this.years}-1-31/20${this.years}-12-31`				} else if (activeIdx == '周') {					arr = [{						value: "年",						child: years					}, {						value: "周",						child: week					}]					this.zdpdate = `20${this.years}年 第${this.week}周`					let wk = weekArr[this.week - 1]					this.range = `${wk.year}-${wk.month}-${wk.date}` + '/' +						`${wk.last.year}-${wk.last.month}-${wk.last.date}`				} else if (activeIdx == '季') {					arr = [{						value: "年",						child: years					}, {						value: "季度",						child: quarter					}]					this.zdpdate = `20${this.years}年 ${this.quarter}季度`					let obj = getQuarterDates(`20${this.years}`, this.quarter)					this.range = obj.startDate + '/' + obj.endDate				}				this.SelArr = arr			},			open() {				this.newDate()				this.$refs.popup.open('bottom')			},			close(num) {				if (num == 1) {					this.newDate()					this.handleEmit()				} else {					this.handleEmit()				}				this.$refs.popup.close()			},			handleEmit() {				let {					zdpdate,					range,				} = this				this.$emit('submit-date', {					zdpdate,					range,					type: this.activeIdx				})			},			handleTabs(val) {				this.activeIdx = val				let {					activeIdx,					years,					month,					day,					quarter,					week				} = this				if (activeIdx == '日') {					this.value = [years, month - 1, day - 1]				} else if (activeIdx == '周') {					this.value = [years, week - 1]				} else if (activeIdx == '月') {					this.value = [years, month - 1]				} else if (activeIdx == '季') {					this.value = [years, quarter - 1, ]				} else if (activeIdx == '年') {					this.value = [years]				}				console.log(this.value, '选择的日期');				this.initArr()			},			// 选择器选择			handleChange(e) {				let {					value				} = e.detail				let {					activeIdx				} = this				console.log(value);				// 年小于前面+0				if (value[0] < 10) {					value[0] = '0' + value[0]				}				this.years = value[0]				if (activeIdx == '日') {					this.month = value[1] + 1 //月					this.day = value[2] + 1 //日				} else if (activeIdx == '周') {					this.week = value[1] + 1 //周				} else if (activeIdx == '季') {					this.quarter = value[1] + 1				} else if (activeIdx == '月') {					this.month = value[1] + 1 //月				}				this.initArr()			},			//获取当前月的天数			getMonthDays(year, month) {				var thisDate = new Date(year, month, 0);				return thisDate.getDate();			},			getYearWeek(endDate) {				//本年的第一天				let beginDate = new Date(endDate.getFullYear(), 0, 1);				//星期从0-6,0代表星期天,6代表星期六				let endWeek = endDate.getDay();				if (endWeek == 0) endWeek = 7;				let beginWeek = beginDate.getDay();				if (beginWeek == 0) beginWeek = 7;				//计算两个日期的天数差				let millisDiff = endDate.getTime() - beginDate.getTime();				let dayDiff = Math.floor((millisDiff + (beginWeek - endWeek) * (24 * 60 * 60 * 1000)) / 86400000);				return Math.ceil(dayDiff / 7) + 1;			},			handleQuarter(month) {				const oneQuarter = [1, 2, 3]				const twoQuarter = [4, 5, 6]				const threeQuarter = [7, 8, 9]				let num				if (oneQuarter.includes(month)) {					num = 1				} else if (twoQuarter.includes(month)) {					num = 2				} else if (threeQuarter.includes(month)) {					num = 3				} else {					num = 4				}				return num			}		}	}</script><style lang="scss" scoped>	* {		box-sizing: border-box;	}	.zdp-pop {		box-sizing: border-box;		padding: 24rpx;		width: 100%;		height: 750rpx;		background-color: #fff;		.top-cont {			height: 100rpx;			display: flex;			justify-content: space-between;			align-items: center;			margin-bottom: 32rpx;			.close-cont {				color: #aaa;				letter-spacing: 6rpx;			}			.text-info {				display: flex;				flex-direction: column;				align-items: center;			}			.save-cont {				background: #409EFF;				color: #fff;				width: 100rpx;				height: 60rpx;				text-align: center;				line-height: 60rpx;				border-radius: 6rpx;			}		}		.tabs-cont {			box-sizing: border-box;			height: 80rpx;			background-color: #F3F5F9;			display: flex;			align-items: center;			border-radius: 4rpx;			padding: 0 10rpx;			.tab-list {				min-width: 20%;				display: flex;				height: 60%;				flex: 1;				justify-content: center;				border-radius: 4rpx;				&.active {					background-color: #fff;				}			}		}		.date-cont {			height: calc(750rpx - 180rpx);			.picker-view {				width: 100%;				height: 100%;				.item {					display: flex;					justify-content: center;					align-items: center;				}				.uni-picker-view-indicator {					height: 100rpx;				}			}		}	}	</style>

utils文件

@/utils/getMonth.js
//获取这个月的月初和月末export function getMonthStartEnd(vars){  var str = '';  if(vars!=null&&vars!=''){    var nyYear=vars.slice(0,4);    var nyMonth=vars.slice(5,vars.length);    var firstDay = new Date(nyYear,nyMonth-1);    var lastDay = new Date(new Date(nyYear,nyMonth).valueOf()-60*60*1000*24);    function datasFormat(d){      var datetime=d.getFullYear() + '-' + (d.getMonth() + 1) + '-' + d.getDate();      return datetime;    }    str = datasFormat(firstDay) + "/" + datasFormat(lastDay)  }  return str}
@/utils/getQuarter.js
export function getQuarterDates(year, quarter) {	const startDate = new Date(year, (quarter - 1) * 3, 1);	const endDate = new Date(year, quarter * 3, 0);	const startDay = startDate.getDate();	const endDay = endDate.getDate();	const startMonth = startDate.getMonth() + 1;	const endMonth = endDate.getMonth() + 1;	const startYear = startDate.getFullYear();	const endYear = endDate.getFullYear();	const startDateString =		`${startYear}-${startMonth < 10 ? '0' + startMonth : startMonth}-${startDay < 10 ? '0' + startDay : startDay}`;	const endDateString =		`${endYear}-${endMonth < 10 ? '0' + endMonth : endMonth}-${endDay < 10 ? '0' + endDay : endDay}`;	return {		startDate: startDateString,		endDate: endDateString	};}// // 示例用法:计算2024年第2季度的起止日期// const quarterDates = getQuarterDates(2024,2);// console.log(quarterDates.startDate); // 输出:2024-04-01// console.log(quarterDates.endDate);   // 输出:2024-06-30
@/utils/getWeek.js
//时间戳转年月日  参数是秒的时间戳 函数返回一个对象 对象里有年 月 日export function yearDay(long){  var time = new Date(long * 1000)  var year = time.getFullYear();  var month = (time.getMonth()+1) < 10 ? '0' + (time.getMonth()+1) : (time.getMonth()+1);  var date = time.getDate() < 10 ? '0' + time.getDate() : time.getDate() ;  var yearday = {year,month,date}  return yearday}//计算一年中的每一周都是从几号到几号//第一周为1月1日到 本年的 第一个周日//第二周为 本年的 第一个周一 往后推到周日//以此类推 再往后推52周。。。//如果最后一周在12月31日之前,则本年有垮了54周,反之53周//12月31 日不论是周几,都算为本周的最后一天//参数年份 ,函数返回一个数组,数组里的对象包含 这一周的开始日期和结束日期export function whichWeek(year){  var d = new Date(year, 0, 1);  while (d.getDay() != 1) {    d.setDate(d.getDate() + 1);  }  let arr = []  let longnum = d.setDate(d.getDate())  if(longnum > +new Date(year, 0, 1)){    let obj = yearDay(+new Date(year, 0, 1) / 1000)    obj.last = yearDay( longnum / 1000 - 86400)    arr.push(obj)  }  let oneitem = yearDay(longnum / 1000)  oneitem.last = yearDay( longnum / 1000 + 86400 * 6)  arr.push(oneitem)  var lastStr  for(var i = 0 ; i<51 ;i++){    let long = d.setDate(d.getDate() + 7)    let obj = yearDay( long / 1000)    obj.last = yearDay( long / 1000 + 86400 * 6)    lastStr = long + 86400000 * 6    arr.push(obj)  }  if(lastStr < +new Date(year + 1, 0, 1)){            let obj = yearDay(lastStr / 1000 + 86400)    obj.last = yearDay(+new Date(year + 1, 0, 1) / 1000 - 86400)    arr.push(obj)  }else{    arr[arr.length-1].last = yearDay(+new Date(year + 1, 0, 1) / 1000 - 86400)  }  return arr}// //例如 2012 年就跨了54周,也有很多是53周的// let week2012 = whichWeek(2012)// console.log(week2012)// //调用完得到的是一个数组见下图

uniapp使用插件使用

https://ext.dcloud.net.cn/plugin?id=16387icon-default.png?t=N7T8https://ext.dcloud.net.cn/plugin?id=16387

zdp-date-picker使用说明

<zdp-date-picker ref="zdpdate" type="月" time="2023-2" @submit-date="handleDate($event)"></zdp-date-picker>

  • 属性参数说明:

ref用于控制picker的弹出与隐藏,组件内有open和close函数

this.$refs.zdpdate.open()
参数名作用类型默认值
type控制打开piker时tabs默认显示的位置String
time显示的默认日期String2023-1

type用于控制打开piker时显示的tabs;默认参数:日、周、月、季、年

time用于控制显示的默认日期;

type=“日” time="2024-1-23" 代表默认显示日、time代表选中日期2024年1月23日

type=“周” time=“2024-4” 代表默认显示周、time代表选中日期2024年第4周

type=“月” time=“2024-1” 代表默认显示月、time代表选中日期2024年1月

type=“季” time=“2024-1” 代表默认显示季、time代表选中日期2024年第1季度

type=“年” time=“2024” 代表默认显示年、time代表选中日期2024

  • 事件返回参数说明:
事件名作用
submit-date用于接收组件返回的时间

submit-date 用于接收组件返回的时间

range 是选中日期的时间范围

zdpdate是具体的固定日期

type 是选中日期类型 日、周、月、季、年

handleDate(e){    let {range,zdpdate,type}=e    this.range=range    this.zdpdate=zdpdate    this.type=type}
  • 自定义插槽:

自定义显示组件内文本内容:

<zdp-date-picker ref="zdpdate" :type="type" time="2024-3"      @submit-date="handleDate($event)">	<template #text="{scope}">		{{scope.range}}		{{scope.zdpdate}}	</template></zdp-date-picker>

也许您对下面的内容还感兴趣: